Flexible and composable runtime type assertion for Javascript. Syntax inspired by prop-types. Supports:
- ES6 data structures
- inner elements in data structures
- nested assertions
- inverse assertions
- custom validators
// takor.oneOf
const isNumOrStr = takor.oneOf(Number, String)
isNumOrStr(10) // true
isNumOrStr(new Set) // false
// takor.shape basic
const checkShape = takor.shape({
key1: takor.oneOf(Number, String)
})
checkShape({ // true
key1: 'string'
})
// takor.shape with nested assertions
const checkNestedElement = takor.shape({
key1: takor.shape({
key2: takor.arrayOf(Number, Set, String)
})
})
checkNestedElement({ // true
key1: {
key2: [0, new Set, '']
}
})
checkNestedElement({ // false
key2: {
key1: [0, new Set, '']
}
})
// supports literal number or string
const isValidDogBreed = takor.oneOf('terrier', 'greyhound', 'golden retriever')
isValidDogBreed('terrier') // true
isValidDogBreed('persian') // false
// custom validator(s)
const lessThanTen = (el) => el < 10
const greaterThanThree = (el) => el > 3
const goodNumberRange = takor.allOf(lessThanTen, greaterThanThree)
// compose existing validator into another
const validNumRangeOrStr = takor.arrayOf(goodNumberRange, String)
validNumRangeOrStr([8, 4, 3.5, 5]) // true
validNumRangeOrStr([8, 4, '100', 5]) // true
validNumRangeOrStr([8, 4, 100, 5]) // false
validNumRangeOrStr(10) // false
validNumRangeOrStr(new Map) // false
// takor.mapOf
const validMap = takor.mapOf(
[Number, takor.oneOf(Array, Set)],
[String, String]
)
validMap(new Map([ // true
[10, []],
[10, new Set],
['10', '10']
]))
validMap(new Map([ // false
[10, []],
[10, new Set],
['10', new Set]
]))
// takor.not
const nonNullOrArray = takor.not.oneOf(null, Array)
nonNullOrArray(10) // true
nonNullOrArray([]) // false
- Quick Examples
- Available Matchers
- Validators
- Inverse Validators
- types
static method | type | description |
---|---|---|
allOf | ListOfMatchers | Passed in validators must meet every criteria |
arrayOf | ListOfMatchers | Asserts the element is an array with specific types stated |
is | SingleMatcher | Performs an assertion on a single value |
mapOf | ListOfTupleMatchers | Asserts inner elemnts of an es6 Map |
oneOf | ListOfMatchers | At least one validator must match |
setOf | ListOfMatchers | Asserts inner elements of a Set |
shape | ShapeOfMatchers | Asserts a specific structure of a pojo (plain old javascript object) |
not.arrayOf | ListOfMatchers | The converse arrayOf |
not.is | SingleMatcher | The converse is |
not.mapOf | ListOfTupleMatchers | The converse mapOf |
not.oneOf | ListOfMatchers | The converse oneOf |
not.setOf | ListOfMatchers | The converse setOf |
not.shape | ShapeOfMatchers | The converse shape |
Out-of-the-box type validators. See examples for usage.
Number
(Constructor)String
(Constructor)Set
(Constructor)Map
(Constructor)Boolean
(Constructor)Array
(Constructor)Function
(Constructor)null
undefined
NaN
true
false
type: IAny
Not a validator. A function that is true
for any value
Intended use is as an argument for validators.
takor.any(10) // true
const assertKeysOnly = takor.shape({
data: takor.shape({
entry: takor.any
})
})
assertKeysOnly({ // true
data: {
entry: []
}
})
type: IFalsey
Not a validator. It is a raw function that checks for any falsey
value type
More information on falsey
can be found on MDN
Intended use is as an argument for validators.
takor.falsey(false) // true
takor.falsey([]) // false
const falseyOnly = takor.arrayOf(takor.falsey)
falseyOnly([1, null, '']) // false
falseyOnly([null, 0, '']) // true
type: IPojo
Not a validator. It is a raw function that if a value is a pojo. Use shape to specify a pojo shape
Intended use is as an argument for validators
takor.pojo({}) // true
takor.pojo(10) // false
// any object or array as long as top level key is `data`
const isPayload = takor.shape({
data: takor.oneOf(takor.pojo, Array)
})
isPayload({ // false
result: {}
})
isPayload({ // true
data: {}
})
isPayload({ // true
data: []
})
type: ITruthy
Not a validator. It is a function that checks if the value is truthy
.
More information on truthy
can be found on MDN
Intended use is as an argument for validators.
takor.truthy(10) // true
takor.truthy(NaN) // false
const truthiesOnly = takor.arrayOf(takor.truthy)
truthiesOnly([1, new Set, '1']) // true
truthiesOnly([1, new Set, '']) // false
type: ListOfMatchers
Passed in validators must meet every criteria
- Contradictory validators will result in
false
const isPopulated = (arr) => arr.length > 0
const populatedStringArr = takor.allOf(takor.arrayOf(String), isPopulated)
populatedStringArr(['']) // true
populatedStringArr([]) // false
populatedStringArr([10]) // false
// contradictory types. impossible to meet criteria
const impossibleCheck = takor.allOf(Number, String)
impossibleCheck(10) // false
impossibleCheck('') // false
type: ListOfMatchers
Asserts the element is an array with specific types stated
const assert = takor.arrayOf(Number)
assert(['Number']) //false
const checkInnerOobj = takor.arrayOf(
takor.shape({
hi: Number
}),
Number,
)
checkInnerOobj([{ hi: 10 }]) // true
const goodShapeNumOrStr = takor.arrayOf(
takor.shape({
hi: Number
}),
String,
Number,
)
goodShapeNumOrStr([10, { hi: 10 }, new Map]) // false
const emptyArr = takor.arrayOf()
emptyArr([]) // true
emptyArr([1]) // false
type: SingleMatcher
Performs an assertion on a single value
This is a less flexible version of typeof. takor.is
only accepts a single validator, while typeof accepts an arbitrary number.
const isStr = takor.is(String)
isStr('') // true
isStr(10) // false
// custom validator
takor.is((el) => el > 0)
enforcer(190) // true
enforcer(-1) // false
type: ListOfTupleMatchers
Asserts inner elemnts of an es6 Map
mapOf
takes an arbitrary number of tuples, correlating to [key, value]
assertions
const allNumbers = takor.mapOf(
[Number, Number]
)
allNumbers(new Map([ // true
[10, 10]
]))
allNumbers(new Map([ // false
[10, '10']
]))
// inner assertion inside mapOf
const valueMapShape = takor.shape({
key: takor.shape({
key2: takor.oneOf(null, Number)
})
})
const checkMapValue = takor.mapOf(
[String, assertShape]
)
checkMapValue(new Map([ // true
['12', { key: { key2: null } }],
])))
type: ListOfMatchers
The converse arrayOf
Any non-Array
value will be true
const checkArray = takor.not.arrayOf(Array, String, Set)
checkArray([[]]) // false
checkArray([10]) // true
checkArray(NaN) // true
type: SingleMatcher
The converse is
const checkStrLen = takor.not.is((str) => str.length === 0)
checkStrLen('') // false
checkStrLen('10') // true
type: ListOfTupleMatchers
The converse mapOf
non-Map
values will always be true
const notAllNumbers = takor.not.mapOf(
[Number, Number]
)
notAllNumbers(new Map([ // false
[10, 10]
]))
notAllNumbers(new Map([ // true
[10, '10']
]))
type: ListOfMatchers
The converse oneOf
const keyIsNotNull = takor.shape({
key: takor.not.oneOf(null)
})
keyIsNotNull(({ // true
key: 10
}))
type: ListOfMatchers
The converse setOf
const notStrs = takor.not.setOf(String)
notStrs(new Set([10])) // true
notStrs(new Set([10, '12'])) // false
type: ShapeOfMatchers
The converse shape
const notEmpty = takor.not.shape({})
notEmpty({ a: 10 }) // true
notEmpty({}) // false
type: ListOfMatchers
At least one validator must match
const numOrStr = takor.oneOf(String, Number)
numOrStr(10) // true
numOrStr(new Set) // false
// check inner elements of an array
const dogOrCat = takor.oneOf('dog', 'cat')
dogOrCat('cat') // true
dogOrCat('bird') // false
type: ListOfMatchers
Asserts inner elements of a Set
const allNums = takor.setOf(Number)
setOfNums(new Set([10, 30, 40])) // true
const strOrNums = takor.setOf(String, Number)
strOrNums(new Set([10, '12'])) // true
strOrNums(new Set([10, '12', new Map])) // false
type: ShapeOfMatchers
Asserts a specific structure of a pojo (plain old javascript object)
shape
checks only top level keys.- Nest another
shape
to assert deeper - Does not check for superfluous keys. Only ensures types of defined keys
const assert = takor.shape({
key: String
})
assert({key: ''}) // true
const assertNested = takor.shape({
key: takor.shape({
key: takor.shape({
key1: String
})
})
})
assertNested({ // false
key: {
els: '10'
}
})
const assertApiPayload = takor.shape({
data: takor.arrayOf(takor.shape({
user: takor.shape({
phoneNumber: Number,
firstName: String
})
}))
})
assertApiPayload({ // true
data: [{
user: {
phoneNumber: 4024224856,
firstName: 'john',
lastName: 'smith' // does not check this key
}
}]
})
// Custom validators are any function that accepts an input value and returns a boolean
type ICustomValidator = (el: any) => boolean
// Baked in common matchers, so you don't have to constantly write them yourself
type IPojo = (el: any) => boolean
type IAny = (el: any) => boolean
type ITruthy = (el: any) => boolean
type IFalsey = (el: any) => boolean
// Shape accepts an object where the value is a validator or a primitive literal
type ShapeOfMatchers = {
[key: string]: IMatcher
}
// A function that takes an arbitrary number of matchers that returns another function to assert values
type ListOfMatchers = (...matchers: IMatcher[]) => (el: any) => boolean
// A function that takes an arbitrary number of tuple of matchers that return another function to assert values
type ListOfTupleMatchers = (...matchers: [IMatcher, IMatcher][]) => (el: any) => boolean
// Only accepts a single matcher
type SingleMatcher = (matcher: IMatcher) => (el: any) => boolean
// List of valid matchers
type IMatcher =
SetConstructor |
MapConstructor |
NumberConstructor |
StringConstructor |
null |
undefined |
ArrayConstructor |
BooleanConstructor |
true |
false |
string |
number |
ICustomValidator | // custom validator
IPojo | // built in matcher
IAny | // built in matcher
ITruthy | // built in matcher
IFalsey // built in matcher