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 🙏

© 2026 – Pkg Stats / Ryan Hefner

@contrail/type-validation

v1.0.50

Published

Defines various utilities and interfaces related to type validation.

Readme

TypeRuleSet Technical Documentation

Overview

TypeRuleSets provide a powerful, conditional validation and constraint system for entities. They allow you to define rules that apply only when specific criteria are met, enabling dynamic validation based on entity state.

Data Structure

TypeRuleSet Interface

interface TypeRuleSet {
  ruleSet: Array<ConditionalTypeRules>;
}

ConditionalTypeRules Interface

interface ConditionalTypeRules {
  criteria: FilterCriteria; // When to apply these rules
  rules: Array<TypeRule>; // What rules to apply
}

TypeRule Interface

interface TypeRule {
  slug: string; // Property to validate (or "ALL" for all properties)
  excludedSlugs?: string[]; // Properties to exclude when slug="ALL"
  required?: boolean; // Whether the property is required
  editable?: boolean; // Whether the property is editable
  optionSetValues?: string[]; // Allowed option set values
  invalidValues?: string[]; // Disallowed values
  minValue?: number; // Minimum numeric value
  maxValue?: number; // Maximum numeric value
  validationFunction?: string; // Custom validation function
}

Supported Filter Condition Types

The criteria field uses the same filter system as the rest of the application:

| Condition | Description | Example Use Cases | | ----------------------- | ------------------------- | ------------------------------------- | | EQUALS | Exact match | Status equals "active" | | NOT_EQUAL_TO | Not equal to | Status not "archived" | | GREATER_THAN | Numeric comparison | Priority > 5 | | LESS_THAN | Numeric comparison | Cost < 1000 | | GREATER_THAN_OR_EQUAL | Numeric comparison | Quantity >= 10 | | LESS_THAN_OR_EQUAL | Numeric comparison | Rating <= 5 | | STARTS_WITH | String prefix | Name starts with "Test" | | ENDS_WITH | String suffix | File ends with ".pdf" | | CONTAINS | String contains | Description contains "urgent" | | IS_ANY_OF | Array membership | Category in ["A", "B", "C"] | | IS_NONE_OF | Array exclusion | Status not in ["deleted", "archived"] | | IS_EMPTY | Null/empty check | Required field is empty | | IS_NOT_EMPTY | Has value | Optional field has value | | IS_IN_LIST | Comma-separated values | Tag in "red,blue,green" | | ARE_ANY_EMPTY | Check multiple properties | Any required field empty |

Rule Types and Behaviors

1. Editable Rules

Purpose: Control whether properties can be modified

{
  slug: "ALL",           // Apply to all properties
  editable: false,       // Make all properties read-only
  excludedSlugs: ["name", "description"]  // Except these
}

2. Required Rules

Purpose: Make properties mandatory based on conditions

{
  slug: "priority",
  required: true  // Priority must have a value
}

3. Value Range Rules

Purpose: Enforce numeric constraints

{
  slug: "quantity",
  minValue: 1,    // Must be at least 1
  maxValue: 100   // Must be at most 100
}

4. Option Set Validation

Purpose: Restrict values to specific options

{
  slug: "status",
  optionSetValues: ["active", "pending", "review"]  // Only these values allowed
}

5. Invalid Value Exclusion

Purpose: Prevent specific values

{
  slug: "category",
  invalidValues: ["deleted", "archived"]  // These values are forbidden
}

How It Works

1. Validation Process

  1. Criteria Evaluation: For each ConditionalTypeRules, the system evaluates whether the entity meets the criteria
  2. Rule Application: If criteria are met, all rules in that set are applied to the entity
  3. Error Collection: Validation errors are collected and returned

2. Return Value

The system returns an array of ValidationError objects:

interface ValidationError {
  slug?: string; // Property that failed validation
  value?: any; // The invalid value
  message: string; // Human-readable error message
  type?: ValidationErrorType; // WARNING or ERROR
}

3. Editable Check Process

  • Multiple TypeRuleSets can be evaluated
  • If ANY rule set makes a property non-editable, it becomes read-only
  • The slug: "ALL" rule applies to all properties except those in excludedSlugs

Advanced Features

1. Nested Property Access

Rules can target nested properties using dot notation:

{
  slug: "itemFamily.lifecycleStage",
  required: true
}

2. Multiple Rule Sets

You can apply multiple TypeRuleSets to an entity. All rules from all matching sets are applied.

3. Option Set Intersection

When multiple rules define optionSetValues, the system finds the intersection (common values) of all sets.

4. Invalid Value Union

When multiple rules define invalidValues, the system combines all invalid values into a single forbidden set.

Example Use Cases

1. Lifecycle-Based Validation

{
  ruleSet: [
    {
      criteria: {
        propertyCriteria: [
          {
            filterPropertyDefinition: {
              slug: 'lifecycleStage',
              propertyType: PropertyType.SingleSelect,
            },
            filterConditionType: FilterConditionType.EQUALS,
            criteriaValue: 'concept',
          },
        ],
      },
      rules: [
        {
          slug: 'priority',
          required: true,
          minValue: 1,
          maxValue: 5,
        },
      ],
    },
  ];
}

2. Conditional Editability

{
  ruleSet: [
    {
      criteria: {
        propertyCriteria: [
          {
            filterPropertyDefinition: {
              slug: 'status',
              propertyType: PropertyType.SingleSelect,
            },
            filterConditionType: FilterConditionType.EQUALS,
            criteriaValue: 'approved',
          },
        ],
      },
      rules: [
        {
          slug: 'ALL',
          editable: false,
          excludedSlugs: ['notes'],
        },
      ],
    },
  ];
}

3. Complex Multi-Criteria Rules

{
  ruleSet: [
    {
      criteria: {
        propertyCriteria: [
          {
            filterPropertyDefinition: {
              slug: 'department',
              propertyType: PropertyType.SingleSelect,
            },
            filterConditionType: FilterConditionType.EQUALS,
            criteriaValue: 'engineering',
          },
          {
            filterPropertyDefinition: {
              slug: 'priority',
              propertyType: PropertyType.Number,
            },
            filterConditionType: FilterConditionType.GREATER_THAN,
            criteriaValue: 5,
          },
        ],
      },
      rules: [
        {
          slug: 'approvalRequired',
          required: true,
          optionSetValues: ['yes'],
        },
        {
          slug: 'ALL',
          editable: false,
          excludedSlugs: ['approvalRequired', 'notes'],
        },
      ],
    },
  ];
}

Integration Points

  • Type Validation: Used by TypeManagedValidator to validate entity changes
  • UI Constraints: Used by TypeConstraintsHelper to determine editability and valid options
  • Option Set Filtering: Used by OptionSetRuleExtractor to dynamically filter available options
  • Form Validation: Applied during form submission to prevent invalid data

Best Practices

1. Rule Organization

  • Group related rules in the same ConditionalTypeRules object
  • Use descriptive criteria that clearly indicate when rules should apply
  • Keep rule sets focused on specific business scenarios

2. Performance Considerations

  • Avoid overly complex criteria that require expensive evaluations
  • Use specific property slugs rather than "ALL" when possible
  • Consider the order of rule evaluation for optimal performance

3. Error Messages

  • Provide clear, actionable error messages
  • Include context about why a rule failed
  • Use consistent messaging across similar validation failures

4. Testing

  • Test rule sets with various entity states
  • Verify that criteria properly filter rule application
  • Ensure that multiple rule sets work together correctly
  • Test edge cases like empty values and boundary conditions

Common Patterns

1. State-Based Validation

Use entity state to determine which validation rules apply:

// Only require approval for high-priority items
{
  criteria: { /* priority > 5 */ },
  rules: [{ slug: "approvalRequired", required: true }]
}

2. Role-Based Constraints

Restrict editing based on user roles or entity ownership:

// Only allow editing of own items
{
  criteria: { /* owner equals current user */ },
  rules: [{ slug: "ALL", editable: true }]
}

3. Workflow Enforcement

Ensure proper workflow progression:

// Lock fields after approval
{
  criteria: { /* status equals "approved" */ },
  rules: [{ slug: "ALL", editable: false, excludedSlugs: ["status"] }]
}

This system provides a flexible, powerful way to implement complex business rules that adapt based on entity state and context.