test-userauth-agent-openssh.js 2.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109
  1. 'use strict';
  2. const assert = require('assert');
  3. const { spawnSync } = require('child_process');
  4. const debug = false;
  5. const SPAWN_OPTS = { windowsHide: true };
  6. // TODO: figure out why this test is failing on Windows
  7. if (process.platform === 'win32') {
  8. console.log('Skipping ssh-agent test on Windows');
  9. process.exit(0);
  10. }
  11. if (process.argv[2] === 'child') {
  12. const {
  13. fixtureKey,
  14. mustCall,
  15. setup,
  16. } = require('./common.js');
  17. const serverCfg = { hostKeys: [ fixtureKey('ssh_host_rsa_key').raw ] };
  18. const clientKey = fixtureKey('openssh_new_rsa');
  19. // Add key to the agent first
  20. {
  21. const {
  22. error, status
  23. } = spawnSync('ssh-add', [ clientKey.fullPath ], SPAWN_OPTS);
  24. if (error || status !== 0) {
  25. console.error('Failed to add key to agent');
  26. process.exit(1);
  27. }
  28. }
  29. const username = 'Agent User';
  30. const { server } = setup(
  31. 'Agent authentication',
  32. {
  33. client: { username, agent: process.env.SSH_AUTH_SOCK },
  34. server: serverCfg,
  35. debug,
  36. }
  37. );
  38. server.on('connection', mustCall((conn) => {
  39. let authAttempt = 0;
  40. conn.on('authentication', mustCall((ctx) => {
  41. assert(ctx.username === username,
  42. `Wrong username: ${ctx.username}`);
  43. switch (++authAttempt) {
  44. case 1:
  45. assert(ctx.method === 'none', `Wrong auth method: ${ctx.method}`);
  46. return ctx.reject();
  47. case 3:
  48. assert(ctx.signature, 'Missing publickey signature');
  49. // FALLTHROUGH
  50. case 2:
  51. assert(ctx.method === 'publickey',
  52. `Wrong auth method: ${ctx.method}`);
  53. assert(ctx.key.algo === clientKey.key.type,
  54. `Wrong key algo: ${ctx.key.algo}`);
  55. assert.deepStrictEqual(clientKey.key.getPublicSSH(),
  56. ctx.key.data,
  57. 'Public key mismatch');
  58. break;
  59. }
  60. if (ctx.signature) {
  61. assert(clientKey.key.verify(ctx.blob, ctx.signature) === true,
  62. 'Could not verify publickey signature');
  63. }
  64. ctx.accept();
  65. }, 3)).on('ready', mustCall(() => {
  66. conn.end();
  67. }));
  68. }));
  69. } else {
  70. {
  71. const {
  72. error, status
  73. } = spawnSync('which', ['ssh-agent'], SPAWN_OPTS);
  74. if (error || status !== 0) {
  75. console.log('No ssh-agent available, skipping agent test ...');
  76. process.exit(0);
  77. }
  78. }
  79. {
  80. const {
  81. error, status
  82. } = spawnSync('which', ['ssh-add'], SPAWN_OPTS);
  83. if (error || status !== 0) {
  84. console.log('No ssh-add available, skipping agent test ...');
  85. process.exit(0);
  86. }
  87. }
  88. const {
  89. error, status
  90. } = spawnSync('ssh-agent',
  91. [ process.execPath, __filename, 'child' ],
  92. { ...SPAWN_OPTS, stdio: 'inherit' });
  93. if (error || status !== 0)
  94. throw new Error('Agent test failed');
  95. }