elastic / kibana

Your window into the Elastic Stack
https://www.elastic.co/products/kibana
Other
19.48k stars 8.04k forks source link

[@kbn/config-schema] Adding support for `is` type checking #185020

Open maryam-saeidi opened 4 weeks ago

maryam-saeidi commented 4 weeks ago

🍒 Summary

In io-ts, there is a is functionality that checks if a variable matches a schema definition. As you see below, this function returns a boolean instead of throwing an error in case the variable does not match the schema. (Kibana example: occurrencesBudgetingMethodSchema.is(slo.budgetingMethod))

It also uses type guard based on the type that is specified for is. Example:

Before is check After type guard
image image
elasticmachine commented 4 weeks ago

Pinging @elastic/kibana-core (Team:Core)

pgayvallet commented 3 weeks ago

Joi supports that via Joi.assert and/or Joi.attempt (or even Joi.validate). I think there would be no major concerns or challenges surfacing a similar API (with typeguard) on our base config-schema Type

pgayvallet commented 3 weeks ago

I tried implementing this using the standard validation approach

  public is(value: unknown, context: Record<string, unknown> = {}): value is V {
    const { error } = this.internalSchema.validate(value, {
      context,
      presence: 'required',
    });
    return !error;
  }

before realizing that the logic doesn't stand in case of default values.

E.g

const mySchema = schema.object({
    foo: schema.string({ default: 'defaultFoo' }),
});

const myValue = {};

if(mySchema.is(myValue)) { // returns true
  myValue.foo // undefined;
}

So TLDR: the feature may make sense for io-ts given it doesn't have native support of default values, but might less for joi/config-schema?

Implementing my snippet would work "as expected" for schemas without default values of any kind, but would not for ones with such default values. And I don't think there's any non-costly / trivial way to fully duplicate/clone a schema while removing its default values...