addMeta( 'viewport', 'width=device-width, initial-scale=1.0' ); // Theme color $out->addMeta( 'theme-color', $this->getConfig()->get( 'CitizenThemeColor' ) ); // Preconnect origin if ( $this->getConfig()->get( 'CitizenEnablePreconnect' ) ) { $out->addLink( [ 'rel' => 'preconnect', 'href' => $this->getConfig()->get( 'CitizenPreconnectURL' ) ] ); } // Generate manifest if ( $this->getConfig()->get( 'CitizenEnableManifest' ) ) { $out->addLink( [ 'rel' => 'manifest', 'href' => wfExpandUrl( wfAppendQuery( wfScript( 'api' ), [ 'action' => 'webapp-manifest' ] ), PROTO_RELATIVE ) ] ); } // CSP if ( $this->getConfig()->get( 'CitizenEnableCSP' ) ) { $cspdirective = $this->getConfig()->get( 'CitizenCSPDirective' ); // Check if report mode is enabled if ( $this->getConfig()->get( 'CitizenEnableCSPReportMode' ) ) { $out->getRequest()->response()->header( 'Content-Security-Policy-Report-Only: ' . $cspdirective ); } else { $out->getRequest()->response()->header( 'Content-Security-Policy: ' . $cspdirective ); } } // HSTS if ( $this->getConfig()->get( 'CitizenEnableHSTS' ) ) { $hstsmaxage = $this->getConfig()->get( 'CitizenHSTSMaxAge' ); $hstsincludesubdomains = $this->getConfig()->get( 'CitizenHSTSIncludeSubdomains' ); $hstspreload = $this->getConfig()->get( 'CitizenHSTSPreload' ); // HSTS max age if ( is_int( $hstsmaxage ) ) { $hstsmaxage = max($hstsmaxage, 0); } else { // Default to 5 mins if input is invalid $hstsmaxage = 300; } $out->getRequest()->response()->header( 'Strict-Transport-Security: max-age=' . $hstsmaxage . ( $hstsincludesubdomains ? '; includeSubDomains' : '' ) . ( $hstspreload ? '; preload' : '' ) ); } // Deny X-Frame-Options if ( $this->getConfig()->get( 'CitizenEnableDenyXFrameOptions' ) ) { $out->getRequest()->response()->header( 'X-Frame-Options: deny' ); } // Strict referrer policy if ( $this->getConfig()->get( 'CitizenEnableStrictReferrerPolicy' ) ) { // iOS Safari, IE, Edge compatiblity $out->addMeta( 'referrer', 'strict-origin' ); $out->addMeta( 'referrer', 'strict-origin-when-cross-origin' ); $out->getRequest()->response()->header( 'Referrer-Policy: strict-origin-when-cross-origin' ); } $out->addModuleStyles( [ 'mediawiki.skinning.content.externallinks', 'skins.citizen', 'skins.citizen.icons', 'skins.citizen.icons.ca', 'skins.citizen.icons.p', 'skins.citizen.icons.toc', 'skins.citizen.icons.es', 'skins.citizen.icons.n', 'skins.citizen.icons.t', 'skins.citizen.icons.pt', 'skins.citizen.icons.footer', 'skins.citizen.icons.badges', 'skins.citizen.icons.search' ] ); $out->addModules( [ 'skins.citizen.js', 'skins.citizen.search' ] ); } /** * @param $out OutputPage */ function setupSkinUserCss( OutputPage $out ) { parent::setupSkinUserCss( $out ); } }