// NewClient connects to the given host via SSH, the client will support // agent forwarding but it must also be enabled per-session. func (a *SSHAgent) NewClient(host string) (*ssh.Client, error) { sshcfg := ssh.ClientConfig{ User: a.User, Auth: []ssh.AuthMethod{ ssh.PublicKeysCallback(a.Signers), }, } addr := ensurePortSuffix(host, defaultPort) tcpconn, err := a.Dial("tcp", addr) if err != nil { return nil, err } sshconn, chans, reqs, err := ssh.NewClientConn(tcpconn, addr, &sshcfg) if err != nil { return nil, err } client := ssh.NewClient(sshconn, chans, reqs) err = agent.ForwardToAgent(client, a) if err != nil { client.Close() return nil, err } return client, nil }
func TestAgentForward(t *testing.T) { server := newServer(t) defer server.Shutdown() conn := server.Dial(clientConfig()) defer conn.Close() keyring := agent.NewKeyring() keyring.Add(testPrivateKeys["dsa"], nil, "") pub := testPublicKeys["dsa"] sess, err := conn.NewSession() if err != nil { t.Fatalf("NewSession: %v", err) } if err := agent.RequestAgentForwarding(sess); err != nil { t.Fatalf("RequestAgentForwarding: %v", err) } if err := agent.ForwardToAgent(conn, keyring); err != nil { t.Fatalf("SetupForwardKeyring: %v", err) } out, err := sess.CombinedOutput("ssh-add -L") if err != nil { t.Fatalf("running ssh-add: %v, out %s", err, out) } key, _, _, _, err := ssh.ParseAuthorizedKey(out) if err != nil { t.Fatalf("ParseAuthorizedKey(%q): %v", out, err) } if !bytes.Equal(key.Marshal(), pub.Marshal()) { t.Fatalf("got key %s, want %s", ssh.MarshalAuthorizedKey(key), ssh.MarshalAuthorizedKey(pub)) } }