Can I Add A Button Or A Link To My Web Page Which Lets Me View The Source Of That Page (like Pre-pending The Url With View-source:)?
In Firefox 78, when visiting view-source:https://example.com/my-page/, it's possible to click on any link in the HTML Source and the link will take you through to view-source:https
Solution 1:
Can I add a button or a link to my web page which lets me view the source of that page?
Yes. It turns out, this is possible with:
- Javascript
- CSS
- a handful of Regular Expressions
N.B. Note that in the example below, the line
constHTMLSourceTab = window.open(window.location.href, '_blank');
does not execute, due to StackSnippet security constraints which prevent execution of window.open()
.
However, the script does work on GitHub Pages.
Example:
const viewHTMLSourceButton = document.getElementsByClassName('viewHTMLSource')[0];
constopenHTMLSource = () => {
constHTMLSourceTab = window.open(window.location.href, '_blank');
let documentDOM = document.documentElement.cloneNode(true);
let documentDOMBody = documentDOM.getElementsByTagName('body')[0];
documentDOMBody.removeAttribute('style');
let viewHTMLSourceButtonHelpers = [...documentDOM.getElementsByClassName('viewHTMLSourceButtonHelper')];
for (helper of viewHTMLSourceButtonHelpers) {helper.remove();}
let documentMarkup = documentDOM.outerHTML;
documentMarkup = documentMarkup.replace(/><head>/g, '>\n<head>');
documentMarkup = documentMarkup.replace(/<\/body><\/html>/g, '</body>\n</html>');
documentMarkup = documentMarkup.replace(/<script>[\s\S]+?<\/scrip.>/g, '');
documentMarkup = documentMarkup.replace(/><script/g, '>\n<script');
documentMarkup = documentMarkup.replace(/<([^>]+?)\n([^>]+?)>/g, '<$1 $2>');
documentMarkup = documentMarkup.split('\n');
for (let i = 0; i < documentMarkup.length; i++) {
documentMarkup[i] = documentMarkup[i].replace(/\</g, '<');
documentMarkup[i] = documentMarkup[i].replace(/\"/g, '"');
documentMarkup[i] = documentMarkup[i].replace(/\>/g, '>');
documentMarkup[i] = documentMarkup[i].replace(/(<\/?)([\w-]+?)(\s|>)/g, '$1<span class="HTMLSourceElementName">$2</span>$3');
documentMarkup[i] = documentMarkup[i].replace(/\="(.+?)"/g, '="<span class="HTMLSourceAttributeValue">$1</span><b>"</b>');
documentMarkup[i] = documentMarkup[i].replace(/([\w-]+)\="/g, '<span class="HTMLSourceAttributeName">$1</span><b>="</b>');
}
let lineCounterWidth;
switch (true) {
case (documentMarkup.length > 9999) : lineCounterWidth = '45'; break;
case (documentMarkup.length > 999) : lineCounterWidth = '36'; break;
case (documentMarkup.length > 99) : lineCounterWidth = '27'; break;
case (documentMarkup.length > 9) : lineCounterWidth = '18'; break;
default : lineCounterWidth = '9';
}
let documentDoctype = '';
documentDoctype += '<li class="HTMLSourceDoctype"><div class="line">';
documentDoctype += '<!DOCTYPE html>';
documentDoctype += '</div></li>';
letHTMLSource = '';
HTMLSource += '<ol class="HTMLSourceList">\n';
HTMLSource += documentDoctype + '\n';
HTMLSource += '<li><div class="line">';
HTMLSource += documentMarkup.join('</div></li>\n<li><div class="line">');
HTMLSource += '</div></li>\n';
HTMLSource += '</ol>';
letHTMLSourceStylesContent = '';
HTMLSourceStylesContent += '.HTMLSource {position: absolute; top: 0; left: 0; z-index: 96; width: 100vw; height: 100vh; padding-bottom: 12px; font-family:monospace; color: rgb(0, 0, 0); background-color: rgb(255, 255, 255); box-sizing: border-box; overflow: auto;}';
HTMLSourceStylesContent += '.HTMLSourceList {list-style-type: none; margin: 8px 0 0; padding-left: 0; counter-reset: line;}';
HTMLSourceStylesContent += '.HTMLSourceList li {position: relative; display: block; clear: both; width: 100%; font-size: 13px; line-height: 16px; white-space: pre-wrap;}';
HTMLSourceStylesContent += '.HTMLSourceList li::before {content: counter(line); display: inline-block; float: left; width: ' + lineCounterWidth + 'px; margin-right: 6px; color: rgb(204, 204, 204); text-align: right; font-style: normal; counter-increment: line;}';
HTMLSourceStylesContent += '.HTMLSourceList li .line {display: inline-block; float: right; width: calc(100% - ' + lineCounterWidth + 'px - 6px);}';
HTMLSourceStylesContent += '.HTMLSourceDoctype {color: rgb(70, 130, 180); font-style: italic;}';
HTMLSourceStylesContent += '.HTMLSourceElementName {color: rgb(128, 0, 128); font-weight: bold;}';
HTMLSourceStylesContent += '.HTMLSourceAttributeName {font-weight: bold;}';
HTMLSourceStylesContent += '.HTMLSourceAttributeValue {color: rgb(0, 0, 255);}';
letHTMLSourceScriptContent = '';
HTMLSourceScriptContent += 'document.body.style.position = "fixed";';
HTMLSourceScriptContent += 'let HTMLSourceStyles = document.createElement("style");';
HTMLSourceScriptContent += 'HTMLSourceStyles.classList.add("viewHTMLSourceButtonHelper");';
HTMLSourceScriptContent += 'HTMLSourceStyles.textContent = `' + HTMLSourceStylesContent + '`;';
HTMLSourceScriptContent += 'document.head.appendChild(HTMLSourceStyles);';
HTMLSourceScriptContent += 'let HTMLSourceMarkup = document.createElement("div");';
HTMLSourceScriptContent += 'HTMLSourceMarkup.classList.add("HTMLSource");';
HTMLSourceScriptContent += 'HTMLSourceMarkup.classList.add("viewHTMLSourceButtonHelper");';
HTMLSourceScriptContent += 'HTMLSourceMarkup.innerHTML = `' + HTMLSource + '`;';
HTMLSourceScriptContent += 'document.body.appendChild(HTMLSourceMarkup);';
letHTMLSourceScript = document.createElement('script');
HTMLSourceScript.classList.add('viewHTMLSourceButtonHelper');
HTMLSourceScript.textContent = HTMLSourceScriptContent;
HTMLSourceTab.addEventListener('DOMContentLoaded', () =>HTMLSourceTab.document.body.appendChild(HTMLSourceScript));
HTMLSourceTab.focus();
};
viewHTMLSourceButton.addEventListener('click', openHTMLSource, false);
hr {
margin: 36px0;
}
<buttontype="button"class="viewHTMLSource">View HTML Source</button><hr /><p><strong>N.B.</strong> Note that in this example, <code>line 26</code>:</p><p><code>const HTMLSourceTab = window.open(window.location.href, '_blank');</code></p><p>does <em>not</em> execute, due to <strong>StackSnippet</strong> security constraints which prevent execution of <code>window.open()</code>.</p><p>See: <ahref="https://meta.stackoverflow.com/questions/337916/why-is-window-open-blocked">https://meta.stackoverflow.com/questions/337916/why-is-window-open-blocked</a></p>
N.B. As mentioned above, the script above doesn't work within the security constraints of StackSnippets
.
However, the script does work on GitHub Pages.
Post a Comment for "Can I Add A Button Or A Link To My Web Page Which Lets Me View The Source Of That Page (like Pre-pending The Url With View-source:)?"