diff --git a/bridges/GithubIssueBridge.php b/bridges/GithubIssueBridge.php index 46fbc4c1..f6857ddb 100644 --- a/bridges/GithubIssueBridge.php +++ b/bridges/GithubIssueBridge.php @@ -33,17 +33,23 @@ class GithubIssueBridge extends BridgeAbstract { ) ); + // Allows generalization with GithubPullRequestBridge + const BRIDGE_OPTIONS = array(0 => 'Project Issues', 1 => 'Issue comments'); + const URL_PATH = 'issues'; + const SEARCH_QUERY_PATH = 'issues'; + const SEARCH_QUERY = '?q=is%3Aissue+sort%3Aupdated-desc'; + public function getName(){ $name = $this->getInput('u') . '/' . $this->getInput('p'); switch($this->queriedContext) { - case 'Project Issues': + case static::BRIDGE_OPTIONS[0]: // Project Issues $prefix = static::NAME . 's for '; if($this->getInput('c')) { $prefix = static::NAME . 's comments for '; } $name = $prefix . $name; break; - case 'Issue comments': + case static::BRIDGE_OPTIONS[1]: // Issue comments $name = static::NAME . ' ' . $name . ' #' . $this->getInput('i'); break; default: return parent::getName(); @@ -51,14 +57,14 @@ class GithubIssueBridge extends BridgeAbstract { return $name; } - public function getURI(){ + public function getURI() { if(null !== $this->getInput('u') && null !== $this->getInput('p')) { $uri = static::URI . $this->getInput('u') . '/' - . $this->getInput('p') . '/issues'; - if($this->queriedContext === 'Issue comments') { - $uri .= '/' . $this->getInput('i'); - } elseif($this->getInput('c')) { - $uri .= '?q=is%3Aissue+sort%3Aupdated-desc'; + . $this->getInput('p') . '/'; + if($this->queriedContext === static::BRIDGE_OPTIONS[1]) { + $uri .= static::URL_PATH . '/' . $this->getInput('i'); + } else { + $uri .= static::SEARCH_QUERY_PATH . static::SEARCH_QUERY; } return $uri; } @@ -72,19 +78,19 @@ class GithubIssueBridge extends BridgeAbstract { . $this->getInput('u') . '/' . $this->getInput('p') - . '/issues/' + . '/' . static::URL_PATH . '/' . $issue_number . '#' . $comment_id; } - private function extractIssueEvent($issueNbr, $title, $comment){ + private function extractIssueEvent($issueNbr, $title, $comment) { $uri = $this->buildGitHubIssueCommentUri($issueNbr, $comment->id); - $author = $comment->find('.author', 0); + $author = $comment->find('.author, .avatar', 0); if ($author) { - $author = $author->plaintext; + $author = trim($author->href, '/'); } else { $author = ''; } @@ -95,20 +101,26 @@ class GithubIssueBridge extends BridgeAbstract { $comment->find('.octicon', 0)->getAttribute('class') )); + $time = $comment->find('relative-time', 0); + if ($time === null) { + return; + } + + foreach($comment->find('.Details-content--hidden, .btn') as $el) { + $el->innertext = ''; + } $content = $comment->plaintext; $item = array(); $item['author'] = $author; $item['uri'] = $uri; $item['title'] = html_entity_decode($title, ENT_QUOTES, 'UTF-8'); - $item['timestamp'] = strtotime( - $comment->find('relative-time', 0)->getAttribute('datetime') - ); + $item['timestamp'] = strtotime($time->getAttribute('datetime')); $item['content'] = $content; return $item; } - private function extractIssueComment($issueNbr, $title, $comment){ + private function extractIssueComment($issueNbr, $title, $comment) { $uri = $this->buildGitHubIssueCommentUri($issueNbr, $comment->id); $author = $comment->find('.author', 0)->plaintext; @@ -117,20 +129,23 @@ class GithubIssueBridge extends BridgeAbstract { $comment->find('.timeline-comment-header-text', 0)->plaintext ); + $time = $comment->find('relative-time', 0); + if ($time === null) { + return; + } + $content = $comment->find('.comment-body', 0)->innertext; $item = array(); $item['author'] = $author; $item['uri'] = $uri; $item['title'] = html_entity_decode($title, ENT_QUOTES, 'UTF-8'); - $item['timestamp'] = strtotime( - $comment->find('relative-time', 0)->getAttribute('datetime') - ); + $item['timestamp'] = strtotime($time->getAttribute('datetime')); $item['content'] = $content; return $item; } - private function extractIssueComments($issue){ + private function extractIssueComments($issue) { $items = array(); $title = $issue->find('.gh-header-title', 0)->plaintext; $issueNbr = trim( @@ -145,29 +160,33 @@ class GithubIssueBridge extends BridgeAbstract { if ($comment->hasClass('comment')) { $comment = $comment->parent; $item = $this->extractIssueComment($issueNbr, $title, $comment); - $items[] = $item; + if ($item !== null) { + $items[] = $item; + } continue; } else { $comment = $comment->parent; $item = $this->extractIssueEvent($issueNbr, $title, $comment); - $items[] = $item; + if ($item !== null) { + $items[] = $item; + } } } return $items; } - public function collectData(){ + public function collectData() { $html = getSimpleHTMLDOM($this->getURI()) or returnServerError( - 'No results for Github Issue ' . $this->getURI() + 'No results for ' . static::NAME . ' ' . $this->getURI() ); switch($this->queriedContext) { - case 'Issue comments': + case static::BRIDGE_OPTIONS[1]: // Issue comments $this->items = $this->extractIssueComments($html); break; - case 'Project Issues': + case static::BRIDGE_OPTIONS[0]: // Project Issues foreach($html->find('.js-active-navigation-container .js-navigation-item') as $issue) { $info = $issue->find('.opened-by', 0); @@ -179,7 +198,7 @@ class GithubIssueBridge extends BridgeAbstract { if($this->getInput('c')) { $uri = static::URI . $this->getInput('u') - . '/' . $this->getInput('p') . '/issues/' . $issueNbr; + . '/' . $this->getInput('p') . '/' . static::URL_PATH . '/' . $issueNbr; $issue = getSimpleHTMLDOMCached($uri, static::CACHE_TIMEOUT); if($issue) { $this->items = array_merge( @@ -208,7 +227,7 @@ class GithubIssueBridge extends BridgeAbstract { $item['content'] .= "\n" . 'Comments: ' . $comment_count; $item['uri'] = self::URI - . $issue->find('.js-navigation-open', 0)->getAttribute('href'); + . trim($issue->find('.js-navigation-open', 0)->getAttribute('href'), '/'); $this->items[] = $item; } break; @@ -246,7 +265,7 @@ class GithubIssueBridge extends BridgeAbstract { $show_comments = 'off'; } break; case 3: { // Project issues with issue comments - if($path_segments[2] !== 'issues') { + if($path_segments[2] !== static::URL_PATH) { return null; } list($user, $project) = $path_segments; diff --git a/bridges/GithubPullRequestBridge.php b/bridges/GithubPullRequestBridge.php new file mode 100644 index 00000000..44cc1c5c --- /dev/null +++ b/bridges/GithubPullRequestBridge.php @@ -0,0 +1,38 @@ + array( + 'u' => array( + 'name' => 'User name', + 'required' => true + ), + 'p' => array( + 'name' => 'Project name', + 'required' => true + ) + ), + 'Project Pull Requests' => array( + 'c' => array( + 'name' => 'Show Pull Request Comments', + 'type' => 'checkbox' + ) + ), + 'Pull Request comments' => array( + 'i' => array( + 'name' => 'Pull Request number', + 'type' => 'number', + 'required' => true + ) + ) + ); + + const BRIDGE_OPTIONS = array(0 => 'Project Pull Requests', 1 => 'Pull Request comments'); + const URL_PATH = 'pull'; + const SEARCH_QUERY_PATH = 'pulls'; + const SEARCH_QUERY = '?q=is%3Apr+sort%3Aupdated-desc'; +}