From 9d26b46200f9a145b8defd7d9b4db98fccb3a477 Mon Sep 17 00:00:00 2001 From: HDegroote <75906619+HDegroote@users.noreply.github.com> Date: Tue, 20 Feb 2024 23:39:03 +0100 Subject: [PATCH] Unflake tests: pass in testnet port to CLI --- bin/client.js | 11 ++++++++--- bin/copy.js | 9 +++++++-- bin/server.js | 9 +++++++-- lib/client-socket.js | 4 ++-- test/basic.js | 23 +++++++++++++---------- test/helpers/index.js | 30 ++++++++++++++---------------- 6 files changed, 51 insertions(+), 35 deletions(-) diff --git a/bin/client.js b/bin/client.js index a6ba3b2..52f04f3 100755 --- a/bin/client.js +++ b/bin/client.js @@ -22,7 +22,7 @@ program .option('-f ', 'Filename of the client seed key.', path.join(SHELLDIR, 'peer')) .option('-L <[address:]port:host:hostport...>', 'Local port forwarding.') // .option('--primary-key ', 'Inline primary key for the client.') - .option('--testnet', 'Use a local testnet.', false) + .option('--testnet ', 'Use a local testnet at the specified port.', parseInt) .action(cmd) .parseAsync() @@ -33,6 +33,11 @@ async function cmd (serverPublicKey, options = {}) { await keygen({ f: keyfile }) } + let bootstrap = null + if (options.testnet) { + bootstrap = [{ host: '127.0.0.1', port: options.testnet }] + } + if (options.L) { // Partially hardcoded "ClientSocket" here as tunnels behaves different, until we can organize better the dht, socket, and mux objects @@ -41,7 +46,7 @@ async function cmd (serverPublicKey, options = {}) { const seed = HypercoreId.decode(fs.readFileSync(keyfile, 'utf8').trim()) const keyPair = DHT.keyPair(seed) - const node = new DHT({ bootstrap: options.testnet ? [{ host: '127.0.0.1', port: 40838 }] : undefined }) + const node = new DHT({ bootstrap }) goodbye(() => node.destroy(), 2) for (const config of options.L) { @@ -58,7 +63,7 @@ async function cmd (serverPublicKey, options = {}) { if (options.R) errorAndExit('-R not supported') - const { node, socket } = ClientSocket({ keyfile, serverPublicKey, testnet: options.testnet }) + const { node, socket } = ClientSocket({ keyfile, serverPublicKey, bootstrap }) const mux = new Protomux(socket) const shell = new ShellClient(this.rawArgs, { node, socket, mux }) diff --git a/bin/copy.js b/bin/copy.js index eb291be..e0acb9f 100755 --- a/bin/copy.js +++ b/bin/copy.js @@ -20,7 +20,7 @@ program .argument('', 'Target') .option('-f ', 'Filename of the client seed key.', path.join(SHELLDIR, 'peer')) // .option('--key ', 'Inline key for the client.') - .option('--testnet', 'Use a local testnet.', false) + .option('--testnet ', 'Use a local testnet.', parseInt) .action(cmd) .parseAsync() @@ -44,7 +44,12 @@ async function cmd (sourcePath, targetPath, options = {}) { errorAndExit('Invalid source or target path.') } - const { node, socket } = ClientSocket({ keyfile, serverPublicKey, testnet: options.testnet }) + let bootstrap = null + if (options.testnet != null) { + bootstrap = [{ host: '127.0.0.1', port: options.testnet }] + } + + const { node, socket } = ClientSocket({ keyfile, serverPublicKey, bootstrap }) const mux = new Protomux(socket) if (fileOperation === 'upload') { diff --git a/bin/server.js b/bin/server.js index a3c80b8..9cf4893 100755 --- a/bin/server.js +++ b/bin/server.js @@ -30,7 +30,7 @@ program .option('--protocol ', 'List of allowed protocols.') .option('--tunnel-host ', 'Restrict tunneling to a limited set of hosts.') .option('--tunnel-port ', 'Restrict tunneling to a limited set of ports.') - .option('--testnet', 'Use a local testnet.', false) + .option('--testnet ', 'Use a local testnet at the specified port.', parseInt) .action(cmd) .parseAsync() @@ -54,7 +54,12 @@ async function cmd (options = {}) { const seed = HypercoreId.decode(fs.readFileSync(keyfile, 'utf8').trim()) const keyPair = DHT.keyPair(seed) - const node = new DHT({ bootstrap: options.testnet ? [{ host: '127.0.0.1', port: 40838 }] : undefined }) + let bootstrap = null + if (options.testnet) { + bootstrap = [{ host: '127.0.0.1', port: options.testnet }] + } + + const node = new DHT({ bootstrap }) goodbye(() => node.destroy(), 3) const server = node.createServer({ firewall: onFirewall }) diff --git a/lib/client-socket.js b/lib/client-socket.js index fce7fbd..e51e897 100644 --- a/lib/client-socket.js +++ b/lib/client-socket.js @@ -9,13 +9,13 @@ module.exports = { waitForSocketTermination } -function ClientSocket ({ keyfile, serverPublicKey, reusableSocket = false, testnet = false }) { +function ClientSocket ({ keyfile, serverPublicKey, reusableSocket = false, bootstrap }) { serverPublicKey = getKnownPeer(serverPublicKey) const seed = HypercoreId.decode(fs.readFileSync(keyfile, 'utf8').trim()) const keyPair = DHT.keyPair(seed) - const node = new DHT({ bootstrap: testnet ? [{ host: '127.0.0.1', port: 40838 }] : undefined }) + const node = new DHT({ bootstrap }) const unregisterNode = goodbye(() => node.destroy(), 2) const socket = node.connect(serverPublicKey, { keyPair, reusableSocket }) diff --git a/test/basic.js b/test/basic.js index 930fa9b..3fb7ed8 100644 --- a/test/basic.js +++ b/test/basic.js @@ -4,6 +4,8 @@ const fs = require('fs') const { create, spawnKeygen, spawnServer, spawnClient, spawnCopy, waitForProcess, waitForServerReady } = require('./helpers/index.js') const { shellFile } = require('../lib/shell.js') +const DEBUG_LOGS = false + test('keygen', async function (t) { t.plan(6) @@ -36,12 +38,12 @@ test('keygen', async function (t) { test('shell', async function (t) { t.plan(4) - const { clientkey, serverkey, firewall, serverKeyPair } = await create(t) - - const server = spawnServer(t, { serverkey, firewall }) + const { clientkey, serverkey, firewall, serverKeyPair, bootstrap } = await create(t) + const server = spawnServer(t, { serverkey, firewall, bootstrap }) server.once('close', (code) => t.pass('server closed: ' + code)) server.stdout.on('data', (data) => { + if (DEBUG_LOGS) console.log(` ${data}`) if (data.startsWith('Firewall allowed:')) { t.pass('Server firewall allowed') } @@ -49,10 +51,11 @@ test('shell', async function (t) { await waitForServerReady(server) - const client = spawnClient(t, serverKeyPair.publicKey.toString('hex'), { clientkey }) + const client = spawnClient(t, serverKeyPair.publicKey.toString('hex'), { clientkey, bootstrap }) client.on('close', (code) => t.pass('client closed: ' + code)) client.stdout.on('data', (data) => { + if (DEBUG_LOGS) console.log(` ${data}`) if (data.indexOf('The number is: 1234') > -1) { t.pass('client stdout match') @@ -74,7 +77,7 @@ test('shell', async function (t) { test('copy - upload (absolute path)', async function (t) { t.plan(5) - const { root, clientkey, serverkey, firewall, serverKeyPair } = await create(t) + const { root, clientkey, serverkey, firewall, serverKeyPair, bootstrap } = await create(t) const src = path.join(root, 'file-original.txt') const dst = path.join(root, 'file-backup.txt') @@ -82,13 +85,13 @@ test('copy - upload (absolute path)', async function (t) { fs.writeFileSync(src, 'hello', { flag: 'wx' }) t.absent(fs.existsSync(dst)) - const server = spawnServer(t, { serverkey, firewall }) + const server = spawnServer(t, { serverkey, firewall, bootstrap }) server.once('close', (code) => t.pass('server closed: ' + code)) await waitForServerReady(server) const pk = serverKeyPair.publicKey.toString('hex') - const upload = spawnCopy(t, src, pk + ':' + dst, { clientkey }) + const upload = spawnCopy(t, src, pk + ':' + dst, { clientkey, bootstrap }) upload.on('close', (code) => t.pass('upload closed: ' + code)) upload.on('close', () => { @@ -104,7 +107,7 @@ test('copy - upload (absolute path)', async function (t) { test('copy - download (absolute path)', async function (t) { t.plan(5) - const { root, clientkey, serverkey, firewall, serverKeyPair } = await create(t) + const { root, clientkey, serverkey, firewall, serverKeyPair, bootstrap } = await create(t) const src = path.join(root, 'file-original.txt') const dst = path.join(root, 'file-backup.txt') @@ -112,13 +115,13 @@ test('copy - download (absolute path)', async function (t) { fs.writeFileSync(src, 'hello', { flag: 'wx' }) t.absent(fs.existsSync(dst)) - const server = spawnServer(t, { serverkey, firewall }) + const server = spawnServer(t, { serverkey, firewall, bootstrap }) server.once('close', (code) => t.pass('server closed: ' + code)) await waitForServerReady(server) const pk = serverKeyPair.publicKey.toString('hex') - const download = spawnCopy(t, pk + ':' + src, dst, { clientkey }) + const download = spawnCopy(t, pk + ':' + src, dst, { clientkey, bootstrap }) download.on('close', (code) => t.pass('download closed: ' + code)) download.on('close', () => { diff --git a/test/helpers/index.js b/test/helpers/index.js index 2a061f1..83804a8 100644 --- a/test/helpers/index.js +++ b/test/helpers/index.js @@ -48,9 +48,10 @@ async function create (t) { const serverKeyPair = keygen(serverkey) addAuthorizedPeer(firewall, clientkey) - const swarm = await useTestnet(t) + const { swarm } = await useTestnet(t) + const bootstrap = swarm.bootstrap - return { root, clientkey, serverkey, firewall, swarm, clientKeyPair, serverKeyPair } + return { root, clientkey, serverkey, firewall, bootstrap, clientKeyPair, serverKeyPair } } // + should require to pass the args array, and just automatically append --testnet @@ -68,8 +69,9 @@ function spawnKeygen (t, { keyfile }) { return sp } -function spawnServer (t, { serverkey, firewall }) { - const sp = spawn(process.execPath, [BIN_SERVER, '-f', serverkey, '--firewall', firewall, '--testnet'], { timeout: 15000 }) +function spawnServer (t, { serverkey, firewall, bootstrap }) { + const bootstrapPort = bootstrap[0].port + const sp = spawn(process.execPath, [BIN_SERVER, '-f', serverkey, '--firewall', firewall, '--testnet', bootstrapPort], { timeout: 15000 }) t.teardown(() => sp.kill()) sp.stdout.setEncoding('utf8') @@ -81,8 +83,9 @@ function spawnServer (t, { serverkey, firewall }) { return sp } -function spawnClient (t, serverPublicKey, { clientkey }) { - const sp = spawn(process.execPath, [BIN_CLIENT, serverPublicKey, '-f', clientkey, '--testnet'], { timeout: 15000 }) +function spawnClient (t, serverPublicKey, { clientkey, bootstrap }) { + const bootstrapPort = bootstrap[0].port + const sp = spawn(process.execPath, [BIN_CLIENT, serverPublicKey, '-f', clientkey, '--testnet', bootstrapPort], { timeout: 15000 }) t.teardown(() => sp.kill()) sp.stdout.setEncoding('utf8') @@ -94,8 +97,9 @@ function spawnClient (t, serverPublicKey, { clientkey }) { return sp } -function spawnCopy (t, source, target, { clientkey }) { - const sp = spawn(process.execPath, [BIN_COPY, source, target, '-f', clientkey, '--testnet'], { timeout: 15000 }) +function spawnCopy (t, source, target, { clientkey, bootstrap }) { + const bootstrapPort = bootstrap[0].port + const sp = spawn(process.execPath, [BIN_COPY, source, target, '-f', clientkey, '--testnet', bootstrapPort], { timeout: 15000 }) t.teardown(() => sp.kill()) sp.stdout.setEncoding('utf8') @@ -122,16 +126,10 @@ function addAuthorizedPeer (firewall, keyfile) { } async function useTestnet (t) { - const swarm = await createTestnet(3, { host: '127.0.0.1', port: 40838 }) + const swarm = await createTestnet(3) t.teardown(() => swarm.destroy()) - const bootstrap = swarm.nodes[0].address() - if (bootstrap.port !== 40838) { - await swarm.destroy() - throw new Error('Swarm failed to be created on specific port') - } - - return swarm + return { swarm } } function sleep (ms) {