diff --git a/lib/transformations/pcs/head.js b/lib/transformations/pcs/head.js index 89e02581c..32c4b2843 100644 --- a/lib/transformations/pcs/head.js +++ b/lib/transformations/pcs/head.js @@ -1,111 +1,114 @@ 'use strict'; /** * Shared base URI so clients don't need to download multiple copies, e.g. one per domain. */ const BASE_URI = 'https://meta.wikimedia.org/api/rest_v1/'; /** * Adds a single link to a CSS stylesheet to html/head * @param {Document} document DOM document * @param {string} cssLink the link to the stylesheet * @return {Element} DOM Element */ function createStylesheetLinkElement(document, cssLink) { const linkEl = document.createElement('link'); linkEl.setAttribute('rel', 'stylesheet'); linkEl.setAttribute('href', cssLink); return linkEl; } /** * Adds links to the PCS CSS stylesheets to html/head/. * Example: - * + * + * * * @param {Document} document DOM document * @param {string} baseUri the baseUri ending with a slash for the RESTBase API */ function addCssLinks(document, baseUri) { const headEl = document.querySelector('html > head'); if (headEl) { headEl.appendChild(createStylesheetLinkElement(document, `${BASE_URI}data/css/mobile/base`)); + headEl.appendChild(createStylesheetLinkElement(document, + `${BASE_URI}data/css/mobile/pagelib`)); headEl.appendChild(createStylesheetLinkElement(document, `${baseUri}data/css/mobile/site`)); } } /** * Creates a single element setting the viewport for a mobile device. * @param {Document} document DOM document * @return {Element} DOM Element */ function createMetaViewportElement(document) { const el = document.createElement('meta'); el.setAttribute('name', 'viewport'); el.setAttribute('content', 'width=device-width, user-scalable=no'); return el; } /** * Adds the viewport meta element to html/head/ * * @param {Document} document DOM document */ function addMetaViewport(document) { const headEl = document.querySelector('html > head'); if (headEl) { headEl.appendChild(createMetaViewportElement(document)); } } /** * Adds the script element to html/head/ * * @param {Document} document DOM document */ function createScriptElement(document) { const el = document.createElement('script'); el.setAttribute('src', `${BASE_URI}data/javascript/mobile/pagelib`); return el; } /** * Create a script tag with an inline script text for triggering loading of the images * on the client side when the placeholder span gets close to being visible. * @param {Document} document DOM document for creating new elements */ function createInlineScriptElement(document) { const el = document.createElement('script'); const inlineScript = ` const transformer = new pagelib.LazyLoadTransformer(window, 2); transformer.collectExistingPlaceholders(document.body); transformer.loadPlaceholders(); `; const textNode = document.createTextNode(inlineScript); el.appendChild(textNode); return el; } /** * Adds Javascript needed to use and trigger the page library client side functionality. * A reference to the actual JS file bundle from the wikimedia-page-library is added to the head. * A short inline script to trigger the loading of the lazy loaded images since the mobile-html * only contains the placeholders but not the image elements for the bigger images on a page. * @param {Document} document DOM document */ function addPageLibJs(document) { const headEl = document.querySelector('html > head'); if (headEl) { headEl.appendChild(createScriptElement(document)); document.body.appendChild(createInlineScriptElement(document)); } } module.exports = { addCssLinks, addMetaViewport, addPageLibJs }; diff --git a/test/features/mobile-html/pagecontent.js b/test/features/mobile-html/pagecontent.js index 81036de81..9e5dae134 100644 --- a/test/features/mobile-html/pagecontent.js +++ b/test/features/mobile-html/pagecontent.js @@ -1,56 +1,56 @@ 'use strict'; const domino = require('domino'); const preq = require('preq'); const assert = require('../../utils/assert.js'); const headers = require('../../utils/headers.js'); const server = require('../../utils/server.js'); describe('mobile-html', function() { this.timeout(20000); // eslint-disable-line no-invalid-this before(() => server.start()); const localUri = (title, domain = 'en.wikipedia.org') => { return `${server.config.uri}${domain}/v1/page/mobile-html/${title}`; }; it('should respond to GET request with expected headers, incl. CORS and CSP headers', () => { const uri = localUri('Foobar'); return headers.checkHeaders(uri, headers.HTML_CONTENT_TYPE_REGEX); }); it('HTML should be sectioned', () => { const uri = localUri('Foobar/788941783'); return preq.get({ uri }) .then((res) => { const document = domino.createDocument(res.body); assert.selectorExistsNTimes(document, 'section', 7, 'should have 7 sections'); }); }); it('mobile-html should have css links + viewport set', () => { const uri = localUri('Foobar/788941783'); return preq.get({ uri }) .then((res) => { const document = domino.createDocument(res.body); - assert.selectorExistsNTimes(document, 'html > head > link[rel=stylesheet]', 2, - 'should have 2 css files'); + assert.selectorExistsNTimes(document, 'html > head > link[rel=stylesheet]', 3, + 'should have 3 css files'); assert.selectorExistsNTimes(document, 'html > head > meta[name=viewport]', 1, 'should have 1 meta element setting viewport'); }); }); it('mobile-html should have lead paragraph moved up', () => { const uri = localUri('Dog/844680047'); return preq.get({ uri }) .then((res) => { const document = domino.createDocument(res.body); const section0 = document.querySelector('section[data-mw-section-id=0]'); // children[0] is the container span for the edit button. assert.ok(section0.children[1].outerHTML.startsWith(`
The domestic dog`)); }); }); });