-
Notifications
You must be signed in to change notification settings - Fork 5
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
Embed Trusted Default Seed Nodes into src/config.ts
for bootstrapping the P2P network
#269
Comments
Some changes necessary here:
Regarding point 3... normally TLS works here because multiple hosts can claim the same certificate. But right now it's not possible to have multiple nodes claim the same node ID. It seems either we have to change it so that when connecting to given IP, we can accept multiple potential node IDs, or we have to ensure that there's 1 public IP (and therefore EIP) per node. We have some code that can deal with the former already, especially since we can accept multiple node ids over a root certificate chain. And the latter is also possible if we were to investigate AWS more deeply and figure out how to connect an EIP to specific container processes on a 1 to 1 basis. I'm leaning towards the former atm. |
src/config.ts
for bootstrapping the P2P network
Changed from starting on 4th Nov to 8th Nov due to #282. |
Changed from starting on 8th Nov to 10th Nov due to #282. |
Specification updated. |
Most of the refactoring work here is done to support the seed nodes. Last bit of work is adding the different sources of seed nodes. From discussions with Roger, I'm going to be adjusting the approach here slightly to instead use the
Given that there's some slight differences in format here:
I'll need to figure out if/how |
After the above, will then need to begin looking into supporting the propagation of errors from networking, and garbage collecting As such, I'd estimate another day or 2 for this. Adjusting this work to conclude on Thursday 18th Nov. |
So after discussion with Roger, we can simplify this. We should have the following:
By default, the CLI flag should overwrite any existing seed nodes (specified in either the environment variable or If the seed nodes specified in the CLI flag or the environment variable are desired to be appended to the default seed nodes specified in We can also potentially extend this for a variadic CLI flag option:
|
Adjusting end date to Wednesday December 1 (from November 18 - delayed from refactoring work in #283), to give time for review and merge. |
Specification
The seed nodes in the Polykey network provide the first point of entry for bootstrapping new keynodes into the wider Polykey network.
We've now got support for deterministic root keypair generation according to a 24-word recovery key mnemonic, as per #202. We will be using this deterministic generation to generate our own set of seed nodes. This generation of seed nodes will be done in #285.
We'll require two sets of keynodes: one for
testnet.polykey.io
and another formainnet.polykey.io
. At least for the time being, we'll just be considering a single, shared seed node for both testnet and mainnet. An additional environment variable (PK_ENV
) or config flag will be required to switch between which nodes to use (i.e. either mainnet in production, or testnet for debugging/testing).Specifying the list of seed nodes
The list of seed nodes is required to be a static list of mappings from
NodeId
toNodeAddress
(in this case, containing a hostname and port). The port for all of these seed nodes should be pre-defined (not defaulted) to be 1314.Recall that the canonical version of a node ID is a 32-byte structure. Discussions of this can be found in #261. Therefore, this 32-byte structure would ideally be used for this static storage. Alternatively, we need to use some other string-encoded version of the node ID.
This list will be able to be supplied from 3 sources:
PK_SEED_NODES
[email protected]:1314;...
new URL()
: e.g.new URL('pk://[email protected]:80')
,new URL('pk://sdof8er@[2001:0db8:85a3:0000:0000:8a2e:0370:7334]:80')
. Note the need for the prependedpk://
when usingnew URL
nodePath
src/config.ts
:DNS resolution
There's a couple of aspects to supporting DNS resolution.
promisify
(if already at an IP, no need to call this)NodeGraph
level (before creating aNodeConnection
)NodeConnection
. This should also occur for any reconnections on dropped connections (see Propagate networking connection error handling into NodeConnection error handling #224 for this)all
parameter in thedns.lookup
options. For this, no need to do crypto random. Just useMath.random
and select an index (https://stackoverflow.com/a/38448710/582917)src/config.ts
for bootstrapping the P2P network #269 (comment)Node reconnection
There was also discussion of needing to resolve #224 in this issue too, such that we can implement some kind of reconnection logic when a previously initialised connection is dropped. This will need to be further discussed, and if required, may take another day or so.
I wonder if we actually care about reconnecting at all. Would it not be sufficient to simply propagate the error up, terminate the connection, and only re-establish connection if another agent to agent call is made? This would fit the current structure of
NodeConnection
(where we have agetConnectionToNode
function that either uses an existing connection, or creates a new one).Additional context
pk agent start
andpk bootstrap
withPK_RECOVERY_CODE
andPK_PASSWORD
#202Tasks
base58btc
?base64
is dangerous because there's unsafe URL characters in the encoding.base64url
is also a potential one here (this is used for the JWS claims in the sigchain too, as this removes the unsafe URL characters.NodeGraph
? From memory in Canonicalise node ID representation #261, we've refactored this such that we use the 32-byte representation. If we use a string encoding for the node ID, we need to firstly convert back to the 32-byteUInt8Array
.nodes
domain:broker
intoseed
nodes (as per Update testnet.polykey.io to point to the list of IPs running seed keynodes #177 (comment))brokerNodeConnections
- the seed nodes should be treated as regular nodes, that get added to theNodeGraph
(Kademlia system) (as per Update testnet.polykey.io to point to the list of IPs running seed keynodes #177 (comment))A note on this though. This could mean that eventually the seed nodes are removed from a bucket (if the bucket were to become full, and they were considered the "least active" node. Is this desired? We'd still have their static information in our config, but not in the internalNodeGraph
system. Perhaps this is okay, given that we should reduce reliance on these nodes as the node becomes aware of other nodes in the Polykey networkNodeGraph
system (i.e. whereNodeId
can then map to aNodeAddress
containing either[ IP address, port ]
or[ hostname, port ]
)NodeConnection
and theGRPCClient
to see what happensPK_SEED_NODES
src/config.ts
Old specification
Block 3 from #194 (comment)
Specification
Once we deploy the test keynodes #194, and make use of recovery codes #202 to generate deterministic root keys and root certificates, this will mean we will have a deterministic Node ID.
We should have a set of Node Ids to be trusted, but we can start with just 1.
The Node ID has to be embedded into our default trusted seed list in the source code.
This can be done in 3 tiers of configuration:
PK_SEED_NODES
src/config.ts
This configuration needs to be something like:
I forgot why I chose 1314, or if we had registered anything here before, but this is suitable as the well known port we use by default.
The
ENCODED-NODEID
should be a multi-base encoding of the Node ids. This means we should also resolve #261, as decoding the node ids will result in aUint8Array
to be used as the canonical node ID.In the case of an environment variable, where one has to specify this configuration as a string, we should use a standardised env variable format involving
:
colon separation, unforunately the standard way of separating domains from ports is to use the:
, therefore we use;
as the separation.And a parser should be written to do that. Note that we require the
port
setting at all times. There is no defaulting of the port.The resulting value should be referred to from
src/config.ts
. All other code should be doingimport config from '../config'
.Now the
NodeGraph
that reads this, needs to support dns hostnames as well as IP addresses. At this point we have not tested what happens if we just use hostnames. The hostnames will be established in theNodeConnection
which uses GRPC client and also the networking domain which uses uTP. You can prototype this and see what happens first.To be safe, we can directly use the dns module: https://nodejs.org/api/dns.html to resolve hostnames if we have a hostname (https://nodejs.org/api/dns.html#dnslookuphostname-options-callback). If you have a IP address, don't call the DNS module, it's not necessary. The call will need to be wrapped as a promise, so use the appropriate
promisify
wrapper in thesrc/utils.ts
.The DNS module will resolve to the IP addresses that we want, and we would then use these. Because the underlying IP addresses may be dynamic, do not cache the IP addresses. Instead you resolve every time you want to establish a running
NodeConnection
. This allows us to change the IP addresses due to migration/redeployment/crashes... etc, and any PK agents connected to the seeds, will just re-connect (there is no re-connection logic built intoNodeManager
yet). Consult the #224 regarding propagating asynchronous errors from networking connections toNodeConnection
. And when you re-connect, you resolve the DNS again to get the appropriate IP address.At this point there's a problem with uTP not supporting IPv6, see #224 for that. So the
testnet.polykey.io
will only return A records which are IPv4 addresses.Multiple A records may be resolved. When multiple are resolved, you must choose 1 randomly to be used. Use the
all
parameter in thedns.lookup
options. For this, no need to do crypto random. Just useMath.random
and select an index (https://stackoverflow.com/a/38448710/582917).The encoded node ids will need to be generated via the #194 procedure, we will keep the recovery keys secret in our own private git repo. But also dog-food PK when appropriate here.
To accompolish this, these 2 additional things need to be done as well:
NodeManager
.networking
is propagated tonodes
Reference documentation should be done in the configuration of the PK (should have a configuration page) as a well as the testnode component architecture.
Additional context
pk agent start
andpk bootstrap
withPK_RECOVERY_CODE
andPK_PASSWORD
#202Tasks
The text was updated successfully, but these errors were encountered: