Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
0.00% covered (danger)
0.00%
0 / 52
0.00% covered (danger)
0.00%
0 / 3
CRAP
0.00% covered (danger)
0.00%
0 / 1
Hooks
0.00% covered (danger)
0.00%
0 / 52
0.00% covered (danger)
0.00%
0 / 3
342
0.00% covered (danger)
0.00%
0 / 1
 onSidebarBeforeOutput
0.00% covered (danger)
0.00%
0 / 40
0.00% covered (danger)
0.00%
0 / 1
182
 getIndexOfDownloadPdfSidebarItem
0.00% covered (danger)
0.00%
0 / 6
0.00% covered (danger)
0.00%
0 / 1
20
 generateDownloadScreenLink
0.00% covered (danger)
0.00%
0 / 6
0.00% covered (danger)
0.00%
0 / 1
2
1<?php
2/**
3 * Hooks for ElectronPdfService extension
4 *
5 * @file
6 * @ingroup Extensions
7 * @license GPL-2.0-or-later
8 */
9
10namespace MediaWiki\Extension\ElectronPdfService;
11
12use MediaWiki\Registration\ExtensionRegistry;
13use MediaWiki\Skin\Hook\SidebarBeforeOutputHook;
14use MediaWiki\Skin\Skin;
15use MediaWiki\SpecialPage\SpecialPage;
16use MediaWiki\Title\Title;
17
18class Hooks implements SidebarBeforeOutputHook {
19
20    /**
21     * If present, make the "Download as PDF" link in the sidebar point to the download screen,
22     * add a new link otherwise.
23     *
24     * @param Skin $skin
25     * @param array &$sidebar
26     */
27    public function onSidebarBeforeOutput( $skin, &$sidebar ): void {
28        $title = $skin->getTitle();
29        if ( $title === null || !$title->exists() ) {
30            return;
31        }
32
33        $action = $skin->getActionName();
34        if ( $action !== 'view' && $action !== 'purge' ) {
35            return;
36        }
37
38        $output = $skin->getOutput();
39        $config = $skin->getConfig();
40
41        if (
42            ExtensionRegistry::getInstance()->isLoaded( 'Collection' ) &&
43            $config->has( 'CollectionFormats' ) &&
44            array_key_exists( 'coll-print_export', $sidebar )
45        ) {
46            $index = self::getIndexOfDownloadPdfSidebarItem(
47                $sidebar['coll-print_export'],
48                $config->get( 'CollectionFormats' )
49            );
50
51            if ( $output->isRevisionCurrent() ) {
52                if ( $index !== null ) {
53                    // if Collection extension provides a download-as-pdf link, make it point to the download screen
54                    $sidebar['coll-print_export'][$index]['href'] = self::generateDownloadScreenLink(
55                        $title
56                    );
57                } else {
58                    // if no download-as-pdf link is there, add one and point to the download screen
59                    $sidebar['coll-print_export'][] = [
60                        'text' => $skin->msg( 'electronpdfservice-sidebar-portlet-print-text' )->text(),
61                        'id' => 'electron-print_pdf',
62                        'href' => self::generateDownloadScreenLink( $title )
63                    ];
64                }
65            } elseif ( $index !== null ) {
66                // Electron/Proton do not support generating PDFs for old versions, but Collection did
67                unset( $sidebar['coll-print_export'][$index] );
68            }
69            return;
70        }
71
72        // in case Collection is not installed, let's add our own portlet
73        // with a link to the download screen
74        $out = [];
75        if ( $output->isRevisionCurrent() ) {
76            $out[] = [
77                'text' => $skin->msg( 'electronpdfservice-sidebar-portlet-print-text' )->text(),
78                'id' => 'electron-print_pdf',
79                'href' => self::generateDownloadScreenLink( $title )
80            ];
81        }
82
83        if ( isset( $sidebar['TOOLBOX']['print'] ) ) {
84            $printItem = $sidebar['TOOLBOX']['print'];
85
86            // Unset 'print' item and move it to our section
87            unset( $sidebar['TOOLBOX']['print'] );
88            $out[] = $printItem;
89        }
90
91        $sidebar['electronpdfservice-sidebar-portlet-heading'] = $out;
92    }
93
94    /**
95     * @param array $portlet
96     * @param string[] $collectionFormats
97     * @return int|null
98     */
99    private static function getIndexOfDownloadPdfSidebarItem(
100        array $portlet,
101        array $collectionFormats
102    ): ?int {
103        $usedPdfLib = array_search( 'PDF', $collectionFormats );
104        if ( $usedPdfLib !== false ) {
105            foreach ( $portlet as $index => $element ) {
106                if ( $element['id'] === 'coll-download-as-' . $usedPdfLib ) {
107                    return $index;
108                }
109            }
110        }
111
112        return null;
113    }
114
115    private static function generateDownloadScreenLink( Title $title ): string {
116        return SpecialPage::getTitleFor( 'DownloadAsPdf' )->getLocalURL(
117            [
118                'page' => $title->getPrefixedDBkey(),
119                'action' => 'show-download-screen'
120            ]
121        );
122    }
123
124}