From c3ee841fefe9bb6d1ba30db97a55d70dbf9705f2 Mon Sep 17 00:00:00 2001 From: Jan-Ka Date: Thu, 28 Sep 2017 18:06:28 +0200 Subject: [PATCH 1/9] add .editorconfig for IDE consistency --- .editorconfig | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 .editorconfig diff --git a/.editorconfig b/.editorconfig new file mode 100644 index 0000000..3c94c19 --- /dev/null +++ b/.editorconfig @@ -0,0 +1,9 @@ +root = true + +[*] +indent_style = tab +indent_size = 4 +end_of_line = lf +charset = utf-8 +trim_trailing_whitespace = true +insert_final_newline = false From 0462e0dc608798e67354a6c66e5014b9c732a04e Mon Sep 17 00:00:00 2001 From: Jan-Ka Date: Thu, 28 Sep 2017 19:53:32 +0200 Subject: [PATCH 2/9] code formatting --- primerpedia.js | 28 ++++++++++++++-------------- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/primerpedia.js b/primerpedia.js index a4fc49a..e89f269 100644 --- a/primerpedia.js +++ b/primerpedia.js @@ -22,18 +22,18 @@ var apiUrl = "http://en.wikipedia.org/w/api.php?"; // https://www.mediawiki.org/wiki/Extension:MobileFrontend#prop.3Dextracts var apiExtractsQuery = "action=query&prop=extracts&exintro&indexpageids=true&format=json"; -function random(){ - apiRequest( apiExtractsQuery + "&generator=random&grnnamespace=0" ); +function random() { + apiRequest(apiExtractsQuery + "&generator=random&grnnamespace=0"); } -function search(){ +function search() { searchTerm = $('#search-term')[0].value; if(searchTerm) - apiRequest( apiExtractsQuery + "&generator=search&gsrlimit=1&gsrsearch=" + searchTerm ); + apiRequest(apiExtractsQuery + "&generator=search&gsrlimit=1&gsrsearch=" + searchTerm); else random(); } -function apiRequest(queryString){ +function apiRequest(queryString) { // Loading animation from http://www.ajaxload.info/ $("#content").html("Loading..."); $.ajax({ @@ -42,9 +42,9 @@ function apiRequest(queryString){ format: "json" }, dataType: "jsonp", - success: function(jsonObject){ + success: function (jsonObject) { var searchData = jsonObject.query.searchinfo; - if( typeof searchData === "undefined" || searchData.totalhits > 0 ){ + if(typeof searchData === "undefined" || searchData.totalhits > 0) { var pageid = jsonObject.query.pageids[0]; var article = jsonObject.query.pages[pageid]; article.url = "http://en.wikipedia.org/wiki/" + encodeURIComponent(article.title); @@ -52,11 +52,11 @@ function apiRequest(queryString){ $("#viewlink").text(article.title).attr('href', article.url); $("#editlink").attr('href', editlink); $("#article-title").show(); - $("#content").html( article.extract ); + $("#content").html(article.extract); $("#license-icon").show(); $("#info-icon").show(); - } else if( typeof searchData.suggestion !== "undefined" ){ - apiRequest( apiExtractsQuery + "&generator=search&gsrlimit=1&gsrsearch=" + searchData.suggestion ); + } else if(typeof searchData.suggestion !== "undefined") { + apiRequest(apiExtractsQuery + "&generator=search&gsrlimit=1&gsrsearch=" + searchData.suggestion); } else { $("#content").html("
The search term wasn't found.
"); } @@ -72,10 +72,10 @@ function getQueryVariable(parameter) { // Split each parameter=value pair using '&' as separator var vars = query.split('&'); // Loop over all the parameter=value pairs, and split them into their parameter/value components - for (var i = 0; i < vars.length; i++) { + for(var i = 0; i < vars.length; i++) { var pair = vars[i].split('='); // If one of the parameter names is the one we're looking for, return its value - if (decodeURIComponent(pair[0]) == parameter) { + if(decodeURIComponent(pair[0]) == parameter) { return decodeURIComponent(pair[1]); } } @@ -83,8 +83,8 @@ function getQueryVariable(parameter) { } // Upon loading the page, check if an URL parameter was passed, and use it to perform a search -$(document).ready(function() { - if (getQueryVariable("search")) { +$(document).ready(function () { + if(getQueryVariable("search")) { document.getElementById('search-term').value = getQueryVariable("search"); search(); } From 8bd20ca432fb8e0d6c40778245ce3971314a92a9 Mon Sep 17 00:00:00 2001 From: Jan-Ka Date: Thu, 28 Sep 2017 19:55:26 +0200 Subject: [PATCH 3/9] replaced apiRequest with native jsonp implementation --- primerpedia.js | 74 ++++++++++++++++++++++++++++++++------------------ 1 file changed, 48 insertions(+), 26 deletions(-) diff --git a/primerpedia.js b/primerpedia.js index e89f269..d41e0a9 100644 --- a/primerpedia.js +++ b/primerpedia.js @@ -21,6 +21,8 @@ var apiUrl = "http://en.wikipedia.org/w/api.php?"; // https://www.mediawiki.org/wiki/Extension:MobileFrontend#prop.3Dextracts var apiExtractsQuery = "action=query&prop=extracts&exintro&indexpageids=true&format=json"; +var requestTimeoutInMs = 3000; +var requestCallbackName = "requestCallback"; function random() { apiRequest(apiExtractsQuery + "&generator=random&grnnamespace=0"); @@ -36,32 +38,52 @@ function search() { function apiRequest(queryString) { // Loading animation from http://www.ajaxload.info/ $("#content").html("Loading..."); - $.ajax({ - url: apiUrl + queryString, - data: { - format: "json" - }, - dataType: "jsonp", - success: function (jsonObject) { - var searchData = jsonObject.query.searchinfo; - if(typeof searchData === "undefined" || searchData.totalhits > 0) { - var pageid = jsonObject.query.pageids[0]; - var article = jsonObject.query.pages[pageid]; - article.url = "http://en.wikipedia.org/wiki/" + encodeURIComponent(article.title); - var editlink = article.url + "?action=edit&section=0"; - $("#viewlink").text(article.title).attr('href', article.url); - $("#editlink").attr('href', editlink); - $("#article-title").show(); - $("#content").html(article.extract); - $("#license-icon").show(); - $("#info-icon").show(); - } else if(typeof searchData.suggestion !== "undefined") { - apiRequest(apiExtractsQuery + "&generator=search&gsrlimit=1&gsrsearch=" + searchData.suggestion); - } else { - $("#content").html("
The search term wasn't found.
"); - } - } - }); + + var script = document.createElement("script"); + script.type = "text/javascript"; + script.async = true; + script.src = apiUrl + queryString + "&callback=" + requestCallbackName; + + document.getElementsByTagName("head")[0].appendChild(script); + + var onCompleted = function () { + // reduce global namespace pollution + delete (window[requestCallbackName]); + // remove jsonp result tag + script.remove(); + } + + var requestTimeout = window.setTimeout(function () { + onCompleted(); + }, requestTimeoutInMs); + + window[requestCallbackName] = function (jsonObject) { + window.clearTimeout(requestTimeout); + + handleRequestResult(jsonObject); + + onCompleted(); + } +} + +function handleRequestResult(jsonObject) { + var searchData = jsonObject.query.searchinfo; + if(typeof searchData === "undefined" || searchData.totalhits > 0) { + var pageid = jsonObject.query.pageids[0]; + var article = jsonObject.query.pages[pageid]; + article.url = "http://en.wikipedia.org/wiki/" + encodeURIComponent(article.title); + var editlink = article.url + "?action=edit&section=0"; + $("#viewlink").text(article.title).attr('href', article.url); + $("#editlink").attr('href', editlink); + $("#article-title").show(); + $("#content").html(article.extract); + $("#license-icon").show(); + $("#info-icon").show(); + } else if(typeof searchData.suggestion !== "undefined") { + apiRequest(apiExtractsQuery + "&generator=search&gsrlimit=1&gsrsearch=" + searchData.suggestion); + } else { + $("#content").html("
The search term wasn't found.
"); + } } // Get query string from URL parameter From 959dca9b199fe634ad69b9b223acbb927ec5d79c Mon Sep 17 00:00:00 2001 From: Jan-Ka Date: Thu, 28 Sep 2017 20:17:26 +0200 Subject: [PATCH 4/9] replaced most of the jQuery in handleRequestResult with native js --- primerpedia.js | 34 +++++++++++++++++++++++++++------- 1 file changed, 27 insertions(+), 7 deletions(-) diff --git a/primerpedia.js b/primerpedia.js index d41e0a9..9684e5b 100644 --- a/primerpedia.js +++ b/primerpedia.js @@ -66,23 +66,43 @@ function apiRequest(queryString) { } } +function toggleVisibility(element, visibility) { + if(element instanceof HTMLElement) { + if(!visibility) { + element.style.setProperty("display", "none"); + } else { + element.style.removeProperty("display"); + } + } +} + function handleRequestResult(jsonObject) { var searchData = jsonObject.query.searchinfo; + //TODO: fix wrong undefined check if(typeof searchData === "undefined" || searchData.totalhits > 0) { var pageid = jsonObject.query.pageids[0]; var article = jsonObject.query.pages[pageid]; article.url = "http://en.wikipedia.org/wiki/" + encodeURIComponent(article.title); var editlink = article.url + "?action=edit&section=0"; - $("#viewlink").text(article.title).attr('href', article.url); - $("#editlink").attr('href', editlink); - $("#article-title").show(); - $("#content").html(article.extract); - $("#license-icon").show(); - $("#info-icon").show(); + + var viewLinkElem = document.getElementById("viewlink"); + + viewLinkElem.textContent = article.title; + viewLinkElem.setAttribute("href", article.url); + + document.getElementById("editlink").setAttribute("href", editlink); + toggleVisibility(document.getElementById("article-title"), true); + document.getElementById("content").innerHTML = article.extract; + toggleVisibility(document.getElementById("license-icon"), true); + toggleVisibility(document.getElementById("info-icon"), true); } else if(typeof searchData.suggestion !== "undefined") { apiRequest(apiExtractsQuery + "&generator=search&gsrlimit=1&gsrsearch=" + searchData.suggestion); } else { - $("#content").html("
The search term wasn't found.
"); + var notFoundNode = document.createElement("div"); + notFoundNode.classList.add("error"); + notFoundNode.textContent = "The search term wasn't found."; + + document.getElementById("content").appendChild(notFoundNode); } } From 73d6ecc8b5eb49438881cd1b7e4088a7ff328450 Mon Sep 17 00:00:00 2001 From: Jan-Ka Date: Thu, 28 Sep 2017 20:37:31 +0200 Subject: [PATCH 5/9] fixed handleRequestResult throwing exception when no result is returned moved content rendering in dedicated functions --- primerpedia.js | 82 ++++++++++++++++++++++++++++++++++---------------- 1 file changed, 56 insertions(+), 26 deletions(-) diff --git a/primerpedia.js b/primerpedia.js index 9684e5b..1ce0dd3 100644 --- a/primerpedia.js +++ b/primerpedia.js @@ -76,34 +76,64 @@ function toggleVisibility(element, visibility) { } } +function clearNode(node) { + var clone = node.cloneNode(false); + node.parentNode.replaceChild(clone, node); + + return clone; +} + +function renderSearchResult(jsonObject) { + var pageid = jsonObject.query.pageids[0]; + var article = jsonObject.query.pages[pageid]; + article.url = "http://en.wikipedia.org/wiki/" + encodeURIComponent(article.title); + var editlink = article.url + "?action=edit&section=0"; + + var viewLinkElem = document.getElementById("viewlink"); + + viewLinkElem.textContent = article.title; + viewLinkElem.setAttribute("href", article.url); + + document.getElementById("editlink").setAttribute("href", editlink); + toggleVisibility(document.getElementById("article-title"), true); + + var contentNode = document.getElementById("content"); + + contentNode = clearNode(contentNode); + contentNode.innerHTML = article.extract; + + toggleVisibility(document.getElementById("license-icon"), true); + toggleVisibility(document.getElementById("info-icon"), true); +} + +function renderNotFoundNode() { + var notFoundNode = document.createElement("div"); + notFoundNode.classList.add("error"); + notFoundNode.textContent = "The search term wasn't found."; + + var contentNode = document.getElementById("content"); + + contentNode = clearNode(contentNode); + + contentNode.appendChild(notFoundNode); +} + function handleRequestResult(jsonObject) { - var searchData = jsonObject.query.searchinfo; - //TODO: fix wrong undefined check - if(typeof searchData === "undefined" || searchData.totalhits > 0) { - var pageid = jsonObject.query.pageids[0]; - var article = jsonObject.query.pages[pageid]; - article.url = "http://en.wikipedia.org/wiki/" + encodeURIComponent(article.title); - var editlink = article.url + "?action=edit&section=0"; - - var viewLinkElem = document.getElementById("viewlink"); - - viewLinkElem.textContent = article.title; - viewLinkElem.setAttribute("href", article.url); - - document.getElementById("editlink").setAttribute("href", editlink); - toggleVisibility(document.getElementById("article-title"), true); - document.getElementById("content").innerHTML = article.extract; - toggleVisibility(document.getElementById("license-icon"), true); - toggleVisibility(document.getElementById("info-icon"), true); - } else if(typeof searchData.suggestion !== "undefined") { - apiRequest(apiExtractsQuery + "&generator=search&gsrlimit=1&gsrsearch=" + searchData.suggestion); - } else { - var notFoundNode = document.createElement("div"); - notFoundNode.classList.add("error"); - notFoundNode.textContent = "The search term wasn't found."; - - document.getElementById("content").appendChild(notFoundNode); + if(jsonObject.hasOwnProperty("query")) { + var searchData = jsonObject.query.searchinfo; + + if(typeof searchData === "undefined" || searchData.totalhits > 0) { + renderSearchResult(jsonObject); + + return; + } else if(typeof searchData.suggestion !== "undefined") { + apiRequest(apiExtractsQuery + "&generator=search&gsrlimit=1&gsrsearch=" + searchData.suggestion); + + return; + } } + + renderNotFoundNode(); } // Get query string from URL parameter From ab22638dcfec768d470e457a5d0cea74333a924c Mon Sep 17 00:00:00 2001 From: Jan-Ka Date: Thu, 28 Sep 2017 20:39:59 +0200 Subject: [PATCH 6/9] fixed title, license-icon and info-icon not hidden on no result --- primerpedia.js | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/primerpedia.js b/primerpedia.js index 1ce0dd3..9fa8b0d 100644 --- a/primerpedia.js +++ b/primerpedia.js @@ -107,6 +107,10 @@ function renderSearchResult(jsonObject) { } function renderNotFoundNode() { + toggleVisibility(document.getElementById("article-title"), false); + toggleVisibility(document.getElementById("license-icon"), false); + toggleVisibility(document.getElementById("info-icon"), false); + var notFoundNode = document.createElement("div"); notFoundNode.classList.add("error"); notFoundNode.textContent = "The search term wasn't found."; From 42cb953bb6fe45bef151bf49be95bf84591e7941 Mon Sep 17 00:00:00 2001 From: Jan-Ka Date: Thu, 28 Sep 2017 20:44:48 +0200 Subject: [PATCH 7/9] replaced document.ready with native window.onload --- index.html | 2 +- primerpedia.js | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/index.html b/index.html index 0f48f6e..553c3a9 100644 --- a/index.html +++ b/index.html @@ -8,7 +8,6 @@ - @@ -64,5 +63,6 @@