UNPKG

@cowwoc/requirements

Version:

A fluent API for enforcing design contracts with automatic message generation.

235 lines (234 loc) 9.41 kB
import { Type, ValidationFailures, type NonUndefinable, type ClassConstructor, type UnknownValidator } from "../../internal/internal.mjs"; /** * Methods that all validators must contain. * * @typeParam T - the type of the value */ interface ValidatorComponent<T> { /** * Returns the name of the value. * * @returns the name of the value */ getName(): string; /** * Returns the value that is being validated. * * @returns the value * @throws RangeError if the value is invalid (e.g. due to dereferencing a property of a `null` value) */ getValue(): T; /** * Returns the value that is being validated. * * @param defaultValue - the fallback value to use if the value is invalid * @returns the validated value, or `defaultValue` if the value is invalid (e.g. due to dereferencing a * property of a `null` value) */ getValueOrDefault(defaultValue: T): T; getValueOrDefault(defaultValue: T | null): T | null; /** * Returns the contextual information for upcoming validations carried out by this validator. The contextual * information is a map of key-value pairs that can provide more details about validation failures. For * example, if the message is "Password may not be empty" and the map contains the key-value pair * `{"username": "john.smith"}`, the error message would be: * ```console * Password may not be empty * username: john.smith * ``` * * @returns an unmodifiable map from each entry's name to its value * @see Validators.getContext */ getContext(): Map<string, unknown>; /** * Sets the contextual information for upcoming validations. * <p> * This method adds contextual information to error messages. The contextual information is stored as * key-value pairs in a map. Values set by this method override any values that are set using * {@link Validators.withContext}. * <p> * There is no way to remove contextual information from a validator. Thread-level contextual information is * removed automatically. * * @param value - the value of the entry * @param name - the name of an entry * @returns this * @throws TypeError if `name` is `undefined` or `null` * @throws RangeError if `name`: * <ul> * <li>contains whitespace</li> * <li>is empty</li> * <li>is already in use by the value being validated or the validator * context</li> * </ul> */ withContext(value: unknown, name: string): this; /** * Facilitates the validation of related properties. For example, * <p> * ```ts * requireThat(nameToFrequency, "nameToFrequency"). * and(m => m.size().isPositive()). * and(m => m.keySet().contains("John")); * ``` * <p> * Any changes made during the validation process will impact this validator. * * @param validation - the nested validation * @returns this * @throws TypeError if `validation` is `undefined` or `null` */ and(validation: (validator: this) => void): this; /** * Checks if any validation has failed. * * @returns `true` if at least one validation has failed */ validationFailed(): boolean; /** * Returns the array of failed validations. * * @returns an array of failed validations */ elseGetFailures(): ValidationFailures; /** * Throws an error if a validation failed; otherwise, returns `true`. * * @returns true if the validation passed * @throws RangeError if a method precondition, class invariant, or method postcondition was violated * @throws MultipleFailuresError if more than one validation failed. This error contains an array of * the failures. */ elseThrow(): boolean; /** * Returns the contextual information associated with this validator. * * @returns the contextual information associated with this validator */ getContextAsString(): string; /** * Ensures that the value is undefined. * * @returns this * @throws TypeError if the value is not `undefined` */ isUndefined(): UnknownValidator<undefined>; /** * Ensures that the value is not undefined. * <p> * This method should be used to validate method arguments that are assigned to class fields but not * accessed right away (such as constructor and setter arguments). It should also be used to validate any * method arguments when the validator contains * {@link ValidatorComponent.getContext|additional contextual information}. * * @returns this * @throws TypeError if the value is `undefined` */ isNotUndefined(): UnknownValidator<NonUndefinable<T>>; /** * Ensures that the value is `null`. * * @returns this * @throws TypeError if the value is not `null` */ isNull(): UnknownValidator<null>; /** * Ensures that the value is not `null`. * <p> * This method should be used to validate method arguments that are assigned to class fields but not * accessed right away (such as constructor and setter arguments). It should also be used to validate any * method arguments when the validator contains * {@link ValidatorComponent.getContext|additional contextual information}. * * @returns this * @throws TypeError if the value is `null` */ isNotNull(): UnknownValidator<NonNullable<T>>; /** * Ensures that the value is an instance of a class. * * @typeParam U - the desired class * @param expected - the desired class * @returns a validator for an object of the desired class * @throws TypeError if the value or `expected` are `undefined` or `null` * @throws RangeError if the value is not an instance of the desired class */ isInstanceOf<U extends object>(expected: ClassConstructor<U>): UnknownValidator<U>; /** * Ensures that the value has the specified type. * * @param expected - the expected type of the value * @returns this * @throws TypeError if the value is not an instance of the specified type */ isType(expected: Type): this; /** * Ensures that the value is not an instance of a class. * * @param unwanted - the unwanted class * @returns this * @throws TypeError if the value or `unwanted` are `undefined` or `null` * @throws RangeError if the value is an instance of the unwanted class */ isNotInstanceOf<U extends object>(unwanted: ClassConstructor<U>): this; /** * Ensures that the value is equal to `expected`. * * @param expected - the expected value * @returns this * @throws RangeError if the value is not equal to `expected` * @see <a href="https://github.com/cowwoc/requirements.java/blob/master/docs/Textual_Diff.md">An * explanation of the output format</a> */ isEqualTo(expected: unknown): this; /** * Ensures that the value is equal to `expected`. * * @param expected - the expected value * @param name - the name of the expected value * @returns this * @throws TypeError if `name` is `undefined` or `null` * @throws RangeError if: * <ul> * <li>`name` is empty</li> * <li>`name` contains whitespace</li> * <li>`name` is already in use by the value being validated or * the validator context</li> * <li>the value is not equal to `expected`</li> * </ul> * @see <a href="https://github.com/cowwoc/requirements.java/blob/master/docs/Textual_Diff.md">An * explanation of the output format</a> */ isEqualTo(expected: unknown, name: string): this; /** * Ensures that the value is not equal to `unwanted`. * * @param unwanted - the unwanted value * @returns this * @throws RangeError if the value is equal to `expected` * @see <a href="https://github.com/cowwoc/requirements.java/blob/master/docs/Textual_Diff.md">An * explanation of the output format</a> */ isNotEqualTo(unwanted: unknown): this; /** * Ensures that the value is not equal to `unwanted`. * * @param unwanted - the unwanted value * @param name - the name of the other value * @returns this * @throws TypeError if `name` is `undefined` or `null` * @throws RangeError if: * <ul> * <li>`name` is empty</li> * <li>`name` contains whitespace</li> * <li>`name` is already in use by the value being validated or * the validator context</li> * <li>the value is equal to the `unwanted` value</li> * </ul> * @see <a href="https://github.com/cowwoc/requirements.java/blob/master/docs/Textual_Diff.md">An * explanation of the output format</a> */ isNotEqualTo(unwanted: unknown, name: string): this; } export type { ValidatorComponent };