MediaWiki:Common.js: Difference between revisions

From GDPRhub
(Add scripts for loading “New on GDPRhub” previews, and for loading a random banner)
 
(Finish code for putting random banner above pages)
Line 2: Line 2:


/* Show random banner (see MediaWiki:Sitenotice, and MediaWiki:Common.css) */
/* Show random banner (see MediaWiki:Sitenotice, and MediaWiki:Common.css) */
var randomContainer = document.querySelector('.show-random-element');
var randomBannerContainers = Array.from(document.querySelectorAll('.random-banner-container'));
if (randomContainer) {
randomBannerContainers.forEach(function (randomBannerContainer) {
var elements = randomContainer.children;
var elements = randomBannerContainer.querySelectorAll('.random-banner-option');
var index = Math.floor(Math.random() * elements.length);
if (elements.length === 0) {
randomContainer.replaceChildren(elements[index]);
randomBannerContainer.replaceChildren(); // remove any children
randomContainer.classList.add('ready');
} else {
}
var index = Math.floor(Math.random() * elements.length);
 
randomBannerContainer.replaceChildren(elements[index]);
}
randomBannerContainer.classList.add('ready');
});


/* “New on GDPRhub” list on main page
/* “New on GDPRhub” list on main page

Revision as of 20:14, 29 June 2021

/* Any JavaScript here will be loaded for all users on every page load. */

/* Show random banner (see MediaWiki:Sitenotice, and MediaWiki:Common.css) */
var randomBannerContainers = Array.from(document.querySelectorAll('.random-banner-container'));
randomBannerContainers.forEach(function (randomBannerContainer) {
	var elements = randomBannerContainer.querySelectorAll('.random-banner-option');
	if (elements.length === 0) {
		randomBannerContainer.replaceChildren(); // remove any children
	} else {
		var index = Math.floor(Math.random() * elements.length);
		randomBannerContainer.replaceChildren(elements[index]);
	}
	randomBannerContainer.classList.add('ready');
});

/* “New on GDPRhub” list on main page
 Functionality defined by multiple pieces: 
 - the NewPages extension
 - MediaWiki:Common.js to load the content to preview
	- relies on OpenGraphMeta+Description2 extensions to provide those contents
 - MediaWiki:Common.css to style the items as cards
*/
var newOnGdprHubContainer = document.getElementById('new-on-gdprhub');
if (newOnGdprHubContainer) loadNewOnGdprHubItems(); // only on the main page
function loadNewOnGdprHubItems() {
	items = Array.from(newOnGdprHubContainer.querySelectorAll('li a'));
	var parser = new DOMParser();
	var promises = items.map(function (item) {
		var pageTitle = item.textContent;
		updateContent(item, {
			title: pageTitle,
		});
		item.classList.add('preview-loading');
		var pageUrl = '/index.php?title=' + encodeURIComponent(pageTitle);
		return fetch(pageUrl)
			.then(function (response) {
				if (!response.ok) throw new Error('fetch got ' + response.status);
				return response.text();
			}).then(function (html) {
				// Cut off html source to only parse content of each page’s <head>
				html = html.slice(0, html.indexOf('</head>'));
				var dom = parser.parseFromString(html, 'text/html');

				var props = getOpenGraphData(dom, ['title', 'description', 'image']);
				props.title = pageTitle; // overwrite title to keep title of redirects
				updateContent(item, props);
				item.classList.add('preview-loaded');
				item.classList.add('preview-loading');
			}).catch(function (error) {
				console.log('Failed to load page preview for "' + pageTitle + '": ' + error);
				updateContent(item, {
					title: pageTitle,
					description: '',
				});
			});
	});
	return Promise.all(promises);

	function updateContent(item, props) {
		item.innerHTML =
			'<div class="card-text">'
				+ (props.title ? '<h4 class="card-title">' + props.title + '</h4>' : '')
				+ (props.description ? '<p class="card-description">' + props.description + '</p>' : '')
			+ '</div>'
			+ '<div class="card-image">'
				+ (props.image ? '<img src="' + props.image + '"/>' : '')
			+ '</div>'
		;
	}

	function getOpenGraphData(dom, propertyNames) {
		var ns = 'og'; // techinaclly we should read this from an xmlns attribute.
		var props = {};
	    propertyNames.forEach(function (name) {
	    	var el = dom.head.querySelector('meta[property="' + ns + ':' + name + '"]');
	    	if (el) props[name] = el.content;
	    });
	    return props;
	}
}