Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Error [ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client #412

Open
cdisk opened this issue Mar 9, 2020 · 4 comments

Comments

@cdisk
Copy link

cdisk commented Mar 9, 2020

Error [ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client.

I want to use both pathRewrite and followRedirects.
I use the vue webpack config this funtions.
But When I add followRedirects config attribute,the console show me this error.

Steps to reproduce

  1. create vue project.
  2. add vue.config.js
  3. add proxy config to vue.config.js file.
  4. add pathRewrite and followRedirects to proxy node.
  5. run command yarn serve to start project.
  6. use ajax call target url in browser.
  7. the yarn console display following errors and stop the project:

Here is my vue.config.js file:

    devServer: {
        proxy: {
            '/api': {
                target: 'http://127.0.0.1:8581/', // 反代目标地址
                changeOrigin: true,
                // autoRewrite: true,
                // xfwd: true,
                // prependPath: true,
                followRedirects: true,
                pathRewrite: {
                    '^/api': ''
                }
            }
        }
    }

Here is the error message displayed in the console:

_http_outgoing.js:485
    throw new ERR_HTTP_HEADERS_SENT('set');
    ^

Error [ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client
    at ClientRequest.setHeader (_http_outgoing.js:485:11)
    at RedirectableRequest.setHeader (/root/workspaces/sqwl/hzsc-pc/node_modules/http-proxy/node_modules/follow-redirects/index.js:118:24)
    at ProxyServer.onProxyReq (/root/workspaces/sqwl/hzsc-pc/node_modules/@vue/cli-service/lib/util/prepareProxy.js:97:20)
    at ProxyServer.emit (/root/workspaces/sqwl/hzsc-pc/node_modules/eventemitter3/index.js:184:35)
    at RedirectableRequest.<anonymous> (/root/workspaces/sqwl/hzsc-pc/node_modules/http-proxy/lib/http-proxy/passes/web-incoming.js:132:27)
    at RedirectableRequest.emit (events.js:223:5)
    at ClientRequest.eventHandlers.<computed> (/root/workspaces/sqwl/hzsc-pc/node_modules/http-proxy/node_modules/follow-redirects/index.js:17:24)
    at ClientRequest.emit (events.js:228:7)
    at tickOnSocket (_http_client.js:684:7)
    at onSocketNT (_http_client.js:723:5)
    at processTicksAndRejections (internal/process/task_queues.js:81:21) {
  code: 'ERR_HTTP_HEADERS_SENT'
}
error Command failed with exit code 1.
info Visit https://yarnpkg.com/en/docs/cli/run for documentation about this command.

please help me.

@uranium93
Copy link

any updates about this Issue ? :/

@maks-humeniuk
Copy link

Not sure if it's relevant, but I also had this error in Angular application, while trying to proxy POST request via pathRewrite.

It appears that pathRewrite works fine for GET requests.

pathRewrite: () => '/mocks/get-heroes-response.mock.json'

Yes, it could also be a function, not an object.

But for POST and PUT bypass should be used instead.

bypass: (request) => {
    if (request.method === 'POST') {
        request.method = 'GET';
        return '/mocks/create-hero-response.mock.json';
    }
}

Using pathRewrite for POST and PUT also works, but with error you sent.

@maks-humeniuk
Copy link

maks-humeniuk commented Sep 22, 2021

After new research I figured out that bypass suffers from webpack/webpack-dev-server#829.

Luckily, you could substitute it with pathRewrite like this.

// for non-GET requests
pathRewrite: (path, request) => {
    request.method === 'GET';
    return '/path/to/mock.json';
}

// for GET requests
pathRewrite: () => '/path/to/mock.json'

If you have multiple returns though, you should wrap request.method === 'GET'; with e.g. if (request.method === 'POST') {} to avoid infinite loop situations.

// for non-GET requests
pathRewrite: (path, request) => {
    if (request.method === 'POST') {
        request.method === 'GET';
        return '/path/to/post-mock.json';
    }
    if (request.method === 'PUT') {
        request.method === 'GET';
        return '/path/to/put-mock.json';
    }
}

Or, more elegant solution.

// for non-GET requests
pathRewrite: (path, request) => {
    const post = request.method === 'POST';
    const put = request.method === 'PUT';
    if (post || put) {
        request.method === 'GET';
    }
    if (post) {
        return '/path/to/post-mock.json';
    }
    if (put) {
        return '/path/to/put-mock.json';
    }
}

@uranium93
Copy link

Little update regarding this. we faced an issue with same error message using express with http-proxy-middleware and the issue was that in implementation next() was called twice, once in the middleware and the other one onError without return.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants