jlguenego / node-expose-sspi

Expose Microsoft Windows SSPI to Node for SSO authentication.

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

nginx proxy on express server / AcceptSecurityContext: SECURITY_STATUS incorrect

anotherCoward opened this issue · comments

First of all, I upgraded from 0.1.44 to 0.1.57.

And right after the first start on production, i was getting the: Error: AcceptSecurityContext: SECURITY_STATUS incorrect (<0): (error code: 0x80090308) - behind a nginx reverse proxy.
The problem is, i wasted a shitload of time, looking for configuration errors and other stuff suggest, like the SPN you noticed in issue #59. - But it worked fine with 0.1.44 and also without the proxy there was no problem, so i started looking at your source and what was changed since then.

I found out that the internal cache from the ServerContextHandleManager just fails, if the connection (proxy to node) is not set to keep alive and the error raised is just wrong and leading into a completely different direction. Just because ServerContextHandleManager couldn't find the handle.

This error is raised because your code submits an undefined token. A custom Error at this point would be really helpful.

Also this configuration/setup could easily be supported with:

  • config allows usage of a multiple header fields for the id value like: sso.auth({ headers: ["x-forwarded-for","x-forwarded-port"] }) and prefers them over req.socket.remoteAddress + '_' + req.socket.remotePort;
  • alternative an config.ignorePort: bool to allow close-connections.
  • implenting a cookie based hash on the request token and use this as id.
  • config.preferProxyHeaders: bool and check if "forwarded" or "x-forwarded-for" is set and Connection is set to "close" and prefer those over remoteAddress
  • Throwing an error that no handle/token for the remote ip:port was found instead of the SECURITY_STATUS incorrect error.

Greetings

I currently solved it with a search for the headers inside the getId function in ServerContextHandleManager:

    if (req.headers["forwarded"])
        return req.headers["forwarded"];
    if (req.headers["x-forwarded-for"])
        return [req.headers["x-forwarded-for"], req.headers["connection"]].join('_');
    if (req.headers["x-real-ip"])
        return [req.headers["x-real-ip"], req.headers["connection"]].join('_');
    return [req.socket.remoteAddress,req.socket.remotePort].join('_');

You should have a look at https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Forwarded and https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/X-Forwarded-For and support them by default.
If Forwarded or X-Forwarded-For is present, use this instead of the remote address and port.
X-Forwarded-For doesn't have a standard defined, but Forwarded does. However, almost all proxy modules support it.

I have installed a windows nginx and reproduced the error (UnauthorizedError: Error while doing SSO: AcceptSecurityContext: SECURITY_STATUS incorrect (<0): (error code: 0x80090308) The token supplied to the function is invalid). I am going to see why exactly and check if what you suggest would be appropriate.

After analysis you are right. Here is what I am going to do:

  • modifying getId to add your proxy case.
  • managing the error about the handle not found.

0.1.58 integrates a correction for this issue. Please try it, and close this issue if satisfied. Thanks 👍

Works like a charm. Thank you.