1<?php
2/**
3 * DokuWiki Plugin ghissues (Syntax Component)
4 *
5 * @license GPL 2 http://www.gnu.org/licenses/gpl-2.0.html
6 * @author  Zach Smith <zsmith12@umd.edu>
7 */
8
9// must be run within Dokuwiki
10if (!defined('DOKU_INC')) die();
11
12class syntax_plugin_ghissues_syntax extends DokuWiki_Syntax_Plugin {
13    /**
14     * @return string Syntax mode type
15     */
16    public function getType() {
17        return 'substition';
18    }
19    /**
20     * @return string Paragraph type
21     */
22    public function getPType() {
23        return 'block';
24    }
25    /**
26     * @return int Sort order - Low numbers go before high numbers
27     */
28    public function getSort() {
29        return 305;
30    }
31
32    /**
33     * Connect lookup pattern to lexer.
34     *
35     * @param string $mode Parser mode
36     */
37    public function connectTo($mode) {
38        $this->Lexer->addSpecialPattern('\{\{ghissues\b.*?}}',$mode,'plugin_ghissues_syntax');
39    }
40
41    /**
42     * Handle matches of the ghissues syntax
43     *
44     * @param string $match The match of the syntax
45     * @param int    $state The state of the handler
46     * @param int    $pos The position in the document
47     * @param Doku_Handler    $handler The handler
48     * @return array Data for the renderer
49     */
50    public function handle($match, $state, $pos, Doku_Handler &$handler){
51        $dropwrapper = trim(substr(substr($match,11),0,-2));
52
53        $exploded = explode(' ',$dropwrapper);
54
55        $repoPath = htmlentities($exploded[0]);
56
57        unset($exploded[0]);
58        $theRest = implode(" ",$exploded);
59
60        $filters='';
61
62		// Check if we're filtering based on issue state
63        $headerState = $this->getLang('open');
64        $matches = array();
65        if ( preg_match("/\bstate:(open|closed|all)\b/", $theRest, $matches) ) {
66        	switch($matches[1]) {
67        		case "open":
68        			$filters="?state=open";
69        			break;
70        		case "closed":
71        			$filters="?state=closed";
72        			$headerState = $this->getLang('closed');
73        			break;
74        		case "all":
75        			$filters="?state=all";
76        			$headerState = $this->getLang('all');
77        			break;
78        	}
79        }
80
81        // Now check for label processing, matches "label:" through end of line
82        $headerLabel = '';
83        $matches = array();
84        $codedLabels = array();
85        if ( preg_match("/\blabels?:(.*\z)/", $theRest, $matches) ) {
86        	if( $filters == '' ) {
87        		$filters = '?labels=';
88        	} else {
89        		$filters .= '&labels=';
90        	}
91        	$rawLabels = array();
92        	$rawLabels = preg_split('~\\\\.(*SKIP)(*FAIL)|,~s', trim($matches[1]));
93        	if ( count($rawLabels) > 1 ) {
94        		$headerLabel = $this->getLang('withLabels');
95        	} else {
96        		$headerLabel = $this->getLang('withLabel');
97        	}
98        	foreach ($rawLabels as $thisIndex => $thisLabel) {
99        		$codedLabels[$thisIndex] = urlencode($thisLabel);
100        	}
101        	$headerLabel .= htmlentities(implode($this->getLang('and'),$rawLabels));
102        	$filters .= implode(',',$codedLabels);
103        }
104
105        $url = 'https://api.github.com/repos/'.$repoPath.'/issues'.$filters;
106		$httpUrl = 'http://www.github.com/'.$repoPath.'/issues'.$filters;
107
108        $buildHeader = $headerState.$this->getLang('issuesIn');
109
110        $wholeHeader = $buildHeader.htmlentities($repoPath).$headerLabel;
111        $wholeFooter = $this->external_link($httpUrl, $this->getLang('viewOnGH'), NULL, '_blank');
112        $data = array( 'header' => $wholeHeader, 'url' => $url, 'footer' => $wholeFooter );
113
114        return $data;
115    }
116
117    /**
118     * Render xhtml output or metadata
119     *
120     * @param string         $mode      Renderer mode (supported modes: xhtml)
121     * @param Doku_Renderer  $renderer  The renderer
122     * @param array          $data      The data from the handler() function
123     * @return bool If rendering was successful.
124     */
125    public function render($mode, Doku_Renderer &$renderer, $data) {
126        if($mode == 'metadata') {
127        	//dbglog("In render metadata");
128
129        	$hashpair = array( $data['url'] => hash('md5', $data['url']) );
130
131        	if (!isset($renderer->meta['plugin_ghissues_apicalls'])) $renderer->meta['plugin_ghissues_apicalls'] = array();
132        	$renderer->meta['plugin_ghissues_apicalls'] = array_unique(array_merge($renderer->meta['plugin_ghissues_apicalls'], $hashpair));
133
134        	return true;
135        }
136
137		if ($mode != 'xhtml') return false;
138		global $conf;
139        //dbglog("ghissues: In render xhtml");
140
141		$renderOutput  = '<div class="ghissues_plugin_box">'."\n".'<div class="ghissues_plugin_box_header">';
142		$renderOutput .= $data['header']."</div>\n";
143		// If we don't load the helper, we're doomed.
144		if ( !($loadFromCache = $this->loadHelper('ghissues_apiCacheInterface')) ) {
145			$renderer->doc .= '<p>ghissues helper failed to load</p>';
146			return false;
147		}
148
149		$renderOutput .= $loadFromCache->getRenderedRequest($data['url']);
150		$renderOutput .= '<div class="ghissues_plugin_box_footer">'.$data['footer'].'</div>';
151		$renderOutput .= '</div>';
152		$renderer->doc .= $renderOutput;
153
154        return true;
155    }
156
157}
158
159// vim:ts=4:sw=4:et:
160