diff --git a/includes/comment.inc b/includes/comment.inc
index 84d46ae..b7cbf64 100644
--- a/includes/comment.inc
+++ b/includes/comment.inc
@@ -571,18 +571,156 @@ function project_issue_update_by_comment($comment_data, $op) {
   // Update the issue data to reflect the new final states.
   db_query("UPDATE {project_issues} SET pid = %d, category = '%s', component = '%s', priority = %d, rid = %d, assigned = %d, sid = %d, priority_weight = %d WHERE nid = %d", $comment_data->pid, $comment_data->category, $comment_data->component, $comment_data->priority, $comment_data->rid, $comment_data->assigned, $comment_data->sid, $priority_weight, $comment_data->nid);
 
-  // Update the issue title.
-  $node = node_load($comment_data->nid, NULL, TRUE);  // Don't use cached since we changed data above.
-  $node->title = $comment_data->title;
-
-  // This also updates the changed date of the issue.
-  node_save($node);
+  // Update the issue title, in case it changed.
+  // Don't use cached since we changed data above.
+  $node = node_load($comment_data->nid, NULL, TRUE);
+  // @todo Check whether we *always* have to save a new revision. Unpublishing/
+  //   deleting comments might unconditionally revert the issue node revision.
+  if ($node->title !== $comment_data->title) {
+    $node->title = $comment_data->title;
+
+    // Saving the node will potentially create a new node revision, if enabled.
+    // Node module's node_save() and _node_save_revision() would set the node
+    // revision author to the current user (the one who wrote an issue comment),
+    // change the node revision created/changed date as well as other node
+    // revision properties.
+    // However, for this node update, only the title of the issue node should be
+    // changed and saved as a new revision (so the change may be reverted). All
+    // other properties of the previous node revision should be left unchanged,
+    // since the comment author did not edit the node, she only wrote a comment.
+    // Therefore, we need to replace the behavior of the private
+    // _node_save_revision() helper function; which forces us to also replace
+    // node_save() to call it.
+    _project_issue_node_save($node);
+
+    // Clear the static node_load() cache.
+    node_load(NULL, NULL, TRUE);
+  }
 
   // Return the object of comment data we used to update the issue.
   return $comment_data;
 }
 
 /**
+ * Save a node object into the database.
+ *
+ * @see project_issue_update_by_comment()
+ * @see _project_issue_node_save_revision()
+ * @see node_save()
+ */
+function _project_issue_node_save(&$node) {
+  // Let modules modify the node before it is saved to the database.
+  node_invoke_nodeapi($node, 'presave');
+  global $user;
+
+  // Insert a new node.
+  $node->is_new = empty($node->nid);
+
+  if ($node->is_new || !empty($node->revision)) {
+    // When inserting a node, $node->log must be set because
+    // {node_revisions}.log does not (and cannot) have a default
+    // value.  If the user does not have permission to create
+    // revisions, however, the form will not contain an element for
+    // log so $node->log will be unset at this point.
+    if (!isset($node->log)) {
+      $node->log = '';
+    }
+  }
+  elseif (empty($node->log)) {
+    // When updating a node, however, avoid clobbering an existing
+    // log entry with an empty one.
+    unset($node->log);
+  }
+
+  // For the same reasons, make sure we have $node->teaser and
+  // $node->body set.
+  if (!isset($node->teaser)) {
+    $node->teaser = '';
+  }
+  if (!isset($node->body)) {
+    $node->body = '';
+  }
+
+  // Save the old revision if needed.
+  if (!$node->is_new && !empty($node->revision) && $node->vid) {
+    $node->old_vid = $node->vid;
+  }
+
+  $time = time();
+  if (empty($node->created)) {
+    $node->created = $time;
+  }
+  // The changed timestamp is always updated for bookkeeping purposes (revisions, searching, ...)
+  $node->changed = $time;
+
+  $node->timestamp = $time;
+  $node->format = isset($node->format) ? $node->format : FILTER_FORMAT_DEFAULT;
+
+  // Generate the node table query and the node_revisions table query.
+  if ($node->is_new) {
+    _project_issue_node_save_revision($node, $user->uid);
+    drupal_write_record('node', $node);
+    db_query('UPDATE {node_revisions} SET nid = %d WHERE vid = %d', $node->nid, $node->vid);
+    $op = 'insert';
+  }
+  else {
+    drupal_write_record('node', $node, 'nid');
+    if (!empty($node->revision)) {
+      _project_issue_node_save_revision($node, $user->uid);
+      db_query('UPDATE {node} SET vid = %d WHERE nid = %d', $node->vid, $node->nid);
+    }
+    else {
+      _project_issue_node_save_revision($node, $user->uid, 'vid');
+    }
+    $op = 'update';
+  }
+
+  // Call the node specific callback (if any).
+  node_invoke($node, $op);
+  node_invoke_nodeapi($node, $op);
+
+  // Update the node access table for this node.
+  node_access_acquire_grants($node);
+
+  // Clear the page and block caches.
+  cache_clear_all();
+}
+
+/**
+ * Helper function to save a revision with the uid of the current user.
+ *
+ * Node is taken by reference, because drupal_write_record() updates the
+ * $node with the revision id, and we need to pass that back to the caller.
+ *
+ * @see project_issue_update_by_comment()
+ * @see _project_issue_node_save()
+ * @see _node_save_revision()
+ */
+function _project_issue_node_save_revision(&$node, $uid, $update = NULL) {
+  // This implementation of _node_save_revision() is only invoked when posting
+  // a comment, so there must be an existing node revision. If there is none
+  // for any reason, then something else went completely wrong.
+  if (empty($node->vid)) {
+    return;
+  }
+  // Only update title and uid.
+  $existing = db_fetch_object(db_query("SELECT * FROM {node_revisions} WHERE vid = %d", array($node->vid)));
+  // Set the node revision title.
+  $existing->title = $node->title;
+  // Set the node revision author to the comment author.
+  $existing->uid = $uid;
+  // Insert a new revision or update the existing one.
+  if (isset($update)) {
+    drupal_write_record('node_revisions', $existing, $update);
+  }
+  else {
+    drupal_write_record('node_revisions', $existing);
+  }
+  // Assign the potentially new revision id.
+  $node->vid = $existing->vid;
+}
+
+/**
  * Adjusts the filepath of issue followups so files are saved to
  * the correct issues directory.
  *
