BoarderCauli
BoarderCauli

Reputation: 1

How to validate fields inside object in typescript using typeguards

I am processing some data in my backend (written in Typescript) provided via a form in html. Before writing the data to the database, I perform validations using type guards.

let myObject = { property: parseProperty(property) } 

where the type definition for "property" is given as:

interface PropertyType = { 
    Field1: string; 
    Field2: string; 
  } 

The property object is first parsed via the following type-guard:

const parseProperty = (property: unknown): PropertyType => {
  if (!property || !isPropertyEntry(property)) {
    throw new Error("Incorrect or missing property entry")
  }
  return property; 

Then we use the typeguard below (which is incomplete) to validate property's objects fields.

const isPropertyEntry = (property : unknown): property is PropertyType => {
  if( !('Field1' in property) || !('Field2' in property) ) {    // <--- invalid statement
    throw new Error("Incorrect or missing field/s in property");
  } 
  ...
  ...

}

TS throws an error for these two statements: 'Field1' in property & 'Field2' in property: Object is of type 'unknown'.ts(2571)

My question is how would I do a proper validation of the object 'property' and make sure Field1 & Field2 exist and are correct type?

Upvotes: 0

Views: 587

Answers (1)

Tobias S.
Tobias S.

Reputation: 23825

It does not look like you want to have a type guard. Since you want to throw an Error when property is not a PropertyType, you probably need an assertion function.

function assertIsPropertyEntry(property: any): asserts property is PropertyType {
  if (
    typeof property !== "object" 
    || !property 
    || !('Field1' in property) 
    || !('Field2' in property)
    || typeof property.Field1 !== "string"
    || typeof property.Field2 !== "string"
  ) {
    throw new Error("Incorrect or missing field/s in property");
  } 
}

const parseProperty = (property: unknown): PropertyType => {
  assertIsPropertyEntry(property)
  return property
}

Playground

Upvotes: 1

Related Questions