From 64820546d758b34720888311d0abffcf95609436 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Thu, 4 Oct 2012 13:40:40 -0500 Subject: [ticket/11103] Move notification files to includes/notification/ PHPBB3-11103 --- phpBB/includes/notification/manager.php | 688 ++++++++++++++++++++++++++++++++ 1 file changed, 688 insertions(+) create mode 100644 phpBB/includes/notification/manager.php (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php new file mode 100644 index 0000000000..15db3f89fd --- /dev/null +++ b/phpBB/includes/notification/manager.php @@ -0,0 +1,688 @@ +phpbb_container = $phpbb_container; + + // Some common things we're going to use + $this->db = $phpbb_container->get('dbal.conn'); + } + + /** + * Load the user's notifications + * + * @param array $options Optional options to control what notifications are loaded + * notification_id Notification id to load (or array of notification ids) + * user_id User id to load notifications for (Default: $user->data['user_id']) + * order_by Order by (Default: time) + * order_dir Order direction (Default: DESC) + * limit Number of notifications to load (Default: 5) + * start Notifications offset (Default: 0) + * all_unread Load all unread messages? If set to true, count_unread is set to true (Default: false) + * count_unread Count all unread messages? (Default: false) + */ + public function load_notifications($options = array()) + { + $user = $this->phpbb_container->get('user'); + + // Merge default options + $options = array_merge(array( + 'notification_id' => false, + 'user_id' => $user->data['user_id'], + 'order_by' => 'time', + 'order_dir' => 'DESC', + 'limit' => 0, + 'start' => 0, + 'all_unread' => false, + 'count_unread' => false, + ), $options); + + // If all_unread, count_unread mus be true + $options['count_unread'] = ($options['all_unread']) ? true : $options['count_unread']; + + // Anonymous users and bots never receive notifications + if ($options['user_id'] == $user->data['user_id'] && ($user->data['user_id'] == ANONYMOUS || $user->data['user_type'] == USER_IGNORE)) + { + return array( + 'notifications' => array(), + 'unread_count' => 0, + ); + } + + $notifications = $user_ids = array(); + $load_special = array(); + $count = 0; + + if ($options['count_unread']) + { + // Get the total number of unread notifications + $sql = 'SELECT COUNT(*) AS count + FROM ' . NOTIFICATIONS_TABLE . ' + WHERE user_id = ' . (int) $options['user_id'] . ' + AND unread = 1'; + $result = $this->db->sql_query($sql); + $count = (int) $this->db->sql_fetchfield('count', $result); + $this->db->sql_freeresult($result); + } + + $rowset = array(); + + // Get the main notifications + $sql = 'SELECT * + FROM ' . NOTIFICATIONS_TABLE . ' + WHERE user_id = ' . (int) $options['user_id'] . + (($options['notification_id']) ? ((is_array($options['notification_id'])) ? ' AND ' . $this->db->sql_in_set('notification_id', $options['notification_id']) : ' AND notification_id = ' . (int) $options['notification_id']) : '') . ' + ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); + $result = $this->db->sql_query_limit($sql, $options['limit'], $options['start']); + + while ($row = $this->db->sql_fetchrow($result)) + { + $rowset[$row['notification_id']] = $row; + } + $this->db->sql_freeresult($result); + + // Get all unread notifications + if ($count && $options['all_unread'] && !empty($rowset)) + { + $sql = 'SELECT * + FROM ' . NOTIFICATIONS_TABLE . ' + WHERE user_id = ' . (int) $options['user_id'] . ' + AND unread = 1 + AND ' . $this->db->sql_in_set('notification_id', array_keys($rowset), true) . ' + ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); + $result = $this->db->sql_query_limit($sql, $options['limit'], $options['start']); + + while ($row = $this->db->sql_fetchrow($result)) + { + $rowset[$row['notification_id']] = $row; + } + $this->db->sql_freeresult($result); + } + + foreach ($rowset as $row) + { + $item_type_class_name = $this->get_item_type_class_name($row['item_type'], true); + + $notification = new $item_type_class_name($this->phpbb_container, $row); + + // Array of user_ids to query all at once + $user_ids = array_merge($user_ids, $notification->users_to_query()); + + // Some notification types also require querying additional tables themselves + if (!isset($load_special[$row['item_type']])) + { + $load_special[$row['item_type']] = array(); + } + $load_special[$row['item_type']] = array_merge($load_special[$row['item_type']], $notification->get_load_special()); + + $notifications[] = $notification; + } + + $this->load_users($user_ids); + + // Allow each type to load it's own special items + foreach ($load_special as $item_type => $data) + { + $item_type_class_name = $this->get_item_type_class_name($item_type, true); + + $item_type_class_name::load_special($this->phpbb_container, $data, $notifications); + } + + return array( + 'notifications' => $notifications, + 'unread_count' => $count, + ); + } + + /** + * Mark notifications read + * + * @param string|array $item_type Type identifier or array of item types (only acceptable if the $data is identical for the specified types) + * @param bool|int|array $item_id Item id or array of item ids. False to mark read for all item ids + * @param bool|int|array $user_id User id or array of user ids. False to mark read for all user ids + * @param bool|int $time Time at which to mark all notifications prior to as read. False to mark all as read. (Default: False) + */ + public function mark_notifications_read($item_type, $item_id, $user_id, $time = false) + { + if (is_array($item_type)) + { + foreach ($item_type as $type) + { + $this->mark_notifications_read($type, $item_id, $user_id, $time); + } + + return; + } + + $time = ($time) ?: time(); + + $this->get_item_type_class_name($item_type); + + $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " + SET unread = 0 + WHERE item_type = '" . $this->db->sql_escape($item_type) . "' + AND time <= " . $time . + (($item_id !== false) ? ' AND ' . (is_array($item_id) ? $this->db->sql_in_set('item_id', $item_id) : 'item_id = ' . (int) $item_id) : '') . + (($user_id !== false) ? ' AND ' . (is_array($user_id) ? $this->db->sql_in_set('user_id', $user_id) : 'user_id = ' . (int) $user_id) : ''); + $this->db->sql_query($sql); + } + + /** + * Mark notifications read from a parent identifier + * + * @param string|array $item_type Type identifier or array of item types (only acceptable if the $data is identical for the specified types) + * @param bool|int|array $item_parent_id Item parent id or array of item parent ids. False to mark read for all item parent ids + * @param bool|int|array $user_id User id or array of user ids. False to mark read for all user ids + * @param bool|int $time Time at which to mark all notifications prior to as read. False to mark all as read. (Default: False) + */ + public function mark_notifications_read_by_parent($item_type, $item_parent_id, $user_id, $time = false) + { + if (is_array($item_type)) + { + foreach ($item_type as $type) + { + $this->mark_notifications_read_by_parent($type, $item_parent_id, $user_id, $time); + } + + return; + } + + $time = ($time) ?: time(); + + $item_type_class_name = $this->get_item_type_class_name($item_type); + + $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " + SET unread = 0 + WHERE item_type = '" . $this->db->sql_escape($item_type) . "' + AND time <= " . $time . + (($item_parent_id !== false) ? ' AND ' . (is_array($item_parent_id) ? $this->db->sql_in_set('item_parent_id', $item_parent_id) : 'item_parent_id = ' . (int) $item_parent_id) : '') . + (($user_id !== false) ? ' AND ' . (is_array($user_id) ? $this->db->sql_in_set('user_id', $user_id) : 'user_id = ' . (int) $user_id) : ''); + $this->db->sql_query($sql); + } + + /** + * Mark notifications read + * + * @param int|array $notification_id Notification id or array of notification ids. + * @param bool|int $time Time at which to mark all notifications prior to as read. False to mark all as read. (Default: False) + */ + public function mark_notifications_read_by_id($notification_id, $time = false) + { + $time = ($time) ?: time(); + + $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " + SET unread = 0 + WHERE time <= " . $time . ' + AND ' . ((is_array($notification_id)) ? $this->db->sql_in_set('notification_id', $notification_id) : 'notification_id = ' . (int) $notification_id); + $this->db->sql_query($sql); + } + + /** + * Add a notification + * + * @param string|array $item_type Type identifier or array of item types (only acceptable if the $data is identical for the specified types) + * Note: If you send an array of types, any user who could receive multiple notifications from this single item will only receive + * a single notification. If they MUST receive multiple notifications, call this function multiple times instead of sending an array + * @param array $data Data specific for this type that will be inserted + */ + public function add_notifications($item_type, $data, $options = array()) + { + $options = array_merge(array( + 'ignore_users' => array(), + ), $options); + + if (is_array($item_type)) + { + $notified_users = array(); + $temp_options = $options; + + foreach ($item_type as $type) + { + $temp_options['ignore_users'] = $options['ignore_users'] + $notified_users; + $notified_users += $this->add_notifications($type, $data, $temp_options); + } + + return $notified_users; + } + + $item_type_class_name = $this->get_item_type_class_name($item_type); + + $item_id = $item_type_class_name::get_item_id($data); + + // find out which users want to receive this type of notification + $notify_users = $item_type_class_name::find_users_for_notification($this->phpbb_container, $data, $options); + + $this->add_notifications_for_users($item_type, $data, $notify_users); + + return $notify_users; + } + + /** + * Add a notification for specific users + * + * @param string|array $item_type Type identifier or array of item types (only acceptable if the $data is identical for the specified types) + * @param array $data Data specific for this type that will be inserted + * @param array $notify_users User list to notify + */ + public function add_notifications_for_users($item_type, $data, $notify_users) + { + if (is_array($item_type)) + { + foreach ($item_type as $type) + { + $this->add_notifications_for_users($type, $data, $notify_users); + } + + return; + } + + $item_type_class_name = $this->get_item_type_class_name($item_type); + + $item_id = $item_type_class_name::get_item_id($data); + + $user_ids = array(); + $notification_objects = $notification_methods = array(); + $new_rows = array(); + + // Never send notifications to the anonymous user! + unset($notify_users[ANONYMOUS]); + + // Make sure not to send new notifications to users who've already been notified about this item + // This may happen when an item was added, but now new users are able to see the item + // todo Users should not receive notifications from multiple events from the same item (ex: for a topic reply with a quote including your username) + // Probably should be handled within each type? + $sql = 'SELECT user_id + FROM ' . NOTIFICATIONS_TABLE . " + WHERE item_type = '" . $this->db->sql_escape($item_type) . "' + AND item_id = " . (int) $item_id; + $result = $this->db->sql_query($sql); + while ($row = $this->db->sql_fetchrow($result)) + { + unset($notify_users[$row['user_id']]); + } + $this->db->sql_freeresult($result); + + if (!sizeof($notify_users)) + { + return; + } + + // Go through each user so we can insert a row in the DB and then notify them by their desired means + foreach ($notify_users as $user => $methods) + { + $notification = new $item_type_class_name($this->phpbb_container); + + $notification->user_id = (int) $user; + + // Store the creation array in our new rows that will be inserted later + $new_rows[] = $notification->create_insert_array($data); + + // Users are needed to send notifications + $user_ids = array_merge($user_ids, $notification->users_to_query()); + + foreach ($methods as $method) + { + // setup the notification methods and add the notification to the queue + if ($method) // blank means we just insert it as a notification, but do not notify them by any other means + { + if (!isset($notification_methods[$method])) + { + $method_class_name = 'phpbb_notification_method_' . $method; + $notification_methods[$method] = new $method_class_name($this->phpbb_container); + } + + $notification_methods[$method]->add_to_queue($notification); + } + } + } + + // insert into the db + $this->db->sql_multi_insert(NOTIFICATIONS_TABLE, $new_rows); + + // We need to load all of the users to send notifications + $this->load_users($user_ids); + + // run the queue for each method to send notifications + foreach ($notification_methods as $method) + { + $method->notify(); + } + } + + /** + * Update a notification + * + * @param string|array $item_type Type identifier or array of item types (only acceptable if the $data is identical for the specified types) + * @param array $data Data specific for this type that will be updated + */ + public function update_notifications($item_type, $data) + { + if (is_array($item_type)) + { + foreach ($item_type as $type) + { + $this->update_notifications($type, $data); + } + + return; + } + + $item_type_class_name = $this->get_item_type_class_name($item_type); + + // Allow the notifications class to over-ride the update_notifications functionality + if (method_exists($item_type_class_name, 'update_notifications')) + { + // Return False to over-ride the rest of the update + if ($item_type_class_name::update_notifications($this->phpbb_container, $data) === false) + { + return; + } + } + + $item_id = $item_type_class_name::get_item_id($data); + + $notification = new $item_type_class_name($this->phpbb_container); + $update_array = $notification->create_update_array($data); + + $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . ' + SET ' . $this->db->sql_build_array('UPDATE', $update_array) . " + WHERE item_type = '" . $this->db->sql_escape($item_type) . "' + AND item_id = " . (int) $item_id; + $this->db->sql_query($sql); + } + + /** + * Delete a notification + * + * @param string|array $item_type Type identifier or array of item types (only acceptable if the $item_id is identical for the specified types) + * @param int|array $item_id Identifier within the type (or array of ids) + * @param array $data Data specific for this type that will be updated + */ + public function delete_notifications($item_type, $item_id) + { + if (is_array($item_type)) + { + foreach ($item_type as $type) + { + $this->delete_notifications($type, $item_id); + } + + return; + } + + $this->get_item_type_class_name($item_type); + + $sql = 'DELETE FROM ' . NOTIFICATIONS_TABLE . " + WHERE item_type = '" . $this->db->sql_escape($item_type) . "' + AND " . (is_array($item_id) ? $this->db->sql_in_set('item_id', $item_id) : 'item_id = ' . (int) $item_id); + $this->db->sql_query($sql); + } + + /** + * Get all of the subscription types + * + * @return array Array of item types + */ + public function get_subscription_types() + { + $subscription_types = array(); + + foreach ($this->get_subscription_files('notifications/type/') as $class => $file) + { + $class = $this->get_item_type_class_name($class); + + if (!class_exists($class)) + { + include($file); + } + + if ($class::is_available($this->phpbb_container) && method_exists($class, 'get_item_type')) + { + if ($class::$notification_option === false) + { + $subscription_types[$class::get_item_type()] = $class::get_item_type(); + } + else + { + $subscription_types[$class::$notification_option['id']] = $class::$notification_option; + } + } + } + + return $subscription_types; + } + + /** + * Get all of the subscription methods + * + * @return array Array of methods + */ + public function get_subscription_methods() + { + $subscription_methods = array(); + + foreach ($this->get_subscription_files('notifications/method/') as $method_name => $file) + { + $class_name = 'phpbb_notification_method_' . $method_name; + + if (!class_exists($class_name)) + { + include($file); + } + + $method = new $class_name($this->phpbb_container); + + if ($method->is_available()) + { + $subscription_methods[] = $method_name; + } + } + + return $subscription_methods; + } + + /** + * Get subscriptions + * + * @param bool|int $user_id The user_id to add the subscription for (bool false for current user) + * @param bool $only_global True to select only global subscription options (item_id = 0) + * + * @return array Subscriptions + */ + public function get_subscriptions($user_id = false, $only_global = false) + { + $user_id = ($user_id === false) ? $this->phpbb_container->get('user')->data['user_id'] : $user_id; + + $subscriptions = array(); + + $sql = 'SELECT * + FROM ' . USER_NOTIFICATIONS_TABLE . ' + WHERE user_id = ' . (int) $user_id . + (($only_global) ? ' AND item_id = 0' : ''); + $result = $this->db->sql_query($sql); + while ($row = $this->db->sql_fetchrow($result)) + { + if ($only_global) + { + if (!isset($subscriptions[$row['item_type']])) + { + $subscriptions[$row['item_type']] = array(); + } + + $subscriptions[$row['item_type']][] = $row['method']; + } + else + { + $subscriptions[] = $row; + } + } + $this->db->sql_freeresult($result); + + return $subscriptions; + } + + /** + * Add a subscription + * + * @param string $item_type Type identifier of the subscription + * @param int $item_id The id of the item + * @param string $method The method of the notification e.g. '', 'email', or 'jabber' + * @param bool|int $user_id The user_id to add the subscription for (bool false for current user) + */ + public function add_subscription($item_type, $item_id = 0, $method = '', $user_id = false) + { + $this->get_item_type_class_name($item_type); + + $user_id = ($user_id === false) ? $this->phpbb_container->get('user')->data['user_id'] : $user_id; + + $sql = 'INSERT INTO ' . USER_NOTIFICATIONS_TABLE . ' ' . + $this->db->sql_build_array('INSERT', array( + 'item_type' => $item_type, + 'item_id' => (int) $item_id, + 'user_id' => (int) $user_id, + 'method' => $method, + )); + $this->db->sql_query($sql); + } + + /** + * Delete a subscription + * + * @param string $item_type Type identifier of the subscription + * @param int $item_id The id of the item + * @param string $method The method of the notification e.g. '', 'email', or 'jabber' + * @param bool|int $user_id The user_id to add the subscription for (bool false for current user) + */ + public function delete_subscription($item_type, $item_id = 0, $method = '', $user_id = false) + { + $this->get_item_type_class_name($item_type); + + $user_id = ($user_id === false) ? $this->phpbb_container->get('user')->data['user_id'] : $user_id; + + $sql = 'DELETE FROM ' . USER_NOTIFICATIONS_TABLE . " + WHERE item_type = '" . $this->db->sql_escape($item_type) . "' + AND item_id = " . (int) $item_id . ' + AND user_id = ' .(int) $user_id . " + AND method = '" . $this->db->sql_escape($method) . "'"; + $this->db->sql_query($sql); + } + + /** + * Load user helper + * + * @param array $user_ids + */ + public function load_users($user_ids) + { + $user_ids[] = ANONYMOUS; + + // Load the users + $user_ids = array_unique($user_ids); + + // Do not load users we already have in $this->users + $user_ids = array_diff($user_ids, array_keys($this->users)); + + if (sizeof($user_ids)) + { + $sql = 'SELECT * + FROM ' . USERS_TABLE . ' + WHERE ' . $this->db->sql_in_set('user_id', $user_ids); + $result = $this->db->sql_query($sql); + + while ($row = $this->db->sql_fetchrow($result)) + { + $this->users[$row['user_id']] = $row; + } + $this->db->sql_freeresult($result); + } + } + + /** + * Get a user row from our users cache + * + * @param int $user_id + * @return array + */ + public function get_user($user_id) + { + return (isset($this->users[$user_id])) ? $this->users[$user_id] : $this->users[ANONYMOUS]; + } + + /** + * Helper to get the notifications item type class name and clean it if unsafe + */ + private function get_item_type_class_name(&$item_type, $safe = false) + { + if (!$safe) + { + $item_type = preg_replace('#[^a-z_]#', '', $item_type); + } + + return 'phpbb_notification_type_' . $item_type; + } + + /** + * Helper to get subscription related files with the finder + */ + private function get_subscription_files($path) + { + $ext_manager = $this->phpbb_container->get('ext.manager'); + $php_ext = $this->phpbb_container->getParameter('core.php_ext'); + + $finder = $ext_manager->get_finder(); + + $subscription_files = array(); + + $files = $finder + ->core_path('includes/' . $path) + ->extension_directory($path) + ->get_files(); + foreach ($files as $file) + { + $class = substr($file, strrpos($file, '/')); + $class = substr($class, 1, (strpos($class, '.' . $php_ext) - 1)); + + if ($class == 'interface' || $class == 'base') + { + continue; + } + + $subscription_files[$class] = $file; + } + + return $subscription_files; + } +} -- cgit v1.2.1 From cea94d89848a806f449610ddb2a7df7b7eec1328 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Thu, 4 Oct 2012 14:27:43 -0500 Subject: [ticket/11103] Use dependency injection instead of phpbb_container PHPBB3-11103 --- phpBB/includes/notification/manager.php | 93 ++++++++++++++++++++------------- 1 file changed, 58 insertions(+), 35 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 15db3f89fd..e2c6c9d0f4 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -23,8 +23,7 @@ if (!defined('IN_PHPBB')) */ class phpbb_notification_manager { - protected $phpbb_container; - protected $db; + protected $db, $cache, $template, $extension_manager, $user, $auth, $config, $phpbb_root_path, $php_ext = null; /** * Users loaded from the DB @@ -33,12 +32,17 @@ class phpbb_notification_manager */ protected $users = array(); - public function __construct(ContainerBuilder $phpbb_container) + public function __construct(dbal $db, phpbb_cache_driver_interface $cache, phpbb_template $template, phpbb_extension_manager $extension_manager, phpbb_user $user, phpbb_auth $auth, phpbb_config $config, $phpbb_root_path, $php_ext) { - $this->phpbb_container = $phpbb_container; - - // Some common things we're going to use - $this->db = $phpbb_container->get('dbal.conn'); + $this->db = $db; + $this->cache = $cache; + $this->template = $template; + $this->extension_manager = $extension_manager; + $this->user = $user; + $this->auth = $auth; + $this->config = $config; + $this->phpbb_root_path = $phpbb_root_path; + $this->php_ext = $php_ext; } /** @@ -56,12 +60,10 @@ class phpbb_notification_manager */ public function load_notifications($options = array()) { - $user = $this->phpbb_container->get('user'); - // Merge default options $options = array_merge(array( 'notification_id' => false, - 'user_id' => $user->data['user_id'], + 'user_id' => $this->user->data['user_id'], 'order_by' => 'time', 'order_dir' => 'DESC', 'limit' => 0, @@ -74,7 +76,7 @@ class phpbb_notification_manager $options['count_unread'] = ($options['all_unread']) ? true : $options['count_unread']; // Anonymous users and bots never receive notifications - if ($options['user_id'] == $user->data['user_id'] && ($user->data['user_id'] == ANONYMOUS || $user->data['user_type'] == USER_IGNORE)) + if ($options['user_id'] == $this->user->data['user_id'] && ($this->user->data['user_id'] == ANONYMOUS || $this->user->data['user_type'] == USER_IGNORE)) { return array( 'notifications' => array(), @@ -136,7 +138,7 @@ class phpbb_notification_manager { $item_type_class_name = $this->get_item_type_class_name($row['item_type'], true); - $notification = new $item_type_class_name($this->phpbb_container, $row); + $notification = $this->get_item_type_class($item_type_class_name, $row); // Array of user_ids to query all at once $user_ids = array_merge($user_ids, $notification->users_to_query()); @@ -153,12 +155,14 @@ class phpbb_notification_manager $this->load_users($user_ids); - // Allow each type to load it's own special items + // Allow each type to load its own special items foreach ($load_special as $item_type => $data) { $item_type_class_name = $this->get_item_type_class_name($item_type, true); - $item_type_class_name::load_special($this->phpbb_container, $data, $notifications); + $item_class = $this->get_item_type_class($item_type_class_name); + + $item_class->load_special($data, $notifications); } return array( @@ -283,7 +287,7 @@ class phpbb_notification_manager $item_id = $item_type_class_name::get_item_id($data); // find out which users want to receive this type of notification - $notify_users = $item_type_class_name::find_users_for_notification($this->phpbb_container, $data, $options); + $notify_users = $this->get_item_type_class($item_type_class_name)->find_users_for_notification($data, $options); $this->add_notifications_for_users($item_type, $data, $notify_users); @@ -343,7 +347,7 @@ class phpbb_notification_manager // Go through each user so we can insert a row in the DB and then notify them by their desired means foreach ($notify_users as $user => $methods) { - $notification = new $item_type_class_name($this->phpbb_container); + $notification = $this->get_item_type_class($item_type_class_name); $notification->user_id = (int) $user; @@ -361,7 +365,7 @@ class phpbb_notification_manager if (!isset($notification_methods[$method])) { $method_class_name = 'phpbb_notification_method_' . $method; - $notification_methods[$method] = new $method_class_name($this->phpbb_container); + $notification_methods[$method] = $this->get_method_class($method_class_name); } $notification_methods[$method]->add_to_queue($notification); @@ -406,7 +410,7 @@ class phpbb_notification_manager if (method_exists($item_type_class_name, 'update_notifications')) { // Return False to over-ride the rest of the update - if ($item_type_class_name::update_notifications($this->phpbb_container, $data) === false) + if ($this->get_item_type_class($item_type_class_name)->update_notifications($data) === false) { return; } @@ -414,7 +418,7 @@ class phpbb_notification_manager $item_id = $item_type_class_name::get_item_id($data); - $notification = new $item_type_class_name($this->phpbb_container); + $notification = $this->get_item_type_class($item_type_class_name); $update_array = $notification->create_update_array($data); $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . ' @@ -460,24 +464,26 @@ class phpbb_notification_manager { $subscription_types = array(); - foreach ($this->get_subscription_files('notifications/type/') as $class => $file) + foreach ($this->get_subscription_files('notifications/type/') as $class_name => $file) { - $class = $this->get_item_type_class_name($class); + $class_name = $this->get_item_type_class_name($class_name); - if (!class_exists($class)) + if (!class_exists($class_name)) { include($file); } - if ($class::is_available($this->phpbb_container) && method_exists($class, 'get_item_type')) + $class = $this->get_item_type_class($class_name); + + if ($class->is_available() && method_exists($class_name, 'get_item_type')) { - if ($class::$notification_option === false) + if ($class_name::$notification_option === false) { - $subscription_types[$class::get_item_type()] = $class::get_item_type(); + $subscription_types[$class_name::get_item_type()] = $class_name::get_item_type(); } else { - $subscription_types[$class::$notification_option['id']] = $class::$notification_option; + $subscription_types[$class_name::$notification_option['id']] = $class_name::$notification_option; } } } @@ -503,7 +509,7 @@ class phpbb_notification_manager include($file); } - $method = new $class_name($this->phpbb_container); + $method = $this->get_method_class($class_name); if ($method->is_available()) { @@ -524,7 +530,7 @@ class phpbb_notification_manager */ public function get_subscriptions($user_id = false, $only_global = false) { - $user_id = ($user_id === false) ? $this->phpbb_container->get('user')->data['user_id'] : $user_id; + $user_id = ($user_id === false) ? $this->user->data['user_id'] : $user_id; $subscriptions = array(); @@ -566,7 +572,7 @@ class phpbb_notification_manager { $this->get_item_type_class_name($item_type); - $user_id = ($user_id === false) ? $this->phpbb_container->get('user')->data['user_id'] : $user_id; + $user_id = ($user_id === false) ? $this->user->data['user_id'] : $user_id; $sql = 'INSERT INTO ' . USER_NOTIFICATIONS_TABLE . ' ' . $this->db->sql_build_array('INSERT', array( @@ -590,7 +596,7 @@ class phpbb_notification_manager { $this->get_item_type_class_name($item_type); - $user_id = ($user_id === false) ? $this->phpbb_container->get('user')->data['user_id'] : $user_id; + $user_id = ($user_id === false) ? $this->user->data['user_id'] : $user_id; $sql = 'DELETE FROM ' . USER_NOTIFICATIONS_TABLE . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "' @@ -654,15 +660,32 @@ class phpbb_notification_manager return 'phpbb_notification_type_' . $item_type; } + /** + * Helper to get the notifications item type class and set it up + */ + private function get_item_type_class($item_type, $data = array()) + { + $item = new $item_type($this, $this->db, $this->cache, $this->template, $this->extension_manager, $this->user, $this->auth, $this->config, $this->phpbb_root_path, $this->php_ext); + + $item->set_initial_data($data); + + return $item; + } + + /** + * Helper to get the notifications method class and set it up + */ + private function get_method_class($method_name) + { + return new $method_name($this, $this->db, $this->cache, $this->template, $this->extension_manager, $this->user, $this->auth, $this->config, $this->phpbb_root_path, $this->php_ext); + } + /** * Helper to get subscription related files with the finder */ private function get_subscription_files($path) { - $ext_manager = $this->phpbb_container->get('ext.manager'); - $php_ext = $this->phpbb_container->getParameter('core.php_ext'); - - $finder = $ext_manager->get_finder(); + $finder = $this->extension_manager->get_finder(); $subscription_files = array(); @@ -673,7 +696,7 @@ class phpbb_notification_manager foreach ($files as $file) { $class = substr($file, strrpos($file, '/')); - $class = substr($class, 1, (strpos($class, '.' . $php_ext) - 1)); + $class = substr($class, 1, (strpos($class, '.' . $this->php_ext) - 1)); if ($class == 'interface' || $class == 'base') { -- cgit v1.2.1 From ff136cc96a62147bc7468b716b86a30f12754e77 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Thu, 4 Oct 2012 15:21:07 -0500 Subject: [ticket/11103] Do not use Symfony\...\ContainerBuilder; It's no longer needed PHPBB3-11103 --- phpBB/includes/notification/manager.php | 2 -- 1 file changed, 2 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index e2c6c9d0f4..be29f37a3e 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -7,8 +7,6 @@ * */ -use Symfony\Component\DependencyInjection\ContainerBuilder; - /** * @ignore */ -- cgit v1.2.1 From ceb56da965f12245bca6b735cb71f3bbaf505307 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Thu, 4 Oct 2012 21:39:17 -0500 Subject: [ticket/11103] Fixing a few bugs from the previous changes PHPBB3-11103 --- phpBB/includes/notification/manager.php | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index be29f37a3e..854d72009e 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -30,7 +30,7 @@ class phpbb_notification_manager */ protected $users = array(); - public function __construct(dbal $db, phpbb_cache_driver_interface $cache, phpbb_template $template, phpbb_extension_manager $extension_manager, phpbb_user $user, phpbb_auth $auth, phpbb_config $config, $phpbb_root_path, $php_ext) + public function __construct(dbal $db, phpbb_cache_driver_interface $cache, phpbb_template $template, phpbb_extension_manager $extension_manager, $user, phpbb_auth $auth, phpbb_config $config, $phpbb_root_path, $php_ext) { $this->db = $db; $this->cache = $cache; @@ -462,7 +462,7 @@ class phpbb_notification_manager { $subscription_types = array(); - foreach ($this->get_subscription_files('notifications/type/') as $class_name => $file) + foreach ($this->get_subscription_files('notification/type/') as $class_name => $file) { $class_name = $this->get_item_type_class_name($class_name); @@ -498,7 +498,7 @@ class phpbb_notification_manager { $subscription_methods = array(); - foreach ($this->get_subscription_files('notifications/method/') as $method_name => $file) + foreach ($this->get_subscription_files('notification/method/') as $method_name => $file) { $class_name = 'phpbb_notification_method_' . $method_name; -- cgit v1.2.1 From 3f2e3ad633930744e1ed92cc529ca473ccfa09e0 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Fri, 5 Oct 2012 00:07:48 -0500 Subject: [ticket/11103] Working on test case Fixing extension type/method naming scheme so they can be autoloaded. Other bugs PHPBB3-11103 --- phpBB/includes/notification/manager.php | 39 +++++++++++++++++++-------------- 1 file changed, 22 insertions(+), 17 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 854d72009e..c1ae61e08a 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -466,11 +466,6 @@ class phpbb_notification_manager { $class_name = $this->get_item_type_class_name($class_name); - if (!class_exists($class_name)) - { - include($file); - } - $class = $this->get_item_type_class($class_name); if ($class->is_available() && method_exists($class_name, 'get_item_type')) @@ -502,11 +497,6 @@ class phpbb_notification_manager { $class_name = 'phpbb_notification_method_' . $method_name; - if (!class_exists($class_name)) - { - include($file); - } - $method = $this->get_method_class($class_name); if ($method->is_available()) @@ -652,7 +642,14 @@ class phpbb_notification_manager { if (!$safe) { - $item_type = preg_replace('#[^a-z_]#', '', $item_type); + $item_type = preg_replace('#[^a-z_-]#', '', $item_type); + } + + if (strpos($item_type, 'ext_') === 0) + { + $item_type_ary = explode('-', substr($item_type, 4), 2); + + return 'phpbb_ext_' . $item_type_ary[0] . '_notification_type_' . $item_type_ary[1]; } return 'phpbb_notification_type_' . $item_type; @@ -661,7 +658,7 @@ class phpbb_notification_manager /** * Helper to get the notifications item type class and set it up */ - private function get_item_type_class($item_type, $data = array()) + public function get_item_type_class($item_type, $data = array()) { $item = new $item_type($this, $this->db, $this->cache, $this->template, $this->extension_manager, $this->user, $this->auth, $this->config, $this->phpbb_root_path, $this->php_ext); @@ -673,7 +670,7 @@ class phpbb_notification_manager /** * Helper to get the notifications method class and set it up */ - private function get_method_class($method_name) + public function get_method_class($method_name) { return new $method_name($this, $this->db, $this->cache, $this->template, $this->extension_manager, $this->user, $this->auth, $this->config, $this->phpbb_root_path, $this->php_ext); } @@ -693,15 +690,23 @@ class phpbb_notification_manager ->get_files(); foreach ($files as $file) { - $class = substr($file, strrpos($file, '/')); - $class = substr($class, 1, (strpos($class, '.' . $this->php_ext) - 1)); + $name = substr($file, strrpos($file, '/')); + $name = substr($name, 1, (strpos($name, '.' . $this->php_ext) - 1)); - if ($class == 'interface' || $class == 'base') + if ($name == 'interface' || $name == 'base') { continue; } - $subscription_files[$class] = $file; + if (!strpos($file, 'includes/')) // is an extension + { + $ext_name = substr($file, (strpos($file, 'ext/') + 4)); + $ext_name = substr($ext_name, 0, strpos($ext_name, '/')); + + $name = 'ext_' . $ext_name . '-' . $name; + } + + $subscription_files[$name] = $file; } return $subscription_files; -- cgit v1.2.1 From bafb5b0ecad7266c9641624bae2de2f3c7efe500 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Fri, 5 Oct 2012 18:12:48 -0500 Subject: [ticket/11103] Starting work on combining notifications Just for posts currently and not yet outputted. PHPBB3-11103 --- phpBB/includes/notification/manager.php | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index c1ae61e08a..c5fd41c901 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -660,6 +660,12 @@ class phpbb_notification_manager */ public function get_item_type_class($item_type, $data = array()) { + if (!strpos($item_type, 'notification_type_')) + { + $item_class = $this->get_item_type_class_name($item_type); + $item_type = $item_class; + } + $item = new $item_type($this, $this->db, $this->cache, $this->template, $this->extension_manager, $this->user, $this->auth, $this->config, $this->phpbb_root_path, $this->php_ext); $item->set_initial_data($data); -- cgit v1.2.1 From 3d79ce28031b4c85ee34bd4d43f0c64b18b1a80b Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Fri, 12 Oct 2012 16:54:42 -0500 Subject: [ticket/11103] Ability to query data before running create_insert_array() Mark post/topic in queue notifications read when visiting mcp Change post/topic in queue notification url to use MCP. Fix the bug: Approving a topic marks the topic as read, but before the notification is created for the user approving the topic (if they would get a notification that the topic has been made). This causes it to be stuck "unread". PHPBB3-11103 --- phpBB/includes/notification/manager.php | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index c5fd41c901..6c74fa965e 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -324,8 +324,6 @@ class phpbb_notification_manager // Make sure not to send new notifications to users who've already been notified about this item // This may happen when an item was added, but now new users are able to see the item - // todo Users should not receive notifications from multiple events from the same item (ex: for a topic reply with a quote including your username) - // Probably should be handled within each type? $sql = 'SELECT user_id FROM ' . NOTIFICATIONS_TABLE . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "' @@ -342,6 +340,11 @@ class phpbb_notification_manager return; } + // Allow notifications to perform actions before creating the insert array (such as run a query to cache some data needed for all notifications) + $notification = $this->get_item_type_class($item_type_class_name); + $pre_create_data = $notification->pre_create_insert_array($data, $notify_users); + unset($notification); + // Go through each user so we can insert a row in the DB and then notify them by their desired means foreach ($notify_users as $user => $methods) { @@ -350,7 +353,7 @@ class phpbb_notification_manager $notification->user_id = (int) $user; // Store the creation array in our new rows that will be inserted later - $new_rows[] = $notification->create_insert_array($data); + $new_rows[] = $notification->create_insert_array($data, $pre_create_data); // Users are needed to send notifications $user_ids = array_merge($user_ids, $notification->users_to_query()); -- cgit v1.2.1 From cb937841269017d13058208378e4c9ad79718c6e Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sat, 13 Oct 2012 20:02:38 -0500 Subject: [ticket/11103] UCP Notification List PHPBB3-11103 --- phpBB/includes/notification/manager.php | 33 +++++++++++++++++++++++++-------- 1 file changed, 25 insertions(+), 8 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 6c74fa965e..22fa12967a 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -68,6 +68,7 @@ class phpbb_notification_manager 'start' => 0, 'all_unread' => false, 'count_unread' => false, + 'count_total' => false, ), $options); // If all_unread, count_unread mus be true @@ -79,12 +80,13 @@ class phpbb_notification_manager return array( 'notifications' => array(), 'unread_count' => 0, + 'total_count' => 0, ); } $notifications = $user_ids = array(); $load_special = array(); - $count = 0; + $total_count = $unread_count = 0; if ($options['count_unread']) { @@ -94,7 +96,18 @@ class phpbb_notification_manager WHERE user_id = ' . (int) $options['user_id'] . ' AND unread = 1'; $result = $this->db->sql_query($sql); - $count = (int) $this->db->sql_fetchfield('count', $result); + $unread_count = (int) $this->db->sql_fetchfield('count', $result); + $this->db->sql_freeresult($result); + } + + if ($options['count_total']) + { + // Get the total number of notifications + $sql = 'SELECT COUNT(*) AS count + FROM ' . NOTIFICATIONS_TABLE . ' + WHERE user_id = ' . (int) $options['user_id']; + $result = $this->db->sql_query($sql); + $total_count = (int) $this->db->sql_fetchfield('count', $result); $this->db->sql_freeresult($result); } @@ -115,7 +128,7 @@ class phpbb_notification_manager $this->db->sql_freeresult($result); // Get all unread notifications - if ($count && $options['all_unread'] && !empty($rowset)) + if ($unread_count && $options['all_unread'] && !empty($rowset)) { $sql = 'SELECT * FROM ' . NOTIFICATIONS_TABLE . ' @@ -165,14 +178,15 @@ class phpbb_notification_manager return array( 'notifications' => $notifications, - 'unread_count' => $count, + 'unread_count' => $unread_count, + 'total_count' => $total_count, ); } /** * Mark notifications read * - * @param string|array $item_type Type identifier or array of item types (only acceptable if the $data is identical for the specified types) + * @param bool|string|array $item_type Type identifier or array of item types (only acceptable if the $data is identical for the specified types). False to mark read for all item types * @param bool|int|array $item_id Item id or array of item ids. False to mark read for all item ids * @param bool|int|array $user_id User id or array of user ids. False to mark read for all user ids * @param bool|int $time Time at which to mark all notifications prior to as read. False to mark all as read. (Default: False) @@ -191,12 +205,15 @@ class phpbb_notification_manager $time = ($time) ?: time(); - $this->get_item_type_class_name($item_type); + if ($item_type !== false) + { + $this->get_item_type_class_name($item_type); + } $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " SET unread = 0 - WHERE item_type = '" . $this->db->sql_escape($item_type) . "' - AND time <= " . $time . + WHERE time <= " . $time . + (($item_type !== false) ? ' AND ' . (is_array($item_type) ? $this->db->sql_in_set('item_type', $item_type) : " item_type = '" . $this->db->sql_escape($item_type) . "'") : '') . (($item_id !== false) ? ' AND ' . (is_array($item_id) ? $this->db->sql_in_set('item_id', $item_id) : 'item_id = ' . (int) $item_id) : '') . (($user_id !== false) ? ' AND ' . (is_array($user_id) ? $this->db->sql_in_set('user_id', $user_id) : 'user_id = ' . (int) $user_id) : ''); $this->db->sql_query($sql); -- cgit v1.2.1 From 94ffbb4050b2985ee62be0ecc0c6a244532e43ca Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sat, 13 Oct 2012 23:24:30 -0500 Subject: [ticket/11103] Add is_disabled column to notifications table EXTENSION AUTHORS TAKE NOTE! This is to prevent errors with notifications from extensions! Set is_disabled to 1 for all your notifications when your extension is disabled so they are ignored and do not cause errors. When your extension is enabled again, set is_disabled to 0 and your notifications will be working again. PHPBB3-11103 --- phpBB/includes/notification/manager.php | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 22fa12967a..16fdae6dd0 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -94,7 +94,8 @@ class phpbb_notification_manager $sql = 'SELECT COUNT(*) AS count FROM ' . NOTIFICATIONS_TABLE . ' WHERE user_id = ' . (int) $options['user_id'] . ' - AND unread = 1'; + AND unread = 1 + AND is_disabled = 0'; $result = $this->db->sql_query($sql); $unread_count = (int) $this->db->sql_fetchfield('count', $result); $this->db->sql_freeresult($result); @@ -105,7 +106,8 @@ class phpbb_notification_manager // Get the total number of notifications $sql = 'SELECT COUNT(*) AS count FROM ' . NOTIFICATIONS_TABLE . ' - WHERE user_id = ' . (int) $options['user_id']; + WHERE user_id = ' . (int) $options['user_id'] . ' + AND is_disabled = 0'; $result = $this->db->sql_query($sql); $total_count = (int) $this->db->sql_fetchfield('count', $result); $this->db->sql_freeresult($result); @@ -118,7 +120,8 @@ class phpbb_notification_manager FROM ' . NOTIFICATIONS_TABLE . ' WHERE user_id = ' . (int) $options['user_id'] . (($options['notification_id']) ? ((is_array($options['notification_id'])) ? ' AND ' . $this->db->sql_in_set('notification_id', $options['notification_id']) : ' AND notification_id = ' . (int) $options['notification_id']) : '') . ' - ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); + AND is_disabled = 0 + ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); $result = $this->db->sql_query_limit($sql, $options['limit'], $options['start']); while ($row = $this->db->sql_fetchrow($result)) @@ -135,7 +138,8 @@ class phpbb_notification_manager WHERE user_id = ' . (int) $options['user_id'] . ' AND unread = 1 AND ' . $this->db->sql_in_set('notification_id', array_keys($rowset), true) . ' - ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); + AND is_disabled = 0 + ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); $result = $this->db->sql_query_limit($sql, $options['limit'], $options['start']); while ($row = $this->db->sql_fetchrow($result)) @@ -344,7 +348,8 @@ class phpbb_notification_manager $sql = 'SELECT user_id FROM ' . NOTIFICATIONS_TABLE . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "' - AND item_id = " . (int) $item_id; + AND item_id = " . (int) $item_id . ' + AND is_disabled = 0'; $result = $this->db->sql_query($sql); while ($row = $this->db->sql_fetchrow($result)) { -- cgit v1.2.1 From c5f280351a96aaebd90c27da095c9b1ff28624a5 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sat, 13 Oct 2012 23:52:49 -0500 Subject: [ticket/11103] UCP Notification option grouping Also add the ability to specify an _EXPLAIN text for the notification option PHPBB3-11103 --- phpBB/includes/notification/manager.php | 23 +++++++++++++++-------- 1 file changed, 15 insertions(+), 8 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 16fdae6dd0..fc9b48c624 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -495,17 +495,24 @@ class phpbb_notification_manager if ($class->is_available() && method_exists($class_name, 'get_item_type')) { - if ($class_name::$notification_option === false) - { - $subscription_types[$class_name::get_item_type()] = $class_name::get_item_type(); - } - else - { - $subscription_types[$class_name::$notification_option['id']] = $class_name::$notification_option; - } + $options = array_merge(array( + 'id' => $class_name::get_item_type(), + 'lang' => 'NOTIFICATION_TYPE_' . strtoupper($class_name::get_item_type()), + 'group' => 'NOTIFICATION_GROUP_MISCELLANEOUS', + ), (($class_name::$notification_option !== false) ? $class_name::$notification_option : array())); + + $subscription_types[$options['group']][$options['id']] = $options; } } + // Move Miscellaneous to the very last section + if (isset($subscription_types['NOTIFICATION_GROUP_MISCELLANEOUS'])) + { + $miscellaneous = $subscription_types['NOTIFICATION_GROUP_MISCELLANEOUS']; + unset($subscription_types['NOTIFICATION_GROUP_MISCELLANEOUS']); + $subscription_types['NOTIFICATION_GROUP_MISCELLANEOUS'] = $miscellaneous; + } + return $subscription_types; } -- cgit v1.2.1 From a48f09033810148fd9b2d5a0b6a683f14ac73a6a Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sun, 14 Oct 2012 12:35:35 -0500 Subject: [ticket/11103] Make sure notifications are marked read when clicking them How do we do this? If an item is unread, the URL to view that item will be the URL to mark it as read (index.php?mark_notification=$id). When the URL is visited it marks the item as read and redirects them to the correct URL for the item. If the item is read, the URL is directly to the item. Prettify the html output PHPBB-11103 --- phpBB/includes/notification/manager.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index fc9b48c624..03776de2b4 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -165,7 +165,7 @@ class phpbb_notification_manager } $load_special[$row['item_type']] = array_merge($load_special[$row['item_type']], $notification->get_load_special()); - $notifications[] = $notification; + $notifications[$row['notification_id']] = $notification; } $this->load_users($user_ids); -- cgit v1.2.1 From eb07b3ad9cfb37fd2943088170e380bff2db94a3 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Thu, 18 Oct 2012 18:45:43 -0500 Subject: [ticket/11103] Expand class vars and use docblocks for phpBB classes PHPBB3-11103 --- phpBB/includes/notification/manager.php | 29 +++++++++++++++++++++++++++-- 1 file changed, 27 insertions(+), 2 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 03776de2b4..a98e1f7af3 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -21,7 +21,32 @@ if (!defined('IN_PHPBB')) */ class phpbb_notification_manager { - protected $db, $cache, $template, $extension_manager, $user, $auth, $config, $phpbb_root_path, $php_ext = null; + /** @var dbal */ + protected $db = null; + + /** @var phpbb_cache_service */ + protected $cache = null; + + /** @var phpbb_template */ + protected $template = null; + + /** @var phpbb_extension_manager */ + protected $extension_manager = null; + + /** @var phpbb_user */ + protected $user = null; + + /** @var phpbb_auth */ + protected $auth = null; + + /** @var phpbb_config */ + protected $config = null; + + /** @var string */ + protected $phpbb_root_path = null; + + /** @var string */ + protected $php_ext = null; /** * Users loaded from the DB @@ -71,7 +96,7 @@ class phpbb_notification_manager 'count_total' => false, ), $options); - // If all_unread, count_unread mus be true + // If all_unread, count_unread must be true $options['count_unread'] = ($options['all_unread']) ? true : $options['count_unread']; // Anonymous users and bots never receive notifications -- cgit v1.2.1 From 2c06c2bd3646585a5b02e6269be655287352a667 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Thu, 18 Oct 2012 19:20:54 -0500 Subject: [ticket/11103] Declare $ for jQuery, check for instance of, newlines at eof PHPBB3-11103 --- phpBB/includes/notification/manager.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index a98e1f7af3..38c72ad755 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -518,7 +518,7 @@ class phpbb_notification_manager $class = $this->get_item_type_class($class_name); - if ($class->is_available() && method_exists($class_name, 'get_item_type')) + if ($class instanceof phpbb_notification_type_interface && $class->is_available() && method_exists($class_name, 'get_item_type')) { $options = array_merge(array( 'id' => $class_name::get_item_type(), @@ -556,7 +556,7 @@ class phpbb_notification_manager $method = $this->get_method_class($class_name); - if ($method->is_available()) + if ($method instanceof phpbb_notification_method_interface && $method->is_available()) { $subscription_methods[] = $method_name; } -- cgit v1.2.1 From 471ca5e7dc8276e80e790e05a2ae36dfe35cfe10 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Fri, 19 Oct 2012 15:49:49 -0500 Subject: [ticket/11103] Change is_disabled to is_enabled If you're following along and would like to update your DB, you can run the following queries to do so: ALTER TABLE phpbb_notifications CHANGE `is_disabled` `is_enabled` TINYINT( 1 ) NOT NULL DEFAULT '1'; UPDATE `phpbb_notifications` SET is_enabled = 1; PHPBB3-11103 --- phpBB/includes/notification/manager.php | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 38c72ad755..3a4c4cd696 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -120,7 +120,7 @@ class phpbb_notification_manager FROM ' . NOTIFICATIONS_TABLE . ' WHERE user_id = ' . (int) $options['user_id'] . ' AND unread = 1 - AND is_disabled = 0'; + AND is_enabled = 1'; $result = $this->db->sql_query($sql); $unread_count = (int) $this->db->sql_fetchfield('count', $result); $this->db->sql_freeresult($result); @@ -132,7 +132,7 @@ class phpbb_notification_manager $sql = 'SELECT COUNT(*) AS count FROM ' . NOTIFICATIONS_TABLE . ' WHERE user_id = ' . (int) $options['user_id'] . ' - AND is_disabled = 0'; + AND is_enabled = 1'; $result = $this->db->sql_query($sql); $total_count = (int) $this->db->sql_fetchfield('count', $result); $this->db->sql_freeresult($result); @@ -145,7 +145,7 @@ class phpbb_notification_manager FROM ' . NOTIFICATIONS_TABLE . ' WHERE user_id = ' . (int) $options['user_id'] . (($options['notification_id']) ? ((is_array($options['notification_id'])) ? ' AND ' . $this->db->sql_in_set('notification_id', $options['notification_id']) : ' AND notification_id = ' . (int) $options['notification_id']) : '') . ' - AND is_disabled = 0 + AND is_enabled = 1 ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); $result = $this->db->sql_query_limit($sql, $options['limit'], $options['start']); @@ -163,7 +163,7 @@ class phpbb_notification_manager WHERE user_id = ' . (int) $options['user_id'] . ' AND unread = 1 AND ' . $this->db->sql_in_set('notification_id', array_keys($rowset), true) . ' - AND is_disabled = 0 + AND is_is_enabled = 1 ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); $result = $this->db->sql_query_limit($sql, $options['limit'], $options['start']); @@ -374,7 +374,7 @@ class phpbb_notification_manager FROM ' . NOTIFICATIONS_TABLE . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND item_id = " . (int) $item_id . ' - AND is_disabled = 0'; + AND is_enabled = 1'; $result = $this->db->sql_query($sql); while ($row = $this->db->sql_fetchrow($result)) { -- cgit v1.2.1 From 94d682f77431add84867bb0b196ad0719b293606 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sat, 20 Oct 2012 20:54:18 -0500 Subject: [ticket/11103] Use the full class name as the item_type/method This is going to require you recreate the db tables. PHPBB3-11103 --- phpBB/includes/notification/manager.php | 200 +++++++++++--------------------- 1 file changed, 67 insertions(+), 133 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 3a4c4cd696..06ebaf24c4 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -138,32 +138,16 @@ class phpbb_notification_manager $this->db->sql_freeresult($result); } - $rowset = array(); - - // Get the main notifications - $sql = 'SELECT * - FROM ' . NOTIFICATIONS_TABLE . ' - WHERE user_id = ' . (int) $options['user_id'] . - (($options['notification_id']) ? ((is_array($options['notification_id'])) ? ' AND ' . $this->db->sql_in_set('notification_id', $options['notification_id']) : ' AND notification_id = ' . (int) $options['notification_id']) : '') . ' - AND is_enabled = 1 - ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); - $result = $this->db->sql_query_limit($sql, $options['limit'], $options['start']); - - while ($row = $this->db->sql_fetchrow($result)) + if (!$options['count_total'] || $total_count) { - $rowset[$row['notification_id']] = $row; - } - $this->db->sql_freeresult($result); + $rowset = array(); - // Get all unread notifications - if ($unread_count && $options['all_unread'] && !empty($rowset)) - { + // Get the main notifications $sql = 'SELECT * FROM ' . NOTIFICATIONS_TABLE . ' - WHERE user_id = ' . (int) $options['user_id'] . ' - AND unread = 1 - AND ' . $this->db->sql_in_set('notification_id', array_keys($rowset), true) . ' - AND is_is_enabled = 1 + WHERE user_id = ' . (int) $options['user_id'] . + (($options['notification_id']) ? ((is_array($options['notification_id'])) ? ' AND ' . $this->db->sql_in_set('notification_id', $options['notification_id']) : ' AND notification_id = ' . (int) $options['notification_id']) : '') . ' + AND is_enabled = 1 ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); $result = $this->db->sql_query_limit($sql, $options['limit'], $options['start']); @@ -172,37 +156,52 @@ class phpbb_notification_manager $rowset[$row['notification_id']] = $row; } $this->db->sql_freeresult($result); - } - - foreach ($rowset as $row) - { - $item_type_class_name = $this->get_item_type_class_name($row['item_type'], true); - $notification = $this->get_item_type_class($item_type_class_name, $row); - - // Array of user_ids to query all at once - $user_ids = array_merge($user_ids, $notification->users_to_query()); - - // Some notification types also require querying additional tables themselves - if (!isset($load_special[$row['item_type']])) + // Get all unread notifications + if ($unread_count && $options['all_unread'] && !empty($rowset)) { - $load_special[$row['item_type']] = array(); + $sql = 'SELECT * + FROM ' . NOTIFICATIONS_TABLE . ' + WHERE user_id = ' . (int) $options['user_id'] . ' + AND unread = 1 + AND ' . $this->db->sql_in_set('notification_id', array_keys($rowset), true) . ' + AND is_enabled = 1 + ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); + $result = $this->db->sql_query_limit($sql, $options['limit'], $options['start']); + + while ($row = $this->db->sql_fetchrow($result)) + { + $rowset[$row['notification_id']] = $row; + } + $this->db->sql_freeresult($result); } - $load_special[$row['item_type']] = array_merge($load_special[$row['item_type']], $notification->get_load_special()); - $notifications[$row['notification_id']] = $notification; - } + foreach ($rowset as $row) + { + $notification = $this->get_item_type_class($row['item_type'], $row); - $this->load_users($user_ids); + // Array of user_ids to query all at once + $user_ids = array_merge($user_ids, $notification->users_to_query()); - // Allow each type to load its own special items - foreach ($load_special as $item_type => $data) - { - $item_type_class_name = $this->get_item_type_class_name($item_type, true); + // Some notification types also require querying additional tables themselves + if (!isset($load_special[$row['item_type']])) + { + $load_special[$row['item_type']] = array(); + } + $load_special[$row['item_type']] = array_merge($load_special[$row['item_type']], $notification->get_load_special()); + + $notifications[$row['notification_id']] = $notification; + } + + $this->load_users($user_ids); - $item_class = $this->get_item_type_class($item_type_class_name); + // Allow each type to load its own special items + foreach ($load_special as $item_type => $data) + { + $item_class = $this->get_item_type_class($item_type); - $item_class->load_special($data, $notifications); + $item_class->load_special($data, $notifications); + } } return array( @@ -234,11 +233,6 @@ class phpbb_notification_manager $time = ($time) ?: time(); - if ($item_type !== false) - { - $this->get_item_type_class_name($item_type); - } - $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " SET unread = 0 WHERE time <= " . $time . @@ -270,8 +264,6 @@ class phpbb_notification_manager $time = ($time) ?: time(); - $item_type_class_name = $this->get_item_type_class_name($item_type); - $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " SET unread = 0 WHERE item_type = '" . $this->db->sql_escape($item_type) . "' @@ -326,12 +318,10 @@ class phpbb_notification_manager return $notified_users; } - $item_type_class_name = $this->get_item_type_class_name($item_type); - - $item_id = $item_type_class_name::get_item_id($data); + $item_id = $item_type::get_item_id($data); // find out which users want to receive this type of notification - $notify_users = $this->get_item_type_class($item_type_class_name)->find_users_for_notification($data, $options); + $notify_users = $this->get_item_type_class($item_type)->find_users_for_notification($data, $options); $this->add_notifications_for_users($item_type, $data, $notify_users); @@ -357,9 +347,7 @@ class phpbb_notification_manager return; } - $item_type_class_name = $this->get_item_type_class_name($item_type); - - $item_id = $item_type_class_name::get_item_id($data); + $item_id = $item_type::get_item_id($data); $user_ids = array(); $notification_objects = $notification_methods = array(); @@ -388,14 +376,14 @@ class phpbb_notification_manager } // Allow notifications to perform actions before creating the insert array (such as run a query to cache some data needed for all notifications) - $notification = $this->get_item_type_class($item_type_class_name); + $notification = $this->get_item_type_class($item_type); $pre_create_data = $notification->pre_create_insert_array($data, $notify_users); unset($notification); // Go through each user so we can insert a row in the DB and then notify them by their desired means foreach ($notify_users as $user => $methods) { - $notification = $this->get_item_type_class($item_type_class_name); + $notification = $this->get_item_type_class($item_type); $notification->user_id = (int) $user; @@ -412,8 +400,7 @@ class phpbb_notification_manager { if (!isset($notification_methods[$method])) { - $method_class_name = 'phpbb_notification_method_' . $method; - $notification_methods[$method] = $this->get_method_class($method_class_name); + $notification_methods[$method] = $this->get_method_class($method); } $notification_methods[$method]->add_to_queue($notification); @@ -452,21 +439,19 @@ class phpbb_notification_manager return; } - $item_type_class_name = $this->get_item_type_class_name($item_type); + $notification = $this->get_item_type_class($item_type); // Allow the notifications class to over-ride the update_notifications functionality - if (method_exists($item_type_class_name, 'update_notifications')) + if (method_exists($notification, 'update_notifications')) { // Return False to over-ride the rest of the update - if ($this->get_item_type_class($item_type_class_name)->update_notifications($data) === false) + if ($notification->update_notifications($data) === false) { return; } } - $item_id = $item_type_class_name::get_item_id($data); - - $notification = $this->get_item_type_class($item_type_class_name); + $item_id = $item_type::get_item_id($data); $update_array = $notification->create_update_array($data); $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . ' @@ -495,8 +480,6 @@ class phpbb_notification_manager return; } - $this->get_item_type_class_name($item_type); - $sql = 'DELETE FROM ' . NOTIFICATIONS_TABLE . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND " . (is_array($item_id) ? $this->db->sql_in_set('item_id', $item_id) : 'item_id = ' . (int) $item_id); @@ -512,17 +495,15 @@ class phpbb_notification_manager { $subscription_types = array(); - foreach ($this->get_subscription_files('notification/type/') as $class_name => $file) + foreach ($this->get_subscription_files('notification/type/') as $class_name) { - $class_name = $this->get_item_type_class_name($class_name); - $class = $this->get_item_type_class($class_name); - if ($class instanceof phpbb_notification_type_interface && $class->is_available() && method_exists($class_name, 'get_item_type')) + if ($class instanceof phpbb_notification_type_interface && $class->is_available()) { $options = array_merge(array( - 'id' => $class_name::get_item_type(), - 'lang' => 'NOTIFICATION_TYPE_' . strtoupper($class_name::get_item_type()), + 'id' => $class_name, + 'lang' => 'NOTIFICATION_TYPE_' . strtoupper($class_name), 'group' => 'NOTIFICATION_GROUP_MISCELLANEOUS', ), (($class_name::$notification_option !== false) ? $class_name::$notification_option : array())); @@ -550,15 +531,13 @@ class phpbb_notification_manager { $subscription_methods = array(); - foreach ($this->get_subscription_files('notification/method/') as $method_name => $file) + foreach ($this->get_subscription_files('notification/method/') as $class_name) { - $class_name = 'phpbb_notification_method_' . $method_name; - $method = $this->get_method_class($class_name); if ($method instanceof phpbb_notification_method_interface && $method->is_available()) { - $subscription_methods[] = $method_name; + $subscription_methods[] = $class_name; } } @@ -615,8 +594,6 @@ class phpbb_notification_manager */ public function add_subscription($item_type, $item_id = 0, $method = '', $user_id = false) { - $this->get_item_type_class_name($item_type); - $user_id = ($user_id === false) ? $this->user->data['user_id'] : $user_id; $sql = 'INSERT INTO ' . USER_NOTIFICATIONS_TABLE . ' ' . @@ -639,8 +616,6 @@ class phpbb_notification_manager */ public function delete_subscription($item_type, $item_id = 0, $method = '', $user_id = false) { - $this->get_item_type_class_name($item_type); - $user_id = ($user_id === false) ? $this->user->data['user_id'] : $user_id; $sql = 'DELETE FROM ' . USER_NOTIFICATIONS_TABLE . " @@ -692,37 +667,11 @@ class phpbb_notification_manager return (isset($this->users[$user_id])) ? $this->users[$user_id] : $this->users[ANONYMOUS]; } - /** - * Helper to get the notifications item type class name and clean it if unsafe - */ - private function get_item_type_class_name(&$item_type, $safe = false) - { - if (!$safe) - { - $item_type = preg_replace('#[^a-z_-]#', '', $item_type); - } - - if (strpos($item_type, 'ext_') === 0) - { - $item_type_ary = explode('-', substr($item_type, 4), 2); - - return 'phpbb_ext_' . $item_type_ary[0] . '_notification_type_' . $item_type_ary[1]; - } - - return 'phpbb_notification_type_' . $item_type; - } - /** * Helper to get the notifications item type class and set it up */ public function get_item_type_class($item_type, $data = array()) { - if (!strpos($item_type, 'notification_type_')) - { - $item_class = $this->get_item_type_class_name($item_type); - $item_type = $item_class; - } - $item = new $item_type($this, $this->db, $this->cache, $this->template, $this->extension_manager, $this->user, $this->auth, $this->config, $this->phpbb_root_path, $this->php_ext); $item->set_initial_data($data); @@ -747,31 +696,16 @@ class phpbb_notification_manager $subscription_files = array(); - $files = $finder + $classes = $finder ->core_path('includes/' . $path) ->extension_directory($path) - ->get_files(); - foreach ($files as $file) - { - $name = substr($file, strrpos($file, '/')); - $name = substr($name, 1, (strpos($name, '.' . $this->php_ext) - 1)); + ->get_classes(); - if ($name == 'interface' || $name == 'base') - { - continue; - } - - if (!strpos($file, 'includes/')) // is an extension - { - $ext_name = substr($file, (strpos($file, 'ext/') + 4)); - $ext_name = substr($ext_name, 0, strpos($ext_name, '/')); - - $name = 'ext_' . $ext_name . '-' . $name; - } - - $subscription_files[$name] = $file; - } + unset($classes[array_search('phpbb_notification_type_interface', $classes)]); + unset($classes[array_search('phpbb_notification_type_base', $classes)]); + unset($classes[array_search('phpbb_notification_method_interface', $classes)]); + unset($classes[array_search('phpbb_notification_method_base', $classes)]); - return $subscription_files; + return $classes; } } -- cgit v1.2.1 From bc18e368c36af90b2e998913e827dc7be71f3bd0 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sat, 20 Oct 2012 21:55:58 -0500 Subject: [ticket/11103] Correct the test case Fix a bug that broke it and make sure to set the needed config/auth settings PHPBB3-11103 --- phpBB/includes/notification/manager.php | 23 +++++++++++++++++++---- 1 file changed, 19 insertions(+), 4 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 06ebaf24c4..75155c5dc3 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -701,10 +701,25 @@ class phpbb_notification_manager ->extension_directory($path) ->get_classes(); - unset($classes[array_search('phpbb_notification_type_interface', $classes)]); - unset($classes[array_search('phpbb_notification_type_base', $classes)]); - unset($classes[array_search('phpbb_notification_method_interface', $classes)]); - unset($classes[array_search('phpbb_notification_method_base', $classes)]); + if (array_search('phpbb_notification_type_interface', $classes) !== false) + { + unset($classes[array_search('phpbb_notification_type_interface', $classes)]); + } + + if (array_search('phpbb_notification_type_base', $classes) !== false) + { + unset($classes[array_search('phpbb_notification_type_base', $classes)]); + } + + if (array_search('phpbb_notification_method_interface', $classes) !== false) + { + unset($classes[array_search('phpbb_notification_method_interface', $classes)]); + } + + if (array_search('phpbb_notification_method_base', $classes) !== false) + { + unset($classes[array_search('phpbb_notification_method_base', $classes)]); + } return $classes; } -- cgit v1.2.1 From e549b7663da47d7518b93074e513c7e1d034bf52 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Mon, 29 Oct 2012 18:09:20 -0500 Subject: [ticket/11103] Set basic notifications to be enabled by default Now, if there is no row for the user in the user_notifications table, the user will receive basic notifications. If the user wishes to not receive notifications, a row must be added with notify = 0. For other methods besides the basic (e.g. email, jabber) a row must still be added with notify = 1 for them to receive notifications PHPBB3-11103 --- phpBB/includes/notification/manager.php | 131 +++++++++++++++++++++++++------- 1 file changed, 105 insertions(+), 26 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 75155c5dc3..3e816108f4 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -545,41 +545,57 @@ class phpbb_notification_manager } /** - * Get subscriptions + * Get global subscriptions (item_id = 0) * * @param bool|int $user_id The user_id to add the subscription for (bool false for current user) - * @param bool $only_global True to select only global subscription options (item_id = 0) * * @return array Subscriptions */ - public function get_subscriptions($user_id = false, $only_global = false) + public function get_global_subscriptions($user_id = false) { $user_id = ($user_id === false) ? $this->user->data['user_id'] : $user_id; $subscriptions = array(); - $sql = 'SELECT * - FROM ' . USER_NOTIFICATIONS_TABLE . ' - WHERE user_id = ' . (int) $user_id . - (($only_global) ? ' AND item_id = 0' : ''); - $result = $this->db->sql_query($sql); - while ($row = $this->db->sql_fetchrow($result)) + foreach ($this->get_subscription_types() as $group_name => $types) { - if ($only_global) + foreach ($types as $id => $type) { - if (!isset($subscriptions[$row['item_type']])) + $sql = 'SELECT method, notify + FROM ' . USER_NOTIFICATIONS_TABLE . ' + WHERE user_id = ' . (int) $user_id . " + AND item_type = '" . $this->db->sql_escape($id) . "' + AND item_id = 0"; + $result = $this->db->sql_query($sql); + + $row = $this->db->sql_fetchrow($result); + if (!$row) { - $subscriptions[$row['item_type']] = array(); + // No rows at all, default to '' + $subscriptions[$id] = array(''); } + else + { + do + { + if (!$row['notify']) + { + continue; + } - $subscriptions[$row['item_type']][] = $row['method']; - } - else - { - $subscriptions[] = $row; + if (!isset($subscriptions[$id])) + { + $subscriptions[$id] = array(); + } + + $subscriptions[$id][] = $row['method']; + } + while ($row = $this->db->sql_fetchrow($result)); + } + + $this->db->sql_freeresult($result); } } - $this->db->sql_freeresult($result); return $subscriptions; } @@ -594,16 +610,45 @@ class phpbb_notification_manager */ public function add_subscription($item_type, $item_id = 0, $method = '', $user_id = false) { + if ($method !== '') + { + $this->add_subscription($item_type, $item_type, '', $user_id); + } + $user_id = ($user_id === false) ? $this->user->data['user_id'] : $user_id; - $sql = 'INSERT INTO ' . USER_NOTIFICATIONS_TABLE . ' ' . - $this->db->sql_build_array('INSERT', array( - 'item_type' => $item_type, - 'item_id' => (int) $item_id, - 'user_id' => (int) $user_id, - 'method' => $method, - )); + $sql = 'SELECT notify + FROM ' . USER_NOTIFICATIONS_TABLE . " + WHERE item_type = '" . $this->db->sql_escape($item_type) . "' + AND item_id = " . (int) $item_id . ' + AND user_id = ' .(int) $user_id . " + AND method = '" . $this->db->sql_escape($method) . "'"; $this->db->sql_query($sql); + $current = $this->db->sql_fetchfield('notify'); + $this->db->sql_freeresult(); + + if ($current === false) + { + $sql = 'INSERT INTO ' . USER_NOTIFICATIONS_TABLE . ' ' . + $this->db->sql_build_array('INSERT', array( + 'item_type' => $item_type, + 'item_id' => (int) $item_id, + 'user_id' => (int) $user_id, + 'method' => $method, + 'notify' => 1, + )); + $this->db->sql_query($sql); + } + else if (!$current) + { + $sql = 'UPDATE ' . USER_NOTIFICATIONS_TABLE . " + SET notify = 1 + WHERE item_type = '" . $this->db->sql_escape($item_type) . "' + AND item_id = " . (int) $item_id . ' + AND user_id = ' .(int) $user_id . " + AND method = '" . $this->db->sql_escape($method) . "'"; + $this->db->sql_query($sql); + } } /** @@ -618,12 +663,46 @@ class phpbb_notification_manager { $user_id = ($user_id === false) ? $this->user->data['user_id'] : $user_id; - $sql = 'DELETE FROM ' . USER_NOTIFICATIONS_TABLE . " + // If no method, make sure that no other notification methods for this item are selected before deleting + if ($method === '') + { + $sql = 'SELECT COUNT(*) as count + FROM ' . USER_NOTIFICATIONS_TABLE . " + WHERE item_type = '" . $this->db->sql_escape($item_type) . "' + AND item_id = " . (int) $item_id . ' + AND user_id = ' .(int) $user_id . " + AND method <> '' + AND notify = 1"; + $this->db->sql_query($sql); + $count = $this->db->sql_fetchfield('count'); + $this->db->sql_freeresult(); + + if ($count) + { + return; + } + } + + $sql = 'UPDATE ' . USER_NOTIFICATIONS_TABLE . " + SET notify = 0 WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND item_id = " . (int) $item_id . ' AND user_id = ' .(int) $user_id . " AND method = '" . $this->db->sql_escape($method) . "'"; $this->db->sql_query($sql); + + if (!$this->db->sql_affectedrows()) + { + $sql = 'INSERT INTO ' . USER_NOTIFICATIONS_TABLE . ' ' . + $this->db->sql_build_array('INSERT', array( + 'item_type' => $item_type, + 'item_id' => (int) $item_id, + 'user_id' => (int) $user_id, + 'method' => $method, + 'notify' => 0, + )); + $this->db->sql_query($sql); + } } /** -- cgit v1.2.1 From ecf6f1eb8ca34da43b14b2da642cc7f1aa397d36 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Mon, 29 Oct 2012 18:15:01 -0500 Subject: [ticket/11103] Code cleanup PHPBB3-11103 --- phpBB/includes/notification/manager.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 3e816108f4..ffdce2032d 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -231,7 +231,7 @@ class phpbb_notification_manager return; } - $time = ($time) ?: time(); + $time = ($time !== false) ? $time : time(); $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " SET unread = 0 -- cgit v1.2.1 From b60ae30b02c411db5ce3711f25e8f43a019ef9ec Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Mon, 29 Oct 2012 18:20:07 -0500 Subject: [ticket/11103] More cleanup PHPBB3-11103 --- phpBB/includes/notification/manager.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index ffdce2032d..b8c9c9742e 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -262,7 +262,7 @@ class phpbb_notification_manager return; } - $time = ($time) ?: time(); + $time = ($time !== false) ? $time : time(); $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " SET unread = 0 @@ -281,7 +281,7 @@ class phpbb_notification_manager */ public function mark_notifications_read_by_id($notification_id, $time = false) { - $time = ($time) ?: time(); + $time = ($time !== false) ? $time : time(); $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " SET unread = 0 -- cgit v1.2.1 From 05e74b82ac5b65896b1a6aa5b7bca7aa1acd3ada Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Mon, 29 Oct 2012 23:34:51 -0500 Subject: [ticket/11103] enable/disable notifications functions disable_notifications This should be called when an extension which has notification types is disabled so that all those notifications are hidden and do not cause errors enable_notifications This should be called when an extension which has notification types that was disabled is re-enabled so that all those notifications that were hidden are shown again PHPBB3-11103 --- phpBB/includes/notification/manager.php | 32 ++++++++++++++++++++++++++++++++ 1 file changed, 32 insertions(+) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index b8c9c9742e..fef93a30c2 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -705,6 +705,38 @@ class phpbb_notification_manager } } + /** + * Disable all notifications of a certain type + * This should be called when an extension which has notification types + * is disabled so that all those notifications are hidden and do not + * cause errors + * + * @param string $item_type + */ + public function disable_notifications($item_type) + { + $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " + SET is_enabled = 0 + WHERE item_type = '" . $this->db->sql_escape($item_type) . "'"; + $this->db->sql_query($sql); + } + + /** + * Enable all notifications of a certain type + * This should be called when an extension which has notification types + * that was disabled is re-enabled so that all those notifications that + * were hidden are shown again + * + * @param string $item_type + */ + public function enable_notifications($item_type) + { + $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " + SET is_enabled = 1 + WHERE item_type = '" . $this->db->sql_escape($item_type) . "'"; + $this->db->sql_query($sql); + } + /** * Load user helper * -- cgit v1.2.1 From f09ee162528d931aabc3f216410d02d3a072c21d Mon Sep 17 00:00:00 2001 From: Nathaniel Guse Date: Fri, 9 Nov 2012 07:40:08 -0600 Subject: [ticket/11103] Use phpBB Container to load types/methods PHPBB3-11103 --- phpBB/includes/notification/manager.php | 70 ++++++++++----------------------- 1 file changed, 21 insertions(+), 49 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index fef93a30c2..102623ab93 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -7,6 +7,8 @@ * */ +use Symfony\Component\DependencyInjection\ContainerBuilder; + /** * @ignore */ @@ -21,6 +23,9 @@ if (!defined('IN_PHPBB')) */ class phpbb_notification_manager { + /** @var ContainerBuilder */ + protected $phpbb_container = null; + /** @var dbal */ protected $db = null; @@ -55,8 +60,9 @@ class phpbb_notification_manager */ protected $users = array(); - public function __construct(dbal $db, phpbb_cache_driver_interface $cache, phpbb_template $template, phpbb_extension_manager $extension_manager, $user, phpbb_auth $auth, phpbb_config $config, $phpbb_root_path, $php_ext) + public function __construct(ContainerBuilder $phpbb_container, dbal $db, phpbb_cache_driver_interface $cache, phpbb_template $template, phpbb_extension_manager $extension_manager, $user, phpbb_auth $auth, phpbb_config $config, $phpbb_root_path, $php_ext) { + $this->phpbb_container = $phpbb_container; $this->db = $db; $this->cache = $cache; $this->template = $template; @@ -495,17 +501,17 @@ class phpbb_notification_manager { $subscription_types = array(); - foreach ($this->get_subscription_files('notification/type/') as $class_name) + foreach ($this->phpbb_container->findTaggedServiceIds('notification.type') as $type_name => $data) { - $class = $this->get_item_type_class($class_name); + $type = $this->get_item_type_class($type_name); - if ($class instanceof phpbb_notification_type_interface && $class->is_available()) + if ($type instanceof phpbb_notification_type_interface && $type->is_available()) { $options = array_merge(array( - 'id' => $class_name, - 'lang' => 'NOTIFICATION_TYPE_' . strtoupper($class_name), + 'id' => $type->get_type(), + 'lang' => 'NOTIFICATION_TYPE_' . strtoupper($type->get_type()), 'group' => 'NOTIFICATION_GROUP_MISCELLANEOUS', - ), (($class_name::$notification_option !== false) ? $class_name::$notification_option : array())); + ), (($type::$notification_option !== false) ? $type::$notification_option : array())); $subscription_types[$options['group']][$options['id']] = $options; } @@ -531,13 +537,16 @@ class phpbb_notification_manager { $subscription_methods = array(); - foreach ($this->get_subscription_files('notification/method/') as $class_name) + foreach ($this->phpbb_container->findTaggedServiceIds('notification.method') as $method_name => $data) { - $method = $this->get_method_class($class_name); + $method = $this->get_method_class($method_name); if ($method instanceof phpbb_notification_method_interface && $method->is_available()) { - $subscription_methods[] = $class_name; + $subscription_methods[$method_name] = array( + 'id' => $method->get_type(), + 'lang' => 'NOTIFICATION_METHOD_' . strtoupper($method->get_type()), + ); } } @@ -783,7 +792,7 @@ class phpbb_notification_manager */ public function get_item_type_class($item_type, $data = array()) { - $item = new $item_type($this, $this->db, $this->cache, $this->template, $this->extension_manager, $this->user, $this->auth, $this->config, $this->phpbb_root_path, $this->php_ext); + $item = $this->phpbb_container->get($item_type); $item->set_initial_data($data); @@ -795,43 +804,6 @@ class phpbb_notification_manager */ public function get_method_class($method_name) { - return new $method_name($this, $this->db, $this->cache, $this->template, $this->extension_manager, $this->user, $this->auth, $this->config, $this->phpbb_root_path, $this->php_ext); - } - - /** - * Helper to get subscription related files with the finder - */ - private function get_subscription_files($path) - { - $finder = $this->extension_manager->get_finder(); - - $subscription_files = array(); - - $classes = $finder - ->core_path('includes/' . $path) - ->extension_directory($path) - ->get_classes(); - - if (array_search('phpbb_notification_type_interface', $classes) !== false) - { - unset($classes[array_search('phpbb_notification_type_interface', $classes)]); - } - - if (array_search('phpbb_notification_type_base', $classes) !== false) - { - unset($classes[array_search('phpbb_notification_type_base', $classes)]); - } - - if (array_search('phpbb_notification_method_interface', $classes) !== false) - { - unset($classes[array_search('phpbb_notification_method_interface', $classes)]); - } - - if (array_search('phpbb_notification_method_base', $classes) !== false) - { - unset($classes[array_search('phpbb_notification_method_base', $classes)]); - } - - return $classes; + return $this->phpbb_container->get($method_name); } } -- cgit v1.2.1 From b8bdcc957bc49b96d43d74077c95a55f4f88e2fa Mon Sep 17 00:00:00 2001 From: Nathaniel Guse Date: Fri, 9 Nov 2012 07:45:23 -0600 Subject: [ticket/11103] count is reserved, do not use in a SQL query PHPBB3-11103 --- phpBB/includes/notification/manager.php | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 102623ab93..ca018fbf3b 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -122,25 +122,25 @@ class phpbb_notification_manager if ($options['count_unread']) { // Get the total number of unread notifications - $sql = 'SELECT COUNT(*) AS count + $sql = 'SELECT COUNT(*) AS unread_count FROM ' . NOTIFICATIONS_TABLE . ' WHERE user_id = ' . (int) $options['user_id'] . ' AND unread = 1 AND is_enabled = 1'; $result = $this->db->sql_query($sql); - $unread_count = (int) $this->db->sql_fetchfield('count', $result); + $unread_count = (int) $this->db->sql_fetchfield('unread_count', $result); $this->db->sql_freeresult($result); } if ($options['count_total']) { // Get the total number of notifications - $sql = 'SELECT COUNT(*) AS count + $sql = 'SELECT COUNT(*) AS total_count FROM ' . NOTIFICATIONS_TABLE . ' WHERE user_id = ' . (int) $options['user_id'] . ' AND is_enabled = 1'; $result = $this->db->sql_query($sql); - $total_count = (int) $this->db->sql_fetchfield('count', $result); + $total_count = (int) $this->db->sql_fetchfield('total_count', $result); $this->db->sql_freeresult($result); } @@ -675,7 +675,7 @@ class phpbb_notification_manager // If no method, make sure that no other notification methods for this item are selected before deleting if ($method === '') { - $sql = 'SELECT COUNT(*) as count + $sql = 'SELECT COUNT(*) as num_notifications FROM ' . USER_NOTIFICATIONS_TABLE . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND item_id = " . (int) $item_id . ' @@ -683,10 +683,10 @@ class phpbb_notification_manager AND method <> '' AND notify = 1"; $this->db->sql_query($sql); - $count = $this->db->sql_fetchfield('count'); + $num_notifications = $this->db->sql_fetchfield('num_notifications'); $this->db->sql_freeresult(); - if ($count) + if ($num_notifications) { return; } -- cgit v1.2.1 From 6a0f6833e61532d28d7bebcc8ad0ec2b2b722e19 Mon Sep 17 00:00:00 2001 From: Nathaniel Guse Date: Fri, 9 Nov 2012 07:48:18 -0600 Subject: [ticket/11103] Comment indentation PHPBB3-11103 --- phpBB/includes/notification/manager.php | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index ca018fbf3b..8392928bd2 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -716,9 +716,10 @@ class phpbb_notification_manager /** * Disable all notifications of a certain type - * This should be called when an extension which has notification types - * is disabled so that all those notifications are hidden and do not - * cause errors + * + * This should be called when an extension which has notification types + * is disabled so that all those notifications are hidden and do not + * cause errors * * @param string $item_type */ @@ -732,9 +733,10 @@ class phpbb_notification_manager /** * Enable all notifications of a certain type - * This should be called when an extension which has notification types - * that was disabled is re-enabled so that all those notifications that - * were hidden are shown again + * + * This should be called when an extension which has notification types + * that was disabled is re-enabled so that all those notifications that + * were hidden are shown again * * @param string $item_type */ -- cgit v1.2.1 From 6c8c54d4d2575cd40fe873cd2108b031ae5830a6 Mon Sep 17 00:00:00 2001 From: Nathaniel Guse Date: Fri, 9 Nov 2012 08:48:41 -0600 Subject: [ticket/11103] Inject table prefix to notifications system instead of constants PHPBB3-11103 --- phpBB/includes/notification/manager.php | 52 ++++++++++++++++++++------------- 1 file changed, 31 insertions(+), 21 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 8392928bd2..3d0ada4a43 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -53,6 +53,12 @@ class phpbb_notification_manager /** @var string */ protected $php_ext = null; + /** @var string */ + protected $notifications_table = null; + + /** @var string */ + protected $user_notifications_table = null; + /** * Users loaded from the DB * @@ -60,7 +66,7 @@ class phpbb_notification_manager */ protected $users = array(); - public function __construct(ContainerBuilder $phpbb_container, dbal $db, phpbb_cache_driver_interface $cache, phpbb_template $template, phpbb_extension_manager $extension_manager, $user, phpbb_auth $auth, phpbb_config $config, $phpbb_root_path, $php_ext) + public function __construct(ContainerBuilder $phpbb_container, dbal $db, phpbb_cache_driver_interface $cache, phpbb_template $template, phpbb_extension_manager $extension_manager, $user, phpbb_auth $auth, phpbb_config $config, $phpbb_root_path, $php_ext, $notifications_table, $user_notifications_table) { $this->phpbb_container = $phpbb_container; $this->db = $db; @@ -70,8 +76,12 @@ class phpbb_notification_manager $this->user = $user; $this->auth = $auth; $this->config = $config; + $this->phpbb_root_path = $phpbb_root_path; $this->php_ext = $php_ext; + + $this->notifications_table = $notifications_table; + $this->user_notifications_table = $user_notifications_table; } /** @@ -123,7 +133,7 @@ class phpbb_notification_manager { // Get the total number of unread notifications $sql = 'SELECT COUNT(*) AS unread_count - FROM ' . NOTIFICATIONS_TABLE . ' + FROM ' . $this->notifications_table . ' WHERE user_id = ' . (int) $options['user_id'] . ' AND unread = 1 AND is_enabled = 1'; @@ -136,7 +146,7 @@ class phpbb_notification_manager { // Get the total number of notifications $sql = 'SELECT COUNT(*) AS total_count - FROM ' . NOTIFICATIONS_TABLE . ' + FROM ' . $this->notifications_table . ' WHERE user_id = ' . (int) $options['user_id'] . ' AND is_enabled = 1'; $result = $this->db->sql_query($sql); @@ -150,7 +160,7 @@ class phpbb_notification_manager // Get the main notifications $sql = 'SELECT * - FROM ' . NOTIFICATIONS_TABLE . ' + FROM ' . $this->notifications_table . ' WHERE user_id = ' . (int) $options['user_id'] . (($options['notification_id']) ? ((is_array($options['notification_id'])) ? ' AND ' . $this->db->sql_in_set('notification_id', $options['notification_id']) : ' AND notification_id = ' . (int) $options['notification_id']) : '') . ' AND is_enabled = 1 @@ -167,7 +177,7 @@ class phpbb_notification_manager if ($unread_count && $options['all_unread'] && !empty($rowset)) { $sql = 'SELECT * - FROM ' . NOTIFICATIONS_TABLE . ' + FROM ' . $this->notifications_table . ' WHERE user_id = ' . (int) $options['user_id'] . ' AND unread = 1 AND ' . $this->db->sql_in_set('notification_id', array_keys($rowset), true) . ' @@ -239,7 +249,7 @@ class phpbb_notification_manager $time = ($time !== false) ? $time : time(); - $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " + $sql = 'UPDATE ' . $this->notifications_table . " SET unread = 0 WHERE time <= " . $time . (($item_type !== false) ? ' AND ' . (is_array($item_type) ? $this->db->sql_in_set('item_type', $item_type) : " item_type = '" . $this->db->sql_escape($item_type) . "'") : '') . @@ -270,7 +280,7 @@ class phpbb_notification_manager $time = ($time !== false) ? $time : time(); - $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " + $sql = 'UPDATE ' . $this->notifications_table . " SET unread = 0 WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND time <= " . $time . @@ -289,7 +299,7 @@ class phpbb_notification_manager { $time = ($time !== false) ? $time : time(); - $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " + $sql = 'UPDATE ' . $this->notifications_table . " SET unread = 0 WHERE time <= " . $time . ' AND ' . ((is_array($notification_id)) ? $this->db->sql_in_set('notification_id', $notification_id) : 'notification_id = ' . (int) $notification_id); @@ -365,7 +375,7 @@ class phpbb_notification_manager // Make sure not to send new notifications to users who've already been notified about this item // This may happen when an item was added, but now new users are able to see the item $sql = 'SELECT user_id - FROM ' . NOTIFICATIONS_TABLE . " + FROM ' . $this->notifications_table . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND item_id = " . (int) $item_id . ' AND is_enabled = 1'; @@ -415,7 +425,7 @@ class phpbb_notification_manager } // insert into the db - $this->db->sql_multi_insert(NOTIFICATIONS_TABLE, $new_rows); + $this->db->sql_multi_insert($this->notifications_table, $new_rows); // We need to load all of the users to send notifications $this->load_users($user_ids); @@ -460,7 +470,7 @@ class phpbb_notification_manager $item_id = $item_type::get_item_id($data); $update_array = $notification->create_update_array($data); - $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . ' + $sql = 'UPDATE ' . $this->notifications_table . ' SET ' . $this->db->sql_build_array('UPDATE', $update_array) . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND item_id = " . (int) $item_id; @@ -486,7 +496,7 @@ class phpbb_notification_manager return; } - $sql = 'DELETE FROM ' . NOTIFICATIONS_TABLE . " + $sql = 'DELETE FROM ' . $this->notifications_table . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND " . (is_array($item_id) ? $this->db->sql_in_set('item_id', $item_id) : 'item_id = ' . (int) $item_id); $this->db->sql_query($sql); @@ -571,7 +581,7 @@ class phpbb_notification_manager foreach ($types as $id => $type) { $sql = 'SELECT method, notify - FROM ' . USER_NOTIFICATIONS_TABLE . ' + FROM ' . $this->user_notifications_table . ' WHERE user_id = ' . (int) $user_id . " AND item_type = '" . $this->db->sql_escape($id) . "' AND item_id = 0"; @@ -627,7 +637,7 @@ class phpbb_notification_manager $user_id = ($user_id === false) ? $this->user->data['user_id'] : $user_id; $sql = 'SELECT notify - FROM ' . USER_NOTIFICATIONS_TABLE . " + FROM ' . $this->user_notifications_table . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND item_id = " . (int) $item_id . ' AND user_id = ' .(int) $user_id . " @@ -638,7 +648,7 @@ class phpbb_notification_manager if ($current === false) { - $sql = 'INSERT INTO ' . USER_NOTIFICATIONS_TABLE . ' ' . + $sql = 'INSERT INTO ' . $this->user_notifications_table . ' ' . $this->db->sql_build_array('INSERT', array( 'item_type' => $item_type, 'item_id' => (int) $item_id, @@ -650,7 +660,7 @@ class phpbb_notification_manager } else if (!$current) { - $sql = 'UPDATE ' . USER_NOTIFICATIONS_TABLE . " + $sql = 'UPDATE ' . $this->user_notifications_table . " SET notify = 1 WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND item_id = " . (int) $item_id . ' @@ -676,7 +686,7 @@ class phpbb_notification_manager if ($method === '') { $sql = 'SELECT COUNT(*) as num_notifications - FROM ' . USER_NOTIFICATIONS_TABLE . " + FROM ' . $this->user_notifications_table . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND item_id = " . (int) $item_id . ' AND user_id = ' .(int) $user_id . " @@ -692,7 +702,7 @@ class phpbb_notification_manager } } - $sql = 'UPDATE ' . USER_NOTIFICATIONS_TABLE . " + $sql = 'UPDATE ' . $this->user_notifications_table . " SET notify = 0 WHERE item_type = '" . $this->db->sql_escape($item_type) . "' AND item_id = " . (int) $item_id . ' @@ -702,7 +712,7 @@ class phpbb_notification_manager if (!$this->db->sql_affectedrows()) { - $sql = 'INSERT INTO ' . USER_NOTIFICATIONS_TABLE . ' ' . + $sql = 'INSERT INTO ' . $this->user_notifications_table . ' ' . $this->db->sql_build_array('INSERT', array( 'item_type' => $item_type, 'item_id' => (int) $item_id, @@ -725,7 +735,7 @@ class phpbb_notification_manager */ public function disable_notifications($item_type) { - $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " + $sql = 'UPDATE ' . $this->notifications_table . " SET is_enabled = 0 WHERE item_type = '" . $this->db->sql_escape($item_type) . "'"; $this->db->sql_query($sql); @@ -742,7 +752,7 @@ class phpbb_notification_manager */ public function enable_notifications($item_type) { - $sql = 'UPDATE ' . NOTIFICATIONS_TABLE . " + $sql = 'UPDATE ' . $this->notifications_table . " SET is_enabled = 1 WHERE item_type = '" . $this->db->sql_escape($item_type) . "'"; $this->db->sql_query($sql); -- cgit v1.2.1 From 2afb8b9df873c3f9572a32ab7a62ea8ba8d8a45b Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Tue, 20 Nov 2012 18:14:48 -0600 Subject: [ticket/11103] Create user loader class, update for DIC Create a very basic user loader class to handle querying/storing user data in a centralized location. Use DIC collection service for notification types/methods. Cleanup unused dependencies. Fix some other issues. PHPBB3-11103 --- phpBB/includes/notification/manager.php | 127 ++++++++++++-------------------- 1 file changed, 48 insertions(+), 79 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 3d0ada4a43..fbfe388c80 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -7,8 +7,6 @@ * */ -use Symfony\Component\DependencyInjection\ContainerBuilder; - /** * @ignore */ @@ -23,30 +21,24 @@ if (!defined('IN_PHPBB')) */ class phpbb_notification_manager { + /** @var array */ + protected $notification_types = null; + + /** @var array */ + protected $notification_methods = null; + /** @var ContainerBuilder */ protected $phpbb_container = null; - - /** @var dbal */ - protected $db = null; - - /** @var phpbb_cache_service */ - protected $cache = null; - /** @var phpbb_template */ - protected $template = null; + /** @var phpbb_user_loader */ + protected $user_loader = null; - /** @var phpbb_extension_manager */ - protected $extension_manager = null; + /** @var dbal */ + protected $db = null; /** @var phpbb_user */ protected $user = null; - /** @var phpbb_auth */ - protected $auth = null; - - /** @var phpbb_config */ - protected $config = null; - /** @var string */ protected $phpbb_root_path = null; @@ -59,23 +51,15 @@ class phpbb_notification_manager /** @var string */ protected $user_notifications_table = null; - /** - * Users loaded from the DB - * - * @var array Array of user data that we've loaded from the DB - */ - protected $users = array(); - - public function __construct(ContainerBuilder $phpbb_container, dbal $db, phpbb_cache_driver_interface $cache, phpbb_template $template, phpbb_extension_manager $extension_manager, $user, phpbb_auth $auth, phpbb_config $config, $phpbb_root_path, $php_ext, $notifications_table, $user_notifications_table) + public function __construct($notification_types, $notification_methods, $phpbb_container, phpbb_user_loader $user_loader, dbal $db, $user, $phpbb_root_path, $php_ext, $notifications_table, $user_notifications_table) { + $this->notification_types = $notification_types; + $this->notification_methods = $notification_methods; $this->phpbb_container = $phpbb_container; + + $this->user_loader = $user_loader; $this->db = $db; - $this->cache = $cache; - $this->template = $template; - $this->extension_manager = $extension_manager; $this->user = $user; - $this->auth = $auth; - $this->config = $config; $this->phpbb_root_path = $phpbb_root_path; $this->php_ext = $php_ext; @@ -209,7 +193,7 @@ class phpbb_notification_manager $notifications[$row['notification_id']] = $notification; } - $this->load_users($user_ids); + $this->user_loader->load_users($user_ids); // Allow each type to load its own special items foreach ($load_special as $item_type => $data) @@ -334,7 +318,7 @@ class phpbb_notification_manager return $notified_users; } - $item_id = $item_type::get_item_id($data); + $item_id = $this->get_item_type_class($item_type)->get_item_id($data); // find out which users want to receive this type of notification $notify_users = $this->get_item_type_class($item_type)->find_users_for_notification($data, $options); @@ -363,7 +347,7 @@ class phpbb_notification_manager return; } - $item_id = $item_type::get_item_id($data); + $item_id = $this->get_item_type_class($item_type)->get_item_id($data); $user_ids = array(); $notification_objects = $notification_methods = array(); @@ -428,7 +412,7 @@ class phpbb_notification_manager $this->db->sql_multi_insert($this->notifications_table, $new_rows); // We need to load all of the users to send notifications - $this->load_users($user_ids); + $this->user_loader->load_users($user_ids); // run the queue for each method to send notifications foreach ($notification_methods as $method) @@ -467,7 +451,7 @@ class phpbb_notification_manager } } - $item_id = $item_type::get_item_id($data); + $item_id = $notification->get_item_id($data); $update_array = $notification->create_update_array($data); $sql = 'UPDATE ' . $this->notifications_table . ' @@ -511,7 +495,7 @@ class phpbb_notification_manager { $subscription_types = array(); - foreach ($this->phpbb_container->findTaggedServiceIds('notification.type') as $type_name => $data) + foreach ($this->notification_types as $type_name => $data) { $type = $this->get_item_type_class($type_name); @@ -547,7 +531,7 @@ class phpbb_notification_manager { $subscription_methods = array(); - foreach ($this->phpbb_container->findTaggedServiceIds('notification.method') as $method_name => $data) + foreach ($this->notification_methods as $method_name => $data) { $method = $this->get_method_class($method_name); @@ -759,63 +743,48 @@ class phpbb_notification_manager } /** - * Load user helper - * - * @param array $user_ids + * Helper to get the notifications item type class and set it up */ - public function load_users($user_ids) + public function get_item_type_class($item_type, $data = array()) { - $user_ids[] = ANONYMOUS; - - // Load the users - $user_ids = array_unique($user_ids); - - // Do not load users we already have in $this->users - $user_ids = array_diff($user_ids, array_keys($this->users)); + $item = $this->load_object('notification.type.' . $item_type); - if (sizeof($user_ids)) - { - $sql = 'SELECT * - FROM ' . USERS_TABLE . ' - WHERE ' . $this->db->sql_in_set('user_id', $user_ids); - $result = $this->db->sql_query($sql); + $item->set_initial_data($data); - while ($row = $this->db->sql_fetchrow($result)) - { - $this->users[$row['user_id']] = $row; - } - $this->db->sql_freeresult($result); - } + return $item; } /** - * Get a user row from our users cache - * - * @param int $user_id - * @return array + * Helper to get the notifications method class and set it up */ - public function get_user($user_id) + public function get_method_class($method_name) { - return (isset($this->users[$user_id])) ? $this->users[$user_id] : $this->users[ANONYMOUS]; + return $this->load_object('notification.method.' . $method_name); } /** - * Helper to get the notifications item type class and set it up + * Helper to load objects (notification types/methods) */ - public function get_item_type_class($item_type, $data = array()) + protected function load_object($object_name) { - $item = $this->phpbb_container->get($item_type); + // Here we cannot just use ContainerBuilder->get(name) + // The reason for this is because get handles services + // which are initialized once and shared. Here we need + // separate new objects because we pass around objects + // that store row data in each object, which would lead + // to over-writing of data if we used get() - $item->set_initial_data($data); + $parameterBag = $this->phpbb_container->getParameterBag(); + $definition = $this->phpbb_container->getDefinition($object_name); + $arguments = $this->phpbb_container->resolveServices( + $parameterBag->unescapeValue($parameterBag->resolveValue($definition->getArguments())) + ); + $r = new \ReflectionClass($parameterBag->resolveValue($definition->getClass())); - return $item; - } + $object = null === $r->getConstructor() ? $r->newInstance() : $r->newInstanceArgs($arguments); - /** - * Helper to get the notifications method class and set it up - */ - public function get_method_class($method_name) - { - return $this->phpbb_container->get($method_name); + $object->set_notification_manager($this); + + return $object; } } -- cgit v1.2.1 From 570c5ad3c08378f377385aaff7d3810ccb8db3ff Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Tue, 20 Nov 2012 23:12:37 -0600 Subject: [ticket/11103] Some comments PHPBB3-11103 --- phpBB/includes/notification/manager.php | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index fbfe388c80..ea91496fb9 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -78,10 +78,15 @@ class phpbb_notification_manager * order_dir Order direction (Default: DESC) * limit Number of notifications to load (Default: 5) * start Notifications offset (Default: 0) - * all_unread Load all unread messages? If set to true, count_unread is set to true (Default: false) - * count_unread Count all unread messages? (Default: false) + * all_unread Load all unread notifications? If set to true, count_unread is set to true (Default: false) + * count_unread Count all unread notifications? (Default: false) + * count_total Count all notifications? (Default: false) + * @return array Array of information based on the request with keys: + * 'notifications' array of notification type objects + * 'unread_count' number of unread notifications the user has if count_unread is true in the options + * 'total_count' number of notifications the user has if count_total is true in the options */ - public function load_notifications($options = array()) + public function load_notifications(array $options = array()) { // Merge default options $options = array_merge(array( @@ -297,8 +302,11 @@ class phpbb_notification_manager * Note: If you send an array of types, any user who could receive multiple notifications from this single item will only receive * a single notification. If they MUST receive multiple notifications, call this function multiple times instead of sending an array * @param array $data Data specific for this type that will be inserted + * @param array $options Optional options to control what notifications are loaded + * ignore_users array of data to specify which users should not receive certain types of notifications + * @return array Information about what users were notified and how they were notified */ - public function add_notifications($item_type, $data, $options = array()) + public function add_notifications($item_type, $data, array $options = array()) { $options = array_merge(array( 'ignore_users' => array(), -- cgit v1.2.1 From c911a34b5b7541b46ee2408da366d2dc7c302090 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Wed, 21 Nov 2012 16:04:01 -0600 Subject: [ticket/11103] Do not prepend notification.(type|method) unless necessary PHPBB3-11103 --- phpBB/includes/notification/manager.php | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index ea91496fb9..4c25fa72f0 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -755,7 +755,9 @@ class phpbb_notification_manager */ public function get_item_type_class($item_type, $data = array()) { - $item = $this->load_object('notification.type.' . $item_type); + $item_type = (strpos($item_type, 'notification.type.') === 0) ? $item_type : 'notification.type.' . $item_type; + + $item = $this->load_object($item_type); $item->set_initial_data($data); @@ -767,7 +769,9 @@ class phpbb_notification_manager */ public function get_method_class($method_name) { - return $this->load_object('notification.method.' . $method_name); + $method_name = (strpos($method_name, 'notification.method.') === 0) ? $method_name : 'notification.method.' . $method_name; + + return $this->load_object($method_name); } /** -- cgit v1.2.1 From 84284a9ccee7d5ccc658c3d1f751a5254b3b9175 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sun, 9 Dec 2012 13:43:06 -0600 Subject: [ticket/11103] Use scope: prototype This lets us clean up the mess that was in load_object(), but requires scope: prototype to be added to the service definitions for all types or methods! PHPBB3-11103 --- phpBB/includes/notification/manager.php | 20 +------------------- 1 file changed, 1 insertion(+), 19 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 4c25fa72f0..22f8f58783 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -779,24 +779,6 @@ class phpbb_notification_manager */ protected function load_object($object_name) { - // Here we cannot just use ContainerBuilder->get(name) - // The reason for this is because get handles services - // which are initialized once and shared. Here we need - // separate new objects because we pass around objects - // that store row data in each object, which would lead - // to over-writing of data if we used get() - - $parameterBag = $this->phpbb_container->getParameterBag(); - $definition = $this->phpbb_container->getDefinition($object_name); - $arguments = $this->phpbb_container->resolveServices( - $parameterBag->unescapeValue($parameterBag->resolveValue($definition->getArguments())) - ); - $r = new \ReflectionClass($parameterBag->resolveValue($definition->getClass())); - - $object = null === $r->getConstructor() ? $r->newInstance() : $r->newInstanceArgs($arguments); - - $object->set_notification_manager($this); - - return $object; + return $this->phpbb_container->get($object_name); } } -- cgit v1.2.1 From ddd874ba76366cebe3cc30df6daa1974e29f34d1 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Thu, 13 Dec 2012 19:46:32 -0600 Subject: [ticket/11103] dbal -> phpbb_db_driver PHPBB3-11103 --- phpBB/includes/notification/manager.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 22f8f58783..653446ab73 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -33,7 +33,7 @@ class phpbb_notification_manager /** @var phpbb_user_loader */ protected $user_loader = null; - /** @var dbal */ + /** @var phpbb_db_driver */ protected $db = null; /** @var phpbb_user */ @@ -51,7 +51,7 @@ class phpbb_notification_manager /** @var string */ protected $user_notifications_table = null; - public function __construct($notification_types, $notification_methods, $phpbb_container, phpbb_user_loader $user_loader, dbal $db, $user, $phpbb_root_path, $php_ext, $notifications_table, $user_notifications_table) + public function __construct($notification_types, $notification_methods, $phpbb_container, phpbb_user_loader $user_loader, phpbb_db_driver $db, $user, $phpbb_root_path, $php_ext, $notifications_table, $user_notifications_table) { $this->notification_types = $notification_types; $this->notification_methods = $notification_methods; -- cgit v1.2.1 From 95bd4d73eb41d677470b0bf77c521ae2a9bb731e Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sat, 15 Dec 2012 10:33:03 -0600 Subject: [ticket/11103] Mark topic/post subscription notification read when approved PHPBB3-11103 --- phpBB/includes/notification/manager.php | 10 ---------- 1 file changed, 10 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 653446ab73..6bf97a3e71 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -226,16 +226,6 @@ class phpbb_notification_manager */ public function mark_notifications_read($item_type, $item_id, $user_id, $time = false) { - if (is_array($item_type)) - { - foreach ($item_type as $type) - { - $this->mark_notifications_read($type, $item_id, $user_id, $time); - } - - return; - } - $time = ($time !== false) ? $time : time(); $sql = 'UPDATE ' . $this->notifications_table . " -- cgit v1.2.1 From d0375c46f91eb88508cbd8e320c7eda78d4f01dd Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sat, 15 Dec 2012 18:25:26 -0600 Subject: [ticket/11103] Purge notifications (to be used when an extension is purged) PHPBB3-11103 --- phpBB/includes/notification/manager.php | 15 +++++++++++++++ 1 file changed, 15 insertions(+) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 653446ab73..fee1d079aa 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -733,6 +733,21 @@ class phpbb_notification_manager $this->db->sql_query($sql); } + /** + * Purge all notifications of a certain type + * + * This should be called when an extension which has notification types + * is purged so that all those notifications are removed + * + * @param string $item_type + */ + public function purge_notifications($item_type) + { + $sql = 'DELETE FROM ' . $this->notifications_table . " + WHERE item_type = '" . $this->db->sql_escape($item_type) . "'"; + $this->db->sql_query($sql); + } + /** * Enable all notifications of a certain type * -- cgit v1.2.1 From c6f138ff12f015543f92d07fb5c93c083a246bab Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sat, 15 Dec 2012 18:35:17 -0600 Subject: [ticket/11103] Prune notifications function To delete all notifications before a certain time PHPBB3-11103 --- phpBB/includes/notification/manager.php | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 90916401c0..a5e1b09754 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -713,7 +713,7 @@ class phpbb_notification_manager * is disabled so that all those notifications are hidden and do not * cause errors * - * @param string $item_type + * @param string $item_type Type identifier of the subscription */ public function disable_notifications($item_type) { @@ -729,7 +729,7 @@ class phpbb_notification_manager * This should be called when an extension which has notification types * is purged so that all those notifications are removed * - * @param string $item_type + * @param string $item_type Type identifier of the subscription */ public function purge_notifications($item_type) { @@ -745,7 +745,7 @@ class phpbb_notification_manager * that was disabled is re-enabled so that all those notifications that * were hidden are shown again * - * @param string $item_type + * @param string $item_type Type identifier of the subscription */ public function enable_notifications($item_type) { @@ -755,6 +755,18 @@ class phpbb_notification_manager $this->db->sql_query($sql); } + /** + * Delete all notifications older than a certain time + * + * @param int $timestamp Unix timestamp to delete all notifications that were created before + */ + public function prune_notifications($timestamp) + { + $sql = 'DELETE FROM ' . $this->notifications_table . ' + WHERE time < ' . (int) $timestamp; + $this->db->sql_query($sql); + } + /** * Helper to get the notifications item type class and set it up */ -- cgit v1.2.1 From f47e51d6dea9d59a36a6babf1f4033104c93a53d Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sat, 15 Dec 2012 19:18:26 -0600 Subject: [ticket/11103] Move is_enabled to a separate table for better performance PHPBB3-11103 --- phpBB/includes/notification/manager.php | 98 +++++++++++++++++++++------------ 1 file changed, 64 insertions(+), 34 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index a5e1b09754..63db3e6e9a 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -45,13 +45,16 @@ class phpbb_notification_manager /** @var string */ protected $php_ext = null; + /** @var string */ + protected $notification_types_table = null; + /** @var string */ protected $notifications_table = null; /** @var string */ protected $user_notifications_table = null; - public function __construct($notification_types, $notification_methods, $phpbb_container, phpbb_user_loader $user_loader, phpbb_db_driver $db, $user, $phpbb_root_path, $php_ext, $notifications_table, $user_notifications_table) + public function __construct($notification_types, $notification_methods, $phpbb_container, phpbb_user_loader $user_loader, phpbb_db_driver $db, $user, $phpbb_root_path, $php_ext, $notification_types_table, $notifications_table, $user_notifications_table) { $this->notification_types = $notification_types; $this->notification_methods = $notification_methods; @@ -64,6 +67,7 @@ class phpbb_notification_manager $this->phpbb_root_path = $phpbb_root_path; $this->php_ext = $php_ext; + $this->notification_types_table = $notification_types_table; $this->notifications_table = $notifications_table; $this->user_notifications_table = $user_notifications_table; } @@ -121,11 +125,12 @@ class phpbb_notification_manager if ($options['count_unread']) { // Get the total number of unread notifications - $sql = 'SELECT COUNT(*) AS unread_count - FROM ' . $this->notifications_table . ' - WHERE user_id = ' . (int) $options['user_id'] . ' - AND unread = 1 - AND is_enabled = 1'; + $sql = 'SELECT COUNT(n.notification_id) AS unread_count + FROM ' . $this->notifications_table . ' n, ' . $this->notification_types_table . ' nt + WHERE n.user_id = ' . (int) $options['user_id'] . ' + AND n.unread = 1 + AND nt.notification_type = n.item_type + AND nt.notification_type_enabled = 1'; $result = $this->db->sql_query($sql); $unread_count = (int) $this->db->sql_fetchfield('unread_count', $result); $this->db->sql_freeresult($result); @@ -134,10 +139,11 @@ class phpbb_notification_manager if ($options['count_total']) { // Get the total number of notifications - $sql = 'SELECT COUNT(*) AS total_count - FROM ' . $this->notifications_table . ' - WHERE user_id = ' . (int) $options['user_id'] . ' - AND is_enabled = 1'; + $sql = 'SELECT COUNT(n.notification_id) AS total_count + FROM ' . $this->notifications_table . ' n, ' . $this->notification_types_table . ' nt + WHERE n.user_id = ' . (int) $options['user_id'] . ' + AND nt.notification_type = n.item_type + AND nt.notification_type_enabled = 1'; $result = $this->db->sql_query($sql); $total_count = (int) $this->db->sql_fetchfield('total_count', $result); $this->db->sql_freeresult($result); @@ -148,12 +154,13 @@ class phpbb_notification_manager $rowset = array(); // Get the main notifications - $sql = 'SELECT * - FROM ' . $this->notifications_table . ' - WHERE user_id = ' . (int) $options['user_id'] . - (($options['notification_id']) ? ((is_array($options['notification_id'])) ? ' AND ' . $this->db->sql_in_set('notification_id', $options['notification_id']) : ' AND notification_id = ' . (int) $options['notification_id']) : '') . ' - AND is_enabled = 1 - ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); + $sql = 'SELECT n.* + FROM ' . $this->notifications_table . ' n, ' . $this->notification_types_table . ' nt + WHERE n.user_id = ' . (int) $options['user_id'] . + (($options['notification_id']) ? ((is_array($options['notification_id'])) ? ' AND ' . $this->db->sql_in_set('n.notification_id', $options['notification_id']) : ' AND n.notification_id = ' . (int) $options['notification_id']) : '') . ' + AND nt.notification_type = n.item_type + AND nt.notification_type_enabled = 1 + ORDER BY n.' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); $result = $this->db->sql_query_limit($sql, $options['limit'], $options['start']); while ($row = $this->db->sql_fetchrow($result)) @@ -165,13 +172,14 @@ class phpbb_notification_manager // Get all unread notifications if ($unread_count && $options['all_unread'] && !empty($rowset)) { - $sql = 'SELECT * - FROM ' . $this->notifications_table . ' - WHERE user_id = ' . (int) $options['user_id'] . ' - AND unread = 1 - AND ' . $this->db->sql_in_set('notification_id', array_keys($rowset), true) . ' - AND is_enabled = 1 - ORDER BY ' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); + $sql = 'SELECT n.* + FROM ' . $this->notifications_table . ' n, ' . $this->notification_types_table . ' nt + WHERE n.user_id = ' . (int) $options['user_id'] . ' + AND n.unread = 1 + AND ' . $this->db->sql_in_set('n.notification_id', array_keys($rowset), true) . ' + AND nt.notification_type = n.item_type + AND nt.notification_type_enabled = 1 + ORDER BY n.' . $this->db->sql_escape($options['order_by']) . ' ' . $this->db->sql_escape($options['order_dir']); $result = $this->db->sql_query_limit($sql, $options['limit'], $options['start']); while ($row = $this->db->sql_fetchrow($result)) @@ -345,6 +353,23 @@ class phpbb_notification_manager return; } + $sql = 'SELECT notification_type + FROM ' . $this->notification_types_table . " + WHERE notification_type = '" . $this->db->sql_escape($item_type) . "'"; + $result = $this->db->sql_query($sql); + + if ($this->db->sql_fetchrow($result) === false) + { + // Does not exist in the database, must add the item type + $sql = 'INSERT INTO ' . $this->notification_types_table . ' ' . $this->db->sql_build_array('INSERT', array( + 'notification_type' => $item_type, + 'notification_type_enabled' => 1, + )); + $this->db->sql_query($sql); + } + + $this->db->sql_freeresult($result); + $item_id = $this->get_item_type_class($item_type)->get_item_id($data); $user_ids = array(); @@ -356,11 +381,12 @@ class phpbb_notification_manager // Make sure not to send new notifications to users who've already been notified about this item // This may happen when an item was added, but now new users are able to see the item - $sql = 'SELECT user_id - FROM ' . $this->notifications_table . " - WHERE item_type = '" . $this->db->sql_escape($item_type) . "' - AND item_id = " . (int) $item_id . ' - AND is_enabled = 1'; + $sql = 'SELECT n.user_id + FROM ' . $this->notifications_table . ' n, ' . $this->notification_types_table . " nt + WHERE n.item_type = '" . $this->db->sql_escape($item_type) . "' + AND n.item_id = " . (int) $item_id . ' + AND nt.notification_type = n.item_type + AND nt.notification_type_enabled = 1'; $result = $this->db->sql_query($sql); while ($row = $this->db->sql_fetchrow($result)) { @@ -717,9 +743,9 @@ class phpbb_notification_manager */ public function disable_notifications($item_type) { - $sql = 'UPDATE ' . $this->notifications_table . " - SET is_enabled = 0 - WHERE item_type = '" . $this->db->sql_escape($item_type) . "'"; + $sql = 'UPDATE ' . $this->notification_types_table . " + SET notification_type_enabled = 0 + WHERE notification_type = '" . $this->db->sql_escape($item_type) . "'"; $this->db->sql_query($sql); } @@ -736,6 +762,10 @@ class phpbb_notification_manager $sql = 'DELETE FROM ' . $this->notifications_table . " WHERE item_type = '" . $this->db->sql_escape($item_type) . "'"; $this->db->sql_query($sql); + + $sql = 'DELETE FROM ' . $this->notification_types_table . " + WHERE notification_type = '" . $this->db->sql_escape($item_type) . "'"; + $this->db->sql_query($sql); } /** @@ -749,9 +779,9 @@ class phpbb_notification_manager */ public function enable_notifications($item_type) { - $sql = 'UPDATE ' . $this->notifications_table . " - SET is_enabled = 1 - WHERE item_type = '" . $this->db->sql_escape($item_type) . "'"; + $sql = 'UPDATE ' . $this->notification_types_table . " + SET notification_type_enabled = 1 + WHERE notification_type = '" . $this->db->sql_escape($item_type) . "'"; $this->db->sql_query($sql); } -- cgit v1.2.1 From 47bed3321634d888a51a611e6586c012a27eb1eb Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sat, 15 Dec 2012 21:02:28 -0600 Subject: [ticket/11103] time -> notification_time PHPBB3-11103 --- phpBB/includes/notification/manager.php | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 63db3e6e9a..8276996b94 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -96,7 +96,7 @@ class phpbb_notification_manager $options = array_merge(array( 'notification_id' => false, 'user_id' => $this->user->data['user_id'], - 'order_by' => 'time', + 'order_by' => 'notification_time', 'order_dir' => 'DESC', 'limit' => 0, 'start' => 0, @@ -238,10 +238,9 @@ class phpbb_notification_manager $sql = 'UPDATE ' . $this->notifications_table . " SET unread = 0 - WHERE time <= " . $time . + WHERE notification_time <= " . $time . (($item_type !== false) ? ' AND ' . (is_array($item_type) ? $this->db->sql_in_set('item_type', $item_type) : " item_type = '" . $this->db->sql_escape($item_type) . "'") : '') . (($item_id !== false) ? ' AND ' . (is_array($item_id) ? $this->db->sql_in_set('item_id', $item_id) : 'item_id = ' . (int) $item_id) : '') . - (($user_id !== false) ? ' AND ' . (is_array($user_id) ? $this->db->sql_in_set('user_id', $user_id) : 'user_id = ' . (int) $user_id) : ''); $this->db->sql_query($sql); } @@ -270,7 +269,7 @@ class phpbb_notification_manager $sql = 'UPDATE ' . $this->notifications_table . " SET unread = 0 WHERE item_type = '" . $this->db->sql_escape($item_type) . "' - AND time <= " . $time . + AND notification_time <= " . $time . (($item_parent_id !== false) ? ' AND ' . (is_array($item_parent_id) ? $this->db->sql_in_set('item_parent_id', $item_parent_id) : 'item_parent_id = ' . (int) $item_parent_id) : '') . (($user_id !== false) ? ' AND ' . (is_array($user_id) ? $this->db->sql_in_set('user_id', $user_id) : 'user_id = ' . (int) $user_id) : ''); $this->db->sql_query($sql); @@ -288,7 +287,7 @@ class phpbb_notification_manager $sql = 'UPDATE ' . $this->notifications_table . " SET unread = 0 - WHERE time <= " . $time . ' + WHERE notification_time <= " . $time . ' AND ' . ((is_array($notification_id)) ? $this->db->sql_in_set('notification_id', $notification_id) : 'notification_id = ' . (int) $notification_id); $this->db->sql_query($sql); } @@ -793,7 +792,7 @@ class phpbb_notification_manager public function prune_notifications($timestamp) { $sql = 'DELETE FROM ' . $this->notifications_table . ' - WHERE time < ' . (int) $timestamp; + WHERE notification_time < ' . (int) $timestamp; $this->db->sql_query($sql); } -- cgit v1.2.1 From fad6bc5a7e58ddd370b88f73712de350b61bca29 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Sat, 15 Dec 2012 21:08:26 -0600 Subject: [ticket/11103] unread -> notification_read PHPBB3-11103 --- phpBB/includes/notification/manager.php | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 8276996b94..fa1fd4b81f 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -128,8 +128,13 @@ class phpbb_notification_manager $sql = 'SELECT COUNT(n.notification_id) AS unread_count FROM ' . $this->notifications_table . ' n, ' . $this->notification_types_table . ' nt WHERE n.user_id = ' . (int) $options['user_id'] . ' +<<<<<<< HEAD AND n.unread = 1 AND nt.notification_type = n.item_type +======= + AND n.notification_read = 0 + AND nt.notification_type = n.notification_type +>>>>>>> 5cedca0... [ticket/11103] unread -> notification_read AND nt.notification_type_enabled = 1'; $result = $this->db->sql_query($sql); $unread_count = (int) $this->db->sql_fetchfield('unread_count', $result); @@ -175,7 +180,7 @@ class phpbb_notification_manager $sql = 'SELECT n.* FROM ' . $this->notifications_table . ' n, ' . $this->notification_types_table . ' nt WHERE n.user_id = ' . (int) $options['user_id'] . ' - AND n.unread = 1 + AND n.notification_read = 0 AND ' . $this->db->sql_in_set('n.notification_id', array_keys($rowset), true) . ' AND nt.notification_type = n.item_type AND nt.notification_type_enabled = 1 @@ -237,7 +242,7 @@ class phpbb_notification_manager $time = ($time !== false) ? $time : time(); $sql = 'UPDATE ' . $this->notifications_table . " - SET unread = 0 + SET notification_read = 1 WHERE notification_time <= " . $time . (($item_type !== false) ? ' AND ' . (is_array($item_type) ? $this->db->sql_in_set('item_type', $item_type) : " item_type = '" . $this->db->sql_escape($item_type) . "'") : '') . (($item_id !== false) ? ' AND ' . (is_array($item_id) ? $this->db->sql_in_set('item_id', $item_id) : 'item_id = ' . (int) $item_id) : '') . @@ -267,8 +272,10 @@ class phpbb_notification_manager $time = ($time !== false) ? $time : time(); $sql = 'UPDATE ' . $this->notifications_table . " - SET unread = 0 + SET notification_read = 1 WHERE item_type = '" . $this->db->sql_escape($item_type) . "' + SET notification_read = 1 + WHERE notification_type = '" . $this->db->sql_escape($notification_type) . "' AND notification_time <= " . $time . (($item_parent_id !== false) ? ' AND ' . (is_array($item_parent_id) ? $this->db->sql_in_set('item_parent_id', $item_parent_id) : 'item_parent_id = ' . (int) $item_parent_id) : '') . (($user_id !== false) ? ' AND ' . (is_array($user_id) ? $this->db->sql_in_set('user_id', $user_id) : 'user_id = ' . (int) $user_id) : ''); @@ -286,7 +293,7 @@ class phpbb_notification_manager $time = ($time !== false) ? $time : time(); $sql = 'UPDATE ' . $this->notifications_table . " - SET unread = 0 + SET notification_read = 1 WHERE notification_time <= " . $time . ' AND ' . ((is_array($notification_id)) ? $this->db->sql_in_set('notification_id', $notification_id) : 'notification_id = ' . (int) $notification_id); $this->db->sql_query($sql); -- cgit v1.2.1 From bf93dceb1f69cddc625b7dbbdf588847660070fa Mon Sep 17 00:00:00 2001 From: Nathaniel Guse Date: Wed, 26 Dec 2012 11:09:03 -0600 Subject: [ticket/11103] Fix merge conflict PHPBB3-11103 --- phpBB/includes/notification/manager.php | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index fa1fd4b81f..9858cda898 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -128,13 +128,8 @@ class phpbb_notification_manager $sql = 'SELECT COUNT(n.notification_id) AS unread_count FROM ' . $this->notifications_table . ' n, ' . $this->notification_types_table . ' nt WHERE n.user_id = ' . (int) $options['user_id'] . ' -<<<<<<< HEAD - AND n.unread = 1 - AND nt.notification_type = n.item_type -======= AND n.notification_read = 0 - AND nt.notification_type = n.notification_type ->>>>>>> 5cedca0... [ticket/11103] unread -> notification_read + AND nt.notification_type = n.item_type AND nt.notification_type_enabled = 1'; $result = $this->db->sql_query($sql); $unread_count = (int) $this->db->sql_fetchfield('unread_count', $result); -- cgit v1.2.1 From 5a8520da62a540f140319ecaef011fc49eaba451 Mon Sep 17 00:00:00 2001 From: Nathaniel Guse Date: Thu, 27 Dec 2012 10:28:57 -0600 Subject: [ticket/11103] Fix some more merging issues PHPBB3-11103 --- phpBB/includes/notification/manager.php | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 9858cda898..52cfa77388 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -240,7 +240,7 @@ class phpbb_notification_manager SET notification_read = 1 WHERE notification_time <= " . $time . (($item_type !== false) ? ' AND ' . (is_array($item_type) ? $this->db->sql_in_set('item_type', $item_type) : " item_type = '" . $this->db->sql_escape($item_type) . "'") : '') . - (($item_id !== false) ? ' AND ' . (is_array($item_id) ? $this->db->sql_in_set('item_id', $item_id) : 'item_id = ' . (int) $item_id) : '') . + (($item_id !== false) ? ' AND ' . (is_array($item_id) ? $this->db->sql_in_set('item_id', $item_id) : 'item_id = ' . (int) $item_id) : ''); $this->db->sql_query($sql); } @@ -269,8 +269,6 @@ class phpbb_notification_manager $sql = 'UPDATE ' . $this->notifications_table . " SET notification_read = 1 WHERE item_type = '" . $this->db->sql_escape($item_type) . "' - SET notification_read = 1 - WHERE notification_type = '" . $this->db->sql_escape($notification_type) . "' AND notification_time <= " . $time . (($item_parent_id !== false) ? ' AND ' . (is_array($item_parent_id) ? $this->db->sql_in_set('item_parent_id', $item_parent_id) : 'item_parent_id = ' . (int) $item_parent_id) : '') . (($user_id !== false) ? ' AND ' . (is_array($user_id) ? $this->db->sql_in_set('user_id', $user_id) : 'user_id = ' . (int) $user_id) : ''); -- cgit v1.2.1 From 07282a30ae077825ea81a4e26839ac0473dc97b7 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Tue, 15 Jan 2013 12:10:07 -0600 Subject: [ticket/11103] Fix some various issues, better comments PHPBB3-11103 --- phpBB/includes/notification/manager.php | 40 +++++++++++++++++++++++---------- 1 file changed, 28 insertions(+), 12 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 52cfa77388..a289ec0dfa 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -22,38 +22,54 @@ if (!defined('IN_PHPBB')) class phpbb_notification_manager { /** @var array */ - protected $notification_types = null; + protected $notification_types; /** @var array */ - protected $notification_methods = null; + protected $notification_methods; /** @var ContainerBuilder */ - protected $phpbb_container = null; + protected $phpbb_container; /** @var phpbb_user_loader */ - protected $user_loader = null; + protected $user_loader; /** @var phpbb_db_driver */ - protected $db = null; + protected $db; /** @var phpbb_user */ - protected $user = null; + protected $user; /** @var string */ - protected $phpbb_root_path = null; + protected $phpbb_root_path; /** @var string */ - protected $php_ext = null; + protected $php_ext; /** @var string */ - protected $notification_types_table = null; + protected $notification_types_table; /** @var string */ - protected $notifications_table = null; + protected $notifications_table; /** @var string */ - protected $user_notifications_table = null; + protected $user_notifications_table; + /** + * Notification Constructor + * + * @param array $notification_types + * @param array $notification_methods + * @param ContainerBuilder $phpbb_container + * @param phpbb_user_loader $user_loader + * @param phpbb_db_driver $db + * @param phpbb_user $user + * @param string $phpbb_root_path + * @param string $php_ext + * @param string $notification_types_table + * @param string $notifications_table + * @param string $user_notifications_table + * @return phpbb_notification_manager + */ public function __construct($notification_types, $notification_methods, $phpbb_container, phpbb_user_loader $user_loader, phpbb_db_driver $db, $user, $phpbb_root_path, $php_ext, $notification_types_table, $notifications_table, $user_notifications_table) { $this->notification_types = $notification_types; @@ -78,7 +94,7 @@ class phpbb_notification_manager * @param array $options Optional options to control what notifications are loaded * notification_id Notification id to load (or array of notification ids) * user_id User id to load notifications for (Default: $user->data['user_id']) - * order_by Order by (Default: time) + * order_by Order by (Default: notification_time) * order_dir Order direction (Default: DESC) * limit Number of notifications to load (Default: 5) * start Notifications offset (Default: 0) -- cgit v1.2.1 From f089e099fed38b1bdae5316fb09f0c8ed847d495 Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Tue, 15 Jan 2013 12:29:20 -0600 Subject: [ticket/11103] Including the set call in the declaration throws errors Call the set_notification_manager from the load_object function instead. PHPBB3-11103 --- phpBB/includes/notification/manager.php | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index a289ec0dfa..5c1016335a 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -841,6 +841,13 @@ class phpbb_notification_manager */ protected function load_object($object_name) { - return $this->phpbb_container->get($object_name); + $object = $this->phpbb_container->get($object_name); + + if (method_exists($object, 'set_notification_manager')) + { + $object->set_notification_manager($this); + } + + return $object; } } -- cgit v1.2.1 From b41b1a36d1ee85abc05c22b443db7b10af077f7e Mon Sep 17 00:00:00 2001 From: Nathan Guse Date: Thu, 28 Feb 2013 15:25:18 -0600 Subject: [ticket/11103] Case time in queries as an int PHPBB3-11103 --- phpBB/includes/notification/manager.php | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'phpBB/includes/notification/manager.php') diff --git a/phpBB/includes/notification/manager.php b/phpBB/includes/notification/manager.php index 5c1016335a..ff83d4bb37 100644 --- a/phpBB/includes/notification/manager.php +++ b/phpBB/includes/notification/manager.php @@ -254,7 +254,7 @@ class phpbb_notification_manager $sql = 'UPDATE ' . $this->notifications_table . " SET notification_read = 1 - WHERE notification_time <= " . $time . + WHERE notification_time <= " . (int) $time . (($item_type !== false) ? ' AND ' . (is_array($item_type) ? $this->db->sql_in_set('item_type', $item_type) : " item_type = '" . $this->db->sql_escape($item_type) . "'") : '') . (($item_id !== false) ? ' AND ' . (is_array($item_id) ? $this->db->sql_in_set('item_id', $item_id) : 'item_id = ' . (int) $item_id) : ''); $this->db->sql_query($sql); @@ -285,7 +285,7 @@ class phpbb_notification_manager $sql = 'UPDATE ' . $this->notifications_table . " SET notification_read = 1 WHERE item_type = '" . $this->db->sql_escape($item_type) . "' - AND notification_time <= " . $time . + AND notification_time <= " . (int) $time . (($item_parent_id !== false) ? ' AND ' . (is_array($item_parent_id) ? $this->db->sql_in_set('item_parent_id', $item_parent_id) : 'item_parent_id = ' . (int) $item_parent_id) : '') . (($user_id !== false) ? ' AND ' . (is_array($user_id) ? $this->db->sql_in_set('user_id', $user_id) : 'user_id = ' . (int) $user_id) : ''); $this->db->sql_query($sql); @@ -303,7 +303,7 @@ class phpbb_notification_manager $sql = 'UPDATE ' . $this->notifications_table . " SET notification_read = 1 - WHERE notification_time <= " . $time . ' + WHERE notification_time <= " . (int) $time . ' AND ' . ((is_array($notification_id)) ? $this->db->sql_in_set('notification_id', $notification_id) : 'notification_id = ' . (int) $notification_id); $this->db->sql_query($sql); } -- cgit v1.2.1