Skip to content

feat: Support http.request signatures added in Node 10.9+#1588

Merged
mastermatt merged 10 commits intonock:betafrom
mastermatt:support-new-request-signature
Jul 9, 2019
Merged

feat: Support http.request signatures added in Node 10.9+#1588
mastermatt merged 10 commits intonock:betafrom
mastermatt:support-new-request-signature

Conversation

@mastermatt
Copy link
Copy Markdown
Member

Fixes #1227
Supersedes #1428

Beginning with v10.9.0, the url parameter can be passed along with a
separate options object to http[s].request, http[s].get, or to the
constructor of ClientRequest. docs

The logic that does the juggling was mostly copied from Node's source.

There was a bit of other cleanup that was committed separately to aid with review.

@mastermatt mastermatt requested a review from paulmelnikow June 17, 2019 02:44
@mastermatt mastermatt force-pushed the support-new-request-signature branch from 826d859 to 3efe155 Compare June 17, 2019 03:09
@paulmelnikow
Copy link
Copy Markdown
Member

This is great! I can give it a read tomorrow.

@mastermatt mastermatt force-pushed the support-new-request-signature branch from aa4d82c to 9a7ec1b Compare June 18, 2019 16:22
@mastermatt
Copy link
Copy Markdown
Member Author

fyi @nijynot and @gkalpak

Instead of passing it all around the overrider.
This mimics how the native implementation does it.
Fixes nock#1227

Beginning with v10.9.0, the `url` parameter can be passed along with a
separate options object to `http[s].request`, `http[s].get`, or to the
constructor of `ClientRequest`.

https://nodejs.org/api/http.html#http_http_request_url_options_callback

The logic that does the juggling was mostly copied from Node's source.
@mastermatt
Copy link
Copy Markdown
Member Author

@paulmelnikow were you able to read through this pr?

@paulmelnikow
Copy link
Copy Markdown
Member

Ah no, I think I lost track of it. Sorry! I'll aim to take a look tonight or tomorrow!

Copy link
Copy Markdown
Member

@paulmelnikow paulmelnikow left a comment

Choose a reason for hiding this comment

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

Thanks so much for this work! I understand most of it, I think, though I left a few questions.

I'll take another pass through thinking about test coverage though this is looking really good.

Sorry it's taken me so long to read this!


// The option per the docs is `protocol`. Its unclear if this line is meant to override that and is misspelled or if
// the intend is to explicitly keep track of which module was called using a separate name.
// Either way, `proto` is used as the source of truth from here on out.
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Not sure what we ought to do here but really appreciate this comment!

res.on('response', callback)
}
return req
return new http.ClientRequest(options, callback)
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Nice!

Object.assign(this, overrider)

if (callback) {
this.once('response', callback)
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Nice!

mastermatt and others added 2 commits July 8, 2019 11:34
Co-Authored-By: Paul Melnikow <github@paulmelnikow.com>
t.done()
})

test('normalizeClientRequestArgs throws for invalid URL', async t => {
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

@gr2m has expressed a preference for testing our helper functions through real use cases in the public API wherever possible, and it seems to pay off well. It also has the advantage of surfacing code that is no longer needed.

Would you be up for expressing these tests in terms of calls to http?

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Yes please 👍

scope.done()
t.done()
})
})
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

👍

Copy link
Copy Markdown
Member

@gr2m gr2m left a comment

Choose a reason for hiding this comment

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

Could you update the docs to mention the new request signature?

@paulmelnikow
Copy link
Copy Markdown
Member

Could you update the docs to mention the new request signature?

This PR doesn't change the documented API, rather it makes the mock surface compatible with Node 10.9+ (#1227).

I don't think we have documentation of the supported mock surface, beyond the tests. We could add some, though I don't think it needs to be in this PR.

@gr2m
Copy link
Copy Markdown
Member

gr2m commented Jul 8, 2019

Okay, thank you for the clarification

@paulmelnikow paulmelnikow changed the title feat: Support new request signature feat: Support http.request signatures added in Node 10.9+ Jul 8, 2019
@mastermatt
Copy link
Copy Markdown
Member Author

I believe I've addressed all the comments.
@gr2m @paulmelnikow could I get another pass from you?

paulmelnikow added a commit that referenced this pull request Jul 8, 2019
Ref #1404 (comment)

This leaves intact two missed coverage spots in `lib/recorder.js` which are being taken care of in #1588.

Also ref #1607
Copy link
Copy Markdown
Member

@paulmelnikow paulmelnikow left a comment

Choose a reason for hiding this comment

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

Feel free to merge when ready!

@mastermatt mastermatt merged commit e3e6a65 into nock:beta Jul 9, 2019
@mastermatt mastermatt deleted the support-new-request-signature branch July 9, 2019 05:32
@nockbot
Copy link
Copy Markdown
Collaborator

nockbot commented Jul 9, 2019

🎉 This PR is included in version 11.0.0-beta.22 🎉

The release is available on:

Your semantic-release bot 📦🚀

@nockbot
Copy link
Copy Markdown
Collaborator

nockbot commented Aug 12, 2019

🎉 This PR is included in version 11.0.0 🎉

The release is available on:

Your semantic-release bot 📦🚀

gr2m pushed a commit that referenced this pull request Sep 4, 2019
Ref #1404 (comment)

This leaves intact two missed coverage spots in `lib/recorder.js` which are being taken care of in #1588.

Also ref #1607
gr2m pushed a commit that referenced this pull request Sep 4, 2019
* Allow three arg form of `request` and `ClientRequest`.

Fixes #1227

Beginning with v10.9.0, the `url` parameter can be passed along with a
separate options object to `http[s].request`, `http[s].get`, or to the
constructor of `ClientRequest`.

https://nodejs.org/api/http.html#http_http_request_url_options_callback

The logic that does the juggling was mostly copied from Node's source.

* Remove unnecessary overrider in intercept.

* Register ClientRequest callback on response event.

Instead of passing it all around the overrider.
This mimics how the native implementation does it.
gr2m pushed a commit that referenced this pull request Sep 4, 2019
Ref #1404 (comment)

This leaves intact two missed coverage spots in `lib/recorder.js` which are being taken care of in #1588.

Also ref #1607
gr2m pushed a commit that referenced this pull request Sep 4, 2019
* Allow three arg form of `request` and `ClientRequest`.

Fixes #1227

Beginning with v10.9.0, the `url` parameter can be passed along with a
separate options object to `http[s].request`, `http[s].get`, or to the
constructor of `ClientRequest`.

https://nodejs.org/api/http.html#http_http_request_url_options_callback

The logic that does the juggling was mostly copied from Node's source.

* Remove unnecessary overrider in intercept.

* Register ClientRequest callback on response event.

Instead of passing it all around the overrider.
This mimics how the native implementation does it.
gr2m pushed a commit that referenced this pull request Sep 5, 2019
Ref #1404 (comment)

This leaves intact two missed coverage spots in `lib/recorder.js` which are being taken care of in #1588.

Also ref #1607
gr2m pushed a commit that referenced this pull request Sep 5, 2019
* Allow three arg form of `request` and `ClientRequest`.

Fixes #1227

Beginning with v10.9.0, the `url` parameter can be passed along with a
separate options object to `http[s].request`, `http[s].get`, or to the
constructor of `ClientRequest`.

https://nodejs.org/api/http.html#http_http_request_url_options_callback

The logic that does the juggling was mostly copied from Node's source.

* Remove unnecessary overrider in intercept.

* Register ClientRequest callback on response event.

Instead of passing it all around the overrider.
This mimics how the native implementation does it.
)
// https://nodejs.org/api/http.html#http_http_get_options_callback
module.get = function(input, options, callback) {
const req = module.request(input, options, callback)
Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Why is this not calling newRequest instead? This breaks the Node API as well

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

This is done to mimic native Node behavior in case other libs are monkey-patching the function.
Can you provide more details on "This breaks the Node API as well"? Preferably in a new issue.

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

I can make a new issue. But writing the details here as well.

New Relic (https://github.com/newrelic/node-newrelic) is overwriting http.get and http.request like you do. But when http.get is calling http.request like here, a call to http.get will call http.request twice when using nock in a New Relic test.

To prove that this is not native Node behaviour (at least on Node 12):

const http = require('http');

function request() {
  console.log('http.request', arguments);
}

http.request = request;

// our request function is not called
http.get('http://google.com', () => {});

juninmd pushed a commit to juninmd/nock that referenced this pull request Mar 21, 2026
Ref nock#1404 (comment)

This leaves intact two missed coverage spots in `lib/recorder.js` which are being taken care of in nock#1588.

Also ref nock#1607
juninmd pushed a commit to juninmd/nock that referenced this pull request Mar 21, 2026
* Allow three arg form of `request` and `ClientRequest`.

Fixes nock#1227

Beginning with v10.9.0, the `url` parameter can be passed along with a
separate options object to `http[s].request`, `http[s].get`, or to the
constructor of `ClientRequest`.

https://nodejs.org/api/http.html#http_http_request_url_options_callback

The logic that does the juggling was mostly copied from Node's source.

* Remove unnecessary overrider in intercept.

* Register ClientRequest callback on response event.

Instead of passing it all around the overrider.
This mimics how the native implementation does it.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants