Search code examples
javascriptangularangular-decorator

How does angular method decorator work?


In this Angular decorator tutorial, the tutorial explains that a throttle decorator (lodash throttle function) can be made this way:

import t from 'lodash.throttle';

export function throttle( milliseconds : number = 500 ) : MethodDecorator {
   return function ( target : any, propertyKey : string, descriptor : PropertyDescriptor ) {
   const original = descriptor.value;
   descriptor.value = t(original, milliseconds);
   return descriptor;
  };
}

And use in the following class

@Component({
  selector: 'app-posts-page',
  template: `
     <posts [posts]="posts$ | async"></posts>
  `
})
export class PostsPageComponent {
  constructor( private store : Store<any> ) {
    this.posts$ = store.select('posts');
  }

  @HostListener('document:scroll')
  @throttle()
  scroll() {
    console.log('scroll');
  }
}

I wonder how throttle works to change scroll function. Could anyone explain or let me know how I can see the compiled code? Thanks!


Solution

  • throttle is a property decorator and it means that it's job is usually to modify the class (object) property descriptor. The descriptor before the modification has the value pointing to scroll function:

    {
      value: scroll() { console.log('scroll'); },
      ...
    }
    

    The decorator accepts this descriptor and replaces the original value with the new decorated function returned by the call to t:

    function ( target : any, propertyKey : string, descriptor : PropertyDescriptor ) {
       // save original value 'scroll'
       const original = descriptor.value;
       // overwrite original value with the decorated function returned by `t`
       descriptor.value = t(original, milliseconds);
       return descriptor;
    };
    

    If the decorator returns the descriptor it's then used to define the property instead of the original descriptor.

    You can read more about decorators in the article: