Sfoglia il codice sorgente

chore(config): refactor to go generate; simplify configRules init (#1295)

Oleksandr Redko 2 anni fa
parent
commit
01e60c81e6

+ 1 - 1
.github/workflows/test.yml

@@ -26,4 +26,4 @@ jobs:
         run: make test
 
       - name: Validate Config
-        run: cd cmd/generate/config && go run main.go
+        run: go generate ./... && git diff --exit-code

+ 3 - 7
CONTRIBUTING.md

@@ -88,15 +88,11 @@ If you want to add a new rule to the [default Gitleaks configuration](https://gi
    validation part. You can use `generateSampleSecret` to create a secret for the
    true positives (`tps` in the example above) used in `validate`.
 
-1. Update `cmd/generate/config/main.go`. Add a line like
-   `configRules = append(configRules, rules.Beamer())` in `main()`. Try and keep
+1. Update `cmd/generate/config/main.go`. Extend `configRules` slice with
+   the `rules.Beamer(),` in `main()`. Try and keep
    this alphabetically pretty please.
 
-1. Change directories into `cmd/generate/config` and run `go run main.go`
-
-   ```
-   cd cmd/generate/config && go run main.go
-   ```
+1. Run `go generate ./...`
 
 1. Check out your new rules in `config/gitleaks.toml` and see if everything looks good.
 

+ 180 - 171
cmd/generate/config/main.go

@@ -14,179 +14,188 @@ const (
 	templatePath = "rules/config.tmpl"
 )
 
+//go:generate go run $GOFILE ../../../config/gitleaks.toml
+
 func main() {
-	var configRules []*config.Rule
-	configRules = append(configRules, rules.AdafruitAPIKey())
-	configRules = append(configRules, rules.AdobeClientID())
-	configRules = append(configRules, rules.AdobeClientSecret())
-	configRules = append(configRules, rules.AgeSecretKey())
-	configRules = append(configRules, rules.Airtable())
-	configRules = append(configRules, rules.AlgoliaApiKey())
-	configRules = append(configRules, rules.AlibabaAccessKey())
-	configRules = append(configRules, rules.AlibabaSecretKey())
-	configRules = append(configRules, rules.AsanaClientID())
-	configRules = append(configRules, rules.AsanaClientSecret())
-	configRules = append(configRules, rules.Atlassian())
-	configRules = append(configRules, rules.Authress())
-	configRules = append(configRules, rules.AWS())
-	configRules = append(configRules, rules.BitBucketClientID())
-	configRules = append(configRules, rules.BitBucketClientSecret())
-	configRules = append(configRules, rules.BittrexAccessKey())
-	configRules = append(configRules, rules.BittrexSecretKey())
-	configRules = append(configRules, rules.Beamer())
-	configRules = append(configRules, rules.CodecovAccessToken())
-	configRules = append(configRules, rules.CoinbaseAccessToken())
-	configRules = append(configRules, rules.Clojars())
-	configRules = append(configRules, rules.ConfluentAccessToken())
-	configRules = append(configRules, rules.ConfluentSecretKey())
-	configRules = append(configRules, rules.Contentful())
-	configRules = append(configRules, rules.Databricks())
-	configRules = append(configRules, rules.DatadogtokenAccessToken())
-	configRules = append(configRules, rules.DefinedNetworkingAPIToken())
-	configRules = append(configRules, rules.DigitalOceanPAT())
-	configRules = append(configRules, rules.DigitalOceanOAuthToken())
-	configRules = append(configRules, rules.DigitalOceanRefreshToken())
-	configRules = append(configRules, rules.DiscordAPIToken())
-	configRules = append(configRules, rules.DiscordClientID())
-	configRules = append(configRules, rules.DiscordClientSecret())
-	configRules = append(configRules, rules.Doppler())
-	configRules = append(configRules, rules.DropBoxAPISecret())
-	configRules = append(configRules, rules.DropBoxLongLivedAPIToken())
-	configRules = append(configRules, rules.DropBoxShortLivedAPIToken())
-	configRules = append(configRules, rules.DroneciAccessToken())
-	configRules = append(configRules, rules.Duffel())
-	configRules = append(configRules, rules.Dynatrace())
-	configRules = append(configRules, rules.EasyPost())
-	configRules = append(configRules, rules.EasyPostTestAPI())
-	configRules = append(configRules, rules.EtsyAccessToken())
-	configRules = append(configRules, rules.Facebook())
-	configRules = append(configRules, rules.FastlyAPIToken())
-	configRules = append(configRules, rules.FinicityClientSecret())
-	configRules = append(configRules, rules.FinicityAPIToken())
-	configRules = append(configRules, rules.FlickrAccessToken())
-	configRules = append(configRules, rules.FinnhubAccessToken())
-	configRules = append(configRules, rules.FlutterwavePublicKey())
-	configRules = append(configRules, rules.FlutterwaveSecretKey())
-	configRules = append(configRules, rules.FlutterwaveEncKey())
-	configRules = append(configRules, rules.FrameIO())
-	configRules = append(configRules, rules.FreshbooksAccessToken())
-	configRules = append(configRules, rules.GoCardless())
-	// TODO figure out what makes sense for GCP
-	// configRules = append(configRules, rules.GCPServiceAccount())
-	configRules = append(configRules, rules.GCPAPIKey())
-	configRules = append(configRules, rules.GitHubPat())
-	configRules = append(configRules, rules.GitHubFineGrainedPat())
-	configRules = append(configRules, rules.GitHubOauth())
-	configRules = append(configRules, rules.GitHubApp())
-	configRules = append(configRules, rules.GitHubRefresh())
-	configRules = append(configRules, rules.GitlabPat())
-	configRules = append(configRules, rules.GitlabPipelineTriggerToken())
-	configRules = append(configRules, rules.GitlabRunnerRegistrationToken())
-	configRules = append(configRules, rules.GitterAccessToken())
-	configRules = append(configRules, rules.GrafanaApiKey())
-	configRules = append(configRules, rules.GrafanaCloudApiToken())
-	configRules = append(configRules, rules.GrafanaServiceAccountToken())
-	configRules = append(configRules, rules.Hashicorp())
-	configRules = append(configRules, rules.HashicorpField())
-	configRules = append(configRules, rules.Heroku())
-	configRules = append(configRules, rules.HubSpot())
-	configRules = append(configRules, rules.HuggingFaceAccessToken())
-	configRules = append(configRules, rules.HuggingFaceOrganizationApiToken())
-	configRules = append(configRules, rules.Intercom())
-	configRules = append(configRules, rules.JFrogAPIKey())
-	configRules = append(configRules, rules.JFrogIdentityToken())
-	configRules = append(configRules, rules.JWT())
-	configRules = append(configRules, rules.JWTBase64())
-	configRules = append(configRules, rules.KrakenAccessToken())
-	configRules = append(configRules, rules.KucoinAccessToken())
-	configRules = append(configRules, rules.KucoinSecretKey())
-	configRules = append(configRules, rules.LaunchDarklyAccessToken())
-	configRules = append(configRules, rules.LinearAPIToken())
-	configRules = append(configRules, rules.LinearClientSecret())
-	configRules = append(configRules, rules.LinkedinClientID())
-	configRules = append(configRules, rules.LinkedinClientSecret())
-	configRules = append(configRules, rules.LobAPIToken())
-	configRules = append(configRules, rules.LobPubAPIToken())
-	configRules = append(configRules, rules.MailChimp())
-	configRules = append(configRules, rules.MailGunPubAPIToken())
-	configRules = append(configRules, rules.MailGunPrivateAPIToken())
-	configRules = append(configRules, rules.MailGunSigningKey())
-	configRules = append(configRules, rules.MapBox())
-	configRules = append(configRules, rules.MattermostAccessToken())
-	configRules = append(configRules, rules.MessageBirdAPIToken())
-	configRules = append(configRules, rules.MessageBirdClientID())
-	configRules = append(configRules, rules.NetlifyAccessToken())
-	configRules = append(configRules, rules.NewRelicUserID())
-	configRules = append(configRules, rules.NewRelicUserKey())
-	configRules = append(configRules, rules.NewRelicBrowserAPIKey())
-	configRules = append(configRules, rules.NPM())
-	configRules = append(configRules, rules.NytimesAccessToken())
-	configRules = append(configRules, rules.OktaAccessToken())
-	configRules = append(configRules, rules.OpenAI())
-	configRules = append(configRules, rules.PlaidAccessID())
-	configRules = append(configRules, rules.PlaidSecretKey())
-	configRules = append(configRules, rules.PlaidAccessToken())
-	configRules = append(configRules, rules.PlanetScalePassword())
-	configRules = append(configRules, rules.PlanetScaleAPIToken())
-	configRules = append(configRules, rules.PlanetScaleOAuthToken())
-	configRules = append(configRules, rules.PostManAPI())
-	configRules = append(configRules, rules.Prefect())
-	configRules = append(configRules, rules.PrivateKey())
-	configRules = append(configRules, rules.PulumiAPIToken())
-	configRules = append(configRules, rules.PyPiUploadToken())
-	configRules = append(configRules, rules.RapidAPIAccessToken())
-	configRules = append(configRules, rules.ReadMe())
-	configRules = append(configRules, rules.RubyGemsAPIToken())
-	configRules = append(configRules, rules.ScalingoAPIToken())
-	configRules = append(configRules, rules.SendbirdAccessID())
-	configRules = append(configRules, rules.SendbirdAccessToken())
-	configRules = append(configRules, rules.SendGridAPIToken())
-	configRules = append(configRules, rules.SendInBlueAPIToken())
-	configRules = append(configRules, rules.SentryAccessToken())
-	configRules = append(configRules, rules.ShippoAPIToken())
-	configRules = append(configRules, rules.ShopifyAccessToken())
-	configRules = append(configRules, rules.ShopifyCustomAccessToken())
-	configRules = append(configRules, rules.ShopifyPrivateAppAccessToken())
-	configRules = append(configRules, rules.ShopifySharedSecret())
-	configRules = append(configRules, rules.SidekiqSecret())
-	configRules = append(configRules, rules.SidekiqSensitiveUrl())
-	configRules = append(configRules, rules.SlackBotToken())
-	configRules = append(configRules, rules.SlackUserToken())
-	configRules = append(configRules, rules.SlackAppLevelToken())
-	configRules = append(configRules, rules.SlackConfigurationToken())
-	configRules = append(configRules, rules.SlackConfigurationRefreshToken())
-	configRules = append(configRules, rules.SlackLegacyBotToken())
-	configRules = append(configRules, rules.SlackLegacyWorkspaceToken())
-	configRules = append(configRules, rules.SlackLegacyToken())
-	configRules = append(configRules, rules.SlackWebHookUrl())
-	configRules = append(configRules, rules.Snyk())
-	configRules = append(configRules, rules.StripeAccessToken())
-	configRules = append(configRules, rules.SquareAccessToken())
-	configRules = append(configRules, rules.SquareSpaceAccessToken())
-	configRules = append(configRules, rules.SumoLogicAccessID())
-	configRules = append(configRules, rules.SumoLogicAccessToken())
-	configRules = append(configRules, rules.TeamsWebhook())
-	configRules = append(configRules, rules.TelegramBotToken())
-	configRules = append(configRules, rules.TravisCIAccessToken())
-	configRules = append(configRules, rules.Twilio())
-	configRules = append(configRules, rules.TwitchAPIToken())
-	configRules = append(configRules, rules.TwitterAPIKey())
-	configRules = append(configRules, rules.TwitterAPISecret())
-	configRules = append(configRules, rules.TwitterAccessToken())
-	configRules = append(configRules, rules.TwitterAccessSecret())
-	configRules = append(configRules, rules.TwitterBearerToken())
-	configRules = append(configRules, rules.Typeform())
-	configRules = append(configRules, rules.VaultBatchToken())
-	configRules = append(configRules, rules.VaultServiceToken())
-	configRules = append(configRules, rules.YandexAPIKey())
-	configRules = append(configRules, rules.YandexAWSAccessToken())
-	configRules = append(configRules, rules.YandexAccessToken())
-	configRules = append(configRules, rules.ZendeskSecretKey())
-	configRules = append(configRules, rules.GenericCredential())
-	configRules = append(configRules, rules.InfracostAPIToken())
+	if len(os.Args) < 2 {
+		os.Stderr.WriteString("Specify path to the gitleaks.toml config\n")
+		os.Exit(2)
+	}
+	gitleaksConfigPath := os.Args[1]
+
+	configRules := []*config.Rule{
+		rules.AdafruitAPIKey(),
+		rules.AdobeClientID(),
+		rules.AdobeClientSecret(),
+		rules.AgeSecretKey(),
+		rules.Airtable(),
+		rules.AlgoliaApiKey(),
+		rules.AlibabaAccessKey(),
+		rules.AlibabaSecretKey(),
+		rules.AsanaClientID(),
+		rules.AsanaClientSecret(),
+		rules.Atlassian(),
+		rules.Authress(),
+		rules.AWS(),
+		rules.BitBucketClientID(),
+		rules.BitBucketClientSecret(),
+		rules.BittrexAccessKey(),
+		rules.BittrexSecretKey(),
+		rules.Beamer(),
+		rules.CodecovAccessToken(),
+		rules.CoinbaseAccessToken(),
+		rules.Clojars(),
+		rules.ConfluentAccessToken(),
+		rules.ConfluentSecretKey(),
+		rules.Contentful(),
+		rules.Databricks(),
+		rules.DatadogtokenAccessToken(),
+		rules.DefinedNetworkingAPIToken(),
+		rules.DigitalOceanPAT(),
+		rules.DigitalOceanOAuthToken(),
+		rules.DigitalOceanRefreshToken(),
+		rules.DiscordAPIToken(),
+		rules.DiscordClientID(),
+		rules.DiscordClientSecret(),
+		rules.Doppler(),
+		rules.DropBoxAPISecret(),
+		rules.DropBoxLongLivedAPIToken(),
+		rules.DropBoxShortLivedAPIToken(),
+		rules.DroneciAccessToken(),
+		rules.Duffel(),
+		rules.Dynatrace(),
+		rules.EasyPost(),
+		rules.EasyPostTestAPI(),
+		rules.EtsyAccessToken(),
+		rules.Facebook(),
+		rules.FastlyAPIToken(),
+		rules.FinicityClientSecret(),
+		rules.FinicityAPIToken(),
+		rules.FlickrAccessToken(),
+		rules.FinnhubAccessToken(),
+		rules.FlutterwavePublicKey(),
+		rules.FlutterwaveSecretKey(),
+		rules.FlutterwaveEncKey(),
+		rules.FrameIO(),
+		rules.FreshbooksAccessToken(),
+		rules.GoCardless(),
+		// TODO figure out what makes sense for GCP
+		// rules.GCPServiceAccount(),
+		rules.GCPAPIKey(),
+		rules.GitHubPat(),
+		rules.GitHubFineGrainedPat(),
+		rules.GitHubOauth(),
+		rules.GitHubApp(),
+		rules.GitHubRefresh(),
+		rules.GitlabPat(),
+		rules.GitlabPipelineTriggerToken(),
+		rules.GitlabRunnerRegistrationToken(),
+		rules.GitterAccessToken(),
+		rules.GrafanaApiKey(),
+		rules.GrafanaCloudApiToken(),
+		rules.GrafanaServiceAccountToken(),
+		rules.Hashicorp(),
+		rules.HashicorpField(),
+		rules.Heroku(),
+		rules.HubSpot(),
+		rules.HuggingFaceAccessToken(),
+		rules.HuggingFaceOrganizationApiToken(),
+		rules.Intercom(),
+		rules.JFrogAPIKey(),
+		rules.JFrogIdentityToken(),
+		rules.JWT(),
+		rules.JWTBase64(),
+		rules.KrakenAccessToken(),
+		rules.KucoinAccessToken(),
+		rules.KucoinSecretKey(),
+		rules.LaunchDarklyAccessToken(),
+		rules.LinearAPIToken(),
+		rules.LinearClientSecret(),
+		rules.LinkedinClientID(),
+		rules.LinkedinClientSecret(),
+		rules.LobAPIToken(),
+		rules.LobPubAPIToken(),
+		rules.MailChimp(),
+		rules.MailGunPubAPIToken(),
+		rules.MailGunPrivateAPIToken(),
+		rules.MailGunSigningKey(),
+		rules.MapBox(),
+		rules.MattermostAccessToken(),
+		rules.MessageBirdAPIToken(),
+		rules.MessageBirdClientID(),
+		rules.NetlifyAccessToken(),
+		rules.NewRelicUserID(),
+		rules.NewRelicUserKey(),
+		rules.NewRelicBrowserAPIKey(),
+		rules.NPM(),
+		rules.NytimesAccessToken(),
+		rules.OktaAccessToken(),
+		rules.OpenAI(),
+		rules.PlaidAccessID(),
+		rules.PlaidSecretKey(),
+		rules.PlaidAccessToken(),
+		rules.PlanetScalePassword(),
+		rules.PlanetScaleAPIToken(),
+		rules.PlanetScaleOAuthToken(),
+		rules.PostManAPI(),
+		rules.Prefect(),
+		rules.PrivateKey(),
+		rules.PulumiAPIToken(),
+		rules.PyPiUploadToken(),
+		rules.RapidAPIAccessToken(),
+		rules.ReadMe(),
+		rules.RubyGemsAPIToken(),
+		rules.ScalingoAPIToken(),
+		rules.SendbirdAccessID(),
+		rules.SendbirdAccessToken(),
+		rules.SendGridAPIToken(),
+		rules.SendInBlueAPIToken(),
+		rules.SentryAccessToken(),
+		rules.ShippoAPIToken(),
+		rules.ShopifyAccessToken(),
+		rules.ShopifyCustomAccessToken(),
+		rules.ShopifyPrivateAppAccessToken(),
+		rules.ShopifySharedSecret(),
+		rules.SidekiqSecret(),
+		rules.SidekiqSensitiveUrl(),
+		rules.SlackBotToken(),
+		rules.SlackUserToken(),
+		rules.SlackAppLevelToken(),
+		rules.SlackConfigurationToken(),
+		rules.SlackConfigurationRefreshToken(),
+		rules.SlackLegacyBotToken(),
+		rules.SlackLegacyWorkspaceToken(),
+		rules.SlackLegacyToken(),
+		rules.SlackWebHookUrl(),
+		rules.Snyk(),
+		rules.StripeAccessToken(),
+		rules.SquareAccessToken(),
+		rules.SquareSpaceAccessToken(),
+		rules.SumoLogicAccessID(),
+		rules.SumoLogicAccessToken(),
+		rules.TeamsWebhook(),
+		rules.TelegramBotToken(),
+		rules.TravisCIAccessToken(),
+		rules.Twilio(),
+		rules.TwitchAPIToken(),
+		rules.TwitterAPIKey(),
+		rules.TwitterAPISecret(),
+		rules.TwitterAccessToken(),
+		rules.TwitterAccessSecret(),
+		rules.TwitterBearerToken(),
+		rules.Typeform(),
+		rules.VaultBatchToken(),
+		rules.VaultServiceToken(),
+		rules.YandexAPIKey(),
+		rules.YandexAWSAccessToken(),
+		rules.YandexAccessToken(),
+		rules.ZendeskSecretKey(),
+		rules.GenericCredential(),
+		rules.InfracostAPIToken(),
+	}
 
 	// ensure rules have unique ids
-	ruleLookUp := make(map[string]config.Rule)
+	ruleLookUp := make(map[string]config.Rule, len(configRules))
 	for _, rule := range configRules {
 		// check if rule is in ruleLookUp
 		if _, ok := ruleLookUp[rule.RuleID]; ok {
@@ -202,7 +211,7 @@ func main() {
 		log.Fatal().Err(err).Msg("Failed to parse template")
 	}
 
-	f, err := os.Create("../../../config/gitleaks.toml")
+	f, err := os.Create(gitleaksConfigPath)
 	if err != nil {
 		log.Fatal().Err(err).Msg("Failed to create rules.toml")
 	}

+ 1 - 1
cmd/generate/config/rules/authress.go

@@ -9,7 +9,7 @@ import (
 
 func Authress() *config.Rule {
 	// Rule Definition
-	// (Note: When changes are made to this, rerun `cd cmd/generate/config && go run main.go` and commit the config/gitleaks.toml file
+	// (Note: When changes are made to this, rerun `go generate ./...` and commit the config/gitleaks.toml file
 	r := config.Rule{
 		Description: "Authress Service Client Access Key",
 		RuleID:      "authress-service-client-access-key",