| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342 | 
							- var sourceMappingURL   = require("source-map-url")
 
- var resolveUrl         = require("./resolve-url")
 
- var decodeUriComponent = require("./decode-uri-component")
 
- var urix               = require("urix")
 
- var atob               = require("atob")
 
- function callbackAsync(callback, error, result) {
 
-   setImmediate(function() { callback(error, result) })
 
- }
 
- function parseMapToJSON(string, data) {
 
-   try {
 
-     return JSON.parse(string.replace(/^\)\]\}'/, ""))
 
-   } catch (error) {
 
-     error.sourceMapData = data
 
-     throw error
 
-   }
 
- }
 
- function readSync(read, url, data) {
 
-   var readUrl = decodeUriComponent(url)
 
-   try {
 
-     return String(read(readUrl))
 
-   } catch (error) {
 
-     error.sourceMapData = data
 
-     throw error
 
-   }
 
- }
 
- function resolveSourceMap(code, codeUrl, read, callback) {
 
-   var mapData
 
-   try {
 
-     mapData = resolveSourceMapHelper(code, codeUrl)
 
-   } catch (error) {
 
-     return callbackAsync(callback, error)
 
-   }
 
-   if (!mapData || mapData.map) {
 
-     return callbackAsync(callback, null, mapData)
 
-   }
 
-   var readUrl = decodeUriComponent(mapData.url)
 
-   read(readUrl, function(error, result) {
 
-     if (error) {
 
-       error.sourceMapData = mapData
 
-       return callback(error)
 
-     }
 
-     mapData.map = String(result)
 
-     try {
 
-       mapData.map = parseMapToJSON(mapData.map, mapData)
 
-     } catch (error) {
 
-       return callback(error)
 
-     }
 
-     callback(null, mapData)
 
-   })
 
- }
 
- function resolveSourceMapSync(code, codeUrl, read) {
 
-   var mapData = resolveSourceMapHelper(code, codeUrl)
 
-   if (!mapData || mapData.map) {
 
-     return mapData
 
-   }
 
-   mapData.map = readSync(read, mapData.url, mapData)
 
-   mapData.map = parseMapToJSON(mapData.map, mapData)
 
-   return mapData
 
- }
 
- var dataUriRegex = /^data:([^,;]*)(;[^,;]*)*(?:,(.*))?$/
 
- /**
 
-  * The media type for JSON text is application/json.
 
-  *
 
-  * {@link https://tools.ietf.org/html/rfc8259#section-11 | IANA Considerations }
 
-  *
 
-  * `text/json` is non-standard media type
 
-  */
 
- var jsonMimeTypeRegex = /^(?:application|text)\/json$/
 
- /**
 
-  * JSON text exchanged between systems that are not part of a closed ecosystem
 
-  * MUST be encoded using UTF-8.
 
-  *
 
-  * {@link https://tools.ietf.org/html/rfc8259#section-8.1 | Character Encoding}
 
-  */
 
- var jsonCharacterEncoding = "utf-8"
 
- function base64ToBuf(b64) {
 
-   var binStr = atob(b64)
 
-   var len = binStr.length
 
-   var arr = new Uint8Array(len)
 
-   for (var i = 0; i < len; i++) {
 
-     arr[i] = binStr.charCodeAt(i)
 
-   }
 
-   return arr
 
- }
 
- function decodeBase64String(b64) {
 
-   if (typeof TextDecoder === "undefined" || typeof Uint8Array === "undefined") {
 
-     return atob(b64)
 
-   }
 
-   var buf = base64ToBuf(b64);
 
-   // Note: `decoder.decode` method will throw a `DOMException` with the
 
-   // `"EncodingError"` value when an coding error is found.
 
-   var decoder = new TextDecoder(jsonCharacterEncoding, {fatal: true})
 
-   return decoder.decode(buf);
 
- }
 
- function resolveSourceMapHelper(code, codeUrl) {
 
-   codeUrl = urix(codeUrl)
 
-   var url = sourceMappingURL.getFrom(code)
 
-   if (!url) {
 
-     return null
 
-   }
 
-   var dataUri = url.match(dataUriRegex)
 
-   if (dataUri) {
 
-     var mimeType = dataUri[1] || "text/plain"
 
-     var lastParameter = dataUri[2] || ""
 
-     var encoded = dataUri[3] || ""
 
-     var data = {
 
-       sourceMappingURL: url,
 
-       url: null,
 
-       sourcesRelativeTo: codeUrl,
 
-       map: encoded
 
-     }
 
-     if (!jsonMimeTypeRegex.test(mimeType)) {
 
-       var error = new Error("Unuseful data uri mime type: " + mimeType)
 
-       error.sourceMapData = data
 
-       throw error
 
-     }
 
-     try {
 
-       data.map = parseMapToJSON(
 
-         lastParameter === ";base64" ? decodeBase64String(encoded) : decodeURIComponent(encoded),
 
-         data
 
-       )
 
-     } catch (error) {
 
-       error.sourceMapData = data
 
-       throw error
 
-     }
 
-     return data
 
-   }
 
-   var mapUrl = resolveUrl(codeUrl, url)
 
-   return {
 
-     sourceMappingURL: url,
 
-     url: mapUrl,
 
-     sourcesRelativeTo: mapUrl,
 
-     map: null
 
-   }
 
- }
 
- function resolveSources(map, mapUrl, read, options, callback) {
 
-   if (typeof options === "function") {
 
-     callback = options
 
-     options = {}
 
-   }
 
-   var pending = map.sources ? map.sources.length : 0
 
-   var result = {
 
-     sourcesResolved: [],
 
-     sourcesContent:  []
 
-   }
 
-   if (pending === 0) {
 
-     callbackAsync(callback, null, result)
 
-     return
 
-   }
 
-   var done = function() {
 
-     pending--
 
-     if (pending === 0) {
 
-       callback(null, result)
 
-     }
 
-   }
 
-   resolveSourcesHelper(map, mapUrl, options, function(fullUrl, sourceContent, index) {
 
-     result.sourcesResolved[index] = fullUrl
 
-     if (typeof sourceContent === "string") {
 
-       result.sourcesContent[index] = sourceContent
 
-       callbackAsync(done, null)
 
-     } else {
 
-       var readUrl = decodeUriComponent(fullUrl)
 
-       read(readUrl, function(error, source) {
 
-         result.sourcesContent[index] = error ? error : String(source)
 
-         done()
 
-       })
 
-     }
 
-   })
 
- }
 
- function resolveSourcesSync(map, mapUrl, read, options) {
 
-   var result = {
 
-     sourcesResolved: [],
 
-     sourcesContent:  []
 
-   }
 
-   if (!map.sources || map.sources.length === 0) {
 
-     return result
 
-   }
 
-   resolveSourcesHelper(map, mapUrl, options, function(fullUrl, sourceContent, index) {
 
-     result.sourcesResolved[index] = fullUrl
 
-     if (read !== null) {
 
-       if (typeof sourceContent === "string") {
 
-         result.sourcesContent[index] = sourceContent
 
-       } else {
 
-         var readUrl = decodeUriComponent(fullUrl)
 
-         try {
 
-           result.sourcesContent[index] = String(read(readUrl))
 
-         } catch (error) {
 
-           result.sourcesContent[index] = error
 
-         }
 
-       }
 
-     }
 
-   })
 
-   return result
 
- }
 
- var endingSlash = /\/?$/
 
- function resolveSourcesHelper(map, mapUrl, options, fn) {
 
-   options = options || {}
 
-   mapUrl = urix(mapUrl)
 
-   var fullUrl
 
-   var sourceContent
 
-   var sourceRoot
 
-   for (var index = 0, len = map.sources.length; index < len; index++) {
 
-     sourceRoot = null
 
-     if (typeof options.sourceRoot === "string") {
 
-       sourceRoot = options.sourceRoot
 
-     } else if (typeof map.sourceRoot === "string" && options.sourceRoot !== false) {
 
-       sourceRoot = map.sourceRoot
 
-     }
 
-     // If the sourceRoot is the empty string, it is equivalent to not setting
 
-     // the property at all.
 
-     if (sourceRoot === null || sourceRoot === '') {
 
-       fullUrl = resolveUrl(mapUrl, map.sources[index])
 
-     } else {
 
-       // Make sure that the sourceRoot ends with a slash, so that `/scripts/subdir` becomes
 
-       // `/scripts/subdir/<source>`, not `/scripts/<source>`. Pointing to a file as source root
 
-       // does not make sense.
 
-       fullUrl = resolveUrl(mapUrl, sourceRoot.replace(endingSlash, "/"), map.sources[index])
 
-     }
 
-     sourceContent = (map.sourcesContent || [])[index]
 
-     fn(fullUrl, sourceContent, index)
 
-   }
 
- }
 
- function resolve(code, codeUrl, read, options, callback) {
 
-   if (typeof options === "function") {
 
-     callback = options
 
-     options = {}
 
-   }
 
-   if (code === null) {
 
-     var mapUrl = codeUrl
 
-     var data = {
 
-       sourceMappingURL: null,
 
-       url: mapUrl,
 
-       sourcesRelativeTo: mapUrl,
 
-       map: null
 
-     }
 
-     var readUrl = decodeUriComponent(mapUrl)
 
-     read(readUrl, function(error, result) {
 
-       if (error) {
 
-         error.sourceMapData = data
 
-         return callback(error)
 
-       }
 
-       data.map = String(result)
 
-       try {
 
-         data.map = parseMapToJSON(data.map, data)
 
-       } catch (error) {
 
-         return callback(error)
 
-       }
 
-       _resolveSources(data)
 
-     })
 
-   } else {
 
-     resolveSourceMap(code, codeUrl, read, function(error, mapData) {
 
-       if (error) {
 
-         return callback(error)
 
-       }
 
-       if (!mapData) {
 
-         return callback(null, null)
 
-       }
 
-       _resolveSources(mapData)
 
-     })
 
-   }
 
-   function _resolveSources(mapData) {
 
-     resolveSources(mapData.map, mapData.sourcesRelativeTo, read, options, function(error, result) {
 
-       if (error) {
 
-         return callback(error)
 
-       }
 
-       mapData.sourcesResolved = result.sourcesResolved
 
-       mapData.sourcesContent  = result.sourcesContent
 
-       callback(null, mapData)
 
-     })
 
-   }
 
- }
 
- function resolveSync(code, codeUrl, read, options) {
 
-   var mapData
 
-   if (code === null) {
 
-     var mapUrl = codeUrl
 
-     mapData = {
 
-       sourceMappingURL: null,
 
-       url: mapUrl,
 
-       sourcesRelativeTo: mapUrl,
 
-       map: null
 
-     }
 
-     mapData.map = readSync(read, mapUrl, mapData)
 
-     mapData.map = parseMapToJSON(mapData.map, mapData)
 
-   } else {
 
-     mapData = resolveSourceMapSync(code, codeUrl, read)
 
-     if (!mapData) {
 
-       return null
 
-     }
 
-   }
 
-   var result = resolveSourcesSync(mapData.map, mapData.sourcesRelativeTo, read, options)
 
-   mapData.sourcesResolved = result.sourcesResolved
 
-   mapData.sourcesContent  = result.sourcesContent
 
-   return mapData
 
- }
 
- module.exports = {
 
-   resolveSourceMap:     resolveSourceMap,
 
-   resolveSourceMapSync: resolveSourceMapSync,
 
-   resolveSources:       resolveSources,
 
-   resolveSourcesSync:   resolveSourcesSync,
 
-   resolve:              resolve,
 
-   resolveSync:          resolveSync,
 
-   parseMapToJSON:       parseMapToJSON
 
- }
 
 
  |