http-proxy-middleware change headers asynchronously

3.4k Views Asked by At

I'm using http-proxy-middleware in NodeJS to proxy a PHP site that does authentication.

The PHP site returns a header "saml-user-id".
I use this saml-user-id to generate a token which I want to add as cookie. I need to lookup the user in the database, so it needs to work asynchronously.

The code looks like this:

// DOESN'T WORK
exports.proxySimpleSamlMiddleware = createProxyMiddleware(['/saml'], {
    ssl: {
        key: fs.readFileSync('/path/to/my.key'),
        cert: fs.readFileSync('path/to/my.crt'),
    },
    target: 'https://127.0.0.1:8443',
    secure: false,
    logLevel: 'debug',
    changeOrigin: true,
    onProxyRes: async (proxyRes, req, res) => { // <-- ASYNCHRONOUS

        let tokenCookie = 'token=';

        if (proxyRes.headers['saml-user-id']) {
            const userId = proxyRes.headers['saml-user-id'];
            const token = await getNewToken(userId);
            tokenCookie = `token=${token}; path=/; httponly; samesite=lax`;
        }

        // Set the 'token' cookie
        // (simplified, in reality I read the existing cookies from the headers
        // and add this cookie to the list)
        proxyRes.headers['set-cookie'] = tokenCookie;
    },
});

The above code doen't work. No headers are changed, and I get an error ("Cannot set headers after they are sent to the client"). I guess that this is because of the asynchronous function in onProxyRes.

If I change the code to this:

    // DOESN'T WORK ASYNCHRONOUSLY
    onProxyRes: (proxyRes, req, res) => { // <-- REMOVED ASYNC
        let tokenCookie = 'token=my-new-token';
        proxyRes.headers['set-cookie'] = tokenCookie;
    },

Then the "token" cookie is set to "my-new-token" as expected. This is not an option because the change I want to make is asynchronous.

I have experimented with "responseIntercepter":

    // DOESN'T WORK
    selfHandleResponse: true,
    onProxyRes: responseInterceptor(async (responseBuffer, proxyRes, req, res) => {
        let tokenCookie = 'token=my-new-token';
        proxyRes.headers['set-cookie'] = tokenCookie;
        return responseBuffer;
    }),

But this doesn't update the "token" cookie either.

My question:
Is there a way using http-proxy-middleware to change the headers asynchronously?

0

There are 0 best solutions below