@sergtyapkin/models-validator
TypeScript icon, indicating that this package has built-in type declarations

1.1.7 • Public • Published

Models validator

Run tests downloads

🎉 Be sure of the right types of incoming data with this! 🎉

Models Validator for Objects. For example, for JSON-parsed Objects that received from network.
You can see examples in tests validateModel.test.js


⏩ Docs for validateModel

[!IMPORTANT] All model fields describes as:
from: fieldType

📝 fieldType can be declared as:

  1. Simple type: String, Number, Date, Object, Array,... (Array in this case can contain any elements of any types)
  2. Enum: new Set(["some_val", 456, "val2"]) (Field can only be "some_val" or 456 or "val2")
  3. One of types: new Set([Number, Boolean]) (Field can only be Number or Boolean. Not string or any other type)
  4. Specialized Array (fixed length): [Number, String, String] (specialized type of every element in array)
  5. Specialized Array (unlimited length):
{
  fieldName: {
    {   
      type: Array,
      item: /**{{any fieldType declaration}}**/,
    }
  }
}
  1. Long type declaration (you can set optional, default and from params):
{
  fieldName: {
    type: /**{{short fieldType declaration}}**/,
    optional: true, // |=>  field will not be exists in result object if it's not provided
    default: "SomeDefaultValue", // => If field not provided in source data, it will have this value
    from: "some_name", // |=>  field will be searched in the source model as a field with the name "some_name" 
  }
}
  1. Nested object declaration:
{
  fieldNested: {
    type: Object,
    fields: {
      // field_1: String,
      // field_2: Number,
    }
    // from: "field_nested",
    // optional: true,
    // default: null,
  }
}

⚙ All fields options at long declaration:

Field Type Description
type {{short fieldType}} Describes the type to which the original field value is converted
optional `Boolean] If it has value "false", field can be not provided.
default Any value that converts to declared 'type' If field is optional and it's not provided in source data, it will have this value.
from String Name of field with which it will be searched in the source model.
item {{long or short fieldType}} If field type is Array, it can be long or short declaring of field type.
fields Object with other fields If field type is Object, it must be Object with long or short declaring of each object field.

Example model description:

const exampleModel = {
  field1: String, // |=> "some_string"
  field2: Number, // |=> 123.4123
  field3: Object, // |=> {any_fields: any_values, ...}
  field4: Array,  // |=> [any_types, ...]
  field5: [Number, String], // |=> [123.1244, "some_string"]
  field6: new Set(["some_val", 456, "val2"]), // |=> Enumeration. Can only be "some_val" or 456 or "val2"
  field7: new Set([String, Boolean]), // |=> 123.231 or `false` but not "any string" or any other type
  field8: { // Equals as `field8: String`
    type: String
  }, 
  field9: {
    type: Object,
    fields: {
      // ... Any fields of nested model, for example:
      field9_1: String,
    },
  },
  field10: {
    type: Number,
    optional: true, // |=>  field will not be exists in result object if it's not provided
  },
  field11: {
    type: Array,
    item: String, // |=> short or long declaration of each field in array
    from: "some_field_11", // |=> field will searched as field "some_field_11" and written in "field11"
  },
  field12: {
    type: Array,
    item: {  // example of long declaration of each field in array:
      type: Object,
      fields: {
        field12_1: String,
      }
    },
  },
}

Example model validation:

import { validateModel } from '@sergtyapkin/models-validator';

const UserModel = { // declare model
  age: Number,
  userName: {
    type: [String, String], // maybe ["john", "doe"]
    from: "user_name", // name in incoming data for validation
  }, 
  sex: new Set(['male', 'female']), // one of two values
  children: {
    type: Array, // array with unlimited length
    optional: true, // mey be not exists
    item: {
      type: Object,
      fields: {
        name: String,
        age: Number,
      }
    }
  }
}

const response = fetch('/user', {method: 'GET'}); // get unvalidated JSON data
const data = validateModel(UserModel, await response.text()); // validate

For more examples you can see file with tests validateModel.test.js


♻️ Reverse validation

Use the function reverseValidateModel to compress validated model back. If in model was fields with from params, reverse validating will writes values in this fields in fields which names describes in from params.

Example:

import { validateModel, reverseValidateModel } from '@sergtyapkin/models-validator';

// STRAIGHT VALIDATING
const Model = { // declare model
  userName: {
    type: [String, String], // maybe ["john", "doe"]
    from: "user_name_snake_case", // name in incoming data for validation 
  }, 
  userAge: {
    type: Number,
    from: "user_age_snake_case",
  }
}

const unvalidatedData = {
  user_name_snake_case: ["John", "Doe"],
  user_age_snake_case: 30,
}
const data = validateModel(Model, unvalidatedData);
/* data = {
  userName: ["John", "Doe"],
  userAge: 30,
}
*/

// REVERSE VALIDATING
const reversedData = reverseValidateModel(Model, data);
/* reversedData = {
  user_name_snake_case: ["John", "Doe"],
  user_age_snake_case: 30,
}
*/

🔁 snake_case and CamelCase generators

You can describe model in only camelCase or PascalCase fields and generator adds longDeclaring param from with snake_case field name. Or vice versa.

Example:

/** CamelCase -> snake_case **/
import { generateSnakeCaseFromCamelCaseModel } from '@sergtyapkin/models-validator';

const Model = generateSnakeCaseFromCamelCaseModel({ // declare model
  someUSERName: String,
  UserAgePascalCase: Number,
});
/* Model = {
  someUSERName: {
    type: String,
    from: "some_user_name",
  }, 
  UserAgePascalCase: {
    type: Number,
    from: "user_age_pascal_case",
  }
}
 */
/** snake_case -> CamelCase **/
import { generateCamelCaseFromSnakeCaseModel } from '@sergtyapkin/models-validator';

const Model = generateCamelCaseFromSnakeCaseModel({ // declare model
  some_user_name: String, 
  user_age_snake_case: Number,
});
/* Model = {
  some_user_name: {
    type: String,
    from: "someUserName",
  }, 
  user_age_snake_case: {
    type: Number,
    from: "userAgeSnakeCase",
  }
}
 */

✂️ Shortcuts

You can describe long types, simple Array or Object fields shortly:

import { Type, ArrayType, ObjectType } from '@sergtyapkin/models-validator';

const Model = { // declare model
  someField: Type(String, true, 'default value'),
};
/* Model = {
  someField: {
    type: String,
    optional: true,
    default: 'default value',
  }, 
}
 */

const ModelWithArray = { // declare model
  someArray: ArrayType(String),
};
/* ModelWithArray = {
  someArrayStr: {
    type: Array,
    item: String,
  }, 
}
 */

const ModelWithObject = { // declare model
  someObject: ObjectType({
    field1: String,
    field2: Number,
  }),
};
/* ModelWithObject = {
  someObject: {
    type: Object,
    fields: {
      field1: String,
      field2: Number,
    },
  }, 
}
 */

const ModelWithObjectInArray = { // declare model
  someObjectInArray: ArrayType({
    field1: String,
    field2: Number,
  }),
};
/* ModelWithObjecwtInArray = {
  someObjectInArray: {
    type: Array,
    item: {
      type: Object,
      fields: {
        field1: String,
        field2: Number,
      },
    },
  }, 
}
 */

Package Sidebar

Install

npm i @sergtyapkin/models-validator

Weekly Downloads

21

Version

1.1.7

License

MIT

Unpacked Size

25.1 kB

Total Files

8

Last publish

Collaborators

  • sergtyapkin