From 07e0f6dde1c5c34104aaa59f65209d00126797f1 Mon Sep 17 00:00:00 2001
From: Mark Carver <mark.carver@me.com>
Date: Mon, 15 Sep 2014 01:18:02 -0500
Subject: Issue #2281551 by Mark Carver, Steven Jones: Create input filter code
 for linking to git commits

---
 .../versioncontrol_project_git.module              | 76 ++++++++++++++++++++++
 1 file changed, 76 insertions(+)

diff --git a/versioncontrol_project_git/versioncontrol_project_git.module b/versioncontrol_project_git/versioncontrol_project_git.module
index 2449714..8360f4d 100644
--- a/versioncontrol_project_git/versioncontrol_project_git.module
+++ b/versioncontrol_project_git/versioncontrol_project_git.module
@@ -121,3 +121,79 @@ function versioncontrol_project_git_views_api() {
     'path' => drupal_get_path('module', 'versioncontrol_project_git') . '/views',
   );
 }
+
+/**
+ * Implements hook_filter_info().
+ */
+function versioncontrol_project_git_filter_info() {
+  $filters['versioncontrol_project_git'] = array(
+    'title' => t('Versioncontrol project - Git revision'),
+    'description' => t('Replaces git revision strings with links to the appropriate commit viewer.'),
+    'process callback' => 'versioncontrol_project_git_revision_filter_process',
+    'tips callback' => 'versioncontrol_project_git_revision_filter_tips',
+  );
+  return $filters;
+}
+
+/**
+ * Filter tips callback for the Git revision filter.
+ */
+function versioncontrol_project_git_revision_filter_tips($filter, $format, $long = FALSE) {
+  if ($long) {
+    return t("References to git commits in the form of project_short_name@commit_hash turn into links automatically. You may reference sandboxes by referencing their numeric short name, and you may use any length of commit hash from 8-40. For example: drupal@2569242a, drupal@2569242afd5eec297e7d72065f4e3dd2586d0fd8");
+  }
+  else {
+    return t('Referenced git commits (ex. drupal@2569242a) turn into links automatically.');
+  }
+}
+
+/**
+ * Filter process callback for the Git revision filter.
+ */
+function versioncontrol_project_git_revision_filter_process($text, $filter, $format, $langcode, $cache, $cache_id) {
+  return preg_replace_callback('/([a-z0-9_]{2,})@([a-z0-9]{8,40})/', 'versioncontrol_project_git_revision_process_callback', $text);
+}
+
+/**
+ * A preg_replace_callback for generating git revision links.
+ *
+ * @param array $matches
+ *   The grouped matches from the regex that invoked this callback. This
+ *   callback assumes that $matches[1] is the project machine name and
+ *   $matches[2] is the commit revision.
+ *
+ * @return string
+ *   A link to the repository with a specific revision. The link will use the
+ *   shorthand display text of "project_name@revision" where "project_name" is
+ *   the machine name of the project and "revision" is the commit hash limited
+ *   to 8 characters. If this callback could not generate a link successfully,
+ *   the original matched text will be returned.
+ *
+ * @see versioncontrol_project_git_revision_filter_process()
+ */
+function versioncontrol_project_git_revision_process_callback($matches) {
+  // Try to fetch a project from the machine name, then a repository, then the
+  // URL handler and finally a URL.
+  try {
+    $machine_name = $matches[1];
+    $revision = $matches[2];
+    if (
+      ($nid = project_get_nid_from_machinename($machine_name)) &&
+      ($repo = versioncontrol_project_repository_load($nid)) &&
+      ($repo instanceof VersioncontrolRepository) &&
+      ($url_handler = $repo->getUrlHandler()) &&
+      ($url_handler instanceof VersioncontrolWebviewerUrlHandlerInterface) &&
+      ($url = $url_handler->getCommitViewUrl($revision))
+    ) {
+      return l($machine_name . '@' . substr($revision, 0, 8), $url, array(
+        'attributes' => array(
+          'target' => '_blank',
+        ),
+      ));
+    }
+  }
+  catch (Exception $e) {
+    // Ignore any caught exceptions and let it return the original matched text.
+  }
+  return $matches[0];
+}
--
2.0.1

