-
Notifications
You must be signed in to change notification settings - Fork 29.6k
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
cluster: refactor module into multiple files #10746
Conversation
I think the triple newlines could be changed to just double newlines (one empty line between function definitions, etc. instead of two). |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Generally LGTM. Couple comments tho (consider to be optional)
this.handle.onconnection = (err, handle) => this.distribute(err, handle); | ||
this.server._handle = null; | ||
this.server = null; | ||
}); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
While we're at it, perhaps consider eliminating the closure by moving these handlers into top level functions. Doing so should result in at least some performance improvement overall.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If it was a function, how would it get access to this
? Wouldn't it have to be bound, which has perf negatives?
'worker.suicide is deprecated. Please use worker.exitedAfterDisconnect.'), | ||
set: internalUtil.deprecate( | ||
(val) => { this.exitedAfterDisconnect = val; }, | ||
'worker.suicide is deprecated. Please use worker.exitedAfterDisconnect.'), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The deprecation message could be made into a const and reused.
}; | ||
|
||
|
||
function onmessage(message, handle) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nit: While we're refactoring all this code, maybe remove handle
as an argument here? It's not used in the function.
6b9bd1a
to
425162e
Compare
Switched from two blank lines to one blank line between functions. @mscdex I have two questions for you:
|
|
OK, thanks! That's what I was thinking on both points, but wanted to check. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Couple small suggestions, and I don't think we should be using mixed case filenames, but basically LGTM.
this.handle.onconnection = (err, handle) => this.distribute(err, handle); | ||
this.server._handle = null; | ||
this.server = null; | ||
}); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If it was a function, how would it get access to this
? Wouldn't it have to be bound, which has perf negatives?
if (getOwnPropertyNames(this.all).length !== 0) | ||
return false; | ||
|
||
for (var handle; handle = this.handles.shift(); handle.close()); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I find this kindof for construction hard to read, could you put the empty statement, the ;
, on the next line?
@@ -0,0 +1,113 @@ | |||
'use strict'; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
file-naming convention in lib/
is is snake_case.js
, AFAICT.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I used https://github.com/nodejs/node/blob/master/lib/internal/streams/BufferList.js as a reference for naming files that hold a single data type.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think that BufferList is an unfortunate outlier. lib/internal/streams/lazy_transform.js is a better model to follow.
'use strict'; | ||
const assert = require('assert'); | ||
const net = require('net'); | ||
const { sendHelper } = require('internal/cluster/utils'); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
sort requires?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm all for sorting requires. Do we sort by the variable name on the left hand side, or the string inside of require()
? What about internal modules? Should they be grouped differently?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Lexical sort (in ASCII order/posix "C" locale) on the statements (which ends up being by name of variable, but variable name usually maps 1:1 to the require name, es6 requires aside) (:sort
in vim, pipe block through !sort
, whatever your editor likes). No grouping, too complicated to document and reproduce.
} | ||
|
||
RoundRobinHandle.prototype.add = function(worker, send) { | ||
assert(worker.id in this.all === false); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why not use !
operator instead of comparison against false? As is done in
+ if (!(this instanceof Worker))
+ return new Worker(options);
@@ -0,0 +1,224 @@ | |||
'use strict'; | |||
const assert = require('assert'); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
sort requires?
|
||
cluster.settings = settings; | ||
|
||
if (initialized === true) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if (initialized)
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think a strict comparison against a boolean is faster. This was also the existing code.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Some of the asserts don't do direct comparisons. but its existing, so NBD. I more noticed the inconsistent usage, sometimes direct comparisons, sometimes not. But again, pre-existing, so its OK.
425162e
to
b032fef
Compare
New CI: https://ci.nodejs.org/job/node-test-pull-request/5848/ Looks like an unrelated failure, so trying again: https://ci.nodejs.org/job/node-test-pull-request/5850/ |
This commit splits the existing cluster module into several internal modules. More specifically, the cluster master and worker implementations are separated, and the various data structures are separated. PR-URL: nodejs#10746 Reviewed-By: James M Snell <[email protected]> Reviewed-By: Sam Roberts <[email protected]>
b032fef
to
2f885e7
Compare
This commit splits the existing cluster module into several internal modules. More specifically, the cluster master and worker implementations are separated, and the various data structures are separated. PR-URL: nodejs#10746 Reviewed-By: James M Snell <[email protected]> Reviewed-By: Sam Roberts <[email protected]>
This commit splits the existing cluster module into several internal modules. More specifically, the cluster master and worker implementations are separated, and the various data structures are separated. PR-URL: #10746 Reviewed-By: James M Snell <[email protected]> Reviewed-By: Sam Roberts <[email protected]>
This commit splits the existing cluster module into several internal modules. More specifically, the cluster master and worker implementations are separated, and the various data structures are separated. PR-URL: nodejs#10746 Reviewed-By: James M Snell <[email protected]> Reviewed-By: Sam Roberts <[email protected]>
This commit splits the existing cluster module into several internal modules. More specifically, the cluster master and worker implementations are separated, and the various data structures are separated. PR-URL: nodejs#10746 Reviewed-By: James M Snell <[email protected]> Reviewed-By: Sam Roberts <[email protected]>
@nodejs/lts @cjihrig ... trying to decide if we should backport this to v6 or not. Recommending that we skip backporting to v4 |
If we do backport to v6, a backport PR will be required. |
I've always found the cluster code unpleasant to deal with. Currently, one large file contains the
Worker
,SharedHandle
, andRoundRobinHandle
structures. The same file also contains the cluster master and worker implementations, each of which modifiesWorker
. This makes the code tricky, because when you jump around in the code, you need to determine what context you're working in. I'm hoping to make it more readable/maintainable.This commit splits the existing cluster module into several internal modules. More specifically, the cluster master and worker implementations are separated, and the various data structures are separated.
Checklist
make -j4 test
(UNIX), orvcbuild test
(Windows) passesAffected core subsystem(s)
cluster