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.
		
		
		
		
		
			
		
			
				
					
					
						
							94 lines
						
					
					
						
							2.2 KiB
						
					
					
				
			
		
		
	
	
							94 lines
						
					
					
						
							2.2 KiB
						
					
					
				'use strict'; | 
						|
var token = '%[a-f0-9]{2}'; | 
						|
var singleMatcher = new RegExp(token, 'gi'); | 
						|
var multiMatcher = new RegExp('(' + token + ')+', 'gi'); | 
						|
 | 
						|
function decodeComponents(components, split) { | 
						|
	try { | 
						|
		// Try to decode the entire string first | 
						|
		return decodeURIComponent(components.join('')); | 
						|
	} catch (err) { | 
						|
		// Do nothing | 
						|
	} | 
						|
 | 
						|
	if (components.length === 1) { | 
						|
		return components; | 
						|
	} | 
						|
 | 
						|
	split = split || 1; | 
						|
 | 
						|
	// Split the array in 2 parts | 
						|
	var left = components.slice(0, split); | 
						|
	var right = components.slice(split); | 
						|
 | 
						|
	return Array.prototype.concat.call([], decodeComponents(left), decodeComponents(right)); | 
						|
} | 
						|
 | 
						|
function decode(input) { | 
						|
	try { | 
						|
		return decodeURIComponent(input); | 
						|
	} catch (err) { | 
						|
		var tokens = input.match(singleMatcher); | 
						|
 | 
						|
		for (var i = 1; i < tokens.length; i++) { | 
						|
			input = decodeComponents(tokens, i).join(''); | 
						|
 | 
						|
			tokens = input.match(singleMatcher); | 
						|
		} | 
						|
 | 
						|
		return input; | 
						|
	} | 
						|
} | 
						|
 | 
						|
function customDecodeURIComponent(input) { | 
						|
	// Keep track of all the replacements and prefill the map with the `BOM` | 
						|
	var replaceMap = { | 
						|
		'%FE%FF': '\uFFFD\uFFFD', | 
						|
		'%FF%FE': '\uFFFD\uFFFD' | 
						|
	}; | 
						|
 | 
						|
	var match = multiMatcher.exec(input); | 
						|
	while (match) { | 
						|
		try { | 
						|
			// Decode as big chunks as possible | 
						|
			replaceMap[match[0]] = decodeURIComponent(match[0]); | 
						|
		} catch (err) { | 
						|
			var result = decode(match[0]); | 
						|
 | 
						|
			if (result !== match[0]) { | 
						|
				replaceMap[match[0]] = result; | 
						|
			} | 
						|
		} | 
						|
 | 
						|
		match = multiMatcher.exec(input); | 
						|
	} | 
						|
 | 
						|
	// Add `%C2` at the end of the map to make sure it does not replace the combinator before everything else | 
						|
	replaceMap['%C2'] = '\uFFFD'; | 
						|
 | 
						|
	var entries = Object.keys(replaceMap); | 
						|
 | 
						|
	for (var i = 0; i < entries.length; i++) { | 
						|
		// Replace all decoded components | 
						|
		var key = entries[i]; | 
						|
		input = input.replace(new RegExp(key, 'g'), replaceMap[key]); | 
						|
	} | 
						|
 | 
						|
	return input; | 
						|
} | 
						|
 | 
						|
module.exports = function (encodedURI) { | 
						|
	if (typeof encodedURI !== 'string') { | 
						|
		throw new TypeError('Expected `encodedURI` to be of type `string`, got `' + typeof encodedURI + '`'); | 
						|
	} | 
						|
 | 
						|
	try { | 
						|
		encodedURI = encodedURI.replace(/\+/g, ' '); | 
						|
 | 
						|
		// Try the built in decoder first | 
						|
		return decodeURIComponent(encodedURI); | 
						|
	} catch (err) { | 
						|
		// Fallback to a more advanced decoder | 
						|
		return customDecodeURIComponent(encodedURI); | 
						|
	} | 
						|
};
 | 
						|
 |