简体   繁体   中英

Controlling the order in which typescript property decorators are applied?

I'm considering writing a validator that checks whether one value is greater than another. For example purchase price greater than sales price.

But first we would have to make sure that the sales price is valid. So we might have something like this:

class Product {        

    @IsNumber
    @IsPositive
    purchasePrice: Number;

    @IsNumber
    @IsPositive
    @IsGreaterThan('purchasePrice')
    salesPrice: Number;
}

In this case the @IsNumber and @IsPositive should execute on both properties before the @IsGreaterThan annotation should execute.

I'm wondering whether this is something that is simple to implement (Perhaps with some class level metadata) or whether I should just write simple function validators to check this type of stuff.

I'm not a decorator expert, but one thought would be to have validation metadata built into each decorator using a number such that the execution of the validators is sorted by this number.

So for example the @IsGreaterThan validator could have a number 2 assigned, and the others a number 1 and that means that the validator should execute the 1 tagged validators first, and then 2 .

The decorator should not have a dependency on the usage order. They should be all standalone and work independently.

In this case, the @IsGreaterThan should have @IsNumber used internally to ensure the target is a number.

On the other hand, controlling the order is easy. The closest is applied first. So in your case, you need

class Product {
  @IsGreaterThan('purchasePrice')
  @IsPositive
  @IsNumber
  salesPrice: number
}

Decorator is just a sugar of a descriptor function, which is a higher order function like this:

function IsNumber(target, key, descriptor) { ... }

So the code above is actually just (pseudo code):

class Product {
  salesPrice = IsGreaterThan('puchasePrice')(IsPositive(IsNumber(Product, 'salesPrice')))
}

Since the class syntax is a sugar itself, the code above looks weird as I just trying to show you the underlying concept.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM