1<?php 2/** 3 * Elgg Pages 4 */ 5 6require_once(dirname(__FILE__) . '/lib/pages.php'); 7 8/** 9 * Initialize the pages plugin 10 * 11 * @return void 12 */ 13function pages_init() { 14 15 // register a library of helper functions 16 \Elgg\Includer::requireFileOnce(__DIR__ . '/lib/pages.php'); 17 18 elgg_register_menu_item('site', [ 19 'name' => 'pages', 20 'icon' => 'file-text-o', 21 'text' => elgg_echo('collection:object:page'), 22 'href' => elgg_generate_url('default:object:page'), 23 ]); 24 25 // Register a url handler 26 elgg_register_plugin_hook_handler('extender:url', 'annotation', 'pages_set_revision_url'); 27 28 // Register for notifications 29 elgg_register_notification_event('object', 'page'); 30 elgg_register_plugin_hook_handler('prepare', 'notification:create:object:page', 'pages_prepare_notification'); 31 32 // add to groups 33 elgg()->group_tools->register('pages'); 34 35 // Language short codes must be of the form "pages:key" 36 // where key is the array key below 37 elgg_set_config('pages', [ 38 'title' => 'text', 39 'description' => 'longtext', 40 'tags' => 'tags', 41 'parent_guid' => 'pages/parent', 42 'access_id' => 'access', 43 'write_access_id' => 'access', 44 ]); 45 46 elgg_register_plugin_hook_handler('register', 'menu:owner_block', 'pages_owner_block_menu'); 47 elgg_register_plugin_hook_handler('register', 'menu:pages_nav', '\Elgg\Pages\Menus::registerPageMenuItems'); 48 elgg_register_plugin_hook_handler('prepare', 'menu:pages_nav', '_elgg_setup_vertical_menu', 999); 49 50 // write permission plugin hooks 51 elgg_register_plugin_hook_handler('permissions_check', 'object', 'pages_write_permission_check'); 52 elgg_register_plugin_hook_handler('container_permissions_check', 'object', 'pages_container_permission_check'); 53 54 elgg_register_plugin_hook_handler('access:collections:write', 'user', 'pages_write_access_options_hook'); 55 56 // icon url override 57 elgg_register_plugin_hook_handler('entity:icon:url', 'object', 'pages_icon_url_override'); 58 59 // entity menu 60 elgg_register_plugin_hook_handler('register', 'menu:entity', 'pages_entity_menu_setup'); 61 62 // register ecml views to parse 63 elgg_register_plugin_hook_handler('get_views', 'ecml', 'pages_ecml_views_hook'); 64 65 // allow to be liked 66 elgg_register_plugin_hook_handler('likes:is_likable', 'object:page', 'Elgg\Values::getTrue'); 67 68 // prevent public write access 69 elgg_register_plugin_hook_handler('view_vars', 'input/access', 'pages_write_access_vars'); 70 71 // register database seed 72 elgg_register_plugin_hook_handler('seeds', 'database', 'pages_register_db_seeds'); 73} 74 75/** 76 * Override the page annotation url 77 * 78 * @param \Elgg\Hook $hook 'extender:url', 'annotation' 79 * 80 * @return void|string 81 */ 82function pages_set_revision_url(\Elgg\Hook $hook) { 83 84 $annotation = $hook->getParam('extender'); 85 if ($annotation->getSubtype() == 'page') { 86 return elgg_generate_url('revision:object:page', [ 87 'id' => $annotation->id, 88 ]); 89 } 90} 91 92/** 93 * Override the default entity icon for pages 94 * 95 * @param \Elgg\Hook $hook 'entity:icon:url', 'object' 96 * 97 * @return string 98 */ 99function pages_icon_url_override(\Elgg\Hook $hook) { 100 if ($hook->getEntityParam() instanceof ElggPage) { 101 return elgg_get_simplecache_url('pages/images/pages.gif'); 102 } 103} 104 105/** 106 * Add a menu item to the user ownerblock 107 * 108 * @param \Elgg\Hook $hook 'register', 'menu:owner_block' 109 * 110 * @return ElggMenuItem[] 111 */ 112function pages_owner_block_menu(\Elgg\Hook $hook) { 113 114 $entity = $hook->getEntityParam(); 115 $return = $hook->getValue(); 116 117 if ($entity instanceof ElggUser) { 118 $url = elgg_generate_url('collection:object:page:owner', [ 119 'username' => $entity->username, 120 ]); 121 $item = new ElggMenuItem('pages', elgg_echo('collection:object:page'), $url); 122 $return[] = $item; 123 } elseif ($entity instanceof ElggGroup) { 124 if ($entity->isToolEnabled('pages')) { 125 $url = elgg_generate_url('collection:object:page:group', [ 126 'guid' => $entity->guid, 127 'subpage' => 'all', 128 ]); 129 $item = new ElggMenuItem('pages', elgg_echo('collection:object:page:group'), $url); 130 $return[] = $item; 131 } 132 } 133 134 return $return; 135} 136 137/** 138 * Add links/info to entity menu particular to pages plugin 139 * 140 * @param \Elgg\Hook $hook 'register', 'menu:entity' 141 * 142 * @return void|ElggMenuItem[] 143 */ 144function pages_entity_menu_setup(\Elgg\Hook $hook) { 145 146 $entity = $hook->getEntityParam(); 147 if (!$entity instanceof ElggPage) { 148 return; 149 } 150 151 if (!$entity->canEdit()) { 152 return; 153 } 154 155 $return = $hook->getValue(); 156 $return[] = \ElggMenuItem::factory([ 157 'name' => 'history', 158 'icon' => 'history', 159 'text' => elgg_echo('pages:history'), 160 'href' => elgg_generate_url('history:object:page', [ 161 'guid' => $entity->guid, 162 ]), 163 ]); 164 165 return $return; 166} 167 168/** 169 * Prepare a notification message about a new page 170 * 171 * @param \Elgg\Hook $hook 'prepare', 'notification:create:object:page' | 'notification:create:object:page_top' 172 * 173 * @return void|Elgg\Notifications\Notification 174 */ 175function pages_prepare_notification(\Elgg\Hook $hook) { 176 177 $event = $hook->getParam('event'); 178 179 $entity = $event->getObject(); 180 if (!$entity instanceof ElggPage) { 181 return; 182 } 183 184 $owner = $event->getActor(); 185 $language = $hook->getParam('language'); 186 187 $descr = $entity->description; 188 $title = $entity->getDisplayName(); 189 190 $notification = $hook->getValue(); 191 $notification->subject = elgg_echo('pages:notify:subject', [$title], $language); 192 $notification->body = elgg_echo('pages:notify:body', [ 193 $owner->getDisplayName(), 194 $title, 195 $descr, 196 $entity->getURL(), 197 ], $language); 198 $notification->summary = elgg_echo('pages:notify:summary', [$entity->getDisplayName()], $language); 199 $notification->url = $entity->getURL(); 200 201 return $notification; 202} 203 204/** 205 * Extend permissions checking to extend can-edit for write users. 206 * 207 * @param \Elgg\Hook $hook 'permissions_check', 'object' 208 * 209 * @return void|bool 210 */ 211function pages_write_permission_check(\Elgg\Hook $hook) { 212 213 $entity = $hook->getEntityParam(); 214 if (!$entity instanceof ElggPage) { 215 return; 216 } 217 218 $write_permission = (int) $entity->write_access_id; 219 $user = $hook->getUserParam(); 220 221 if (empty($write_permission) || !$user instanceof ElggUser) { 222 return; 223 } 224 225 switch ($write_permission) { 226 case ACCESS_PRIVATE: 227 // Elgg's default decision is what we want 228 return; 229 default: 230 $list = get_access_array($user->guid); 231 if (in_array($write_permission, $list)) { 232 // user in the access collection 233 return true; 234 } 235 break; 236 } 237} 238 239/** 240 * Extend container permissions checking to extend container write access for write users, needed for personal pages 241 * 242 * @param \Elgg\Hook $hook 'container_permissions_check', 'object' 243 * 244 * @return void|bool 245 */ 246function pages_container_permission_check(\Elgg\Hook $hook) { 247 248 if ($hook->getValue()) { 249 // already have access 250 return; 251 } 252 253 // check type/subtype 254 if ($hook->getType() !== 'object' || $hook->getParam('subtype') !== 'page') { 255 return; 256 } 257 258 $user = $hook->getUserParam(); 259 if (!$user instanceof ElggUser) { 260 return; 261 } 262 263 // look up a page object given via input 264 $page_guid = (int) get_input('guid'); // defined by route 265 if (empty($page_guid)) { 266 // try the parent guid for use in the action 267 $page_guid = (int) get_input('parent_guid'); 268 } 269 if (empty($page_guid)) { 270 return; 271 } 272 273 $page = get_entity($page_guid); 274 if (!$page instanceof ElggPage) { 275 return; 276 } 277 278 // check if the page write access is in the users read access array 279 return in_array($page->write_access_id, get_access_array($user->guid)); 280} 281 282/** 283 * Return views to parse for pages. 284 * 285 * @param \Elgg\Hook $hook 'get_views', 'ecml' 286 * 287 * @return array 288 */ 289function pages_ecml_views_hook(\Elgg\Hook $hook) { 290 $return_value = $hook->getValue(); 291 $return_value['object/page'] = elgg_echo('item:object:page'); 292 return $return_value; 293} 294 295/** 296 * Is the given value a page object? 297 * 298 * @param ElggObject $value the entity to check 299 * 300 * @return bool 301 * @internal 302 */ 303function pages_is_page($value) { 304 305 if (!$value instanceof ElggObject) { 306 return false; 307 } 308 309 return in_array($value->getSubtype(), ['page', 'page_top']); 310} 311 312/** 313 * Return options for the write_access_id input 314 * 315 * @param \Elgg\Hook $hook 'access:collections:write', 'user' 316 * 317 * @return void|array 318 */ 319function pages_write_access_options_hook(\Elgg\Hook $hook) { 320 321 $input_params = $hook->getParam('input_params'); 322 $return_value = $hook->getValue(); 323 324 if (empty($input_params) || !isset($return_value[ACCESS_PUBLIC])) { 325 return; 326 } 327 328 if (elgg_extract('entity_subtype', $input_params) !== 'page') { 329 return; 330 } 331 332 if (elgg_extract('purpose', $input_params) !== 'write') { 333 return; 334 } 335 336 unset($return_value[ACCESS_PUBLIC]); 337 338 return $return_value; 339} 340 341/** 342 * Called on view_vars, input/access hook 343 * Prevent ACCESS_PUBLIC from ending up as a write access option 344 * 345 * @param \Elgg\Hook $hook 'view_vars', 'input/access' 346 * 347 * @return void|array 348 */ 349function pages_write_access_vars(\Elgg\Hook $hook) { 350 $return = $hook->getValue(); 351 if (elgg_extract('name', $return) !== 'write_access_id' || elgg_extract('purpose', $return) !== 'write') { 352 return; 353 } 354 355 $value = (int) elgg_extract('value', $return); 356 if ($value !== ACCESS_PUBLIC && $value !== ACCESS_DEFAULT) { 357 return; 358 } 359 360 $default_access = get_default_access(); 361 362 if ($value === ACCESS_PUBLIC || $default_access === ACCESS_PUBLIC) { 363 // is the value public, or default which resolves to public? 364 // if so we'll set it to logged in, the next most permissible write access level 365 $return['value'] = ACCESS_LOGGED_IN; 366 } 367 368 return $return; 369} 370 371/** 372 * Register database seed 373 * 374 * @param \Elgg\Hook $hook 'seeds', 'database' 375 * @return array 376 */ 377function pages_register_db_seeds(\Elgg\Hook $hook) { 378 379 $seeds = $hook->getValue(); 380 381 $seeds[] = \Elgg\Pages\Seeder::class; 382 383 return $seeds; 384} 385 386return function() { 387 elgg_register_event_handler('init', 'system', 'pages_init'); 388}; 389