Bug 1260510 - Fix style editor when inline style tag has a data-uri sourcemap. r=pbro draft
authorNicolas Chevobbe <chevobbe.nicolas@gmail.com>
Wed, 30 Mar 2016 22:23:49 +0200
changeset 348357 2e0692e7e258
parent 347695 71d3427c6831
child 517848 a2ae07334537
push id14824
push userchevobbe.nicolas@gmail.com
push dateThu, 07 Apr 2016 11:53:10 +0000
reviewerspbro
bugs1260510
milestone48.0a1
Bug 1260510 - Fix style editor when inline style tag has a data-uri sourcemap. r=pbro MozReview-Commit-ID: HqBO04sIgYO
devtools/client/styleeditor/StyleEditorUI.jsm
devtools/client/styleeditor/StyleSheetEditor.jsm
devtools/client/styleeditor/test/browser.ini
devtools/client/styleeditor/test/browser_styleeditor_sourcemaps_inline.js
devtools/client/styleeditor/test/sourcemaps-inline.html
--- a/devtools/client/styleeditor/StyleEditorUI.jsm
+++ b/devtools/client/styleeditor/StyleEditorUI.jsm
@@ -798,17 +798,18 @@ StyleEditorUI.prototype = {
    */
   _updateSummaryForEditor: function(editor, summary) {
     summary = summary || editor.summary;
     if (!summary) {
       return;
     }
 
     let ruleCount = editor.styleSheet.ruleCount;
-    if (editor.styleSheet.relatedStyleSheet && editor.linkedCSSFile) {
+    if (editor.styleSheet.relatedStyleSheet
+      && editor.styleSheet.relatedStyleSheet.ruleCount) {
       ruleCount = editor.styleSheet.relatedStyleSheet.ruleCount;
     }
     if (ruleCount === undefined) {
       ruleCount = "-";
     }
 
     let flags = [];
     if (editor.styleSheet.disabled) {
@@ -823,21 +824,23 @@ StyleEditorUI.prototype = {
     this._view.setItemClassName(summary, flags.join(" "));
 
     let label = summary.querySelector(".stylesheet-name > label");
     label.setAttribute("value", editor.friendlyName);
     if (editor.styleSheet.href) {
       label.setAttribute("tooltiptext", editor.styleSheet.href);
     }
 
-    let linkedCSSFile = "";
+    let linkedCSSSource = "";
     if (editor.linkedCSSFile) {
-      linkedCSSFile = OS.Path.basename(editor.linkedCSSFile);
+      linkedCSSSource = OS.Path.basename(editor.linkedCSSFile);
+    } else if (editor.styleSheet.relatedStyleSheet) {
+      linkedCSSSource = editor.styleSheet.relatedStyleSheet.title || "";
     }
-    text(summary, ".stylesheet-linked-file", linkedCSSFile);
+    text(summary, ".stylesheet-linked-file", linkedCSSSource);
     text(summary, ".stylesheet-title", editor.styleSheet.title || "");
     text(summary, ".stylesheet-rule-count",
       PluralForm.get(ruleCount,
                      getString("ruleCount.label")).replace("#1", ruleCount));
   },
 
   /**
    * Update the @media rules sidebar for an editor. Hide if there are no rules
--- a/devtools/client/styleeditor/StyleSheetEditor.jsm
+++ b/devtools/client/styleeditor/StyleSheetEditor.jsm
@@ -217,16 +217,19 @@ StyleSheetEditor.prototype = {
    * If this is an original source, get the path of the CSS file it generated.
    */
   linkCSSFile: function() {
     if (!this.styleSheet.isOriginalSource) {
       return;
     }
 
     let relatedSheet = this.styleSheet.relatedStyleSheet;
+    if (!relatedSheet || !relatedSheet.href) {
+      return;
+    }
 
     let path;
     let href = removeQuery(relatedSheet.href);
     let uri = NetUtil.newURI(href);
 
     if (uri.scheme == "file") {
       let file = uri.QueryInterface(Ci.nsIFileURL).file;
       path = file.path;
--- a/devtools/client/styleeditor/test/browser.ini
+++ b/devtools/client/styleeditor/test/browser.ini
@@ -35,16 +35,17 @@ support-files =
   sourcemap-css/media-rules.css
   sourcemap-css/media-rules.css.map
   sourcemap-css/test-bootstrap-scss.css
   sourcemap-css/test-stylus.css
   sourcemap-sass/sourcemaps.scss
   sourcemap-sass/media-rules.scss
   sourcemap-styl/test-stylus.styl
   sourcemaps.html
+  sourcemaps-inline.html
   sourcemaps-large.html
   sourcemaps-watching.html
   test_private.css
   test_private.html
   doc_long.css
   doc_uncached.css
   doc_uncached.html
   doc_xulpage.xul
@@ -79,16 +80,17 @@ skip-if = e10s && debug # Bug 1252201 - 
 [browser_styleeditor_pretty.js]
 [browser_styleeditor_private_perwindowpb.js]
 [browser_styleeditor_reload.js]
 [browser_styleeditor_scroll.js]
 [browser_styleeditor_sv_keynav.js]
 [browser_styleeditor_sv_resize.js]
 [browser_styleeditor_selectstylesheet.js]
 [browser_styleeditor_sourcemaps.js]
+[browser_styleeditor_sourcemaps_inline.js]
 [browser_styleeditor_sourcemap_large.js]
 [browser_styleeditor_sourcemap_watching.js]
 [browser_styleeditor_sync.js]
 [browser_styleeditor_syncAddRule.js]
 [browser_styleeditor_syncAlreadyOpen.js]
 [browser_styleeditor_syncEditSelector.js]
 [browser_styleeditor_syncIntoRuleView.js]
 [browser_styleeditor_transition_rule.js]
new file mode 100644
--- /dev/null
+++ b/devtools/client/styleeditor/test/browser_styleeditor_sourcemaps_inline.js
@@ -0,0 +1,91 @@
+/* vim: set ts=2 et sw=2 tw=80: */
+/* Any copyright is dedicated to the Public Domain.
+   http://creativecommons.org/publicdomain/zero/1.0/ */
+
+"use strict";
+
+// https rather than chrome to improve coverage
+const TESTCASE_URI = TEST_BASE_HTTPS + "sourcemaps-inline.html";
+const PREF = "devtools.styleeditor.source-maps-enabled";
+
+const sassContent = [
+  "body {",
+  "  background-color: black;",
+  "  & > h1 {",
+  "    color: white;  ",
+  "  }",
+  "}",
+  ""
+].join("\n");
+
+const cssContent = [
+  "body {",
+  "  background-color: black;",
+  "}",
+  "body > h1 {",
+  "  color: white;",
+  "}",
+  "/*# sourceMappingURL=data:application/json;base64,ewoidmVyc2lvbiI6IDMsCi" +
+  "JtYXBwaW5ncyI6ICJBQUFBLElBQUs7RUFDSCxnQkFBZ0IsRUFBRSxLQUFLOztBQUN2QixTQU" +
+  "FPO0VBQ0wsS0FBSyxFQUFFLEtBQUsiLAoic291cmNlcyI6IFsidGVzdC5zY3NzIl0sCiJzb3" +
+  "VyY2VzQ29udGVudCI6IFsiYm9keSB7XG4gIGJhY2tncm91bmQtY29sb3I6IGJsYWNrO1xuIC" +
+  "AmID4gaDEge1xuICAgIGNvbG9yOiB3aGl0ZTsgIFxuICB9XG59XG4iXSwKIm5hbWVzIjogW1" +
+  "0sCiJmaWxlIjogInRlc3QuY3NzIgp9Cg== */"
+].join("\n");
+
+waitForExplicitFinish();
+
+add_task(function*() {
+  let {ui} = yield openStyleEditorForURL(TESTCASE_URI);
+
+  is(ui.editors.length, 1,
+    "correct number of editors with source maps enabled");
+
+  testEditor(ui.editors[0], "test.scss", sassContent);
+
+  // Test disabling original sources
+  yield togglePref(ui);
+
+  is(ui.editors.length, 1, "correct number of editors after pref toggled");
+
+  // Test CSS editors
+  yield testEditor(ui.editors[0], "<inline style sheet #1>", cssContent);
+
+  Services.prefs.clearUserPref(PREF);
+});
+
+function testEditor(editor, expectedName, expectedText) {
+  let name = getStylesheetNameFor(editor);
+  is(expectedName, name, name + " editor name is correct");
+
+  return openEditor(editor).then(() => {
+    let text = editor.sourceEditor.getText();
+    is(text, expectedText, name + " editor contains expected text");
+  });
+}
+
+/* Helpers */
+
+function togglePref(UI) {
+  let editorsPromise = UI.once("stylesheets-reset");
+  let selectedPromise = UI.once("editor-selected");
+
+  Services.prefs.setBoolPref(PREF, false);
+
+  return promise.all([editorsPromise, selectedPromise]);
+}
+
+function openEditor(editor) {
+  getLinkFor(editor).click();
+
+  return editor.getSourceEditor();
+}
+
+function getLinkFor(editor) {
+  return editor.summary.querySelector(".stylesheet-name");
+}
+
+function getStylesheetNameFor(editor) {
+  return editor.summary.querySelector(".stylesheet-name > label")
+    .getAttribute("value");
+}
new file mode 100644
--- /dev/null
+++ b/devtools/client/styleeditor/test/sourcemaps-inline.html
@@ -0,0 +1,16 @@
+<!doctype html>
+<html>
+<head>
+  <title>testcase for testing CSS source maps in inline style</title>
+  <style type="text/css">body {
+  background-color: black;
+}
+body > h1 {
+  color: white;
+}
+/*# sourceMappingURL=data:application/json;base64,ewoidmVyc2lvbiI6IDMsCiJtYXBwaW5ncyI6ICJBQUFBLElBQUs7RUFDSCxnQkFBZ0IsRUFBRSxLQUFLOztBQUN2QixTQUFPO0VBQ0wsS0FBSyxFQUFFLEtBQUsiLAoic291cmNlcyI6IFsidGVzdC5zY3NzIl0sCiJzb3VyY2VzQ29udGVudCI6IFsiYm9keSB7XG4gIGJhY2tncm91bmQtY29sb3I6IGJsYWNrO1xuICAmID4gaDEge1xuICAgIGNvbG9yOiB3aGl0ZTsgIFxuICB9XG59XG4iXSwKIm5hbWVzIjogW10sCiJmaWxlIjogInRlc3QuY3NzIgp9Cg== */</style>
+</head>
+<body>
+  <h1>Source maps testcase</div>
+</body>
+</html>