mirror of
https://github.com/Hopiu/angular.js.git
synced 2026-03-20 16:30:26 +00:00
encode query params correctly but not too agressively
This commit is contained in:
parent
eccd9bfbb3
commit
78a0f41058
4 changed files with 65 additions and 12 deletions
|
|
@ -811,20 +811,44 @@ function toKeyValue(obj) {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* we need our custom mehtod because encodeURIComponent is too agressive and doesn't follow
|
* we need our custom mehtod because encodeURIComponent is too agressive and doesn't follow
|
||||||
* http://www.ietf.org/rfc/rfc2396.txt with regards to the character set (pchar) allowed in path
|
* http://www.ietf.org/rfc/rfc3986.txt with regards to the character set (pchar) allowed in path
|
||||||
* segments
|
* segments:
|
||||||
|
* segment = *pchar
|
||||||
|
* pchar = unreserved / pct-encoded / sub-delims / ":" / "@"
|
||||||
|
* pct-encoded = "%" HEXDIG HEXDIG
|
||||||
|
* unreserved = ALPHA / DIGIT / "-" / "." / "_" / "~"
|
||||||
|
* sub-delims = "!" / "$" / "&" / "'" / "(" / ")"
|
||||||
|
* / "*" / "+" / "," / ";" / "="
|
||||||
*/
|
*/
|
||||||
function encodeUriSegment(val) {
|
function encodeUriSegment(val) {
|
||||||
|
return encodeUriQuery(val, true).
|
||||||
|
replace(/%26/gi, '&').
|
||||||
|
replace(/%3D/gi, '=').
|
||||||
|
replace(/%2B/gi, '+');
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This method is intended for encoding *key* or *value* parts of query component. We need a custom
|
||||||
|
* method becuase encodeURIComponent is too agressive and encodes stuff that doesn't have to be
|
||||||
|
* encoded per http://tools.ietf.org/html/rfc3986:
|
||||||
|
* query = *( pchar / "/" / "?" )
|
||||||
|
* pchar = unreserved / pct-encoded / sub-delims / ":" / "@"
|
||||||
|
* unreserved = ALPHA / DIGIT / "-" / "." / "_" / "~"
|
||||||
|
* pct-encoded = "%" HEXDIG HEXDIG
|
||||||
|
* sub-delims = "!" / "$" / "&" / "'" / "(" / ")"
|
||||||
|
* / "*" / "+" / "," / ";" / "="
|
||||||
|
*/
|
||||||
|
function encodeUriQuery(val, pctEncodeSpaces) {
|
||||||
return encodeURIComponent(val).
|
return encodeURIComponent(val).
|
||||||
replace(/%40/gi, '@').
|
replace(/%40/gi, '@').
|
||||||
replace(/%3A/gi, ':').
|
replace(/%3A/gi, ':').
|
||||||
replace(/%26/gi, '&').
|
|
||||||
replace(/%3D/gi, '=').
|
|
||||||
replace(/%2B/gi, '+').
|
|
||||||
replace(/%24/g, '$').
|
replace(/%24/g, '$').
|
||||||
replace(/%2C/gi, ',');
|
replace(/%2C/gi, ',').
|
||||||
|
replace((pctEncodeSpaces ? null : /%20/g), '+');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @workInProgress
|
* @workInProgress
|
||||||
* @ngdoc directive
|
* @ngdoc directive
|
||||||
|
|
|
||||||
|
|
@ -26,7 +26,7 @@ Route.prototype = {
|
||||||
var query = [];
|
var query = [];
|
||||||
forEachSorted(params, function(value, key){
|
forEachSorted(params, function(value, key){
|
||||||
if (!self.urlParams[key]) {
|
if (!self.urlParams[key]) {
|
||||||
query.push(encodeURIComponent(key) + '=' + encodeURIComponent(value));
|
query.push(encodeUriQuery(key) + '=' + encodeUriQuery(value));
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
url = url.replace(/\/*$/, '');
|
url = url.replace(/\/*$/, '');
|
||||||
|
|
|
||||||
|
|
@ -55,7 +55,6 @@ describe('angular', function(){
|
||||||
expect(copy(123)).toEqual(123);
|
expect(copy(123)).toEqual(123);
|
||||||
expect(copy([{key:null}])).toEqual([{key:null}]);
|
expect(copy([{key:null}])).toEqual([{key:null}]);
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('equals', function(){
|
describe('equals', function(){
|
||||||
|
|
@ -170,7 +169,7 @@ describe('angular', function(){
|
||||||
|
|
||||||
|
|
||||||
describe('encodeUriSegment', function() {
|
describe('encodeUriSegment', function() {
|
||||||
it('should correctly encode uri segment and not encode chars defined as pchar set in rfc2396',
|
it('should correctly encode uri segment and not encode chars defined as pchar set in rfc3986',
|
||||||
function() {
|
function() {
|
||||||
//don't encode alphanum
|
//don't encode alphanum
|
||||||
expect(encodeUriSegment('asdf1234asdf')).
|
expect(encodeUriSegment('asdf1234asdf')).
|
||||||
|
|
@ -191,6 +190,36 @@ describe('angular', function(){
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
|
describe('encodeUriQuery', function() {
|
||||||
|
it('should correctly encode uri query and not encode chars defined as pchar set in rfc3986',
|
||||||
|
function() {
|
||||||
|
//don't encode alphanum
|
||||||
|
expect(encodeUriQuery('asdf1234asdf')).
|
||||||
|
toEqual('asdf1234asdf');
|
||||||
|
|
||||||
|
//don't encode unreserved
|
||||||
|
expect(encodeUriQuery("-_.!~*'() -_.!~*'()")).
|
||||||
|
toEqual("-_.!~*'()+-_.!~*'()");
|
||||||
|
|
||||||
|
//don't encode the rest of pchar
|
||||||
|
expect(encodeUriQuery(':@$, :@$,')).
|
||||||
|
toEqual(':@$,+:@$,');
|
||||||
|
|
||||||
|
//encode '&', ';', '=', '+', and '#'
|
||||||
|
expect(encodeUriQuery('&;=+# &;=+#')).
|
||||||
|
toEqual('%26%3B%3D%2B%23+%26%3B%3D%2B%23');
|
||||||
|
|
||||||
|
//encode ' ' as '+'
|
||||||
|
expect(encodeUriQuery(' ')).
|
||||||
|
toEqual('++');
|
||||||
|
|
||||||
|
//encode ' ' as '%20' when a flag is used
|
||||||
|
expect(encodeUriQuery(' ', true)).
|
||||||
|
toEqual('%20%20');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
describe ('rngScript', function() {
|
describe ('rngScript', function() {
|
||||||
it('should match angular.js', function() {
|
it('should match angular.js', function() {
|
||||||
expect('angular.js'.match(rngScript)).not.toBeNull();
|
expect('angular.js'.match(rngScript)).not.toBeNull();
|
||||||
|
|
|
||||||
|
|
@ -49,14 +49,14 @@ describe("resource", function() {
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should not encode @ in url params', function() {
|
it('should not encode @ in url params', function() {
|
||||||
//encodeURIComponent is too agressive and doesn't follow http://www.ietf.org/rfc/rfc2396.txt
|
//encodeURIComponent is too agressive and doesn't follow http://www.ietf.org/rfc/rfc3986.txt
|
||||||
//with regards to the character set (pchar) allowed in path segments
|
//with regards to the character set (pchar) allowed in path segments
|
||||||
//so we need this test to make sure that we don't over-encode the params and break stuff like
|
//so we need this test to make sure that we don't over-encode the params and break stuff like
|
||||||
//buzz api which uses @self
|
//buzz api which uses @self
|
||||||
|
|
||||||
var R = resource.route('/Path/:a');
|
var R = resource.route('/Path/:a');
|
||||||
xhr.expectGET('/Path/doh@foo?bar=baz%401').respond({});
|
xhr.expectGET('/Path/doh@fo%20o?!do%26h=g%3Da+h&:bar=$baz@1').respond({});
|
||||||
R.get({a: 'doh@foo', bar: 'baz@1'});
|
R.get({a: 'doh@fo o', ':bar': '$baz@1', '!do&h': 'g=a h'});
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should encode & in url params', function() {
|
it('should encode & in url params', function() {
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue