jquense / yup

Dead simple Object schema validation
MIT License
22.94k stars 935 forks source link

Support Standard-schema API? #2255

Open logaretm opened 3 weeks ago

logaretm commented 3 weeks ago

Hello,

standard-schema is a community effort to build a standard interface for schema libraries without any runtime dependencies, just by implementing a type.

I think the community can benefit from having yup implement the standard schema interface which will improve compatibility and easy migration from and to participating schema providers.

Being a maintainer of a popular form library and with another project on the way, it would be much easier to bake in type inference and validation capabilities without requiring users to install a resolver.

I think Yup already has all the parts needed, it is just a matter of conforming to the standard schema API.

I realize you may not have time to add this in. I can PR this, but I would like to get your thoughts before I dig in.

jquense commented 1 day ago

hey! Which other libraries support this and does anything consume it? I'm fine with minimal interop support if there is real value and demand, but i'm not particularly interested in supporting a wider API just for the sake of matching someones spec. These things aren't free for me to maintain etc.

logaretm commented 21 hours ago

Which other libraries support this and does anything consume it?

So at the moment the following libraries support it:

As for consumers, it is growing and as of now these are the libraries that consume it:

I also maintain vee-validate which may support it in the near future in the next major release and with another library that is coming out soon that already does consume standard schemas.


i'm not particularly interested in supporting a wider API just for the sake of matching someones spec

Fair, as a maintainer I totally understand that. To be honest, there is no real demand for it at the moment as it probably needs some time to mature, but it looks like it is on the upwards trend with adoption.

As for the interface itself the v1 interface looks like this:

/**
 * The Standard Schema interface.
 */
interface StandardSchema<Input = unknown, Output = Input> {
  /**
   * The Standard Schema properties.
   */
  readonly "~standard": StandardSchemaProps<Input, Output>;
}

/**
 * The Standard Schema properties interface.
 */
interface StandardSchemaProps<Input = unknown, Output = Input> {
  /**
   * The version number of the standard.
   */
  readonly version: 1;
  /**
   * The vendor name of the schema library.
   */
  readonly vendor: string;
  /**
   * Validates unknown input values.
   */
  readonly validate: (value: unknown) => StandardResult<Output> | Promise<StandardResult<Output>>;
  /**
   * Inferred types associated with the schema.
   */
  readonly types?: StandardTypes<Input, Output> | undefined;
}

I think adding it isn't too complex to yup's existing code, probably needs to be implemented once at the base schema level since most of the properties are static.

Maybe the only difference is how paths are expressed in the Issue object, standard schemas express the path as an array denoting the properties/symbols path.

I was going to create an external library that would adapt and wrap yup's schemas to standard schema spec, but wanted to check the possibility of having it implemented.

What do you think? I'm happy to take a stab at PRing this if you do not have the time, and only if you think the added API surface area isn't too much of a burden to maintain.


EDIT: I made a draft PR here against my fork, the path splitting was a bit more involved than I expected. Let me know your thoughts.

Bundle size diff (~3%)

Before (master)

Label Size
Bundle Size 72.6 KB
Minified Size 39.07 KB
Gzipped Size 11.44 KB

After

Label Size
Bundle Size 75.73 KB
Minified Size 40.08 KB
Gzipped Size 11.79 KB