Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(162)

Unified Diff: pkg/html_import/lib/src/HTMLImports.js

Issue 158083002: introduce web_components pkg for consolidated polyfills (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Created 6 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: pkg/html_import/lib/src/HTMLImports.js
diff --git a/pkg/html_import/lib/src/HTMLImports.js b/pkg/html_import/lib/src/HTMLImports.js
deleted file mode 100644
index a77e7165e762204c44d3b7fa8cd4b8af8e325c26..0000000000000000000000000000000000000000
--- a/pkg/html_import/lib/src/HTMLImports.js
+++ /dev/null
@@ -1,423 +0,0 @@
-/*
- * Copyright 2013 The Polymer Authors. All rights reserved.
- * Use of this source code is governed by a BSD-style
- * license that can be found in the LICENSE file.
- */
-
-(function(scope) {
-
-if (!scope) {
- scope = window.HTMLImports = {flags:{}};
-}
-
-// imports
-
-var xhr = scope.xhr;
-
-// importer
-
-var IMPORT_LINK_TYPE = 'import';
-var STYLE_LINK_TYPE = 'stylesheet';
-
-// highlander object represents a primary document (the argument to 'load')
-// at the root of a tree of documents
-
-// for any document, importer:
-// - loads any linked documents (with deduping), modifies paths and feeds them back into importer
-// - loads text of external script tags
-// - loads text of external style tags inside of <element>, modifies paths
-
-// when importer 'modifies paths' in a document, this includes
-// - href/src/action in node attributes
-// - paths in inline stylesheets
-// - all content inside templates
-
-// linked style sheets in an import have their own path fixed up when their containing import modifies paths
-// linked style sheets in an <element> are loaded, and the content gets path fixups
-// inline style sheets get path fixups when their containing import modifies paths
-
-var loader;
-
-var importer = {
- documents: {},
- cache: {},
- preloadSelectors: [
- 'link[rel=' + IMPORT_LINK_TYPE + ']',
- 'element link[rel=' + STYLE_LINK_TYPE + ']',
- 'template',
- 'script[src]:not([type])',
- 'script[src][type="text/javascript"]'
- ].join(','),
- loader: function(inNext) {
- // construct a loader instance
- loader = new Loader(importer.loaded, inNext);
- // alias the loader cache (for debugging)
- loader.cache = importer.cache;
- return loader;
- },
- load: function(inDocument, inNext) {
- // construct a loader instance
- loader = importer.loader(inNext);
- // add nodes from document into loader queue
- importer.preload(inDocument);
- },
- preload: function(inDocument) {
- // all preloadable nodes in inDocument
- var nodes = inDocument.querySelectorAll(importer.preloadSelectors);
- // from the main document, only load imports
- // TODO(sjmiles): do this by altering the selector list instead
- nodes = this.filterMainDocumentNodes(inDocument, nodes);
- // extra link nodes from templates, filter templates out of the nodes list
- nodes = this.extractTemplateNodes(nodes);
- // add these nodes to loader's queue
- loader.addNodes(nodes);
- },
- filterMainDocumentNodes: function(inDocument, nodes) {
- if (inDocument === document) {
- nodes = Array.prototype.filter.call(nodes, function(n) {
- return !isScript(n);
- });
- }
- return nodes;
- },
- extractTemplateNodes: function(nodes) {
- var extra = [];
- nodes = Array.prototype.filter.call(nodes, function(n) {
- if (n.localName === 'template') {
- if (n.content) {
- var l$ = n.content.querySelectorAll('link[rel=' + STYLE_LINK_TYPE +
- ']');
- if (l$.length) {
- extra = extra.concat(Array.prototype.slice.call(l$, 0));
- }
- }
- return false;
- }
- return true;
- });
- if (extra.length) {
- nodes = nodes.concat(extra);
- }
- return nodes;
- },
- loaded: function(url, elt, resource) {
- if (isDocumentLink(elt)) {
- var document = importer.documents[url];
- // if we've never seen a document at this url
- if (!document) {
- // generate an HTMLDocument from data
- document = makeDocument(resource, url);
- // resolve resource paths relative to host document
- path.resolvePathsInHTML(document);
- // cache document
- importer.documents[url] = document;
- // add nodes from this document to the loader queue
- importer.preload(document);
- }
- // store import record
- elt.import = {
- href: url,
- ownerNode: elt,
- content: document
- };
- // store document resource
- elt.content = resource = document;
- }
- // store generic resource
- // TODO(sorvell): fails for nodes inside <template>.content
- // see https://code.google.com/p/chromium/issues/detail?id=249381.
- elt.__resource = resource;
- // css path fixups
- if (isStylesheetLink(elt)) {
- path.resolvePathsInStylesheet(elt);
- }
- }
-};
-
-function isDocumentLink(elt) {
- return isLinkRel(elt, IMPORT_LINK_TYPE);
-}
-
-function isStylesheetLink(elt) {
- return isLinkRel(elt, STYLE_LINK_TYPE);
-}
-
-function isLinkRel(elt, rel) {
- return elt.localName === 'link' && elt.getAttribute('rel') === rel;
-}
-
-function isScript(elt) {
- return elt.localName === 'script';
-}
-
-function makeDocument(resource, url) {
- // create a new HTML document
- var doc = resource;
- if (!(doc instanceof Document)) {
- doc = document.implementation.createHTMLDocument(IMPORT_LINK_TYPE);
- // install html
- doc.body.innerHTML = resource;
- }
- // cache the new document's source url
- doc._URL = url;
- // establish a relative path via <base>
- var base = doc.createElement('base');
- base.setAttribute('href', document.baseURI);
- doc.head.appendChild(base);
- // TODO(sorvell): MDV Polyfill intrusion: boostrap template polyfill
- if (window.HTMLTemplateElement && HTMLTemplateElement.bootstrap) {
- HTMLTemplateElement.bootstrap(doc);
- }
- return doc;
-}
-
-var Loader = function(inOnLoad, inOnComplete) {
- this.onload = inOnLoad;
- this.oncomplete = inOnComplete;
- this.inflight = 0;
- this.pending = {};
- this.cache = {};
-};
-
-Loader.prototype = {
- addNodes: function(inNodes) {
- // number of transactions to complete
- this.inflight += inNodes.length;
- // commence transactions
- forEach(inNodes, this.require, this);
- // anything to do?
- this.checkDone();
- },
- require: function(inElt) {
- var url = path.nodeUrl(inElt);
- // TODO(sjmiles): ad-hoc
- inElt.__nodeUrl = url;
- // deduplication
- if (!this.dedupe(url, inElt)) {
- // fetch this resource
- this.fetch(url, inElt);
- }
- },
- dedupe: function(inUrl, inElt) {
- if (this.pending[inUrl]) {
- // add to list of nodes waiting for inUrl
- this.pending[inUrl].push(inElt);
- // don't need fetch
- return true;
- }
- if (this.cache[inUrl]) {
- // complete load using cache data
- this.onload(inUrl, inElt, loader.cache[inUrl]);
- // finished this transaction
- this.tail();
- // don't need fetch
- return true;
- }
- // first node waiting for inUrl
- this.pending[inUrl] = [inElt];
- // need fetch (not a dupe)
- return false;
- },
- fetch: function(url, elt) {
- var receiveXhr = function(err, resource) {
- this.receive(url, elt, err, resource);
- }.bind(this);
- xhr.load(url, receiveXhr);
- // TODO(sorvell): blocked on
- // https://code.google.com/p/chromium/issues/detail?id=257221
- // xhr'ing for a document makes scripts in imports runnable; otherwise
- // they are not; however, it requires that we have doctype=html in
- // the import which is unacceptable. This is only needed on Chrome
- // to avoid the bug above.
- /*
- if (isDocumentLink(elt)) {
- xhr.loadDocument(url, receiveXhr);
- } else {
- xhr.load(url, receiveXhr);
- }
- */
- },
- receive: function(inUrl, inElt, inErr, inResource) {
- if (!inErr) {
- loader.cache[inUrl] = inResource;
- }
- loader.pending[inUrl].forEach(function(e) {
- if (!inErr) {
- this.onload(inUrl, e, inResource);
- }
- this.tail();
- }, this);
- loader.pending[inUrl] = null;
- },
- tail: function() {
- --this.inflight;
- this.checkDone();
- },
- checkDone: function() {
- if (!this.inflight) {
- this.oncomplete();
- }
- }
-};
-
-var URL_ATTRS = ['href', 'src', 'action'];
-var URL_ATTRS_SELECTOR = '[' + URL_ATTRS.join('],[') + ']';
-var URL_TEMPLATE_SEARCH = '{{.*}}';
-
-var path = {
- nodeUrl: function(inNode) {
- return path.resolveUrl(path.getDocumentUrl(document), path.hrefOrSrc(inNode));
- },
- hrefOrSrc: function(inNode) {
- return inNode.getAttribute("href") || inNode.getAttribute("src");
- },
- documentUrlFromNode: function(inNode) {
- return path.getDocumentUrl(inNode.ownerDocument || inNode);
- },
- getDocumentUrl: function(inDocument) {
- var url = inDocument &&
- // TODO(sjmiles): ShadowDOMPolyfill intrusion
- (inDocument._URL || (inDocument.impl && inDocument.impl._URL)
- || inDocument.baseURI || inDocument.URL)
- || '';
- // take only the left side if there is a #
- return url.split('#')[0];
- },
- resolveUrl: function(inBaseUrl, inUrl, inRelativeToDocument) {
- if (this.isAbsUrl(inUrl)) {
- return inUrl;
- }
- var url = this.compressUrl(this.urlToPath(inBaseUrl) + inUrl);
- if (inRelativeToDocument) {
- url = path.makeRelPath(path.getDocumentUrl(document), url);
- }
- return url;
- },
- isAbsUrl: function(inUrl) {
- return /(^data:)|(^http[s]?:)|(^\/)/.test(inUrl);
- },
- urlToPath: function(inBaseUrl) {
- var parts = inBaseUrl.split("/");
- parts.pop();
- parts.push('');
- return parts.join("/");
- },
- compressUrl: function(inUrl) {
- var parts = inUrl.split("/");
- for (var i=0, p; i<parts.length; i++) {
- p = parts[i];
- if (p === "..") {
- parts.splice(i-1, 2);
- i -= 2;
- }
- }
- return parts.join("/");
- },
- // make a relative path from source to target
- makeRelPath: function(inSource, inTarget) {
- var s, t;
- s = this.compressUrl(inSource).split("/");
- t = this.compressUrl(inTarget).split("/");
- while (s.length && s[0] === t[0]){
- s.shift();
- t.shift();
- }
- for(var i = 0, l = s.length-1; i < l; i++) {
- t.unshift("..");
- }
- var r = t.join("/");
- return r;
- },
- resolvePathsInHTML: function(root, url) {
- url = url || path.documentUrlFromNode(root)
- path.resolveAttributes(root, url);
- path.resolveStyleElts(root, url);
- // handle template.content
- var templates = root.querySelectorAll('template');
- if (templates) {
- forEach(templates, function(t) {
- if (t.content) {
- path.resolvePathsInHTML(t.content, url);
- }
- });
- }
- },
- resolvePathsInStylesheet: function(inSheet) {
- var docUrl = path.nodeUrl(inSheet);
- inSheet.__resource = path.resolveCssText(inSheet.__resource, docUrl);
- },
- resolveStyleElts: function(inRoot, inUrl) {
- var styles = inRoot.querySelectorAll('style');
- if (styles) {
- forEach(styles, function(style) {
- style.textContent = path.resolveCssText(style.textContent, inUrl);
- });
- }
- },
- resolveCssText: function(inCssText, inBaseUrl) {
- return inCssText.replace(/url\([^)]*\)/g, function(inMatch) {
- // find the url path, ignore quotes in url string
- var urlPath = inMatch.replace(/["']/g, "").slice(4, -1);
- urlPath = path.resolveUrl(inBaseUrl, urlPath, true);
- return "url(" + urlPath + ")";
- });
- },
- resolveAttributes: function(inRoot, inUrl) {
- // search for attributes that host urls
- var nodes = inRoot && inRoot.querySelectorAll(URL_ATTRS_SELECTOR);
- if (nodes) {
- forEach(nodes, function(n) {
- this.resolveNodeAttributes(n, inUrl);
- }, this);
- }
- },
- resolveNodeAttributes: function(inNode, inUrl) {
- URL_ATTRS.forEach(function(v) {
- var attr = inNode.attributes[v];
- if (attr && attr.value &&
- (attr.value.search(URL_TEMPLATE_SEARCH) < 0)) {
- var urlPath = path.resolveUrl(inUrl, attr.value, true);
- attr.value = urlPath;
- }
- });
- }
-};
-
-xhr = xhr || {
- async: true,
- ok: function(inRequest) {
- return (inRequest.status >= 200 && inRequest.status < 300)
- || (inRequest.status === 304)
- || (inRequest.status === 0);
- },
- load: function(url, next, nextContext) {
- var request = new XMLHttpRequest();
- if (scope.flags.debug || scope.flags.bust) {
- url += '?' + Math.random();
- }
- request.open('GET', url, xhr.async);
- request.addEventListener('readystatechange', function(e) {
- if (request.readyState === 4) {
- next.call(nextContext, !xhr.ok(request) && request,
- request.response, url);
- }
- });
- request.send();
- return request;
- },
- loadDocument: function(url, next, nextContext) {
- this.load(url, next, nextContext).responseType = 'document';
- }
-};
-
-var forEach = Array.prototype.forEach.call.bind(Array.prototype.forEach);
-
-// exports
-
-scope.path = path;
-scope.xhr = xhr;
-scope.importer = importer;
-scope.getDocumentUrl = path.getDocumentUrl;
-scope.IMPORT_LINK_TYPE = IMPORT_LINK_TYPE;
-
-})(window.HTMLImports);

Powered by Google App Engine
This is Rietveld 408576698