vole
Clone
Read only, no credentials:
https://rodent.software/git/vole.git
Write over SSH with a registered key:
git clone ssh://git@0.0.0.0:2222/vole.git
A free and open-source forge that lives in your Git repo.
Align the CLI with Git's command conventions
ade6107e546a7f1859ca4fe23a327d44871dce6d · Keenan Nemetz · 15d ago · parent 04e00cfc
cmd/vole/acl.go +48−8
| @@ -1,7 +1,6 @@ | |||
| 1 | 1 | package main | |
| 2 | 2 | ||
| 3 | 3 | import ( | |
| 4 | "errors" | ||
| 5 | 4 | "fmt" | |
| 6 | 5 | "os" | |
| 7 | 6 | "strconv" | |
| @@ -13,9 +12,25 @@ import ( | |||
| 13 | 12 | ||
| 14 | 13 | // ---------- acl ---------- | |
| 15 | 14 | ||
| 15 | // aclUsage is the help for the access-control command group. | ||
| 16 | const aclUsage = `usage: vole admin acl <command> [options] [args] | ||
| 17 | |||
| 18 | show <repo> | ||
| 19 | set <repo> <user> <none|read|contributor|maintain|admin> | ||
| 20 | default <repo> <none|read|contributor|maintain|admin> | ||
| 21 | protect <repo> <ref-pattern>... | ||
| 22 | approvals <repo> <n> | ||
| 23 | checks <repo> <on|off> | ||
| 24 | runners <repo> [<user>...] [--add <user> | --remove <user> | --clear]` | ||
| 25 | |||
| 16 | 26 | func cmdACL(args []string) error { | |
| 17 | 27 | if len(args) == 0 { | |
| 18 | return errors.New("usage: vole admin acl show|set|default|protect|checks|approvals|runners") | ||
| 28 | fmt.Fprintln(os.Stderr, aclUsage) | ||
| 29 | return usageErr{msg: "no acl subcommand given"} | ||
| 30 | } | ||
| 31 | if args[0] == "-h" || args[0] == "--help" || args[0] == "help" { | ||
| 32 | fmt.Fprintln(os.Stdout, aclUsage) | ||
| 33 | return nil | ||
| 19 | 34 | } | |
| 20 | 35 | sub := args[0] | |
| 21 | 36 | f, err := parseFlags(args[1:], configFlag(), | |
| @@ -24,6 +39,27 @@ func cmdACL(args []string) error { | |||
| 24 | 39 | if err != nil { | |
| 25 | 40 | return err | |
| 26 | 41 | } | |
| 42 | if f.help { | ||
| 43 | fmt.Fprintln(os.Stdout, aclUsage) | ||
| 44 | return nil | ||
| 45 | } | ||
| 46 | aclFlags := map[string][]string{ | ||
| 47 | "show": {"config"}, | ||
| 48 | "set": {"config"}, | ||
| 49 | "default": {"config"}, | ||
| 50 | "protect": {"config"}, | ||
| 51 | "checks": {"config"}, | ||
| 52 | "approvals": {"config"}, | ||
| 53 | "runners": {"config", "add", "remove", "clear"}, | ||
| 54 | } | ||
| 55 | names, ok := aclFlags[sub] | ||
| 56 | if !ok { | ||
| 57 | fmt.Fprintln(os.Stderr, aclUsage) | ||
| 58 | return usagef("unknown acl subcommand %q", sub) | ||
| 59 | } | ||
| 60 | if err := f.checkAllowed("vole admin acl "+sub, names...); err != nil { | ||
| 61 | return err | ||
| 62 | } | ||
| 27 | 63 | st, err := forge.OpenPath(f.cfgPath) | |
| 28 | 64 | if err != nil { | |
| 29 | 65 | return err | |
| @@ -47,6 +83,9 @@ func cmdACL(args []string) error { | |||
| 47 | 83 | ||
| 48 | 84 | switch sub { | |
| 49 | 85 | case "show": | |
| 86 | if len(f.rest) != 1 { | ||
| 87 | return usageErr{msg: "usage: vole admin acl show <repo>"} | ||
| 88 | } | ||
| 50 | 89 | vis := "private" | |
| 51 | 90 | if a.Can("", access.Read) { | |
| 52 | 91 | vis = "public" | |
| @@ -80,7 +119,7 @@ func cmdACL(args []string) error { | |||
| 80 | 119 | ||
| 81 | 120 | case "set": | |
| 82 | 121 | if len(f.rest) != 3 { | |
| 83 | return errors.New("usage: vole admin acl set <repo> <user> <none|read|contributor|maintain|admin>") | ||
| 122 | return usageErr{msg: "usage: vole admin acl set <repo> <user> <none|read|contributor|maintain|admin>"} | ||
| 84 | 123 | } | |
| 85 | 124 | role, err := access.ParseRole(f.rest[2]) | |
| 86 | 125 | if err != nil { | |
| @@ -102,7 +141,7 @@ func cmdACL(args []string) error { | |||
| 102 | 141 | ||
| 103 | 142 | case "default": | |
| 104 | 143 | if len(f.rest) != 2 { | |
| 105 | return errors.New("usage: vole admin acl default <repo> <none|read|contributor|maintain|admin>") | ||
| 144 | return usageErr{msg: "usage: vole admin acl default <repo> <none|read|contributor|maintain|admin>"} | ||
| 106 | 145 | } | |
| 107 | 146 | role, err := access.ParseRole(f.rest[1]) | |
| 108 | 147 | if err != nil { | |
| @@ -122,7 +161,7 @@ func cmdACL(args []string) error { | |||
| 122 | 161 | ||
| 123 | 162 | case "protect": | |
| 124 | 163 | if len(f.rest) < 2 { | |
| 125 | return errors.New("usage: vole admin acl protect <repo> <ref-pattern>...") | ||
| 164 | return usageErr{msg: "usage: vole admin acl protect <repo> <ref-pattern>..."} | ||
| 126 | 165 | } | |
| 127 | 166 | a.Protected = f.rest[1:] | |
| 128 | 167 | if err := m.SetACL(a, os.Getenv("USER")); err != nil { | |
| @@ -134,7 +173,7 @@ func cmdACL(args []string) error { | |||
| 134 | 173 | ||
| 135 | 174 | case "checks": | |
| 136 | 175 | if len(f.rest) != 2 { | |
| 137 | return errors.New("usage: vole admin acl checks <repo> <on|off>") | ||
| 176 | return usageErr{msg: "usage: vole admin acl checks <repo> <on|off>"} | ||
| 138 | 177 | } | |
| 139 | 178 | switch strings.ToLower(f.rest[1]) { | |
| 140 | 179 | case "on", "true", "yes", "1": | |
| @@ -232,7 +271,7 @@ func cmdACL(args []string) error { | |||
| 232 | 271 | ||
| 233 | 272 | case "approvals": | |
| 234 | 273 | if len(f.rest) != 2 { | |
| 235 | return errors.New("usage: vole admin acl approvals <repo> <n>") | ||
| 274 | return usageErr{msg: "usage: vole admin acl approvals <repo> <n>"} | ||
| 236 | 275 | } | |
| 237 | 276 | n, err := strconv.Atoi(f.rest[1]) | |
| 238 | 277 | if err != nil || n < 0 { | |
| @@ -250,7 +289,8 @@ func cmdACL(args []string) error { | |||
| 250 | 289 | } | |
| 251 | 290 | return nil | |
| 252 | 291 | } | |
| 253 | return fmt.Errorf("unknown acl subcommand %q", sub) | ||
| 292 | fmt.Fprintln(os.Stderr, aclUsage) | ||
| 293 | return usagef("unknown acl subcommand %q", sub) | ||
| 254 | 294 | } | |
| 255 | 295 | ||
| 256 | 296 | // runnerAccount resolves a name or id to an account id, refusing an unknown one | |