Search code examples
typescriptrepositoryloopbackjs

Custom function using repository in sequence


I created a custom function that needs to be executed in every route of my server.

This function needs to retrive a parameter in the header of the request and check this parameter inside the DB. (controlled by a repository)

how can I gain the access of this repository within my function?

I try different possibilities but I cannot be able to achieve a result:

  1. create a repository inside the function (the db seems empty :( )
  2. try to pass the repository from the controller (would be okay but in the sequence file I cannot have access to the controller nor the repository :(
  3. try to include the controller in the function but like 2.

I'm a beginner of loopback and typescript as you can see =)


Solution

  • I think you are looking for the recently introduced Interceptors, see Interceptors and Interceptor generator.

    Since you want to invoke your function for every incoming request, you can use a Global interceptor.

    how can I gain the access of this repository within my function?

    Write an Interceptor Provider, it allows you to leverage @inject-based dependency-injection to receive the repository. For example:

    class MyRequestValidator implements Provider<Interceptor> {
      constructor(
        @repository(TokenRepository) protected tokenRepo: TokenRepository,
        @inject(RestBindings.Http.REQUEST) protected request: Request,
      ) {}
    
      value() {
        return this.intercept.bind(this);
      }
    
      async intercept<T>(
        invocationCtx: InvocationContext,
        next: () => ValueOrPromise<T>,
      ) {
        // parse the parameter from this.request.headers[name]
        const token = this.request.headers['x-my-token'];
    
        // call this.tokenRepo methods to query the database
        const found = await this.tokenRepo.findOne({where:{id: token}});
        const isValid = !found.expired;
    
        if (!isValid) {
          // throw new Error() to abort with error
          throw new HttpErrors.BadRequest('Invalid token.'));
        }
    
        // call next() to continue with request handling
        return next();
      }
    }