diff --git a/package.json b/package.json index 83e4713..c7b2983 100644 --- a/package.json +++ b/package.json @@ -49,7 +49,7 @@ "@types/node": "^10.12.10", "@types/tempy": "^0.2.0", "@types/zen-observable": "^0.8.0", - "ava": "*", + "ava": "^0.25.0", "del-cli": "^1.1.0", "jsdom": "^11.6.2", "rxjs": "^6.3.3", diff --git a/readme.md b/readme.md index 1814497..97c023b 100644 --- a/readme.md +++ b/readme.md @@ -255,6 +255,22 @@ is.urlInstance(url); //=> true ``` +### .url(value) + +Returns `true` if `value` is a URL string. + +Note: this only does basic checking using the [`URL` class](https://developer.mozilla.org/en-US/docs/Web/API/URL) constructor. + +```js +const url = 'https://example.com'; + +is.url(url); +//=> true + +is.url(new URL(url)); +//=> false +``` + ##### .truthy(value) Returns `true` for all values that evaluate to true in a boolean context: diff --git a/source/index.ts b/source/index.ts index cc1c7ed..babe375 100644 --- a/source/index.ts +++ b/source/index.ts @@ -2,6 +2,7 @@ /// /// /// +import {URL} from 'url'; type TypedArray = Int8Array | Uint8Array | Uint8ClampedArray | Int16Array | Uint16Array | Int32Array | Uint32Array | Float32Array | Float64Array; type Primitive = null | undefined | string | number | boolean | Symbol; @@ -188,6 +189,19 @@ namespace is { // tslint:disable-line:no-namespace export const directInstanceOf = (instance: unknown, klass: Class): instance is T => Object.getPrototypeOf(instance) === klass.prototype; export const urlInstance = (value: unknown): value is URL => isObjectOfType(TypeName.URL)(value); + export const urlString = (value: unknown) => { + if (!string(value)) { + return false; + } + + try { + new URL(value); // tslint:disable-line no-unused-expression + return true; + } catch { + return false; + } + }; + export const truthy = (value: unknown) => Boolean(value); export const falsy = (value: unknown) => !value; diff --git a/source/tests/test.ts b/source/tests/test.ts index 05dbc11..cc4353e 100644 --- a/source/tests/test.ts +++ b/source/tests/test.ts @@ -576,13 +576,22 @@ test('is.directInstanceOf', t => { }); test('is.urlInstance', t => { - const url = new URL('https://www.example.com'); + const url = new URL('https://example.com'); t.true(is.urlInstance(url)); t.false(is.urlInstance({})); t.false(is.urlInstance(undefined)); t.false(is.urlInstance(null)); }); +test('is.urlString', t => { + const url = 'https://example.com'; + t.true(is.urlString(url)); + t.false(is.urlString(new URL(url))); + t.false(is.urlString({})); + t.false(is.urlString(undefined)); + t.false(is.urlString(null)); +}); + test('is.truthy', t => { t.true(is.truthy('unicorn')); t.true(is.truthy('🦄')); @@ -681,8 +690,9 @@ test('is.class', t => { }); test('is.typedArray', t => { - // Typescript currently does not support empty constructors for these + // TypeScript currently does not support empty constructors for these // See https://github.com/Microsoft/TypeScript/issues/19680 + // TODO: Remove the `0` when targeting `es2017` (Node.js 8), in other places of this file too. const typedArrays = [ new Int8Array(0), new Uint8Array(0),