Repository: webpack-contrib/source-map-loader
Pull request #188 (2022-10-07 16:48:45)

Fix handle absolute source url
<!--
  HOLY CRAP a Pull Request. We ❤️ those!

  If you remove or skip this template, you'll make the 🐼 sad and the mighty god
  of Github will appear and pile-drive the close button from a great height
  while making animal noises.

  Please place an x (no spaces!) in all [ ] that apply
-->

This PR contains a:

- [x] **bugfix**
- [ ] new **feature**
- [ ] **code refactor**
- [x] **test update** <!-- if bug or feature is checked, this should be too -->
- [ ] **typo fix**
- [ ] **metadata update**

### Motivation / Use-Case

fixes https://github.com/webpack-contrib/source-map-loader/issues/186

### Breaking Changes

No

### Additional Info

No

codecov[bot]: # [Codecov](https://codecov.io/gh/webpack-contrib/source-map-loader/pull/188?src=pr&el=h1&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=webpack-contrib) Report
Base: **97.79**% // Head: **97.83**% // Increases project coverage by **`+0.04%`** :tada:
> Coverage data is based on head [(`aea1973`)](https://codecov.io/gh/webpack-contrib/source-map-loader/pull/188?src=pr&el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=webpack-contrib) compared to base [(`3094e6a`)](https://codecov.io/gh/webpack-contrib/source-map-loader/commit/3094e6a9691a34c41693a9ab28eecb49d55a3fb0?el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=webpack-contrib).
> Patch coverage: 100.00% of modified lines in pull request are covered.

<details><summary>Additional details and impacted files</summary>


```diff
@@            Coverage Diff             @@
##           master     #188      +/-   ##
==========================================
+ Coverage   97.79%   97.83%   +0.04%     
==========================================
  Files           5        5              
  Lines         317      323       +6     
  Branches       96       99       +3     
==========================================
+ Hits          310      316       +6     
  Misses          6        6              
  Partials        1        1              
```


| [Impacted Files](https://codecov.io/gh/webpack-contrib/source-map-loader/pull/188?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=webpack-contrib) | Coverage Δ | |
|---|---|---|
| [src/index.js](https://codecov.io/gh/webpack-contrib/source-map-loader/pull/188/diff?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=webpack-contrib#diff-c3JjL2luZGV4Lmpz) | `100.00% <100.00%> (ø)` | |
| [src/utils.js](https://codecov.io/gh/webpack-contrib/source-map-loader/pull/188/diff?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=webpack-contrib#diff-c3JjL3V0aWxzLmpz) | `100.00% <100.00%> (ø)` | |

Help us with your feedback. Take ten seconds to tell us [how you rate us](https://about.codecov.io/nps?utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=webpack-contrib). Have a feature suggestion? [Share it here.](https://app.codecov.io/gh/feedback/?utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=webpack-contrib)

</details>

[:umbrella: View full report at Codecov](https://codecov.io/gh/webpack-contrib/source-map-loader/pull/188?src=pr&el=continue&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=webpack-contrib).   
:loudspeaker: Do you have feedback about the report comment? [Let us know in this issue](https://about.codecov.io/codecov-pr-comment-feedback/?utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=webpack-contrib).


Patch:
diff --git a/src/index.js b/src/index.js
index fa03809..eac13e3 100644
--- a/src/index.js
+++ b/src/index.js
@@ -5,7 +5,12 @@
 import path from "path";
 
 import schema from "./options.json";
-import { getSourceMappingURL, fetchFromURL, flattenSourceMap } from "./utils";
+import {
+  getSourceMappingURL,
+  fetchFromURL,
+  flattenSourceMap,
+  isURL,
+} from "./utils";
 
 export default async function loader(input, inputMap) {
   const options = this.getOptions(schema);
@@ -122,7 +127,7 @@ export default async function loader(input, inputMap) {
 
       if (skipReading) {
         sourceContent = originalSourceContent;
-      } else if (!errored && sourceURL) {
+      } else if (!errored && sourceURL && !isURL(sourceURL)) {
         this.addDependency(sourceURL);
       }
 
diff --git a/src/utils.js b/src/utils.js
index 824a917..459f7a1 100644
--- a/src/utils.js
+++ b/src/utils.js
@@ -96,6 +96,10 @@ function getSourceMappingURL(code) {
 }
 
 function getAbsolutePath(context, request, sourceRoot) {
+  if (isURL(sourceRoot)) {
+    return new URL(request, sourceRoot).toString();
+  }
+
   if (sourceRoot) {
     if (path.isAbsolute(sourceRoot)) {
       return path.join(sourceRoot, request);
@@ -125,6 +129,10 @@ function fetchFromDataURL(loaderContext, sourceURL) {
 async function fetchFromFilesystem(loaderContext, sourceURL) {
   let buffer;
 
+  if (isURL(sourceURL)) {
+    return { path: sourceURL };
+  }
+
   try {
     buffer = await new Promise((resolve, reject) => {
       loaderContext.fs.readFile(sourceURL, (error, data) => {
@@ -179,6 +187,10 @@ async function fetchPathsFromFilesystem(
   return result;
 }
 
+function isURL(value) {
+  return /^[a-z][a-z0-9+.-]*:/i.test(value) && !path.win32.isAbsolute(value);
+}
+
 async function fetchFromURL(
   loaderContext,
   context,
@@ -187,7 +199,7 @@ async function fetchFromURL(
   skipReading = false
 ) {
   // 1. It's an absolute url and it is not `windows` path like `C:\dir\file`
-  if (/^[a-z][a-z0-9+.-]*:/i.test(url) && !path.win32.isAbsolute(url)) {
+  if (isURL(url)) {
     const { protocol } = urlUtils.parse(url);
 
     if (protocol === "data:") {
@@ -268,4 +280,4 @@ async function fetchFromURL(
   return { sourceURL, sourceContent };
 }
 
-export { getSourceMappingURL, fetchFromURL, flattenSourceMap };
+export { getSourceMappingURL, fetchFromURL, flattenSourceMap, isURL };


Test patch:
diff --git a/test/__snapshots__/loader.test.js.snap b/test/__snapshots__/loader.test.js.snap
index f7a4983..9362b43 100644
--- a/test/__snapshots__/loader.test.js.snap
+++ b/test/__snapshots__/loader.test.js.snap
@@ -113,6 +113,27 @@ exports[`source-map-loader should leave normal files with fake source-map untouc
 
 exports[`source-map-loader should leave normal files with fake source-map untouched: warnings 1`] = `[]`;
 
+exports[`source-map-loader should process absolute URL in sourceRoot: code 1`] = `
+"const foo = "test";
+"
+`;
+
+exports[`source-map-loader should process absolute URL in sourceRoot: errors 1`] = `[]`;
+
+exports[`source-map-loader should process absolute URL in sourceRoot: map 1`] = `
+{
+  "file": "index.d.ts",
+  "mappings": "AAAA,OAAO,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AACpD,OAAO,EAAE,MAAM,EAAE,KAAK,aAAa,EAAE,CAAC;AAEtC,OAAO,EACH,UAAU,EACV,iBAAiB,EACjB,SAAS,EACT,OAAO,EACP,QAAQ,EACX,MAAM,YAAY,CAAC;AAEpB,OAAO,EAAE,UAAU,EAAE,KAAK,iBAAiB,EAAE,CAAC;AAE9C,aAAK,OAAO,GAAG,aAAa,GAAG,iBAAiB,CAAC;AAIjD;;;;;GAKG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,OAAO,GAAG,QAAQ,CAIvE;AACD;;;;;;;;;GASG;AACH,wBAAgB,QAAQ,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,OAAO,GAAG,SAAS,EAAE,CAErE;AACD;;;;;;GAMG;AACH,wBAAgB,eAAe,CAC3B,EAAE,EAAE,CAAC,KAAK,EAAE,KAAK,GAAG,IAAI,EAAE,GAAG,EAAE,SAAS,EAAE,KAAK,IAAI,EACnD,OAAO,CAAC,EAAE,OAAO,EACjB,SAAS,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,KAAK,IAAI,GACvC,MAAM,CAGR;AAED,OAAO,EACH,OAAO,IAAI,SAAS,EACpB,KAAK,SAAS,IAAI,kBAAkB,GACvC,MAAM,gBAAgB,CAAC;AAMxB,OAAO,KAAK,WAAW,MAAM,gBAAgB,CAAC;AAC9C,OAAO,EAAE,WAAW,EAAE,CAAC;AAEvB,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,UAAU,CAAC;AAEzC,OAAO,EAAE,OAAO,EAAE,CAAC;AAEnB;;;;;GAKG;AACH,wBAAgB,SAAS,CACrB,IAAI,EAAE,MAAM,EACZ,OAAO,GAAE,aAAa,GAAG,iBAAqC,GAC/D,IAAI,GAAG,IAAI,CAEb;AAED,OAAO,KAAK,QAAQ,MAAM,UAAU,CAAC;AAGrC,OAAO,EAAE,UAAU,IAAI,cAAc,EAAE,CAAC",
+  "names": [],
+  "sources": [
+    "https://raw.githubusercontent.com/fb55/htmlparser2/4763205746cd80120b5d2b69041197a394d24ba9/src/index.ts",
+  ],
+  "version": 3,
+}
+`;
+
+exports[`source-map-loader should process absolute URL in sourceRoot: warnings 1`] = `[]`;
+
 exports[`source-map-loader should process css sourceMap: code 1`] = `
 "* {
   box-sizing: border-box; }
diff --git a/test/fixtures/absolute-source-root.js b/test/fixtures/absolute-source-root.js
new file mode 100644
index 0000000..c291190
--- /dev/null
+++ b/test/fixtures/absolute-source-root.js
@@ -0,0 +1,2 @@
+const foo = "test";
+//# sourceMappingURL=absolute-source-root.js.map
diff --git a/test/fixtures/absolute-source-root.js.map b/test/fixtures/absolute-source-root.js.map
new file mode 100644
index 0000000..4edcea9
--- /dev/null
+++ b/test/fixtures/absolute-source-root.js.map
@@ -0,0 +1,1 @@
+{"version":3,"file":"index.d.ts","sourceRoot":"https://raw.githubusercontent.com/fb55/htmlparser2/4763205746cd80120b5d2b69041197a394d24ba9/src/","sources":["index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AACpD,OAAO,EAAE,MAAM,EAAE,KAAK,aAAa,EAAE,CAAC;AAEtC,OAAO,EACH,UAAU,EACV,iBAAiB,EACjB,SAAS,EACT,OAAO,EACP,QAAQ,EACX,MAAM,YAAY,CAAC;AAEpB,OAAO,EAAE,UAAU,EAAE,KAAK,iBAAiB,EAAE,CAAC;AAE9C,aAAK,OAAO,GAAG,aAAa,GAAG,iBAAiB,CAAC;AAIjD;;;;;GAKG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,OAAO,GAAG,QAAQ,CAIvE;AACD;;;;;;;;;GASG;AACH,wBAAgB,QAAQ,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,OAAO,GAAG,SAAS,EAAE,CAErE;AACD;;;;;;GAMG;AACH,wBAAgB,eAAe,CAC3B,EAAE,EAAE,CAAC,KAAK,EAAE,KAAK,GAAG,IAAI,EAAE,GAAG,EAAE,SAAS,EAAE,KAAK,IAAI,EACnD,OAAO,CAAC,EAAE,OAAO,EACjB,SAAS,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,KAAK,IAAI,GACvC,MAAM,CAGR;AAED,OAAO,EACH,OAAO,IAAI,SAAS,EACpB,KAAK,SAAS,IAAI,kBAAkB,GACvC,MAAM,gBAAgB,CAAC;AAMxB,OAAO,KAAK,WAAW,MAAM,gBAAgB,CAAC;AAC9C,OAAO,EAAE,WAAW,EAAE,CAAC;AAEvB,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,UAAU,CAAC;AAEzC,OAAO,EAAE,OAAO,EAAE,CAAC;AAEnB;;;;;GAKG;AACH,wBAAgB,SAAS,CACrB,IAAI,EAAE,MAAM,EACZ,OAAO,GAAE,aAAa,GAAG,iBAAqC,GAC/D,IAAI,GAAG,IAAI,CAEb;AAED,OAAO,KAAK,QAAQ,MAAM,UAAU,CAAC;AAGrC,OAAO,EAAE,UAAU,IAAI,cAAc,EAAE,CAAC"}
\ No newline at end of file
diff --git a/test/loader.test.js b/test/loader.test.js
index ed4e9df..2816cef 100644
--- a/test/loader.test.js
+++ b/test/loader.test.js
@@ -752,4 +752,17 @@ describe("source-map-loader", () => {
     expect(getWarnings(stats)).toMatchSnapshot("warnings");
     expect(getErrors(stats)).toMatchSnapshot("errors");
   });
+
+  it("should process absolute URL in sourceRoot", async () => {
+    const testId = "absolute-source-root.js";
+    const compiler = getCompiler(testId);
+    const stats = await compile(compiler);
+    const codeFromBundle = getCodeFromBundle(stats, compiler);
+
+    expect(codeFromBundle.map).toBeDefined();
+    expect(normalizeMap(codeFromBundle.map)).toMatchSnapshot("map");
+    expect(codeFromBundle.code).toMatchSnapshot("code");
+    expect(getWarnings(stats)).toMatchSnapshot("warnings");
+    expect(getErrors(stats)).toMatchSnapshot("errors");
+  });
 });