npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

@twilio/declarative-type-validator

v0.2.8

Published

Declarative runtime type validator for JavaScript

Downloads

578,321

Readme

Declarative Type Validator

Provides runtime type validation functionality for class methods and functions.

Usage

Most of the time, using a decorator is the most convenient way to apply type checking to a class method:

import { validateTypesAsync } from "@twilio/declarative-type-validator";

class TestClass {
  @validateTypes("number")
  someMethod(value) {
    console.log(`value is a number: ${value}`);
  }
}

Or if it is an async method, you could use an async version of the decorator, in which case the type error will be thrown as a rejected promise:

import { validateTypesAsync } from "@twilio/declarative-type-validator";

class TestClass {
  @validateTypesAsync("number")
  async someMethod(value) {
    console.log(`value is a number: ${value}`);
  }
}

Each argument passed into the decorator should be a valid rule that corresponds to the respective argument of the method being decorated. If an argument requires more than one check, you can pass an array of rules which will get applied following the OR logic:

import { validateTypesAsync } from "@twilio/declarative-type-validator";

class TestClass {
  @validateTypes(["number", "string"])
  someMethod(value) {
    console.log(`value is either a number or a string: ${value}`);
  }

  @validateTypes("string", ["number", "boolean"])
  someOtherMethod(value, secondValue) {
    console.log(`value is a string: ${value}`);
    console.log(`secondValue is either a number or a boolean: ${secondValue}`);
  }
}

Since constructors can't be decorated the same way that normal methods can, you could utilize the validateConstructorTypes decorator (applied to the class itself, as opposed to the constructor method) to apply argument validation to the constructor:

import { validateConstructorTypes } from "@twilio/declarative-type-validator";

@validateConstructorTypes("string", ["number", "boolean"])
class TestClass {
  constructor(value, secondValue) {
    console.log(`value is a string: ${value}`);
    console.log(`secondValue is either a number or a boolean: ${secondValue}`);
  }
}

For functions outside of classes, you can utilize runtimeTypeValidation function instead. It accepts two arguments, first being the array of rules (each element of the array corresponding to an array of rules for the respective argument), with the second being the arguments to validate.

Here's an example of the two methods from previous example rewritten using the runtimeTypeValidation function:

import { runtimeTypeValidation } from "@twilio/declarative-type-validator";

function someFunction(value) {
  runtimeTypeValidation([[type("number")]], [value]);

  console.log(`value is a number: ${value}`);
}

function someOtherFunction(value, secondValue) {
  runtimeTypeValidation(
    [[type("string")], [type("number", "boolean")]],
    [value, secondValue]
  );

  console.log(`value is a string: ${value}`);
  console.log(`secondValue is either a number or a boolean: ${secondValue}`);
}

Rules

Type validator comes with a few prebuilt rules. They come in two shapes: rule factories and rule constants.

Rule factories are functions which generate an object describing the validation rule. Every single rule factory accepts one or multiple arguments. The rule factories are:

  • type
  • literal
  • custom
  • objectSchema
  • array

Rule constants are pre-made rule objects which don't require any parameters. The rule constants are:

  • nonEmptyString
  • nonNegativeInteger
  • pureObject

type

Validates against either a primitive type (typeof x) or a constructor function (instanceof x). If multiple arguments are passed, then they will be applied following the OR logic.

Note

Using the type rule factory itself could be omitted if a string representing a primitive type or a constructor function is passed as a rule itself.

Examples

Single primitive type
@validateTypes(type("number"))
// OR
@validateTypes("number")
Multiple primitive types for the same argument
@validateTypes(["number", "string"])
// OR
@validateTypes(type("number", "string"))
// OR
@validateTypes([type("number"), type("string")])
Single constructor function (class)
@validateTypes(FormData)
Multiple constructor functions (classes) for the same argument
@validateTypes([FormData, Blob])
// OR
@validateTypes(type(FormData, Blob))
// OR
@validateTypes([type(FormData), type(Blob)])

literal

Validates against a literal value (compared using the strict equality operator ===). If multiple arguments are passed, then they will be applied following the OR logic.

Examples

Single literal
@validateTypes(literal("foobar"))
Multiple literals for the same argument
@validateTypes(literal("foobar", 15))
// OR
@validateTypes([literal("foobar"), literal(15)])

custom

Validates against a custom rule. The custom rule is represented as a function that returns a tuple of type [boolean, string] where the boolean is whether the check has passed and the string is the description of the rule. The value to validate gets passed as the first argument.

If multiple arguments are passed to the custom rule, then they will be applied following the OR logic.

Examples

Validate that a number is greater than 15
@validateTypes(
  custom((value) => [
    typeof value === "number" && value > 15,
    "a number greater than 15",
  ])
)

nonEmptyString

Validates a non-empty string.

Example

@validateTypes(nonEmptyString)

nonNegativeInteger

Validates a non-negative integer. I.E., it should contain no decimal point and be greater than or equal to 0.

Example

@validateTypes(nonNegativeInteger)

pureObject

Validates an object that is not null and is not an array.

Example

@validateTypes(pureObject)

objectSchema

Validates an object against a schema. The first argument is a short description of the object (which will appear in runtime type errors) with the second argument being the schema itself. The rule will validates every key of the schema object against a rule (or a set of rules) defined as values.

Examples

A simple object schema
@validateTypes(
  objectSchema("network configuration", {
    port: "number",
    protocol: literal("http", "https"),
    retries: custom((value) => [
      typeof value === "number" && value > 0 && value < 16,
      "a value between 0 (exclusive) and 15 (inclusive)"
    ])
  })
)
A nested object schema
@validateTypes(
  objectSchema("root object", {
    foo: ["boolean", "number"],
    bar: objectSchema("child object", {
      baz: "number",
    }),
  })
)

array

Validates an array. The first argument is the description of the expected items in the plural form (E.G.: "items" or "numbers"). The second argument is the rule (or an array of rules, if there are multiple) that each element of the array should conform to.

Examples

An array of numbers
@validateTypes(array("numbers", "number"))
An array of numbers and/or strings
@validateTypes(array("numbers and/or strings", ["number", "string"]))
An array of arrays of numbers
@validateTypes(array("arrays of numbers", array("numbers", "number")))