
Security News
Socket Releases Free Certified Patches for Critical vm2 Sandbox Escape
A critical vm2 sandbox escape can allow untrusted JavaScript to break isolation and execute commands on the host Node.js process.
@sidewinder/type
Advanced tools
Sidewinder Types is an extended version of the TypeBox type library. It provides built in support for Uint8Array. It also encodes serializable runtime reflection data allowing remote systems to introspect and reconstruct associative types when schemas are exchanged over the wire. For additional information on TypeBox see the official documentation located here. For validation of the schemas built with this library, refer to the Sidewinder Validation package located here
License MIT
$ npm install @sidewinder/type
The following demonstrates general usage.
import { Static, Type } from '@sidewinder/type'
//--------------------------------------------------------------------------------------------
//
// Let's say you have the following type ...
//
//--------------------------------------------------------------------------------------------
type T = {
id: string
name: string
timestamp: number
}
//--------------------------------------------------------------------------------------------
//
// ... you can express this type in the following way.
//
//--------------------------------------------------------------------------------------------
const T = Type.Object({
// const T = {
id: Type.String(), // type: 'object',
name: Type.String(), // properties: {
timestamp: Type.Integer(), // id: {
}) // type: 'string'
// },
// name: {
// type: 'string'
// },
// timestamp: {
// type: 'integer'
// }
// },
// required: [
// "id",
// "name",
// "timestamp"
// ]
// }
//--------------------------------------------------------------------------------------------
//
// ... then infer back to the original static type this way.
//
//--------------------------------------------------------------------------------------------
type T = Static<typeof T> // type T = {
// id: string,
// name: string,
// timestamp: number
// }
//--------------------------------------------------------------------------------------------
//
// ... then use the type both as JSON schema and as a TypeScript type.
//
//--------------------------------------------------------------------------------------------
function receive(value: T) {
// ... as a Type
if (JSON.validate(T, value)) {
// ... as a Schema
// ok...
}
}
The following table outlines the Sidewinder Type mappings between TypeScript and JSON schema.
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¬āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¬āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā
ā Sidewinder Type ā TypeScript ā JSON Schema ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Any() ā type T = any ā const T = { } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Unknown() ā type T = unknown ā const T = { } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.String() ā type T = string ā const T = { ā
ā ā ā type: 'string' ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Number() ā type T = number ā const T = { ā
ā ā ā type: 'number' ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Integer() ā type T = number ā const T = { ā
ā ā ā type: 'integer' ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Boolean() ā type T = boolean ā const T = { ā
ā ā ā type: 'boolean' ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Null() ā type T = null ā const T = { ā
ā ā ā type: 'null' ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.RegEx(/foo/) ā type T = string ā const T = { ā
ā ā ā type: 'string', ā
ā ā ā pattern: 'foo' ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Literal(42) ā type T = 42 ā const T = { ā
ā ā ā const: 42 ā
ā ā ā type: 'number' ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Array( ā type T = number[] ā const T = { ā
ā Type.Number() ā ā type: 'array', ā
ā ) ā ā items: { ā
ā ā ā type: 'number' ā
ā ā ā } ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Object({ ā type T = { ā const T = { ā
ā x: Type.Number(), ā x: number, ā type: 'object', ā
ā y: Type.Number() ā y: number ā properties: { ā
ā }) ā } ā x: { ā
ā ā ā type: 'number' ā
ā ā ā }, ā
ā ā ā y: { ā
ā ā ā type: 'number' ā
ā ā ā } ā
ā ā ā }, ā
ā ā ā required: ['x', 'y'] ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Tuple([ ā type T = [number, number] ā const T = { ā
ā Type.Number(), ā ā type: 'array', ā
ā Type.Number() ā ā items: [ ā
ā ]) ā ā { ā
ā ā ā type: 'number' ā
ā ā ā }, { ā
ā ā ā type: 'number' ā
ā ā ā } ā
ā ā ā ], ā
ā ā ā additionalItems: false, ā
ā ā ā minItems: 2, ā
ā ā ā maxItems: 2, ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā enum Foo { ā enum Foo { ā const T = { ā
ā A, ā A, ā anyOf: [{ ā
ā B ā B ā type: 'number', ā
ā } ā } ā const: 0 ā
ā ā ā }, { ā
ā const T = Type.Enum(Foo) ā type T = Foo ā type: 'number', ā
ā ā ā const: 1 ā
ā ā ā }] ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.KeyOf( ā type T = keyof { ā const T = { ā
ā Type.Object({ ā x: number, ā enum: ['x', 'y'], ā
ā x: Type.Number(), ā y: number ā type: 'string' ā
ā y: Type.Number() ā } ā } ā
ā }) ā ā ā
ā ) ā ā ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Union([ ā type T = string | number ā const T = { ā
ā Type.String(), ā ā anyOf: [{ ā
ā Type.Number() ā ā type: 'string' ā
ā ]) ā ā }, { ā
ā ā ā type: 'number' ā
ā ā ā }] ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Intersect([ ā type T = { ā const T = { ā
ā Type.Object({ ā x: number ā allOf: [{ ā
ā x: Type.Number() ā } & { ā type: 'object', ā
ā }), ā y: number ā properties: { ā
ā Type.Object({ ā } ā x: { ā
ā y: Type.Number() ā ā type: 'number' ā
ā }) ā ā } ā
ā }) ā ā }, ā
ā ā ā required: ['x'] ā
ā ā ā }, { ā
ā ā ā type: 'object', ā
ā ā ā properties: { ā
ā ā ā y: { ā
ā ā ā type: 'number' ā
ā ā ā } ā
ā ā ā }, ā
ā ā ā required: ['y'] ā
ā ā ā }] ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Record( ā type T = { ā const T = { ā
ā Type.String(), ā [key: string]: number ā type: 'object', ā
ā Type.Number() ā } ā patternProperties: { ā
ā ) ā ā '^.*$': { ā
ā ā ā type: 'number' ā
ā ā ā } ā
ā ā ā } ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Partial( ā type T = Partial<{ ā const T = { ā
ā Type.Object({ ā x: number, ā type: 'object', ā
ā x: Type.Number(), ā y: number ā properties: { ā
ā y: Type.Number() | }> ā x: { ā
ā }) ā ā type: 'number' ā
ā ) ā ā }, ā
ā ā ā y: { ā
ā ā ā type: 'number' ā
ā ā ā } ā
ā ā ā } ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Required( ā type T = Required<{ ā const T = { ā
ā Type.Object({ ā x?: number, ā type: 'object', ā
ā x: Type.Optional( ā y?: number ā properties: { ā
ā Type.Number() | }> ā x: { ā
ā ), ā ā type: 'number' ā
ā y: Type.Optional( ā ā }, ā
ā Type.Number() ā ā y: { ā
ā ) ā ā type: 'number' ā
ā }) ā ā } ā
ā ) ā ā }, ā
ā ā ā required: ['x', 'y'] ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Pick( ā type T = Pick<{ ā const T = { ā
ā Type.Object({ ā x: number, ā type: 'object', ā
ā x: Type.Number(), ā y: number ā properties: { ā
ā y: Type.Number(), | }, 'x'> ā x: { ā
ā }), ['x'] ā ā type: 'number' ā
ā ) ā ā } ā
ā ā ā }, ā
ā ā ā required: ['x'] ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Omit( ā type T = Omit<{ ā const T = { ā
ā Type.Object({ ā x: number, ā type: 'object', ā
ā x: Type.Number(), ā y: number ā properties: { ā
ā y: Type.Number(), | }, 'x'> ā y: { ā
ā }), ['x'] ā ā type: 'number' ā
ā ) ā ā } ā
ā ā ā }, ā
ā ā ā required: ['y'] ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā“āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā“āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā
Sidewinder Types provides modifiers that can be applied to an objects properties. This allows for optional and readonly to be applied to that property. The following table illustates how they map between TypeScript and JSON Schema.
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¬āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¬āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā
ā Sidewinder Type ā TypeScript ā JSON Schema ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Object({ ā type T = { ā const T = { ā
ā name: Type.Optional( ā name?: string, ā type: 'object', ā
ā Type.String(), ā } ā properties: { ā
ā ) ā ā name: { ā
ā }) ā ā type: 'string' ā
ā ā ā } ā
ā ā ā } ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Object({ ā type T = { ā const T = { ā
ā name: Type.Readonly( ā readonly name: string, ā type: 'object', ā
ā Type.String(), ā } ā properties: { ā
ā ) ā ā name: { ā
ā }) ā ā type: 'string' ā
ā ā ā } ā
ā ā ā }, ā
ā ā ā required: ['name'] ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Object({ ā type T = { ā const T = { ā
ā name: Type.ReadonlyOptional( ā readonly name?: string, ā type: 'object', ā
ā Type.String(), ā } ā properties: { ā
ā ) ā ā name: { ā
ā }) ā ā type: 'string' ā
ā ā ā } ā
ā ā ā } ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā“āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā“āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā
You can pass additional JSON schema options on the last argument of any given type. The following are some examples.
// string must be an email
const T = Type.String({ format: 'email' })
// number must be a multiple of 2
const T = Type.Number({ multipleOf: 2 })
// array must have at least 5 integer values
const T = Type.Array(Type.Integer(), { minItems: 5 })
Generic types can be created using functions. The following creates a generic Nullable<T> type.
import { Type, Static, TSchema } from '@sidewinder/type'
// type Nullable<T> = T | null
const Nullable = <T extends TSchema>(type: T) => Type.Union([type, Type.Null()])
const T = Nullable(Type.String()) // const T = {
// "anyOf": [{
// type: 'string'
// }, {
// type: 'null'
// }]
// }
type T = Static<typeof T> // type T = string | null
const U = Nullable(Type.Number()) // const U = {
// "anyOf": [{
// type: 'number'
// }, {
// type: 'null'
// }]
// }
type U = Static<typeof U> // type U = number | null
Types can be referenced with Type.Ref(...). To reference a type, the target type must specify an $id.
const T = Type.String({ $id: 'T' }) // const T = {
// $id: 'T',
// type: 'string'
// }
const R = Type.Ref(T) // const R = {
// $ref: 'T'
// }
It can sometimes be helpful to organize shared referenced types under a common namespace. The Type.Namespace(...) function can be used to create a shared definition container for related types. The following creates a Math3D container and a Vertex structure that references types in the container.
const Math3D = Type.Namespace(
{
// const Math3D = {
Vector4: Type.Object({
// $id: 'Math3D',
x: Type.Number(), // $defs: {
y: Type.Number(), // Vector4: {
z: Type.Number(), // type: 'object',
w: Type.Number(), // properties: {
}), // x: { type: 'number' },
Vector3: Type.Object({
// y: { type: 'number' },
x: Type.Number(), // z: { type: 'number' },
y: Type.Number(), // w: { type: 'number' }
z: Type.Number(), // },
}), // required: ['x', 'y', 'z', 'w']
Vector2: Type.Object({
// },
x: Type.Number(), // Vector3: {
y: Type.Number(), // type: 'object',
}), // properties: {
},
{ $id: 'Math3D' },
) // x: { 'type': 'number' },
// y: { 'type': 'number' },
// z: { 'type': 'number' }
// },
// required: ['x', 'y', 'z']
// },
// Vector2: {
// type: 'object',
// properties: {
// x: { 'type': 'number' },
// y: { 'type': 'number' },
// },
// required: ['x', 'y']
// }
// }
// }
const Vertex = Type.Object({
// const Vertex = {
position: Type.Ref(Math3D, 'Vector4'), // type: 'object',
normal: Type.Ref(Math3D, 'Vector3'), // properties: {
uv: Type.Ref(Math3D, 'Vector2'), // position: { $ref: 'Math3D#/$defs/Vector4' },
}) // normal: { $ref: 'Math3D#/$defs/Vector3' },
// uv: { $ref: 'Math3D#/$defs/Vector2' }
// },
// required: ['position', 'normal', 'uv']
// }
Recursive types can be created with the Type.Rec(...) function. The following creates a Node type that contains an array of inner Nodes. Note that due to current restrictions on TypeScript inference, it is not possible for Sidewinder Types to statically infer for recursive types. Sidewinder Types will infer the inner recursive type as any.
const Node = Type.Rec(
(Self) =>
Type.Object({
// const Node = {
id: Type.String(), // $id: 'Node',
nodes: Type.Array(Self), // $ref: 'Node#/$defs/self',
}),
{ $id: 'Node' },
) // $defs: {
// self: {
// type: 'object',
// properties: {
// id: {
// type: 'string'
// },
// nodes: {
// type: 'array',
// items: {
// $ref: 'Node#/$defs/self'
// }
// }
// }
// }
// }
type Node = Static<typeof Node> // type Node = {
// id: string
// nodes: any[]
// }
function visit(node: Node) {
for (const inner of node.nodes) {
visit(inner as Node) // Assert inner as Node
}
}
In addition to JSON schema types, Sidewinder Types provides several extended types that allow for function and constructor types to be composed. These additional types are not valid JSON Schema and will not validate using typical JSON Schema validation. However, these types can be used to frame JSON schema and describe callable interfaces that may receive JSON validated data. These types are as follows.
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¬āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¬āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā
ā Sidewinder Type ā TypeScript ā Extended Schema ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Constructor([ ā type T = new ( ā const T = { ā
ā Type.String(), ā arg0: string, ā type: 'constructor' ā
ā Type.Number(), ā arg1: number ā arguments: [{ ā
ā ], Type.Boolean()) ā ) => boolean ā type: 'string' ā
ā ā ā }, { ā
ā ā ā type: 'number' ā
ā ā ā }], ā
ā ā ā returns: { ā
ā ā ā type: 'boolean' ā
ā ā ā } ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Function([ ā type T = ( ā const T = { ā
| Type.String(), ā arg0: string, ā type : 'function', ā
ā Type.Number(), ā arg1: number ā arguments: [{ ā
ā ], Type.Boolean()) ā ) => boolean ā type: 'string' ā
ā ā ā }, { ā
ā ā ā type: 'number' ā
ā ā ā }], ā
ā ā ā returns: { ā
ā ā ā type: 'boolean' ā
ā ā ā } ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Promise( ā type T = Promise<string> ā const T = { ā
ā Type.String() ā ā type: 'promise', ā
ā ) ā ā item: { ā
ā ā ā type: 'string' ā
ā ā ā } ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Undefined() ā type T = undefined ā const T = { ā
ā ā ā type: 'undefined' ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Uint8Array() ā type T = Uint8Array ā const T = { ā
ā ā ā type: 'object', ā
ā ā ā specialized: 'Uint8Array' ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¼āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā¤
ā const T = Type.Void() ā type T = void ā const T = { ā
ā ā ā type: 'null' ā
ā ā ā } ā
ā ā ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā“āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā“āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā
FAQs
Sidewinder Type
The npm package @sidewinder/type receives a total of 110 weekly downloads. As such, @sidewinder/type popularity was classified as not popular.
We found that @sidewinder/type demonstrated a not healthy version release cadence and project activity because the last version was released a year ago.Ā It has 0 open source maintainers collaborating on the project.
Did you know?

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Security News
A critical vm2 sandbox escape can allow untrusted JavaScript to break isolation and execute commands on the host Node.js process.

Research
Five malicious NuGet packages impersonate Chinese .NET libraries to deploy a stealer targeting browser credentials, crypto wallets, SSH keys, and local files.

Security News
pnpm 11 turns on a 1-day Minimum Release Age and blocks exotic subdeps by default, adding safeguards against fast-moving supply chain attacks.