@@ -2,6 +2,7 @@ package main
2
2
3
3
import (
4
4
"context"
5
+ "errors"
5
6
"flag"
6
7
"fmt"
7
8
"net/http"
@@ -14,104 +15,95 @@ import (
14
15
"golang.org/x/oauth2"
15
16
16
17
"github.com/genuinetools/audit/version"
18
+ "github.com/genuinetools/pkg/cli"
17
19
"github.com/google/go-github/github"
18
20
"github.com/sirupsen/logrus"
19
21
)
20
22
21
- const (
22
- // BANNER is what is printed for help/info output.
23
- BANNER = ` _ _ _
24
- __ _ _ _ __| (_) |_
25
- / _` + "`" + ` | | | |/ _` + "`" + ` | | __|
26
- | (_| | |_| | (_| | | |_
27
- \__,_|\__,_|\__,_|_|\__|
28
-
29
- Auditing what collaborators, hooks, and deploy keys you have added on all your GitHub repositories.
30
- Version: %s
31
- Build: %s
32
-
33
- `
34
- )
35
-
36
23
var (
37
24
token string
38
25
repo string
26
+ owner bool
39
27
40
28
debug bool
41
- vrsn bool
42
- owner bool
43
29
)
44
30
45
- func init () {
46
- // parse flags
47
- flag .StringVar (& token , "token" , os .Getenv ("GITHUB_TOKEN" ), "GitHub API token (or env var GITHUB_TOKEN)" )
48
- flag .StringVar (& repo , "repo" , "" , "specific repo to test (e.g. 'genuinetools/audit')" )
49
-
50
- flag .BoolVar (& vrsn , "version" , false , "print version and exit" )
51
- flag .BoolVar (& vrsn , "v" , false , "print version and exit (shorthand)" )
52
- flag .BoolVar (& debug , "d" , false , "run in debug mode" )
53
- flag .BoolVar (& owner , "owner" , false , "only audit repos the token owner owns" )
54
-
55
- flag .Usage = func () {
56
- fmt .Fprint (os .Stderr , fmt .Sprintf (BANNER , version .VERSION , version .GITCOMMIT ))
57
- flag .PrintDefaults ()
58
- }
59
-
60
- flag .Parse ()
61
-
62
- if vrsn {
63
- fmt .Printf ("audit version %s, build %s" , version .VERSION , version .GITCOMMIT )
64
- os .Exit (0 )
65
- }
31
+ func main () {
32
+ // Create a new cli program.
33
+ p := cli .NewProgram ()
34
+ p .Name = "audit"
35
+ p .Description = "Tool to audit what collaborators, hooks, and deploy keys are on your GitHub repositories"
36
+
37
+ // Set the GitCommit and Version.
38
+ p .GitCommit = version .GITCOMMIT
39
+ p .Version = version .VERSION
40
+
41
+ // Setup the global flags.
42
+ p .FlagSet = flag .NewFlagSet ("global" , flag .ExitOnError )
43
+ p .FlagSet .StringVar (& token , "token" , os .Getenv ("GITHUB_TOKEN" ), "GitHub API token (or env var GITHUB_TOKEN)" )
44
+ p .FlagSet .StringVar (& repo , "repo" , "" , "specific repo to test (e.g. 'genuinetools/audit')" )
45
+ p .FlagSet .BoolVar (& owner , "owner" , false , "only audit repos the token owner owns" )
46
+ p .FlagSet .BoolVar (& debug , "d" , false , "enable debug logging" )
47
+
48
+ // Set the before function.
49
+ p .Before = func (ctx context.Context ) error {
50
+ // Set the log level.
51
+ if debug {
52
+ logrus .SetLevel (logrus .DebugLevel )
53
+ }
66
54
67
- // set log level
68
- if debug {
69
- logrus .SetLevel (logrus .DebugLevel )
70
- }
55
+ if token == "" {
56
+ return errors .New ("GitHub token cannot be empty" )
57
+ }
71
58
72
- if token == "" {
73
- usageAndExit ("GitHub token cannot be empty." , 1 )
59
+ return nil
74
60
}
75
- }
76
61
77
- func main () {
78
- // On ^C, or SIGTERM handle exit.
79
- signals := make (chan os.Signal , 0 )
80
- signal .Notify (signals , os .Interrupt )
81
- signal .Notify (signals , syscall .SIGTERM )
82
- ctx , cancel := context .WithCancel (context .Background ())
83
- go func () {
84
- for sig := range signals {
85
- cancel ()
86
- logrus .Infof ("Received %s, exiting." , sig .String ())
87
- os .Exit (0 )
62
+ // Set the main program action.
63
+ p .Action = func (ctx context.Context ) error {
64
+ // On ^C, or SIGTERM handle exit.
65
+ signals := make (chan os.Signal , 0 )
66
+ signal .Notify (signals , os .Interrupt )
67
+ signal .Notify (signals , syscall .SIGTERM )
68
+ var cancel context.CancelFunc
69
+ ctx , cancel = context .WithCancel (ctx )
70
+ go func () {
71
+ for sig := range signals {
72
+ cancel ()
73
+ logrus .Infof ("Received %s, exiting." , sig .String ())
74
+ os .Exit (0 )
75
+ }
76
+ }()
77
+
78
+ // Create the http client.
79
+ ts := oauth2 .StaticTokenSource (
80
+ & oauth2.Token {AccessToken : token },
81
+ )
82
+ tc := oauth2 .NewClient (ctx , ts )
83
+
84
+ // Create the github client.
85
+ client := github .NewClient (tc )
86
+ page := 1
87
+ perPage := 100
88
+ var affiliation string
89
+ if owner {
90
+ affiliation = "owner"
91
+ } else {
92
+ affiliation = "owner,collaborator,organization_member"
88
93
}
89
- }()
94
+ logrus .Debugf ("Getting repositories..." )
95
+ if err := getRepositories (ctx , client , page , perPage , affiliation , repo ); err != nil {
96
+ if v , ok := err .(* github.RateLimitError ); ok {
97
+ logrus .Fatalf ("%s Limit: %d; Remaining: %d; Retry After: %s" , v .Message , v .Rate .Limit , v .Rate .Remaining , time .Until (v .Rate .Reset .Time ).String ())
98
+ }
90
99
91
- // Create the http client.
92
- ts := oauth2 .StaticTokenSource (
93
- & oauth2.Token {AccessToken : token },
94
- )
95
- tc := oauth2 .NewClient (ctx , ts )
96
-
97
- // Create the github client.
98
- client := github .NewClient (tc )
99
- page := 1
100
- perPage := 100
101
- var affiliation string
102
- if owner {
103
- affiliation = "owner"
104
- } else {
105
- affiliation = "owner,collaborator,organization_member"
106
- }
107
- logrus .Debugf ("Getting repositories..." )
108
- if err := getRepositories (ctx , client , page , perPage , affiliation , repo ); err != nil {
109
- if v , ok := err .(* github.RateLimitError ); ok {
110
- logrus .Fatalf ("%s Limit: %d; Remaining: %d; Retry After: %s" , v .Message , v .Rate .Limit , v .Rate .Remaining , time .Until (v .Rate .Reset .Time ).String ())
100
+ logrus .Fatal (err )
111
101
}
112
-
113
- logrus .Fatal (err )
102
+ return nil
114
103
}
104
+
105
+ // Run our program.
106
+ p .Run ()
115
107
}
116
108
117
109
func getRepositories (ctx context.Context , client * github.Client , page , perPage int , affiliation string , searchRepo string ) error {
0 commit comments