2015-06-17 16:39:49 +00:00
|
|
|
package command
|
|
|
|
|
|
|
|
import (
|
|
|
|
"fmt"
|
2015-06-18 00:33:03 +00:00
|
|
|
"io/ioutil"
|
2015-06-17 16:39:49 +00:00
|
|
|
"log"
|
2015-06-24 22:13:12 +00:00
|
|
|
"net"
|
2015-06-18 00:33:03 +00:00
|
|
|
"os"
|
|
|
|
"os/exec"
|
2015-06-17 16:39:49 +00:00
|
|
|
"strings"
|
2015-06-18 00:33:03 +00:00
|
|
|
"syscall"
|
2015-06-17 16:39:49 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
type SshCommand struct {
|
|
|
|
Meta
|
|
|
|
}
|
|
|
|
|
|
|
|
func (c *SshCommand) Run(args []string) int {
|
2015-06-18 00:33:03 +00:00
|
|
|
log.SetFlags(log.LstdFlags | log.Lshortfile)
|
2015-06-17 16:39:49 +00:00
|
|
|
log.Printf("Vishal: SshCommand.Run: args:%#v len(args):%d\n", args, len(args))
|
|
|
|
flags := c.Meta.FlagSet("ssh", FlagSetDefault)
|
|
|
|
flags.Usage = func() { c.Ui.Error(c.Help()) }
|
|
|
|
if err := flags.Parse(args); err != nil {
|
|
|
|
return 1
|
|
|
|
}
|
|
|
|
|
|
|
|
client, err := c.Client()
|
|
|
|
if err != nil {
|
|
|
|
c.Ui.Error(fmt.Sprintf("Error initializing client: %s", err))
|
|
|
|
return 2
|
|
|
|
}
|
2015-06-26 01:47:32 +00:00
|
|
|
if len(args) < 1 {
|
|
|
|
c.Ui.Error(fmt.Sprintf("Insufficient arguments"))
|
|
|
|
return 2
|
|
|
|
}
|
2015-06-17 16:39:49 +00:00
|
|
|
log.Printf("Vishal: sshCommand.Run: args[0]: %#v\n", args[0])
|
2015-06-24 22:13:12 +00:00
|
|
|
input := strings.Split(args[0], "@")
|
|
|
|
username := input[0]
|
|
|
|
ipAddr, err := net.ResolveIPAddr("ip4", input[1])
|
|
|
|
log.Printf("Vishal: ssh.Ssh ipAddr_resolved: %#v\n", ipAddr.String())
|
|
|
|
data := map[string]interface{}{
|
|
|
|
"username": username,
|
|
|
|
"ip": ipAddr.String(),
|
|
|
|
}
|
|
|
|
|
2015-06-26 01:47:32 +00:00
|
|
|
keySecret, err := client.Ssh().KeyCreate(data)
|
2015-06-17 16:39:49 +00:00
|
|
|
if err != nil {
|
2015-06-24 22:13:12 +00:00
|
|
|
c.Ui.Error(fmt.Sprintf("Error getting key for establishing SSH session", err))
|
2015-06-17 16:39:49 +00:00
|
|
|
return 2
|
|
|
|
}
|
2015-06-24 22:13:12 +00:00
|
|
|
sshOneTimeKey := string(keySecret.Data["key"].(string))
|
2015-06-26 01:47:32 +00:00
|
|
|
log.Printf("Vishal: command.ssh.Run returned! len(key):%d\n", len(sshOneTimeKey))
|
2015-06-19 16:59:36 +00:00
|
|
|
ag := strings.Split(args[0], "@")
|
|
|
|
sshOtkFileName := "vault_ssh_otk_" + ag[0] + "_" + ag[1] + ".pem"
|
2015-06-24 22:13:12 +00:00
|
|
|
err = ioutil.WriteFile(sshOtkFileName, []byte(sshOneTimeKey), 0400)
|
2015-06-17 16:39:49 +00:00
|
|
|
//if sshOneTimeKey is empty, fail
|
|
|
|
//Establish a session directly from client to the target using the one time key received without making the vault server the middle guy:w
|
2015-06-18 00:33:03 +00:00
|
|
|
sshBinary, err := exec.LookPath("ssh")
|
|
|
|
if err != nil {
|
|
|
|
log.Printf("ssh binary not found in PATH\n")
|
|
|
|
}
|
|
|
|
|
|
|
|
sshEnv := os.Environ()
|
|
|
|
|
2015-06-19 16:59:36 +00:00
|
|
|
sshNew := "ssh -i " + sshOtkFileName + " " + args[0]
|
2015-06-19 00:48:41 +00:00
|
|
|
log.Printf("Vishal: sshNew:%#v\n", sshNew)
|
2015-06-19 16:59:36 +00:00
|
|
|
sshCmdArgs := []string{"ssh", "-i", sshOtkFileName, args[0]}
|
|
|
|
//defer os.Remove("vault_ssh_otk_" + args[0] + ".pem")
|
2015-06-18 00:33:03 +00:00
|
|
|
|
|
|
|
if err := syscall.Exec(sshBinary, sshCmdArgs, sshEnv); err != nil {
|
|
|
|
log.Printf("Execution failed: sshCommand: " + err.Error())
|
|
|
|
}
|
2015-06-17 16:39:49 +00:00
|
|
|
return 0
|
|
|
|
}
|
|
|
|
|
2015-06-24 22:13:12 +00:00
|
|
|
type OneTimeKey struct {
|
|
|
|
Key string
|
|
|
|
}
|
|
|
|
|
2015-06-17 16:39:49 +00:00
|
|
|
func (c *SshCommand) Synopsis() string {
|
|
|
|
return "Initiate a SSH session"
|
|
|
|
}
|
|
|
|
|
|
|
|
func (c *SshCommand) Help() string {
|
|
|
|
helpText := `
|
|
|
|
SshCommand Help String
|
|
|
|
`
|
|
|
|
return strings.TrimSpace(helpText)
|
|
|
|
}
|