Package Exports
- guardz
- guardz/dist/index.js
This package does not declare an exports field, so the exports above have been automatically detected and optimized by JSPM instead. If any package subpath is missing, it is recommended to post an issue to the original package (guardz) to support the "exports" field. If that is not possible, create a JSPM override to customize the exports field for this package.
Readme
Guardz
A comprehensive TypeScript type guard library with advanced validation capabilities, error reporting, and performance optimizations.
🚀 Quick Start
Installation
# npm
npm install guardz
# yarn
yarn add guardz
# pnpm
pnpm add guardz
TypeScript Configuration
Ensure your tsconfig.json
includes:
{
"compilerOptions": {
"strict": true,
"noImplicitAny": true,
"exactOptionalPropertyTypes": true
}
}
Basic Usage
import { isNonEmptyString, isNumber, isString, isType } from 'guardz';
// Basic guard
const value: unknown = getUnknownValue();
if(isString(value)) {
// TypeScript now knows value is a string - type narrowing in action
console.log(value.length); // Safe to access string properties
}
// Simulate getting data from an external source (API, database, etc.)
const maybeUser: unknown = await getUserInfoFromServer();
// Define a type guard for user type checking
const isUser = isType<UserDTO>({
id: isNumber,
name: isNonEmptyString,
email: isNonEmptyString,
});
// Use type guard for type narrowing
if (isUser(maybeUser)) {
// TypeScript now knows maybeUser is a valid UserDTO
console.log(maybeUser.id);
console.log(maybeUser.name);
console.log(maybeUser.email);
}
🎯 Type Guards vs Validators
Guardz is a type guard library, not a validation library.
Guardz focuses on providing lightweight, composable type guards that enable TypeScript's type narrowing while maintaining excellent performance. For a detailed explanation of the differences between type guards and validators, see this comprehensive guide.
✨ Features
- Comprehensive Type Guards: 50+ built-in type guards for all JavaScript types
- Advanced Type Narrowing: Array type guards, object type guards, union types, and more
- TypeScript Integration: Seamless type narrowing with exact type inference
- Performance Optimized: Fast type guards with minimal overhead
- TypeScript First: Full type safety with precise type inference
- Zero Dependencies: Lightweight with no external dependencies
- Tree Shaking: Optimized for bundle size with tree shaking support
📖 Basic Examples
Basic Type Guards
import { isString, isNumber, isBoolean, isSymbol, isArrayWithEachItem, isObject } from 'guardz';
isString('hello'); // true
isNumber(42); // true
isBoolean(true); // true
isSymbol(Symbol('a')); // true
isArrayWithEachItem(isNumber)([1, 2, 3]); // true
isObject({ a: 1 }); // true
isSymbol Example
import { isSymbol } from 'guardz';
const value: unknown = Symbol('test');
if (isSymbol(value)) {
// value is now typed as symbol
console.log(value.toString());
}
Object Type Guards
import { isType, isString, isNumber, isPositiveInteger, isUndefinedOr } from 'guardz';
interface User {
id: number;
name: string;
email: string;
age?: number;
}
const isUser = isType<User>({
id: isPositiveInteger,
name: isString,
email: isString,
age: isUndefinedOr(isNumber), // Handle optional property
});
const user = { id: 1, name: 'John', email: 'john@example.com' };
console.log(isUser(user)); // true
Array Type Guards
import { isArrayWithEachItem, isString, isNumber } from 'guardz';
const isStringArray = isArrayWithEachItem(isString);
const isNumberArray = isArrayWithEachItem(isNumber);
console.log(isStringArray(['a', 'b', 'c'])); // true
console.log(isNumberArray([1, 2, 3])); // true
Array Utilities
import { isString, isNumber, isType, by } from 'guardz';
const isUser = isType({ name: isString, age: isNumber });
const users = [
{ name: 'Alice', age: 25 },
{ name: 'Bob', age: '30' }, // invalid
{ name: 'Charlie', age: 35 },
];
// ❌ This won't work due to parameter mismatch
// const validUsers = users.filter(isUser);
// ✅ Use by for simple filtering
const validUsers = users.filter(by(isUser));
console.log('Valid users:', validUsers);
Union Types
import { isOneOfTypes, isString, isNumber, isBoolean } from 'guardz';
const isPrimitive = isOneOfTypes(isString, isNumber, isBoolean);
console.log(isPrimitive('hello')); // true
console.log(isPrimitive(42)); // true
console.log(isPrimitive(true)); // true
console.log(isPrimitive({})); // false
Error Handling
import { isType, isString, isNumber } from 'guardz';
const errors: string[] = [];
const config = {
identifier: 'user',
callbackOnError: (error: string) => errors.push(error),
errorMode: 'multi', // 'single' | 'multi' | 'json'
};
const isUser = isType({
name: isString,
age: isNumber,
});
const invalidUser = { name: 123, age: 'thirty' };
const result = isUser(invalidUser, config);
console.log(result); // false
console.log(errors); // ['user.name: Expected string, got number (123)', 'user.age: Expected number, got string ("thirty")']
Pattern Validation
import { isRegex, isPattern } from 'guardz';
import type { Pattern } from 'guardz';
// Validate RegExp objects
const patterns: unknown[] = [/^[a-z]+$/, new RegExp('\\d+'), 'not a regex'];
patterns.forEach(pattern => {
if (isRegex(pattern)) {
console.log(`Valid RegExp: ${pattern.source} (flags: ${pattern.flags})`);
}
});
// Create branded types for pattern-matched strings
type Email = Pattern<'Email'>;
type PhoneNumber = Pattern<'PhoneNumber'>;
type URL = Pattern<'URL'>;
const isEmail = isPattern<'Email'>(/^[^\s@]+@[^\s@]+\.[^\s@]+$/);
const isPhoneNumber = isPattern<'PhoneNumber'>('^\\+?[\\d\\s\\-()]{10,}$');
const isUrl = isPattern<'URL'>('^https?:\\/\\/.+');
// Validate strings against patterns
const email: unknown = 'user@example.com';
if (isEmail(email)) {
// email is now typed as Email (branded string)
console.log(`Valid email: ${email}`);
}
const phone: unknown = '+1-555-123-4567';
if (isPhoneNumber(phone)) {
// phone is now typed as PhoneNumber (branded string)
console.log(`Valid phone: ${phone}`);
}
// Type safety with branded types
function processEmail(email: Email) {
// This function only accepts validated email strings
console.log(`Processing email: ${email}`);
}
function processPhoneNumber(phone: PhoneNumber) {
// This function only accepts validated phone number strings
console.log(`Processing phone: ${phone}`);
}
// These work with type safety:
const validEmail: unknown = 'user@example.com';
if (isEmail(validEmail)) {
processEmail(validEmail); // TypeScript knows this is safe
}
// These would cause TypeScript errors:
// processEmail('invalid-email'); // Error: Argument of type 'string' is not assignable to parameter of type 'Email'
// processPhoneNumber('123'); // Error: Argument of type 'string' is not assignable to parameter of type 'PhoneNumber'
🎯 Common Use Cases
API Response Validation
import { isType, isString, isNumber, isArrayWithEachItem, isOneOf } from 'guardz';
interface ApiResponse<T> {
data: T;
status: 'success' | 'error';
message: string;
timestamp: number;
}
const isUserResponse = isType<ApiResponse<User>>({
data: isType({
id: isNumber,
name: isString,
email: isString,
}),
status: isOneOf('success', 'error'), // Use isOneOf for exact values
message: isString,
timestamp: isNumber,
});
// Validate API responses
const response = await fetch('/api/users/1');
const data = await response.json();
if (isUserResponse(data)) {
console.log('Valid user:', data.data.name);
} else {
console.log('Invalid response format');
}
Form Data Validation
import { isType, isString, isNumber, isPositiveInteger } from 'guardz';
interface RegistrationForm {
username: string;
email: string;
age: number;
password: string;
}
const isRegistrationForm = isType<RegistrationForm>({
username: isString,
email: isString, // Could add email regex validation
age: isPositiveInteger,
password: isString,
});
const formData = {
username: 'john_doe',
email: 'john@example.com',
age: 25,
password: 'secure123',
};
if (isRegistrationForm(formData)) {
// Process valid form data
await registerUser(formData);
} else {
// Handle validation errors
showValidationErrors(errors);
}
Database Result Validation
import { isType, isString, isNumber, isDate } from 'guardz';
interface DatabaseUser {
id: number;
username: string;
email: string;
created_at: string;
updated_at: string;
}
const isDatabaseUser = isType<DatabaseUser>({
id: isNumber,
username: isString,
email: isString,
created_at: isString,
updated_at: isString,
});
// Validate database results
const users = await db.query('SELECT * FROM users');
const validUsers = users.filter(isDatabaseUser);
Configuration Validation
import { isType, isString, isNumber, isBoolean } from 'guardz';
interface AppConfig {
port: number;
database: {
host: string;
port: number;
name: string;
};
features: {
auth: boolean;
caching: boolean;
};
}
const isAppConfig = isType<AppConfig>({
port: isNumber,
database: isType({
host: isString,
port: isNumber,
name: isString,
}),
features: isType({
auth: isBoolean,
caching: isBoolean,
}),
});
// Validate environment configuration
const config = {
port: process.env.PORT ? parseInt(process.env.PORT) : 3000,
database: {
host: process.env.DB_HOST || 'localhost',
port: process.env.DB_PORT ? parseInt(process.env.DB_PORT) : 5432,
name: process.env.DB_NAME || 'myapp',
},
features: {
auth: process.env.AUTH_ENABLED === 'true',
caching: process.env.CACHE_ENABLED === 'true',
},
};
if (!isAppConfig(config)) {
throw new Error('Invalid configuration');
}
🔧 Advanced Features
Reusable Type Guard Patterns
Create reusable type guard functions for consistent validation patterns:
import { isString, isNumber, isPositiveInteger, isType } from 'guardz';
// Create semantic type guards using existing functions
const isUserId = isPositiveInteger; // Already a reusable type guard
const isEmail = isString; // Already a reusable type guard
const isName = isString; // Already a reusable type guard
// Use them consistently across your application
interface User {
id: number; // Uses isUserId (isPositiveInteger)
name: string; // Uses isName (isString)
email: string; // Uses isEmail (isString)
}
const isUser = isType<User>({
id: isUserId,
name: isName,
email: isEmail,
});
Generic Types
For complex generic types with conditional properties, use factory functions with isType
:
import { isType, isString, isNumber, isUndefinedOr } from 'guardz';
// Define generic types with conditional properties
type ApiKeysSelect<T extends boolean = true> = {
name: T extends true ? string : string | undefined;
collectionPermissions: T extends true ? string : string | undefined;
updatedAt: T extends true ? string : string | undefined;
createdAt: T extends true ? string : string | undefined;
enableAPIKey: T extends true ? boolean : boolean | undefined;
apiKey: T extends true ? string : string | undefined;
apiKeyIndex: T extends true ? number : number | undefined;
};
// Create type guard factory for generic types
export const isApiKeysSelect = <T extends boolean = true>(
typeGuardT: TypeGuardFn<T>,
): TypeGuardFn<ApiKeysSelect<T>> =>
isType<ApiKeysSelect<T>>({
name: isUndefinedOr(typeGuardT),
collectionPermissions: isUndefinedOr(typeGuardT),
updatedAt: isUndefinedOr(typeGuardT),
createdAt: isUndefinedOr(typeGuardT),
enableAPIKey: isUndefinedOr(typeGuardT),
apiKey: isUndefinedOr(typeGuardT),
apiKeyIndex: isUndefinedOr(typeGuardT),
});
// Usage
const isRequiredApiKeys = isApiKeysSelect(isString);
const isOptionalApiKeys = isApiKeysSelect(isUndefinedOr(isString));
💡 Pro Tip: For complex generic type validation with multiple conditional properties, consider using guardz-generator which automatically generates type guards for generic types and handles conditional properties efficiently.
Advanced Generic Patterns
// Multiple generic parameters
type Container<T, U, V extends boolean = true> = {
primary: T;
secondary: U;
metadata: V extends true ? { timestamp: number; version: string } : undefined;
};
// Factory for multiple generic parameters
export const isContainer = <T, U, V extends boolean = true>(
primaryGuard: TypeGuardFn<T>,
secondaryGuard: TypeGuardFn<U>,
metadataGuard?: TypeGuardFn<{ timestamp: number; version: string }>,
): TypeGuardFn<Container<T, U, V>> =>
isType<Container<T, U, V>>({
primary: primaryGuard,
secondary: secondaryGuard,
metadata: metadataGuard ? isUndefinedOr(metadataGuard) : undefined,
});
// Usage
const isStringNumberContainer = isContainer(isString, isNumber);
const isStringNumberContainerWithMetadata = isContainer(
isString,
isNumber,
isType({ timestamp: isNumber, version: isString })
);
Performance Optimizations
import { isType, isString, isNumber, isArrayWithEachItem } from 'guardz';
// Optimized for repeated validation
const isUser = isType({
id: isNumber,
name: isString,
tags: isArrayWithEachItem(isString),
});
// Reuse the same guard instance
const users = [/* large array of user objects */];
const validUsers = users.filter(isUser); // Fast validation
// Use appropriate error modes for performance
const fastConfig = { errorMode: 'single' }; // Fastest
const detailedConfig = { errorMode: 'multi' }; // More detailed
const treeConfig = { errorMode: 'json' }; // Most detailed
🔄 Migration Guide
From Zod
// Zod
import { z } from 'zod';
const UserSchema = z.object({
id: z.number(),
name: z.string(),
email: z.string().email(),
});
// Guardz
import { isType, isNumber, isString } from 'guardz';
const isUser = isType({
id: isNumber,
name: isString,
email: isString, // Add custom email validation if needed
});
From Joi
// Joi
import Joi from 'joi';
const userSchema = Joi.object({
id: Joi.number().required(),
name: Joi.string().required(),
email: Joi.string().email().required(),
});
// Guardz
import { isType, isNumber, isString } from 'guardz';
const isUser = isType({
id: isNumber,
name: isString,
email: isString,
});
From Yup
// Yup
import * as yup from 'yup';
const userSchema = yup.object({
id: yup.number().required(),
name: yup.string().required(),
email: yup.string().email().required(),
});
// Guardz
import { isType, isNumber, isString } from 'guardz';
const isUser = isType({
id: isNumber,
name: isString,
email: isString,
});
🛠️ Troubleshooting
Common Issues
TypeScript Errors
Problem: Type 'unknown' is not assignable to parameter of type 'TypeGuardFn<T>'
Solution: Ensure you're using the correct type guard function:
// ❌ Wrong
const isUser = isType({
id: isNumber, // This is correct
name: 'string', // ❌ This is wrong - should be isString
});
// ✅ Correct
const isUser = isType({
id: isNumber,
name: isString, // ✅ Use the type guard function
});
Performance Issues
Problem: Validation is slow with large objects
Solution: Use appropriate error modes and optimize validation:
// ❌ Slow - collects all errors
const result = isUser(data, { errorMode: 'multi' });
// ✅ Fast - stops at first error
const result = isUser(data, { errorMode: 'single' });
// ✅ Fastest - no error collection
const result = isUser(data);
Bundle Size Issues
Problem: Large bundle size
Solution: Use tree shaking and import only what you need:
// ❌ Imports everything
import * as guardz from 'guardz';
// ✅ Only imports what you need
import { isType, isString, isNumber } from 'guardz';
Debugging
Enable detailed error reporting:
const errors: string[] = [];
const config = {
identifier: 'user',
callbackOnError: (error: string) => {
errors.push(error);
console.log('Validation error:', error);
},
errorMode: 'multi',
};
const result = isUser(data, config);
console.log('All errors:', errors);
⚡ Performance Tips
Error Mode Selection
single
(default): Fastest, stops at first errormulti
: Medium speed, collects all errors with detailsjson
: Slowest, provides hierarchical error tree structure
Validation Strategies
// For production - fast validation
const isUserFast = isType({
id: isNumber,
name: isString,
email: isString,
});
// For development - detailed errors
const isUserDev = isType({
id: isNumber,
name: isString,
email: isString,
});
// Usage
const config = process.env.NODE_ENV === 'production'
? undefined
: { errorMode: 'multi', callbackOnError: console.error };
Caching Type Guards
// Create type guards once, reuse them
const isUser = isType({
id: isNumber,
name: isString,
email: isString,
});
// Reuse the same guard instance
const validateUsers = (users: unknown[]) => {
return users.filter(isUser);
};
🔧 API Reference
Primitive Type Guards
isString
- Validates that a value is a stringisNumber
- Validates that a value is a valid number (excludes NaN)isBoolean
- Validates that a value is a booleanisBigInt
- Validates that a value is a BigIntisFunction
- Validates that a value is a function (including regular functions, arrow functions, class constructors, and methods)isSymbol
- Validates that a value is a Symbol
Special Type Guards
isAsserted
- Always returns true and asserts value is T (useful for 3rd party types without runtime validation)isEnum
- Creates a type guard that checks if a value matches any value from an enumisEqualTo
- Creates a type guard that checks if a value is exactly equal to a specific value using strict equality (===)isRegex
- Validates that a value is a RegExp objectisPattern<P>
- Creates a type guard that validates strings against a regex pattern and returns a branded type
Array Type Guards
isArrayWithEachItem<T>(typeGuard: TypeGuardFn<T>)
- Creates a type guard that validates arrays where each item matches a specific typeisNonEmptyArray
- Validates that a value is a non-empty arrayisNonEmptyArrayWithEachItem<T>(typeGuard: TypeGuardFn<T>)
- Creates a type guard that validates non-empty arrays where each item matches a specific type
Object Type Guards
isNonNullObject
- Validates that a value is a non-null object (excludes arrays)isType<T>(schema: Record<string, TypeGuardFn<any>>)
- Creates a type guard that validates objects against a schemaisObject<T>(schema: Record<string, TypeGuardFn<any>>)
- Alias for isType - creates a type guard for a specific object shapeisObjectWith<T>(schema: Record<string, TypeGuardFn<any>>)
- Alias for isType - validates objects with specific propertiesisObjectWithEachItem<T>(typeGuard: TypeGuardFn<T>)
- Creates a type guard that validates plain objects where each property value matches a specific type (only checks enumerable own properties)
Number Type Guards
isInteger
- Validates that a value is an integer (whole number)isPositiveInteger
- Validates that a value is a positive integer (greater than 0 and a whole number)isNegativeInteger
- Validates that a value is a negative integer (less than 0 and a whole number)isNonNegativeInteger
- Validates that a value is a non-negative integer (0 or greater and a whole number)isNonPositiveInteger
- Validates that a value is a non-positive integer (0 or less and a whole number)isPositiveNumber
- Validates that a value is a positive number (greater than 0)isNegativeNumber
- Validates that a value is a negative number (less than 0)isNonNegativeNumber
- Validates that a value is a non-negative number (0 or greater)isNonPositiveNumber
- Validates that a value is a non-positive number (0 or less)isNumeric
- Validates that a value is numeric (a number or a string that can be converted to a number)isDateLike
- Validates that a value can be treated as a Date (Date object, date string, or numeric timestamp)
String Type Guards
isNonEmptyString
- Validates that a value is a non-empty string (trims whitespace, so strings containing only whitespace are considered empty)
Null/Undefined Type Guards
isNil
- Validates that a value is null or undefinedisNullOr
- Creates a type guard that validates if a value is either null or matches a specific typeisUndefinedOr
- Creates a type guard that validates if a value is either undefined or matches a specific typeisNilOr
- Creates a type guard that validates if a value is either of type T, null, or undefined
Union Type Guards
isOneOf
- Creates a type guard that checks if a value matches one of several specific values using strict equality (===)isOneOfTypes
- Creates a type guard that checks if a value matches at least one of several type guards
Web API Type Guards
isDate
- Validates that a value is a valid Date object (excludes invalid dates likenew Date("invalid")
)isError
- Validates that a value is an Error objectisBlob
- Validates that a value is a Blob objectisFile
- Validates that a value is a File objectisFileList
- Validates that a value is a FileList objectisFormData
- Validates that a value is a FormData objectisURL
- Validates that a value is a URL objectisURLSearchParams
- Validates that a value is a URLSearchParams object
Collection Type Guards
isMap
- Validates that a value is a Map objectisSet
- Validates that a value is a Set objectisIndexSignature
- Creates a type guard that validates objects with index signatures (objects with dynamic keys of a specific type and values of a specific type)
Utility Type Guards
isUnknown
- Always returns true (useful for unknown types)isAny
- Always returns true (useful for any types)isDefined
- Validates that a value is defined (not null/undefined)isBooleanLike
- Validates that a value can be treated as a boolean (boolean, "true"/"false", "1"/"0", or 1/0)isExtensionOf
- Creates a type guard for types that extend a base type by combining a base type guard with validation for additional properties (useful for inheritance patterns)isIntersectionOf
- Creates a type guard that validates a value against multiple type guards, ensuring the value satisfies all of themisPartialOf
- Creates a type guard that validates partial objects matching a specific type (allows missing properties)isTuple
- Creates a type guard that validates tuples (fixed-length arrays with specific types at each position)
Schema Type Guards
isSchema
- Creates a type guard function for object schemas with improved nested type support (automatically handles nested structures)isShape
- Alias for isSchemaisNestedType
- Alias for isSchema
Advanced Type Guards
isBranded
- Creates a type guard function for a branded type using a predicate function (validates and narrows to branded types)guardWithTolerance
- Validates data against a type guard but returns the data regardless of validation result (useful for logging errors while proceeding with potentially invalid data)
Type Guard Error Generation
generateTypeGuardError
- Generates error messages for type guard failures
Utility Types
PredicateFn
- A predicate function that validates a value and returns true if valid, false otherwise
Type Converters
toNumber
- Converts a Numeric value to a number (safely converts validated numeric values)toDate
- Converts a DateLike value to a Date object (safely converts validated date values)toBoolean
- Converts a BooleanLike value to a boolean (safely converts validated boolean values)
Validation Types
ValidationError
- Error type for validation failures with path, expected type, actual value, and messageValidationTree
- Tree structure for hierarchical validation errorsValidationResult
- Result type for validation operations with validity status and errorsValidationContext
- Context type for validation operations with path and configuration
Branded Types
Branded<T, B>
- Branded type with a specific brand identifier (supports string and unique symbol brands)BrandSymbols
- Predefined brand symbols for common use casesBrandedWith<T, K>
- Utility type to create branded types with predefined symbolsNonEmptyArray<T>
- Array type that cannot be emptyNonEmptyString
- String type that cannot be emptyPositiveNumber
- Number type that must be positiveNegativeNumber
- Number type that must be negativeNonNegativeNumber
- Number type that must be non-negativeNonPositiveNumber
- Number type that must be non-positivePositiveInteger
- Integer type that must be positiveNegativeInteger
- Integer type that must be negativeNonNegativeInteger
- Integer type that must be non-negativeNonPositiveInteger
- Integer type that must be non-positiveInteger
- Integer typeNullable<T>
- Type that can be nullNumeric
- Numeric type (number or string that can be converted to number)DateLike
- Date-like type (Date object, date string, or numeric timestamp)BooleanLike
- Boolean-like type (boolean, "true"/"false", "1"/"0", or 1/0)Pattern<P>
- Branded string type that matches a specific regex pattern
🛠️ Error Generation
Guardz provides detailed error reporting with configurable error handling:
import { isType, isString, isNumber } from 'guardz';
const errors: string[] = [];
const config = {
identifier: 'user',
callbackOnError: (error: string) => errors.push(error),
errorMode: 'multi', // 'single' | 'multi' | 'json'
};
const isUser = isType({
name: isString,
age: isNumber,
});
const invalidUser = { name: 123, age: 'thirty' };
const result = isUser(invalidUser, config);
console.log(errors);
// [
// 'user.name: Expected string, got number (123)',
// 'user.age: Expected number, got string ("thirty")'
// ]
Error Modes
single
- Basic error messages (default)multi
- Detailed error messages with valuesjson
- Hierarchical error tree structure
🎯 Utility Types
Guardz provides utility types for enhanced type safety:
import type { TypeGuardFn, TypeGuardFnConfig } from 'guardz';
// TypeGuardFn<T> - Type guard function type
// TypeGuardFnConfig - Configuration for type guards
🔐 Unique Symbol Branded Types
Guardz supports branded types with unique symbols for enhanced type safety:
import { isBranded, Branded, BrandSymbols, type BrandedWith } from 'guardz';
// Custom unique symbol brands
const UserIdBrand = Symbol('UserId');
type UserId = Branded<number, typeof UserIdBrand>;
const isUserId = isBranded<UserId>((value) => {
return typeof value === 'number' && value > 0 && Number.isInteger(value);
});
// Predefined brand symbols
type Email = BrandedWith<string, 'Email'>;
const isEmail = isBranded<Email>((value) => {
if (typeof value !== 'string') return false;
const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
return emailRegex.test(value);
});
// Usage
const id: unknown = 123;
if (isUserId(id)) {
// id is now typed as UserId (number & { readonly brand: typeof UserIdBrand })
console.log(id);
}
🤝 Contributing
We welcome contributions! Please see our Contributing Guide for details.
Development Setup
git clone https://github.com/thiennp/guardz.git
cd guardz
npm install
npm test
📄 License
This project is licensed under the MIT License - see the LICENSE file for details.
📚 Documentation
- API Reference: GitHub README
- Showcases: Complete TypeScript Examples - All possible TypeScript cases and real-world scenarios
- Examples: Practical Usage Examples - Ready-to-run code samples
- CHANGELOG: Version History - Latest updates and changes
🆘 Support
- Issues: GitHub Issues
- Discussions: GitHub Discussions
- Email: nguyenphongthien@gmail.com
🔗 Related Projects
- guardz-generator - Code generator for complex type guards and generic types
- guardz-cli - Command-line interface for Guardz
- guardz-vscode - VS Code extension for Guardz
🙏 Acknowledgments
Thanks to all contributors and the TypeScript community for making this project possible.
Made with ❤️ by the Guardz Team