summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaniel Silverstone <dsilvers@digital-scurf.org>2012-06-17 15:44:55 +0100
committerDaniel Silverstone <dsilvers@digital-scurf.org>2012-06-17 15:44:55 +0100
commit35b476da0595a027d166158ae9b4a97d466fad3a (patch)
treeeea5054743a9bbd6b11adfb97432d5b848865c95
parent9ed736a0822c7e61a27fe585a22fba601bbb7791 (diff)
downloadgitano-35b476da0595a027d166158ae9b4a97d466fad3a.tar.gz
COMMAND: New sshkey user command for manipulating ssh keys
-rw-r--r--lib/gitano/usercommand.lua117
1 files changed, 115 insertions, 2 deletions
diff --git a/lib/gitano/usercommand.lua b/lib/gitano/usercommand.lua
index 9d4f52f..cb4885b 100644
--- a/lib/gitano/usercommand.lua
+++ b/lib/gitano/usercommand.lua
@@ -7,6 +7,9 @@
local log = require 'gitano.log'
local util = require 'gitano.util'
local repository = require 'gitano.repository'
+local config = require 'gitano.config'
+
+local sio = require 'luxio.simple'
local builtin_whoami_short = "Find out how Gitano identifies you"
@@ -73,14 +76,124 @@ local function builtin_whoami_run(config, repo, cmdline, env)
return "exit", 0
end
+local builtin_sshkey_short = "SSH key management"
+local builtin_sshkey_usage = [[
+usage: sshkey [<del|add> <tag>]
+
+With no subcommand, sshkey will list the ssh keys you have, similarly to
+the whoami command.
+
+sshkey add <tag>
+
+ Adds an ssh key with the given tag. The content of the key must
+ be supplied on a single line on stdin.
+
+ cat id_rsa.pub | ssh gitano@somehost sshkey add personal-laptop
+
+sshkey del <tag>
+
+ Removes an ssh key with the given tag. If the current access is
+ via that ssh key then you cannot remove it. Add a new key and
+ switch to using that one first.
+]]
+
+local function builtin_sshkey_validate(config, _, cmdline)
+ if #cmdline == 1 then
+ cmdline[2] = "list"
+ end
+ if cmdline[2] == "list" then
+ if #cmdline > 2 then
+ log.error("sshkey list: No arguments expected")
+ return false
+ end
+ elseif cmdline[2] == "add" or cmdline[2] == "del" then
+ if #cmdline ~= 3 then
+ log.error("sshkey", cmdline[2] .. ": Expected tag and no more")
+ return false
+ end
+ else
+ log.error("sshkey: Unknown subcommand", cmdline[2])
+ return false
+ end
+
+ return true
+end
+
+local function builtin_sshkey_prep(config, _, cmdline, context)
+ local utab = config.users[context.user]
+ if cmdline[2] == "add" then
+ -- Ensure that the given tag doesn't already exist
+ if utab.keys[cmdline[3]] then
+ return "deny", "Key tag " .. cmdline[3] .. " already exists"
+ end
+ elseif cmdline[2] == "del" then
+ -- Ensure that the given tag does exist
+ if not utab.keys[cmdline[3]] then
+ return "deny", "Key tag " .. cmdline[3] .. " does not exist"
+ end
+ end
+ return "allow", "Users may manipulate their keys"
+end
+
+local function builtin_sshkey_run(conf, _, cmdline, env)
+ local utab = conf.users[env.GITANO_USER]
+ if cmdline[2] == "list" then
+ local pfx = " SSH key:"
+ for tagname, keydata in pairs(utab.keys) do
+ local suffix = (env.GITANO_KEYTAG == tagname) and " [*]" or ""
+ log.state(pfx, tagname, "=>", keydata.keytag .. suffix)
+ pfx = " "
+ end
+ elseif cmdline[2] == "add" then
+ local sshkey = sio.stdin:read("*l")
+ local keytype, keydata, keytag = sshkey:match("^([^ ]+) ([^ ]+) ([^ ]+)$")
+ if not (keytype and keydata and keytag) then
+ log.error("Unable to parse key,", filename,
+ "did not smell like an OpenSSH v2 key")
+ return "exit", 1
+ end
+ if (keytype ~= "ssh-rsa") and (keytype ~= "ssh-dss") and
+ (keytype ~= "ecdsa-sha2-nistp256") and
+ (keytype ~= "ecdsa-sha2-nistp384") and
+ (keytype ~= "ecdsa-sha2-nistp521") then
+ log.error("Unknown key type", keytype)
+ return "exit", 1
+ end
+ local keytab = {
+ data = sshkey,
+ keyname = cmdline[3],
+ username = env.GITANO_USER,
+ keytag = keytag,
+ }
+ utab.keys[cmdline[3]] = keytab
+
+ elseif cmdline[2] == "del" then
+ utab.keys[cmdline[3]] = nil
+ end
+
+ if cmdline[2] ~= "list" then
+ -- Store the config back.
+ local action = (cmdline[2] == "add") and "Added" or "Deleted"
+ action = action .. " " .. cmdline[3] .. " for " .. env.GITANO_USER
+ local ok, msg = config.commit(conf, action, env.GITANO_USER)
+ if not ok then
+ log.error(msg)
+ return "exit", 1
+ end
+ end
+
+ return "exit", 0
+end
local function register_commands(reg)
assert(reg("whoami", builtin_whoami_short, builtin_whoami_helptext,
builtin_whoami_validate,
builtin_whoami_prep, builtin_whoami_run, false, false))
-
+ assert(reg("sshkey", builtin_sshkey_short, builtin_sshkey_helptext,
+ builtin_sshkey_validate, builtin_sshkey_prep,
+ builtin_sshkey_run, false, false))
end
return {
register = register_commands
-} \ No newline at end of file
+}