? error_log
? files
? generate-content.php
? generate-users.php
? patch.patch
? modules/devel
Index: includes/form.inc
===================================================================
RCS file: /cvs/drupal/drupal/includes/form.inc,v
retrieving revision 1.130
diff -u -F^f -r1.130 form.inc
--- includes/form.inc 22 Jul 2006 19:26:58 -0000 1.130
+++ includes/form.inc 1 Aug 2006 13:54:12 -0000
@@ -603,6 +603,7 @@ function form_render(&$elements) {
if (!isset($elements)) {
return NULL;
}
+
$content = '';
uasort($elements, "_form_sort");
if (!isset($elements['#children'])) {
@@ -648,7 +649,32 @@ function form_render(&$elements) {
if (isset($content) && $content !== '') {
$prefix = isset($elements['#prefix']) ? $elements['#prefix'] : '';
$suffix = isset($elements['#suffix']) ? $elements['#suffix'] : '';
- return $prefix . $content . $suffix;
+ $content = $prefix . $content . $suffix;
+
+ if (isset($elements['#after_render']) && !isset($elements['#after_render_done'])) {
+ foreach ($elements['#after_render'] as $function) {
+ $function($elements, $content);
+ }
+ $elements['#after_render_done'] = TRUE;
+ }
+
+ return $content;
+ }
+}
+
+/**
+ * Iterates through the form array and strips out any
+ * sub-elements keyed by the second parameter. Useful for
+ * resetting a form to be rendered a second time without
+ * rebuilding.
+ */
+function form_strip_key(&$elements, $key_to_strip) {
+ if (isset($elements[$key_to_strip])) {
+ unset($elements[$key_to_strip]);
+ }
+ $children = element_children($elements);
+ foreach ($children as $key) {
+ form_strip_key($elements[$key], $key_to_strip);
}
}
Index: modules/blog/blog.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/blog/blog.module,v
retrieving revision 1.252
diff -u -F^f -r1.252 blog.module
--- modules/blog/blog.module 27 Jul 2006 08:07:04 -0000 1.252
+++ modules/blog/blog.module 1 Aug 2006 13:54:12 -0000
@@ -238,7 +238,7 @@ function blog_view(&$node, $teaser = FAL
$breadcrumb[] = array('path' => 'node/'. $node->nid);
menu_set_location($breadcrumb);
}
- $node = node_prepare($node, $teaser);
+ return node_prepare($node, $teaser);
}
/**
Index: modules/book/book.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/book/book.module,v
retrieving revision 1.375
diff -u -F^f -r1.375 book.module
--- modules/book/book.module 19 Jul 2006 07:15:34 -0000 1.375
+++ modules/book/book.module 1 Aug 2006 13:54:12 -0000
@@ -438,16 +438,6 @@ function book_content($node, $teaser = F
}
/**
- * Implementation of hook_view().
- *
- * If not displayed on the main page, we render the node as a page in the
- * book with extra links to the previous and next pages.
- */
-function book_view(&$node, $teaser = FALSE, $page = FALSE) {
- $node = node_prepare($node, $teaser);
-}
-
-/**
* Implementation of hook_nodeapi().
*
* Appends book navigation to all nodes in the book.
@@ -474,11 +464,18 @@ function book_nodeapi(&$node, $op, $teas
}
$node->breadcrumb[] = array('path' => 'node/'. $node->nid);
- $node->body .= theme('book_navigation', $node);
+ $content = array();
+ $content['book_navigation'] = array(
+ '#type' => 'markup',
+ '#value' => theme('book_navigation', $node),
+ '#weight' => 100,
+ );
if ($page) {
menu_set_location($node->breadcrumb);
}
+
+ return $content;
}
}
break;
Index: modules/forum/forum.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/forum/forum.module,v
retrieving revision 1.339
diff -u -F^f -r1.339 forum.module
--- modules/forum/forum.module 29 Jul 2006 17:56:41 -0000 1.339
+++ modules/forum/forum.module 1 Aug 2006 13:54:12 -0000
@@ -305,9 +305,14 @@ function forum_view(&$node, $teaser = FA
menu_set_location($breadcrumb);
}
- $node = node_prepare($node, $teaser);
+ $content = node_prepare($node, $teaser);
+ $content['forum_navigation'] = array(
+ '#type' => 'markup',
+ '#value' => theme('forum_topic_navigation', $node),
+ '#weight' => 100,
+ );
- $node->body .= theme('forum_topic_navigation', $node);
+ return $content
}
/**
Index: modules/node/node.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/node/node.module,v
retrieving revision 1.662
diff -u -F^f -r1.662 node.module
--- modules/node/node.module 26 Jul 2006 08:25:25 -0000 1.662
+++ modules/node/node.module 1 Aug 2006 13:54:13 -0000
@@ -515,21 +515,7 @@ function node_view($node, $teaser = FALS
// Remove the delimiter (if any) that separates the teaser from the body.
// TODO: this strips legitimate uses of '' also.
$node->body = str_replace('', '', $node->body);
-
- if ($node->log != '' && !$teaser) {
- $node->body .= '
'. t('Log') .':
'. filter_xss($node->log) .'
';
- }
-
- // The 'view' hook can be implemented to overwrite the default function
- // to display nodes.
- if (node_hook($node, 'view')) {
- node_invoke($node, 'view', $teaser, $page);
- }
- else {
- $node = node_prepare($node, $teaser);
- }
- // Allow modules to change $node->body before viewing.
- node_invoke_nodeapi($node, 'view', $teaser, $page);
+
if ($links) {
$node->links = module_invoke_all('link', 'node', $node, !$page);
@@ -538,11 +524,21 @@ function node_view($node, $teaser = FALS
$function($node, $node->links);
}
}
- // unset unused $node part so that a bad theme can not open a security hole
+
+ $node->content = node_build_content($node, $teaser, $page);
+
+ if (isset($content['#readmore'])) {
+ $node->readmore = TRUE;
+ }
+
+ // set the proper node part, then unset unused $node part so that a bad
+ // theme can not open a security hole
if ($teaser) {
+ $node->teaser = form_render($node->content);
unset($node->body);
}
else {
+ $node->body = form_render($node->content);
unset($node->teaser);
}
@@ -550,17 +546,63 @@ function node_view($node, $teaser = FALS
}
/**
- * Apply filters to a node in preparation for theming.
+ * Apply filters and build the node's standard elements.
*/
function node_prepare($node, $teaser = FALSE) {
- $node->readmore = (strlen($node->teaser) < strlen($node->body));
- if ($teaser == FALSE) {
- $node->body = check_markup($node->body, $node->format, FALSE);
+ $content['body'] = array(
+ '#type' => 'markup',
+ '#value' => check_markup($teaser ? $node->teaser : $node->body, $node->format, FALSE),
+ '#weight' => 0,
+ );
+
+ if ($node->log != '' && !$teaser) {
+ $content['log_message'] = array(
+ '#type' => 'markup',
+ '#value' => theme('node_log_message', filter_xss($node->log)),
+ '#weight' => 20,
+ );
+ }
+
+ if (strlen($node->teaser) < strlen($node->body)) {
+ $content['#readmore'] = TRUE;
+ }
+
+ return $content;
+}
+
+/**
+ * Builds a structured array representing the node's content.
+ *
+ * @param $node
+ * A node object.
+ * @param $teaser
+ * Whether to display the teaser only, as on the main page.
+ * @param $page
+ * Whether the node is being displayed by itself as a page.
+ *
+ * @return
+ * An structured array containing the individual elements
+ * of the node's body.
+ */
+function node_build_content($node, $teaser = FALSE, $page = FALSE) {
+ // The 'view' hook can be implemented to overwrite the default function
+ // to display nodes.
+ if (node_hook($node, 'view')) {
+ $content = node_invoke($node, 'view', $teaser, $page);
}
else {
- $node->teaser = check_markup($node->teaser, $node->format, FALSE);
+ $content = node_prepare($node, $teaser);
}
- return $node;
+
+ // Allow modules to make their own additions to the content array.
+ $content = array_merge($content, node_invoke_nodeapi($node, 'view', $teaser, $page));
+
+ foreach (module_implements('node_content_alter') AS $module) {
+ $function = $module .'_node_content_alter';
+ $function($node, $content);
+ }
+
+ return $content;
}
/**
@@ -1831,6 +1873,10 @@ function theme_node_preview($node) {
return $output;
}
+function theme_node_log_message($log) {
+ return ''. t('Log') .':
'. $log .'
';
+}
+
function node_form_submit($form_id, $edit) {
global $user;
Index: modules/upload/upload.module
===================================================================
RCS file: /cvs/drupal/drupal/modules/upload/upload.module,v
retrieving revision 1.113
diff -u -F^f -r1.113 upload.module
--- modules/upload/upload.module 19 Jul 2006 07:15:35 -0000 1.113
+++ modules/upload/upload.module 1 Aug 2006 13:54:13 -0000
@@ -425,31 +425,15 @@ function upload_nodeapi(&$node, $op, $te
case 'view':
if (isset($node->files) && user_access('view uploaded files')) {
- // Manipulate so that inline references work in preview
- if (!variable_get('clean_url', 0)) {
- $previews = array();
- foreach ($node->files as $file) {
- if (strpos($file->fid, 'upload') !== FALSE) {
- $previews[] = $file;
- }
- }
-
- // URLs to files being previewed are actually Drupal paths. When Clean
- // URLs are disabled, the two do not match. We perform an automatic
- // replacement from temporary to permanent URLs. That way, the author
- // can use the final URL in the body before having actually saved (to
- // place inline images for example).
- foreach ($previews as $file) {
- $old = file_create_filename($file->filename, file_create_path());
- $new = url($old);
- $node->body = str_replace($old, $new, $node->body);
- $node->teaser = str_replace($old, $new, $node->teaser);
- }
- }
-
- // Add the attachments list to node body
+ // Add the attachments list to node body with a heavy
+ // weight to ensure they're below other elements
if (count($node->files) && !$teaser) {
- $node->body .= theme('upload_attachments', $node->files);
+ $content['files'] = array(
+ '#type' => 'markup',
+ '#value' => theme('upload_attachments', $node->files),
+ '#weight' => 50,
+ );
+ return $content;
}
}
break;
@@ -499,6 +483,39 @@ function upload_nodeapi(&$node, $op, $te
}
}
+function upload_node_content_alter($node, &$content) {
+ if (isset($node->files) && user_access('view uploaded files')) {
+ // Manipulate so that inline references work in preview
+ if (!variable_get('clean_url', 0)) {
+ $previews = array();
+ foreach ($node->files as $file) {
+ $file = (object)$file;
+ if (strpos($file->fid, 'upload') !== FALSE) {
+ $previews[] = $file;
+ }
+ }
+ // URLs to files being previewed are actually Drupal paths. When Clean
+ // URLs are disabled, the two do not match. We perform an automatic
+ // replacement from temporary to permanent URLs. That way, the author
+ // can use the final URL in the body before having actually saved (to
+ // place inline images for example).
+ foreach ($previews as $file) {
+ $old = file_create_filename($file->filename, file_create_path());
+ $content['#upload_urls'][$old] = url($old);
+ }
+ $content['#after_render'][] = 'upload_fix_preview_urls';
+ }
+ }
+}
+
+function upload_fix_preview_urls($elements, $content) {
+ if (is_array($elements['#upload_urls'])) {
+ foreach ($elements['#upload_urls'] as $old => $new) {
+ str_replace($old, $new, $content);
+ }
+ }
+}
+
/**
* Displays file attachments in table
*/