Mercurial > defr > drupal > core
comparison modules/book/book.install @ 1:c1f4ac30525a 6.0
Drupal 6.0
| author | Franck Deroche <webmaster@defr.org> |
|---|---|
| date | Tue, 23 Dec 2008 14:28:28 +0100 |
| parents | |
| children | 3edae6ecd6c6 |
comparison
equal
deleted
inserted
replaced
| 0:5a113a1c4740 | 1:c1f4ac30525a |
|---|---|
| 1 <?php | |
| 2 // $Id: book.install,v 1.20 2008/01/10 18:13:42 goba Exp $ | |
| 3 | |
| 4 /** | |
| 5 * Implementation of hook_install(). | |
| 6 */ | |
| 7 function book_install() { | |
| 8 // Create tables. | |
| 9 drupal_install_schema('book'); | |
| 10 // Add the node type. | |
| 11 _book_install_type_create(); | |
| 12 } | |
| 13 | |
| 14 /** | |
| 15 * Implementation of hook_uninstall(). | |
| 16 */ | |
| 17 function book_uninstall() { | |
| 18 // Delete menu links. | |
| 19 db_query("DELETE FROM {menu_links} WHERE module = 'book'"); | |
| 20 menu_cache_clear_all(); | |
| 21 // Remove tables. | |
| 22 drupal_uninstall_schema('book'); | |
| 23 } | |
| 24 | |
| 25 function _book_install_type_create() { | |
| 26 // Create an additional node type | |
| 27 $book_node_type = array( | |
| 28 'type' => 'book', | |
| 29 'name' => t('Book page'), | |
| 30 'module' => 'node', | |
| 31 'description' => t('A <em>book page</em> is a page of content, organized into a collection of related entries collectively known as a <em>book</em>. A <em>book page</em> automatically displays links to adjacent pages, providing a simple navigation system for organizing and reviewing structured content.'), | |
| 32 'custom' => TRUE, | |
| 33 'modified' => TRUE, | |
| 34 'locked' => FALSE, | |
| 35 ); | |
| 36 | |
| 37 $book_node_type = (object)_node_type_set_defaults($book_node_type); | |
| 38 node_type_save($book_node_type); | |
| 39 // Default to not promoted. | |
| 40 variable_set('node_options_book', array('status')); | |
| 41 // Use this default type for adding content to books. | |
| 42 variable_set('book_allowed_types', array('book')); | |
| 43 variable_set('book_child_type', 'book'); | |
| 44 } | |
| 45 | |
| 46 /** | |
| 47 * Drupal 5.x to 6.x update. | |
| 48 * | |
| 49 * This function moves any existing book hierarchy into the new structure used | |
| 50 * in the 6.x module. Rather than storing the hierarchy in the {book} table, | |
| 51 * the menu API is used to store the hierarchy in the {menu_links} table and the | |
| 52 * {book} table serves to uniquely connect a node to a menu link. | |
| 53 * | |
| 54 * In order to accomplish this, the current hierarchy is processed using a stack. | |
| 55 * The stack insures that each parent is processed before any of its children | |
| 56 * in the book hierarchy, and is compatible with batched update processing. | |
| 57 * | |
| 58 */ | |
| 59 function book_update_6000() { | |
| 60 $ret = array(); | |
| 61 | |
| 62 // Set up for a multi-part update. | |
| 63 if (!isset($_SESSION['book_update_6000'])) { | |
| 64 | |
| 65 $schema['book'] = array( | |
| 66 'fields' => array( | |
| 67 'mlid' => array('type' => 'int', 'unsigned' => TRUE, 'not null' => TRUE, 'default' => 0), | |
| 68 'nid' => array('type' => 'int', 'unsigned' => TRUE, 'not null' => TRUE, 'default' => 0), | |
| 69 'bid' => array('type' => 'int', 'unsigned' => TRUE, 'not null' => TRUE, 'default' => 0), | |
| 70 ), | |
| 71 'primary key' => array('mlid'), | |
| 72 'unique keys' => array( | |
| 73 'nid' => array('nid'), | |
| 74 ), | |
| 75 'indexes' => array( | |
| 76 'bid' => array('bid'), | |
| 77 ), | |
| 78 ); | |
| 79 // Add the node type. | |
| 80 _book_install_type_create(); | |
| 81 | |
| 82 // Fix role permissions to account for the changed names | |
| 83 // Setup the array holding strings to match and the corresponding | |
| 84 // strings to replace them with. | |
| 85 $replace = array( | |
| 86 'outline posts in books' => 'administer book outlines', | |
| 87 'create book pages' => 'create book content', | |
| 88 'edit book pages' => 'edit any book content', | |
| 89 'edit own book pages' => 'edit own book content', | |
| 90 'see printer-friendly version' => 'access printer-friendly version', | |
| 91 ); | |
| 92 | |
| 93 // Loop over all the roles, and do the necessary transformations. | |
| 94 $query = db_query("SELECT rid, perm FROM {permission} ORDER BY rid"); | |
| 95 while ($role = db_fetch_object($query)) { | |
| 96 // Replace all the old permissions with the corresponding new permissions. | |
| 97 $fixed_perm = strtr($role->perm, $replace); | |
| 98 // If the user could previously create book pages, they should get the new | |
| 99 // 'add content to books' permission. | |
| 100 if (strpos($role->perm, 'create book pages') !== FALSE) { | |
| 101 $fixed_perm .= ', add content to books'; | |
| 102 } | |
| 103 // Only save if the permissions have changed. | |
| 104 if ($fixed_perm != $role->perm) { | |
| 105 $ret[] = update_sql("UPDATE {permission} SET perm = '$fixed_perm' WHERE rid = $role->rid"); | |
| 106 } | |
| 107 } | |
| 108 | |
| 109 // Determine whether there are any existing nodes in the book hierarchy. | |
| 110 if (db_result(db_query("SELECT COUNT(*) FROM {book}"))) { | |
| 111 // Temporary table for the old book hierarchy; we'll discard revision info. | |
| 112 $schema['book_temp'] = array( | |
| 113 'fields' => array( | |
| 114 'nid' => array('type' => 'int', 'unsigned' => TRUE, 'not null' => TRUE, 'default' => 0), | |
| 115 'parent' => array('type' => 'int', 'not null' => TRUE, 'default' => 0), | |
| 116 'weight' => array('type' => 'int', 'not null' => TRUE, 'default' => 0, 'size' => 'tiny') | |
| 117 ), | |
| 118 'indexes' => array( | |
| 119 'parent' => array('parent') | |
| 120 ), | |
| 121 'primary key' => array('nid'), | |
| 122 ); | |
| 123 | |
| 124 db_create_table($ret, 'book_temp', $schema['book_temp']); | |
| 125 | |
| 126 // Insert each node in the old table into the temporary table. | |
| 127 $ret[] = update_sql("INSERT INTO {book_temp} (nid, parent, weight) SELECT b.nid, b.parent, b.weight FROM {book} b INNER JOIN {node} n on b.vid = n.vid"); | |
| 128 $ret[] = update_sql("DROP TABLE {book}"); | |
| 129 | |
| 130 db_create_table($ret, 'book', $schema['book']); | |
| 131 | |
| 132 $_SESSION['book_update_6000_orphans']['from'] = 0; | |
| 133 $_SESSION['book_update_6000'] = array(); | |
| 134 $result = db_query("SELECT * from {book_temp} WHERE parent = 0"); | |
| 135 | |
| 136 // Collect all books - top-level nodes. | |
| 137 while ($a = db_fetch_array($result)) { | |
| 138 $_SESSION['book_update_6000'][] = $a; | |
| 139 } | |
| 140 $ret['#finished'] = FALSE; | |
| 141 return $ret; | |
| 142 } | |
| 143 else { | |
| 144 // No exising nodes in the hierarchy, so drop the table and re-create it. | |
| 145 $ret[] = update_sql("DROP TABLE {book}"); | |
| 146 db_create_table($ret, 'book', $schema['book']); | |
| 147 return $ret; | |
| 148 } | |
| 149 } | |
| 150 elseif ($_SESSION['book_update_6000_orphans']) { | |
| 151 // Do the first batched part of the update - collect orphans. | |
| 152 $update_count = 400; // Update this many at a time | |
| 153 | |
| 154 $result = db_query_range("SELECT * FROM {book_temp}", $_SESSION['book_update_6000_orphans']['from'], $update_count); | |
| 155 $has_rows = FALSE; | |
| 156 // Go through the next $update_count book pages and locate the orphans. | |
| 157 while ($book = db_fetch_array($result)) { | |
| 158 $has_rows = TRUE; | |
| 159 // Orphans are defined as nodes whose parent does not exist in the table. | |
| 160 if ($book['parent'] && !db_result(db_query("SELECT COUNT(*) FROM {book_temp} WHERE nid = %d", $book['parent']))) { | |
| 161 if (empty($_SESSION['book_update_6000_orphans']['book'])) { | |
| 162 // The first orphan becomes the parent for all other orphans. | |
| 163 $book['parent'] = 0; | |
| 164 $_SESSION['book_update_6000_orphans']['book'] = $book; | |
| 165 $ret[] = array('success' => TRUE, 'query' => 'Relocated orphan book pages.'); | |
| 166 } | |
| 167 else { | |
| 168 // Re-assign the parent value of the book, and add it to the stack. | |
| 169 $book['parent'] = $_SESSION['book_update_6000_orphans']['book']['nid']; | |
| 170 $_SESSION['book_update_6000'][] = $book; | |
| 171 } | |
| 172 } | |
| 173 } | |
| 174 if ($has_rows) { | |
| 175 $_SESSION['book_update_6000_orphans']['from'] += $update_count; | |
| 176 } | |
| 177 else { | |
| 178 // Done with this part | |
| 179 if (!empty($_SESSION['book_update_6000_orphans']['book'])) { | |
| 180 // The orphans' parent is added last, so it will be processed first. | |
| 181 $_SESSION['book_update_6000'][] = $_SESSION['book_update_6000_orphans']['book']; | |
| 182 } | |
| 183 $_SESSION['book_update_6000_orphans'] = FALSE; | |
| 184 } | |
| 185 $ret['#finished'] = FALSE; | |
| 186 return $ret; | |
| 187 } | |
| 188 else { | |
| 189 // Do the next batched part of the update | |
| 190 $update_count = 100; // Update this many at a time | |
| 191 | |
| 192 while ($update_count && $_SESSION['book_update_6000']) { | |
| 193 // Get the last node off the stack. | |
| 194 $book = array_pop($_SESSION['book_update_6000']); | |
| 195 | |
| 196 // Add all of this node's children to the stack | |
| 197 $result = db_query("SELECT * FROM {book_temp} WHERE parent = %d", $book['nid']); | |
| 198 while ($a = db_fetch_array($result)) { | |
| 199 $_SESSION['book_update_6000'][] = $a; | |
| 200 } | |
| 201 | |
| 202 if ($book['parent']) { | |
| 203 // If its not a top level page, get its parent's mlid. | |
| 204 $parent = db_fetch_array(db_query("SELECT b.mlid AS plid, b.bid FROM {book} b WHERE b.nid = %d", $book['parent'])); | |
| 205 $book = array_merge($book, $parent); | |
| 206 } | |
| 207 else { | |
| 208 // There is not a parent - this is a new book. | |
| 209 $book['plid'] = 0; | |
| 210 $book['bid'] = $book['nid']; | |
| 211 } | |
| 212 | |
| 213 $book += array( | |
| 214 'module' => 'book', | |
| 215 'link_path' => 'node/'. $book['nid'], | |
| 216 'router_path' => 'node/%', | |
| 217 'menu_name' => 'book-toc-'. $book['bid'], | |
| 218 ); | |
| 219 $book = array_merge($book, db_fetch_array(db_query("SELECT title AS link_title FROM {node} WHERE nid = %d", $book['nid']))); | |
| 220 | |
| 221 // Items with depth > MENU_MAX_DEPTH cannot be saved. | |
| 222 if (menu_link_save($book)) { | |
| 223 db_query("INSERT INTO {book} (mlid, nid, bid) VALUES (%d, %d, %d)", $book['mlid'], $book['nid'], $book['bid']); | |
| 224 } | |
| 225 else { | |
| 226 // The depth was greater then MENU_MAX_DEPTH, so attach it to the | |
| 227 // closest valid parent. | |
| 228 $book['plid'] = db_result(db_query("SELECT plid FROM {menu_links} WHERE mlid = %d", $book['plid'])); | |
| 229 if (menu_link_save($book)) { | |
| 230 db_query("INSERT INTO {book} (mlid, nid, bid) VALUES (%d, %d, %d)", $book['mlid'], $book['nid'], $book['bid']); | |
| 231 } | |
| 232 } | |
| 233 $update_count--; | |
| 234 } | |
| 235 $ret['#finished'] = FALSE; | |
| 236 } | |
| 237 | |
| 238 if (empty($_SESSION['book_update_6000'])) { | |
| 239 $ret['#finished'] = TRUE; | |
| 240 $ret[] = array('success' => TRUE, 'query' => 'Relocated existing book pages.'); | |
| 241 $ret[] = update_sql("DROP TABLE {book_temp}"); | |
| 242 unset($_SESSION['book_update_6000']); | |
| 243 unset($_SESSION['book_update_6000_orphans']); | |
| 244 } | |
| 245 | |
| 246 return $ret; | |
| 247 } | |
| 248 | |
| 249 /** | |
| 250 * Implementation of hook_schema(). | |
| 251 */ | |
| 252 function book_schema() { | |
| 253 $schema['book'] = array( | |
| 254 'description' => t('Stores book outline information. Uniquely connects each node in the outline to a link in {menu_links}'), | |
| 255 'fields' => array( | |
| 256 'mlid' => array( | |
| 257 'type' => 'int', | |
| 258 'unsigned' => TRUE, | |
| 259 'not null' => TRUE, | |
| 260 'default' => 0, | |
| 261 'description' => t("The book page's {menu_links}.mlid."), | |
| 262 ), | |
| 263 'nid' => array( | |
| 264 'type' => 'int', | |
| 265 'unsigned' => TRUE, | |
| 266 'not null' => TRUE, | |
| 267 'default' => 0, | |
| 268 'description' => t("The book page's {node}.nid."), | |
| 269 ), | |
| 270 'bid' => array( | |
| 271 'type' => 'int', | |
| 272 'unsigned' => TRUE, | |
| 273 'not null' => TRUE, | |
| 274 'default' => 0, | |
| 275 'description' => t("The book ID is the {book}.nid of the top-level page."), | |
| 276 ), | |
| 277 ), | |
| 278 'primary key' => array('mlid'), | |
| 279 'unique keys' => array( | |
| 280 'nid' => array('nid'), | |
| 281 ), | |
| 282 'indexes' => array( | |
| 283 'bid' => array('bid'), | |
| 284 ), | |
| 285 ); | |
| 286 | |
| 287 return $schema; | |
| 288 } | |
| 289 | |
| 290 |
