index.js 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128
  1. "use strict";
  2. Object.defineProperty(exports, "__esModule", {
  3. value: true
  4. });
  5. exports.default = loader;
  6. var _path = _interopRequireDefault(require("path"));
  7. var _options = _interopRequireDefault(require("./options.json"));
  8. var _utils = require("./utils");
  9. function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
  10. /*
  11. MIT License http://www.opensource.org/licenses/mit-license.php
  12. Author Tobias Koppers @sokra
  13. */
  14. async function loader(input, inputMap) {
  15. const options = this.getOptions(_options.default);
  16. const {
  17. sourceMappingURL,
  18. replacementString
  19. } = (0, _utils.getSourceMappingURL)(input);
  20. const callback = this.async();
  21. if (!sourceMappingURL) {
  22. callback(null, input, inputMap);
  23. return;
  24. }
  25. let behaviourSourceMappingUrl;
  26. try {
  27. behaviourSourceMappingUrl = typeof options.filterSourceMappingUrl !== "undefined" ? options.filterSourceMappingUrl(sourceMappingURL, this.resourcePath) : "consume";
  28. } catch (error) {
  29. callback(error);
  30. return;
  31. }
  32. // eslint-disable-next-line default-case
  33. switch (behaviourSourceMappingUrl) {
  34. case "skip":
  35. callback(null, input, inputMap);
  36. return;
  37. case false:
  38. case "remove":
  39. callback(null, input.replace(replacementString, ""), inputMap);
  40. return;
  41. }
  42. let sourceURL;
  43. let sourceContent;
  44. try {
  45. ({
  46. sourceURL,
  47. sourceContent
  48. } = await (0, _utils.fetchFromURL)(this, this.context, sourceMappingURL));
  49. } catch (error) {
  50. this.emitWarning(error);
  51. callback(null, input, inputMap);
  52. return;
  53. }
  54. if (sourceURL) {
  55. this.addDependency(sourceURL);
  56. }
  57. let map;
  58. try {
  59. map = JSON.parse(sourceContent.replace(/^\)\]\}'/, ""));
  60. } catch (parseError) {
  61. this.emitWarning(new Error(`Failed to parse source map from '${sourceMappingURL}': ${parseError}`));
  62. callback(null, input, inputMap);
  63. return;
  64. }
  65. const context = sourceURL ? _path.default.dirname(sourceURL) : this.context;
  66. if (map.sections) {
  67. // eslint-disable-next-line no-param-reassign
  68. map = await (0, _utils.flattenSourceMap)(map);
  69. }
  70. const resolvedSources = await Promise.all(map.sources.map(async (source, i) => {
  71. // eslint-disable-next-line no-shadow
  72. let sourceURL;
  73. // eslint-disable-next-line no-shadow
  74. let sourceContent;
  75. const originalSourceContent = map.sourcesContent && typeof map.sourcesContent[i] !== "undefined" && map.sourcesContent[i] !== null ? map.sourcesContent[i] :
  76. // eslint-disable-next-line no-undefined
  77. undefined;
  78. const skipReading = typeof originalSourceContent !== "undefined";
  79. let errored = false;
  80. // We do not skipReading here, because we need absolute paths in sources.
  81. // This is necessary so that for sourceMaps with the same file structure in sources, name collisions do not occur.
  82. // https://github.com/webpack-contrib/source-map-loader/issues/51
  83. try {
  84. ({
  85. sourceURL,
  86. sourceContent
  87. } = await (0, _utils.fetchFromURL)(this, context, source, map.sourceRoot, skipReading));
  88. } catch (error) {
  89. errored = true;
  90. this.emitWarning(error);
  91. }
  92. if (skipReading) {
  93. sourceContent = originalSourceContent;
  94. } else if (!errored && sourceURL && !(0, _utils.isURL)(sourceURL)) {
  95. this.addDependency(sourceURL);
  96. }
  97. // Return original value of `source` when error happens
  98. return {
  99. sourceURL: errored ? source : sourceURL,
  100. sourceContent
  101. };
  102. }));
  103. const newMap = {
  104. ...map
  105. };
  106. newMap.sources = [];
  107. newMap.sourcesContent = [];
  108. delete newMap.sourceRoot;
  109. resolvedSources.forEach(source => {
  110. // eslint-disable-next-line no-shadow
  111. const {
  112. sourceURL,
  113. sourceContent
  114. } = source;
  115. newMap.sources.push(sourceURL || "");
  116. newMap.sourcesContent.push(sourceContent || "");
  117. });
  118. const sourcesContentIsEmpty = newMap.sourcesContent.filter(entry => Boolean(entry)).length === 0;
  119. if (sourcesContentIsEmpty) {
  120. delete newMap.sourcesContent;
  121. }
  122. callback(null, input.replace(replacementString, ""), newMap);
  123. }