* Factory method to create an SSHKaos instance. * Establishes the SSH connection and SFTP session.
(options: SSHKaosOptions)
| 481 | * Establishes the SSH connection and SFTP session. |
| 482 | */ |
| 483 | static async create(options: SSHKaosOptions): Promise<SSHKaos> { |
| 484 | // Start from extraOptions (advanced ssh2 options) so our managed fields |
| 485 | // below take precedence. |
| 486 | const config: ConnectConfig = { |
| 487 | ...options.extraOptions, |
| 488 | host: options.host, |
| 489 | port: options.port ?? 22, |
| 490 | username: options.username, |
| 491 | }; |
| 492 | |
| 493 | if (options.password !== undefined) { |
| 494 | config.password = options.password; |
| 495 | } |
| 496 | |
| 497 | // Build private keys from keyContents and keyPaths |
| 498 | const privateKeys: (Buffer | string)[] = []; |
| 499 | if (options.keyContents) { |
| 500 | for (const content of options.keyContents) { |
| 501 | privateKeys.push(content); |
| 502 | } |
| 503 | } |
| 504 | if (options.keyPaths) { |
| 505 | const keyPromises = options.keyPaths.map((keyPath) => readFile(keyPath, 'utf-8')); |
| 506 | const keyData = await Promise.all(keyPromises); |
| 507 | for (const key of keyData) { |
| 508 | privateKeys.push(key); |
| 509 | } |
| 510 | } |
| 511 | if (privateKeys.length > 0) { |
| 512 | const authHandler = buildAuthHandler(options.username, privateKeys, options.password); |
| 513 | if (authHandler !== undefined) { |
| 514 | config.authHandler = authHandler; |
| 515 | } |
| 516 | } |
| 517 | |
| 518 | // Disable host key verification (like asyncssh known_hosts=None) |
| 519 | config.hostVerifier = () => true; |
| 520 | |
| 521 | const client = await connectClient(config); |
| 522 | try { |
| 523 | const sftp = await getSftp(client); |
| 524 | |
| 525 | // Determine home and cwd |
| 526 | const home = await sftpRealpath(sftp, '.'); |
| 527 | let cwd: string; |
| 528 | if (options.cwd === undefined) { |
| 529 | cwd = home; |
| 530 | } else { |
| 531 | cwd = await sftpRealpath(sftp, options.cwd); |
| 532 | const attrs = await sftpStat(sftp, cwd); |
| 533 | if (!attrs.isDirectory()) { |
| 534 | throw new KaosValueError(`${cwd} is not a directory`); |
| 535 | } |
| 536 | } |
| 537 | |
| 538 | return new SSHKaos(client, sftp, home, cwd); |
| 539 | } catch (error) { |
| 540 | client.end(); |
nothing calls this directly
no test coverage detected