xref: /plugin/doi/syntax/isbn.php (revision 19099051d67524067917f46dcae400e7d8a95f79)
126b57c75SAndreas Gohr<?php
226b57c75SAndreas Gohr
326b57c75SAndreas Gohr/**
426b57c75SAndreas Gohr * DokuWiki Plugin doi (Syntax Component)
526b57c75SAndreas Gohr *
626b57c75SAndreas Gohr * @license GPL 2 http://www.gnu.org/licenses/gpl-2.0.html
726b57c75SAndreas Gohr * @author  Andreas Gohr <gohr@cosmocode.de>
826b57c75SAndreas Gohr */
926b57c75SAndreas Gohrclass syntax_plugin_doi_isbn extends \dokuwiki\Extension\SyntaxPlugin
1026b57c75SAndreas Gohr{
1126b57c75SAndreas Gohr    /** @inheritDoc */
1226b57c75SAndreas Gohr    public function getType()
1326b57c75SAndreas Gohr    {
1426b57c75SAndreas Gohr        return 'substition';
1526b57c75SAndreas Gohr    }
1626b57c75SAndreas Gohr
1726b57c75SAndreas Gohr    /** @inheritDoc */
1826b57c75SAndreas Gohr    public function getPType()
1926b57c75SAndreas Gohr    {
2026b57c75SAndreas Gohr        return 'normal';
2126b57c75SAndreas Gohr    }
2226b57c75SAndreas Gohr
2326b57c75SAndreas Gohr    /** @inheritDoc */
2426b57c75SAndreas Gohr    public function getSort()
2526b57c75SAndreas Gohr    {
2626b57c75SAndreas Gohr        return 155;
2726b57c75SAndreas Gohr    }
2826b57c75SAndreas Gohr
2926b57c75SAndreas Gohr    /** @inheritDoc */
3026b57c75SAndreas Gohr    public function connectTo($mode)
3126b57c75SAndreas Gohr    {
3226b57c75SAndreas Gohr        $this->Lexer->addSpecialPattern('\[\[isbn>[^\]]+\]\]', $mode, 'plugin_doi_isbn');
3326b57c75SAndreas Gohr    }
3426b57c75SAndreas Gohr
3526b57c75SAndreas Gohr    /** @inheritDoc */
3626b57c75SAndreas Gohr    public function handle($match, $state, $pos, Doku_Handler $handler)
3726b57c75SAndreas Gohr    {
38*19099051SAndreas Gohr        $isbn = substr($match, 7, -2);
39*19099051SAndreas Gohr        $isbn = preg_replace('/[^0-9X]/i', '', $isbn);
4026b57c75SAndreas Gohr
41*19099051SAndreas Gohr        return ['isbn' => $isbn];
4226b57c75SAndreas Gohr    }
4326b57c75SAndreas Gohr
4426b57c75SAndreas Gohr    /** @inheritDoc */
4526b57c75SAndreas Gohr    public function render($mode, Doku_Renderer $renderer, $data)
4626b57c75SAndreas Gohr    {
4726b57c75SAndreas Gohr        $publication = $this->fetchInfo($data['isbn']);
4826b57c75SAndreas Gohr        $title = $publication['details']['title'] ?? $data['isbn'];
4926b57c75SAndreas Gohr        $url = $publication['details']['info_url'] ?? 'https://www.google.com/search?q=isbn+' . $data['isbn'];
5026b57c75SAndreas Gohr
5126b57c75SAndreas Gohr        if ($mode !== 'xhtml' || !$publication) {
5226b57c75SAndreas Gohr            $renderer->externallink($url, $title);
5326b57c75SAndreas Gohr            return true;
5426b57c75SAndreas Gohr        }
5526b57c75SAndreas Gohr
5626b57c75SAndreas Gohr        /** @var Doku_Renderer_xhtml $renderer */
5726b57c75SAndreas Gohr        $this->formatPub($publication, $renderer);
5826b57c75SAndreas Gohr
5926b57c75SAndreas Gohr        return true;
6026b57c75SAndreas Gohr    }
6126b57c75SAndreas Gohr
6226b57c75SAndreas Gohr    /**
6326b57c75SAndreas Gohr     * Render the given message
6426b57c75SAndreas Gohr     *
6526b57c75SAndreas Gohr     * @param array $message
6626b57c75SAndreas Gohr     * @param Doku_Renderer_xhtml $renderer
6726b57c75SAndreas Gohr     * @return void
6826b57c75SAndreas Gohr     */
6926b57c75SAndreas Gohr    protected function formatPub($message, $renderer)
7026b57c75SAndreas Gohr    {
7126b57c75SAndreas Gohr        $url = $message['info_url'];
7226b57c75SAndreas Gohr        $message = $message['details'];
7326b57c75SAndreas Gohr
7426b57c75SAndreas Gohr        $isbn = $message['isbn_13'][0] ?? $message['isbn_10'][0] ?? '';
7526b57c75SAndreas Gohr        $title = $message['title'] ?? $isbn;
7626b57c75SAndreas Gohr
7726b57c75SAndreas Gohr        $class = 'book';
7826b57c75SAndreas Gohr
7926b57c75SAndreas Gohr        $authorList = [];
8026b57c75SAndreas Gohr        foreach ($message['authors'] ?? [] as $author) {
8126b57c75SAndreas Gohr            $authorList[] = '<strong>' . hsc($author['name']) . '</strong>';
8226b57c75SAndreas Gohr        }
8326b57c75SAndreas Gohr
8426b57c75SAndreas Gohr        $published = $message['publish_date'] ?? '';
8526b57c75SAndreas Gohr        if (preg_match('/\b(\d{4})\b/', $published, $m)) {
8626b57c75SAndreas Gohr            $published = ' <span>(' . hsc($m[1]) . ')</span>';
8726b57c75SAndreas Gohr        } else {
8826b57c75SAndreas Gohr            $published = '';
8926b57c75SAndreas Gohr        }
9026b57c75SAndreas Gohr
9126b57c75SAndreas Gohr        $publisher = hsc($message['publishers'][0] ?? '');
9226b57c75SAndreas Gohr
9326b57c75SAndreas Gohr        //output
9426b57c75SAndreas Gohr        $renderer->doc .= '<div class="plugin_doi ' . $class . '">';
9526b57c75SAndreas Gohr        $renderer->externallink($url, $title);
9626b57c75SAndreas Gohr        $renderer->doc .= $published;
9726b57c75SAndreas Gohr
9826b57c75SAndreas Gohr        $renderer->doc .= '<div class="meta">';
9926b57c75SAndreas Gohr        if ($authorList) {
10026b57c75SAndreas Gohr            $renderer->doc .= '<span class="authors">' . join(', ', $authorList) . '</span>';
10126b57c75SAndreas Gohr        }
10226b57c75SAndreas Gohr        $renderer->doc .= '</div>';
10326b57c75SAndreas Gohr
10426b57c75SAndreas Gohr        $renderer->doc .= '<div class="meta">';
10526b57c75SAndreas Gohr        if ($publisher) {
10626b57c75SAndreas Gohr            $renderer->doc .= '<span class="publisher">' . $publisher . '</span>';
10726b57c75SAndreas Gohr        }
10826b57c75SAndreas Gohr        $renderer->doc .= ' <code class="isbn">ISBN:' . $isbn . '</code>';
10926b57c75SAndreas Gohr        $renderer->doc .= '</div>';
11026b57c75SAndreas Gohr
11126b57c75SAndreas Gohr        $renderer->doc .= '</div>';
11226b57c75SAndreas Gohr    }
11326b57c75SAndreas Gohr
11426b57c75SAndreas Gohr    /**
11526b57c75SAndreas Gohr     * Fetch the info for the given ISBN
11626b57c75SAndreas Gohr     *
11726b57c75SAndreas Gohr     * @param string $isbn
11826b57c75SAndreas Gohr     * @return false|array
11926b57c75SAndreas Gohr     */
12026b57c75SAndreas Gohr    protected function fetchInfo($isbn)
12126b57c75SAndreas Gohr    {
1224163f19cSAndreas Gohr        $cache = getCacheName($isbn, '.isbn.json');
1234163f19cSAndreas Gohr        if (@filemtime($cache) > filemtime(__FILE__)) {
1244163f19cSAndreas Gohr            $data = json_decode(file_get_contents($cache), true);
1254163f19cSAndreas Gohr        } else {
12626b57c75SAndreas Gohr            $http = new \dokuwiki\HTTP\DokuHTTPClient();
12726b57c75SAndreas Gohr            $json = $http->get('https://openlibrary.org/api/books?jscmd=details&format=json&bibkeys=ISBN:' . $isbn);
12826b57c75SAndreas Gohr            if (!$json) return false;
12926b57c75SAndreas Gohr
1304163f19cSAndreas Gohr            file_put_contents($cache, $json);
13126b57c75SAndreas Gohr            $data = json_decode($json, true);
1324163f19cSAndreas Gohr        }
13326b57c75SAndreas Gohr        return array_shift($data); // first entry
13426b57c75SAndreas Gohr    }
13526b57c75SAndreas Gohr}
13626b57c75SAndreas Gohr
137