typescript-ioc icon indicating copy to clipboard operation
typescript-ioc copied to clipboard

@InRequestScope not returning the same Instance

Open rafaferry opened this issue 5 years ago • 4 comments

I'm using typescript-ioc on server side with nodejs and express, and trying to create an object that holds de logged user, that I should be able to access it in any place on my application. To do so, i've created the following class:

@InRequestScope
@OnlyInstantiableByContainer
class LoggedInUserService { ... }

And i've created an express middleware that would extract the logged user from request, and fill it in LoggedInUserService. But it seems that In the same request, or even in the same function, different instances of LoggedInUserService are retrieve from Container.

function extractUser (req:express.Request, resp: express.Response, next:Function): void {
  const auth = req.headers.authorization
  if (auth != null) {
    const token = auth.replace(/bearer /ig, '')
    const jwtToken = jwt.verify(token, config.jwtSecret) as PIJWTToken
    const loggedInUserService = Container.get(LoggedInUserService)
    loggedInUserService.setup(jwtToken.email)
    const LoggedInUserService2 = Container.get(UsuarioLogadoService)
    
    //the next line is returning false;
    console.log('same instance?', loggedInUserService === loggedInUserService2)
  }
  next()
}

When I use Singleton scope, I do get the same Instance. Do I need to create some configuration for @InRequestScope ? What am I missing?

Thank you

rafaferry avatar Apr 06 '20 18:04 rafaferry

Navigating through the types docs, i think i've misunderstood the Request Scope.

I need an HTTP Request scope, but its not clear to me how could I create such scope with the framework. Is it even possible?

I think I would have to create a Build context per HttpRequest, and that it should be in a express middleware function.

Do you have any hint for this?

rafaferry avatar Apr 06 '20 19:04 rafaferry

Same problem here, any help?

Thanks!

pballester avatar Apr 16 '20 11:04 pballester

@pballester sorry for the very late response.

I did this using the new async_hook - AsyncLocalStorage api (node 13+), but I didn't integrate it with typescript-ioc.

The code is something like this:

import { AsyncLocalStorage } from 'async_hooks';

const storage = new AsyncLocalStorage<Map<string, any | undefined>>();

//This must be the first middleware. In any code after this, storage.getStore() will return the same MAP instance.
this._express.use((req: express.Request, resp: express.Response, next: Function) => {
      storage.run(new Map(), () => next());
});

rafaferry avatar Jun 22 '20 16:06 rafaferry

Would love to get this working as it just doesn't seem very straight forward. @Singleton works fine but @InRequestScope can't seem to get it to work.

dgocoder avatar Aug 13 '20 23:08 dgocoder