-
Notifications
You must be signed in to change notification settings - Fork 31.2k
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
net: introduce removal methods for net.BlockList #40224
base: main
Are you sure you want to change the base?
Conversation
761927c
to
bc06179
Compare
bc06179
to
cdf1e51
Compare
cdf1e51
to
a040d37
Compare
a040d37
to
74944f6
Compare
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.
Thank you, this looks like it could be a great first contribution!
doc/api/net.md
Outdated
* `address` {string|net.SocketAddress} An IPv4 or IPv6 address. | ||
* `type` {string} Either `'ipv4'` or `'ipv6'`. **Default:** `'ipv4'`. | ||
|
||
Removes a rule to block the given IP address. |
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 documentation for these functions should specify whether they throw if no such rule was found, and they should probably clarify that, based on my understanding, they require exact matches. For example, it is not possible to remove a part of an existing range rule.
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.
@tniessen Good point, the removal methods don't currently throw if a matching rule isn't found. I think that behavior (i.e. throwing if rule not found) makes sense. I can implement / document it if that's alright?
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.
hmm or the method could return a boolean indicating whether a matching rule was removed?
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 not sure what the behavior of the adding functions is (I'm on mobile right now so can't test).
- If add throws if a rule already exists, remove should throw if no such rule exists.
- If add doesn't add duplicate rules, maybe this should return a boolean (similar to JS sets).
- If add does add duplicate rules, and if this removes exactly one of them (as opposed to all of them), then removal should throw if no rule exists that could be removed.
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.
Gotcha, so add used to create duplicate rules. I changed this behavior to ease rule removal, so add no longer creates duplicate rules. Maybe this change is undesirable. I could be missing context on why duplicate rules were allowed in the first place.
Otherwise, I agree with your points. Remove probably shouldn't throw since add doesn't. It should return a boolean like map, set, etc. as you mentioned.
FWIW, Not including removal methods on a block list instance was intentional and I'd be -1 on adding them in the general case. The reason goes back to the original use case for this -- that I haven't yet, but still plan to, get back to, and that's allowing a node.js process to be started with a blocklist that user code cannot modify. e.g. something like |
@jasnell Thanks for providing some background. I have a few questions:
Were you planning to remove the add methods in the API then? My thought was having methods to remove rules made sense if there were methods to add rules. Of course, if the original intention was to make
So another class like
By "mistake", it sounds to me like this could come back to bite developers in some way. Could you elaborate on this? Finally, was there intention behind allowing duplicate rules? I removed the following behavior in this PR so it would be helpful to know the reasoning for this: const list = new net.BlockList();
list.addAddress('127.0.0.1');
list.addAddress('127.0.0.1');
console.log(list);
// BlockList {
// rules: [
// 'Address: IPv4 127.0.0.1',
// 'Address: IPv4 127.0.0.1'
// ]
// } Anyway, I don't want to step on your toes or take an ill-advised approach so I appreciate your feedback. |
No I wasn't planning on removing the add. Udder code should be allowed to make the policy more restrictive, just not less. |
For a hypothetical |
I'm working on a project right now that's using a Again, maybe I shouldn't be using |
Hello! This is my 1st PR and I'm not a C++ developer so bear with me :)
High level changes
Currently, to "remove" a rule from
net.BlockList
, one must create a newBlockList
and add every other existing rule to it. This PR introducesremoveAddress()
,removeRange()
, andremoveSubnet()
methods tolib/internal/blocklist.js
so users can easily modify rule sets.Adding redundant addresses, ranges, or subnets no longer creates multiple rules in the
BlockList
. However, this behavior doesn't apply to a subnet that overlaps another subnet or a subnet that's equivalent to a range. The modification to rule-adding behavior eases rule removal discussed in the next section.Low level changes
To achieve the functionality mentioned, this PR adds
SocketAddressRange
andSocketAddressMask
classes tosrc/node_sockaddr*
. These classes have their own hashing implementations so their instances can be uniquely mapped to rules.SocketAddressRangeRule
andSocketAddressMaskRule
now utilize these classes, respectively.SocketAddressBlocklist
now has separate mappings for address, range, and subnet rules. This way,SocketAddressBlocklist
can uniquely identify an address, range, or subnet and its corresponding rule. This makes rule removal easier but also compels a change to rule-adding behavior where redundant addresses, ranges, or subnets do not create additional rules when compared to rules in the same category.I updated the documentation and added test cases for rule removal and checking redundant addition of rules.
Some open questions
SocketAddressRange
andSocketAddressMask
be exposed in thenet
API? If so, would it make sense to do this in a separate PR?