in src/main/scala/com/gu/ssm/Main.scala [87:124]
private def setUpBastionSSH(
awsClients: AWSClients,
executionTarget: ExecutionTarget,
user: String,
sism: SingleInstanceSelectionMode,
onlyUsePrivateIP: Boolean,
rawOutput: Boolean,
bastionInstance: ExecutionTarget,
bastionPortNumberOpt: Option[Int],
bastionUser: String,
targetInstancePortNumberOpt: Option[Int],
useAgent: Option[Boolean],
preferredAlgs: List[String]): ProgramResult = {
val fProgramResult = for {
sshArtifacts <- Attempt.fromEither(SSH.createKey())
(privateKeyFile, publicKey) = sshArtifacts
bastionConfig <- IO.getSSMConfig(awsClients.ec2Client, awsClients.stsClient, bastionInstance)
bastionInstance <- Attempt.fromEither(Logic.getSSHInstance(bastionConfig.targets, sism))
bastionAddPublicKeyCommand = SSH.addPublicKeyCommand(user, publicKey) + SSH.outputHostKeysCommand()
bastionRemovePublicKeyCommand = SSH.removePublicKeyCommand(user, publicKey)
bastionAddress <- Attempt.fromEither(Logic.getAddress(bastionInstance, onlyUsePrivateIP))
targetConfig <- IO.getSSMConfig(awsClients.ec2Client, awsClients.stsClient, executionTarget)
targetInstance <- Attempt.fromEither(Logic.getSSHInstance(targetConfig.targets, sism))
targetAddress <- Attempt.fromEither(Logic.getAddress(targetInstance, true))
targetAddPublicKeyCommand = SSH.addTaintedCommand(targetConfig.name) + SSH.addPublicKeyCommand(user, publicKey) + SSH.outputHostKeysCommand()
targetRemovePublicKeyCommand = SSH.removePublicKeyCommand(user, publicKey)
bastionResult <- IO.executeOnInstance(bastionInstance.id, bastionConfig.name, bastionAddPublicKeyCommand, awsClients.ssmClient)
_ <- IO.executeOnInstanceAsync(bastionInstance.id, bastionConfig.name, bastionRemovePublicKeyCommand, awsClients.ssmClient)
_ <- IO.tagAsTainted(targetInstance.id, targetConfig.name, awsClients.ec2Client)
targetResult <- IO.executeOnInstance(targetInstance.id, targetConfig.name, targetAddPublicKeyCommand, awsClients.ssmClient)
_ <- IO.executeOnInstanceAsync(targetInstance.id, targetConfig.name, targetRemovePublicKeyCommand, awsClients.ssmClient)
bastionHostKey <- Attempt.fromEither(Logic.getHostKeyEntry(bastionResult, preferredAlgs))
targetHostKey <- Attempt.fromEither(Logic.getHostKeyEntry(targetResult, preferredAlgs))
hostKeyFile <- SSH.writeHostKey((bastionAddress, bastionHostKey), (targetAddress, targetHostKey))
} yield SSH.sshCmdBastion(rawOutput)(privateKeyFile, bastionInstance, targetInstance, user, bastionAddress, targetAddress, bastionPortNumberOpt, bastionUser, targetInstancePortNumberOpt, useAgent, Some(hostKeyFile))
val programResult = Await.result(fProgramResult.asFuture, Duration.Inf)
ProgramResult.convertErrorToResult(programResult.map(UI.sshOutput(rawOutput)))
}