Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: ignore-on-exit flag to control the error code #162

Merged
merged 28 commits into from
Sep 28, 2023
Merged
Show file tree
Hide file tree
Changes from 10 commits
Commits
Show all changes
28 commits
Select commit Hold shift + click to select a range
9fdbd5a
Addded ignore-secret flag to all plugins (relevant sub-commands)
Aug 6, 2023
db979d9
Added ignore-on-exit flag to all sub commands
Aug 8, 2023
a17f2ae
Merge branch 'Checkmarx:master' into issue_155
nirmo Aug 8, 2023
b5860fb
changed IgnoreOnExitFlag var to ignoreOnExitFlag
Aug 8, 2023
06373e6
Merge branch 'issue_155' of https://github.com/nirmo/2ms into issue_155
Aug 8, 2023
6f4361a
issue 155 - add ignore-on-exit flag and change exit code logic
Aug 11, 2023
61ffa53
Merge branch 'Checkmarx:master' into issue_155
nirmo Aug 11, 2023
c5a866f
Merge branch 'Checkmarx:master' into issue_155
nirmo Aug 11, 2023
48ed7c0
Merge branch 'issue_155' of https://github.com/nirmo/2ms into issue_155
Aug 11, 2023
7b35e70
Issue 155 - minor changes
Aug 11, 2023
f74f216
Issue155 - added error channel and removed log fatal(s)
Aug 18, 2023
b399c8b
moved errorChan check after sleep wait
Aug 18, 2023
193afd6
merging changes from master
Aug 24, 2023
3b56fc8
sync with main
Sep 2, 2023
a3e131c
simplfying showError, removing comments and adding error channel check
Sep 2, 2023
dfcad26
modified ShowError and getFiles funcs
Sep 4, 2023
2eb264d
Merge pull request #2 from nirmo/master
nirmo Sep 4, 2023
40342fb
make the ignore-on-exit to be enum flag
Sep 27, 2023
417451f
refactor: reduce main size
Sep 27, 2023
7cc6483
move error decide to exit_handler
Sep 27, 2023
2785d3b
refactor: listen for errors
Sep 27, 2023
75a159a
one exit point
Sep 27, 2023
4d8a234
Merge remote-tracking branch 'origin/master' into pr/nirmo/162-1
Sep 27, 2023
060fde0
update README
Sep 27, 2023
2d328a7
Merge remote-tracking branch 'origin/master' into pr/nirmo/162-1
Sep 28, 2023
c880867
avoid using log.Fatal
Sep 28, 2023
1cbb777
remove comment
Sep 28, 2023
4a268a9
simplify the cmd.Error
Sep 28, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
76 changes: 53 additions & 23 deletions cmd/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ const (
includeRuleFlagName = "include-rule"
excludeRuleFlagName = "exclude-rule"
ignoreFlagName = "ignore-result"
ignoreOnExitFlagName = "ignore-on-exit"
)

var (
Expand All @@ -47,6 +48,7 @@ var (
includeRuleVar []string
excludeRuleVar []string
ignoreVar []string
ignoreOnExitVar string
)

var rootCmd = &cobra.Command{
Expand Down Expand Up @@ -107,10 +109,9 @@ func initialize() {
}
}

func Execute() {
func Execute() error {
vConfig.SetEnvPrefix(envPrefix)
vConfig.AutomaticEnv()

cobra.OnInitialize(initialize)
rootCmd.PersistentFlags().StringVar(&configFilePath, configFileFlag, "", "config file path")
cobra.CheckErr(rootCmd.MarkPersistentFlagFilename(configFileFlag, "yaml", "yml", "json"))
Expand All @@ -122,52 +123,62 @@ func Execute() {
rootCmd.PersistentFlags().StringSliceVar(&excludeRuleVar, excludeRuleFlagName, []string{}, "exclude rules by name or tag to apply to the scan (removes from list, starts from all)")
rootCmd.MarkFlagsMutuallyExclusive(includeRuleFlagName, excludeRuleFlagName)
rootCmd.PersistentFlags().StringSliceVar(&ignoreVar, ignoreFlagName, []string{}, "ignore specific result by id")
rootCmd.PersistentFlags().StringVar(&ignoreOnExitVar, ignoreOnExitFlagName, "none", "defines which kind of non-zero exits code should be ignored\naccepts: all, results, errors, none\nexample: if 'results' is set, only engine errors will make 2ms exit code different from 0")

rootCmd.AddCommand(secrets.RulesCommand)

group := "Commands"
rootCmd.AddGroup(&cobra.Group{Title: group, ID: group})

for _, plugin := range allPlugins {
subCommand, err := plugin.DefineCommand(channels)
if err != nil {
log.Fatal().Msg(fmt.Sprintf("error while defining command for plugin %s: %s", plugin.GetName(), err.Error()))
return fmt.Errorf("error while defining command for plugin %s: %s", plugin.GetName(), err.Error())
}
subCommand.GroupID = group
subCommand.PreRun = preRun
subCommand.PostRun = postRun
subCommand.PreRunE = preRun
subCommand.PostRunE = postRun
baruchiro marked this conversation as resolved.
Show resolved Hide resolved
rootCmd.AddCommand(subCommand)
}

if err := rootCmd.Execute(); err != nil {
log.Fatal().Msg(err.Error())
return err
}

return nil
}

func validateFormat(stdout string, reportPath []string) {
func validateFormat(stdout string, reportPath []string) error {
r := regexp.MustCompile(outputFormatRegexpPattern)
if !(r.MatchString(stdout)) {
log.Fatal().Msgf(`invalid output format: %s, available formats are: json, yaml and sarif`, stdout)
baruchiro marked this conversation as resolved.
Show resolved Hide resolved
return fmt.Errorf(`invalid output format: %s, available formats are: json, yaml and sarif`, stdout)
}

for _, path := range reportPath {
fileExtension := filepath.Ext(path)
format := strings.TrimPrefix(fileExtension, ".")
if !(r.MatchString(format)) {
log.Fatal().Msgf(`invalid report extension: %s, available extensions are: json, yaml and sarif`, format)
return fmt.Errorf(`invalid report extension: %s, available extensions are: json, yaml and sarif`, format)
}
}

return nil
}

func preRun(cmd *cobra.Command, args []string) {
validateFormat(stdoutFormatVar, reportPathVar)
func preRun(cmd *cobra.Command, args []string) error {
if err := validateFormat(stdoutFormatVar, reportPathVar); err != nil {
return err
}

secrets, err := secrets.Init(includeRuleVar, excludeRuleVar)
if err != nil {
log.Fatal().Msg(err.Error())
return err
}

if err := secrets.AddRegexRules(customRegexRuleVar); err != nil {
log.Fatal().Msg(err.Error())
return err
}

if err := InitShouldIgnoreArg(ignoreOnExitVar); err != nil {
return err
}
baruchiro marked this conversation as resolved.
Show resolved Hide resolved

go func() {
Expand All @@ -181,16 +192,18 @@ func preRun(cmd *cobra.Command, args []string) {
report.TotalSecretsFound++
report.Results[secret.ID] = append(report.Results[secret.ID], secret)
case err, ok := <-channels.Errors:
if !ok {
//ToDo discuss whether this is the right approach
if !ok || ShowError("errors") {
return
}
log.Fatal().Msg(err.Error())
}
}
}()
return nil
}

func postRun(cmd *cobra.Command, args []string) {
func postRun(cmd *cobra.Command, args []string) error {
channels.WaitGroup.Wait()

cfg := config.LoadConfig("2ms", Version)
Expand All @@ -205,17 +218,34 @@ func postRun(cmd *cobra.Command, args []string) {
if len(reportPathVar) > 0 {
err := report.WriteFile(reportPathVar, cfg)
if err != nil {
log.Error().Msgf("Failed to create report file with error: %s", err)
return fmt.Errorf("failed to create report file with error: %s", err)
}
}
} else {
log.Error().Msg("Scan completed with empty content")
os.Exit(0)
fmt.Println("Scan completed with empty content")
return nil
baruchiro marked this conversation as resolved.
Show resolved Hide resolved
}

if report.TotalSecretsFound > 0 {
if report.TotalSecretsFound > 0 && ShowError("errors") {
os.Exit(1)
} else {
os.Exit(0)
}

return nil
}

// InitShouldIgnoreArg initializes what kind of errors should be used on exit codes
baruchiro marked this conversation as resolved.
Show resolved Hide resolved
func InitShouldIgnoreArg(arg string) error {
validArgs := []string{"none", "all", "results", "errors"}
for _, validArg := range validArgs {
if strings.EqualFold(validArg, arg) {
ignoreOnExitVar = strings.ToLower(arg)
return nil
}
}
return fmt.Errorf("unknown argument for --ignore-on-exit: %s\nvalid arguments:\n %s", arg, strings.Join(validArgs, "\n "))
}

// ShowError returns true if should show error, otherwise returns false
func ShowError(kind string) bool {
return strings.EqualFold(ignoreOnExitVar, "none") || (!strings.EqualFold(ignoreOnExitVar, "all") && !strings.EqualFold(ignoreOnExitVar, kind))
}
baruchiro marked this conversation as resolved.
Show resolved Hide resolved
7 changes: 6 additions & 1 deletion main.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,12 @@ func main() {
stopChan := make(chan os.Signal, 1)
signal.Notify(stopChan, os.Interrupt)
go listenForInterrupt(stopChan)
cmd.Execute()

if err := cmd.Execute(); err != nil {
if cmd.ShowError("errors") {
os.Exit(1)
}
}
baruchiro marked this conversation as resolved.
Show resolved Hide resolved
}

func listenForInterrupt(stopScan chan os.Signal) {
Expand Down