1c64c1748SAndreas Gohr<?php 2c64c1748SAndreas Gohr 3c64c1748SAndreas Gohr/** 4c64c1748SAndreas Gohr * DokuWiki Plugin dbquery (Syntax Component) 5c64c1748SAndreas Gohr * 6c64c1748SAndreas Gohr * @license GPL 2 http://www.gnu.org/licenses/gpl-2.0.html 7c64c1748SAndreas Gohr * @author Andreas Gohr <dokuwiki@cosmocode.de> 8c64c1748SAndreas Gohr */ 9c64c1748SAndreas Gohrclass syntax_plugin_dbquery_query extends DokuWiki_Syntax_Plugin 10c64c1748SAndreas Gohr{ 11c64c1748SAndreas Gohr /** @inheritDoc */ 12c64c1748SAndreas Gohr public function getType() 13c64c1748SAndreas Gohr { 14c64c1748SAndreas Gohr return 'substition'; 15c64c1748SAndreas Gohr } 16c64c1748SAndreas Gohr 17c64c1748SAndreas Gohr /** @inheritDoc */ 18c64c1748SAndreas Gohr public function getPType() 19c64c1748SAndreas Gohr { 20c64c1748SAndreas Gohr return 'block'; 21c64c1748SAndreas Gohr } 22c64c1748SAndreas Gohr 23c64c1748SAndreas Gohr /** @inheritDoc */ 24c64c1748SAndreas Gohr public function getSort() 25c64c1748SAndreas Gohr { 26c64c1748SAndreas Gohr return 135; 27c64c1748SAndreas Gohr } 28c64c1748SAndreas Gohr 29c64c1748SAndreas Gohr /** @inheritDoc */ 30c64c1748SAndreas Gohr public function connectTo($mode) 31c64c1748SAndreas Gohr { 32c64c1748SAndreas Gohr $this->Lexer->addSpecialPattern('{{QUERY:\w+}}', $mode, 'plugin_dbquery_query'); 33c64c1748SAndreas Gohr } 34c64c1748SAndreas Gohr 35c64c1748SAndreas Gohr /** @inheritDoc */ 36c64c1748SAndreas Gohr public function handle($match, $state, $pos, Doku_Handler $handler) 37c64c1748SAndreas Gohr { 38c64c1748SAndreas Gohr return ['name' => substr($match, 8, -2)]; 39c64c1748SAndreas Gohr } 40c64c1748SAndreas Gohr 41c64c1748SAndreas Gohr /** @inheritDoc */ 42c64c1748SAndreas Gohr public function render($mode, Doku_Renderer $renderer, $data) 43c64c1748SAndreas Gohr { 44c64c1748SAndreas Gohr if ($mode !== 'xhtml') { 45c64c1748SAndreas Gohr return false; 46c64c1748SAndreas Gohr } 47c64c1748SAndreas Gohr 48c64c1748SAndreas Gohr /** @var helper_plugin_dbquery $hlp */ 49c64c1748SAndreas Gohr $hlp = plugin_load('helper', 'dbquery'); 50c64c1748SAndreas Gohr try { 51c64c1748SAndreas Gohr $qdata = $hlp->loadDataFromPage($data['name']); 52c64c1748SAndreas Gohr $result = $hlp->executeQuery($qdata['codeblocks']['_']); 53c64c1748SAndreas Gohr } catch (\Exception $e) { 54c64c1748SAndreas Gohr msg(hsc($e->getMessage()), -1); 55c64c1748SAndreas Gohr return true; 56c64c1748SAndreas Gohr } 57c64c1748SAndreas Gohr 58c64c1748SAndreas Gohr if (count($result) === 1 && isset($result[0]['status']) && isset($qdata['codeblocks'][$result[0]['status']])) { 59c64c1748SAndreas Gohr $this->renderStatus($result, $qdata['codeblocks'][$result[0]['status']], $renderer); 60c64c1748SAndreas Gohr } else { 61c64c1748SAndreas Gohr if ($qdata['macros']['transpose']) { 62c64c1748SAndreas Gohr $this->renderTransposedResultTable($result, $renderer); 63c64c1748SAndreas Gohr } else { 64c64c1748SAndreas Gohr $this->renderResultTable($result, $renderer); 65c64c1748SAndreas Gohr } 66c64c1748SAndreas Gohr } 67c64c1748SAndreas Gohr 68c64c1748SAndreas Gohr return true; 69c64c1748SAndreas Gohr } 70c64c1748SAndreas Gohr 71c64c1748SAndreas Gohr /** 72c64c1748SAndreas Gohr * Render given result via the given status HTML 73c64c1748SAndreas Gohr * 74c64c1748SAndreas Gohr * @param string[][] $result 75c64c1748SAndreas Gohr * @param string $html 76c64c1748SAndreas Gohr * @param Doku_Renderer $R 77c64c1748SAndreas Gohr */ 78c64c1748SAndreas Gohr public function renderStatus($result, $html, Doku_Renderer $R) 79c64c1748SAndreas Gohr { 80c64c1748SAndreas Gohr $value = isset($result[0]['result']) ? $result[0]['result'] : ''; 81c64c1748SAndreas Gohr $html = str_replace(':result', hsc($value), $html); 82c64c1748SAndreas Gohr $R->doc .= $html; 83c64c1748SAndreas Gohr } 84c64c1748SAndreas Gohr 85c64c1748SAndreas Gohr /** 86c64c1748SAndreas Gohr * Render the given result as a table 87c64c1748SAndreas Gohr * 88c64c1748SAndreas Gohr * @param string[][] $result 89c64c1748SAndreas Gohr * @param Doku_Renderer $R 90c64c1748SAndreas Gohr */ 91c64c1748SAndreas Gohr public function renderResultTable($result, Doku_Renderer $R) 92c64c1748SAndreas Gohr { 93c64c1748SAndreas Gohr global $lang; 94c64c1748SAndreas Gohr 95c64c1748SAndreas Gohr if (!count($result)) { 96c64c1748SAndreas Gohr $R->cdata($lang['nothingfound']); 97c64c1748SAndreas Gohr return; 98c64c1748SAndreas Gohr } 99c64c1748SAndreas Gohr 100c64c1748SAndreas Gohr $R->table_open(); 101c64c1748SAndreas Gohr $R->tablerow_open(); 102c64c1748SAndreas Gohr foreach (array_keys($result[0]) as $header) { 103c64c1748SAndreas Gohr $R->tableheader_open(); 104c64c1748SAndreas Gohr $R->cdata($header); 105c64c1748SAndreas Gohr $R->tableheader_close(); 106c64c1748SAndreas Gohr } 107c64c1748SAndreas Gohr $R->tablerow_close(); 108c64c1748SAndreas Gohr 109c64c1748SAndreas Gohr foreach ($result as $row) { 110c64c1748SAndreas Gohr $R->tablerow_open(); 111c64c1748SAndreas Gohr foreach ($row as $cell) { 112c64c1748SAndreas Gohr $R->tablecell_open(); 113*1b7b5e66SAndreas Gohr $this->cellFormat($cell, $R); 114c64c1748SAndreas Gohr $R->tablecell_close(); 115c64c1748SAndreas Gohr } 116c64c1748SAndreas Gohr $R->tablerow_close(); 117c64c1748SAndreas Gohr } 118c64c1748SAndreas Gohr $R->table_close(); 119c64c1748SAndreas Gohr } 120c64c1748SAndreas Gohr 121c64c1748SAndreas Gohr /** 122c64c1748SAndreas Gohr * Render the given result as a table, but turned 90 degrees 123c64c1748SAndreas Gohr * 124c64c1748SAndreas Gohr * @param string[][] $result 125c64c1748SAndreas Gohr * @param Doku_Renderer $R 126c64c1748SAndreas Gohr */ 127c64c1748SAndreas Gohr public function renderTransposedResultTable($result, Doku_Renderer $R) 128c64c1748SAndreas Gohr { 129c64c1748SAndreas Gohr global $lang; 130c64c1748SAndreas Gohr 131c64c1748SAndreas Gohr if (!count($result)) { 132c64c1748SAndreas Gohr $R->cdata($lang['nothingfound']); 133c64c1748SAndreas Gohr return; 134c64c1748SAndreas Gohr } 135c64c1748SAndreas Gohr 136c64c1748SAndreas Gohr $width = count($result[0]); 137c64c1748SAndreas Gohr $height = count($result); 138c64c1748SAndreas Gohr 139c64c1748SAndreas Gohr $R->table_open(); 140c64c1748SAndreas Gohr for ($x = 0; $x < $width; $x++) { 141c64c1748SAndreas Gohr $R->tablerow_open(); 142c64c1748SAndreas Gohr $R->tableheader_open(); 143c64c1748SAndreas Gohr $R->cdata(array_keys($result[0])[$x]); 144c64c1748SAndreas Gohr $R->tableheader_close(); 145c64c1748SAndreas Gohr 146c64c1748SAndreas Gohr for ($y = 0; $y < $height; $y++) { 147c64c1748SAndreas Gohr $R->tablecell_open(); 148*1b7b5e66SAndreas Gohr $this->cellFormat(array_values($result[$y])[$x], $R); 149c64c1748SAndreas Gohr $R->tablecell_close(); 150c64c1748SAndreas Gohr } 151c64c1748SAndreas Gohr $R->tablerow_close(); 152c64c1748SAndreas Gohr } 153c64c1748SAndreas Gohr $R->table_close(); 154c64c1748SAndreas Gohr } 155c64c1748SAndreas Gohr 156*1b7b5e66SAndreas Gohr /** 157*1b7b5e66SAndreas Gohr * Pass the given cell content to the correct renderer call 158*1b7b5e66SAndreas Gohr * 159*1b7b5e66SAndreas Gohr * Detects a subset of the wiki link syntax 160*1b7b5e66SAndreas Gohr * 161*1b7b5e66SAndreas Gohr * @param string $content 162*1b7b5e66SAndreas Gohr * @param Doku_Renderer $R 163*1b7b5e66SAndreas Gohr * @return void 164*1b7b5e66SAndreas Gohr */ 165*1b7b5e66SAndreas Gohr protected function cellFormat($content, Doku_Renderer $R) 166*1b7b5e66SAndreas Gohr { 167*1b7b5e66SAndreas Gohr // external urls 168*1b7b5e66SAndreas Gohr if (preg_match('/^\[\[(https?:\/\/[^|\]]+)(|.*?)?]]$/', $content, $m)) { 169*1b7b5e66SAndreas Gohr $url = $m[1]; 170*1b7b5e66SAndreas Gohr $title = $m[2] ?? ''; 171*1b7b5e66SAndreas Gohr $title = trim($title,'|'); 172*1b7b5e66SAndreas Gohr $R->externallink($url, $title); 173*1b7b5e66SAndreas Gohr return; 174*1b7b5e66SAndreas Gohr } 175*1b7b5e66SAndreas Gohr 176*1b7b5e66SAndreas Gohr // internal urls 177*1b7b5e66SAndreas Gohr if (preg_match('/^\[\[([^|\]]+)(|.*?)?]]$/', $content, $m)) { 178*1b7b5e66SAndreas Gohr $page = cleanID($m[1]); 179*1b7b5e66SAndreas Gohr $title = $m[2] ?? ''; 180*1b7b5e66SAndreas Gohr $title = trim($title,'|'); 181*1b7b5e66SAndreas Gohr $R->internallink($page, $title); 182*1b7b5e66SAndreas Gohr return; 183*1b7b5e66SAndreas Gohr } 184*1b7b5e66SAndreas Gohr 185*1b7b5e66SAndreas Gohr $R->cdata($content); 186*1b7b5e66SAndreas Gohr } 187c64c1748SAndreas Gohr} 188c64c1748SAndreas Gohr 189