Page Menu
Home
Phorge
Search
Configure Global Search
Log In
Files
F2891551
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Award Token
Flag For Later
Advanced/Developer...
View Handle
View Hovercard
Size
8 KB
Referenced Files
None
Subscribers
None
View Options
diff --git a/src/infrastructure/daemon/irc/handler/base/PhabricatorIRCHandler.php b/src/infrastructure/daemon/irc/handler/base/PhabricatorIRCHandler.php
index 4a66ee418b..10daa1cb27 100644
--- a/src/infrastructure/daemon/irc/handler/base/PhabricatorIRCHandler.php
+++ b/src/infrastructure/daemon/irc/handler/base/PhabricatorIRCHandler.php
@@ -1,48 +1,52 @@
<?php
/*
* Copyright 2011 Facebook, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/**
* Responds to IRC messages. You plug a bunch of these into a
* @{class:PhabricatorIRCBot} to give it special behavior.
*
* @group irc
*/
abstract class PhabricatorIRCHandler {
private $bot;
final public function __construct(PhabricatorIRCBot $irc_bot) {
$this->bot = $irc_bot;
}
final protected function write($command, $message) {
$this->bot->writeCommand($command, $message);
return $this;
}
final protected function getConduit() {
return $this->bot->getConduit();
}
final protected function getConfig($key, $default = null) {
return $this->bot->getConfig($key, $default);
}
+ final protected function getURI($path) {
+ return $this->bot->getConfig('conduit.uri').$path;
+ }
+
abstract public function receiveMessage(PhabricatorIRCMessage $message);
}
diff --git a/src/infrastructure/daemon/irc/handler/objectname/PhabricatorIRCObjectNameHandler.php b/src/infrastructure/daemon/irc/handler/objectname/PhabricatorIRCObjectNameHandler.php
index b9316a5311..de771d4e2b 100644
--- a/src/infrastructure/daemon/irc/handler/objectname/PhabricatorIRCObjectNameHandler.php
+++ b/src/infrastructure/daemon/irc/handler/objectname/PhabricatorIRCObjectNameHandler.php
@@ -1,181 +1,215 @@
<?php
/*
* Copyright 2011 Facebook, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/**
* Looks for Dxxxx, Txxxx and links to them.
*
* @group irc
*/
class PhabricatorIRCObjectNameHandler extends PhabricatorIRCHandler {
/**
* Map of PHIDs to the last mention of them (as an epoch timestamp); prevents
* us from spamming chat when a single object is discussed.
*/
private $recentlyMentioned = array();
public function receiveMessage(PhabricatorIRCMessage $message) {
switch ($message->getCommand()) {
case 'PRIVMSG':
$channel = $message->getChannel();
if (!$channel) {
break;
}
+ $this->handleSymbols($message);
+
$message = $message->getMessageText();
$matches = null;
- $phids = array();
$pattern =
'@'.
'(?<!/)(?:^|\b)'. // Negative lookbehind prevent matching "/D123".
'(D|T|P|V)(\d+)'.
'(?:\b|$)'.
'@';
$revision_ids = array();
$task_ids = array();
$paste_ids = array();
$commit_names = array();
$vote_ids = array();
if (preg_match_all($pattern, $message, $matches, PREG_SET_ORDER)) {
foreach ($matches as $match) {
switch ($match[1]) {
case 'D':
$revision_ids[] = $match[2];
break;
case 'T':
$task_ids[] = $match[2];
break;
case 'P':
$paste_ids[] = $match[2];
break;
case 'V':
$vote_ids[] = $match[2];
break;
}
}
}
$pattern =
'@'.
'(?<!/)(?:^|\b)'.
'(r[A-Z]+[0-9a-z]{1,40})'.
'(?:\b|$)'.
'@';
if (preg_match_all($pattern, $message, $matches, PREG_SET_ORDER)) {
foreach ($matches as $match) {
$commit_names[] = $match[1];
}
}
$output = array();
if ($revision_ids) {
$revisions = $this->getConduit()->callMethodSynchronous(
'differential.find',
array(
'query' => 'revision-ids',
'guids' => $revision_ids,
));
foreach ($revisions as $revision) {
$output[$revision['phid']] =
'D'.$revision['id'].' '.$revision['name'].' - '.
$revision['uri'];
}
}
if ($task_ids) {
foreach ($task_ids as $task_id) {
$task = $this->getConduit()->callMethodSynchronous(
'maniphest.info',
array(
'task_id' => $task_id,
));
$output[$task['phid']] = 'T'.$task['id'].': '.$task['title'].
' (Priority: '.$task['priority'].') - '.$task['uri'];
}
}
if ($vote_ids) {
foreach ($vote_ids as $vote_id) {
$vote = $this->getConduit()->callMethodSynchronous(
'slowvote.info',
array(
'poll_id' => $vote_id,
));
$output[$vote['phid']] = 'V'.$vote['id'].': '.$vote['question'].
' Come Vote '.$vote['uri'];
}
}
if ($paste_ids) {
foreach ($paste_ids as $paste_id) {
$paste = $this->getConduit()->callMethodSynchronous(
'paste.info',
array(
'paste_id' => $paste_id,
));
// Eventually I'd like to show the username of the paster as well,
// however that will need something like a user.username_from_phid
// since we (ideally) want to keep the bot to Conduit calls...and
// not call to Phabricator-specific stuff (like actually loading
// the User object and fetching his/her username.)
$output[$paste['phid']] = 'P'.$paste['id'].': '.$paste['uri'].' - '.
$paste['title'];
if ($paste['language']) {
$output[$paste['phid']] .= ' ('.$paste['language'].')';
}
}
}
if ($commit_names) {
$commits = $this->getConduit()->callMethodSynchronous(
'diffusion.getcommits',
array(
'commits' => $commit_names,
));
foreach ($commits as $commit) {
if (isset($commit['error'])) {
continue;
}
$output[$commit['commitPHID']] = $commit['uri'];
}
}
foreach ($output as $phid => $description) {
// Don't mention the same object more than once every 10 minutes, so
// we avoid spamming the chat over and over again for discsussions of
// a specific revision, for example.
$quiet_until = idx($this->recentlyMentioned, $phid, 0) + (60 * 10);
if (time() < $quiet_until) {
continue;
}
$this->recentlyMentioned[$phid] = time();
$this->write('PRIVMSG', "{$channel} :{$description}");
}
break;
}
}
+ private function handleSymbols(PhabricatorIRCMessage $message) {
+ $channel = $message->getChannel();
+ $text = $message->getMessageText();
+
+ $matches = null;
+ if (!preg_match('/where is (\S+?)\?/i', $text, $matches)) {
+ return;
+ }
+
+ $symbol = $matches[1];
+ $results = $this->getConduit()->callMethodSynchronous(
+ 'diffusion.findsymbols',
+ array(
+ 'name' => $symbol,
+ ));
+
+ if (count($results) > 1) {
+ $uri = $this->getURI('/diffusion/symbol/'.$symbol.'/');
+ $response = "Multiple symbols named '{$symbol}': {$uri}";
+ } else if (count($results) == 1) {
+ $result = head($results);
+ $response =
+ $result['type'].' '.
+ $result['name'].' '.
+ '('.$result['language'].'): '.
+ $result['uri'];
+ } else {
+ $response = "No symbol '{$symbol}' found anywhere.";
+ }
+
+ $this->write('PRIVMSG', "{$channel} :{$response}");
+ }
+
}
File Metadata
Details
Attached
Mime Type
text/x-diff
Expires
Sun, Jan 19, 15:21 (3 w, 1 d ago)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
1125946
Default Alt Text
(8 KB)
Attached To
Mode
rP Phorge
Attached
Detach File
Event Timeline
Log In to Comment