You can not select more than 25 topics
			Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
		
		
		
		
			
				
					75 lines
				
				1.7 KiB
			
		
		
			
		
	
	
					75 lines
				
				1.7 KiB
			| 
								 
											4 years ago
										 
									 | 
							
								"use strict";
							 | 
						||
| 
								 | 
							
								const MIMEType = require("whatwg-mimetype");
							 | 
						||
| 
								 | 
							
								const { parseURL, serializeURL } = require("whatwg-url");
							 | 
						||
| 
								 | 
							
								const {
							 | 
						||
| 
								 | 
							
								  stripLeadingAndTrailingASCIIWhitespace,
							 | 
						||
| 
								 | 
							
								  stringPercentDecode,
							 | 
						||
| 
								 | 
							
								  isomorphicDecode,
							 | 
						||
| 
								 | 
							
								  forgivingBase64Decode
							 | 
						||
| 
								 | 
							
								} = require("./utils.js");
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								module.exports = stringInput => {
							 | 
						||
| 
								 | 
							
								  const urlRecord = parseURL(stringInput);
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  if (urlRecord === null) {
							 | 
						||
| 
								 | 
							
								    return null;
							 | 
						||
| 
								 | 
							
								  }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  return module.exports.fromURLRecord(urlRecord);
							 | 
						||
| 
								 | 
							
								};
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								module.exports.fromURLRecord = urlRecord => {
							 | 
						||
| 
								 | 
							
								  if (urlRecord.scheme !== "data") {
							 | 
						||
| 
								 | 
							
								    return null;
							 | 
						||
| 
								 | 
							
								  }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  const input = serializeURL(urlRecord, true).substring("data:".length);
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  let position = 0;
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  let mimeType = "";
							 | 
						||
| 
								 | 
							
								  while (position < input.length && input[position] !== ",") {
							 | 
						||
| 
								 | 
							
								    mimeType += input[position];
							 | 
						||
| 
								 | 
							
								    ++position;
							 | 
						||
| 
								 | 
							
								  }
							 | 
						||
| 
								 | 
							
								  mimeType = stripLeadingAndTrailingASCIIWhitespace(mimeType);
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  if (position === input.length) {
							 | 
						||
| 
								 | 
							
								    return null;
							 | 
						||
| 
								 | 
							
								  }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  ++position;
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  const encodedBody = input.substring(position);
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  let body = stringPercentDecode(encodedBody);
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  // Can't use /i regexp flag because it isn't restricted to ASCII.
							 | 
						||
| 
								 | 
							
								  const mimeTypeBase64MatchResult = /(.*); *[Bb][Aa][Ss][Ee]64$/.exec(mimeType);
							 | 
						||
| 
								 | 
							
								  if (mimeTypeBase64MatchResult) {
							 | 
						||
| 
								 | 
							
								    const stringBody = isomorphicDecode(body);
							 | 
						||
| 
								 | 
							
								    body = forgivingBase64Decode(stringBody);
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    if (body === null) {
							 | 
						||
| 
								 | 
							
								      return null;
							 | 
						||
| 
								 | 
							
								    }
							 | 
						||
| 
								 | 
							
								    mimeType = mimeTypeBase64MatchResult[1];
							 | 
						||
| 
								 | 
							
								  }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  if (mimeType.startsWith(";")) {
							 | 
						||
| 
								 | 
							
								    mimeType = "text/plain" + mimeType;
							 | 
						||
| 
								 | 
							
								  }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  let mimeTypeRecord;
							 | 
						||
| 
								 | 
							
								  try {
							 | 
						||
| 
								 | 
							
								    mimeTypeRecord = new MIMEType(mimeType);
							 | 
						||
| 
								 | 
							
								  } catch (e) {
							 | 
						||
| 
								 | 
							
								    mimeTypeRecord = new MIMEType("text/plain;charset=US-ASCII");
							 | 
						||
| 
								 | 
							
								  }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								  return {
							 | 
						||
| 
								 | 
							
								    mimeType: mimeTypeRecord,
							 | 
						||
| 
								 | 
							
								    body
							 | 
						||
| 
								 | 
							
								  };
							 | 
						||
| 
								 | 
							
								};
							 |