mirror of
https://github.com/shivammathur/setup-php.git
synced 2025-09-07 13:24:07 +07:00
Improve code quality and write tests
This commit is contained in:
3
node_modules/urlgrey/.npmignore
generated
vendored
Normal file
3
node_modules/urlgrey/.npmignore
generated
vendored
Normal file
@ -0,0 +1,3 @@
|
||||
test.html
|
||||
urlgrey.js
|
||||
urlgrey.min.js
|
4
node_modules/urlgrey/.travis.yml
generated
vendored
Normal file
4
node_modules/urlgrey/.travis.yml
generated
vendored
Normal file
@ -0,0 +1,4 @@
|
||||
language: node_js
|
||||
node_js:
|
||||
- "0.10"
|
||||
- "0.11"
|
43
node_modules/urlgrey/Makefile
generated
vendored
Normal file
43
node_modules/urlgrey/Makefile
generated
vendored
Normal file
@ -0,0 +1,43 @@
|
||||
REPORTER = spec
|
||||
|
||||
lint:
|
||||
./node_modules/.bin/jshint ./test ./index.js ./util.js
|
||||
|
||||
browser-test:
|
||||
$(MAKE) browser-build
|
||||
gnome-open test.html
|
||||
|
||||
browser-build-min:
|
||||
@rm -f urlgrey.min.js
|
||||
@./node_modules/.bin/browserify index.js \
|
||||
-s urlgrey | \
|
||||
./node_modules/.bin/uglifyjs > urlgrey.min.js
|
||||
|
||||
browser-build:
|
||||
@rm -f urlgrey.js
|
||||
@./node_modules/.bin/browserify index.js \
|
||||
-s urlgrey > urlgrey.js
|
||||
|
||||
precommit:
|
||||
$(MAKE) test
|
||||
$(MAKE) browser-build
|
||||
$(MAKE) browser-build-min
|
||||
echo "Artifacts built!"
|
||||
|
||||
test:
|
||||
$(MAKE) lint
|
||||
@NODE_ENV=test ./node_modules/.bin/mocha -b --reporter $(REPORTER)
|
||||
|
||||
test-cov:
|
||||
$(MAKE) lint
|
||||
@NODE_ENV=test ./node_modules/.bin/istanbul cover \
|
||||
./node_modules/mocha/bin/_mocha -- -R spec
|
||||
|
||||
test-coveralls:
|
||||
echo TRAVIS_JOB_ID $(TRAVIS_JOB_ID)
|
||||
$(MAKE) test
|
||||
@NODE_ENV=test ./node_modules/.bin/istanbul cover \
|
||||
./node_modules/mocha/bin/_mocha --report lcovonly -- -R spec && \
|
||||
cat ./coverage/lcov.info | ./node_modules/coveralls/bin/coveralls.js || true
|
||||
|
||||
.PHONY: test
|
221
node_modules/urlgrey/README.md
generated
vendored
Normal file
221
node_modules/urlgrey/README.md
generated
vendored
Normal file
@ -0,0 +1,221 @@
|
||||

|
||||
|
||||
|
||||
[](https://travis-ci.org/cainus/urlgrey)
|
||||
[](https://coveralls.io/r/cainus/urlgrey)
|
||||
[](http://badge.fury.io/js/urlgrey)
|
||||
|
||||
[](http://ci.testling.com/cainus/urlgrey)
|
||||
|
||||
Urlgrey is a library for url manipulation. It's got a chainable/fluent interface
|
||||
that makes a number of methods available for querying different aspects of a url,
|
||||
and even modifying it to create new urls.
|
||||
|
||||
Most methods are named after different parts of the url and allow you to read that part from the
|
||||
current url if you don't pass any parameters, or they allow you to generate a new url with a
|
||||
change to that part in the current url if you do pass a parameter.
|
||||
|
||||
For the examples below, we'll use the following url:
|
||||
```
|
||||
https://user:pass@subdomain.asdf.com/path/kid?asdf=1234#frag
|
||||
```
|
||||
|
||||
To create a new urlgrey object, just pass a url to urlgrey like so:
|
||||
```javascript
|
||||
var url = urlgrey("https://user:pass@subdomain.asdf.com/path/kid?asdf=1234#frag")
|
||||
```
|
||||
|
||||
##API specifics:
|
||||
|
||||
###url.child([lastPart])
|
||||
|
||||
Setter/getter for the last part of a path:
|
||||
```javascript
|
||||
url.child(); // returns "kid"
|
||||
url.child("grandkid"); // returns a new uri object with the uri
|
||||
// https://user:pass@subdomain.asdf.com/path/kid/grandkid?asdf=1234#frag
|
||||
```
|
||||
###url.decode(encodedString);
|
||||
Returns the decoded version of the input string using node's standard querystring.unescape().
|
||||
```javascript
|
||||
url.decode('this%20is%20a%20test'); // returns "this is a test"
|
||||
```
|
||||
|
||||
###url.encode(unencodedString);
|
||||
Returns the encoded version of the input string using node's standard querystring.escape().
|
||||
```javascript
|
||||
url.encode('this is a test'); // returns 'this%20is%20a%20test'
|
||||
```
|
||||
|
||||
###url.hash([newHash])
|
||||
Setter/getter for the url fragment/anchor/hash of a path.
|
||||
```javascript
|
||||
url.hash(); // returns 'frag'
|
||||
url.hash("blah"); // returns a new uri object with the uri
|
||||
// https://user:pass@subdomain.asdf.com/path/kid/?asdf=1234#blah
|
||||
```
|
||||
###url.hostname([newHostname])
|
||||
Setter/getter for the url hostname.
|
||||
```javascript
|
||||
url.hostname(); // returns 'subdomain.asdf.com'
|
||||
url.hostname("geocities.com"); // returns a new uri object with the uri
|
||||
// https://user:pass@geocities.com/path/kid/?asdf=1234#frag
|
||||
```
|
||||
###url.parent();
|
||||
Get the parent URI of the current URI. (This property is read-only).
|
||||
```javascript
|
||||
url.parent(); // returns a new uri object with the uri
|
||||
// https://user:pass@subdomain.asdf.com/path/
|
||||
```
|
||||
|
||||
###url.password([newPassword]);
|
||||
Setter/getter for the password portion of the url.
|
||||
```javascript
|
||||
url.password(); // returns 'pass'
|
||||
url.password("newpass"); // returns a new uri object with the uri
|
||||
// https://user:newpass@subdomain.asdf.com/path/kid/?asdf=1234#frag
|
||||
```
|
||||
###url.extendedPath([string]);
|
||||
Setter/getter for the path, querystring and fragment portion of the url
|
||||
all at once.
|
||||
```javascript
|
||||
url.extendedPath(); // returns '/path/kid?asdf=1234#frag'
|
||||
url.extendedPath("/newpath?new=query#newfrag"); // returns a new uri object with the uri
|
||||
// https://user:newpass@subdomain.asdf.com/newpath?new=query#newfrag
|
||||
|
||||
```
|
||||
|
||||
###url.path([mixed]);
|
||||
Setter/getter for the path portion of the url.
|
||||
```javascript
|
||||
url.path(); // returns '/path/kid'
|
||||
url.path("newpath"); // returns a new uri object with the uri
|
||||
// https://user:newpass@subdomain.asdf.com/newpath
|
||||
|
||||
// ALSO, .path() can take arrays of strings as input as well:
|
||||
url.path(['qwer', '/asdf'], 'qwer/1234/', '/1234/');
|
||||
// this returns a new uri object with the uri
|
||||
// https://user:newpass@subdomain.asdf.com/qwer/asdf/qwer/1234/1234
|
||||
```
|
||||
|
||||
Note: changing the path will remove the querystring and hash, since they rarely make sense on a new path.
|
||||
|
||||
###url.port([newPort]);
|
||||
Setter/getter for the port portion of the url.
|
||||
```javascript
|
||||
url.port(); // returns 80
|
||||
url.port(8080); // returns a new uri object with the uri
|
||||
// https://user:pass@subdomain.asdf.com:8080/path/kid/?asdf=1234#frag
|
||||
```
|
||||
|
||||
|
||||
###url.protocol([newProtocol]);
|
||||
|
||||
|
||||
Setter/getter for the protocol portion of the url.
|
||||
```javascript
|
||||
url.protocol(); // returns 'https'
|
||||
url.protocol("http"); // returns a new uri object with the uri
|
||||
// http://user:pass@subdomain.asdf.com/path/kid/?asdf=1234#frag
|
||||
```
|
||||
|
||||
###url.query([mixed]);
|
||||
|
||||
Setter/getter for the querystring using javascript objects.
|
||||
```javascript
|
||||
url.query(); // returns {asdf : 1234}
|
||||
url.query(false); // returns a new uri object with the querystring-free uri
|
||||
// https://user:pass@subdomain.asdf.com/path/kid#frag
|
||||
url.query({spaced : 'space test'})
|
||||
// returns a new uri object with the input object serialized
|
||||
// and merged into the querystring like so:
|
||||
// https://user:pass@subdomain.asdf.com/path/kid/?asdf=1234&spaced=space%20test#frag
|
||||
```
|
||||
|
||||
NOTE: escaping and unescaping of applicable characters happens automatically. (eg " " to "%20", and vice versa)
|
||||
|
||||
NOTE: an input object will overwrite an existing querystring where they have the same names.
|
||||
|
||||
NOTE: an input object will remove an existing name-value pair where they have the same names and the value in the input name-value pair is null.
|
||||
|
||||
|
||||
###url.queryString([newQueryString]);
|
||||
|
||||
Setter/getter for the querystring using a plain string representation. This is lower-level than .query(), but allows complete control of the querystring.
|
||||
```javascript
|
||||
url.queryString(); // returns asdf=1234 (notice there is no leading '?')
|
||||
url.queryString("blah"); // returns a new uri object with a new querystring
|
||||
// https://user:pass@subdomain.asdf.com/path/kid?blah#frag
|
||||
```
|
||||
|
||||
NOTE: no escaping/unescaping of applicable characters will occur. This must be done manually.
|
||||
|
||||
###url.rawChild();
|
||||
|
||||
This method is the same as url.child() but does not automatically url-encode
|
||||
any part of the input.
|
||||
|
||||
###url.rawPath();
|
||||
This method is the same as url.path() but does not automatically url-encode
|
||||
any part of the path.
|
||||
|
||||
###url.rawQuery();
|
||||
This method is the same as url.query() but does not automatically url-encode
|
||||
any of the keys or values in an input object.
|
||||
|
||||
|
||||
###url.toJson();
|
||||
Returns the json representation of the uri object, which is simply the uri as a string. The output is exactly the same as .toString(). This method is read-only.
|
||||
```javascript
|
||||
url.toJson(); // returns "https://user:pass@subdomain.asdf.com/path/kid/?asdf=1234#frag"
|
||||
```
|
||||
|
||||
###url.toString();
|
||||
Returns the string representation of the uri object, which is simply the uri as a string. This method is read-only.
|
||||
```javascript
|
||||
url.toString(); // returns "https://user:pass@subdomain.asdf.com/path/kid/?asdf=1234#frag"
|
||||
```
|
||||
|
||||
###url.username([newUsername])
|
||||
Setter/getter for the username portion of the url.
|
||||
```javascript
|
||||
url.username(); // returns 'user'
|
||||
url.username("newuser"); // returns a new uri object with the
|
||||
// uri https://newuser:pass@subdomain.asdf.com/path/kid/?asdf=1234#frag
|
||||
```
|
||||
|
||||
##Installation:
|
||||
### node.js:
|
||||
`npm install urlgrey --save`
|
||||
|
||||
Also! If you're using urlgrey in an http application, see [urlgrey-connect](https://github.com/cainus/urlgrey-connect). It gives you an urlgrey object already instantiated with the request url as req.uri in all your request handlers.
|
||||
### in the browser:
|
||||
Lots of options:
|
||||
* grab urlgrey.js from the root of this repo for [browserify](http://browserify.org/)-built, unminified version.
|
||||
* grab urlgrey.min.js from the root of this repo for a [browserify](http://browserify.org/)-built, minified version.
|
||||
* use [browserify](http://browserify.org/) and include this like any other node package.
|
||||
|
||||
|
||||
##Contributing:
|
||||
###Testing:
|
||||
####Run the node tests:
|
||||
* `make test`
|
||||
|
||||
####Run the browser file:// tests:
|
||||
* `make browser-build`
|
||||
* ...then open test.html in a browser
|
||||
|
||||
####Run the browser tests on a real server:
|
||||
* `make browser-build`
|
||||
* `python -m SimpleHTTPServer 9999`
|
||||
* ...then open http://localhost://9999/test.html in a browser
|
||||
|
||||
###Building before committing
|
||||
* `make precommit`
|
||||
|
||||
###Running node tests with a coverage report
|
||||
* `make test-cov`
|
||||
|
||||
|
||||
|
||||
|
4613
node_modules/urlgrey/browser/chai.js
generated
vendored
Normal file
4613
node_modules/urlgrey/browser/chai.js
generated
vendored
Normal file
File diff suppressed because it is too large
Load Diff
270
node_modules/urlgrey/browser/mocha.css
generated
vendored
Normal file
270
node_modules/urlgrey/browser/mocha.css
generated
vendored
Normal file
@ -0,0 +1,270 @@
|
||||
@charset "utf-8";
|
||||
|
||||
body {
|
||||
margin:0;
|
||||
}
|
||||
|
||||
#mocha {
|
||||
font: 20px/1.5 "Helvetica Neue", Helvetica, Arial, sans-serif;
|
||||
margin: 60px 50px;
|
||||
}
|
||||
|
||||
#mocha ul,
|
||||
#mocha li {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
#mocha ul {
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
#mocha h1,
|
||||
#mocha h2 {
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
#mocha h1 {
|
||||
margin-top: 15px;
|
||||
font-size: 1em;
|
||||
font-weight: 200;
|
||||
}
|
||||
|
||||
#mocha h1 a {
|
||||
text-decoration: none;
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
#mocha h1 a:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
#mocha .suite .suite h1 {
|
||||
margin-top: 0;
|
||||
font-size: .8em;
|
||||
}
|
||||
|
||||
#mocha .hidden {
|
||||
display: none;
|
||||
}
|
||||
|
||||
#mocha h2 {
|
||||
font-size: 12px;
|
||||
font-weight: normal;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
#mocha .suite {
|
||||
margin-left: 15px;
|
||||
}
|
||||
|
||||
#mocha .test {
|
||||
margin-left: 15px;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
#mocha .test.pending:hover h2::after {
|
||||
content: '(pending)';
|
||||
font-family: arial, sans-serif;
|
||||
}
|
||||
|
||||
#mocha .test.pass.medium .duration {
|
||||
background: #c09853;
|
||||
}
|
||||
|
||||
#mocha .test.pass.slow .duration {
|
||||
background: #b94a48;
|
||||
}
|
||||
|
||||
#mocha .test.pass::before {
|
||||
content: '✓';
|
||||
font-size: 12px;
|
||||
display: block;
|
||||
float: left;
|
||||
margin-right: 5px;
|
||||
color: #00d6b2;
|
||||
}
|
||||
|
||||
#mocha .test.pass .duration {
|
||||
font-size: 9px;
|
||||
margin-left: 5px;
|
||||
padding: 2px 5px;
|
||||
color: #fff;
|
||||
-webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.2);
|
||||
-moz-box-shadow: inset 0 1px 1px rgba(0,0,0,.2);
|
||||
box-shadow: inset 0 1px 1px rgba(0,0,0,.2);
|
||||
-webkit-border-radius: 5px;
|
||||
-moz-border-radius: 5px;
|
||||
-ms-border-radius: 5px;
|
||||
-o-border-radius: 5px;
|
||||
border-radius: 5px;
|
||||
}
|
||||
|
||||
#mocha .test.pass.fast .duration {
|
||||
display: none;
|
||||
}
|
||||
|
||||
#mocha .test.pending {
|
||||
color: #0b97c4;
|
||||
}
|
||||
|
||||
#mocha .test.pending::before {
|
||||
content: '◦';
|
||||
color: #0b97c4;
|
||||
}
|
||||
|
||||
#mocha .test.fail {
|
||||
color: #c00;
|
||||
}
|
||||
|
||||
#mocha .test.fail pre {
|
||||
color: black;
|
||||
}
|
||||
|
||||
#mocha .test.fail::before {
|
||||
content: '✖';
|
||||
font-size: 12px;
|
||||
display: block;
|
||||
float: left;
|
||||
margin-right: 5px;
|
||||
color: #c00;
|
||||
}
|
||||
|
||||
#mocha .test pre.error {
|
||||
color: #c00;
|
||||
max-height: 300px;
|
||||
overflow: auto;
|
||||
}
|
||||
|
||||
/**
|
||||
* (1): approximate for browsers not supporting calc
|
||||
* (2): 42 = 2*15 + 2*10 + 2*1 (padding + margin + border)
|
||||
* ^^ seriously
|
||||
*/
|
||||
#mocha .test pre {
|
||||
display: block;
|
||||
float: left;
|
||||
clear: left;
|
||||
font: 12px/1.5 monaco, monospace;
|
||||
margin: 5px;
|
||||
padding: 15px;
|
||||
border: 1px solid #eee;
|
||||
max-width: 85%; /*(1)*/
|
||||
max-width: calc(100% - 42px); /*(2)*/
|
||||
word-wrap: break-word;
|
||||
border-bottom-color: #ddd;
|
||||
-webkit-border-radius: 3px;
|
||||
-webkit-box-shadow: 0 1px 3px #eee;
|
||||
-moz-border-radius: 3px;
|
||||
-moz-box-shadow: 0 1px 3px #eee;
|
||||
border-radius: 3px;
|
||||
}
|
||||
|
||||
#mocha .test h2 {
|
||||
position: relative;
|
||||
}
|
||||
|
||||
#mocha .test a.replay {
|
||||
position: absolute;
|
||||
top: 3px;
|
||||
right: 0;
|
||||
text-decoration: none;
|
||||
vertical-align: middle;
|
||||
display: block;
|
||||
width: 15px;
|
||||
height: 15px;
|
||||
line-height: 15px;
|
||||
text-align: center;
|
||||
background: #eee;
|
||||
font-size: 15px;
|
||||
-moz-border-radius: 15px;
|
||||
border-radius: 15px;
|
||||
-webkit-transition: opacity 200ms;
|
||||
-moz-transition: opacity 200ms;
|
||||
transition: opacity 200ms;
|
||||
opacity: 0.3;
|
||||
color: #888;
|
||||
}
|
||||
|
||||
#mocha .test:hover a.replay {
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
#mocha-report.pass .test.fail {
|
||||
display: none;
|
||||
}
|
||||
|
||||
#mocha-report.fail .test.pass {
|
||||
display: none;
|
||||
}
|
||||
|
||||
#mocha-report.pending .test.pass,
|
||||
#mocha-report.pending .test.fail {
|
||||
display: none;
|
||||
}
|
||||
#mocha-report.pending .test.pass.pending {
|
||||
display: block;
|
||||
}
|
||||
|
||||
#mocha-error {
|
||||
color: #c00;
|
||||
font-size: 1.5em;
|
||||
font-weight: 100;
|
||||
letter-spacing: 1px;
|
||||
}
|
||||
|
||||
#mocha-stats {
|
||||
position: fixed;
|
||||
top: 15px;
|
||||
right: 10px;
|
||||
font-size: 12px;
|
||||
margin: 0;
|
||||
color: #888;
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
#mocha-stats .progress {
|
||||
float: right;
|
||||
padding-top: 0;
|
||||
}
|
||||
|
||||
#mocha-stats em {
|
||||
color: black;
|
||||
}
|
||||
|
||||
#mocha-stats a {
|
||||
text-decoration: none;
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
#mocha-stats a:hover {
|
||||
border-bottom: 1px solid #eee;
|
||||
}
|
||||
|
||||
#mocha-stats li {
|
||||
display: inline-block;
|
||||
margin: 0 5px;
|
||||
list-style: none;
|
||||
padding-top: 11px;
|
||||
}
|
||||
|
||||
#mocha-stats canvas {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
}
|
||||
|
||||
#mocha code .comment { color: #ddd; }
|
||||
#mocha code .init { color: #2f6fad; }
|
||||
#mocha code .string { color: #5890ad; }
|
||||
#mocha code .keyword { color: #8a6343; }
|
||||
#mocha code .number { color: #2f6fad; }
|
||||
|
||||
@media screen and (max-device-width: 480px) {
|
||||
#mocha {
|
||||
margin: 60px 0px;
|
||||
}
|
||||
|
||||
#mocha #stats {
|
||||
position: absolute;
|
||||
}
|
||||
}
|
5598
node_modules/urlgrey/browser/mocha.js
generated
vendored
Normal file
5598
node_modules/urlgrey/browser/mocha.js
generated
vendored
Normal file
File diff suppressed because it is too large
Load Diff
147
node_modules/urlgrey/browser/querystring.js
generated
vendored
Normal file
147
node_modules/urlgrey/browser/querystring.js
generated
vendored
Normal file
@ -0,0 +1,147 @@
|
||||
// Copyright Joyent, Inc. and other Node contributors.
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the
|
||||
// "Software"), to deal in the Software without restriction, including
|
||||
// without limitation the rights to use, copy, modify, merge, publish,
|
||||
// distribute, sublicense, and/or sell copies of the Software, and to permit
|
||||
// persons to whom the Software is furnished to do so, subject to the
|
||||
// following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included
|
||||
// in all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN
|
||||
// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
|
||||
// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
|
||||
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
|
||||
// USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
|
||||
// Query String Utilities
|
||||
|
||||
var QueryString = exports;
|
||||
var isString = require('../util').isString;
|
||||
var isArray = require('../util').isArray;
|
||||
var isBoolean = require('../util').isBoolean;
|
||||
var isNumber = require('../util').isNumber;
|
||||
var isObject = require('../util').isObject;
|
||||
var isNull = require('../util').isNull;
|
||||
var keys = require('../util').keys;
|
||||
var map = require('../util').map;
|
||||
|
||||
// If obj.hasOwnProperty has been overridden, then calling
|
||||
// obj.hasOwnProperty(prop) will break.
|
||||
// See: https://github.com/joyent/node/issues/1707
|
||||
function hasOwnProperty(obj, prop) {
|
||||
return Object.prototype.hasOwnProperty.call(obj, prop);
|
||||
}
|
||||
|
||||
|
||||
function charCode(c) {
|
||||
return c.charCodeAt(0);
|
||||
}
|
||||
|
||||
QueryString.unescape = function(s) {
|
||||
return decodeURIComponent(s);
|
||||
};
|
||||
|
||||
|
||||
QueryString.escape = function(str) {
|
||||
return encodeURIComponent(str);
|
||||
};
|
||||
|
||||
var stringifyPrimitive = function(v) {
|
||||
if (isString(v))
|
||||
return v;
|
||||
if (isBoolean(v))
|
||||
return v ? 'true' : 'false';
|
||||
if (isNumber(v))
|
||||
return isFinite(v) ? v : '';
|
||||
return '';
|
||||
};
|
||||
|
||||
|
||||
QueryString.stringify = QueryString.encode = function(obj, sep, eq, name) {
|
||||
sep = sep || '&';
|
||||
eq = eq || '=';
|
||||
if (isNull(obj)) {
|
||||
obj = undefined;
|
||||
}
|
||||
|
||||
if (isObject(obj)) {
|
||||
return map(keys(obj), function(k) {
|
||||
var ks = QueryString.escape(stringifyPrimitive(k)) + eq;
|
||||
if (isArray(obj[k])) {
|
||||
return map(obj[k], function(v) {
|
||||
return ks + QueryString.escape(stringifyPrimitive(v));
|
||||
}).join(sep);
|
||||
} else {
|
||||
return ks + QueryString.escape(stringifyPrimitive(obj[k]));
|
||||
}
|
||||
}).join(sep);
|
||||
|
||||
}
|
||||
|
||||
if (!name) return '';
|
||||
return QueryString.escape(stringifyPrimitive(name)) + eq +
|
||||
QueryString.escape(stringifyPrimitive(obj));
|
||||
};
|
||||
|
||||
// Parse a key=val string.
|
||||
QueryString.parse = QueryString.decode = function(qs, sep, eq, options) {
|
||||
sep = sep || '&';
|
||||
eq = eq || '=';
|
||||
var obj = {};
|
||||
|
||||
if (!isString(qs) || qs.length === 0) {
|
||||
return obj;
|
||||
}
|
||||
|
||||
var regexp = /\+/g;
|
||||
qs = qs.split(sep);
|
||||
|
||||
var maxKeys = 1000;
|
||||
if (options && isNumber(options.maxKeys)) {
|
||||
maxKeys = options.maxKeys;
|
||||
}
|
||||
|
||||
var len = qs.length;
|
||||
// maxKeys <= 0 means that we should not limit keys count
|
||||
if (maxKeys > 0 && len > maxKeys) {
|
||||
len = maxKeys;
|
||||
}
|
||||
|
||||
for (var i = 0; i < len; ++i) {
|
||||
var x = qs[i].replace(regexp, '%20'),
|
||||
idx = x.indexOf(eq),
|
||||
kstr, vstr, k, v;
|
||||
|
||||
if (idx >= 0) {
|
||||
kstr = x.substr(0, idx);
|
||||
vstr = x.substr(idx + 1);
|
||||
} else {
|
||||
kstr = x;
|
||||
vstr = '';
|
||||
}
|
||||
|
||||
try {
|
||||
k = decodeURIComponent(kstr);
|
||||
v = decodeURIComponent(vstr);
|
||||
} catch (e) {
|
||||
k = QueryString.unescape(kstr, true);
|
||||
v = QueryString.unescape(vstr, true);
|
||||
}
|
||||
|
||||
if (!hasOwnProperty(obj, k)) {
|
||||
obj[k] = v;
|
||||
} else if (isArray(obj[k])) {
|
||||
obj[k].push(v);
|
||||
} else {
|
||||
obj[k] = [obj[k], v];
|
||||
}
|
||||
}
|
||||
|
||||
return obj;
|
||||
};
|
424
node_modules/urlgrey/browser/url.js
generated
vendored
Normal file
424
node_modules/urlgrey/browser/url.js
generated
vendored
Normal file
@ -0,0 +1,424 @@
|
||||
// Copyright Joyent, Inc. and other Node contributors.
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||
// copy of this software and associated documentation files (the
|
||||
// "Software"), to deal in the Software without restriction, including
|
||||
// without limitation the rights to use, copy, modify, merge, publish,
|
||||
// distribute, sublicense, and/or sell copies of the Software, and to permit
|
||||
// persons to whom the Software is furnished to do so, subject to the
|
||||
// following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included
|
||||
// in all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN
|
||||
// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
|
||||
// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
|
||||
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
|
||||
// USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
|
||||
var punycode = { encode : function (s) { return s; } };
|
||||
if (!String.prototype.trim) {
|
||||
String.prototype.trim = function () {
|
||||
return this.replace(/^\s+|\s+$/g, '');
|
||||
};
|
||||
}
|
||||
|
||||
var isObject = require('../util').isObject;
|
||||
var isString = require('../util').isString;
|
||||
var keys = require('../util').keys;
|
||||
var substr = require('../util').substr;
|
||||
|
||||
exports.parse = urlParse;
|
||||
exports.format = urlFormat;
|
||||
|
||||
exports.Url = Url;
|
||||
|
||||
function Url() {
|
||||
this.protocol = null;
|
||||
this.slashes = null;
|
||||
this.auth = null;
|
||||
this.host = null;
|
||||
this.port = null;
|
||||
this.hostname = null;
|
||||
this.hash = null;
|
||||
this.search = null;
|
||||
this.query = null;
|
||||
this.pathname = null;
|
||||
this.path = null;
|
||||
this.href = null;
|
||||
}
|
||||
|
||||
// Reference: RFC 3986, RFC 1808, RFC 2396
|
||||
|
||||
// define these here so at least they only have to be
|
||||
// compiled once on the first module load.
|
||||
var protocolPattern = /^([a-z0-9.+-]+:)/i,
|
||||
portPattern = /:[0-9]*$/,
|
||||
|
||||
// RFC 2396: characters reserved for delimiting URLs.
|
||||
// We actually just auto-escape these.
|
||||
delims = ['<', '>', '"', '`', ' ', '\r', '\n', '\t'],
|
||||
|
||||
// RFC 2396: characters not allowed for various reasons.
|
||||
unwise = ['{', '}', '|', '\\', '^', '`'].concat(delims),
|
||||
|
||||
// Allowed by RFCs, but cause of XSS attacks. Always escape these.
|
||||
autoEscape = ['\''].concat(unwise),
|
||||
// Characters that are never ever allowed in a hostname.
|
||||
// Note that any invalid chars are also handled, but these
|
||||
// are the ones that are *expected* to be seen, so we fast-path
|
||||
// them.
|
||||
nonHostChars = ['%', '/', '?', ';', '#'].concat(autoEscape),
|
||||
hostEndingChars = ['/', '?', '#'],
|
||||
hostnameMaxLen = 255,
|
||||
hostnamePartPattern = /^[a-z0-9A-Z_-]{0,63}$/,
|
||||
hostnamePartStart = /^([a-z0-9A-Z_-]{0,63})(.*)$/,
|
||||
// protocols that can allow "unsafe" and "unwise" chars.
|
||||
unsafeProtocol = {
|
||||
'javascript': true,
|
||||
'javascript:': true
|
||||
},
|
||||
// protocols that never have a hostname.
|
||||
hostlessProtocol = {
|
||||
'javascript': true,
|
||||
'javascript:': true
|
||||
},
|
||||
// protocols that always contain a // bit.
|
||||
slashedProtocol = {
|
||||
'http': true,
|
||||
'https': true,
|
||||
'ftp': true,
|
||||
'gopher': true,
|
||||
'file': true,
|
||||
'http:': true,
|
||||
'https:': true,
|
||||
'ftp:': true,
|
||||
'gopher:': true,
|
||||
'file:': true
|
||||
},
|
||||
querystring = require('querystring');
|
||||
|
||||
function urlParse(url, parseQueryString, slashesDenoteHost) {
|
||||
if (url && isObject(url) && url instanceof Url) return url;
|
||||
|
||||
var u = new Url();
|
||||
u.parse(url, parseQueryString, slashesDenoteHost);
|
||||
return u;
|
||||
}
|
||||
|
||||
Url.prototype.parse = function(url, parseQueryString, slashesDenoteHost) {
|
||||
if (!isString(url)) {
|
||||
throw new TypeError("Parameter 'url' must be a string, not " + typeof url);
|
||||
}
|
||||
|
||||
var rest = url;
|
||||
|
||||
// trim before proceeding.
|
||||
// This is to support parse stuff like " http://foo.com \n"
|
||||
rest = rest.trim();
|
||||
|
||||
var proto = protocolPattern.exec(rest);
|
||||
if (proto) {
|
||||
proto = proto[0];
|
||||
var lowerProto = proto.toLowerCase();
|
||||
this.protocol = lowerProto;
|
||||
rest = rest.substr(proto.length);
|
||||
}
|
||||
|
||||
// figure out if it's got a host
|
||||
// user@server is *always* interpreted as a hostname, and url
|
||||
// resolution will treat //foo/bar as host=foo,path=bar because that's
|
||||
// how the browser resolves relative URLs.
|
||||
var slashes;
|
||||
if (slashesDenoteHost || proto || rest.match(/^\/\/[^@\/]+@[^@\/]+/)) {
|
||||
slashes = rest.substr(0, 2) === '//';
|
||||
if (slashes && !(proto && hostlessProtocol[proto])) {
|
||||
rest = rest.substr(2);
|
||||
this.slashes = true;
|
||||
}
|
||||
}
|
||||
|
||||
if (!hostlessProtocol[proto] &&
|
||||
(slashes || (proto && !slashedProtocol[proto]))) {
|
||||
|
||||
// there's a hostname.
|
||||
// the first instance of /, ?, ;, or # ends the host.
|
||||
//
|
||||
// If there is an @ in the hostname, then non-host chars *are* allowed
|
||||
// to the left of the last @ sign, unless some host-ending character
|
||||
// comes *before* the @-sign.
|
||||
// URLs are obnoxious.
|
||||
//
|
||||
// ex:
|
||||
// http://a@b@c/ => user:a@b host:c
|
||||
// http://a@b?@c => user:a host:c path:/?@c
|
||||
|
||||
// v0.12 TODO(isaacs): This is not quite how Chrome does things.
|
||||
// Review our test case against browsers more comprehensively.
|
||||
|
||||
// find the first instance of any hostEndingChars
|
||||
var hostEnd = -1;
|
||||
for (var i = 0; i < hostEndingChars.length; i++) {
|
||||
var hec = rest.indexOf(hostEndingChars[i]);
|
||||
if (hec !== -1 && (hostEnd === -1 || hec < hostEnd))
|
||||
hostEnd = hec;
|
||||
}
|
||||
|
||||
// at this point, either we have an explicit point where the
|
||||
// auth portion cannot go past, or the last @ char is the decider.
|
||||
var auth, atSign;
|
||||
if (hostEnd === -1) {
|
||||
// atSign can be anywhere.
|
||||
atSign = rest.lastIndexOf('@');
|
||||
} else {
|
||||
// atSign must be in auth portion.
|
||||
// http://a@b/c@d => host:b auth:a path:/c@d
|
||||
atSign = rest.lastIndexOf('@', hostEnd);
|
||||
}
|
||||
|
||||
// Now we have a portion which is definitely the auth.
|
||||
// Pull that off.
|
||||
if (atSign !== -1) {
|
||||
auth = rest.slice(0, atSign);
|
||||
rest = rest.slice(atSign + 1);
|
||||
this.auth = decodeURIComponent(auth);
|
||||
}
|
||||
|
||||
// the host is the remaining to the left of the first non-host char
|
||||
hostEnd = -1;
|
||||
for (var i = 0; i < nonHostChars.length; i++) {
|
||||
var hec = rest.indexOf(nonHostChars[i]);
|
||||
if (hec !== -1 && (hostEnd === -1 || hec < hostEnd))
|
||||
hostEnd = hec;
|
||||
}
|
||||
// if we still have not hit it, then the entire thing is a host.
|
||||
if (hostEnd === -1)
|
||||
hostEnd = rest.length;
|
||||
|
||||
this.host = rest.slice(0, hostEnd);
|
||||
rest = rest.slice(hostEnd);
|
||||
|
||||
// pull out port.
|
||||
this.parseHost();
|
||||
|
||||
// we've indicated that there is a hostname,
|
||||
// so even if it's empty, it has to be present.
|
||||
this.hostname = this.hostname || '';
|
||||
|
||||
// if hostname begins with [ and ends with ]
|
||||
// assume that it's an IPv6 address.
|
||||
var ipv6Hostname = this.hostname[0] === '[' &&
|
||||
this.hostname[this.hostname.length - 1] === ']';
|
||||
|
||||
// validate a little.
|
||||
if (!ipv6Hostname) {
|
||||
var hostparts = this.hostname.split(/\./);
|
||||
for (var i = 0, l = hostparts.length; i < l; i++) {
|
||||
var part = hostparts[i];
|
||||
if (!part) continue;
|
||||
if (!part.match(hostnamePartPattern)) {
|
||||
var newpart = '';
|
||||
for (var j = 0, k = part.length; j < k; j++) {
|
||||
if (part.charCodeAt(j) > 127) {
|
||||
// we replace non-ASCII char with a temporary placeholder
|
||||
// we need this to make sure size of hostname is not
|
||||
// broken by replacing non-ASCII by nothing
|
||||
newpart += 'x';
|
||||
} else {
|
||||
newpart += part[j];
|
||||
}
|
||||
}
|
||||
// we test again with ASCII char only
|
||||
if (!newpart.match(hostnamePartPattern)) {
|
||||
var validParts = hostparts.slice(0, i);
|
||||
var notHost = hostparts.slice(i + 1);
|
||||
var bit = part.match(hostnamePartStart);
|
||||
if (bit) {
|
||||
validParts.push(bit[1]);
|
||||
notHost.unshift(bit[2]);
|
||||
}
|
||||
if (notHost.length) {
|
||||
rest = '/' + notHost.join('.') + rest;
|
||||
}
|
||||
this.hostname = validParts.join('.');
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (this.hostname.length > hostnameMaxLen) {
|
||||
this.hostname = '';
|
||||
} else {
|
||||
// hostnames are always lower case.
|
||||
this.hostname = this.hostname.toLowerCase();
|
||||
}
|
||||
|
||||
if (!ipv6Hostname) {
|
||||
// IDNA Support: Returns a puny coded representation of "domain".
|
||||
// It only converts the part of the domain name that
|
||||
// has non ASCII characters. I.e. it dosent matter if
|
||||
// you call it with a domain that already is in ASCII.
|
||||
var domainArray = this.hostname.split('.');
|
||||
var newOut = [];
|
||||
for (var i = 0; i < domainArray.length; ++i) {
|
||||
var s = domainArray[i];
|
||||
newOut.push(s.match(/[^A-Za-z0-9_-]/) ?
|
||||
'xn--' + punycode.encode(s) : s);
|
||||
}
|
||||
this.hostname = newOut.join('.');
|
||||
}
|
||||
|
||||
var p = this.port ? ':' + this.port : '';
|
||||
var h = this.hostname || '';
|
||||
this.host = h + p;
|
||||
this.href += this.host;
|
||||
|
||||
// strip [ and ] from the hostname
|
||||
// the host field still retains them, though
|
||||
if (ipv6Hostname) {
|
||||
this.hostname = this.hostname.substr(1, this.hostname.length - 2);
|
||||
if (rest[0] !== '/') {
|
||||
rest = '/' + rest;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// now rest is set to the post-host stuff.
|
||||
// chop off any delim chars.
|
||||
if (!unsafeProtocol[lowerProto]) {
|
||||
|
||||
// First, make 100% sure that any "autoEscape" chars get
|
||||
// escaped, even if encodeURIComponent doesn't think they
|
||||
// need to be.
|
||||
for (var i = 0, l = autoEscape.length; i < l; i++) {
|
||||
var ae = autoEscape[i];
|
||||
var esc = encodeURIComponent(ae);
|
||||
if (esc === ae) {
|
||||
esc = escape(ae);
|
||||
}
|
||||
rest = rest.split(ae).join(esc);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// chop off from the tail first.
|
||||
var hash = rest.indexOf('#');
|
||||
if (hash !== -1) {
|
||||
// got a fragment string.
|
||||
this.hash = rest.substr(hash);
|
||||
rest = rest.slice(0, hash);
|
||||
}
|
||||
var qm = rest.indexOf('?');
|
||||
if (qm !== -1) {
|
||||
this.search = rest.substr(qm);
|
||||
this.query = rest.substr(qm + 1);
|
||||
if (parseQueryString) {
|
||||
this.query = querystring.parse(this.query);
|
||||
}
|
||||
rest = rest.slice(0, qm);
|
||||
} else if (parseQueryString) {
|
||||
// no query string, but parseQueryString still requested
|
||||
this.search = '';
|
||||
this.query = {};
|
||||
}
|
||||
if (rest) this.pathname = rest;
|
||||
if (slashedProtocol[lowerProto] &&
|
||||
this.hostname && !this.pathname) {
|
||||
this.pathname = '/';
|
||||
}
|
||||
|
||||
//to support http.request
|
||||
if (this.pathname || this.search) {
|
||||
var p = this.pathname || '';
|
||||
var s = this.search || '';
|
||||
this.path = p + s;
|
||||
}
|
||||
|
||||
// finally, reconstruct the href based on what has been validated.
|
||||
this.href = this.format();
|
||||
return this;
|
||||
};
|
||||
|
||||
// format a parsed object into a url string
|
||||
function urlFormat(obj) {
|
||||
// ensure it's an object, and not a string url.
|
||||
// If it's an obj, this is a no-op.
|
||||
// this way, you can call url_format() on strings
|
||||
// to clean up potentially wonky urls.
|
||||
if (isString(obj)) obj = urlParse(obj);
|
||||
if (!(obj instanceof Url)) return Url.prototype.format.call(obj);
|
||||
return obj.format();
|
||||
}
|
||||
|
||||
Url.prototype.format = function() {
|
||||
var auth = this.auth || '';
|
||||
if (auth) {
|
||||
auth = encodeURIComponent(auth);
|
||||
auth = auth.replace(/%3A/i, ':');
|
||||
auth += '@';
|
||||
}
|
||||
|
||||
var protocol = this.protocol || '',
|
||||
pathname = this.pathname || '',
|
||||
hash = this.hash || '',
|
||||
host = false,
|
||||
query = '';
|
||||
|
||||
if (this.host) {
|
||||
host = auth + this.host;
|
||||
} else if (this.hostname) {
|
||||
host = auth + (this.hostname.indexOf(':') === -1 ?
|
||||
this.hostname :
|
||||
'[' + this.hostname + ']');
|
||||
if (this.port) {
|
||||
host += ':' + this.port;
|
||||
}
|
||||
}
|
||||
|
||||
if (this.query &&
|
||||
isObject(this.query) &&
|
||||
keys(this.query).length) {
|
||||
query = querystring.stringify(this.query);
|
||||
}
|
||||
|
||||
var search = this.search || (query && ('?' + query)) || '';
|
||||
|
||||
if (protocol && substr(protocol, -1) !== ':') protocol += ':';
|
||||
|
||||
// only the slashedProtocols get the //. Not mailto:, xmpp:, etc.
|
||||
// unless they had them to begin with.
|
||||
if (this.slashes ||
|
||||
(!protocol || slashedProtocol[protocol]) && host !== false) {
|
||||
host = '//' + (host || '');
|
||||
if (pathname && pathname.charAt(0) !== '/') pathname = '/' + pathname;
|
||||
} else if (!host) {
|
||||
host = '';
|
||||
}
|
||||
|
||||
if (hash && hash.charAt(0) !== '#') hash = '#' + hash;
|
||||
if (search && search.charAt(0) !== '?') search = '?' + search;
|
||||
|
||||
pathname = pathname.replace(/[?#]/g, function(match) {
|
||||
return encodeURIComponent(match);
|
||||
});
|
||||
search = search.replace('#', '%23');
|
||||
|
||||
return protocol + host + pathname + search + hash;
|
||||
};
|
||||
|
||||
Url.prototype.parseHost = function() {
|
||||
var host = this.host;
|
||||
var port = portPattern.exec(host);
|
||||
if (port) {
|
||||
port = port[0];
|
||||
if (port !== ':') {
|
||||
this.port = port.substr(1);
|
||||
}
|
||||
host = host.substr(0, host.length - port.length);
|
||||
}
|
||||
if (host) this.hostname = host;
|
||||
};
|
443
node_modules/urlgrey/index.js
generated
vendored
Normal file
443
node_modules/urlgrey/index.js
generated
vendored
Normal file
@ -0,0 +1,443 @@
|
||||
var urlParse = require('url').parse;
|
||||
var querystring = require('querystring');
|
||||
var isBrowser = (typeof window !== "undefined");
|
||||
|
||||
var getDefaults = function(){
|
||||
var defaultUrl = "http://localhost:80";
|
||||
if (isBrowser){
|
||||
defaultUrl = window.location.href.toString();
|
||||
}
|
||||
var defaults = urlParse(defaultUrl);
|
||||
return defaults;
|
||||
};
|
||||
|
||||
if (!Array.isArray) {
|
||||
Array.isArray = function (arg) {
|
||||
return Object.prototype.toString.call(arg) === '[object Array]';
|
||||
};
|
||||
}
|
||||
|
||||
var objectEach = function(obj, cb){
|
||||
for (var k in obj){
|
||||
if (Object.prototype.hasOwnProperty.call(obj, k)) {
|
||||
cb(obj[k], k);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
var argsArray = function(obj){
|
||||
if (!obj) { return []; }
|
||||
if (Array.isArray(obj)) { return obj.slice() ; }
|
||||
var args = [];
|
||||
objectEach(obj, function(v, k){
|
||||
args[k] = v;
|
||||
});
|
||||
return args;
|
||||
};
|
||||
|
||||
var arrLast = function(arr){
|
||||
return arr[arr.length-1];
|
||||
};
|
||||
|
||||
var arrFlatten = function(input, output) {
|
||||
if (!output) { output = []; }
|
||||
for (var i = 0; i < input.length; i++){
|
||||
var value = input[i];
|
||||
if (Array.isArray(value)) {
|
||||
arrFlatten(value, output);
|
||||
} else {
|
||||
output.push(value);
|
||||
}
|
||||
}
|
||||
return output;
|
||||
};
|
||||
|
||||
|
||||
var UrlGrey = function(url){
|
||||
if (!url && isBrowser){
|
||||
url = window.location.href.toString();
|
||||
}
|
||||
this.url = url;
|
||||
this._parsed = null;
|
||||
};
|
||||
|
||||
UrlGrey.prototype.parsed = function(){
|
||||
if (!this._parsed){
|
||||
this._parsed = urlParse(this.url);
|
||||
var defaults = getDefaults();
|
||||
var p = this._parsed;
|
||||
p.protocol = p.protocol || defaults.protocol;
|
||||
p.protocol = p.protocol.slice(0,-1);
|
||||
if (p.hash){
|
||||
p.hash = p.hash.substring(1);
|
||||
}
|
||||
p.username = '';
|
||||
p.password = '';
|
||||
if (p.protocol !== 'file'){
|
||||
p.port = parseInt(p.port, 10);
|
||||
if (p.auth){
|
||||
var auth = p.auth.split(':');
|
||||
p.username = auth[0];
|
||||
p.password = auth[1];
|
||||
}
|
||||
}
|
||||
if (isBrowser){
|
||||
p.hostname = p.hostname || defaults.hostname;
|
||||
}
|
||||
}
|
||||
|
||||
// enforce only returning these properties
|
||||
this._parsed = {
|
||||
protocol : this._parsed.protocol,
|
||||
auth: this._parsed.auth,
|
||||
host: this._parsed.host,
|
||||
port: this._parsed.port,
|
||||
hostname: this._parsed.hostname,
|
||||
hash: this._parsed.hash,
|
||||
search: this._parsed.search,
|
||||
query: this._parsed.query,
|
||||
pathname: this._parsed.pathname,
|
||||
path: this._parsed.path,
|
||||
href: this._parsed.href,
|
||||
username: this._parsed.username,
|
||||
password: this._parsed.password
|
||||
};
|
||||
|
||||
|
||||
return this._parsed;
|
||||
};
|
||||
|
||||
|
||||
UrlGrey.prototype.extendedPath = function(url){
|
||||
if (url){
|
||||
var p = urlParse(url);
|
||||
var obj = new UrlGrey(this.toString());
|
||||
if (p.hash){
|
||||
p.hash = p.hash.substring(1);
|
||||
}
|
||||
obj.parsed().hash = p.hash;
|
||||
obj.parsed().query = p.query;
|
||||
obj = obj.path(p.pathname);
|
||||
return obj;
|
||||
} else {
|
||||
var href = this.path();
|
||||
href += this.queryString() ? '?' + this.queryString() : '';
|
||||
href += this.hash() ? '#' + this.hash() : '';
|
||||
return href;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
UrlGrey.prototype.port = function(num){
|
||||
var hostname = this.parsed().hostname;
|
||||
|
||||
// setter
|
||||
if (num){
|
||||
if (this.protocol() === 'file'){
|
||||
throw new Error("file urls don't have ports");
|
||||
}
|
||||
var obj = new UrlGrey(this.toString());
|
||||
obj.parsed().port = parseInt(num, 10);
|
||||
return obj;
|
||||
}
|
||||
|
||||
// getter
|
||||
var output = this._parsed.port;
|
||||
if (!output){
|
||||
switch(this.protocol()){
|
||||
case 'http' : return 80;
|
||||
case 'https' : return 443;
|
||||
default : return null;
|
||||
}
|
||||
}
|
||||
return parseInt(output, 10);
|
||||
};
|
||||
|
||||
UrlGrey.prototype.query = function(mergeObject){
|
||||
if (arguments.length === 0) {
|
||||
return querystring.parse(this.queryString());
|
||||
} else if (mergeObject === null || mergeObject === false){
|
||||
return this.queryString('');
|
||||
} else {
|
||||
// read the object out
|
||||
var oldQuery = querystring.parse(this.queryString());
|
||||
objectEach(mergeObject, function(v, k){
|
||||
if (v === null || v === false){
|
||||
delete oldQuery[k];
|
||||
} else {
|
||||
oldQuery[k] = v;
|
||||
}
|
||||
});
|
||||
var newString = querystring.stringify(oldQuery);
|
||||
var ret = this.queryString(newString);
|
||||
return ret;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
UrlGrey.prototype.rawQuery = function(mergeObject){
|
||||
if (arguments.length === 0) {
|
||||
if (this.queryString().length === 0) { return {}; }
|
||||
|
||||
return this.queryString().split("&").reduce(function(obj, pair) {
|
||||
pair = pair.split("=");
|
||||
var key = pair[0];
|
||||
var val = pair[1];
|
||||
obj[key] = val;
|
||||
return obj;
|
||||
}, {});
|
||||
} else if (mergeObject === null || mergeObject === false){
|
||||
return this.queryString('');
|
||||
} else {
|
||||
// read the object out
|
||||
var oldQuery = querystring.parse(this.queryString());
|
||||
objectEach(mergeObject, function(v, k){
|
||||
if (v === null){
|
||||
delete oldQuery[k];
|
||||
} else {
|
||||
oldQuery[k] = v;
|
||||
}
|
||||
});
|
||||
var pairs = [];
|
||||
objectEach(oldQuery, function(v, k){
|
||||
pairs.push(k + '=' + v);
|
||||
});
|
||||
var newString = pairs.join('&');
|
||||
|
||||
return this.queryString(newString);
|
||||
}
|
||||
};
|
||||
|
||||
addPropertyGetterSetter('protocol');
|
||||
addPropertyGetterSetter('username');
|
||||
addPropertyGetterSetter('password');
|
||||
addPropertyGetterSetter('hostname');
|
||||
addPropertyGetterSetter('hash');
|
||||
// add a method called queryString that manipulates 'query'
|
||||
addPropertyGetterSetter('query', 'queryString');
|
||||
addPropertyGetterSetter('pathname', 'path');
|
||||
|
||||
UrlGrey.prototype.path = function(){
|
||||
var args = arrFlatten(argsArray(arguments));
|
||||
if (args.length !== 0){
|
||||
var obj = new UrlGrey(this.toString());
|
||||
var str = args.join('/');
|
||||
str = str.replace(/\/+/g, '/'); // remove double slashes
|
||||
str = str.replace(/\/$/, ''); // remove all trailing slashes
|
||||
args = str.split('/');
|
||||
for(var i = 0; i < args.length; i++){
|
||||
args[i] = this.encode(args[i]);
|
||||
}
|
||||
str = args.join('/');
|
||||
if (str[0] !== '/'){ str = '/' + str; }
|
||||
obj.parsed().pathname = str;
|
||||
return obj;
|
||||
}
|
||||
return this.parsed().pathname;
|
||||
};
|
||||
|
||||
UrlGrey.prototype.rawPath = function(){
|
||||
var args = arrFlatten(argsArray(arguments));
|
||||
if (args.length !== 0){
|
||||
var obj = new UrlGrey(this.toString());
|
||||
var str = args.join('/');
|
||||
str = str.replace(/\/+/g, '/'); // remove double slashes
|
||||
str = str.replace(/\/$/, ''); // remove all trailing slashes
|
||||
if (str[0] !== '/'){ str = '/' + str; }
|
||||
obj.parsed().pathname = str;
|
||||
return obj;
|
||||
}
|
||||
return this.parsed().pathname;
|
||||
};
|
||||
|
||||
UrlGrey.prototype.encode = function(str){
|
||||
try {
|
||||
return encodeURIComponent(str);
|
||||
} catch (ex) {
|
||||
return querystring.escape(str);
|
||||
}
|
||||
};
|
||||
|
||||
UrlGrey.prototype.decode = function(str){
|
||||
return decode(str);
|
||||
};
|
||||
|
||||
UrlGrey.prototype.parent = function(){
|
||||
// read-only. (can't SET parent)
|
||||
var pieces = this.path().split("/");
|
||||
var popped = pieces.pop();
|
||||
if (popped === ''){ // ignore trailing slash
|
||||
popped = pieces.pop();
|
||||
}
|
||||
if (!popped){
|
||||
throw new Error("The current path has no parent path");
|
||||
}
|
||||
return this.query(false).hash('').path(pieces.join("/"));
|
||||
};
|
||||
|
||||
UrlGrey.prototype.rawChild = function(suffixes){
|
||||
if (suffixes){
|
||||
suffixes = argsArray(arguments);
|
||||
return this.query(false).hash('').rawPath(this.path(), suffixes);
|
||||
} else {
|
||||
// if no suffix, return the child
|
||||
var pieces = this.path().split("/");
|
||||
var last = arrLast(pieces);
|
||||
if ((pieces.length > 1) && (last === '')){
|
||||
// ignore trailing slashes
|
||||
pieces.pop();
|
||||
last = arrLast(pieces);
|
||||
}
|
||||
return last;
|
||||
}
|
||||
};
|
||||
|
||||
UrlGrey.prototype.child = function(suffixes){
|
||||
suffixes = argsArray(arguments);
|
||||
if (suffixes.length > 0){
|
||||
return this.query(false).hash('').path(this.path(), suffixes);
|
||||
}
|
||||
|
||||
// if no suffix, return the child
|
||||
var pieces = pathPieces(this.path());
|
||||
var last = arrLast(pieces);
|
||||
if ((pieces.length > 1) && (last === '')){
|
||||
// ignore trailing slashes
|
||||
pieces.pop();
|
||||
last = arrLast(pieces);
|
||||
}
|
||||
return last;
|
||||
};
|
||||
|
||||
UrlGrey.prototype.toJSON = function(){
|
||||
return this.toString();
|
||||
};
|
||||
|
||||
UrlGrey.prototype.toString = function(){
|
||||
var p = this.parsed();
|
||||
var retval = this.protocol() + '://';
|
||||
if (this.protocol() !== 'file'){
|
||||
var userinfo = p.username + ':' + p.password;
|
||||
if (userinfo !== ':'){
|
||||
retval += userinfo + '@';
|
||||
}
|
||||
retval += p.hostname;
|
||||
var port = portString(this);
|
||||
if (port !== ''){
|
||||
retval += ':' + port;
|
||||
}
|
||||
}
|
||||
retval += this.path() === '/' ? '' : this.path();
|
||||
var qs = this.queryString();
|
||||
if (qs){
|
||||
retval += '?' + qs;
|
||||
}
|
||||
if (p.hash){
|
||||
retval += '#' + p.hash;
|
||||
}
|
||||
return retval;
|
||||
};
|
||||
|
||||
var pathPieces = function(path){
|
||||
var pieces = path.split('/');
|
||||
for(var i = 0; i < pieces.length; i++){
|
||||
pieces[i] = decode(pieces[i]);
|
||||
}
|
||||
return pieces;
|
||||
};
|
||||
|
||||
var decode = function(str){
|
||||
try {
|
||||
return decodeURIComponent(str);
|
||||
} catch (ex) {
|
||||
return querystring.unescape(str);
|
||||
}
|
||||
};
|
||||
|
||||
var portString = function(o){
|
||||
if (o.protocol() === 'https'){
|
||||
if (o.port() === 443){
|
||||
return '';
|
||||
}
|
||||
}
|
||||
if (o.protocol() === 'http'){
|
||||
if (o.port() === 80){
|
||||
return '';
|
||||
}
|
||||
}
|
||||
return '' + o.port();
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
UrlGrey.prototype.absolute = function(path){
|
||||
if (path[0] == '/'){
|
||||
path = path.substring(1);
|
||||
}
|
||||
var parsed = urlParse(path);
|
||||
if (!!parsed.protocol){ // if it's already absolute, just return it
|
||||
return path;
|
||||
}
|
||||
return this._protocol + "://" + this._host + '/' + path;
|
||||
};
|
||||
|
||||
// TODO make this interpolate vars into the url. both sinatra style and url-tempates
|
||||
// TODO name this:
|
||||
UrlGrey.prototype.get = function(nameOrPath, varDict){
|
||||
if (!!nameOrPath){
|
||||
if (!!varDict){
|
||||
return this.absolute(this._router.getUrl(nameOrPath, varDict));
|
||||
}
|
||||
return this.absolute(this._router.getUrl(nameOrPath));
|
||||
}
|
||||
return this.url;
|
||||
};*/
|
||||
|
||||
/*
|
||||
// TODO needs to take a template as an input
|
||||
UrlGrey.prototype.param = function(key, defaultValue){
|
||||
var value = this.params()[key];
|
||||
if (!!value) {
|
||||
return value;
|
||||
}
|
||||
return defaultValue;
|
||||
};
|
||||
|
||||
// TODO extract params, given a template?
|
||||
// TODO needs to take a template as an input
|
||||
UrlGrey.prototype.params = function(inUrl){
|
||||
if (!!inUrl){
|
||||
return this._router.pathVariables(inUrl);
|
||||
}
|
||||
if (!!this._params){
|
||||
return this._params;
|
||||
}
|
||||
return this._router.pathVariables(this.url);
|
||||
};
|
||||
*/
|
||||
|
||||
// TODO relative() // takes an absolutepath and returns a relative one
|
||||
// TODO absolute() // takes a relative path and returns an absolute one.
|
||||
|
||||
|
||||
|
||||
module.exports = function(url){ return new UrlGrey(url); };
|
||||
|
||||
function addPropertyGetterSetter(propertyName, methodName){
|
||||
if (!methodName){
|
||||
methodName = propertyName;
|
||||
}
|
||||
UrlGrey.prototype[methodName] = function(str){
|
||||
if (!str && str !== "") {
|
||||
return this.parsed()[propertyName];
|
||||
} else {
|
||||
var obj = new UrlGrey(this.toString());
|
||||
obj.parsed()[propertyName] = str;
|
||||
return obj;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
99
node_modules/urlgrey/package.json
generated
vendored
Normal file
99
node_modules/urlgrey/package.json
generated
vendored
Normal file
@ -0,0 +1,99 @@
|
||||
{
|
||||
"_args": [
|
||||
[
|
||||
"urlgrey@0.4.4",
|
||||
"E:\\python\\setup-php"
|
||||
]
|
||||
],
|
||||
"_from": "urlgrey@0.4.4",
|
||||
"_id": "urlgrey@0.4.4",
|
||||
"_inBundle": false,
|
||||
"_integrity": "sha1-iS/pWWCAXoVRnxzUOJ8stMu3ZS8=",
|
||||
"_location": "/urlgrey",
|
||||
"_phantomChildren": {},
|
||||
"_requested": {
|
||||
"type": "version",
|
||||
"registry": true,
|
||||
"raw": "urlgrey@0.4.4",
|
||||
"name": "urlgrey",
|
||||
"escapedName": "urlgrey",
|
||||
"rawSpec": "0.4.4",
|
||||
"saveSpec": null,
|
||||
"fetchSpec": "0.4.4"
|
||||
},
|
||||
"_requiredBy": [
|
||||
"/codecov"
|
||||
],
|
||||
"_resolved": "https://registry.npmjs.org/urlgrey/-/urlgrey-0.4.4.tgz",
|
||||
"_spec": "0.4.4",
|
||||
"_where": "E:\\python\\setup-php",
|
||||
"author": {
|
||||
"name": "Gregg Caines"
|
||||
},
|
||||
"browser": {
|
||||
"url": "./browser/url.js",
|
||||
"querystring": "./browser/querystring.js"
|
||||
},
|
||||
"bugs": {
|
||||
"url": "https://github.com/cainus/urlgrey/issues"
|
||||
},
|
||||
"dependencies": {},
|
||||
"description": "urlgrey is a library for url querying and manipulation",
|
||||
"devDependencies": {
|
||||
"browserify": "2.35.2",
|
||||
"chai": "1.8.1",
|
||||
"coveralls": "2.5.0",
|
||||
"istanbul": "0.1.45",
|
||||
"jscoverage": "0.3.6",
|
||||
"jshint": "2.3.0",
|
||||
"mocha": "1.8.1",
|
||||
"mocha-lcov-reporter": "0.0.1",
|
||||
"tape": "2.3.0",
|
||||
"uglify-js": "2.4.3"
|
||||
},
|
||||
"directories": {
|
||||
"test": "test"
|
||||
},
|
||||
"engine": {
|
||||
"node": ">=0.8.6"
|
||||
},
|
||||
"homepage": "https://github.com/cainus/urlgrey#readme",
|
||||
"keywords": [
|
||||
"url",
|
||||
"uri"
|
||||
],
|
||||
"license": "BSD-2-Clause",
|
||||
"main": "index.js",
|
||||
"maintainers": [
|
||||
{
|
||||
"name": "Gregg Caines",
|
||||
"email": "gregg@caines.ca",
|
||||
"url": "http://caines.ca"
|
||||
}
|
||||
],
|
||||
"name": "urlgrey",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "git://github.com/cainus/urlgrey.git"
|
||||
},
|
||||
"scripts": {
|
||||
"test": "make test-coveralls"
|
||||
},
|
||||
"testling": {
|
||||
"browsers": [
|
||||
"ie10",
|
||||
"ie11",
|
||||
"firefox/nightly",
|
||||
"firefox/25",
|
||||
"firefox/8",
|
||||
"chrome/6",
|
||||
"chrome/18",
|
||||
"chrome/31",
|
||||
"chrome/canary",
|
||||
"opera/17"
|
||||
],
|
||||
"harness": "mocha",
|
||||
"files": "test/index.js"
|
||||
},
|
||||
"version": "0.4.4"
|
||||
}
|
543
node_modules/urlgrey/tapetest.js
generated
vendored
Normal file
543
node_modules/urlgrey/tapetest.js
generated
vendored
Normal file
@ -0,0 +1,543 @@
|
||||
var test = require('tape');
|
||||
|
||||
var tapetest = function(){
|
||||
var isBrowser = !(typeof module !== 'undefined' && module.exports);
|
||||
if (!isBrowser){
|
||||
var urlgrey = require('./index');
|
||||
}
|
||||
|
||||
test('chaining always produces a new object and leaves the original unaffected',
|
||||
function (t) {
|
||||
t.plan(2);
|
||||
// doesn't over-write the original url
|
||||
var urlStr = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
var url = urlgrey(urlStr);
|
||||
t.equal(
|
||||
url.hostname('asdf.com').toString(),
|
||||
"https://user:pass@asdf.com/path?asdf=1234#frag"
|
||||
);
|
||||
url.port(8080);
|
||||
url.protocol('http');
|
||||
url.username('http');
|
||||
url.password('http');
|
||||
url.path('http');
|
||||
url.hash('http');
|
||||
url.queryString('http=1234');
|
||||
url.query(false);
|
||||
url.extendedPath("/asdf?qwer=asdf#swqertwert23");
|
||||
t.equal(
|
||||
url.toString(),
|
||||
urlStr
|
||||
); // original object is unmodified
|
||||
});
|
||||
|
||||
|
||||
test('toJSON() returns the same thing as toString', function(t){
|
||||
t.plan(2);
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).toJSON(),
|
||||
urlgrey(url).toString()
|
||||
);
|
||||
t.equal(
|
||||
'https://user:pass@subdomain.asdf.com/path?asdf=1234#frag',
|
||||
urlgrey(url).toString()
|
||||
);
|
||||
});
|
||||
|
||||
|
||||
test('hostname() gets the hostname', function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).hostname(),
|
||||
'subdomain.asdf.com'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
if (isBrowser){
|
||||
test("hostname() gets the hostname even if unset", function(t){
|
||||
t.plan(1);
|
||||
var url = "/path?asdf=1234#frag";
|
||||
var u = urlgrey(url);
|
||||
if (u.protocol() === 'file'){
|
||||
// chrome uses localhost. other browsers don't
|
||||
t.ok(
|
||||
(u.hostname() === '') || (u.hostname() === 'localhost')
|
||||
);
|
||||
} else {
|
||||
t.equal(
|
||||
u.hostname(),
|
||||
window.location.hostname + ''
|
||||
);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
test("hostname() sets the hostname", function(t){
|
||||
var url = "http://subdomain.asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).hostname("blah").toString(),
|
||||
'http://blah'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
test("port() gets the port", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com:9090";
|
||||
t.equal(
|
||||
urlgrey(url).port(),
|
||||
9090
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
test("port() gets a correct default port when it's missing", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).port(),
|
||||
443
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("port() omits the port when it's 80 for http", function(t){
|
||||
var url = "http://subdomain.asdf.com:9090";
|
||||
t.equal(
|
||||
urlgrey(url).port(80).toString(),
|
||||
'http://subdomain.asdf.com'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("port() omits the port when it's 443 for https", function(t){
|
||||
var url = "https://subdomain.asdf.com:9090";
|
||||
t.equal(
|
||||
urlgrey(url).port(443).toString(),
|
||||
'https://subdomain.asdf.com'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("port() sets the port", function(t){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).port(9090).toString(),
|
||||
'https://subdomain.asdf.com:9090'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
test("rawPath() gets the path", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).rawPath(),
|
||||
'/path'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("rawPath() sets the path", function(t){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).rawPath("blah").toString(),
|
||||
'https://subdomain.asdf.com/blah'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("rawPath() does not encode pieces of the path", function(t){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).rawPath("not encode here", "and/not/here").toString(),
|
||||
'https://subdomain.asdf.com/not encode here/and/not/here'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("rawPath() sets the path from strings and arrays of strings", function(t){
|
||||
var url = "https://asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).rawPath(['qwer', '/asdf'], 'qwer/1234/', '/1234/').toString(),
|
||||
'https://asdf.com/qwer/asdf/qwer/1234/1234'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("path() gets the path", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).path(),
|
||||
'/path'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("path() sets the path", function(t){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).path("blah").toString(),
|
||||
'https://subdomain.asdf.com/blah'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("path() url encodes pieces of the path, but not slashes", function(t){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).path("encode here", "but/not/here").toString(),
|
||||
'https://subdomain.asdf.com/encode%20here/but/not/here'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("path() sets the path from strings and arrays of strings", function(t){
|
||||
var url = "https://asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).path(['qwer', '/asdf'], 'qwer/1234/', '/1234/').toString(),
|
||||
'https://asdf.com/qwer/asdf/qwer/1234/1234'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("hash() gets the hash", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).hash(),
|
||||
'frag'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("hash() sets the hash", function(t){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).hash("blah").toString(),
|
||||
'https://subdomain.asdf.com#blah'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("password() gets the password", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).password(),
|
||||
'pass'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("password() sets the password", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).password("blah").toString(),
|
||||
'https://user:blah@subdomain.asdf.com'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
|
||||
test("username() gets the username", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).username(),
|
||||
'user'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("username() sets the username", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com";
|
||||
t.equal(
|
||||
urlgrey(url).username("blah").toString(),
|
||||
'https://blah:pass@subdomain.asdf.com'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
test("parent() returns the second-last item in the path if there is no input", function(t){
|
||||
var url = "http://asdf.com/path/kid?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).parent().toString(),
|
||||
'http://asdf.com/path'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("parent() ignores a trailing slash", function(t){
|
||||
var url = "http://asdf.com/path/kid/?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).parent().toString(),
|
||||
'http://asdf.com/path'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
test("parent() throws an exception when no parent path exists", function(t){
|
||||
var url = "http://asdf.com/";
|
||||
t.plan(1);
|
||||
try {
|
||||
urlgrey(url).parent();
|
||||
t.fail("expected exception was not raised.");
|
||||
} catch (ex){
|
||||
t.equal(
|
||||
ex.message,
|
||||
'The current path has no parent path'
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test("extendedPath() returns the part of the url after the host:port", function(t){
|
||||
var url = "http://asdf.com:8080/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).extendedPath(),
|
||||
'/path?asdf=1234#frag'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("extendedPath() lets you set the part of the url after the host:port", function(t){
|
||||
var url = "http://asdf.com:8080/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).extendedPath('/asdf?qwer=1234#fraggle').toString(),
|
||||
'http://asdf.com:8080/asdf?qwer=1234#fraggle'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
test("rawChild() returns a url with the given path suffix added", function(t){
|
||||
var url = "http://asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).rawChild('kid here').toString(),
|
||||
'http://asdf.com/path/kid here'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("rawChild() returns a url with the given path suffixes added, without escaping", function(t){
|
||||
var url = "http://asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).rawChild('kid here', 'and here').toString(),
|
||||
'http://asdf.com/path/kid here/and here'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("rawChild() returns the last item in the path if there is no input", function(t){
|
||||
var url = "http://asdf.com/path/kid?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).rawChild(),
|
||||
'kid'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("rawChild() ignores a trailing slash", function(t){
|
||||
var url = "http://asdf.com/path/kid/?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).rawChild(),
|
||||
'kid'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
test("child() returns a url with the given path suffix added", function(t){
|
||||
var url = "http://asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).child('kid here').toString(),
|
||||
'http://asdf.com/path/kid%20here'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("child() returns a url with the given path suffixes added", function(t){
|
||||
var url = "http://asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).child('kid here', 'and here').toString(),
|
||||
'http://asdf.com/path/kid%20here/and%20here'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("child() returns a url with the given path suffix added even if it's 0", function(t){
|
||||
var url = "http://asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).child(0).toString(),
|
||||
'http://asdf.com/path/0'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("child() returns the last item in the path if there is no input", function(t){
|
||||
var url = "http://asdf.com/path/kid?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).child(),
|
||||
'kid'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("child() ignores a trailing slash", function(t){
|
||||
var url = "http://asdf.com/path/kid/?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).child(),
|
||||
'kid'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("parsed() returns some stuff", function(t){
|
||||
var url = "http://gdizzle:pazz@asdf.com:5678/path/kid/?asdf=1234#frag";
|
||||
var actual = urlgrey(url).parsed();
|
||||
var expected = {
|
||||
"protocol": "http",
|
||||
"auth": "gdizzle:pazz",
|
||||
"host": "asdf.com:5678",
|
||||
"port": 5678,
|
||||
"hostname": "asdf.com",
|
||||
"hash": "frag",
|
||||
"search": "?asdf=1234",
|
||||
"query": "asdf=1234",
|
||||
"pathname": "/path/kid/",
|
||||
"path": "/path/kid/?asdf=1234",
|
||||
"href": "http://gdizzle:pazz@asdf.com:5678/path/kid/?asdf=1234#frag",
|
||||
"username": "gdizzle",
|
||||
"password": "pazz"
|
||||
};
|
||||
t.deepLooseEqual(
|
||||
actual, expected
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("toString() returns the input string if unmodified", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).toString(),
|
||||
url
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("toString() returns an absolute uri even if one is not given", function(t){
|
||||
var url = "/path?asdf=1234#frag";
|
||||
t.ok(
|
||||
/^http:\/\/|file:\/\//.test(urlgrey(url).toString())
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
test("protocol() gets the protocol", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).protocol(),
|
||||
'https'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
if (isBrowser){
|
||||
test("protocol() gets the protocol as the current one if unset", function(t){
|
||||
t.equal(
|
||||
urlgrey('').protocol(),
|
||||
window.location.href.slice(0, 4)
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
} else {
|
||||
test("protocol() gets the protocol as http if unset", function(t){
|
||||
var url = "/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).protocol(),
|
||||
'http'
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
}
|
||||
|
||||
test("protocol() sets the protocol", function(t){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
var expected = "http://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
t.equal(
|
||||
urlgrey(url).protocol('http').toString(),
|
||||
expected
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
test("queryString() sets the queryString", function(t){
|
||||
t.equal(
|
||||
urlgrey("http://s.asdf.com").queryString('asdf=1234').toString(),
|
||||
"http://s.asdf.com?asdf=1234"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("queryString() updates the queryString", function(t){
|
||||
t.equal(
|
||||
urlgrey("http://s.asdf.com?asdf=1234").queryString('qwer=1235').toString(),
|
||||
"http://s.asdf.com?qwer=1235"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("queryString() gets the queryString", function(t){
|
||||
t.equal(
|
||||
urlgrey("http://s.asdf.com/?qwer=1234").queryString(),
|
||||
"qwer=1234"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("queryString() 'roundtrips' the queryString", function(t){
|
||||
t.equal(
|
||||
urlgrey("http://s.asdf.com/?qwer=1234")
|
||||
.queryString('asdf=1234').queryString(),
|
||||
"asdf=1234"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
|
||||
test("rawQuery() adds a querystring", function(t){
|
||||
t.equal(
|
||||
urlgrey("http://asdf.com").rawQuery({asdf:'12 34'}).toString(),
|
||||
"http://asdf.com?asdf=12 34"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("rawQuery() modifies a querystring", function(t){
|
||||
t.equal(
|
||||
urlgrey("http://asdf.com?asdf=5678&b=2").rawQuery({asdf:'12 34'}).toString(),
|
||||
"http://asdf.com?asdf=12 34&b=2"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("rawQuery() clears a querystring", function(t){
|
||||
t.equal(
|
||||
urlgrey("http://asdf.com?asdf=5678").rawQuery(false) .toString(),
|
||||
"http://asdf.com"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("rawQuery() extracts a querystring as an object", function(t){
|
||||
t.looseEqual(
|
||||
urlgrey("http://asdf.com?asdf=56%2078").rawQuery(),
|
||||
{asdf:'56 78'}
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("query() adds a querystring", function(t){
|
||||
t.equal(
|
||||
urlgrey("http://asdf.com").query({asdf:'12 34'}) .toString(),
|
||||
"http://asdf.com?asdf=12%2034"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("query() modifies a querystring", function(t){
|
||||
t.equal(
|
||||
urlgrey("http://asdf.com?asdf=5678&b=2").query({asdf:1234}).toString(),
|
||||
"http://asdf.com?asdf=1234&b=2"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("query() clears a querystring", function(t){
|
||||
t.equal(
|
||||
urlgrey("http://asdf.com?asdf=5678").query(false).toString(),
|
||||
"http://asdf.com"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("query() extracts a querystring as an object", function(t){
|
||||
t.looseEqual(
|
||||
urlgrey("http://asdf.com?asdf=56%2078").query(),
|
||||
{asdf:'56 78'}
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("encode() returns a url-encoded version of its input string", function(t){
|
||||
t.equal(
|
||||
urlgrey('').encode("this is a test"),
|
||||
"this%20is%20a%20test"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
test("decode() returns a url-decoded version of its input string", function(t){
|
||||
t.equal(
|
||||
urlgrey('').decode("this%20is%20a%20test"),
|
||||
"this is a test"
|
||||
);
|
||||
t.end();
|
||||
});
|
||||
};
|
||||
|
||||
module.exports = tapetest;
|
404
node_modules/urlgrey/test/index.js
generated
vendored
Normal file
404
node_modules/urlgrey/test/index.js
generated
vendored
Normal file
@ -0,0 +1,404 @@
|
||||
var isBrowser = !(typeof module !== 'undefined' && module.exports);
|
||||
if (!isBrowser){
|
||||
// non-browser code
|
||||
var chai = require('chai');
|
||||
chai.should();
|
||||
var urlgrey = require('../index');
|
||||
}
|
||||
|
||||
describe("urlgrey", function(){
|
||||
describe("chainability", function(){
|
||||
it("doesn't over-write the original url", function(){
|
||||
var urlStr = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
var url = urlgrey(urlStr);
|
||||
url.hostname('asdf.com')
|
||||
.toString().should.equal("https://user:pass@asdf.com/path?asdf=1234#frag");
|
||||
url.port(8080);
|
||||
url.protocol('http');
|
||||
url.username('http');
|
||||
url.password('http');
|
||||
url.path('http');
|
||||
url.hash('http');
|
||||
url.queryString('http=1234');
|
||||
url.query(false);
|
||||
url.extendedPath("/asdf?qwer=asdf#swqertwert23");
|
||||
url.toString().should.equal(urlStr); // original object is unmodified
|
||||
});
|
||||
});
|
||||
describe("#toJSON", function(){
|
||||
it("returns the same thing as toString", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).toJSON().should.equal(urlgrey(url).toString());
|
||||
});
|
||||
});
|
||||
describe("#hostname", function(){
|
||||
it("gets the hostname", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).hostname().should.equal('subdomain.asdf.com');
|
||||
});
|
||||
if (isBrowser){
|
||||
it("gets the hostname even if unset", function(){
|
||||
var url = "/path?asdf=1234#frag";
|
||||
var u = urlgrey(url);
|
||||
if (u.protocol() === 'file'){
|
||||
// chrome uses localhost. other browsers don't
|
||||
chai.expect((u.hostname() === '') || (u.hostname() === 'localhost')).to.eql(true);
|
||||
} else {
|
||||
chai.expect(u.hostname()).to.equal(window.location.hostname + '');
|
||||
}
|
||||
});
|
||||
}
|
||||
it("sets the hostname", function(){
|
||||
var url = "http://subdomain.asdf.com";
|
||||
urlgrey(url).hostname("blah")
|
||||
.toString().should.equal('http://blah');
|
||||
});
|
||||
});
|
||||
describe("#port", function(){
|
||||
it("gets the port", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com:9090";
|
||||
urlgrey(url).port().should.equal(9090);
|
||||
});
|
||||
it("gets a correct default port when it's missing", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com";
|
||||
urlgrey(url).port().should.equal(443);
|
||||
});
|
||||
it("omits the port when it's 80", function(){
|
||||
var url = "http://subdomain.asdf.com:9090";
|
||||
urlgrey(url).port(80)
|
||||
.toString().should.equal('http://subdomain.asdf.com');
|
||||
});
|
||||
it("sets the port", function(){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
urlgrey(url).port(9090)
|
||||
.toString().should.equal('https://subdomain.asdf.com:9090');
|
||||
});
|
||||
});
|
||||
describe("#rawPath", function(){
|
||||
it("gets the path", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).rawPath().should.equal('/path');
|
||||
});
|
||||
it("sets the path", function(){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
urlgrey(url).rawPath("blah")
|
||||
.toString().should.equal('https://subdomain.asdf.com/blah');
|
||||
});
|
||||
it("does not encode pieces of the path", function(){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
urlgrey(url).rawPath("not encode here", "and/not/here")
|
||||
.toString().should.equal('https://subdomain.asdf.com/not encode here/and/not/here');
|
||||
});
|
||||
it ("sets the path from strings and arrays of strings", function(){
|
||||
var url = "https://asdf.com";
|
||||
urlgrey(url).rawPath(['qwer', '/asdf'], 'qwer/1234/', '/1234/')
|
||||
.toString().should.equal('https://asdf.com/qwer/asdf/qwer/1234/1234');
|
||||
});
|
||||
});
|
||||
describe("#path", function(){
|
||||
it("gets the path", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).path().should.equal('/path');
|
||||
});
|
||||
it("sets the path", function(){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
urlgrey(url).path("blah")
|
||||
.toString().should.equal('https://subdomain.asdf.com/blah');
|
||||
});
|
||||
it("url encodes pieces of the path, but not slashes", function(){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
urlgrey(url).path("encode here", "but/not/here")
|
||||
.toString().should.equal('https://subdomain.asdf.com/encode%20here/but/not/here');
|
||||
});
|
||||
it ("sets the path from strings and arrays of strings", function(){
|
||||
var url = "https://asdf.com";
|
||||
urlgrey(url).path(['qwer', '/asdf'], 'qwer/1234/', '/1234/')
|
||||
.toString().should.equal('https://asdf.com/qwer/asdf/qwer/1234/1234');
|
||||
});
|
||||
});
|
||||
describe("#hash", function(){
|
||||
it("gets the hash", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).hash().should.equal('frag');
|
||||
});
|
||||
it("sets the hash", function(){
|
||||
var url = "https://subdomain.asdf.com";
|
||||
urlgrey(url).hash("blah")
|
||||
.toString().should.equal('https://subdomain.asdf.com#blah');
|
||||
});
|
||||
});
|
||||
describe("#password", function(){
|
||||
it("gets the password", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).password().should.equal('pass');
|
||||
});
|
||||
it("sets the password", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com";
|
||||
urlgrey(url).password("blah")
|
||||
.toString().should.equal('https://user:blah@subdomain.asdf.com');
|
||||
});
|
||||
});
|
||||
describe("#username", function(){
|
||||
it("gets the username", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).username().should.equal('user');
|
||||
});
|
||||
it("sets the username", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com";
|
||||
urlgrey(url).username("blah")
|
||||
.toString().should.equal('https://blah:pass@subdomain.asdf.com');
|
||||
});
|
||||
});
|
||||
describe("#parent", function(){
|
||||
it("returns the second-last item in the path if there is no input", function(){
|
||||
var url = "http://asdf.com/path/kid?asdf=1234#frag";
|
||||
urlgrey(url).parent()
|
||||
.toString().should.equal('http://asdf.com/path');
|
||||
});
|
||||
it("ignores a trailing slash", function(){
|
||||
var url = "http://asdf.com/path/kid/?asdf=1234#frag";
|
||||
urlgrey(url).parent()
|
||||
.toString().should.equal('http://asdf.com/path');
|
||||
});
|
||||
it("throws an exception when no parent path exists", function(){
|
||||
var url = "http://asdf.com/";
|
||||
try {
|
||||
urlgrey(url).parent();
|
||||
should.fail("expected exception was not raised.");
|
||||
} catch (ex){
|
||||
ex.message.should.equal('The current path has no parent path');
|
||||
}
|
||||
});
|
||||
});
|
||||
describe("#extendedPath", function(){
|
||||
it("returns the part of the url after the host:port", function(){
|
||||
var url = "http://asdf.com:8080/path?asdf=1234#frag";
|
||||
urlgrey(url).extendedPath().should.equal('/path?asdf=1234#frag');
|
||||
});
|
||||
it("lets you set the part of the url after the host:port", function(){
|
||||
var url = "http://asdf.com:8080/path?asdf=1234#frag";
|
||||
urlgrey(url).extendedPath('/asdf?qwer=1234#fraggle').toString()
|
||||
.should.equal('http://asdf.com:8080/asdf?qwer=1234#fraggle');
|
||||
});
|
||||
});
|
||||
describe("#rawChild", function(){
|
||||
it("returns a url with the given path suffix added", function(){
|
||||
var url = "http://asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).rawChild('{kid here}')
|
||||
.toString().should.equal('http://asdf.com/path/{kid here}');
|
||||
});
|
||||
it("returns a url with the given path suffixes added, without escaping", function(){
|
||||
var url = "http://asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).rawChild('{kid here}', '{and here}')
|
||||
.toString().should.equal('http://asdf.com/path/{kid here}/{and here}');
|
||||
});
|
||||
it("returns the last item in the path if there is no input", function(){
|
||||
var url = "http://asdf.com/path/kid?asdf=1234#frag";
|
||||
urlgrey(url).rawChild().should.equal('kid');
|
||||
});
|
||||
it("ignores a trailing slash", function(){
|
||||
var url = "http://asdf.com/path/kid/?asdf=1234#frag";
|
||||
urlgrey(url).rawChild().should.equal('kid');
|
||||
});
|
||||
});
|
||||
describe("#child", function(){
|
||||
it("returns a url with the given path suffix added", function(){
|
||||
var url = "http://asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).child('kid here')
|
||||
.toString().should.equal('http://asdf.com/path/kid%20here');
|
||||
});
|
||||
it("returns a url with the given path suffixes added", function(){
|
||||
var url = "http://asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).child('kid here', 'and here')
|
||||
.toString().should.equal('http://asdf.com/path/kid%20here/and%20here');
|
||||
});
|
||||
it("returns a url with the given path suffix added even if it's 0", function(){
|
||||
var url = "http://asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).child(0)
|
||||
.toString().should.equal('http://asdf.com/path/0');
|
||||
});
|
||||
it("returns the last item in the path if there is no input", function(){
|
||||
var url = "http://asdf.com/path/kid?asdf=1234#frag";
|
||||
urlgrey(url).child().should.equal('kid');
|
||||
});
|
||||
it("ignores a trailing slash", function(){
|
||||
var url = "http://asdf.com/path/kid/?asdf=1234#frag";
|
||||
urlgrey(url).child().should.equal('kid');
|
||||
});
|
||||
it("url-decodes the child if it's encoded", function(){
|
||||
var url = "http://asdf.com/path/the%20kid";
|
||||
urlgrey(url).child().should.equal('the kid');
|
||||
});
|
||||
it("url-encodes the child if necessary", function(){
|
||||
var url = "http://asdf.com/path/";
|
||||
urlgrey(url).child('the kid').toString().should.equal('http://asdf.com/path/the%20kid');
|
||||
});
|
||||
});
|
||||
describe("#parsed", function(){
|
||||
it("returns some stuff", function(){
|
||||
var url = "http://gdizzle:pazz@asdf.com:5678/path/kid/?asdf=1234#frag";
|
||||
var actual = urlgrey(url).parsed();
|
||||
var expected = {
|
||||
"protocol": "http",
|
||||
"auth": "gdizzle:pazz",
|
||||
"host": "asdf.com:5678",
|
||||
"port": 5678,
|
||||
"hostname": "asdf.com",
|
||||
"hash": "frag",
|
||||
"search": "?asdf=1234",
|
||||
"query": "asdf=1234",
|
||||
"pathname": "/path/kid/",
|
||||
"path": "/path/kid/?asdf=1234",
|
||||
"href": "http://gdizzle:pazz@asdf.com:5678/path/kid/?asdf=1234#frag",
|
||||
"username": "gdizzle",
|
||||
"password": "pazz"
|
||||
};
|
||||
chai.expect(actual).to.eql(expected);
|
||||
});
|
||||
});
|
||||
describe("#toString", function(){
|
||||
it("returns the input string if unmodified", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).toString().should.equal(url);
|
||||
});
|
||||
it("returns an absolute uri even if one is not given", function(){
|
||||
var url = "/path?asdf=1234#frag";
|
||||
urlgrey(url).toString()
|
||||
.should.match(/^http:\/\/|file:\/\//);
|
||||
});
|
||||
});
|
||||
describe("#protocol", function(){
|
||||
it("gets the protocol", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).protocol().should.equal('https');
|
||||
});
|
||||
|
||||
if (isBrowser){
|
||||
it ("gets the protocol as the current one if unset", function(){
|
||||
urlgrey('').protocol()
|
||||
.should.equal(window.location.href.slice(0, 4));
|
||||
});
|
||||
} else {
|
||||
it("gets the protocol as http if unset", function(){
|
||||
var url = "/path?asdf=1234#frag";
|
||||
urlgrey(url).protocol().should.equal('http');
|
||||
});
|
||||
}
|
||||
|
||||
it("sets the protocol", function(){
|
||||
var url = "https://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
var expected = "http://user:pass@subdomain.asdf.com/path?asdf=1234#frag";
|
||||
urlgrey(url).protocol('http').toString().should.equal(expected);
|
||||
});
|
||||
});
|
||||
|
||||
describe("#queryString", function(){
|
||||
it("sets the queryString", function(){
|
||||
var updated = urlgrey("http://s.asdf.com").queryString('foo=1234');
|
||||
|
||||
updated.toString().should.equal("http://s.asdf.com?foo=1234");
|
||||
updated.query().should.deep.equal({foo: "1234"});
|
||||
});
|
||||
it("changes the queryString", function(){
|
||||
var updated = urlgrey("http://s.asdf.com?foo=1234&bar=5678").queryString('baz=3456');
|
||||
|
||||
updated.toString().should.equal("http://s.asdf.com?baz=3456");
|
||||
updated.query().should.deep.equal({baz: "3456"});
|
||||
});
|
||||
it("gets the queryString", function(){
|
||||
chai.expect(
|
||||
urlgrey("http://s.asdf.com/?qwer=1234").queryString()
|
||||
).to.equal("qwer=1234");
|
||||
});
|
||||
it("'roundtrips' the queryString", function(){
|
||||
urlgrey("http://s.asdf.com/?qwer=1234").queryString('asdf=1234')
|
||||
.queryString().should.equal("asdf=1234");
|
||||
});
|
||||
|
||||
});
|
||||
describe("#rawQuery", function(){
|
||||
it("adds a querystring", function(){
|
||||
var updated = urlgrey("http://asdf.com").rawQuery({foo:'12 34'});
|
||||
|
||||
updated.toString().should.equal("http://asdf.com?foo=12 34");
|
||||
updated.rawQuery().should.deep.equal({foo: "12 34"});
|
||||
});
|
||||
it("appends a querystring", function(){
|
||||
var updated = urlgrey("http://asdf.com?foo=1234").rawQuery({bar:'56 78'});
|
||||
|
||||
updated.toString().should.equal("http://asdf.com?foo=1234&bar=56 78");
|
||||
updated.rawQuery().should.deep.equal({foo: "1234", bar: "56 78"});
|
||||
});
|
||||
it("modifies a querystring", function(){
|
||||
var updated = urlgrey("http://asdf.com?foo=1234&bar=abcd").rawQuery({foo: "56 78"});
|
||||
|
||||
updated.toString().should.equal("http://asdf.com?foo=56 78&bar=abcd");
|
||||
updated.rawQuery().should.deep.equal({foo: "56 78", bar: "abcd"});
|
||||
});
|
||||
it("clears a querystring", function(){
|
||||
var updated = urlgrey("http://asdf.com?foo=1234").rawQuery(false);
|
||||
|
||||
updated.toString().should.equal("http://asdf.com");
|
||||
updated.rawQuery().should.deep.equal({});
|
||||
});
|
||||
it("clears an element of a querystring with null or false", function(){
|
||||
var updated = urlgrey("http://asdf.com")
|
||||
.rawQuery({foo: 1, bar: 2, baz: 3})
|
||||
.rawQuery({foo: 0, bar: null});
|
||||
|
||||
updated.toString().should.equal("http://asdf.com?foo=0&baz=3");
|
||||
updated.rawQuery().should.deep.equal({foo: "0", baz: "3"});
|
||||
});
|
||||
it("extracts a querystring as an object", function(){
|
||||
urlgrey("http://asdf.com?asdf=56%2078").rawQuery().should.deep.equal({asdf:'56%2078'});
|
||||
});
|
||||
});
|
||||
describe("#query", function(){
|
||||
it("adds a querystring", function(){
|
||||
var updated = urlgrey("http://asdf.com").query({foo:'12 34'});
|
||||
|
||||
updated.toString().should.equal("http://asdf.com?foo=12%2034");
|
||||
updated.query().should.deep.equal({foo: "12 34"});
|
||||
});
|
||||
it("appends a querystring", function(){
|
||||
var updated = urlgrey("http://asdf.com?foo=1234").query({bar:'56 78'});
|
||||
|
||||
updated.toString().should.equal("http://asdf.com?foo=1234&bar=56%2078");
|
||||
updated.query().should.deep.equal({foo: "1234", bar: "56 78"});
|
||||
});
|
||||
it("modifies a querystring", function(){
|
||||
var updated = urlgrey("http://asdf.com?foo=1234&bar=abcd").query({foo: "56 78"});
|
||||
|
||||
updated.toString().should.equal("http://asdf.com?foo=56%2078&bar=abcd");
|
||||
updated.query().should.deep.equal({foo: "56 78", bar: "abcd"});
|
||||
});
|
||||
it("clears a querystring", function(){
|
||||
var updated = urlgrey("http://asdf.com?foo=1234").query(false);
|
||||
|
||||
updated.toString().should.equal("http://asdf.com");
|
||||
updated.query().should.deep.equal({});
|
||||
});
|
||||
it("clears an element of a querystring with null or false", function(){
|
||||
var updated = urlgrey("http://asdf.com")
|
||||
.rawQuery({foo: 1, bar: 2, baz: 3})
|
||||
.rawQuery({foo: 0, bar: null});
|
||||
|
||||
updated.toString().should.equal("http://asdf.com?foo=0&baz=3");
|
||||
updated.query().should.deep.equal({foo: "0", baz: "3"});
|
||||
});
|
||||
it("extracts a querystring as an object", function(){
|
||||
urlgrey("http://asdf.com?asdf=56%2078").query().should.deep.equal({asdf:'56 78'});
|
||||
});
|
||||
});
|
||||
describe('#encode', function(){
|
||||
it ("returns a url-encoded version of its input string", function(){
|
||||
urlgrey('').encode("this is a test").should.equal("this%20is%20a%20test");
|
||||
});
|
||||
});
|
||||
describe('#decode', function(){
|
||||
it ("returns a url-decoded version of its input string", function(){
|
||||
urlgrey('').decode("this%20is%20a%20test").should.equal("this is a test");
|
||||
});
|
||||
});
|
||||
|
||||
});
|
BIN
node_modules/urlgrey/urlgrey.png
generated
vendored
Normal file
BIN
node_modules/urlgrey/urlgrey.png
generated
vendored
Normal file
Binary file not shown.
After Width: | Height: | Size: 8.4 KiB |
61
node_modules/urlgrey/util.js
generated
vendored
Normal file
61
node_modules/urlgrey/util.js
generated
vendored
Normal file
@ -0,0 +1,61 @@
|
||||
|
||||
var isObject = function (o){
|
||||
return (typeof o === "object") &&
|
||||
(o !== null) &&
|
||||
(Object.prototype.toString.call(o) === '[object Object]');
|
||||
};
|
||||
exports.isObject = isObject;
|
||||
exports.isString = function(o){
|
||||
return Object.prototype.toString.call(o) === '[object String]';
|
||||
};
|
||||
exports.isArray = function(o){
|
||||
return Object.prototype.toString.call(o) === "[object Array]";
|
||||
};
|
||||
exports.isBoolean = function(o) {
|
||||
return typeof o === 'boolean';
|
||||
};
|
||||
exports.isNumber = function(o) {
|
||||
return typeof o === 'number' && isFinite(o);
|
||||
};
|
||||
exports.isNull = function(o) {
|
||||
return o === null;
|
||||
};
|
||||
|
||||
exports.keys = function (object) {
|
||||
if (!isObject(object)) {
|
||||
throw new TypeError("Object.keys called on a non-object");
|
||||
}
|
||||
|
||||
var result = [];
|
||||
for (var name in object) {
|
||||
if (hasOwnProperty.call(object, name)) {
|
||||
result.push(name);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
};
|
||||
|
||||
// String.prototype.substr - negative index don't work in IE8
|
||||
if ('ab'.substr(-1) !== 'b') {
|
||||
exports.substr = function (str, start, length) {
|
||||
// did we get a negative start, calculate how much it is from the beginning of the string
|
||||
if (start < 0) { start = str.length + start; }
|
||||
|
||||
// call the original function
|
||||
return str.substr(start, length);
|
||||
};
|
||||
} else {
|
||||
exports.substr = function (str, start, length) {
|
||||
return str.substr(start, length);
|
||||
};
|
||||
}
|
||||
|
||||
// Array.prototype.map is supported in IE9
|
||||
exports.map = function map(xs, fn) {
|
||||
if (xs.map) { return xs.map(fn); }
|
||||
var out = new Array(xs.length);
|
||||
for (var i = 0; i < xs.length; i++) {
|
||||
out[i] = fn(xs[i], i, xs);
|
||||
}
|
||||
return out;
|
||||
};
|
Reference in New Issue
Block a user