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

proptype

v1.0.0

Published

A proptype library inspired by react prop types, and more.

Downloads

43

Readme

Proptype

This library is inspired by ReactJS's Prop Validation module. The module serves well enough for ReactJS projects, but along with validations, I needed a little more:

  1. distinguish between types at runtime, and
  2. extract information about prop types.

A use case for this library is, if you are working on something such as a UI Builder that requires you to show a form with appropriate fields depending on property types expected by the component. You may find this library useful to defines property types required by your UI components.

Although this library is inspired by ReactJS, it is not restricted to be used with ReactJS in anyway. In fact, property types specific to ReactJS i.e. element, node are not present in this library.

Usage

If you have used ReactJS, the prop type declarations are very similar:

import { PropTypes } from 'proptype';

const objectPropTypes = PropTypes.shape({
  optionalAny: PropTypes.any, 
  // => AnyType instance
  
  optionalArray: PropTypes.array, 
  // => ArrayType instance
  
  optionalBool: PropTypes.bool, 
  // => BoolType instance
  
  optionalFunc: PropTypes.func, 
  // => FuncType instance
  
  optionalNumber: PropTypes.number, 
  // => NumberType instance
  
  optionalObject: PropTypes.object, 
  // => ObjectType instance  
  
  optionalString: PropTypes.string, 
  // => StringType instance
  
  optionalSymbol: PropTypes.symbol, 
  // => SymbolType instance
  
  optionalInstanceOf: PropTypes.instanceOf(SomeClass), 
  // => InstanceOfType instance
  // optionalInstanceOf.InstanceOf => SomeClass
  
  optionalCustom: PropTypes.custom(function myValidator(value) {
    if (value.isValid()) {
      return null;
    }
    
    return new Error('Whatever error message');
  }),
  // => CustomType instance
  // optionalCustom.validator => myValidator function
  
  optionalArrayOfNumbers: PropTypes.arrayOf(PropTypes.number), 
  // ArrayOfType instance
  // optionalArrayOfNumbers.arrayOf => NumberType instance
  
  optionalObjectOfStrings: PropTypes.objectOf(PropTypes.string), 
  // ObjectOfType instance
  // optionalObjectOfStrings.objectOf => StringType instance
  
  optionalOneOf: PropTypes.oneOf([1, 'two', 3]), 
  // => OneOfType instance
  // => optionalOneOf.oneOf => [1, 'two', 3]
  
  optionalOneOfType: PropTypes.oneOfType([PropTypes.number, PropTypes.string]),
  // => OneOfTypeType instance
  // optionalOneOfType.oneOfType => [PropTypes.number, PropTypes.string]
  
  optionalShape: PropTypes.shape({
    oNum: PropTypes.number,
    rString: PropTypes.string.isRequired,
    rShape: PropTypes.shape({
      a: PropTypes.array,
      b: PropTypes.func.isRequired,
    }).isRequired,
  }),
  // => ShapeType instance
  // optionalShape.shape => {
  //                            oNum: PropTypes.number, => NumberType instance
  //                            rString: PropTypes.string.isRequired, => StringType instance
  //                            rShape: PropTypes.shape({
  //                              a: PropTypes.array, => ArrayType instance
  //                              b: PropTypes.func.isRequired, => FuncType instance
  //                            }).isRequired, => ShapeType instance
  //                          }
                                                 
}).isRequired;

objectPropTypes.validate(objectPropValues);

You can suffix isRequired to mark the type as required, which otherwise would accept null and undefined values as valid.

For example:

const optionalType = PropTypes.number;
optionalType.required() === false;
let err = optionalType.validate(null); // => null;
err = optionalType.validate(23); // => null
err = optionalType.validate('abc'); // => Error instance

const requiredType = PropTypes.number.isRequired;
requiredType.required() === true;
let err = requiredType.validate(null); // => Error instance;
err = requiredType.validate(23); // => null
err = requiredType.validate('abc'); // => Error instance

Supported Type Classes

Following type classes are exported:

  • AnyType
  • ArrayType
  • BoolType
  • FuncType
  • NumberType
  • ObjectType
  • StringType
  • SymbolType
  • ArrayOfType
  • CustomType
  • InstanceOfType
  • ObjectOfType
  • OneOfType
  • OneOfTypeType
  • ShapeType

You can import them as:

import { AnyType, ArrayType, ... } from 'proptype';

Type instance to json objects

Each Type except InstanceOfType and CustomType supports a toJson() method. For example:

const myShapeType = new ShapeType({
 optionalNumber: new NumberType,
 requiredString: new StringType(true)
}, true);

// or using PropTypes

const anotherShapeType = PropTypes.shape({
  optionalNumber: PropTypes.number,
  requiredString: PropTypes.string.isRequired,
}).isRequired;

// both these calls
myShapeType.toJson();
anotherShapeType.toJson();
// will result =>
// {
//    type: 'shape',
//    required: true,
//    shape: {
//      optionalNumber: {
//        type: 'number',
//        required: false
//      },
//      requiredString: {
//        type: 'string',
//        required: true
//      }
//    }
//  }

Creating Type instances from json objects

You can use a json object to create type instance hierarchy. For example:

import proptype from 'proptype'

const type = proptype.fromJson({
  type: 'shape',
  required: true,
  shape: {
    optionalNumber: {
      type: 'number',
      required: false
    },
    requiredString: {
      type: 'string',
      required: true
    }
  }
});

type.validate({ optionalNumber: 2, requiredString: 'abc' }); // => null
type.validate({ optionalNumber: 2 }); // => Error

Adding Types

You can define you own custom types as:

import proptype, { PropTypes, AnyType } from 'proptype';

class MyCustomType extends AnyType {
  static TYPE_NAME = 'myCustomType';
  
  static fromJson(obj) {
    // create the type instance from obj
    return new MyCustomType(obj.whatever, obj.it, obj.requires, obj.required); 
  }
  
  constructor(whatever, it, requires, required = false) {
    super(required);
    // initialise the type
  }
  
  validate(value) {
    if (value.isNotValid()) {
      return new Error('with some message');
    }
    
    // return null for valid values
    return null;
  }
  
  toJson() {
    return {
      type: MyCustomType.TYPE_NAME,
      required: this.required(),
      whatever: 'whatever',
      it: 'it',
      requires: 'requires'
    };
  }
}

proptype.register(MyCustomType);

const myObjProps = PropTypes.shape({
  myCustomValue: PropTypes.myCustomType(whatever, it, requires).isRequired
});

License

Copyright © 2015-2016 Chetan Verma. This source code is licensed under the MIT license found in the LICENSE.txt file. The documentation to the project is licensed under the CC BY-SA 4.0 license.

A note of thanks

Last, but not the least, this library is built using babel-starter-kit Try it out for your next project!