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

doc: explain HTTP writeHead()'s fast path behavior #21289

Closed

Conversation

gireeshpunathil
Copy link
Member

calling writeHead() into a Response object that has no headers already
set causes getHeader() to return undefined, even if the header was set
in the writeHead() function call. Explain this behavior as an
optimiation as opposed to a bug.

Fixes: #10354

Checklist
  • make -j4 test (UNIX), or vcbuild test (Windows) passes
  • tests and/or benchmarks are included
  • documentation is changed or added
  • commit message follows commit guidelines

@nodejs-github-bot
Copy link
Collaborator

@gireeshpunathil sadly an error occured when I tried to trigger a build :(

@nodejs-github-bot nodejs-github-bot added doc Issues and PRs related to the documentations. http Issues or PRs related to the http subsystem. labels Jun 12, 2018
@vsemozhetbyt
Copy link
Contributor

Is this intended to be in the request.setHeader() section, not in the response.setHeader() section?

doc/api/http.md Outdated
@@ -648,6 +648,13 @@ stored without modification. Therefore, [`request.getHeader()`][] may return
non-string values. However, the non-string values will be converted to strings
for network transmission.

If [`response.writeHead()`][] method is called and this method has not been
called, it will directly write the supplied header values onto the network channel
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This long line seems to break linting.

Copy link
Member

@lpinca lpinca left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM with @vsemozhetbyt's nit addressed.

@gireeshpunathil
Copy link
Member Author

that is interesting. I ran lint and lint-ci targets locally, and it does not throw this error.

$ make lint
make[1]: Entering directory `/home/node'
Running JS linter...
make[1]: Leaving directory `/home/node'
make[1]: Entering directory `/home/node'
Running C++ linter...
Total errors found: 0
make[1]: Leaving directory `/home/node'
make[1]: Entering directory `/home/node'
Running C++ linter on addon docs...
Total errors found: 0
make[1]: Leaving directory `/home/node'
make[1]: Entering directory `/home/node'
The markdown linter is not installed.
To install (requires internet access) run: make lint-md-build
make[1]: Leaving directory `/home/node'

$ make lint-ci

Running JS linter...
The markdown linter is not installed.
To install (requires internet access) run: make lint-md-build
Running C++ linter on addon docs...
Total errors found: 0

any idea why?

Nevertheless, made the changes and pushed, please have a look.

@gireeshpunathil
Copy link
Member Author

@vsemozhetbyt

Is this intended to be in the request.setHeader() section, not in the response.setHeader() section?

No, it is meant at response.setHeader() and response.writeHead() sites itself, because those are the APIs whose usage context and behavior were under question, and hence I clarified it under both the APIs. Please let me know if there is an issue with that.

@richardlau
Copy link
Member

@gireeshpunathil The lint and lint-ci targets will skip linting docs unless dependencies are installed. As the output says, run: make lint-md-build and then try again.

@vsemozhetbyt
Copy link
Contributor

@gireeshpunathil Currently, the first fragment is placed in the request.setHeader() section)

Copy link
Member

@apapirovski apapirovski left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This needs to be fixed up before it can land

doc/api/http.md Outdated
@@ -648,6 +648,13 @@ stored without modification. Therefore, [`request.getHeader()`][] may return
non-string values. However, the non-string values will be converted to strings
for network transmission.

If [`response.writeHead()`][] method is called and this method has not been
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is inserted in an incorrect area or has the wrong links.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed, ptal.

doc/api/http.md Outdated
called, it will directly write the supplied header values onto the network
channel without caching internally, and the [`response.getHeader()`][] on the
header will not yield the expected result. If progressive population of headers
are desired with potential future retrieval and modification, use
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

are desired -> is desired?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed

doc/api/http.md Outdated
If this method is called and [`response.setHeader()`][] has not been called,
it will directly write the supplied header values onto the network channel
without caching internally, and the [`response.getHeader()`][] on the header
will not yield the expected result. If progressive population of headers are
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

are desired -> is desired?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed, thanks.

calling writeHead() into a Response object that has no headers already
set causes getHeader() to return undefined, even if the header was set
in the writeHead() function call. Explain this behavior as an
optimiation as opposed to a bug.

Fixes: nodejs#10354
called, it will directly write the supplied header values onto the network
channel without caching internally, and the [`response.getHeader()`][] on the
header will not yield the expected result. If progressive population of headers
is desired with potential future retrieval and modification, use
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is modification still possible after writeHead? Sounds to me like only retrieval is possible. Ditto below.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@TimothyGu - yes, that is right: headers written through writeHead are not modifiable, and attempt to do so results in error Cannot set headers after they are sent to the client. Hence the suggestion to use setHeader() API for such cases. If the text is not conveying that let me know where and how can I fix it, thanks.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, you wrote

If progressive population of headers is desired with potential future retrieval and modification, use …

It seemed to me that the bolded bit should perhaps be removed.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

sorry, missed this update. Sorry, I am missing your point:
#cat 10354.js

const h = require('http')
h.createServer((q, r) => {
  r.setHeader('foo', 'bar')
  r.setHeader('foo', 'new')
  r.end()
}).listen(12000, () => {
  const c = h.get('http://localhost:12000', (m) => {
    console.log(m.headers)
  })
})

#node 10354.js

{ foo: 'new',
  date: 'Thu, 21 Jun 2018 14:42:33 GMT',
  connection: 'close',
  'content-length': '0' }

setHeader() is indeed used for modification, and hence the text. Can you please clarify your point?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Never mind, I see what this is trying to say now.

Copy link
Contributor

@vsemozhetbyt vsemozhetbyt left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Doc format LGTM)

@addaleax addaleax added the author ready PRs that have at least one approval, no pending requests for changes, and a CI started. label Jun 14, 2018
@gireeshpunathil
Copy link
Member Author

In the light of recent changes to the build process, what is the CI recommendation for doc changes? (sorry, I was not keeping track of the conversations) full CI (manual trigger) / lite CI (manual trigger) / do nothing - as the auto-CI said all checks have passed.

@gireeshpunathil
Copy link
Member Author

answering my own question, I guess it is node-test-pull-request-lite-pipeline for docs:
https://ci.nodejs.org/job/node-test-pull-request-lite-pipeline/119/

gireeshpunathil added a commit that referenced this pull request Jun 22, 2018
calling writeHead() into a Response object that has no headers already
set causes getHeader() to return undefined, even if the header was set
in the writeHead() function call. Explain this behavior as an
optimiation as opposed to a bug.

Fixes: #10354
PR-URL: #21289

Reviewed-By: Anatoli Papirovski <apapirovski@mac.com>
Reviewed-By: James M Snell <jasnell@gmail.com>
Reviewed-By: Luigi Pinca <luigipinca@gmail.com>
Reviewed-By: Timothy Gu <timothygu99@gmail.com>
Reviewed-By: Vse Mozhet Byt <vsemozhetbyt@gmail.com>
Reviewed-By: Trivikram Kamat <trivikr.dev@gmail.com>
@gireeshpunathil
Copy link
Member Author

landed as cbe307d

targos pushed a commit that referenced this pull request Jun 22, 2018
calling writeHead() into a Response object that has no headers already
set causes getHeader() to return undefined, even if the header was set
in the writeHead() function call. Explain this behavior as an
optimiation as opposed to a bug.

Fixes: #10354
PR-URL: #21289

Reviewed-By: Anatoli Papirovski <apapirovski@mac.com>
Reviewed-By: James M Snell <jasnell@gmail.com>
Reviewed-By: Luigi Pinca <luigipinca@gmail.com>
Reviewed-By: Timothy Gu <timothygu99@gmail.com>
Reviewed-By: Vse Mozhet Byt <vsemozhetbyt@gmail.com>
Reviewed-By: Trivikram Kamat <trivikr.dev@gmail.com>
@targos targos mentioned this pull request Jul 3, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
author ready PRs that have at least one approval, no pending requests for changes, and a CI started. doc Issues and PRs related to the documentations. http Issues or PRs related to the http subsystem.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

getHeader() returns undefined after using writeHead() in a certain circumstance
10 participants