// writeSSHKeys writes out a new ~/.ssh/authorised_keys file, retaining any non Juju keys // and adding the specified set of Juju keys. func (kw *keyupdaterWorker) writeSSHKeys(jujuKeys []string) error { allKeys := kw.nonJujuKeys // Ensure any Juju keys have the required prefix in their comment. for i, key := range jujuKeys { jujuKeys[i] = ssh.EnsureJujuComment(key) } allKeys = append(allKeys, jujuKeys...) return ssh.ReplaceKeys(SSHUser, allKeys...) }
// splitAuthKeys splits the given authorized keys // into the form expected to be found in the // user data. func splitAuthKeys(keys string) []interface{} { slines := strings.FieldsFunc(keys, func(r rune) bool { return r == '\n' }) var lines []interface{} for _, line := range slines { lines = append(lines, ssh.EnsureJujuComment(strings.TrimSpace(line))) } return lines }
// AddSSHAuthorizedKeys adds a set of keys in // ssh authorized_keys format (see ssh(8) for details) // that will be added to ~/.ssh/authorized_keys for the // configured user (see SetUser). func (cfg *Config) AddSSHAuthorizedKeys(keyData string) { akeys, _ := cfg.attrs["ssh_authorized_keys"].([]string) keys := ssh.SplitAuthorisedKeys(keyData) for _, key := range keys { // Ensure the key has a comment prepended with "Juju:" so we // can distinguish between Juju managed keys and those added // externally. jujuKey := ssh.EnsureJujuComment(key) akeys = append(akeys, jujuKey) } cfg.attrs["ssh_authorized_keys"] = akeys }
func (s *AuthorisedKeysKeysSuite) TestEnsureJujuComment(c *gc.C) { sshKey := sshtesting.ValidKeyOne.Key for _, test := range []struct { key string expected string }{ {"invalid-key", "invalid-key"}, {sshKey, sshKey + " Juju:sshkey"}, {sshKey + " user@host", sshKey + " Juju:user@host"}, {sshKey + " Juju:user@host", sshKey + " Juju:user@host"}, {sshKey + " " + sshKey[3:5], sshKey + " Juju:" + sshKey[3:5]}, } { actual := ssh.EnsureJujuComment(test.key) c.Assert(actual, gc.Equals, test.expected) } }