Page Menu
Home
Phabricator
Search
Configure Global Search
Log In
Files
F15421488
D13036.id31480.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Award Token
Flag For Later
Size
16 KB
Referenced Files
None
Subscribers
None
D13036.id31480.diff
View Options
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
@@ -507,6 +507,8 @@
'DiffusionEmptyResultView' => 'applications/diffusion/view/DiffusionEmptyResultView.php',
'DiffusionExistsQueryConduitAPIMethod' => 'applications/diffusion/conduit/DiffusionExistsQueryConduitAPIMethod.php',
'DiffusionExternalController' => 'applications/diffusion/controller/DiffusionExternalController.php',
+ 'DiffusionExternalSymbolQuery' => 'applications/diffusion/symbol/DiffusionExternalSymbolQuery.php',
+ 'DiffusionExternalSymbolsSource' => 'applications/diffusion/symbol/DiffusionExternalSymbolsSource.php',
'DiffusionFileContent' => 'applications/diffusion/data/DiffusionFileContent.php',
'DiffusionFileContentQuery' => 'applications/diffusion/query/filecontent/DiffusionFileContentQuery.php',
'DiffusionFileContentQueryConduitAPIMethod' => 'applications/diffusion/conduit/DiffusionFileContentQueryConduitAPIMethod.php',
@@ -2955,6 +2957,7 @@
'PhortuneSubscriptionWorker' => 'applications/phortune/worker/PhortuneSubscriptionWorker.php',
'PhortuneTestPaymentProvider' => 'applications/phortune/provider/PhortuneTestPaymentProvider.php',
'PhortuneWePayPaymentProvider' => 'applications/phortune/provider/PhortuneWePayPaymentProvider.php',
+ 'PhpExternalSymbolsSource' => 'applications/diffusion/symbol/PhpExternalSymbolsSource.php',
'PhragmentBrowseController' => 'applications/phragment/controller/PhragmentBrowseController.php',
'PhragmentCanCreateCapability' => 'applications/phragment/capability/PhragmentCanCreateCapability.php',
'PhragmentConduitAPIMethod' => 'applications/phragment/conduit/PhragmentConduitAPIMethod.php',
@@ -3097,6 +3100,7 @@
'ProjectRemarkupRule' => 'applications/project/remarkup/ProjectRemarkupRule.php',
'ProjectRemarkupRuleTestCase' => 'applications/project/remarkup/__tests__/ProjectRemarkupRuleTestCase.php',
'ProjectReplyHandler' => 'applications/project/mail/ProjectReplyHandler.php',
+ 'PythonExternalSymbolsSource' => 'applications/diffusion/symbol/PythonExternalSymbolsSource.php',
'QueryFormattingTestCase' => 'infrastructure/storage/__tests__/QueryFormattingTestCase.php',
'ReleephAuthorFieldSpecification' => 'applications/releeph/field/specification/ReleephAuthorFieldSpecification.php',
'ReleephBranch' => 'applications/releeph/storage/ReleephBranch.php',
@@ -6479,6 +6483,7 @@
'PhortuneSubscriptionWorker' => 'PhabricatorWorker',
'PhortuneTestPaymentProvider' => 'PhortunePaymentProvider',
'PhortuneWePayPaymentProvider' => 'PhortunePaymentProvider',
+ 'PhpExternalSymbolsSource' => 'DiffusionExternalSymbolsSource',
'PhragmentBrowseController' => 'PhragmentController',
'PhragmentCanCreateCapability' => 'PhabricatorPolicyCapability',
'PhragmentConduitAPIMethod' => 'ConduitAPIMethod',
@@ -6663,6 +6668,7 @@
'ProjectRemarkupRule' => 'PhabricatorObjectRemarkupRule',
'ProjectRemarkupRuleTestCase' => 'PhabricatorTestCase',
'ProjectReplyHandler' => 'PhabricatorApplicationTransactionReplyHandler',
+ 'PythonExternalSymbolsSource' => 'DiffusionExternalSymbolsSource',
'QueryFormattingTestCase' => 'PhabricatorTestCase',
'ReleephAuthorFieldSpecification' => 'ReleephFieldSpecification',
'ReleephBranch' => array(
diff --git a/src/applications/diffusion/controller/DiffusionSymbolController.php b/src/applications/diffusion/controller/DiffusionSymbolController.php
--- a/src/applications/diffusion/controller/DiffusionSymbolController.php
+++ b/src/applications/diffusion/controller/DiffusionSymbolController.php
@@ -12,7 +12,7 @@
->setViewer($user)
->setName($this->name);
- if ($request->getStr('context') !== null) {
+ if ($request->getStr('context')) {
$query->setContext($request->getStr('context'));
}
@@ -47,63 +47,69 @@
$symbols = $query->execute();
- // For PHP builtins, jump to php.net documentation.
- if ($request->getBool('jump') && count($symbols) == 0) {
- if ($request->getStr('lang', 'php') == 'php') {
- if ($request->getStr('type', 'function') == 'function') {
- $functions = get_defined_functions();
- if (in_array($this->name, $functions['internal'])) {
- return id(new AphrontRedirectResponse())
- ->setIsExternal(true)
- ->setURI('http://www.php.net/function.'.$this->name);
- }
- }
- if ($request->getStr('type', 'class') == 'class') {
- if (class_exists($this->name, false) ||
- interface_exists($this->name, false)) {
- if (id(new ReflectionClass($this->name))->isInternal()) {
- return id(new AphrontRedirectResponse())
- ->setIsExternal(true)
- ->setURI('http://www.php.net/class.'.$this->name);
- }
- }
- }
- }
+
+
+ $external_query = id(new DiffusionExternalSymbolQuery())
+ ->withNames(array($this->name));
+
+ if ($request->getStr('context')) {
+ $external_query->withContexts(array($request->getStr('context')));
+ }
+
+ if ($request->getStr('type')) {
+ $external_query->withTypes(array($request->getStr('type')));
+ }
+
+ if ($request->getStr('lang')) {
+ $external_query->withLanguages(array($request->getStr('lang')));
+ }
+
+ $external_sources = id(new PhutilSymbolLoader())
+ ->setAncestorClass('DiffusionExternalSymbolsSource')
+ ->loadObjects();
+ $results = array($symbols);
+ foreach ($external_sources as $source) {
+ $results[] = $source->lookupSymbol($external_query);
+ }
+ $symbols = array_mergev($results);
+
+ if ($request->getBool('jump') && count($symbols) == 1) {
+ // If this is a clickthrough from Differential, just jump them
+ // straight to the target if we got a single hit.
+ $symbol = head($symbols);
+ return id(new AphrontRedirectResponse())
+ ->setIsExternal($symbol->isExternal())
+ ->setURI($symbol->getURI());
}
$rows = array();
foreach ($symbols as $symbol) {
- $file = $symbol->getPath();
- $line = $symbol->getLineNumber();
+ $href = $symbol->getURI();
- $repo = $symbol->getRepository();
- if ($repo) {
- $href = $symbol->getURI();
-
- if ($request->getBool('jump') && count($symbols) == 1) {
- // If this is a clickthrough from Differential, just jump them
- // straight to the target if we got a single hit.
- return id(new AphrontRedirectResponse())->setURI($href);
- }
+ if ($symbol->isExternal()) {
+ $source = $symbol->getSource();
+ $location = $symbol->getLocation();
+ } else {
+ $repo = $symbol->getRepository();
+ $file = $symbol->getPath();
+ $line = $symbol->getLineNumber();
- $location = phutil_tag(
- 'a',
- array(
- 'href' => $href,
- ),
- $file.':'.$line);
- } else if ($file) {
+ $source = $repo->getMonogram();
$location = $file.':'.$line;
- } else {
- $location = '?';
}
+ $location = phutil_tag(
+ 'a',
+ array(
+ 'href' => $href,
+ ),
+ $location);
$rows[] = array(
$symbol->getSymbolType(),
$symbol->getSymbolContext(),
$symbol->getSymbolName(),
$symbol->getSymbolLanguage(),
- $repo->getMonogram(),
+ $source,
$location,
);
}
@@ -115,8 +121,8 @@
pht('Context'),
pht('Name'),
pht('Language'),
- pht('Repository'),
- pht('File'),
+ pht('Source'),
+ pht('Location'),
));
$table->setColumnClasses(
array(
diff --git a/src/applications/diffusion/symbol/DiffusionExternalSymbolQuery.php b/src/applications/diffusion/symbol/DiffusionExternalSymbolQuery.php
new file mode 100644
--- /dev/null
+++ b/src/applications/diffusion/symbol/DiffusionExternalSymbolQuery.php
@@ -0,0 +1,40 @@
+<?php
+
+final class DiffusionExternalSymbolQuery {
+ private $languages = array();
+ private $types = array();
+ private $names = array();
+ private $contexts = array();
+
+ public function withLanguages(array $languages) {
+ $this->languages = $languages;
+ return $this;
+ }
+ public function withTypes(array $types) {
+ $this->types = $types;
+ return $this;
+ }
+ public function withNames(array $names) {
+ $this->names = $names;
+ return $this;
+ }
+ public function withContexts(array $contexts) {
+ $this->contexts = $contexts;
+ return $this;
+ }
+
+
+ public function getLanguages() {
+ return $this->languages;
+ }
+ public function getTypes() {
+ return $this->types;
+ }
+ public function getNames() {
+ return $this->names;
+ }
+ public function getContexts() {
+ return $this->contexts;
+ }
+
+}
diff --git a/src/applications/diffusion/symbol/DiffusionExternalSymbolsSource.php b/src/applications/diffusion/symbol/DiffusionExternalSymbolsSource.php
new file mode 100644
--- /dev/null
+++ b/src/applications/diffusion/symbol/DiffusionExternalSymbolsSource.php
@@ -0,0 +1,15 @@
+<?php
+
+abstract class DiffusionExternalSymbolsSource {
+
+ /**
+ * @return list of PhabricatorRepositorySymbol
+ */
+ abstract public function lookupSymbol(DiffusionExternalSymbolQuery $query);
+
+ protected function buildExternalSymbol() {
+ return id(new PhabricatorRepositorySymbol())
+ ->setIsExternal(true)
+ ->makeEphemeral();
+ }
+}
diff --git a/src/applications/diffusion/symbol/PhpExternalSymbolsSource.php b/src/applications/diffusion/symbol/PhpExternalSymbolsSource.php
new file mode 100644
--- /dev/null
+++ b/src/applications/diffusion/symbol/PhpExternalSymbolsSource.php
@@ -0,0 +1,49 @@
+<?php
+
+final class PhpExternalSymbolsSource extends DiffusionExternalSymbolsSource {
+
+ public function lookupSymbol(DiffusionExternalSymbolQuery $query) {
+ $langs = $query->getLanguages();
+ if ($langs && !in_array('php', $langs)) {
+ return array();
+ }
+
+ $names = $query->getNames();
+ $symbols = array();
+
+ $types = $query->getTypes();
+ if (!$types || in_array('function', $types)) {
+ $functions = get_defined_functions();
+ $functions = $functions['internal'];
+
+ foreach ($names as $name) {
+ if (in_array($name, $functions)) {
+ $symbols[] = $this->buildExternalSymbol()
+ ->setSymbolName($name)
+ ->setSymbolType('function')
+ ->setSource('PHP')
+ ->setLocation('Manual at php.net')
+ ->setSymbolLanguage('PHP')
+ ->setExternalURI('http://www.php.net/function.'.$name);
+ }
+ }
+ }
+ if (!$types || in_array('class', $types)) {
+ foreach ($names as $name) {
+ if (class_exists($name, false) || interface_exists($name, false)) {
+ if (id(new ReflectionClass($name))->isInternal()) {
+ $symbols[] = $this->buildExternalSymbol()
+ ->setSymbolName($name)
+ ->setSymbolType('class')
+ ->setSource('PHP')
+ ->setLocation('Manual at php.net')
+ ->setSymbolLanguage('PHP')
+ ->setExternalURI('http://www.php.net/class.'.$name);
+ }
+ }
+ }
+ }
+
+ return $symbols;
+ }
+}
diff --git a/src/applications/diffusion/symbol/PythonExternalSymbolsSource.php b/src/applications/diffusion/symbol/PythonExternalSymbolsSource.php
new file mode 100644
--- /dev/null
+++ b/src/applications/diffusion/symbol/PythonExternalSymbolsSource.php
@@ -0,0 +1,135 @@
+<?php
+
+final class PythonExternalSymbolsSource extends DiffusionExternalSymbolsSource {
+
+ public function lookupSymbol(DiffusionExternalSymbolQuery $query) {
+ $langs = $query->getLanguages();
+ if ($langs && !array_intersect(array('py', 'python'), $langs)) {
+ return array();
+ }
+
+ $names = $query->getNames();
+ $symbols = array();
+
+ $types = $query->getTypes();
+ if ($types && !in_array('builtin', $types)) {
+ return $symbols;
+ }
+
+ foreach ($names as $name) {
+ if (idx(self::$python2Builtins, $name)) {
+ $symbols[] = $this->buildExternalSymbol()
+ ->setSymbolName($name)
+ ->setSymbolType('builtin')
+ ->setSource('Standard Library')
+ ->setLocation('The Python 2 Standard Library')
+ ->setSymbolLanguage('Python')
+ ->setExternalURI(
+ 'https://docs.python.org/2/library/functions.html#'.$name);
+ }
+ if (idx(self::$python3Builtins, $name)) {
+ $symbols[] = $this->buildExternalSymbol()
+ ->setSymbolName($name)
+ ->setSymbolType('builtin')
+ ->setSource('Standard Library')
+ ->setLocation('The Python 3 Standard Library')
+ ->setSymbolLanguage('Python')
+ ->setExternalURI(
+ 'https://docs.python.org/3/library/functions.html#'.$name);
+ }
+ }
+ return $symbols;
+ }
+
+ private static $python2Builtins = array(
+ '__import__' => true,
+ 'abs' => true,
+ 'all' => true,
+ 'any' => true,
+ 'basestring' => true,
+ 'bin' => true,
+ 'bool' => true,
+ 'bytearray' => true,
+ 'callable' => true,
+ 'chr' => true,
+ 'classmethod' => true,
+ 'cmp' => true,
+ 'compile' => true,
+ 'complex' => true,
+ 'delattr' => true,
+ 'dict' => true,
+ 'dir' => true,
+ 'divmod' => true,
+ 'enumerate' => true,
+ 'eval' => true,
+ 'execfile' => true,
+ 'file' => true,
+ 'filter' => true,
+ 'float' => true,
+ 'format' => true,
+ 'frozenset' => true,
+ 'getattr' => true,
+ 'globals' => true,
+ 'hasattr' => true,
+ 'hash' => true,
+ 'help' => true,
+ 'hex' => true,
+ 'id' => true,
+ 'input' => true,
+ 'int' => true,
+ 'isinstance' => true,
+ 'issubclass' => true,
+ 'iter' => true,
+ 'len' => true,
+ 'list' => true,
+ 'locals' => true,
+ 'long' => true,
+ 'map' => true,
+ 'max' => true,
+ 'memoryview' => true,
+ 'min' => true,
+ 'next' => true,
+ 'object' => true,
+ 'oct' => true,
+ 'open' => true,
+ 'ord' => true,
+ 'pow' => true,
+ 'print' => true,
+ 'property' => true,
+ 'range' => true,
+ 'raw_input' => true,
+ 'reduce' => true,
+ 'reload' => true,
+ 'repr' => true,
+ 'reversed' => true,
+ 'round' => true,
+ 'set' => true,
+ 'setattr' => true,
+ 'slice' => true,
+ 'sorted' => true,
+ 'staticmethod' => true,
+ 'str' => true,
+ 'sum' => true,
+ 'super' => true,
+ 'tuple' => true,
+ 'type' => true,
+ 'unichr' => true,
+ 'unicode' => true,
+ 'vars' => true,
+ 'xrange' => true,
+ 'zip' => true,
+ );
+
+ // This list only contains functions that are new or changed between the
+ // Python versions.
+ private static $python3Builtins = array(
+ 'ascii' => true,
+ 'bytes' => true,
+ 'filter' => true,
+ 'map' => true,
+ 'next' => true,
+ 'range' => true,
+ 'super' => true,
+ 'zip' => true,
+ );
+}
diff --git a/src/applications/repository/storage/PhabricatorRepositorySymbol.php b/src/applications/repository/storage/PhabricatorRepositorySymbol.php
--- a/src/applications/repository/storage/PhabricatorRepositorySymbol.php
+++ b/src/applications/repository/storage/PhabricatorRepositorySymbol.php
@@ -15,6 +15,10 @@
protected $symbolLanguage;
protected $pathID;
protected $lineNumber;
+ private $isExternal;
+ private $source;
+ private $location;
+ private $externalURI;
private $path = self::ATTACHABLE;
private $repository = self::ATTACHABLE;
@@ -40,6 +44,10 @@
}
public function getURI() {
+ if ($this->isExternal) {
+ return $this->externalURI;
+ }
+
$request = DiffusionRequest::newFromDictionary(
array(
'user' => PhabricatorUser::getOmnipotentUser(),
@@ -71,4 +79,32 @@
return $this;
}
+ public function isExternal() {
+ return $this->isExternal;
+ }
+ public function setIsExternal($is_external) {
+ $this->isExternal = $is_external;
+ return $this;
+ }
+
+ public function getSource() {
+ return $this->source;
+ }
+ public function setSource($source) {
+ $this->source = $source;
+ return $this;
+ }
+
+ public function getLocation() {
+ return $this->location;
+ }
+ public function setLocation($location) {
+ $this->location = $location;
+ return $this;
+ }
+
+ public function setExternalURI($external_uri) {
+ $this->externalURI = $external_uri;
+ return $this;
+ }
}
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Sun, Mar 23, 12:14 AM (1 w, 1 d ago)
Storage Engine
blob
Storage Format
Encrypted (AES-256-CBC)
Storage Handle
7717609
Default Alt Text
D13036.id31480.diff (16 KB)
Attached To
Mode
D13036: Framework for external symbol search
Attached
Detach File
Event Timeline
Log In to Comment