Add user create
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful

This commit is contained in:
Torjus Håkestad 2022-01-20 03:22:18 +01:00
parent ce5584ba7e
commit c6b282fbcc
2 changed files with 99 additions and 0 deletions

View File

@ -13,6 +13,7 @@ import (
"syscall" "syscall"
"time" "time"
"git.t-juice.club/torjus/gpaste"
"github.com/google/uuid" "github.com/google/uuid"
"github.com/urfave/cli/v2" "github.com/urfave/cli/v2"
"golang.org/x/term" "golang.org/x/term"
@ -53,6 +54,18 @@ func main() {
ArgsUsage: "USERNAME", ArgsUsage: "USERNAME",
Action: ActionLogin, Action: ActionLogin,
}, },
{
Name: "admin",
Usage: "Admin related commands",
Subcommands: []*cli.Command{
{
Name: "create-user",
Usage: "Create a new user",
ArgsUsage: "USERNAME",
Action: ActionUserCreate,
},
},
},
}, },
} }
@ -170,6 +183,52 @@ func ActionLogin(c *cli.Context) error {
return nil return nil
} }
func ActionUserCreate(c *cli.Context) error {
// TODO: Needs to supply auth token to actually work
username := c.Args().First()
if username == "" {
return cli.Exit("USERNAME not supplied.", 1)
}
password, err := readPassword()
if err != nil {
return fmt.Errorf("error reading password: %w", err)
}
url := fmt.Sprintf("%s/api/user", c.String("url"))
client := &http.Client{}
// TODO: Change timeout
ctx, cancel := context.WithTimeout(c.Context, 10*time.Second)
defer cancel()
body := new(bytes.Buffer)
requestData := &gpaste.RequestAPIUserCreate{
Username: username,
Password: password,
}
encoder := json.NewEncoder(body)
if err := encoder.Encode(requestData); err != nil {
return fmt.Errorf("error encoding response: %w", err)
}
req, err := http.NewRequestWithContext(ctx, http.MethodPost, url, body)
if err != nil {
return fmt.Errorf("error creating request: %w", err)
}
resp, err := client.Do(req)
if err != nil {
return fmt.Errorf("unable to perform request: %s", err)
}
defer resp.Body.Close()
if resp.StatusCode != http.StatusAccepted {
return cli.Exit("got non-ok response from server", 0)
}
fmt.Printf("Created user %s\n", username)
return nil
}
func readPassword() (string, error) { func readPassword() (string, error) {
fmt.Print("Enter Password: ") fmt.Print("Enter Password: ")
bytePassword, err := term.ReadPassword(int(syscall.Stdin)) bytePassword, err := term.ReadPassword(int(syscall.Stdin))

40
http.go
View File

@ -47,6 +47,7 @@ func NewHTTPServer(cfg *ServerConfig) *HTTPServer {
r.Post("/api/file", srv.HandlerAPIFilePost) r.Post("/api/file", srv.HandlerAPIFilePost)
r.Get("/api/file/{id}", srv.HandlerAPIFileGet) r.Get("/api/file/{id}", srv.HandlerAPIFileGet)
r.Post("/api/login", srv.HandlerAPILogin) r.Post("/api/login", srv.HandlerAPILogin)
r.Post("/api/user", srv.HandlerAPIUserCreate)
srv.Handler = r srv.Handler = r
return srv return srv
@ -188,3 +189,42 @@ func (s *HTTPServer) HandlerAPILogin(w http.ResponseWriter, r *http.Request) {
s.Logger.Infow("Error encoding json response to client.", "req_id", reqID, "error", err, "remote_addr", r.RemoteAddr) s.Logger.Infow("Error encoding json response to client.", "req_id", reqID, "error", err, "remote_addr", r.RemoteAddr)
} }
} }
type RequestAPIUserCreate struct {
Username string `json:"username"`
Password string `json:"password"`
}
func (s *HTTPServer) HandlerAPIUserCreate(w http.ResponseWriter, r *http.Request) {
reqID := middleware.GetReqID(r.Context())
defer r.Body.Close()
level, err := AuthLevelFromRequest(r)
if err != nil || level < AuthLevelAdmin {
w.WriteHeader(http.StatusUnauthorized)
return
}
var req RequestAPIUserCreate
decoder := json.NewDecoder(r.Body)
if err := decoder.Decode(&req); err != nil {
s.Logger.Debugw("Error parsing request.", "req_id", reqID, "error", err, "remote_addr", r.RemoteAddr)
w.WriteHeader(http.StatusBadRequest)
return
}
// TODO: Ensure user does not already exist
user := &User{Username: req.Username}
if err := user.SetPassword(req.Password); err != nil {
s.Logger.Warnw("Error setting user password.", "req_id", reqID, "error", err, "remote_addr", r.RemoteAddr)
w.WriteHeader(http.StatusBadRequest)
return
}
if err := s.Users.Store(user); err != nil {
s.Logger.Warnw("Error setting user password.", "req_id", reqID, "error", err, "remote_addr", r.RemoteAddr)
w.WriteHeader(http.StatusInternalServerError)
return
}
s.Logger.Infow("Created user.", "req_id", reqID, "remote_addr", r.RemoteAddr, "username", req.Username)
}