* The actual URL instance. Instead of returning an object we've opted-in to * create an actual constructor as it's much more memory efficient and * faster and it pleases my OCD. * * @constructor * @param {String} address URL we want to parse. * @param {Object|String} location Location defaults
(address, location, parser)
| 8126 | * @api public |
| 8127 | */ |
| 8128 | function URL(address, location, parser) { |
| 8129 | if (!(this instanceof URL)) { |
| 8130 | return new URL(address, location, parser); |
| 8131 | } |
| 8132 | |
| 8133 | var relative, extracted, parse, instruction, index, key |
| 8134 | , instructions = rules.slice() |
| 8135 | , type = typeof location |
| 8136 | , url = this |
| 8137 | , i = 0; |
| 8138 | |
| 8139 | // |
| 8140 | // The following if statements allows this module two have compatibility with |
| 8141 | // 2 different API: |
| 8142 | // |
| 8143 | // 1. Node.js's `url.parse` api which accepts a URL, boolean as arguments |
| 8144 | // where the boolean indicates that the query string should also be parsed. |
| 8145 | // |
| 8146 | // 2. The `URL` interface of the browser which accepts a URL, object as |
| 8147 | // arguments. The supplied object will be used as default values / fall-back |
| 8148 | // for relative paths. |
| 8149 | // |
| 8150 | if ('object' !== type && 'string' !== type) { |
| 8151 | parser = location; |
| 8152 | location = null; |
| 8153 | } |
| 8154 | |
| 8155 | if (parser && 'function' !== typeof parser) parser = qs.parse; |
| 8156 | |
| 8157 | location = lolcation(location); |
| 8158 | |
| 8159 | // |
| 8160 | // Extract protocol information before running the instructions. |
| 8161 | // |
| 8162 | extracted = extractProtocol(address || ''); |
| 8163 | relative = !extracted.protocol && !extracted.slashes; |
| 8164 | url.slashes = extracted.slashes || relative && location.slashes; |
| 8165 | url.protocol = extracted.protocol || location.protocol || ''; |
| 8166 | address = extracted.rest; |
| 8167 | |
| 8168 | // |
| 8169 | // When the authority component is absent the URL starts with a path |
| 8170 | // component. |
| 8171 | // |
| 8172 | if (!extracted.slashes) instructions[2] = [/(.*)/, 'pathname']; |
| 8173 | |
| 8174 | for (; i < instructions.length; i++) { |
| 8175 | instruction = instructions[i]; |
| 8176 | parse = instruction[0]; |
| 8177 | key = instruction[1]; |
| 8178 | |
| 8179 | if (parse !== parse) { |
| 8180 | url[key] = address; |
| 8181 | } else if ('string' === typeof parse) { |
| 8182 | if (~(index = address.indexOf(parse))) { |
| 8183 | if ('number' === typeof instruction[2]) { |
| 8184 | url[key] = address.slice(0, index); |
| 8185 | address = address.slice(index + instruction[2]); |
nothing calls this directly
no test coverage detected