diff --git a/README.txt b/README.txt index f968102ef384cc36dca958da8b7af7de2ddc54a0..725d0e27e71e6c18bc209d3721942d84eabe5a45 100644 --- a/README.txt +++ b/README.txt @@ -1,117 +1,117 @@ -Readme ------- -This module allows users to put each other on a personal 'Buddy List'. - -Features include buddy groups and the ability to track your buddies' recent posts. - -Send comments to Robert Douglass at: http://drupal.org/user/5449/contact - - -Requirements ------------- -This module requires Drupal 4.7. - -This module does not yet offer PostgreSQL support. If you would like to contribute to this module by creating the appropriate PostgreSQL schema, please submit your code at http://drupal.org/project/issues/buddylist - - -Upgrading from 4.6 ------------------- -WARNING: There is currently no migration path from 4.6 to 4.7. There are significant database schema changes and the 4.7 module will not work with the 4.6 schema. A migration path is forthcoming. If you need one sooner, contact me: http://drupal.org/user/5449/contact - - -Installation ------------- -1. Copy the buddylist.module to the Drupal modules/ directory. - -2. Enable buddy list in the "site settings | modules" administration screen. - - Enabling the buddylist module will trigger the creation of the database schema. If you are shown error messages you may have to create the schema by hand. Please see the database definition at the end of this file. - -3. Enable buddy list blocks you want in the "blocks" administration screen. - -4. Optionally add the following theme function to your PHPTemplate's template.php file: - -function phptemplate_username($object) { - global $user; - /* Use the default theme_username for anonymous users, nodes by this user */ - if ($user->uid == 0 || $object->uid == $user->uid || $object->uid == 0) { - return theme_username($object); - } - if (!user_access('maintain buddy list')) { - return theme_username($object); - } - - /* an array, keyed on buddy uids */ - $buddies = buddylist_get_buddies($user->uid); - /* Find out if this buddy is in the user's buddy list */ - foreach ($buddies as $buddyuid => $buddystructure) { - if ($buddyuid == $object->uid) { - $output .= theme_username($object); - $output .= " ("; - $output .= theme('remove_from_buddylist_link', $object); - $output .= ")"; - return $output; - } - } - /* The user is not in the buddylist, give a link to add */ - $output .= theme_username($object); - $output .= " ("; - $output .= theme('add_to_buddylist_link', $object); - $output .= ")"; - return $output; -} - - -Database Schema ---------------- -If the automatic creation of the database tables was unsuccessful you can try creating the tables by hand using the following SQL: - -CREATE TABLE `buddylist` ( - `uid` int(10) unsigned NOT NULL default '0', - `buddy` int(10) unsigned NOT NULL default '0', - `timestamp` int(11) NOT NULL default '0', - `received` tinyint(1) NOT NULL default '0', - UNIQUE KEY `uid-buddy-label` (`uid`,`buddy`), - KEY `uid` (`uid`) -) TYPE=MyISAM /*!40100 DEFAULT CHARACTER SET utf8 */; - --- --- Table structure for table `buddylist_buddy_group` --- - -CREATE TABLE `buddylist_buddy_group` ( - `uid` int(11) NOT NULL default '0', - `buddy` int(11) NOT NULL default '0', - `label_id` int(11) NOT NULL default '0', - PRIMARY KEY (`uid`,`buddy`,`label_id`) -) TYPE=MyISAM /*!40100 DEFAULT CHARACTER SET utf8 */; - --- --- Table structure for table `buddylist_groups` --- - -CREATE TABLE `buddylist_groups` ( - `uid` int(11) NOT NULL default '0', - `label_id` int(11) NOT NULL default '0', - `label` varchar(255) NOT NULL default '', - `visible` tinyint(1) NOT NULL default '0', - PRIMARY KEY (`uid`,`label_id`) -) TYPE=MyISAM /*!40100 DEFAULT CHARACTER SET utf8 */; - - -Credits -------- -Written by Adrian Rossouw. -Thanks to Ratko Kovacina for the comments/debugging info -Browsing improvements by Doug Sikora - -Maintainer: Robert Douglass -Status: maintained (Feb. 2006) - -TODO ----- -1. PGSQL schema (see buddylist.install, buddylist_install()) -2. Rework texts so that one is not stuck with "buddy" but could choose "contact", for example -3. Make a workflow whereby a buddy request is sent to the buddy for confirmation which is required before the buddy can be added. -4. Make the notification that someone added you to their buddylist use the privatemsg module, if available. +Readme +------ +This module allows users to put each other on a personal 'Buddy List'. + +Features include buddy groups and the ability to track your buddies' recent posts. + +Send comments to Robert Douglass at: http://drupal.org/user/5449/contact + + +Requirements +------------ +This module requires Drupal 4.7. + +This module does not yet offer PostgreSQL support. If you would like to contribute to this module by creating the appropriate PostgreSQL schema, please submit your code at http://drupal.org/project/issues/buddylist + + +Upgrading from 4.6 +------------------ +WARNING: There is currently no migration path from 4.6 to 4.7. There are significant database schema changes and the 4.7 module will not work with the 4.6 schema. A migration path is forthcoming. If you need one sooner, contact me: http://drupal.org/user/5449/contact + + +Installation +------------ +1. Copy the buddylist.module to the Drupal modules/ directory. + +2. Enable buddy list in the "site settings | modules" administration screen. + + Enabling the buddylist module will trigger the creation of the database schema. If you are shown error messages you may have to create the schema by hand. Please see the database definition at the end of this file. + +3. Enable buddy list blocks you want in the "blocks" administration screen. + +4. Optionally add the following theme function to your PHPTemplate's template.php file: + +function phptemplate_username($object) { + global $user; + /* Use the default theme_username for anonymous users, nodes by this user */ + if ($user->uid == 0 || $object->uid == $user->uid || $object->uid == 0) { + return theme_username($object); + } + if (!user_access('maintain buddy list')) { + return theme_username($object); + } + + /* an array, keyed on buddy uids */ + $buddies = buddylist_get_buddies($user->uid); + /* Find out if this buddy is in the user's buddy list */ + foreach ($buddies as $buddyuid => $buddystructure) { + if ($buddyuid == $object->uid) { + $output .= theme_username($object); + $output .= ' ('; + $output .= theme('remove_from_buddylist_link', $object); + $output .= ')'; + return $output; + } + } + /* The user is not in the buddylist, give a link to add */ + $output .= theme_username($object); + $output .= ' ('; + $output .= theme('add_to_buddylist_link', $object); + $output .= ')'; + return $output; +} + + +Database Schema +--------------- +If the automatic creation of the database tables was unsuccessful you can try creating the tables by hand using the following SQL: + +CREATE TABLE `buddylist` ( + `uid` int(10) unsigned NOT NULL default '0', + `buddy` int(10) unsigned NOT NULL default '0', + `timestamp` int(11) NOT NULL default '0', + `received` tinyint(1) NOT NULL default '0', + UNIQUE KEY `uid-buddy-label` (`uid`,`buddy`), + KEY `uid` (`uid`) +) TYPE=MyISAM /*!40100 DEFAULT CHARACTER SET utf8 */; + +-- +-- Table structure for table `buddylist_buddy_group` +-- + +CREATE TABLE `buddylist_buddy_group` ( + `uid` int(11) NOT NULL default '0', + `buddy` int(11) NOT NULL default '0', + `label_id` int(11) NOT NULL default '0', + PRIMARY KEY (`uid`,`buddy`,`label_id`) +) TYPE=MyISAM /*!40100 DEFAULT CHARACTER SET utf8 */; + +-- +-- Table structure for table `buddylist_groups` +-- + +CREATE TABLE `buddylist_groups` ( + `uid` int(11) NOT NULL default '0', + `label_id` int(11) NOT NULL default '0', + `label` varchar(255) NOT NULL default '', + `visible` tinyint(1) NOT NULL default '0', + PRIMARY KEY (`uid`,`label_id`) +) TYPE=MyISAM /*!40100 DEFAULT CHARACTER SET utf8 */; + + +Credits +------- +Written by Adrian Rossouw. +Thanks to Ratko Kovacina for the comments/debugging info +Browsing improvements by Doug Sikora + +Maintainer: Robert Douglass +Status: maintained (Feb. 2006) + +TODO +---- +1. PGSQL schema (see buddylist.install, buddylist_install()) +2. Rework texts so that one is not stuck with "buddy" but could choose "contact", for example +3. Make a workflow whereby a buddy request is sent to the buddy for confirmation which is required before the buddy can be added. +4. Make the notification that someone added you to their buddylist use the privatemsg module, if available. 5. Consider possible Views module integration. \ No newline at end of file diff --git a/buddylist.module b/buddylist.module index 6d7281ad105dc258015c8f3a9a1f5cc2130058e4..4d01040e288d31f279aee27202beb9708ca59941 100644 --- a/buddylist.module +++ b/buddylist.module @@ -20,7 +20,7 @@ function buddylist_help($section) {
  • administer the buddy list block at administer » settings » buddylist
  • -

    For more information, read the configuration and customization handbook Buddylist page

    ", +

    For more information, read the configuration and customization handbook Buddylist page

    ", array('%Userprofiles' => url('profile'), '%setaccesspermissions' => url('admin/access/permission'), '%blockadministration' => url('admin/block'), @@ -61,9 +61,9 @@ function buddylist_menu($may_cache) { // RSS feeds $links[] = array('path' => 'buddylist/'. $id .'/buddies/recent/feed', 'title' => t('xml feed'), 'access' => user_access('view buddy lists'), 'callback' => 'buddylist_buddyfeed', 'type' => MENU_CALLBACK, 'callback arguments' => array($id)); // other callbacks - $links[] = array('path' => 'buddy/add', 'title' => t('add to buddylist'), 'access' => user_access('maintain buddy list'), 'callback' => 'buddylist_addbuddy', 'callback arguments' => arg(2), 'type' => MENU_CALLBACK); - $links[] = array('path' => 'buddy/delete', 'title' => t('delete from buddylist'), 'access' => user_access('maintain buddy list'), 'callback' => 'buddylist_deletebuddy', 'callback arguments' => arg(2), 'type' => MENU_CALLBACK); - } + $links[] = array('path' => 'buddy/add', 'title' => t('add to buddylist'), 'access' => user_access('maintain buddy list'), 'callback' => 'buddylist_addbuddy', 'callback arguments' => array(arg(2)), 'type' => MENU_CALLBACK); + $links[] = array('path' => 'buddy/delete', 'title' => t('delete from buddylist'), 'access' => user_access('maintain buddy list'), 'callback' => 'buddylist_deletebuddy', 'callback arguments' => array(arg(2)), 'type' => MENU_CALLBACK); + } return $links; } @@ -106,7 +106,7 @@ function buddylist_settings() { '#maxlength' => 128, '#description' => t('This will be the title for the recent buddies post block. If none is specified, "My buddies\' recent posts" will be used.'), ); - + // User profile page settings $form['profile_settings'] = array( '#type' => 'fieldset', @@ -130,6 +130,7 @@ function buddylist_settings() { function buddylist_user($type, &$edit, &$thisuser, $category = NULL) { global $user; + $output = array(); // show any buddylist notifications upon login and upon viewing own profile if (user_access('view buddy lists') && (($type == 'login') || ($type == 'view') && ($thisuser->uid == $user->uid))) { buddylist_setmsg_received($thisuser); @@ -207,10 +208,10 @@ function buddylist_block($op = 'list', $delta = 0) { } } - + $block['content'] = theme('user_list', $users); $block['subject'] = variable_get('buddylist_list_block_title', t('My buddy list')); - + // check if a "more" link should generated by seeing if there are more buddies than the specified $upperlimit if (count($buddies) > variable_get('buddylist_blocklisting_size', 5)) { $block['content'] .= ''; @@ -304,9 +305,9 @@ function buddylist_get_buddies($uid = NULL, $key = 'uid') { } if (!isset($buddies[$key][$uid])) { $buddies[$key][$uid] = array(); - $sql = "SELECT b.buddy, u.name, u.mail FROM {buddylist} b - INNER JOIN {users} u ON b.buddy = u.uid - WHERE b.uid = %d"; + $sql = 'SELECT b.buddy, u.name, u.mail FROM {buddylist} b + INNER JOIN {users} u ON b.buddy = u.uid + WHERE b.uid = %d'; $result = db_query($sql, $uid); while ($row = db_fetch_object($result)) { $buddies[$key][$uid][$row->buddy]['name'] = $row->name; @@ -343,7 +344,7 @@ function buddylist_setmsg_received($thisuser) { } /** - * expose add and remove links to theming. + * expose add and remove links to theming. */ function theme_remove_from_buddylist_link($buddyuser) { return l(t('Remove %name from my buddy list', array('%name' => theme('placeholder', $buddyuser->name))), 'buddy/delete/' . $buddyuser->uid, NULL, drupal_get_destination(), NULL, FALSE, TRUE); @@ -430,7 +431,7 @@ function buddylist_buddiesrecent_page($uid) { $output .= drupal_get_form('buddies_recent', $form); $output .= theme('xml_icon', url('buddylist/'. $uid .'/buddies/recent/feed')); drupal_set_html_head(''); - + return $output; } @@ -439,17 +440,17 @@ function buddylist_buddiesgroups_page($uid) { drupal_set_title(t('%username\'s buddy groups', array('%username' => $thisuser->name))); $headers = array(t('buddy'), t('# of buddies'), t("buddy's posts")); - + $result = db_query('SELECT DISTINCT(label), label_id FROM {buddylist_groups} WHERE uid = %d ORDER BY label ASC', $thisuser->uid); $groups = array(); while ($row = db_fetch_object($result)) { $groups[$row->label_id] = $row->label; } - + if (count($groups) == 0) { drupal_set_message(t("You don't have any groups defined. To organize your buddies into groups, visit the %edit_groups page", array('%edit_groups' => l(t('edit_groups'), "buddylist/$uid/buddies/groups/edit")))); } - + $buddies = buddylist_get_buddies($thisuser->uid); foreach ($groups as $label_id => $label) { @@ -470,7 +471,7 @@ function buddylist_buddiesgroups_page($uid) { ); } } - + return drupal_get_form('groups_tables', $form); } @@ -482,7 +483,7 @@ function buddylist_count_buddies($uid) { function buddylist_buddiesgroups_form($uid) { $thisuser = user_load(array('uid' => $uid)); drupal_set_title(t('%username\'s buddy groups', array('%username' => $thisuser->name))); - + if ($buddies = buddylist_get_buddies($thisuser->uid)) { // Add group form @@ -493,13 +494,13 @@ function buddylist_buddiesgroups_form($uid) { $form['add']['add_group'] = array( '#type' => 'textfield', '#title' => t('Add new group'), - + ); $form['add']['submit'] = array( '#type' => 'submit', '#value' => t('Add'), ); - $output['add'] = drupal_get_form('buddylist_edit_groups_add', $form['add']); + $output['add'] = drupal_get_form('buddylist_edit_groups_add', $form['add']); // Get all groups $result = db_query("SELECT label_id, label FROM {buddylist_groups} WHERE uid = %d ORDER BY label ASC", $uid); @@ -509,7 +510,7 @@ function buddylist_buddiesgroups_form($uid) { $all_groups[$row->label_id] = $row->label; } } - + if (count($all_groups) > 0) { // Make a form to remove groups $form['remove'] = array('#type' => 'fieldset', @@ -529,14 +530,14 @@ function buddylist_buddiesgroups_form($uid) { ); $output['remove'] = drupal_get_form('buddylist_edit_groups_remove', $form['remove']); } - + // Build the table with buddies and their groups foreach ($buddies as $uid => $buddy) { $items = array(); foreach ($buddy['groups'] as $group) { - $items[] = $group['label_id']; + $items[] = $group['label_id']; } - + if (count($all_groups) > 0) { $form['table']['groups'][$uid] = array( '#type' => 'checkboxes', @@ -552,7 +553,7 @@ function buddylist_buddiesgroups_form($uid) { '#type' => 'value', '#value' => $thisuser->uid, ); - + if (count($form['table']['groups']) == 0) { drupal_set_message(t("You don't have any groups defined.")); } @@ -563,7 +564,7 @@ function buddylist_buddiesgroups_form($uid) { ); $output['table'] = drupal_get_form('buddylist_edit_groups_table', $form['table']); } - + return theme('buddylist_edit_groups_form', $output); } else { @@ -572,11 +573,11 @@ function buddylist_buddiesgroups_form($uid) { } function theme_buddylist_edit_groups_form($forms) { - $output = '
    '. - $forms['add']. - ''. - $forms['remove']. - '
    '. + $output = '
    '. + $forms['add']. + ''. + $forms['remove']. + '
    '. $forms['table']; return $output; } @@ -593,7 +594,7 @@ function theme_buddylist_edit_groups_table($form) { $headers = array(t('buddy'), t('buddy groups')); $output .= theme('table', $headers, $rows); - + $output .= form_render($form); return $output; @@ -628,7 +629,7 @@ function buddylist_edit_groups_table_submit($form_id, $form_values) { } } - drupal_set_message(t('buddy groups saved.')); + drupal_set_message(t('buddy groups saved.')); } /** @@ -637,7 +638,7 @@ function buddylist_edit_groups_table_submit($form_id, $form_values) { * @param $uid user id of the user to whom the group will belong. * @param $group string; name of the group * @param $visible determines whether the user's buddies can see which groups they've been put in. - * + * * @return $label_id the existing or newly created id for the name of this group. */ function buddylist_buddygroup_new($uid, $group, $visible = FALSE) { @@ -670,18 +671,18 @@ function buddylist_buddygroup_remove_buddy($uid, $buddy, $label_id) { function buddylist_buddygroup_add_buddy($uid, $buddy, $label_id) { db_lock_table('buddylist_buddy_group'); buddylist_buddygroup_remove_buddy($uid, $buddy, $label_id); - db_query("INSERT INTO {buddylist_buddy_group} VALUES (%d, %d, %d)", $uid, $buddy, $label_id); + db_query('INSERT INTO {buddylist_buddy_group} VALUES (%d, %d, %d)', $uid, $buddy, $label_id); db_unlock_tables(); } /** * Feed for buddies recent posts */ -function buddylist_buddyfeed($uid) { +function buddylist_buddyfeed($uid) { $buddy_ids = array_keys(buddylist_get_buddies($uid)); - + // false query to be used if no posts from buddies are available (as in this user has no buddies). - $result = db_query("SELECT nid FROM {node} WHERE 0"); + $result = db_query('SELECT nid FROM {node} WHERE 0'); if (count($buddy_ids > 0)) { $buddy_ids_str = '('. implode(',', $buddy_ids). ')'; $result = db_query(db_rewrite_sql('SELECT nid FROM {node} WHERE status = 1 AND uid IN %s ORDER BY nid DESC'), $buddy_ids_str); @@ -693,10 +694,11 @@ function buddylist_buddyfeed($uid) { } -function buddylist_addbuddy($uid) { +function buddylist_addbuddy($uid) { global $user; + $uid = (int)$uid[0]; $buddy = user_load(array('uid' => $uid)); - + if (empty($buddy->name)) { return t('This user does not exist'); } @@ -710,8 +712,8 @@ function buddylist_addbuddy($uid) { $form['uid'] = array('#type' => 'hidden', '#value' => $uid); $form['name'] = array('#type' => 'hidden', '#value' => $buddy->name); return confirm_form('buddylist_addbuddy_confirm', - $form, - t('Add user %name to your buddy list?', array('%name' => theme('placeholder', $buddy->name))), + $form, + t('Add user %name to your buddy list?', array('%name' => theme('placeholder', $buddy->name))), $_GET['destination'], ' ', t('Add'), t('Cancel')); @@ -726,10 +728,9 @@ function buddylist_addbuddy_confirm_submit($form_id, $form_values) { return 'user'; }; - - function buddylist_deletebuddy($uid) { global $user; + $uid = (int)$uid[0]; $buddy = user_load(array('uid' => $uid)); if (empty($buddy->name)) { @@ -742,8 +743,8 @@ function buddylist_deletebuddy($uid) { $form['uid'] = array('#type' => 'hidden', '#value' => $uid); $form['name'] = array('#type' => 'hidden', '#value' => $buddy->name); return confirm_form('buddylist_deletebuddy_confirm', - $form, - t('Remove user %name from your buddy list?', array('%name' => theme('placeholder', $buddy->name))), + $form, + t('Remove user %name from your buddy list?', array('%name' => theme('placeholder', $buddy->name))), $_GET['destination'], ' ', t('Remove'), t('Cancel')); diff --git a/contrib/buddylist_access/buddylist_access.module b/contrib/buddylist_access/buddylist_access.module index d574bee09e0f719bbf8eb6714d04842a9d0cb941..b721412f733c519f449ab8d0b6f6b4e5dbcad4a0 100644 --- a/contrib/buddylist_access/buddylist_access.module +++ b/contrib/buddylist_access/buddylist_access.module @@ -6,20 +6,20 @@ * @file * Add access control to nodes based on buddygroups */ - + /** * Implementation of hook_help(). - */ + */ function buddylist_access_help($section) { switch ($section) { case 'admin/modules#description': return t('node access control by buddy group'); } } - + function buddylist_access_nodeapi(&$node, $op, $teaser = NULL, $page = NULL) { global $user; - + switch ($op) { case 'load': // nothing yet @@ -36,10 +36,13 @@ while ($row = db_fetch_object($result)) { $edit['buddylist_groups'][] = substr($row->realm, 9); } - $output = buddylist_groups_select($node->uid, t('Optional. Restrict access to this post to members of these groups.'), $edit); - $output .= form_hidden('buddylist_groups_uid', $node->uid); + $form = buddylist_groups_select($node->uid, t('Optional. Restrict access to this post to members of these groups.'), $edit); + $form['buddylist_groups_uid'] = array( + '#type' => 'hidden', + '#value' => $node->uid + ); } - return $output; + return $form; } break; case 'insert': @@ -61,7 +64,7 @@ foreach ($node->buddylist_groups as $key => $label) { $sql = "INSERT INTO {node_access} (nid, realm, gid, grant_view) VALUES (%d, '%s', %d, %d)"; db_query($sql, $node->nid, "buddyof||$label", $node->buddylist_groups_uid, 1); - } + } } } else { @@ -70,12 +73,13 @@ db_query($sql, $node->nid); } } - + // realm = buddyof||$label // we use a gid=$node->uid so that all access restrictions become moot during a node author change function buddylist_access_node_grants($account, $op) { if ($op == 'view') { - $sql = "SELECT b.uid, label FROM {buddylist} b INNER JOIN {users} u ON b.uid = u.uid WHERE b.buddy = %d"; +// !!! - query is broken + $sql = 'SELECT b.uid, g.label FROM {buddylist} b, {buddylist_groups} g INNER JOIN {users} u ON b.uid = u.uid WHERE b.buddy = %d'; $result = db_query($sql, $account->uid); while ($row = db_fetch_object($result)) { $grants["buddyof||$row->label"][] = $row->uid; @@ -85,7 +89,7 @@ return $grants; } } - + function buddylist_access_settings() { $op = $_POST['op']; drupal_set_title(t('Buddylist access configuration')); @@ -95,13 +99,21 @@ $status = t('enabled'); $btn_text = t('Disable'); } - $group = t('Buddylist_access access control is currently') . ' ' . theme('placeholder', $status). '.
    '; - $group .= form_button($btn_text). '
    '; - $output = form_group(t('Module status'), $group, t('After enabling this module via the module settings page or before disabling this module, use the above button to properly configure your node_access table.')); - + + $form['module_status'] = array( + '#type' => 'fieldset', + '#title' => t('Module status'), + '#prefix' => t('Buddylist_access access control is currently') . ' ' . theme('placeholder', $status). '.
    ', + '#description' => t('After enabling this module via the module settings page or before disabling this module, use the above button to properly configure your node_access table.') + ); + $form['module_status'] = array( + '#type' => 'button', + '#value' => $btn_text, + '#suffix' => '
    ' + ); if ($op) { if ($op == t('Enable')) { - _buddylist_access_update_db(TRUE); + _buddylist_access_update_db(TRUE); variable_set('buddylist_access_enabled', 1); } elseif ($op == t('Disable')) { @@ -110,9 +122,9 @@ } drupal_goto('admin/settings/buddylist_access'); } - return $output; + return $form; } - + /** * Update the node_access table when a user enables/disables the module in the * settings page. Because Drupal does not, at this @@ -157,4 +169,3 @@ function _buddylist_access_update_db($enable) { } } -