normalize-url 4.2.0 → 4.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (4) hide show
  1. package/index.d.ts +203 -170
  2. package/index.js +62 -0
  3. package/package.json +6 -6
  4. package/readme.md +24 -16
package/index.d.ts CHANGED
@@ -1,183 +1,216 @@
1
- export interface Options {
2
- /**
3
- * @default 'http:'
4
- */
5
- readonly defaultProtocol?: string;
1
+ declare namespace normalizeUrl {
2
+ interface Options {
3
+ /**
4
+ @default 'http:'
5
+ */
6
+ readonly defaultProtocol?: string;
6
7
 
7
- /**
8
- * Prepends `defaultProtocol` to the URL if it's protocol-relative.
9
- *
10
- * @default true
11
- *
12
- * @example
13
- *
14
- * normalizeUrl('//sindresorhus.com:80/');
15
- * //=> 'http://sindresorhus.com'
16
- *
17
- * normalizeUrl('//sindresorhus.com:80/', {normalizeProtocol: false});
18
- * //=> '//sindresorhus.com'
19
- */
20
- readonly normalizeProtocol?: boolean;
8
+ /**
9
+ Prepends `defaultProtocol` to the URL if it's protocol-relative.
21
10
 
22
- /**
23
- * Normalizes `https:` URLs to `http:`.
24
- *
25
- * @default false
26
- *
27
- * @example
28
- *
29
- * normalizeUrl('https://sindresorhus.com:80/');
30
- * //=> 'https://sindresorhus.com'
31
- *
32
- * normalizeUrl('https://sindresorhus.com:80/', {forceHttp: true});
33
- * //=> 'http://sindresorhus.com'
34
- */
35
- readonly forceHttp?: boolean;
11
+ @default true
36
12
 
37
- /**
38
- * Normalizes `http:` URLs to `https:`.
39
- *
40
- * This option can't be used with the `forceHttp` option at the same time.
41
- *
42
- * @default false
43
- *
44
- * @example
45
- *
46
- * normalizeUrl('https://sindresorhus.com:80/');
47
- * //=> 'https://sindresorhus.com'
48
- *
49
- * normalizeUrl('http://sindresorhus.com:80/', {forceHttps: true});
50
- * //=> 'https://sindresorhus.com'
51
- */
52
- readonly forceHttps?: boolean;
13
+ @example
14
+ ```
15
+ normalizeUrl('//sindresorhus.com:80/');
16
+ //=> 'http://sindresorhus.com'
53
17
 
54
- /**
55
- * Strip the [authentication](https://en.wikipedia.org/wiki/Basic_access_authentication) part of a URL.
56
- *
57
- * @default true
58
- *
59
- * @example
60
- *
61
- * normalizeUrl('user:password@sindresorhus.com');
62
- * //=> 'https://sindresorhus.com'
63
- *
64
- * normalizeUrl('user:password@sindresorhus.com', {stripAuthentication: false});
65
- * //=> 'https://user:password@sindresorhus.com'
66
- */
67
- readonly stripAuthentication?: boolean;
18
+ normalizeUrl('//sindresorhus.com:80/', {normalizeProtocol: false});
19
+ //=> '//sindresorhus.com'
20
+ ```
21
+ */
22
+ readonly normalizeProtocol?: boolean;
68
23
 
69
- /**
70
- * Removes hash from the URL.
71
- *
72
- * @default false
73
- *
74
- * @example
75
- *
76
- * normalizeUrl('sindresorhus.com/about.html#contact');
77
- * //=> 'http://sindresorhus.com/about.html#contact'
78
- *
79
- * normalizeUrl('sindresorhus.com/about.html#contact', {stripHash: true});
80
- * //=> 'http://sindresorhus.com/about.html'
81
- */
82
- readonly stripHash?: boolean;
24
+ /**
25
+ Normalizes `https:` URLs to `http:`.
83
26
 
84
- /**
85
- * Removes HTTP(S) protocol from an URL `http://sindresorhus.com` → `sindresorhus.com`.
86
- *
87
- * @default false
88
- *
89
- * @example
90
- *
91
- * normalizeUrl('https://sindresorhus.com');
92
- * //=> 'https://sindresorhus.com'
93
- *
94
- * normalizeUrl('sindresorhus.com', {stripProtocol: true});
95
- * //=> 'sindresorhus.com'
96
- */
97
- readonly stripProtocol?: boolean;
27
+ @default false
98
28
 
99
- /**
100
- * Removes `www.` from the URL.
101
- *
102
- * @default true
103
- *
104
- * @example
105
- *
106
- * normalizeUrl('http://www.sindresorhus.com');
107
- * //=> 'http://sindresorhus.com'
108
- *
109
- * normalizeUrl('http://www.sindresorhus.com', {stripWWW: false});
110
- * //=> 'http://www.sindresorhus.com'
111
- */
112
- readonly stripWWW?: boolean;
29
+ @example
30
+ ```
31
+ normalizeUrl('https://sindresorhus.com:80/');
32
+ //=> 'https://sindresorhus.com'
113
33
 
114
- /**
115
- * Removes query parameters that matches any of the provided strings or regexes.
116
- *
117
- * @default [/^utm_\w+/i]
118
- *
119
- * @example
120
- *
121
- * normalizeUrl('www.sindresorhus.com?foo=bar&ref=test_ref', {
122
- * removeQueryParameters: ['ref']
123
- * });
124
- * //=> 'http://sindresorhus.com/?foo=bar'
125
- */
126
- readonly removeQueryParameters?: (RegExp | string)[];
34
+ normalizeUrl('https://sindresorhus.com:80/', {forceHttp: true});
35
+ //=> 'http://sindresorhus.com'
36
+ ```
37
+ */
38
+ readonly forceHttp?: boolean;
127
39
 
128
- /**
129
- * Removes trailing slash.
130
- *
131
- * **Note**: Trailing slash is always removed if the URL doesn't have a pathname.
132
- *
133
- * @default true
134
- *
135
- * @example
136
- *
137
- * normalizeUrl('http://sindresorhus.com/redirect/');
138
- * //=> 'http://sindresorhus.com/redirect'
139
- *
140
- * normalizeUrl('http://sindresorhus.com/redirect/', {removeTrailingSlash: false});
141
- * //=> 'http://sindresorhus.com/redirect/'
142
- *
143
- * normalizeUrl('http://sindresorhus.com/', {removeTrailingSlash: false});
144
- * //=> 'http://sindresorhus.com'
145
- */
146
- readonly removeTrailingSlash?: boolean;
40
+ /**
41
+ Normalizes `http:` URLs to `https:`.
147
42
 
148
- /**
149
- * Removes the default directory index file from path that matches any of the provided strings or regexes.
150
- * When `true`, the regex `/^index\.[a-z]+$/` is used.
151
- *
152
- * @default false
153
- *
154
- * @example
155
- *
156
- * normalizeUrl('www.sindresorhus.com/foo/default.php', {
157
- * removeDirectoryIndex: [/^default\.[a-z]+$/]
158
- * });
159
- * //=> 'http://sindresorhus.com/foo'
160
- */
161
- readonly removeDirectoryIndex?: (RegExp | string)[];
43
+ This option can't be used with the `forceHttp` option at the same time.
162
44
 
163
- /**
164
- * Sorts the query parameters alphabetically by key.
165
- *
166
- * @default true
167
- *
168
- * @example
169
- *
170
- * normalizeUrl('www.sindresorhus.com?b=two&a=one&c=three', {
171
- * sortQueryParameters: false
172
- * });
173
- * //=> 'http://sindresorhus.com/?b=two&a=one&c=three'
174
- */
175
- readonly sortQueryParameters?: boolean;
45
+ @default false
46
+
47
+ @example
48
+ ```
49
+ normalizeUrl('https://sindresorhus.com:80/');
50
+ //=> 'https://sindresorhus.com'
51
+
52
+ normalizeUrl('http://sindresorhus.com:80/', {forceHttps: true});
53
+ //=> 'https://sindresorhus.com'
54
+ ```
55
+ */
56
+ readonly forceHttps?: boolean;
57
+
58
+ /**
59
+ Strip the [authentication](https://en.wikipedia.org/wiki/Basic_access_authentication) part of a URL.
60
+
61
+ @default true
62
+
63
+ @example
64
+ ```
65
+ normalizeUrl('user:password@sindresorhus.com');
66
+ //=> 'https://sindresorhus.com'
67
+
68
+ normalizeUrl('user:password@sindresorhus.com', {stripAuthentication: false});
69
+ //=> 'https://user:password@sindresorhus.com'
70
+ ```
71
+ */
72
+ readonly stripAuthentication?: boolean;
73
+
74
+ /**
75
+ Removes hash from the URL.
76
+
77
+ @default false
78
+
79
+ @example
80
+ ```
81
+ normalizeUrl('sindresorhus.com/about.html#contact');
82
+ //=> 'http://sindresorhus.com/about.html#contact'
83
+
84
+ normalizeUrl('sindresorhus.com/about.html#contact', {stripHash: true});
85
+ //=> 'http://sindresorhus.com/about.html'
86
+ ```
87
+ */
88
+ readonly stripHash?: boolean;
89
+
90
+ /**
91
+ Removes HTTP(S) protocol from an URL `http://sindresorhus.com` → `sindresorhus.com`.
92
+
93
+ @default false
94
+
95
+ @example
96
+ ```
97
+ normalizeUrl('https://sindresorhus.com');
98
+ //=> 'https://sindresorhus.com'
99
+
100
+ normalizeUrl('sindresorhus.com', {stripProtocol: true});
101
+ //=> 'sindresorhus.com'
102
+ ```
103
+ */
104
+ readonly stripProtocol?: boolean;
105
+
106
+ /**
107
+ Removes `www.` from the URL.
108
+
109
+ @default true
110
+
111
+ @example
112
+ ```
113
+ normalizeUrl('http://www.sindresorhus.com');
114
+ //=> 'http://sindresorhus.com'
115
+
116
+ normalizeUrl('http://www.sindresorhus.com', {stripWWW: false});
117
+ //=> 'http://www.sindresorhus.com'
118
+ ```
119
+ */
120
+ readonly stripWWW?: boolean;
121
+
122
+ /**
123
+ Removes query parameters that matches any of the provided strings or regexes.
124
+
125
+ @default [/^utm_\w+/i]
126
+
127
+ @example
128
+ ```
129
+ normalizeUrl('www.sindresorhus.com?foo=bar&ref=test_ref', {
130
+ removeQueryParameters: ['ref']
131
+ });
132
+ //=> 'http://sindresorhus.com/?foo=bar'
133
+ ```
134
+ */
135
+ readonly removeQueryParameters?: ReadonlyArray<RegExp | string>;
136
+
137
+ /**
138
+ Removes trailing slash.
139
+
140
+ __Note__: Trailing slash is always removed if the URL doesn't have a pathname.
141
+
142
+ @default true
143
+
144
+ @example
145
+ ```
146
+ normalizeUrl('http://sindresorhus.com/redirect/');
147
+ //=> 'http://sindresorhus.com/redirect'
148
+
149
+ normalizeUrl('http://sindresorhus.com/redirect/', {removeTrailingSlash: false});
150
+ //=> 'http://sindresorhus.com/redirect/'
151
+
152
+ normalizeUrl('http://sindresorhus.com/', {removeTrailingSlash: false});
153
+ //=> 'http://sindresorhus.com'
154
+ ```
155
+ */
156
+ readonly removeTrailingSlash?: boolean;
157
+
158
+ /**
159
+ Removes the default directory index file from path that matches any of the provided strings or regexes.
160
+ When `true`, the regex `/^index\.[a-z]+$/` is used.
161
+
162
+ @default false
163
+
164
+ @example
165
+ ```
166
+ normalizeUrl('www.sindresorhus.com/foo/default.php', {
167
+ removeDirectoryIndex: [/^default\.[a-z]+$/]
168
+ });
169
+ //=> 'http://sindresorhus.com/foo'
170
+ ```
171
+ */
172
+ readonly removeDirectoryIndex?: ReadonlyArray<RegExp | string>;
173
+
174
+ /**
175
+ Sorts the query parameters alphabetically by key.
176
+
177
+ @default true
178
+
179
+ @example
180
+ ```
181
+ normalizeUrl('www.sindresorhus.com?b=two&a=one&c=three', {
182
+ sortQueryParameters: false
183
+ });
184
+ //=> 'http://sindresorhus.com/?b=two&a=one&c=three'
185
+ ```
186
+ */
187
+ readonly sortQueryParameters?: boolean;
188
+ }
176
189
  }
177
190
 
178
- /**
179
- * [Normalize](https://en.wikipedia.org/wiki/URL_normalization) a URL.
180
- *
181
- * @param url - URL to normalize.
182
- */
183
- export default function normalizeUrl(url: string, options?: Options): string;
191
+ declare const normalizeUrl: {
192
+ /**
193
+ [Normalize](https://en.wikipedia.org/wiki/URL_normalization) a URL.
194
+
195
+ @param url - URL to normalize, including [data URL](https://developer.mozilla.org/en-US/docs/Web/HTTP/Basics_of_HTTP/Data_URIs).
196
+
197
+ @example
198
+ ```
199
+ import normalizeUrl = require('normalize-url');
200
+
201
+ normalizeUrl('sindresorhus.com');
202
+ //=> 'http://sindresorhus.com'
203
+
204
+ normalizeUrl('HTTP://xn--xample-hva.com:80/?b=bar&a=foo');
205
+ //=> 'http://êxample.com/?a=foo&b=bar'
206
+ ```
207
+ */
208
+ (url: string, options?: normalizeUrl.Options): string;
209
+
210
+ // TODO: Remove this for the next major release, refactor the whole definition to:
211
+ // declare function normalizeUrl(url: string, options?: normalizeUrl.Options): string;
212
+ // export = normalizeUrl;
213
+ default: typeof normalizeUrl;
214
+ };
215
+
216
+ export = normalizeUrl;
package/index.js CHANGED
@@ -2,10 +2,66 @@
2
2
  // TODO: Use the `URL` global when targeting Node.js 10
3
3
  const URLParser = typeof URL === 'undefined' ? require('url').URL : URL;
4
4
 
5
+ // https://developer.mozilla.org/en-US/docs/Web/HTTP/Basics_of_HTTP/Data_URIs
6
+ const DATA_URL_DEFAULT_MIME_TYPE = 'text/plain';
7
+ const DATA_URL_DEFAULT_CHARSET = 'us-ascii';
8
+
5
9
  const testParameter = (name, filters) => {
6
10
  return filters.some(filter => filter instanceof RegExp ? filter.test(name) : filter === name);
7
11
  };
8
12
 
13
+ const normalizeDataURL = (urlString, {stripHash}) => {
14
+ const parts = urlString.match(/^data:(.*?),(.*?)(?:#(.*))?$/);
15
+
16
+ if (!parts) {
17
+ throw new Error(`Invalid URL: ${urlString}`);
18
+ }
19
+
20
+ const mediaType = parts[1].split(';');
21
+ const body = parts[2];
22
+ const hash = stripHash ? '' : parts[3];
23
+
24
+ let base64 = false;
25
+
26
+ if (mediaType[mediaType.length - 1] === 'base64') {
27
+ mediaType.pop();
28
+ base64 = true;
29
+ }
30
+
31
+ // Lowercase MIME type
32
+ const mimeType = (mediaType.shift() || '').toLowerCase();
33
+ const attributes = mediaType
34
+ .map(attribute => {
35
+ let [key, value = ''] = attribute.split('=').map(string => string.trim());
36
+
37
+ // Lowercase `charset`
38
+ if (key === 'charset') {
39
+ value = value.toLowerCase();
40
+
41
+ if (value === DATA_URL_DEFAULT_CHARSET) {
42
+ return '';
43
+ }
44
+ }
45
+
46
+ return `${key}${value ? `=${value}` : ''}`;
47
+ })
48
+ .filter(Boolean);
49
+
50
+ const normalizedMediaType = [
51
+ ...attributes
52
+ ];
53
+
54
+ if (base64) {
55
+ normalizedMediaType.push('base64');
56
+ }
57
+
58
+ if (normalizedMediaType.length !== 0 || (mimeType && mimeType !== DATA_URL_DEFAULT_MIME_TYPE)) {
59
+ normalizedMediaType.unshift(mimeType);
60
+ }
61
+
62
+ return `data:${normalizedMediaType.join(';')},${base64 ? body.trim() : body}${hash ? `#${hash}` : ''}`;
63
+ };
64
+
9
65
  const normalizeUrl = (urlString, options) => {
10
66
  options = {
11
67
  defaultProtocol: 'http:',
@@ -37,6 +93,11 @@ const normalizeUrl = (urlString, options) => {
37
93
 
38
94
  urlString = urlString.trim();
39
95
 
96
+ // Data URL
97
+ if (/^data:/i.test(urlString)) {
98
+ return normalizeDataURL(urlString, options);
99
+ }
100
+
40
101
  const hasRelativeProtocol = urlString.startsWith('//');
41
102
  const isRelativeUrl = !hasRelativeProtocol && /^\.*\//.test(urlString);
42
103
 
@@ -156,4 +217,5 @@ const normalizeUrl = (urlString, options) => {
156
217
  };
157
218
 
158
219
  module.exports = normalizeUrl;
220
+ // TODO: Remove this for the next major release
159
221
  module.exports.default = normalizeUrl;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "normalize-url",
3
- "version": "4.2.0",
3
+ "version": "4.5.0",
4
4
  "description": "Normalize a URL",
5
5
  "license": "MIT",
6
6
  "repository": "sindresorhus/normalize-url",
@@ -13,7 +13,7 @@
13
13
  "node": ">=8"
14
14
  },
15
15
  "scripts": {
16
- "test": "xo && nyc ava && tsd-check"
16
+ "test": "xo && nyc ava && tsd"
17
17
  },
18
18
  "files": [
19
19
  "index.js",
@@ -35,10 +35,10 @@
35
35
  "canonical"
36
36
  ],
37
37
  "devDependencies": {
38
- "ava": "^1.2.1",
39
- "coveralls": "^3.0.0",
40
- "nyc": "^13.1.0",
41
- "tsd-check": "^0.3.0",
38
+ "ava": "^2.4.0",
39
+ "coveralls": "^3.0.6",
40
+ "nyc": "^14.1.1",
41
+ "tsd": "^0.8.0",
42
42
  "xo": "^0.24.0"
43
43
  }
44
44
  }
package/readme.md CHANGED
@@ -27,17 +27,17 @@ normalizeUrl('HTTP://xn--xample-hva.com:80/?b=bar&a=foo');
27
27
 
28
28
  ## API
29
29
 
30
- ### normalizeUrl(url, [options])
30
+ ### normalizeUrl(url, options?)
31
31
 
32
32
  #### url
33
33
 
34
34
  Type: `string`
35
35
 
36
- URL to normalize.
36
+ URL to normalize, including [data URL](https://developer.mozilla.org/en-US/docs/Web/HTTP/Basics_of_HTTP/Data_URIs).
37
37
 
38
38
  #### options
39
39
 
40
- Type: `Object`
40
+ Type: `object`
41
41
 
42
42
  ##### defaultProtocol
43
43
 
@@ -49,7 +49,7 @@ Default: `http:`
49
49
  Type: `boolean`<br>
50
50
  Default: `true`
51
51
 
52
- Prepends `defaultProtocol` to the URL if it's protocol-relative.
52
+ Prepend `defaultProtocol` to the URL if it's protocol-relative.
53
53
 
54
54
  ```js
55
55
  normalizeUrl('//sindresorhus.com:80/');
@@ -64,7 +64,7 @@ normalizeUrl('//sindresorhus.com:80/', {normalizeProtocol: false});
64
64
  Type: `boolean`<br>
65
65
  Default: `false`
66
66
 
67
- Normalizes `https:` URLs to `http:`.
67
+ Normalize `https:` to `http:`.
68
68
 
69
69
  ```js
70
70
  normalizeUrl('https://sindresorhus.com:80/');
@@ -79,7 +79,7 @@ normalizeUrl('https://sindresorhus.com:80/', {forceHttp: true});
79
79
  Type: `boolean`<br>
80
80
  Default: `false`
81
81
 
82
- Normalizes `http:` URLs to `https:`.
82
+ Normalize `http:` to `https:`.
83
83
 
84
84
  ```js
85
85
  normalizeUrl('https://sindresorhus.com:80/');
@@ -96,7 +96,7 @@ This option can't be used with the `forceHttp` option at the same time.
96
96
  Type: `boolean`<br>
97
97
  Default: `true`
98
98
 
99
- Strip the [authentication](https://en.wikipedia.org/wiki/Basic_access_authentication) part of a URL.
99
+ Strip the [authentication](https://en.wikipedia.org/wiki/Basic_access_authentication) part of the URL.
100
100
 
101
101
  ```js
102
102
  normalizeUrl('user:password@sindresorhus.com');
@@ -111,7 +111,7 @@ normalizeUrl('user:password@sindresorhus.com', {stripAuthentication: false});
111
111
  Type: `boolean`<br>
112
112
  Default: `false`
113
113
 
114
- Removes hash from the URL.
114
+ Strip the hash part of the URL.
115
115
 
116
116
  ```js
117
117
  normalizeUrl('sindresorhus.com/about.html#contact');
@@ -126,7 +126,7 @@ normalizeUrl('sindresorhus.com/about.html#contact', {stripHash: true});
126
126
  Type: `boolean`<br>
127
127
  Default: `false`
128
128
 
129
- Removes HTTP(S) protocol from an URL `http://sindresorhus.com` → `sindresorhus.com`.
129
+ Remove HTTP(S) protocol from the URL: `http://sindresorhus.com` → `sindresorhus.com`.
130
130
 
131
131
  ```js
132
132
  normalizeUrl('https://sindresorhus.com');
@@ -141,7 +141,7 @@ normalizeUrl('sindresorhus.com', {stripProtocol: true});
141
141
  Type: `boolean`<br>
142
142
  Default: `true`
143
143
 
144
- Removes `www.` from the URL.
144
+ Remove `www.` from the URL.
145
145
 
146
146
  ```js
147
147
  normalizeUrl('http://www.sindresorhus.com');
@@ -153,10 +153,10 @@ normalizeUrl('http://www.sindresorhus.com', {stripWWW: false});
153
153
 
154
154
  ##### removeQueryParameters
155
155
 
156
- Type: `Array<RegExp|string>`<br>
156
+ Type: `Array<RegExp | string>`<br>
157
157
  Default: `[/^utm_\w+/i]`
158
158
 
159
- Removes query parameters that matches any of the provided strings or regexes.
159
+ Remove query parameters that matches any of the provided strings or regexes.
160
160
 
161
161
  ```js
162
162
  normalizeUrl('www.sindresorhus.com?foo=bar&ref=test_ref', {
@@ -170,7 +170,7 @@ normalizeUrl('www.sindresorhus.com?foo=bar&ref=test_ref', {
170
170
  Type: `boolean`<br>
171
171
  Default: `true`
172
172
 
173
- Removes trailing slash.
173
+ Remove trailing slash.
174
174
 
175
175
  **Note:** Trailing slash is always removed if the URL doesn't have a pathname.
176
176
 
@@ -187,7 +187,7 @@ normalizeUrl('http://sindresorhus.com/', {removeTrailingSlash: false});
187
187
 
188
188
  ##### removeDirectoryIndex
189
189
 
190
- Type: `boolean` `Array<RegExp|string>`<br>
190
+ Type: `boolean | Array<RegExp | string>`<br>
191
191
  Default: `false`
192
192
 
193
193
  Removes the default directory index file from path that matches any of the provided strings or regexes. When `true`, the regex `/^index\.[a-z]+$/` is used.
@@ -219,6 +219,14 @@ normalizeUrl('www.sindresorhus.com?b=two&a=one&c=three', {
219
219
  - [compare-urls](https://github.com/sindresorhus/compare-urls) - Compare URLs by first normalizing them
220
220
 
221
221
 
222
- ## License
222
+ ---
223
223
 
224
- MIT © [Sindre Sorhus](https://sindresorhus.com)
224
+ <div align="center">
225
+ <b>
226
+ <a href="https://tidelift.com/subscription/pkg/npm-normalize-url?utm_source=npm-normalize-url&utm_medium=referral&utm_campaign=readme">Get professional support for this package with a Tidelift subscription</a>
227
+ </b>
228
+ <br>
229
+ <sub>
230
+ Tidelift helps make open source sustainable for maintainers while giving companies<br>assurances about security, maintenance, and licensing for their dependencies.
231
+ </sub>
232
+ </div>