diff --git a/cmd/help/main.go b/cmd/help/main.go index 7c89b31..318aa13 100644 --- a/cmd/help/main.go +++ b/cmd/help/main.go @@ -1,10 +1,12 @@ package main import ( + "bytes" "database/sql" "errors" "fmt" "os" + "os/exec" "strconv" "strings" @@ -16,7 +18,7 @@ import ( "github.com/mattn/go-tty" ) -// TODO consider local-only help command for renaming and adding emails to account +// TODO consider local-only help command for renaming, email mgmt, deleting account // TODO put colorscheme, prompting stuff into own packages for use in the other commands. would be good to get off of survey. @@ -262,9 +264,27 @@ func redeemCode(db *sql.DB, cs colorScheme, p *Prompter) error { return nil } - // TODO need to create a new helper: appendkeyfile and use sudoers to allow help to call it. also need to add help user and add it to /etc/ssh/sshd_config + cmd := exec.Command("sudo", "--user", user.Username, "/town/bin/appendkeyfile", user.Username) + cmd.Stdin = bytes.NewBufferString(key) + stdoutBuff := bytes.NewBuffer([]byte{}) + cmd.Stdout = stdoutBuff + if err = cmd.Run(); err != nil { + // TODO log error + //return fmt.Errorf("appendkeyfile failed with '%s': %w", string(stdoutBuff.Bytes()), err) + return errors.New("adding to keys file failed") + } + + // TODO add help user + // TODO update sshd_config + // TODO update sudoers + // TODO compile appendkeyfile and add to /town/bin/ + + err = code.MarkUsed(db) + if err != nil { + // TODO log err + return errors.New("database was sad") + } - // TODO mark used return nil } diff --git a/towndb/towndb.go b/towndb/towndb.go index 01e175d..9d03b04 100644 --- a/towndb/towndb.go +++ b/towndb/towndb.go @@ -221,4 +221,32 @@ func (c *AuthCode) Hydrate(db *sql.DB) error { return stmt.QueryRow(c.Code).Scan(&c.ID, &c.Used, &c.Created) } -// TODO other auth code as needed +func (c *AuthCode) MarkUsed(db *sql.DB) error { + if c.ID == 0 { + return errors.New("not hydrated") + } + + stmt, err := db.Prepare(` + UPDATE auth_codes SET used = 1 WHERE id = ?`) + if err != nil { + return err + } + defer stmt.Close() + + result, err := stmt.Exec(c.ID) + if err != nil { + return err + } + + var rowsAffected int64 + + if rowsAffected, err = result.RowsAffected(); err != nil { + return err + } + + if rowsAffected == 0 { + return errors.New("no rows affected") + } + + return nil +}