Page MenuHomePhabricator

D20538.diff
No OneTemporary

D20538.diff

diff --git a/src/__phutil_library_map__.php b/src/__phutil_library_map__.php
--- a/src/__phutil_library_map__.php
+++ b/src/__phutil_library_map__.php
@@ -999,6 +999,8 @@
'DiffusionServeController' => 'applications/diffusion/controller/DiffusionServeController.php',
'DiffusionSetPasswordSettingsPanel' => 'applications/diffusion/panel/DiffusionSetPasswordSettingsPanel.php',
'DiffusionSetupException' => 'applications/diffusion/exception/DiffusionSetupException.php',
+ 'DiffusionSourceHyperlinkEngineExtension' => 'applications/diffusion/engineextension/DiffusionSourceHyperlinkEngineExtension.php',
+ 'DiffusionSourceLinkView' => 'applications/diffusion/view/DiffusionSourceLinkView.php',
'DiffusionSubversionCommandEngine' => 'applications/diffusion/protocol/DiffusionSubversionCommandEngine.php',
'DiffusionSubversionSSHWorkflow' => 'applications/diffusion/ssh/DiffusionSubversionSSHWorkflow.php',
'DiffusionSubversionServeSSHWorkflow' => 'applications/diffusion/ssh/DiffusionSubversionServeSSHWorkflow.php',
@@ -4340,6 +4342,7 @@
'PhabricatorRemarkupDocumentEngine' => 'applications/files/document/PhabricatorRemarkupDocumentEngine.php',
'PhabricatorRemarkupEditField' => 'applications/transactions/editfield/PhabricatorRemarkupEditField.php',
'PhabricatorRemarkupFigletBlockInterpreter' => 'infrastructure/markup/interpreter/PhabricatorRemarkupFigletBlockInterpreter.php',
+ 'PhabricatorRemarkupHyperlinkEngineExtension' => 'applications/remarkup/engineextension/PhabricatorRemarkupHyperlinkEngineExtension.php',
'PhabricatorRemarkupUIExample' => 'applications/uiexample/examples/PhabricatorRemarkupUIExample.php',
'PhabricatorRepositoriesSetupCheck' => 'applications/config/check/PhabricatorRepositoriesSetupCheck.php',
'PhabricatorRepository' => 'applications/repository/storage/PhabricatorRepository.php',
@@ -6681,6 +6684,8 @@
'DiffusionServeController' => 'DiffusionController',
'DiffusionSetPasswordSettingsPanel' => 'PhabricatorSettingsPanel',
'DiffusionSetupException' => 'Exception',
+ 'DiffusionSourceHyperlinkEngineExtension' => 'PhabricatorRemarkupHyperlinkEngineExtension',
+ 'DiffusionSourceLinkView' => 'AphrontView',
'DiffusionSubversionCommandEngine' => 'DiffusionCommandEngine',
'DiffusionSubversionSSHWorkflow' => 'DiffusionSSHWorkflow',
'DiffusionSubversionServeSSHWorkflow' => 'DiffusionSubversionSSHWorkflow',
@@ -6786,7 +6791,7 @@
'DoorkeeperExternalObjectQuery' => 'PhabricatorCursorPagedPolicyAwareQuery',
'DoorkeeperFeedStoryPublisher' => 'Phobject',
'DoorkeeperFeedWorker' => 'FeedPushWorker',
- 'DoorkeeperHyperlinkEngineExtension' => 'PhutilRemarkupHyperlinkEngineExtension',
+ 'DoorkeeperHyperlinkEngineExtension' => 'PhabricatorRemarkupHyperlinkEngineExtension',
'DoorkeeperImportEngine' => 'Phobject',
'DoorkeeperJIRAFeedWorker' => 'DoorkeeperFeedWorker',
'DoorkeeperMissingLinkException' => 'Exception',
@@ -10595,6 +10600,7 @@
'PhabricatorRemarkupDocumentEngine' => 'PhabricatorDocumentEngine',
'PhabricatorRemarkupEditField' => 'PhabricatorEditField',
'PhabricatorRemarkupFigletBlockInterpreter' => 'PhutilRemarkupBlockInterpreter',
+ 'PhabricatorRemarkupHyperlinkEngineExtension' => 'PhutilRemarkupHyperlinkEngineExtension',
'PhabricatorRemarkupUIExample' => 'PhabricatorUIExample',
'PhabricatorRepositoriesSetupCheck' => 'PhabricatorSetupCheck',
'PhabricatorRepository' => array(
@@ -10883,7 +10889,7 @@
'PhabricatorSecuritySetupCheck' => 'PhabricatorSetupCheck',
'PhabricatorSelectEditField' => 'PhabricatorEditField',
'PhabricatorSelectSetting' => 'PhabricatorSetting',
- 'PhabricatorSelfHyperlinkEngineExtension' => 'PhutilRemarkupHyperlinkEngineExtension',
+ 'PhabricatorSelfHyperlinkEngineExtension' => 'PhabricatorRemarkupHyperlinkEngineExtension',
'PhabricatorSessionsSettingsPanel' => 'PhabricatorSettingsPanel',
'PhabricatorSetConfigType' => 'PhabricatorTextConfigType',
'PhabricatorSetting' => 'Phobject',
diff --git a/src/applications/diffusion/engineextension/DiffusionSourceHyperlinkEngineExtension.php b/src/applications/diffusion/engineextension/DiffusionSourceHyperlinkEngineExtension.php
new file mode 100644
--- /dev/null
+++ b/src/applications/diffusion/engineextension/DiffusionSourceHyperlinkEngineExtension.php
@@ -0,0 +1,84 @@
+<?php
+
+final class DiffusionSourceHyperlinkEngineExtension
+ extends PhabricatorRemarkupHyperlinkEngineExtension {
+
+ const LINKENGINEKEY = 'diffusion-src';
+
+ public function processHyperlinks(array $hyperlinks) {
+ $engine = $this->getEngine();
+ $viewer = $engine->getConfig('viewer');
+
+ if (!$viewer) {
+ return;
+ }
+
+ $hyperlinks = $this->getSelfLinks($hyperlinks);
+
+ $links = array();
+ foreach ($hyperlinks as $link) {
+ $uri = $link->getURI();
+ $uri = new PhutilURI($uri);
+
+ $path = $uri->getPath();
+
+ $pattern =
+ '(^'.
+ '/(?:diffusion|source)'.
+ '/(?P<identifier>[^/]+)'.
+ '/browse'.
+ '/(?P<blob>.*)'.
+ '\z)';
+ $matches = null;
+ if (!preg_match($pattern, $path, $matches)) {
+ continue;
+ }
+
+ $links[] = array(
+ 'ref' => $link,
+ 'identifier' => $matches['identifier'],
+ 'blob' => $matches['blob'],
+ );
+ }
+
+ if (!$links) {
+ return;
+ }
+
+ $identifiers = ipull($links, 'identifier');
+
+ $query = id(new PhabricatorRepositoryQuery())
+ ->setViewer($viewer)
+ ->withIdentifiers($identifiers);
+
+ $query->execute();
+
+ $repository_map = $query->getIdentifierMap();
+
+ foreach ($links as $link) {
+ $identifier = $link['identifier'];
+
+ $repository = idx($repository_map, $identifier);
+ if (!$repository) {
+ continue;
+ }
+
+ $ref = $link['ref'];
+ $uri = $ref->getURI();
+
+
+ $tag = id(new DiffusionSourceLinkView())
+ ->setViewer($viewer)
+ ->setRepository($repository)
+ ->setURI($uri)
+ ->setBlob($link['blob']);
+
+ if (!$ref->isEmbed()) {
+ $tag->setText($uri);
+ }
+
+ $ref->setResult($tag);
+ }
+ }
+
+}
diff --git a/src/applications/diffusion/request/DiffusionGitRequest.php b/src/applications/diffusion/request/DiffusionGitRequest.php
--- a/src/applications/diffusion/request/DiffusionGitRequest.php
+++ b/src/applications/diffusion/request/DiffusionGitRequest.php
@@ -2,10 +2,6 @@
final class DiffusionGitRequest extends DiffusionRequest {
- public function supportsBranches() {
- return true;
- }
-
protected function isStableCommit($symbol) {
return preg_match('/^[a-f0-9]{40}\z/', $symbol);
}
diff --git a/src/applications/diffusion/request/DiffusionMercurialRequest.php b/src/applications/diffusion/request/DiffusionMercurialRequest.php
--- a/src/applications/diffusion/request/DiffusionMercurialRequest.php
+++ b/src/applications/diffusion/request/DiffusionMercurialRequest.php
@@ -2,10 +2,6 @@
final class DiffusionMercurialRequest extends DiffusionRequest {
- public function supportsBranches() {
- return true;
- }
-
protected function isStableCommit($symbol) {
return preg_match('/^[a-f0-9]{40}\z/', $symbol);
}
diff --git a/src/applications/diffusion/request/DiffusionRequest.php b/src/applications/diffusion/request/DiffusionRequest.php
--- a/src/applications/diffusion/request/DiffusionRequest.php
+++ b/src/applications/diffusion/request/DiffusionRequest.php
@@ -28,7 +28,10 @@
private $branchObject = false;
private $refAlternatives;
- abstract public function supportsBranches();
+ final public function supportsBranches() {
+ return $this->getRepository()->supportsRefs();
+ }
+
abstract protected function isStableCommit($symbol);
protected function didInitialize() {
diff --git a/src/applications/diffusion/request/DiffusionSvnRequest.php b/src/applications/diffusion/request/DiffusionSvnRequest.php
--- a/src/applications/diffusion/request/DiffusionSvnRequest.php
+++ b/src/applications/diffusion/request/DiffusionSvnRequest.php
@@ -2,10 +2,6 @@
final class DiffusionSvnRequest extends DiffusionRequest {
- public function supportsBranches() {
- return false;
- }
-
protected function isStableCommit($symbol) {
return preg_match('/^[1-9]\d*\z/', $symbol);
}
diff --git a/src/applications/diffusion/view/DiffusionSourceLinkView.php b/src/applications/diffusion/view/DiffusionSourceLinkView.php
new file mode 100644
--- /dev/null
+++ b/src/applications/diffusion/view/DiffusionSourceLinkView.php
@@ -0,0 +1,208 @@
+<?php
+
+final class DiffusionSourceLinkView
+ extends AphrontView {
+
+ private $repository;
+ private $text;
+ private $uri;
+ private $blob;
+ private $blobMap;
+ private $refName;
+ private $path;
+ private $line;
+ private $commit;
+
+ public function setRepository($repository) {
+ $this->repository = $repository;
+ $this->blobMap = null;
+ return $this;
+ }
+
+ public function getRepository() {
+ return $this->repository;
+ }
+
+ public function setText($text) {
+ $this->text = $text;
+ return $this;
+ }
+
+ public function getText() {
+ return $this->text;
+ }
+
+ public function setURI($uri) {
+ $this->uri = $uri;
+ return $this;
+ }
+
+ public function getURI() {
+ return $this->uri;
+ }
+
+ public function setBlob($blob) {
+ $this->blob = $blob;
+ $this->blobMap = null;
+ return $this;
+ }
+
+ public function getBlob() {
+ return $this->blob;
+ }
+
+ public function setRefName($ref_name) {
+ $this->refName = $ref_name;
+ return $this;
+ }
+
+ public function getRefName() {
+ return $this->refName;
+ }
+
+ public function setPath($path) {
+ $this->path = $path;
+ return $this;
+ }
+
+ public function getPath() {
+ return $this->path;
+ }
+
+ public function setCommit($commit) {
+ $this->commit = $commit;
+ return $this;
+ }
+
+ public function getCommit() {
+ return $this->commit;
+ }
+
+ public function setLine($line) {
+ $this->line = $line;
+ return $this;
+ }
+
+ public function getLine() {
+ return $this->line;
+ }
+
+ public function getDisplayPath() {
+ if ($this->path !== null) {
+ return $this->path;
+ }
+
+ return $this->getBlobPath();
+ }
+
+ public function getDisplayRefName() {
+ if ($this->refName !== null) {
+ return $this->refName;
+ }
+
+ return $this->getBlobRefName();
+ }
+
+ public function getDisplayCommit() {
+ if ($this->commit !== null) {
+ return $this->commit;
+ }
+
+ return $this->getBlobCommit();
+ }
+
+ public function getDisplayLine() {
+ if ($this->line !== null) {
+ return $this->line;
+ }
+
+ return $this->getBlobLine();
+ }
+
+ private function getBlobPath() {
+ return idx($this->getBlobMap(), 'path');
+ }
+
+ private function getBlobRefName() {
+ return idx($this->getBlobMap(), 'branch');
+ }
+
+ private function getBlobLine() {
+ return idx($this->getBlobMap(), 'line');
+ }
+
+ private function getBlobCommit() {
+ return idx($this->getBlobMap(), 'commit');
+ }
+
+ private function getBlobMap() {
+ if ($this->blobMap === null) {
+ $repository = $this->getRepository();
+ $blob = $this->blob;
+
+ if ($repository && ($blob !== null)) {
+ $map = DiffusionRequest::parseRequestBlob(
+ $blob,
+ $repository->supportsRefs());
+ } else {
+ $map = array();
+ }
+
+ $this->blobMap = $map;
+ }
+
+ return $this->blobMap;
+ }
+
+ public function render() {
+ $repository = $this->getRepository();
+ $uri = $this->getURI();
+
+ $color = 'blue';
+ $icon = 'fa-file-text-o';
+
+ $text = $this->getText();
+ if (!strlen($text)) {
+ $path = $this->getDisplayPath();
+
+ $line = $this->getDisplayLine();
+ if ($line !== null) {
+ $path = pht('%s:%s', $path, $line);
+ }
+
+ if ($repository) {
+ $path = pht('%s %s', $repository->getMonogram(), $path);
+ }
+
+ if ($repository && $repository->supportsRefs()) {
+ $default_ref = $repository->getDefaultBranch();
+ } else {
+ $default_ref = null;
+ }
+
+ $ref_name = $this->getDisplayRefName();
+ if ($ref_name === $default_ref) {
+ $ref_name = null;
+ }
+
+ $commit = $this->getDisplayCommit();
+ if ($ref_name !== null && $commit !== null) {
+ $text = pht('%s (on %s at %s)', $path, $ref_name, $commit);
+ } else if ($ref_name !== null) {
+ $text = pht('%s (on %s)', $path, $ref_name);
+ } else if ($commit !== null) {
+ $text = pht('%s (at %s)', $path, $commit);
+ } else {
+ $text = $path;
+ }
+ }
+
+ return id(new PHUITagView())
+ ->setType(PHUITagView::TYPE_SHADE)
+ ->setColor($color)
+ ->setIcon($icon)
+ ->setHref($uri)
+ ->setName($text);
+ }
+
+}
diff --git a/src/applications/doorkeeper/engineextension/DoorkeeperHyperlinkEngineExtension.php b/src/applications/doorkeeper/engineextension/DoorkeeperHyperlinkEngineExtension.php
--- a/src/applications/doorkeeper/engineextension/DoorkeeperHyperlinkEngineExtension.php
+++ b/src/applications/doorkeeper/engineextension/DoorkeeperHyperlinkEngineExtension.php
@@ -1,7 +1,7 @@
<?php
final class DoorkeeperHyperlinkEngineExtension
- extends PhutilRemarkupHyperlinkEngineExtension {
+ extends PhabricatorRemarkupHyperlinkEngineExtension {
const LINKENGINEKEY = 'doorkeeper';
diff --git a/src/applications/meta/engineextension/PhabricatorSelfHyperlinkEngineExtension.php b/src/applications/meta/engineextension/PhabricatorSelfHyperlinkEngineExtension.php
--- a/src/applications/meta/engineextension/PhabricatorSelfHyperlinkEngineExtension.php
+++ b/src/applications/meta/engineextension/PhabricatorSelfHyperlinkEngineExtension.php
@@ -1,7 +1,7 @@
<?php
final class PhabricatorSelfHyperlinkEngineExtension
- extends PhutilRemarkupHyperlinkEngineExtension {
+ extends PhabricatorRemarkupHyperlinkEngineExtension {
const LINKENGINEKEY = 'phabricator-self';
@@ -15,15 +15,7 @@
return;
}
- // Find links which point to resources on the Phabricator install itself.
- // We're going to try to enhance these.
- $self_links = array();
- foreach ($hyperlinks as $link) {
- $uri = $link->getURI();
- if (PhabricatorEnv::isSelfURI($uri)) {
- $self_links[] = $link;
- }
- }
+ $self_links = $this->getSelfLinks($hyperlinks);
// For links in the form "/X123", we can reasonably guess that they are
// fairly likely to be object names. Try to look them up.
diff --git a/src/applications/remarkup/engineextension/PhabricatorRemarkupHyperlinkEngineExtension.php b/src/applications/remarkup/engineextension/PhabricatorRemarkupHyperlinkEngineExtension.php
new file mode 100644
--- /dev/null
+++ b/src/applications/remarkup/engineextension/PhabricatorRemarkupHyperlinkEngineExtension.php
@@ -0,0 +1,32 @@
+<?php
+
+abstract class PhabricatorRemarkupHyperlinkEngineExtension
+ extends PhutilRemarkupHyperlinkEngineExtension {
+
+ final protected function getSelfLinks(array $hyperlinks) {
+ assert_instances_of($hyperlinks, 'PhutilRemarkupHyperlinkRef');
+
+ $allowed_protocols = array(
+ 'http' => true,
+ 'https' => true,
+ );
+
+ $results = array();
+ foreach ($hyperlinks as $link) {
+ $uri = $link->getURI();
+
+ if (!PhabricatorEnv::isSelfURI($uri)) {
+ continue;
+ }
+
+ $protocol = id(new PhutilURI($uri))->getProtocol();
+ if (!isset($allowed_protocols[$protocol])) {
+ continue;
+ }
+
+ $results[] = $link;
+ }
+
+ return $results;
+ }
+}
diff --git a/src/applications/repository/storage/PhabricatorRepository.php b/src/applications/repository/storage/PhabricatorRepository.php
--- a/src/applications/repository/storage/PhabricatorRepository.php
+++ b/src/applications/repository/storage/PhabricatorRepository.php
@@ -2040,6 +2040,15 @@
return true;
}
+
+ public function supportsRefs() {
+ if ($this->isSVN()) {
+ return false;
+ }
+
+ return true;
+ }
+
public function getAlmanacServiceCacheKey() {
$service_phid = $this->getAlmanacServicePHID();
if (!$service_phid) {

File Metadata

Mime Type
text/plain
Expires
Wed, Dec 18, 10:25 PM (15 h, 32 m)
Storage Engine
blob
Storage Format
Encrypted (AES-256-CBC)
Storage Handle
6904682
Default Alt Text
D20538.diff (16 KB)

Event Timeline