As the title reads, I want to import an HTML-file as external CSS to a website. Just hear me out: my problem is that I'm working with a very inconvenient CMS that doesn't let me upload CSS-files no matter what.
I'm able to write CSS inside the page directly via HTML-style-tag but that generates a lot of text on every site and also makes maintaining CSS tedious.
As I can't upload CSS-files, I thought maybe I can create a dummy-site inside the CMS with only CSS in it and then later import that site as CSS. The idea was: when parsed, the HTML of the site (header, body, etc.) will just be skipped (as when CSS has i.e. type-errors) while any valid CSS found is going to be imported.
Now when I try importing this website with
<style type="text/css"> @import url(dummyCSSWebsiteURL); </style>
(as the CMS also doesn't grant me access to the header of a page), I - of course - get the error:
"Resource interpreted as Stylesheet but transferred with MIME type text/html"
as I am obviously requesting an HTML-file and not CSS.
I also tried jQuery to simply include all the dummy-HTML into an element (that I would have just not displayed):
$("#cssDummy").load(dummyCSSWebsiteURL);
but I get 2 errors that are probably just showing what a horribly inefficient idea this is:
Synchronous XMLHttpRequest on the main thread is deprecated because of its detrimental effects to the end user's experience
A parser-blocking, cross site (i.e. different eTLD+1) script, ["..."], is invoked via document.write. The network request for this script MAY be blocked by the browser in this or a future page load due to poor network connectivity. If blocked in this page load, it will be confirmed in a subsequent console message.
maybe I am just disregarding (or not understanding) things on a conceptual level at all but I still wonder if there is a workaround for this problem?
EDIT: I found a workaround
Definitely don't recommend. Try using different server as pointed out in the comments if you can. I used an XMLHttpRequest to get the external site's HTML, then used regEx to match the content of the div on the page that contains the css and - with added style-tags - inserted the matched css into a div on the page.
Code for external site that contains the CSS:
<div id="generalCode">.testBox{background-color: red; min-height: 200px;}</div>
Code on site that imports the external CSS:
<div class="testBox">
</div>
<div id="cssCodeOnPage">
</div>
<script>
// use onload if you want
getCssCode();
function getCssCode(){
// send request to page where div #generalCode contains css
var xhr = new XMLHttpRequest();
xhr.open('GET', dummyCSSWebsiteURL);
xhr.onload = function(){
// use regex to separate css from rest of html
var re = /<div id="generalCode">([\s\S]*?)<\/div>/;
var cssString = xhr.response.match(re)[1];
cssString = "<style>" + cssString +"</style>";
// insert css into div
var cssDivOnPage = document.getElementById('cssCodeOnPage');
cssDivOnPage.innerHTML = cssString;
}
xhr.send();
}
(sorry for this monstrosity of a question..)
I think the best option is to load that HTML page into an iframe, query the styles out of hte iframe, and then attach that to the current document. I created a live example on Glitch here.
Nothing but the <style>
block will be copied from the HTML. The external HTML document does need to be an actual HTML document though (<html><head><style>....
), otherwise the page won't be queryable to retrieve the CSS.
This is an example in plain JavaScript:
// Create an iframe
const iframe = document.createElement("iframe");
// Make it not visible
iframe.style.visibility = "hidden";
// This will run once the HTML page has loaded in the <iframe>
iframe.onload = () => {
// Find the <style> element in the HTML document
const style = iframe.contentDocument.querySelector("style");
// Take that <style> element and append it to the current document's <head>
document.querySelector("head").appendChild(style);
// Remove the <iframe> after we are done.
iframe.parentElement.removeChild(iframe);
};
// Setting a source starts the loading process
iframe.src = "css.html";
// The <iframe> doesn't actually load until it is appended to a document
document.querySelector("body").appendChild(iframe);