chore: import upstream snapshot with attribution
gitleaks / gitleaks (push) Has been skipped
Test / test (ubuntu-latest) (push) Failing after 0s
Test / test (windows-latest) (push) Has been cancelled

This commit is contained in:
wehub-resource-sync
2026-07-13 12:12:29 +08:00
commit 48b3ccf279
454 changed files with 32865 additions and 0 deletions
+136
View File
@@ -0,0 +1,136 @@
// The `detect` and `protect` command is now deprecated. Here are some equivalent commands
// to help guide you.
// OLD CMD: gitleaks detect --source={repo}
// NEW CMD: gitleaks git {repo}
// OLD CMD: gitleaks protect --source={repo}
// NEW CMD: gitleaks git --pre-commit {repo}
// OLD CMD: gitleaks protect --staged --source={repo}
// NEW CMD: gitleaks git --pre-commit --staged {repo}
// OLD CMD: gitleaks detect --no-git --source={repo}
// NEW CMD: gitleaks directory {directory/file}
// OLD CMD: gitleaks detect --no-git --pipe
// NEW CMD: gitleaks stdin
package cmd
import (
"os"
"time"
"github.com/spf13/cobra"
"github.com/zricethezav/gitleaks/v8/cmd/scm"
"github.com/zricethezav/gitleaks/v8/logging"
"github.com/zricethezav/gitleaks/v8/report"
"github.com/zricethezav/gitleaks/v8/sources"
)
func init() {
rootCmd.AddCommand(detectCmd)
detectCmd.Flags().Bool("no-git", false, "treat git repo as a regular directory and scan those files, --log-opts has no effect on the scan when --no-git is set")
detectCmd.Flags().Bool("pipe", false, "scan input from stdin, ex: `cat some_file | gitleaks detect --pipe`")
detectCmd.Flags().Bool("follow-symlinks", false, "scan files that are symlinks to other files")
detectCmd.Flags().StringP("source", "s", ".", "path to source")
detectCmd.Flags().String("log-opts", "", "git log options")
detectCmd.Flags().String("platform", "", "the target platform used to generate links (github, gitlab)")
}
var detectCmd = &cobra.Command{
Use: "detect",
Short: "detect secrets in code",
Run: runDetect,
Hidden: true,
}
func runDetect(cmd *cobra.Command, args []string) {
// start timer
start := time.Now()
sourcePath := mustGetStringFlag(cmd, "source")
// setup config (aka, the thing that defines rules)
initConfig(sourcePath)
initDiagnostics()
cfg := Config(cmd)
// create detector
detector := Detector(cmd, cfg, sourcePath)
// parse flags
detector.FollowSymlinks = mustGetBoolFlag(cmd, "follow-symlinks")
exitCode := mustGetIntFlag(cmd, "exit-code")
noGit := mustGetBoolFlag(cmd, "no-git")
fromPipe := mustGetBoolFlag(cmd, "pipe")
// determine what type of scan:
// - git: scan the history of the repo
// - no-git: scan files by treating the repo as a plain directory
var (
err error
findings []report.Finding
)
if noGit {
findings, err = detector.DetectSource(
cmd.Context(), &sources.Files{
Config: &cfg,
FollowSymlinks: detector.FollowSymlinks,
MaxFileSize: detector.MaxTargetMegaBytes * 1_000_000,
Path: sourcePath,
Sema: detector.Sema,
MaxArchiveDepth: detector.MaxArchiveDepth,
},
)
if err != nil {
// don't exit on error, just log it
logging.Error().Err(err).Msg("failed to scan directory")
}
} else if fromPipe {
findings, err = detector.DetectSource(
cmd.Context(), &sources.File{
Content: os.Stdin,
MaxArchiveDepth: detector.MaxArchiveDepth,
},
)
if err != nil {
// log fatal to exit, no need to continue since a report
// will not be generated when scanning from a pipe...for now
logging.Fatal().Err(err).Msg("failed scan input from stdin")
}
} else {
var (
gitCmd *sources.GitCmd
scmPlatform scm.Platform
)
logOpts := mustGetStringFlag(cmd, "log-opts")
if gitCmd, err = sources.NewGitLogCmdContext(cmd.Context(), sourcePath, logOpts); err != nil {
logging.Fatal().Err(err).Msg("could not create Git cmd")
}
if scmPlatform, err = scm.PlatformFromString(mustGetStringFlag(cmd, "platform")); err != nil {
logging.Fatal().Err(err).Send()
}
findings, err = detector.DetectSource(
cmd.Context(), &sources.Git{
Cmd: gitCmd,
Config: &detector.Config,
Remote: sources.NewRemoteInfoContext(cmd.Context(), scmPlatform, sourcePath),
Sema: detector.Sema,
MaxArchiveDepth: detector.MaxArchiveDepth,
},
)
if err != nil {
// don't exit on error, just log it
logging.Error().Err(err).Msg("failed to scan Git repository")
}
}
findingSummaryAndExit(detector, findings, exitCode, start, err)
}
+239
View File
@@ -0,0 +1,239 @@
package cmd
import (
"errors"
"fmt"
"net/http"
_ "net/http/pprof"
"os"
"path/filepath"
"runtime"
"runtime/pprof"
"runtime/trace"
"strings"
"github.com/zricethezav/gitleaks/v8/logging"
)
// DiagnosticsManager manages various types of diagnostics
type DiagnosticsManager struct {
Enabled bool
DiagTypes []string
OutputDir string
cpuProfile *os.File
memProfile string
traceProfile *os.File
}
// NewDiagnosticsManager creates a new DiagnosticsManager instance
func NewDiagnosticsManager(diagnosticsFlag string, diagnosticsDir string) (*DiagnosticsManager, error) {
if diagnosticsFlag == "" {
return &DiagnosticsManager{Enabled: false}, nil
}
dm := &DiagnosticsManager{
Enabled: true,
DiagTypes: strings.Split(diagnosticsFlag, ","),
OutputDir: diagnosticsDir,
}
if diagnosticsFlag == "http" {
if len(diagnosticsDir) != 0 {
return nil, errors.New("the diagnostics directory should not be set in http mode")
}
return dm, nil
}
// If no output directory is specified, use the current directory
if dm.OutputDir == "" {
var err error
dm.OutputDir, err = os.Getwd()
if err != nil {
return nil, fmt.Errorf("failed to get current directory: %w", err)
}
logging.Debug().Msgf("No diagnostics directory specified, using current directory: %s", dm.OutputDir)
}
// Create the output directory if it doesn't exist
if err := os.MkdirAll(dm.OutputDir, 0755); err != nil {
return nil, fmt.Errorf("failed to create diagnostics directory: %w", err)
}
// Make sure the output directory is absolute
if !filepath.IsAbs(dm.OutputDir) {
absPath, err := filepath.Abs(dm.OutputDir)
if err != nil {
return nil, fmt.Errorf("failed to get absolute path for diagnostics directory: %w", err)
}
dm.OutputDir = absPath
}
logging.Debug().Msgf("Diagnostics enabled: %s", strings.Join(dm.DiagTypes, ","))
logging.Debug().Msgf("Diagnostics output directory: %s", dm.OutputDir)
return dm, nil
}
// StartDiagnostics starts all enabled diagnostics
func (dm *DiagnosticsManager) StartDiagnostics() error {
if !dm.Enabled {
return nil
}
var err error
for _, diagType := range dm.DiagTypes {
diagType = strings.TrimSpace(diagType)
switch diagType {
case "cpu":
if err = dm.StartCPUProfile(); err != nil {
return err
}
case "mem":
if err = dm.SetupMemoryProfile(); err != nil {
return err
}
case "trace":
if err = dm.StartTraceProfile(); err != nil {
return err
}
case "http":
if err = dm.StartHttpHandler(); err != nil {
return err
}
default:
logging.Warn().Msgf("Unknown diagnostics type: %s", diagType)
}
}
return nil
}
// StopDiagnostics stops all started diagnostics
func (dm *DiagnosticsManager) StopDiagnostics() {
if !dm.Enabled {
return
}
logging.Debug().Msg("Stopping diagnostics and writing profiling data...")
for _, diagType := range dm.DiagTypes {
diagType = strings.TrimSpace(diagType)
switch diagType {
case "cpu":
dm.StopCPUProfile()
case "mem":
dm.WriteMemoryProfile()
case "trace":
dm.StopTraceProfile()
case "http":
// No need to stop the http one
}
}
}
func (dm *DiagnosticsManager) StartHttpHandler() error {
if len(dm.DiagTypes) > 1 {
return errors.New("other diagnostics modes should not be enabled when http mode is enabled")
}
go func() {
logging.Error().Err(http.ListenAndServe("localhost:6060", nil)).Send()
}()
logging.Info().Str("url", "http://localhost:6060/debug/pprof/").Msg("Diagnostics server started")
return nil
}
// StartCPUProfile starts CPU profiling
func (dm *DiagnosticsManager) StartCPUProfile() error {
cpuProfilePath := filepath.Join(dm.OutputDir, "cpu.pprof")
f, err := os.Create(cpuProfilePath)
if err != nil {
return fmt.Errorf("could not create CPU profile at %s: %w", cpuProfilePath, err)
}
if err := pprof.StartCPUProfile(f); err != nil {
_ = f.Close()
return fmt.Errorf("could not start CPU profile: %w", err)
}
dm.cpuProfile = f
return nil
}
// StopCPUProfile stops CPU profiling
func (dm *DiagnosticsManager) StopCPUProfile() {
if dm.cpuProfile != nil {
pprof.StopCPUProfile()
if err := dm.cpuProfile.Close(); err != nil {
logging.Error().Err(err).Msg("Error closing CPU profile file")
}
logging.Info().Msgf("CPU profile written to: %s", dm.cpuProfile.Name())
dm.cpuProfile = nil
}
}
// SetupMemoryProfile sets up memory profiling to be written when StopDiagnostics is called
func (dm *DiagnosticsManager) SetupMemoryProfile() error {
memProfilePath := filepath.Join(dm.OutputDir, "mem.pprof")
dm.memProfile = memProfilePath
return nil
}
// WriteMemoryProfile writes the memory profile to disk
func (dm *DiagnosticsManager) WriteMemoryProfile() {
if dm.memProfile == "" {
return
}
f, err := os.Create(dm.memProfile)
if err != nil {
logging.Error().Err(err).Msgf("Could not create memory profile at %s", dm.memProfile)
return
}
// Get memory profile
runtime.GC() // Run GC before taking the memory profile
if err := pprof.WriteHeapProfile(f); err != nil {
logging.Error().Err(err).Msg("Could not write memory profile")
} else {
logging.Info().Msgf("Memory profile written to: %s", dm.memProfile)
}
if err := f.Close(); err != nil {
logging.Error().Err(err).Msg("Error closing memory profile file")
}
dm.memProfile = ""
}
// StartTraceProfile starts execution tracing
func (dm *DiagnosticsManager) StartTraceProfile() error {
traceProfilePath := filepath.Join(dm.OutputDir, "trace.out")
f, err := os.Create(traceProfilePath)
if err != nil {
return fmt.Errorf("could not create trace profile at %s: %w", traceProfilePath, err)
}
if err := trace.Start(f); err != nil {
_ = f.Close()
return fmt.Errorf("could not start trace profile: %w", err)
}
dm.traceProfile = f
return nil
}
// StopTraceProfile stops execution tracing
func (dm *DiagnosticsManager) StopTraceProfile() {
if dm.traceProfile != nil {
trace.Stop()
if err := dm.traceProfile.Close(); err != nil {
logging.Error().Err(err).Msg("Error closing trace profile file")
}
logging.Info().Msgf("Trace profile written to: %s", dm.traceProfile.Name())
dm.traceProfile = nil
}
}
+74
View File
@@ -0,0 +1,74 @@
package cmd
import (
"time"
"github.com/spf13/cobra"
"github.com/zricethezav/gitleaks/v8/logging"
"github.com/zricethezav/gitleaks/v8/sources"
)
func init() {
rootCmd.AddCommand(directoryCmd)
directoryCmd.Flags().Bool("follow-symlinks", false, "scan files that are symlinks to other files")
}
var directoryCmd = &cobra.Command{
Use: "dir [flags] [path]",
Aliases: []string{"file", "directory"},
Short: "scan directories or files for secrets",
Run: runDirectory,
}
func runDirectory(cmd *cobra.Command, args []string) {
// grab source
source := "."
if len(args) == 1 {
source = args[0]
if source == "" {
source = "."
}
}
initConfig(source)
initDiagnostics()
var err error
// setup config (aka, the thing that defines rules)
cfg := Config(cmd)
// start timer
start := time.Now()
detector := Detector(cmd, cfg, source)
// set follow symlinks flag
if detector.FollowSymlinks, err = cmd.Flags().GetBool("follow-symlinks"); err != nil {
logging.Fatal().Err(err).Send()
}
// set exit code
exitCode, err := cmd.Flags().GetInt("exit-code")
if err != nil {
logging.Fatal().Err(err).Msg("could not get exit code")
}
findings, err := detector.DetectSource(
cmd.Context(),
&sources.Files{
Config: &cfg,
FollowSymlinks: detector.FollowSymlinks,
MaxFileSize: detector.MaxTargetMegaBytes * 1_000_000,
Path: source,
Sema: detector.Sema,
MaxArchiveDepth: detector.MaxArchiveDepth,
},
)
if err != nil {
logging.Error().Err(err).Msg("failed scan directory")
}
findingSummaryAndExit(detector, findings, exitCode, start, err)
}
+121
View File
@@ -0,0 +1,121 @@
package base
import (
"fmt"
"strings"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func CreateGlobalConfig() config.Config {
return config.Config{
Title: "gitleaks config",
Allowlists: []*config.Allowlist{
{
Description: "global allow lists",
Regexes: []*regexp.Regexp{
// ----------- General placeholders -----------
regexp.MustCompile(`(?i)^true|false|null$`),
// Awkward workaround to detect repeated characters.
func() *regexp.Regexp {
var (
letters = "abcdefghijklmnopqrstuvwxyz*."
patterns []string
)
for _, char := range letters {
if char == '*' || char == '.' {
patterns = append(patterns, fmt.Sprintf("\\%c+", char))
} else {
patterns = append(patterns, fmt.Sprintf("%c+", char))
}
}
return regexp.MustCompile("^(?i:" + strings.Join(patterns, "|") + ")$")
}(),
// ----------- Environment Variables -----------
regexp.MustCompile(`^\$(?:\d+|{\d+})$`),
regexp.MustCompile(`^\$(?:[A-Z_]+|[a-z_]+)$`),
regexp.MustCompile(`^\${(?:[A-Z_]+|[a-z_]+)}$`),
// ----------- Interpolated Variables -----------
// Ansible (https://docs.ansible.com/ansible/latest/playbook_guide/playbooks_variables.html)
regexp.MustCompile(`^\{\{[ \t]*[\w ().|]+[ \t]*}}$`),
// GitHub Actions
// https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/store-information-in-variables
// https://docs.github.com/en/actions/security-for-github-actions/security-guides/using-secrets-in-github-actions
regexp.MustCompile(`^\$\{\{[ \t]*(?:(?:env|github|secrets|vars)(?:\.[A-Za-z]\w+)+[\w "'&./=|]*)[ \t]*}}$`),
// NuGet (https://learn.microsoft.com/en-us/nuget/reference/nuget-config-file#using-environment-variables)
regexp.MustCompile(`^%(?:[A-Z_]+|[a-z_]+)%$`),
// String formatting.
regexp.MustCompile(`^%[+\-# 0]?[bcdeEfFgGoOpqstTUvxX]$`), // Golang (https://pkg.go.dev/fmt)
regexp.MustCompile(`^\{\d{0,2}}$`), // Python (https://docs.python.org/3/tutorial/inputoutput.html)
// Urban Code Deploy (https://www.ibm.com/support/pages/replace-token-step-replaces-replacement-values-windows-variables)
regexp.MustCompile(`^@(?:[A-Z_]+|[a-z_]+)@$`),
// ----------- Miscellaneous -----------
// File paths
regexp.MustCompile(`^/Users/(?i)[a-z0-9]+/[\w .-/]+$`), // MacOS
regexp.MustCompile(`^/(?:bin|etc|home|opt|tmp|usr|var)/[\w ./-]+$`), // Linux
// 11980 Jps -Dapplication.home=D:\develop_tools\jdk\jdk1.8.0_131 -Xms8m
//regexp.MustCompile(`^$`), // Windows
},
Paths: []*regexp.Regexp{
regexp.MustCompile(`gitleaks\.toml`),
// ----------- Documents and media -----------
regexp.MustCompile(`(?i)\.(?:bmp|gif|jpe?g|png|svg|tiff?)$`), // Images
regexp.MustCompile(`(?i)\.(?:eot|[ot]tf|woff2?)$`), // Fonts
regexp.MustCompile(`(?i)\.(?:docx?|xlsx?|pdf|bin|socket|vsidx|v2|suo|wsuo|.dll|pdb|exe|gltf)$`),
// ----------- Golang files -----------
regexp.MustCompile(`go\.(?:mod|sum|work(?:\.sum)?)$`),
regexp.MustCompile(`(?:^|/)vendor/modules\.txt$`),
regexp.MustCompile(`(?:^|/)vendor/(?:github\.com|golang\.org/x|google\.golang\.org|gopkg\.in|istio\.io|k8s\.io|sigs\.k8s\.io)(?:/.*)?$`),
// ----------- Java files -----------
// Gradle
regexp.MustCompile(`(?:^|/)gradlew(?:\.bat)?$`),
regexp.MustCompile(`(?:^|/)gradle\.lockfile$`),
regexp.MustCompile(`(?:^|/)mvnw(?:\.cmd)?$`),
regexp.MustCompile(`(?:^|/)\.mvn/wrapper/MavenWrapperDownloader\.java$`),
// ----------- JavaScript files -----------
// Dependencies and lock files.
regexp.MustCompile(`(?:^|/)node_modules(?:/.*)?$`),
regexp.MustCompile(`(?:^|/)(?:deno\.lock|npm-shrinkwrap\.json|package-lock\.json|pnpm-lock\.yaml|yarn\.lock)$`),
regexp.MustCompile(`(?:^|/)bower_components(?:/.*)?$`),
// TODO: Add more common static assets, such as swagger-ui.
regexp.MustCompile(`(?:^|/)(?:angular|bootstrap|jquery(?:-?ui)?|plotly|swagger-?ui)[a-zA-Z0-9.-]*(?:\.min)?\.js(?:\.map)?$`),
regexp.MustCompile(`(?:^|/)javascript\.json$`),
// ----------- Python files -----------
// Dependencies and lock files.
regexp.MustCompile(`(?:^|/)(?:Pipfile|poetry)\.lock$`),
// Virtual environments
regexp.MustCompile(`(?i)(?:^|/)(?:v?env|virtualenv)/lib(?:64)?(?:/.*)?$`),
regexp.MustCompile(`(?i)(?:^|/)(?:lib(?:64)?/python[23](?:\.\d{1,2})+|python/[23](?:\.\d{1,2})+/lib(?:64)?)(?:/.*)?$`),
// dist-info directory (https://py-pkgs.org/04-package-structure.html#building-sdists-and-wheels)
regexp.MustCompile(`(?i)(?:^|/)[a-z0-9_.]+-[0-9.]+\.dist-info(?:/.+)?$`),
// ----------- Ruby files -----------
regexp.MustCompile(`(?:^|/)vendor/(?:bundle|ruby)(?:/.*?)?$`),
regexp.MustCompile(`\.gem$`), // tar archive
// Misc
regexp.MustCompile(`verification-metadata\.xml`),
regexp.MustCompile(`Database.refactorlog`),
// ----------- Git files ------------
regexp.MustCompile(`(?:^|/)\.git$`),
},
StopWords: []string{
"abcdefghijklmnopqrstuvwxyz", // character range
// ----------- Secrets -----------
// Checkmarx client secret. (https://github.com/checkmarx-ts/checkmarx-python-sdk/blob/86560f6e2a3e46d16322101294da10d5d190312d/README.md?plain=1#L56)
"014df517-39d1-4453-b7b3-9930c563627c",
},
},
},
}
}
+203
View File
@@ -0,0 +1,203 @@
package base
import (
"testing"
)
var allowlistRegexTests = map[string]struct {
invalid []string
valid []string
}{
"general placeholders": {
invalid: []string{
`true`, `True`, `false`, `False`, `null`, `NULL`,
},
},
"general placeholders - repeated characters": {
invalid: []string{
`aaaaaaaaaaaaaaaaa`, `BBBBBBBBBBbBBBBBBBbBB`, `********************`,
},
valid: []string{`aaaaaaaaaaaaaaaaaaabaa`, `pas*************d`},
},
"environment variables": {
invalid: []string{`$2`, `$GIT_PASSWORD`, `${GIT_PASSWORD}`, `$password`},
valid: []string{`$yP@R.@=ibxI`, `$2a6WCust9aE`, `${not_complete1`},
},
"interpolated variables - ansible": {
invalid: []string{
`{{ x }}`, `{{ password }}`, `{{password}}`, `{{ data.proxy_password }}`,
`{{ dict1 | ansible.builtin.combine(dict2) }}`,
},
},
"interpolated variables - github actions": {
invalid: []string{
`${{ env.First_Name }}`,
`${{ env.DAY_OF_WEEK == 'Monday' }}`,
`${{env.JAVA_VERSION}}`,
`${{ github.event.issue.title }}`,
`${{ github.repository == "Gattocrucco/lsqfitgp" }}`,
`${{ github.event.pull_request.number || github.ref }}`,
`${{ github.event_name == 'pull_request' && github.event.action == 'unassigned' }}`,
`${{ secrets.SuperSecret }}`,
`${{ vars.JOB_NAME }}`,
`${{ vars.USE_VARIABLES == 'true' }}`,
},
},
"interpolated variables - nuget": {
invalid: []string{
`%MY_PASSWORD%`, `%password%`,
},
},
"interpolated variables - string fmt - golang": {
invalid: []string{
`%b`, `%c`, `%d`, `% d`, `%e`, `%E`, `%f`, `%F`, `%g`, `%G`, `%o`, `%O`, `%p`, `%q`, `%-s`, `%s`, `%t`, `%T`, `%U`, `%#U`, `%+v`, `%#v`, `%v`, `%x`, `%X`,
},
},
"interpolated variables - string fmt - python": {
invalid: []string{
`{}`, `{0}`, `{10}`,
},
},
"interpolated variables - ucd": {
invalid: []string{`@password@`, `@LDAP_PASS@`},
valid: []string{`@username@mastodon.example`},
},
"miscellaneous - file paths": {
invalid: []string{
// MacOS
`/Users/james/Projects/SwiftCode/build/Release`,
// Linux
`/tmp/screen-exchange`,
},
valid: []string{},
},
}
func TestConfigAllowlistRegexes(t *testing.T) {
cfg := CreateGlobalConfig()
allowlists := cfg.Allowlists
for name, cases := range allowlistRegexTests {
t.Run(name, func(t *testing.T) {
for _, c := range cases.invalid {
for _, a := range allowlists {
if !a.RegexAllowed(c) {
t.Errorf("invalid value not marked as allowed: %s", c)
}
}
}
for _, c := range cases.valid {
for _, a := range allowlists {
if a.RegexAllowed(c) {
t.Errorf("valid value marked as allowed: %s", c)
}
}
}
})
}
}
func BenchmarkConfigAllowlistRegexes(b *testing.B) {
cfg := CreateGlobalConfig()
allowlists := cfg.Allowlists
for n := 0; n < b.N; n++ {
for _, cases := range allowlistRegexTests {
for _, c := range cases.invalid {
for _, a := range allowlists {
a.RegexAllowed(c)
}
}
for _, c := range cases.valid {
for _, a := range allowlists {
a.RegexAllowed(c)
}
}
}
}
}
var allowlistPathsTests = map[string]struct {
invalid []string
valid []string
}{
"javascript - common static assets": {
invalid: []string{
`tests/e2e/nuget/wwwroot/lib/bootstrap/dist/js/bootstrap.esm.min.js`,
`src/main/static/lib/angular.1.2.16.min.js`,
`src/main/resources/static/jquery-ui-1.12.1/jquery-ui-min.js`,
`src/main/resources/static/js/jquery-ui-1.10.4.min.js`,
`src-static/js/plotly.min.js`,
`swagger/swaggerui/swagger-ui-bundle.js.map`,
`swagger/swaggerui/swagger-ui-es-bundle.js.map`,
`src/main/static/swagger-ui.min.js`,
`swagger/swaggerui/swagger-ui.js`,
},
},
"python": {
invalid: []string{
// lock files
`Pipfile.lock`, `poetry.lock`,
// virtual environments
"env/lib/python3.7/site-packages/urllib3/util/url.py",
"venv/Lib/site-packages/regex-2018.08.29.dist-info/DESCRIPTION.rst",
"venv/lib64/python3.5/site-packages/pynvml.py",
"python/python3/virtualenv/Lib/site-packages/pyphonetics/utils.py",
"virtualenv/lib64/python3.7/base64.py",
// packages
"cde-root/usr/lib64/python2.4/site-packages/Numeric.pth",
"lib/python3.9/site-packages/setuptools/_distutils/msvccompiler.py",
"lib/python3.8/site-packages/botocore/data/alexaforbusiness/2017-11-09/service-2.json",
"code/python/3.7.4/Lib/site-packages/dask/bytes/tests/test_bytes_utils.py",
"python/3.7.4/Lib/site-packages/fsspec/utils.py",
"python/2.7.16.32/Lib/bsddb/test/test_dbenv.py",
"python/lib/python3.8/site-packages/boto3/data/ec2/2016-04-01/resources-1.json",
// distinfo
"libs/PyX-0.15.dist-info/AUTHORS",
},
},
}
func TestConfigAllowlistPaths(t *testing.T) {
cfg := CreateGlobalConfig()
allowlists := cfg.Allowlists
for name, cases := range allowlistPathsTests {
t.Run(name, func(t *testing.T) {
for _, c := range cases.invalid {
for _, a := range allowlists {
if !a.PathAllowed(c) {
t.Errorf("invalid path not marked as allowed: %s", c)
}
}
}
for _, c := range cases.valid {
for _, a := range allowlists {
if a.PathAllowed(c) {
t.Errorf("valid path marked as allowed: %s", c)
}
}
}
})
}
}
func BenchmarkConfigAllowlistPaths(b *testing.B) {
cfg := CreateGlobalConfig()
allowlists := cfg.Allowlists
for n := 0; n < b.N; n++ {
for _, cases := range allowlistPathsTests {
for _, c := range cases.invalid {
for _, a := range allowlists {
a.PathAllowed(c)
}
}
for _, c := range cases.valid {
for _, a := range allowlists {
a.PathAllowed(c)
}
}
}
}
}
+301
View File
@@ -0,0 +1,301 @@
package main
import (
"os"
"slices"
"text/template"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/base"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/rules"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/logging"
)
const (
templatePath = "rules/config.tmpl"
)
//go:generate go run $GOFILE ../../../config/gitleaks.toml
func main() {
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.OnePasswordSecretKey(),
rules.OnePasswordServiceAccountToken(),
rules.AdafruitAPIKey(),
rules.AdobeClientID(),
rules.AdobeClientSecret(),
rules.AgeSecretKey(),
rules.AirtableApiKey(),
rules.AirtablePersonalAccessToken(),
rules.AlgoliaApiKey(),
rules.AlibabaAccessKey(),
rules.AlibabaSecretKey(),
rules.AmazonBedrockAPIKeyLongLived(),
rules.AmazonBedrockAPIKeyShortLived(),
rules.AnthropicAdminApiKey(),
rules.AnthropicApiKey(),
rules.ArtifactoryApiKey(),
rules.ArtifactoryReferenceToken(),
rules.AsanaClientID(),
rules.AsanaClientSecret(),
rules.Atlassian(),
rules.Authress(),
rules.AWS(),
rules.AzureActiveDirectoryClientSecret(),
rules.BitBucketClientID(),
rules.BitBucketClientSecret(),
rules.BittrexAccessKey(),
rules.BittrexSecretKey(),
rules.Beamer(),
rules.CodecovAccessToken(),
rules.CoinbaseAccessToken(),
rules.ClickHouseCloud(),
rules.Clojars(),
rules.CloudflareAPIKey(),
rules.CloudflareGlobalAPIKey(),
rules.CloudflareOriginCAKey(),
rules.CohereAPIToken(),
rules.ConfluentAccessToken(),
rules.ConfluentSecretKey(),
rules.Contentful(),
rules.CurlHeaderAuth(),
rules.CurlBasicAuth(),
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.FacebookSecret(),
rules.FacebookAccessToken(),
rules.FacebookPageAccessToken(),
rules.FastlyAPIToken(),
rules.FinicityClientSecret(),
rules.FinicityAPIToken(),
rules.FlickrAccessToken(),
rules.FinnhubAccessToken(),
rules.FlutterwavePublicKey(),
rules.FlutterwaveSecretKey(),
rules.FlutterwaveEncKey(),
rules.FlyIOAccessToken(),
rules.FrameIO(),
rules.Freemius(),
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.GitlabCiCdJobToken(),
rules.GitlabDeployToken(),
rules.GitlabFeatureFlagClientToken(),
rules.GitlabFeedToken(),
rules.GitlabIncomingMailToken(),
rules.GitlabKubernetesAgentToken(),
rules.GitlabOauthAppSecret(),
rules.GitlabPat(),
rules.GitlabPatRoutable(),
rules.GitlabPipelineTriggerToken(),
rules.GitlabRunnerRegistrationToken(),
rules.GitlabRunnerAuthenticationToken(),
rules.GitlabRunnerAuthenticationTokenRoutable(),
rules.GitlabScimToken(),
rules.GitlabSessionCookie(),
rules.GitterAccessToken(),
rules.GrafanaApiKey(),
rules.GrafanaCloudApiToken(),
rules.GrafanaServiceAccountToken(),
rules.HarnessApiKey(),
rules.HashiCorpTerraform(),
rules.HashicorpField(),
rules.Heroku(),
rules.HerokuV2(),
rules.HubSpot(),
rules.HuggingFaceAccessToken(),
rules.HuggingFaceOrganizationApiToken(),
rules.Intercom(),
rules.Intra42ClientSecret(),
rules.JFrogAPIKey(),
rules.JFrogIdentityToken(),
rules.JWT(),
rules.JWTBase64(),
rules.KrakenAccessToken(),
rules.KubernetesSecret(),
rules.KucoinAccessToken(),
rules.KucoinSecretKey(),
rules.LaunchDarklyAccessToken(),
rules.LinearAPIToken(),
rules.LinearClientSecret(),
rules.LinkedinClientID(),
rules.LinkedinClientSecret(),
rules.LobAPIToken(),
rules.LobPubAPIToken(),
rules.LookerClientID(),
rules.LookerClientSecret(),
rules.MailChimp(),
rules.MailGunPubAPIToken(),
rules.MailGunPrivateAPIToken(),
rules.MailGunSigningKey(),
rules.MapBox(),
rules.MattermostAccessToken(),
rules.MaxMindLicenseKey(),
rules.Meraki(),
rules.MessageBirdAPIToken(),
rules.MessageBirdClientID(),
rules.NetlifyAccessToken(),
rules.NewRelicUserID(),
rules.NewRelicUserKey(),
rules.NewRelicBrowserAPIKey(),
rules.NewRelicInsertKey(),
rules.Notion(),
rules.NPM(),
rules.NugetConfigPassword(),
rules.NytimesAccessToken(),
rules.OctopusDeployApiKey(),
rules.OktaAccessToken(),
rules.OpenAI(),
rules.OpenshiftUserToken(),
rules.PerplexityAPIKey(),
rules.PlaidAccessID(),
rules.PlaidSecretKey(),
rules.PlaidAccessToken(),
rules.PlanetScalePassword(),
rules.PlanetScaleAPIToken(),
rules.PlanetScaleOAuthToken(),
rules.PostManAPI(),
rules.Prefect(),
rules.PrivateAIToken(),
rules.PrivateKey(),
rules.PrivateKeyPKCS12File(),
rules.PulumiAPIToken(),
rules.PyPiUploadToken(),
rules.RapidAPIAccessToken(),
rules.ReadMe(),
rules.RubyGemsAPIToken(),
rules.ScalingoAPIToken(),
rules.SendbirdAccessID(),
rules.SendbirdAccessToken(),
rules.SendGridAPIToken(),
rules.SendInBlueAPIToken(),
rules.SentryAccessToken(),
rules.SentryOrgToken(),
rules.SentryUserToken(),
rules.SettlemintApplicationAccessToken(),
rules.SettlemintPersonalAccessToken(),
rules.SettlemintServiceAccessToken(),
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.Sonar(),
rules.SourceGraph(),
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, len(configRules))
for _, rule := range configRules {
if err := rule.Validate(); err != nil {
logging.Fatal().Err(err).
Str("rule-id", rule.RuleID).
Msg("Failed to validate rule")
}
// check if rule is in ruleLookUp
if _, ok := ruleLookUp[rule.RuleID]; ok {
logging.Fatal().
Str("rule-id", rule.RuleID).
Msg("rule id is not unique")
}
// TODO: eventually change all the signatures to get ride of this
// nasty dereferencing.
ruleLookUp[rule.RuleID] = *rule
// Slices are de-duplicated with a map, every iteration has a different order.
// This is an awkward workaround.
for _, allowlist := range rule.Allowlists {
slices.Sort(allowlist.Commits)
slices.Sort(allowlist.StopWords)
}
}
tmpl, err := template.ParseFiles(templatePath)
if err != nil {
logging.Fatal().Err(err).Msg("Failed to parse template")
}
f, err := os.Create(gitleaksConfigPath)
if err != nil {
logging.Fatal().Err(err).Msg("Failed to create rules.toml")
}
defer f.Close()
cfg := base.CreateGlobalConfig()
cfg.Rules = ruleLookUp
for _, allowlist := range cfg.Allowlists {
slices.Sort(allowlist.Commits)
slices.Sort(allowlist.StopWords)
}
if err = tmpl.Execute(f, cfg); err != nil {
logging.Fatal().Err(err).Msg("could not execute template")
}
}
+81
View File
@@ -0,0 +1,81 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
// https://developer.1password.com/docs/service-accounts/security/?token-example=encoded
func OnePasswordServiceAccountToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "1password-service-account-token",
Description: "Uncovered a possible 1Password service account token, potentially compromising access to secrets in vaults.",
Regex: regexp.MustCompile(`ops_eyJ[a-zA-Z0-9+/]{250,}={0,3}`),
Entropy: 4,
Keywords: []string{"ops_"},
}
// validate
tps := []string{
utils.GenerateSampleSecret("1password", secrets.NewSecret(`ops_eyJ[a-zA-Z0-9+/]{250,}={0,3}`)),
`### 1Password System Vault Name
export OP_SERVICE_ACCOUNT_TOKEN=ops_eyJzaWduSW5BZGRyZXNzIjoibXkuMXBhc3N3b3JkLmNvbSIsInVzZXJBdXRoIjp7Im1ldGhvZCI6IlNSUGctNDA5NiIsImFsZyI6IlBCRVMyZy1IUzI1NiIsIml0ZXJhdGlvbnMiOjY1MdAwMCwic2FsdCI6InE2dE0tYzNtRDhiNUp2OHh1YVzsUmcifSwiZW1haWwiOiJ5Z3hmcm0zb21oY3NtQDFwYXNzd29yZHNlcnZpY2VhY2NvdW50cy5jb20iLCJzcnBYIjoiM2E5NDdhZmZhMDQ5NTAxZjkxYzk5MGFiY2JiYWRlZjFjMjM5Y2Q3YTMxYmI1MmQyZjUzOTA2Y2UxOTA1OTYwYiIsIm11ayI6eyJhbGciOiJBMjU2R0NNIiwiZXh0Ijp0cnVlLCJrIjoiVVpleERsLVgyUWxpa0VqRjVUUjRoODhOd29ZcHRqSHptQmFTdlNrWGZmZyIsImtleV9vcHMiOlsiZW5jcnlwdCIsImRlY3J5cHQiXSwia3R5Ijoib2N0Iiwia2lkIjoibXAifSwic2VjcmV0S2V5IjoiQTMtNDZGUUVNLUVZS1hTQS1NUU0yUy04U0JSUS01QjZGUC1HS1k2ViIsInRocm90dGxlU2VjcmV0Ijp7InNlZWQiOiJjZmU2ZTU0NGUxZTlmY2NmZjJlYjBhYWZmYTEzNjZlMmE2ZmUwZDVlZGI2ZTUzOTVkZTljZmY0NDY3NDUxOGUxIiwidXVpZCI6IjNVMjRMNVdCNkpFQ0pEQlhJNFZOSTRCUzNRIn0sImRldmljZVV1aWQiOiJqaGVlY3F4cm41YTV6ZzRpMnlkbjRqd3U3dSJ9
`,
`PYTEST_SVC_ACCT_TOKEN=ops_eyJzaWduSW5BZGRyZXNzIjoiemFjaC1hbmQtbGVhbm5lLjFwYXNzd29yZC5jb20iLCJ1c2VyQXV0aCI6eyJtZXRob2QiOiJTUlBnLTQwOTYiLCJhbGciOiJQQkVLMmctSFMyNTYiLCJpdGVyYXRpb25zIjo2NTAwMDAsInNhbHQiOiJlYUZRQmNVemJyTHhnM2d4bHFQLVVBIn0sImVtYWlsIjoiMm9iNGRpeDdiNTdrYUAxcGFzc3dvcmRzZXJ2aWNlYWNjb3VudHMuY29tIiwic3JwWCI6ImVmZDY4YjNhZTkwMmRjZjRiMzEzYjE5MjYwZmY0OGUzMjU2ZDlhOGNkM2JmMmY3YzI2YzU1ZWJkNjZlZGU4NWEiLCJtdWsiOnsiYWxnIjoiQTI1NkdDTSIsImV4dCI6dHJ1ZSwiayI6IlMwaGE0SDhqbEhRblJCWmxvYnBmR1BneERmbS1pRGNkZWY0bFdYU0VSbmMiLCJrZXlfb3BzIjpbImRlY3J5cHQiLCJlbmNyeXB0Il0sImt0eSI6Im9jdCIsImtpZCI6Im1wIn0sInNlY3JldEtleSI6IkEzLUdHOUVRNi1LUzQ0QVctQU5QVkYtUkdQTDktQlNKUTMtR1NHR0giLCJ0aHJvdHRsZVNlY3JldCI6eyJzZWVkIjoiN2I0OTMxMmJiOTlkZTFiNjU5ODZkYzIzOWU4YWNmZWMxMTU0M2E2OGQxYmYwMjZmZTgzMjg3NWYxNmJlOWY2NiIsInV1aWQiOiJDV1RHQ0hMNlNWRkdSTlg0SzNENUJVSDZDSSJ9LCJkZXZpY2VVdWlkIjoiMnFld3JpaGtqbmt1Zmh6ZGdmZ2hnNmM1cGUifQ`,
` "sourceContent": "ops_eyJlbWFpbCI6ImVqd2U2NHFtbHhocmlAMXBhc3N3b3Jkc2VydmljZWFjY291bnRzLmxjbCIsIm11ayI6eyJhbGciOiJBMjU2R0NNIiwiZXh0Ijp0cnVlLCJrIjoiTThWUGZJYzhWRWZUaGNNWExhS0NLRjhzTWg1Sk1ac1BBdHU5MmZRTmItbyIsImtleV9vcHMiOlsiZW5jcnlwdCIsImRlY3J5cHQiXSwia3R5Ijoib2N0Iiwia2lkIjoibXAifSwic2VjcmV0S2V5IjoiQTMtQzRaSk1OLVBRVFpUTC1IR0w4NC1HNjRNNy1LVlpSTi00WlZQNiIsInNycFgiOiI4NzBkNjdhOWU2MjY2MjVkOWUzNjg1MDc4MDRjOWMzMmU2NjFjNTdlN2U1NTg3NzgyOTFiZjI5ZDVhMjc5YWUxIiwic2lnbkluQWRkcmVzcyI6ImdvdGhhbS5iNWxvY2FsLmNvbTo0MDAwIiwidXNlckF1dGgiOnsibWV0aG9kIjoiU1JQZy00MDk2IiwiYWxnIjoiUEJFUzJnLUhTMjU2IiwiaXRlcmF0aW9ucyI6MTAwMDAwLCJzYWx0IjoiRk1SVVBpeXJONFhmXzhIb2g2WVJYUSJ9fQ\n\nops_token is secret.\n",`,
}
fps := []string{
// Invalid
` login:
serviceAccountToken:
fn::secret: ops_eyJzaWduSW5B..[Redacted]`,
`: To start using this service account, run the following command:
:
: export OP_SERVICE_ACCOUNT_TOKEN=ops_eyJzaWduSW5BZGRyZXNzIjoiaHR0cHM6...`,
// Low entropy.
`ops_eyJxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx`,
}
return utils.Validate(r, tps, fps)
}
// Reference:
// - https://1passwordstatic.com/files/security/1password-white-paper.pdf
func OnePasswordSecretKey() *config.Rule {
// 1Password secret keys include several hyphens but these are only for readability
// and are stripped during 1Password login. This means that the following are technically
// the same valid key:
// - A3ASWWYB798JRYLJVD423DC286TVMH43EB
// - A-3-A-S-W-W-Y-B-7-9-8-J-R-Y-L-J-V-D-4-2-3-D-C-2-8-6-T-V-M-H-4-3-E-B
// But in practice, when these keys are added to a vault, exported in an emergency kit, or
// copied, they have hyphens that follow one of two patterns I can find:
// - A3-ASWWYB-798JRY-LJVD4-23DC2-86TVM-H43EB (every key I've generated has this pattern)
// - A3-ASWWYB-798JRYLJVD4-23DC2-86TVM-H43EB (the whitepaper includes this example, which could just be a typo)
// To avoid a complicated regex that checks for every possible situation it's probably best
// to scan for the these two patterns.
r := config.Rule{
Description: "Uncovered a possible 1Password secret key, potentially compromising access to secrets in vaults.",
RuleID: "1password-secret-key",
Regex: regexp.MustCompile(`\bA3-[A-Z0-9]{6}-(?:(?:[A-Z0-9]{11})|(?:[A-Z0-9]{6}-[A-Z0-9]{5}))-[A-Z0-9]{5}-[A-Z0-9]{5}-[A-Z0-9]{5}\b`),
Entropy: 3.8,
Keywords: []string{"A3-"},
}
// validate
tps := utils.GenerateSampleSecrets("1password", secrets.NewSecret(`A3-[A-Z0-9]{6}-[A-Z0-9]{11}-[A-Z0-9]{5}-[A-Z0-9]{5}-[A-Z0-9]{5}`))
tps = append(tps, utils.GenerateSampleSecrets("1password", secrets.NewSecret(`A3-[A-Z0-9]{6}-[A-Z0-9]{6}-[A-Z0-9]{5}-[A-Z0-9]{5}-[A-Z0-9]{5}-[A-Z0-9]{5}`))...)
tps = append(tps,
// from whitepaper
`A3-ASWWYB-798JRYLJVD4-23DC2-86TVM-H43EB`,
`A3-ASWWYB-798JRY-LJVD4-23DC2-86TVM-H43EB`,
)
fps := []string{
// low entropy
`A3-XXXXXX-XXXXXXXXXXX-XXXXX-XXXXX-XXXXX`,
// lowercase
`A3-xXXXXX-XXXXXX-XXXXX-XXXXX-XXXXX-XXXXX`,
}
return utils.Validate(r, tps, fps)
}
+21
View File
@@ -0,0 +1,21 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func AdafruitAPIKey() *config.Rule {
// define rule
r := config.Rule{
Description: "Identified a potential Adafruit API Key, which could lead to unauthorized access to Adafruit services and sensitive data exposure.",
RuleID: "adafruit-api-key",
Regex: utils.GenerateSemiGenericRegex([]string{"adafruit"}, utils.AlphaNumericExtendedShort("32"), true),
Keywords: []string{"adafruit"},
}
// validate
tps := utils.GenerateSampleSecrets("adafruit", secrets.NewSecret(utils.AlphaNumericExtendedShort("32")))
return utils.Validate(r, tps, nil)
}
+39
View File
@@ -0,0 +1,39 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func AdobeClientID() *config.Rule {
// define rule
r := config.Rule{
RuleID: "adobe-client-id",
Description: "Detected a pattern that resembles an Adobe OAuth Web Client ID, posing a risk of compromised Adobe integrations and data breaches.",
Regex: utils.GenerateSemiGenericRegex([]string{"adobe"}, utils.Hex("32"), true),
Entropy: 2,
Keywords: []string{"adobe"},
}
// validate
tps := utils.GenerateSampleSecrets("adobe", secrets.NewSecret(utils.Hex("32")))
return utils.Validate(r, tps, nil)
}
func AdobeClientSecret() *config.Rule {
// define rule
r := config.Rule{
RuleID: "adobe-client-secret",
Description: "Discovered a potential Adobe Client Secret, which, if exposed, could allow unauthorized Adobe service access and data manipulation.",
Regex: utils.GenerateUniqueTokenRegex(`p8e-(?i)[a-z0-9]{32}`, false),
Entropy: 2,
Keywords: []string{"p8e-"},
}
// validate
tps := []string{
"adobeClient := \"p8e-" + secrets.NewSecret(utils.Hex("32")) + "\"",
}
return utils.Validate(r, tps, nil)
}
+21
View File
@@ -0,0 +1,21 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func AgeSecretKey() *config.Rule {
// define rule
r := config.Rule{
Description: "Discovered a potential Age encryption tool secret key, risking data decryption and unauthorized access to sensitive information.",
RuleID: "age-secret-key",
Regex: regexp.MustCompile(`AGE-SECRET-KEY-1[QPZRY9X8GF2TVDW0S3JN54KHCE6MUA7L]{58}`),
Keywords: []string{"AGE-SECRET-KEY-1"},
}
// validate
tps := utils.GenerateSampleSecrets("age", `AGE-SECRET-KEY-1QQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQ`) // gitleaks:allow
return utils.Validate(r, tps, nil)
}
+37
View File
@@ -0,0 +1,37 @@
package rules
import (
"regexp"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func AirtableApiKey() *config.Rule {
// define rule
r := config.Rule{
Description: "Uncovered a possible Airtable API Key, potentially compromising database access and leading to data leakage or alteration.",
RuleID: "airtable-api-key",
Regex: utils.GenerateSemiGenericRegex([]string{"airtable"}, utils.AlphaNumeric("17"), true),
Keywords: []string{"airtable"},
}
// validate
tps := utils.GenerateSampleSecrets("airtable", secrets.NewSecret(utils.AlphaNumeric("17")))
return utils.Validate(r, tps, nil)
}
func AirtablePersonalAccessToken() *config.Rule {
// define rule
r := config.Rule{
Description: "Uncovered a possible Airtable Personal AccessToken, potentially compromising database access and leading to data leakage or alteration.",
RuleID: "airtable-personnal-access-token",
Regex: regexp.MustCompile(`\b(pat[[:alnum:]]{14}\.[a-f0-9]{64})\b`),
Keywords: []string{"airtable"},
}
// validate
tps := utils.GenerateSampleSecrets("airtable", "pat"+secrets.NewSecret(utils.AlphaNumeric("14")+"\\."+utils.Hex("64")))
return utils.Validate(r, tps, nil)
}
+21
View File
@@ -0,0 +1,21 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func AlgoliaApiKey() *config.Rule {
// define rule
r := config.Rule{
Description: "Identified an Algolia API Key, which could result in unauthorized search operations and data exposure on Algolia-managed platforms.",
RuleID: "algolia-api-key",
Regex: utils.GenerateSemiGenericRegex([]string{"algolia"}, `[a-z0-9]{32}`, true),
Keywords: []string{"algolia"},
}
// validate
tps := utils.GenerateSampleSecrets("algolia", secrets.NewSecret(utils.Hex("32")))
return utils.Validate(r, tps, nil)
}
+40
View File
@@ -0,0 +1,40 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func AlibabaAccessKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "alibaba-access-key-id",
Description: "Detected an Alibaba Cloud AccessKey ID, posing a risk of unauthorized cloud resource access and potential data compromise.",
Regex: utils.GenerateUniqueTokenRegex(`LTAI(?i)[a-z0-9]{20}`, false),
Entropy: 2,
Keywords: []string{"LTAI"},
}
// validate
tps := []string{
"alibabaKey := \"LTAI" + secrets.NewSecret(utils.Hex("20")) + "\"",
}
return utils.Validate(r, tps, nil)
}
// TODO
func AlibabaSecretKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "alibaba-secret-key",
Description: "Discovered a potential Alibaba Cloud Secret Key, potentially allowing unauthorized operations and data access within Alibaba Cloud.",
Regex: utils.GenerateSemiGenericRegex([]string{"alibaba"}, utils.AlphaNumeric("30"), true),
Entropy: 2,
Keywords: []string{"alibaba"},
}
// validate
tps := utils.GenerateSampleSecrets("alibaba", secrets.NewSecret(utils.AlphaNumeric("30")))
return utils.Validate(r, tps, nil)
}
+69
View File
@@ -0,0 +1,69 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func AnthropicApiKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "anthropic-api-key",
Description: "Identified an Anthropic API Key, which may compromise AI assistant integrations and expose sensitive data to unauthorized access.",
Regex: utils.GenerateUniqueTokenRegex(`sk-ant-api03-[a-zA-Z0-9_\-]{93}AA`, false),
Keywords: []string{
"sk-ant-api03",
},
}
// validate
tps := []string{
// Valid API key example
"sk-ant-api03-abc123xyz-456def789ghij-klmnopqrstuvwx-3456yza789bcde-1234fghijklmnopby56aaaogaopaaaabc123xyzAA",
// Generate additional random test keys
utils.GenerateSampleSecret("anthropic", "sk-ant-api03-"+secrets.NewSecret(utils.AlphaNumericExtendedShort("93"))+"AA"),
}
fps := []string{
// Too short key (missing characters)
"sk-ant-api03-abc123xyz-456de-klMnopqrstuvwx-3456yza789bcde-1234fghijklmnopAA",
// Wrong suffix
"sk-ant-api03-abc123xyz-456def789ghij-klmnopqrstuvwx-3456yza789bcde-1234fghijklmnopby56aaaogaopaaaabc123xyzBB",
// Wrong prefix (admin key, not API key)
"sk-ant-admin01-abc123xyz-456def789ghij-klmnopqrstuvwx-3456yza789bcde-1234fghijklmnopby56aaaogaopaaaabc123xyzAA",
}
return utils.Validate(r, tps, fps)
}
func AnthropicAdminApiKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "anthropic-admin-api-key",
Description: "Detected an Anthropic Admin API Key, risking unauthorized access to administrative functions and sensitive AI model configurations.",
Regex: utils.GenerateUniqueTokenRegex(`sk-ant-admin01-[a-zA-Z0-9_\-]{93}AA`, false),
Keywords: []string{
"sk-ant-admin01",
},
}
// validate
tps := []string{
// Valid admin key example
"sk-ant-admin01-abc12fake-456def789ghij-klmnopqrstuvwx-3456yza789bcde-12fakehijklmnopby56aaaogaopaaaabc123xyzAA",
// Generate additional random test keys
utils.GenerateSampleSecret("anthropic", "sk-ant-admin01-"+secrets.NewSecret(utils.AlphaNumericExtendedShort("93"))+"AA"),
}
fps := []string{
// Too short key (missing characters)
"sk-ant-admin01-abc123xyz-456de-klMnopqrstuvwx-3456yza789bcde-1234fghijklmnopAA",
// Wrong suffix
"sk-ant-admin01-abc123xyz-456def789ghij-klmnopqrstuvwx-3456yza789bcde-1234fghijklmnopby56aaaogaopaaaabc123xyzBB",
// Wrong prefix (API key, not admin key)
"sk-ant-api03-abc123xyz-456def789ghij-klmnopqrstuvwx-3456yza789bcde-1234fghijklmnopby56aaaogaopaaaabc123xyzAA",
}
return utils.Validate(r, tps, fps)
}
+58
View File
@@ -0,0 +1,58 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func ArtifactoryApiKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "artifactory-api-key",
Description: "Detected an Artifactory api key, posing a risk unauthorized access to the central repository.",
Regex: regexp.MustCompile(`\bAKCp[A-Za-z0-9]{69}\b`),
Entropy: 4.5,
Keywords: []string{"AKCp"},
}
// validate
tps := []string{
"artifactoryApiKey := \"AKCp" + secrets.NewSecret(utils.AlphaNumeric("69")) + "\"",
}
// false positives
fps := []string{
`lowEntropy := AKCpXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX`,
"wrongStart := \"AkCp" + secrets.NewSecret(utils.AlphaNumeric("69")) + "\"",
"wrongLength := \"AkCp" + secrets.NewSecret(utils.AlphaNumeric("59")) + "\"",
"partOfAlongUnrelatedBlob gYnkgAkCp" + secrets.NewSecret(utils.AlphaNumeric("69")) + "VyZSB2",
}
return utils.Validate(r, tps, fps)
}
func ArtifactoryReferenceToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "artifactory-reference-token",
Description: "Detected an Artifactory reference token, posing a risk of impersonation and unauthorized access to the central repository.",
Regex: regexp.MustCompile(`\bcmVmd[A-Za-z0-9]{59}\b`),
Entropy: 4.5,
Keywords: []string{"cmVmd"},
}
// validate
tps := []string{
"artifactoryRefToken := \"cmVmd" + secrets.NewSecret(utils.AlphaNumeric("59")) + "\"",
}
// false positives
fps := []string{
`lowEntropy := cmVmdXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX`,
"wrongStart := \"cmVMd" + secrets.NewSecret(utils.AlphaNumeric("59")) + "\"",
"wrongLength := \"cmVmd" + secrets.NewSecret(utils.AlphaNumeric("49")) + "\"",
"partOfAlongUnrelatedBlob gYnkgcmVmd" + secrets.NewSecret(utils.AlphaNumeric("59")) + "VyZSB2",
}
return utils.Validate(r, tps, fps)
}
+36
View File
@@ -0,0 +1,36 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func AsanaClientID() *config.Rule {
// define rule
r := config.Rule{
Description: "Discovered a potential Asana Client ID, risking unauthorized access to Asana projects and sensitive task information.",
RuleID: "asana-client-id",
Regex: utils.GenerateSemiGenericRegex([]string{"asana"}, utils.Numeric("16"), true),
Keywords: []string{"asana"},
}
// validate
tps := utils.GenerateSampleSecrets("asana", secrets.NewSecret(utils.Numeric("16")))
return utils.Validate(r, tps, nil)
}
func AsanaClientSecret() *config.Rule {
// define rule
r := config.Rule{
Description: "Identified an Asana Client Secret, which could lead to compromised project management integrity and unauthorized access.",
RuleID: "asana-client-secret",
Regex: utils.GenerateSemiGenericRegex([]string{"asana"}, utils.AlphaNumeric("32"), true),
Keywords: []string{"asana"},
}
// validate
tps := utils.GenerateSampleSecrets("asana", secrets.NewSecret(utils.AlphaNumeric("32")))
return utils.Validate(r, tps, nil)
}
+36
View File
@@ -0,0 +1,36 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func Atlassian() *config.Rule {
// define rule
r := config.Rule{
Description: "Detected an Atlassian API token, posing a threat to project management and collaboration tool security and data confidentiality.",
RuleID: "atlassian-api-token",
Regex: utils.MergeRegexps(
utils.GenerateSemiGenericRegex(
[]string{"(?-i:ATLASSIAN|[Aa]tlassian)", "(?-i:CONFLUENCE|[Cc]onfluence)", "(?-i:JIRA|[Jj]ira)"},
`[a-z0-9]{20}[a-f0-9]{4}`, // The last 4 characters are an MD5 hash.
true,
),
utils.GenerateUniqueTokenRegex(`ATATT3[A-Za-z0-9_\-=]{186}`, false),
),
Entropy: 3.5,
Keywords: []string{"atlassian", "confluence", "jira", "atatt3"},
}
// validate
tps := utils.GenerateSampleSecrets("atlassian", secrets.NewSecret(utils.AlphaNumeric("20")+"[a-f0-9]{4}"))
tps = append(tps, utils.GenerateSampleSecrets("confluence", secrets.NewSecret(utils.AlphaNumeric("20")+"[a-f0-9]{4}"))...)
tps = append(tps, utils.GenerateSampleSecrets("jira", secrets.NewSecret(utils.AlphaNumeric("20")+"[a-f0-9]{4}"))...)
tps = append(tps, `JIRA_API_TOKEN=HXe8DGg1iJd2AopzyxkFB7F2`)
tps = append(tps, utils.GenerateSampleSecrets("jira", "ATATT3xFfGF0K3irG5tKKi-6u-wwaXQFeGwZ-IHR-hQ3CulkKtMSuteRQFfLZ6jihHThzZCg_UjnDt-4Wl_gIRf4zrZJs5JqaeuBhsfJ4W5GD6yGg3W7903gbvaxZPBjxIQQ7BgFDSkPS8oPispw4KLz56mdK-G6CIvLO6hHRrZHY0Q3tvJ6JxE=C63992E6")...)
fps := []string{"getPagesInConfluenceSpace,searchConfluenceUsingCql"}
return utils.Validate(r, tps, fps)
}
+31
View File
@@ -0,0 +1,31 @@
package rules
import (
"fmt"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func Authress() *config.Rule {
// Rule Definition
// (Note: When changes are made to this, rerun `go generate ./...` and commit the config/gitleaks.toml file
r := config.Rule{
RuleID: "authress-service-client-access-key",
Description: "Uncovered a possible Authress Service Client Access Key, which may compromise access control services and sensitive data.",
Regex: utils.GenerateUniqueTokenRegex(`(?:sc|ext|scauth|authress)_(?i)[a-z0-9]{5,30}\.[a-z0-9]{4,6}\.(?-i:acc)[_-][a-z0-9-]{10,32}\.[a-z0-9+/_=-]{30,120}`, false),
Entropy: 2,
Keywords: []string{"sc_", "ext_", "scauth_", "authress_"},
}
// validate
// https://authress.io/knowledge-base/docs/authorization/service-clients/secrets-scanning/#1-detection
service_client_id := "sc_" + utils.AlphaNumeric("10")
access_key_id := utils.AlphaNumeric("4")
account_id := "acc_" + utils.AlphaNumeric("10")
signature_key := utils.AlphaNumericExtendedShort("40")
tps := utils.GenerateSampleSecrets("authress", secrets.NewSecret(fmt.Sprintf(`%s\.%s\.%s\.%s`, service_client_id, access_key_id, account_id, signature_key)))
return utils.Validate(r, tps, nil)
}
+109
View File
@@ -0,0 +1,109 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func AWS() *config.Rule {
// define rule
r := config.Rule{
RuleID: "aws-access-token",
Description: "Identified a pattern that may indicate AWS credentials, risking unauthorized cloud resource access and data breaches on AWS platforms.",
Regex: regexp.MustCompile(`\b((?:A3T[A-Z0-9]|AKIA|ASIA|ABIA|ACCA)[A-Z2-7]{16})\b`),
Entropy: 3,
Keywords: []string{
// https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_identifiers.html#identifiers-unique-ids
"A3T", // todo: might not be a valid AWS token
"AKIA", // Access key
"ASIA", // Temporary (AWS STS) access key
"ABIA", // AWS STS service bearer token
"ACCA", // Context-specific credential
},
Allowlists: []*config.Allowlist{
{
Regexes: []*regexp.Regexp{
regexp.MustCompile(`.+EXAMPLE$`),
},
},
},
}
// validate
tps := utils.GenerateSampleSecrets("AWS", "AKIALALEMEL33243OLIB") // gitleaks:allow
// current AWS tokens cannot contain [0,1,8,9], so their entropy is slightly lower than expected.
tps = append(tps, utils.GenerateSampleSecrets("AWS", "AKIA"+secrets.NewSecret("[A-Z2-7]{16}"))...)
tps = append(tps, utils.GenerateSampleSecrets("AWS", "ASIA"+secrets.NewSecret("[A-Z2-7]{16}"))...)
tps = append(tps, utils.GenerateSampleSecrets("AWS", "ABIA"+secrets.NewSecret("[A-Z2-7]{16}"))...)
tps = append(tps, utils.GenerateSampleSecrets("AWS", "ACCA"+secrets.NewSecret("[A-Z2-7]{16}"))...)
fps := []string{
`key = AKIAXXXXXXXXXXXXXXXX`, // Low entropy
`aws_access_key: AKIAIOSFODNN7EXAMPLE`, // Placeholder
`msgstr "Näytä asiakirjamallikansio."`, // Lowercase
`TODAYINASIAASACKOFRICEFELLOVER`, // wrong length
`CTTCATAGGGTTCACGCTGTGTAAT-ACG--CCTGAGGC-CACA-AGGGGACTTCAGCAACCGTCGGG-GATTC-ATTGCCA-A--TGGAAGCAATC-TA-TGGGTTA-TCGCGGAGTCCGCAAAGACGGCCAGTATG-AAGCAGATTTCGCAC-CAATGTGACTGCATTTCGTG-ATCGGGGTAAGTA-TC-GCCGATTC-GC--CCGTCCA-AGT-CGAAG-TA--GGCAATATAAAGCTGC-CATTGCCGAAGCTATCTCGCTA-TACTTGAT-AATCGGCGG-TAG-CACAG-GTCGCAGTATCG-AC-T--AGG-CCTCTCAAAAGTT-GGGTCCCGGCCTCTGGGAAAAACACCTCT-A-AGCGTCAATCAGCTCGGTTTCGCATATTA-TGATATCCCCCGTTGACCAATTGA--TAGTACCCGAGCTTACCGTCGG-ATTCTGGAGTCTT-ATGAGGTTACCGACGA-CGCAGTACCATAAGT-GCGCAATTTGACTGTTCCCGTCGAGTAACCA-AGCTTTGCTCA-CCGGGATGCGCGCCGATGTGACCAGGGGGCGCATGTTACATTGAC-A-GCTGGATCATGTTATGAC-GTGGGTC-ATGCTAAAAGCCTAAAGGACGGT-GCATTAGTAT-TACCGGGACCTCATATCAATGCGCTCGCTAGTTCCTCTTCTCTTGATAACGTATATGCGTCAGGCGCCCGTCCGCCTCCAATACGTG-ACAACGTC-AGTACTGAGCCTC--AA-ACATCGTCTTGTTCG-CC-TACAAAGGATCGGTAGAAAACTCAATATTCGGGTATAAGGTCGTAGGAAGTGTGTCGCCCAGGGCCG-CTAGA-AGCGCACACAAGCG-CTCCTGTCAAGGAGTTG-GTGAAAA-ATGAAC--GACT-ATTGCGTCAC--CTACCTCT-AAGTTTTT-GACAATTTCATGGACGAATTGA-AGCGTCCACAAGCATCTGCCGTAGATATGCGGTAGGTTTTTACATATG-TCACTGCAGAGTCACGGACA-CACATCGCTGTCAAAATGCTCGTACCTAGT-GT-TTGCGATCCCCC-GCGGCATTA-TCTTTTGAACCCTCGTCCCTGTGG-CTCTGATGATTGAG-GTCTGTA-TTCCCTCGTTGTGGGGGGATTGGACCTT-TGTATAGGTTCTTTAACCG-ATGGGGGGCCG--ATCGA-A-TA-TGCTCCTGTTTGCCCCGAACCTT-ACCTCGG-TCCAGACA-CTAAGAAAAACCCC-C-ACTGTAAGGTGCTGAGCCTTTGGATAGCC-CGCGAATGAT-CC-TAGTTGACAA-CTGAACGCGCTCGAACA-TGCCC-GCCCTCTGA--CTGCTGTCTG-GCACCTTTAGACACGCGTCGAC-CATATATT-AGCGCTGTCTGTGG-AGGT-TGTGTCTTGTTGCTCA-CT-CATTATCTGT-AACTGGCTCC-CTC-CCAT-TGGCGTCTTTACACCAACCGCTAGGTTACAGTGCA-TCTAGCGCCTATTATCAGGGCGT-TTGCAGCGGCGCGGTGGCTATGT-GTTAGACATATC-CTTACACTGTATGCTAG-AGCAAGCCAC-TCTGAATGGGTTGC-CGATGAATGA-TCTTGATC-GAGCTCGCA-AC---TACATGGAGTCCGAAGTGAACCTACGGATGATCGTATTCCAACACGAGGATC-TATACGTATAGG-A-GGCG-TAATCCACAATTTAGTAACTCTTGACGC---GGATGAAAAT-GTCGTTACACCTTCCAGAGGCTCGG-GTATATATATGACCT--TGTGATTGAGGACGATCTAGAATAA-CT-GT-G-CT-AAAGTACAGTAGTTTCTATGT-GGTAGGTGGAGAATACAGAGTAG-ATGATTC-GTGGGCCACA-C--T-ACTTTCAT-TAGAGCAGAGA-C-GTGAGTGAGTTTTACACTAGCCAGATGGACCG-GTGA-AGTCTAACAGCCACCGCTT-GTGAGGTCGTTTCCCAGTC-ACCCTACTACAGGCAAAAACTCAGTGT-CC-GTGA-GTGCGTTAGTGATATTCCCTAACGGTTAGGTAACT-CATGAATTCA-AT-TAAGCGTGTCC-CGGT-CACGCCCCCATGGGGGCCTTCTTGGGAGG--AGCATCTTAT--AT-GCTCACGTGGTT-GATAGG-A-T-AATACACTTTTAGTCAGTCCATCAATAAC-AAAGGAAC---CAGGTGGTCGCAGATA-TCCCGCTGATATAGCACTGTGTAAACTCAGGTGATA-CTAAGC--GCTCTAAT-ACG-CTTAATGGCAATGCCCAGTTC--ACGACTAGCTTATGAGGCCCAGCTATGGACTGCGGC-GGCATGTCGGC-GATGGTTGCCCTCGCCCTAAATTATGTACGA-T-ACCGCCT-CTTGTTCT-CCGCCCATAGGGT-C--AGCAGGCGATAGACTCCCAGAAATTTCCTCGTCGT-CCGAATAAGACTAACACGACTA-TT-CCTCTAC-GT-G-AA-CTTATCA-CAAATG-GCT-TACC-TAGGTGGTGGCAGATCACTTTCCGGTG-TATTACGAATTGACGCATACCGAC-A-CGC-GCTTGTTGGATAATCGACTCTAACCTCCTCTCTGGCACATGT-GCTGGATTACCTC-TATTTT-TCTCGCTTAG--GGAACG-T-CCTCTGTCGCGTGAG-GTACGTTTCACGGGAG-CGGCTTGTTCATGCCACGTCCATTATCGA-AGTG-C-GTAAGG-A-GAGCCCTA--GACTCTACACGGAAA-TC-AAC-GTAGAAGGCTC-A-CT`,
}
return utils.Validate(r, tps, fps)
}
func AmazonBedrockAPIKeyLongLived() *config.Rule {
// https://docs.aws.amazon.com/bedrock/latest/userguide/api-keys-how.html
// https://medium.com/@adan.alvarez/api-keys-for-bedrock-a-brief-security-overview-2133ed9a2b3f
r := config.Rule{
RuleID: "aws-amazon-bedrock-api-key-long-lived",
Description: "Identified a pattern that may indicate long-lived Amazon Bedrock API keys, risking unauthorized Amazon Bedrock usage",
Regex: utils.GenerateUniqueTokenRegex(`ABSK[A-Za-z0-9+/]{109,269}={0,2}`, false),
Entropy: 3,
Keywords: []string{
"ABSK", // Amazon Bedrock API Key (long-lived)
},
}
// validate
tps := []string{
// Valid API key example
"ABSKQmVkcm9ja0FQSUtleS1EXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXM=",
// Generate additional random test keys
utils.GenerateSampleSecret("bedrock", "ABSKQmVkcm9ja0FQSUtleS1"+secrets.NewSecret(utils.AlphaNumeric("108"))+"="),
utils.GenerateSampleSecret("bedrock", "ABSKQmVkcm9ja0FQSUtleS1"+secrets.NewSecret(utils.AlphaNumeric("246"))),
}
fps := []string{
// Too short key (missing characters)
"ABSKQmVkcm9ja0FQSUtleS1EXAMPLE",
// Too long
"ABSKQmVkcm9ja0FQSUtleS1EXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLE=",
// Wrong prefix
"AXSKQmVkcm9ja0FQSUtleS1EXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXAMPLEEXM=",
}
return utils.Validate(r, tps, fps)
}
func AmazonBedrockAPIKeyShortLived() *config.Rule {
// https://docs.aws.amazon.com/bedrock/latest/userguide/api-keys-how.html
// https://github.com/aws/aws-bedrock-token-generator-js/blob/86277e1489354192c64ffc8f995601daacc1f715/src/token.ts#L21
r := config.Rule{
RuleID: "aws-amazon-bedrock-api-key-short-lived",
Description: "Identified a pattern that may indicate short-lived Amazon Bedrock API keys, risking unauthorized Amazon Bedrock usage",
Regex: regexp.MustCompile(`bedrock-api-key-YmVkcm9jay5hbWF6b25hd3MuY29t`),
Entropy: 3,
Keywords: []string{
"bedrock-api-key-", // Amazon Bedrock API Key (short lived)
},
}
// validate
tps := utils.GenerateSampleSecrets("AmazonBedrockAPIKeyShortLived", `bedrock-api-key-YmVkcm9jay5hbWF6b25hd3MuY29t`)
fps := []string{
// Too short key (missing characters)
"bedrock-api-key-",
// Wrong prefix
"bedrock-api-key-YmVkcm9jay5hbWF6b25hd3MuY29x",
}
return utils.Validate(r, tps, fps)
}
+65
View File
@@ -0,0 +1,65 @@
package rules
import (
"fmt"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
// References:
// - https://learn.microsoft.com/en-us/microsoft-365/compliance/sit-defn-azure-ad-client-secret
// - https://learn.microsoft.com/en-us/azure/active-directory/develop/quickstart-register-app#add-credentials
func AzureActiveDirectoryClientSecret() *config.Rule {
// define rule
r := config.Rule{
RuleID: "azure-ad-client-secret",
Description: "Azure AD Client Secret",
// After inspecting dozens of secrets, I'm fairly confident that they start with `xxx\dQ~`.
// However, this may not be (entirely) true, and this rule might need to be further refined in the future.
// Furthermore, it's possible that secrets have a checksum that could be used to further constrain this pattern.
Regex: regexp.MustCompile(`(?:^|[\\'"\x60\s>=:(,)])([a-zA-Z0-9_~.]{3}\dQ~[a-zA-Z0-9_~.-]{31,34})(?:$|[\\'"\x60\s<),])`), // wtf, Go? https://github.com/golang/go/issues/18221
Entropy: 3,
Keywords: []string{
"Q~",
},
}
// validate
tps := []string{
`client_secret=bP88Q~rcBcYjzzOhg1Hnn76Wm3jGgakZiZ.8vMgR`, // gitleaks:allow
`client_secret=bP88Q~rcBcYjzzOhg1Hnn76Wm3jGgakZiZ.8vMgR
`, // gitleaks:allow
`client_secret: .IQ8Q~79R7TOWOspFnWcEG-dYt4KXqFqxK16cxr`, // gitleaks:allow
`AUTH_CLIENTSECRET = _V28Q~IC8qxmlWNpHuDm34JlbKv9LXV5MvUR3a-P`, // gitleaks:allow
`<value xsi:type="xsd:string">~Gg8Q~nVhlLi2vpg_nXBGqFsbGK-t~Hus1JmTa0y</value>`, // gitleaks:allow
`"CLIENT_SECRET": "YYz7Q~Sudoqwap1PnzEBA3zqBK~i5uesDIv.C"`, // gitleaks:allow
`Set-PSUAuthenticationMethod -Type 'OpenIDConnect' -CallbackPath '/auth/oidc' -ClientId 'fake' -ClientSecret '2Vq7Q~q5VgKljZ7cb3.0sp0Apz.vOjRIPyeTr'`, // gitleaks:allow
`client-secret: "t028Q~-aLbmQuinnZtzbgtlEAYstnBWEmGPAoBm"`, // gitleaks:allow
`"cas.authn.azure-active-directory.client-secret=qHF8Q~PCM5HhMoyTFc5TYEomnzR6Kim9UJhe8a.P",`, // gitleaks:allow
`"line": "client_srt = \"qpF8Q~PCM5MhMoyTFc5TYEomnYRUKim9UJhe8a2P\";",`, // gitleaks:allow
`"client_secret": acctest.Representation{RepType: acctest.Required, Create: 'dO29Q~F5-VwnW.lZdd11xFF_t5NAXCaGwDl9NbT1'},`, // gitleaks:allow
`Example= GN.7Q~4AkLZBNEbz4Jxlm~O5G6SsyFxYg6zMR`, // gitleaks:allow
`"the_value": "QtT8Q~9C-_Ij~RouHVpD2Tuf3oHWGh.DQ3kcjbAn"`, // gitleaks:allow
`QtT8Q~9C-_Ij~RouHVpD2Tuf3oHWGh.DQ3kcjbAn`, // gitleaks:allow
`(use the client secret: QtT8Q~9C-_Ij~RouHVpD2Tuf3oHWGh.DQ3kcjbAn)`, // gitleaks:allow
`(QtT8Q~9C-_Ij~RouHVpD2Tuf3oHWGh.DQ3kcjbAn)`, // gitleaks:allow
`\"pass\": \"` + fmt.Sprintf("%s%sQ~%s", secrets.NewSecret(`[\w~.]{3}`), secrets.NewSecret(utils.Numeric("1")), secrets.NewSecret(`[\w~.-]{31,34}`)),
}
fps := []string{
`![图源:《深入拆解Tomcat & Jetty》](https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/6a9e704af49b4380bb686f0c96d33b81~tplv-k3u1fbpfcp-watermark.image)`,
`~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~`,
`~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~`,
`.ui.visible.right.sidebar~.ui.visible.left.sidebar~.pusher{transform:translate3d(0,0,0)}`,
`buf.WriteString("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n\n::\n\n")`,
`'url': 'http://www.2doc.nl/speel~VARA_101375237~mh17-het-verdriet-van-nederland~.html',`,
`@ar = split("~", "965f1453~47~09414c93e4cef985416f472549220827da3ba6fed8ad28e29ef6ad170ad53a69051e9b06f439ef6da5df8670181f7eb2481650");`,
`'#!/registries/5/portainer.demo~2Fportainerregistrytesting~2Falpine',`,
`// CloudFront-Signature: Ixn4bF1LLrLcB8XG-t5bZbIB0vfwSF2s4gkef~PcNBdx73MVvZD3v8DZ5GzcqNrybMiqdYJY5KqK6vTsf5JXDgwFFz-h98wdsbV-izcuonPdzMHp4Ay4qyXM6Ed5jB9dUWYGwMkA6rsWXpftfX8xmk4tG1LwFuJV6nAsx4cfpuKwo4vU2Hyr2-fkA7MZG8AHkpDdVUnjm1q-Re9HdG0nCq-2lnBAdOchBpJt37narOj-Zg6cbx~6rzQLVQd8XIv-Bn7VTc1tkBAJVtGOHb0Q~PLzSRmtNGYTnpL0z~gp3tq8lhZc2HuvJW5-tZaYP9yufeIzk5bqsT6DT4iDuclKKw__, , , false`,
`+ "<Trust Comment=\"\" Identity=\"USK@u2vn3Lh6Kte2-TgBSNKorbsKkuAt34ckoLmgx0ndXO0,4~q8Q~3wIHjX9DT0yCNfQmr9oxmYrDZoQVLOdNg~yk0,AQACAAE/WebOfTrustRC2/2\" Value=\"100\"/>"`,
`client_secret=bP88Q~xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx`,
}
return utils.Validate(r, tps, fps)
}
+25
View File
@@ -0,0 +1,25 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func Beamer() *config.Rule {
// define rule
r := config.Rule{
Description: "Detected a Beamer API token, potentially compromising content management and exposing sensitive notifications and updates.",
RuleID: "beamer-api-token",
Regex: utils.GenerateSemiGenericRegex([]string{"beamer"},
`b_[a-z0-9=_\-]{44}`, true),
Keywords: []string{"beamer"},
}
// validate
tps := utils.GenerateSampleSecrets("beamer", "b_"+secrets.NewSecret(utils.AlphaNumericExtended("44")))
fps := []string{
`│   ├── R21A-A-V010SP13RC181024R16900-CN-B_250K-Release-OTA-97B6C6C59241976086FABDC41472150C.bfu`,
}
return utils.Validate(r, tps, fps)
}
+36
View File
@@ -0,0 +1,36 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func BitBucketClientID() *config.Rule {
// define rule
r := config.Rule{
Description: "Discovered a potential Bitbucket Client ID, risking unauthorized repository access and potential codebase exposure.",
RuleID: "bitbucket-client-id",
Regex: utils.GenerateSemiGenericRegex([]string{"bitbucket"}, utils.AlphaNumeric("32"), true),
Keywords: []string{"bitbucket"},
}
// validate
tps := utils.GenerateSampleSecrets("bitbucket", secrets.NewSecret(utils.AlphaNumeric("32")))
return utils.Validate(r, tps, nil)
}
func BitBucketClientSecret() *config.Rule {
// define rule
r := config.Rule{
Description: "Discovered a potential Bitbucket Client Secret, posing a risk of compromised code repositories and unauthorized access.",
RuleID: "bitbucket-client-secret",
Regex: utils.GenerateSemiGenericRegex([]string{"bitbucket"}, utils.AlphaNumericExtended("64"), true),
Keywords: []string{"bitbucket"},
}
// validate
tps := utils.GenerateSampleSecrets("bitbucket", secrets.NewSecret(utils.AlphaNumeric("64")))
return utils.Validate(r, tps, nil)
}
+36
View File
@@ -0,0 +1,36 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func BittrexAccessKey() *config.Rule {
// define rule
r := config.Rule{
Description: "Identified a Bittrex Access Key, which could lead to unauthorized access to cryptocurrency trading accounts and financial loss.",
RuleID: "bittrex-access-key",
Regex: utils.GenerateSemiGenericRegex([]string{"bittrex"}, utils.AlphaNumeric("32"), true),
Keywords: []string{"bittrex"},
}
// validate
tps := utils.GenerateSampleSecrets("bittrex", secrets.NewSecret(utils.AlphaNumeric("32")))
return utils.Validate(r, tps, nil)
}
func BittrexSecretKey() *config.Rule {
// define rule
r := config.Rule{
Description: "Detected a Bittrex Secret Key, potentially compromising cryptocurrency transactions and financial security.",
RuleID: "bittrex-secret-key",
Regex: utils.GenerateSemiGenericRegex([]string{"bittrex"}, utils.AlphaNumeric("32"), true),
Keywords: []string{"bittrex"},
}
// validate
tps := utils.GenerateSampleSecrets("bittrex", secrets.NewSecret(utils.AlphaNumeric("32")))
return utils.Validate(r, tps, nil)
}
+30
View File
@@ -0,0 +1,30 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func ClickHouseCloud() *config.Rule {
// define rule
r := config.Rule{
RuleID: "clickhouse-cloud-api-secret-key",
Description: "Identified a pattern that may indicate clickhouse cloud API secret key, risking unauthorized clickhouse cloud api access and data breaches on ClickHouse Cloud platforms.",
Regex: regexp.MustCompile(`\b(4b1d[A-Za-z0-9]{38})\b`),
Entropy: 3,
Keywords: []string{
"4b1d", // Prefix
},
}
// validate
tps := utils.GenerateSampleSecrets("ClickHouse", "4b1dbRdW3rOcB7xLthrM4BTBGK1qPLkHigpN1bXD6z")
tps = append(tps, utils.GenerateSampleSecrets("ClickHouse", "4b1d"+secrets.NewSecret("[A-Za-z0-9]{38}"))...)
fps := []string{
`key = 4b1dXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX`, // Low entropy
`key = adf4b1dbRdW3rOcB7xLthrM4BTBGK1qPLkHigpN1bXD6z`, // Not start of a word
}
return utils.Validate(r, tps, fps)
}
+23
View File
@@ -0,0 +1,23 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func Clojars() *config.Rule {
// define rule
r := config.Rule{
RuleID: "clojars-api-token",
Description: "Uncovered a possible Clojars API token, risking unauthorized access to Clojure libraries and potential code manipulation.",
Regex: regexp.MustCompile(`(?i)CLOJARS_[a-z0-9]{60}`),
Entropy: 2,
Keywords: []string{"clojars_"},
}
// validate
tps := utils.GenerateSampleSecrets("clojars", "CLOJARS_"+secrets.NewSecret(utils.AlphaNumeric("60")))
return utils.Validate(r, tps, nil)
}
+81
View File
@@ -0,0 +1,81 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
var global_keys = []string{
`cloudflare_global_api_key = "d3d1443e0adc9c24564c6c5676d679d47e2ca"`, // gitleaks:allow
`CLOUDFLARE_GLOBAL_API_KEY: 674538c7ecac77d064958a04a83d9e9db068c`, // gitleaks:allow
`cloudflare: "0574b9f43978174cc2cb9a1068681225433c4"`, // gitleaks:allow
}
var api_keys = []string{
`cloudflare_api_key = "Bu0rrK-lerk6y0Suqo1qSqlDDajOk61wZchCkje4"`, // gitleaks:allow
`CLOUDFLARE_API_KEY: 5oK0U90ME14yU6CVxV90crvfqVlNH2wRKBwcLWDc`, // gitleaks:allow
`cloudflare: "oj9Yoyq0zmOyWmPPob1aoY5YSNNuJ0fbZSOURBlX"`, // gitleaks:allow
}
var origin_ca_keys = []string{
`CLOUDFLARE_ORIGIN_CA: v1.0-aaa334dc886f30631ba0a610-0d98ef66290d7e50aac7c27b5986c99e6f3f1084c881d8ac0eae5de1d1aa0644076ff57022069b3237d19afe60ad045f207ef2b16387ee37b749441b2ae2e9ebe5b4606e846475d4a5`,
`CLOUDFLARE_ORIGIN_CA: v1.0-15d20c7fccb4234ac5cdd756-d5c2630d1b606535cf9320ae7456b090e0896cec64169a92fae4e931ab0f72f111b2e4ffed5b2bb40f6fba6b2214df23b188a23693d59ce3fb0d28f7e89a2206d98271b002dac695ed`,
}
var identifiers = []string{"cloudflare"}
func CloudflareGlobalAPIKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "cloudflare-global-api-key",
Description: "Detected a Cloudflare Global API Key, potentially compromising cloud application deployments and operational security.",
Regex: utils.GenerateSemiGenericRegex(identifiers, utils.Hex("37"), true),
Entropy: 2,
Keywords: identifiers,
}
// validate
tps := utils.GenerateSampleSecrets("cloudflare", secrets.NewSecret(utils.Hex("37")))
tps = append(tps, global_keys...)
fps := append(api_keys, origin_ca_keys...)
return utils.Validate(r, tps, fps)
}
func CloudflareAPIKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "cloudflare-api-key",
Description: "Detected a Cloudflare API Key, potentially compromising cloud application deployments and operational security.",
Regex: utils.GenerateSemiGenericRegex(identifiers, utils.AlphaNumericExtendedShort("40"), true),
Entropy: 2,
Keywords: identifiers,
}
// validate
tps := utils.GenerateSampleSecrets("cloudflare", secrets.NewSecret(utils.AlphaNumericExtendedShort("40")))
tps = append(tps, api_keys...)
fps := append(global_keys, origin_ca_keys...)
return utils.Validate(r, tps, fps)
}
func CloudflareOriginCAKey() *config.Rule {
ca_identifiers := append(identifiers, "v1.0-")
// define rule
r := config.Rule{
Description: "Detected a Cloudflare Origin CA Key, potentially compromising cloud application deployments and operational security.",
RuleID: "cloudflare-origin-ca-key",
Regex: utils.GenerateUniqueTokenRegex(`v1\.0-`+utils.Hex("24")+"-"+utils.Hex("146"), false),
Entropy: 2,
Keywords: ca_identifiers,
}
// validate
tps := utils.GenerateSampleSecrets("cloudflare", "v1.0-aaa334dc886f30631ba0a610-0d98ef66290d7e50aac7c27b5986c99e6f3f1084c881d8ac0eae5de1d1aa0644076ff57022069b3237d19afe60ad045f207ef2b16387ee37b749441b2ae2e9ebe5b4606e846475d4a5")
tps = append(tps, origin_ca_keys...)
fps := append(global_keys, api_keys...)
return utils.Validate(r, tps, fps)
}
+23
View File
@@ -0,0 +1,23 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func CodecovAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "codecov-access-token",
Description: "Found a pattern resembling a Codecov Access Token, posing a risk of unauthorized access to code coverage reports and sensitive data.",
Regex: utils.GenerateSemiGenericRegex([]string{"codecov"}, utils.AlphaNumeric("32"), true),
Keywords: []string{
"codecov",
},
}
// validate
tps := utils.GenerateSampleSecrets("codecov", secrets.NewSecret(utils.AlphaNumeric("32")))
return utils.Validate(r, tps, nil)
}
+32
View File
@@ -0,0 +1,32 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func CohereAPIToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "cohere-api-token",
Description: "Identified a Cohere Token, posing a risk of unauthorized access to AI services and data manipulation.",
Regex: utils.GenerateSemiGenericRegex([]string{"cohere", "CO_API_KEY"}, `[a-zA-Z0-9]{40}`, false),
Entropy: 4,
Keywords: []string{
"cohere",
"CO_API_KEY",
},
}
// validate
tps := []string{
utils.GenerateSampleSecret("cohere", secrets.NewSecret(`[a-zA-Z0-9]{40}`)),
// https://github.com/cohere-ai/cohere-go/blob/abe8044073ed498ffbb206a602d03c2414b64512/client/client.go#L38C30-L38C40
`export CO_API_KEY=` + secrets.NewSecret(`[a-zA-Z0-9]{40}`),
}
fps := []string{
`CO_API_KEY=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx`,
}
return utils.Validate(r, tps, fps)
}
+24
View File
@@ -0,0 +1,24 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func CoinbaseAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "coinbase-access-token",
Description: "Detected a Coinbase Access Token, posing a risk of unauthorized access to cryptocurrency accounts and financial transactions.",
Regex: utils.GenerateSemiGenericRegex([]string{"coinbase"},
utils.AlphaNumericExtendedShort("64"), true),
Keywords: []string{
"coinbase",
},
}
// validate
tps := utils.GenerateSampleSecrets("coinbase", secrets.NewSecret(utils.AlphaNumericExtendedShort("64")))
return utils.Validate(r, tps, nil)
}
+75
View File
@@ -0,0 +1,75 @@
# This file has been auto-generated. Do not edit manually.
# If you would like to contribute new rules, please use
# cmd/generate/config/main.go and follow the contributing guidelines
# at https://github.com/gitleaks/gitleaks/blob/master/CONTRIBUTING.md
#
# How the hell does secret scanning work? Read this:
# https://lookingatcomputer.substack.com/p/regex-is-almost-all-you-need
#
# This is the default gitleaks configuration file.
# Rules and allowlists are defined within this file.
# Rules instruct gitleaks on what should be considered a secret.
# Allowlists instruct gitleaks on what is allowed, i.e. not a secret.
title = "{{.Title}}"
# minVersion indicates the minimum Gitleaks version required to use this config.
# If the running version is older, a warning will be logged and not all
# config-enabled features are guaranteed to work.
minVersion = "v8.25.0"
{{ with .Allowlists }}{{ range $i, $allowlist := . }}{{ if or $allowlist.Regexes $allowlist.Paths $allowlist.Commits $allowlist.StopWords }}# TODO: change to [[allowlists]]{{println}}[allowlist]
{{- with .Description }}{{println}}description = "{{ . }}"{{ end }}
{{- with .MatchCondition }}{{println}}condition = "{{ .String }}"{{ end }}
{{- with .Commits -}}{{println}}commits = [
{{ range $j, $commit := . }}"{{ $commit }}",{{ end }}
]{{ end }}
{{- with .Paths }}{{println}}paths = [{{ range $j, $path := . }}
'''{{ $path }}''',{{ end }}
]{{ end }}
{{- if and .RegexTarget .Regexes }}{{println}}regexTarget = "{{ .RegexTarget }}"{{ end -}}
{{- with .Regexes }}{{println}}regexes = [{{ range $i, $regex := . }}
'''{{ $regex }}''',{{ end }}
]{{ end }}
{{- with .StopWords }}{{println}}stopwords = [{{ range $j, $stopword := . }}
"{{ $stopword }}",{{ end }}
]{{ end }}{{ end }}{{ end }}{{ end }}{{println}}
{{- range $i, $rule := .Rules }}{{println}}[[rules]]
id = "{{$rule.RuleID}}"
description = "{{$rule.Description}}"
{{- with $rule.Regex }}
regex = '''{{ . }}'''{{ end -}}
{{- with $rule.Path }}
path = '''{{ . }}'''{{ end -}}
{{- with $rule.SecretGroup }}
secretGroup = {{ . }}{{ end -}}
{{- with $rule.Entropy }}
entropy = {{ . }}{{ end -}}
{{- with $rule.Keywords }}
{{- if gt (len .) 1}}
keywords = [{{ range $j, $keyword := . }}
"{{ $keyword }}",{{ end }}
]{{else}}
keywords = [{{ range $j, $keyword := . }}"{{ $keyword }}"{{ end }}]{{end}}{{ end }}
{{- with $rule.Tags }}
tags = [
{{ range $j, $tag := . }}"{{ $tag }}",{{ end }}
]{{ end }}
{{- with $rule.Allowlists }}{{ range $i, $allowlist := . }}{{ if or $allowlist.Regexes $allowlist.Paths $allowlist.Commits $allowlist.StopWords }}{{println}}[[rules.allowlists]]
{{- with .Description }}{{println}}description = "{{ . }}"{{ end }}
{{- with .MatchCondition }}{{println}}condition = "{{ .String }}"{{ end }}
{{- with .Commits -}}{{println}}commits = [
{{ range $j, $commit := . }}"{{ $commit }}",{{ end }}
]{{ end }}
{{- with .Paths }}{{println}}paths = [
{{ range $j, $path := . }}'''{{ $path }}''',{{ end }}
]{{ end }}
{{- if and .RegexTarget .Regexes }}{{println}}regexTarget = "{{ .RegexTarget }}"{{ end -}}
{{- with .Regexes }}{{println}}regexes = [{{ range $i, $regex := . }}
'''{{ $regex }}''',{{ end }}
]{{ end }}
{{- with .StopWords }}{{println}}stopwords = [{{ range $j, $stopword := . }}
"{{ $stopword }}",{{ end }}
]{{ end }}{{ end }}{{ end }}{{ end }}
{{ end }}
+40
View File
@@ -0,0 +1,40 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func ConfluentSecretKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "confluent-secret-key",
Description: "Found a Confluent Secret Key, potentially risking unauthorized operations and data access within Confluent services.",
Regex: utils.GenerateSemiGenericRegex([]string{"confluent"}, utils.AlphaNumeric("64"), true),
Keywords: []string{
"confluent",
},
}
// validate
tps := utils.GenerateSampleSecrets("confluent", secrets.NewSecret(utils.AlphaNumeric("64")))
return utils.Validate(r, tps, nil)
}
func ConfluentAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "confluent-access-token",
Description: "Identified a Confluent Access Token, which could compromise access to streaming data platforms and sensitive data flow.",
Regex: utils.GenerateSemiGenericRegex([]string{"confluent"}, utils.AlphaNumeric("16"), true),
Keywords: []string{
"confluent",
},
}
// validate
tps := utils.GenerateSampleSecrets("confluent", secrets.NewSecret(utils.AlphaNumeric("16")))
return utils.Validate(r, tps, nil)
}
+22
View File
@@ -0,0 +1,22 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func Contentful() *config.Rule {
// define rule
r := config.Rule{
Description: "Discovered a Contentful delivery API token, posing a risk to content management systems and data integrity.",
RuleID: "contentful-delivery-api-token",
Regex: utils.GenerateSemiGenericRegex([]string{"contentful"},
utils.AlphaNumericExtended("43"), true),
Keywords: []string{"contentful"},
}
// validate
tps := utils.GenerateSampleSecrets("contentful", secrets.NewSecret(utils.AlphaNumeric("43")))
return utils.Validate(r, tps, nil)
}
+201
View File
@@ -0,0 +1,201 @@
package rules
import (
"fmt"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
// https://curl.se/docs/manpage.html#-u
func CurlBasicAuth() *config.Rule {
r := config.Rule{
RuleID: "curl-auth-user",
Description: "Discovered a potential basic authorization token provided in a curl command, which could compromise the curl accessed resource.",
Regex: regexp.MustCompile(`\bcurl\b(?:.*|.*(?:[\r\n]{1,2}.*){1,5})[ \t\n\r](?:-u|--user)(?:=|[ \t]{0,5})("(:[^"]{3,}|[^:"]{3,}:|[^:"]{3,}:[^"]{3,})"|'([^:']{3,}:[^']{3,})'|((?:"[^"]{3,}"|'[^']{3,}'|[\w$@.-]+):(?:"[^"]{3,}"|'[^']{3,}'|[\w${}@.-]+)))(?:\s|\z)`),
Keywords: []string{"curl"},
Entropy: 2,
Allowlists: []*config.Allowlist{
{
Regexes: []*regexp.Regexp{
regexp.MustCompile(`[^:]+:(?:change(?:it|me)|pass(?:word)?|pwd|test|token|\*+|x+)`), // common placeholder passwords
regexp.MustCompile(`['"]?<[^>]+>['"]?:['"]?<[^>]+>|<[^:]+:[^>]+>['"]?`), // <placeholder>
regexp.MustCompile(`[^:]+:\[[^]]+]`), // [placeholder]
regexp.MustCompile(`['"]?[^:]+['"]?:['"]?\$(?:\d|\w+|\{(?:\d|\w+)})['"]?`), // $1 or $VARIABLE
regexp.MustCompile(`\$\([^)]+\):\$\([^)]+\)`), // $(cat login.txt)
regexp.MustCompile(`['"]?\$?{{[^}]+}}['"]?:['"]?\$?{{[^}]+}}['"]?`), // ${{ secrets.FOO }} or {{ .Values.foo }}
},
},
},
}
// validate
tps := []string{
// short
`curl --cacert ca.crt -u elastic:P@ssw0rd$1 https://localhost:9200`, // same lines, no quotes
`sh-5.0$ curl -k -X POST https://infinispan:11222/rest/v2/caches/default/hello \
-H 'Content-type: text/plain' \
-d 'world' \
-u developer:yqDVtkqPECriaLRi`, // different line
`curl -u ":d2LkV78zLx!t" https://localhost:9200`, // empty username
`curl -u "d2LkV78zLx!t:" https://localhost:9200`, // empty password
// long
`curl -sw '%{http_code}' -X POST --user 'johns:h0pk1ns~21s' $GItHUB_API_URL/$GIT_COMMIT --data`,
`curl --user roger23@gmail.com:pQ9wTxu4Fg https://www.dropbox.com/cli_link?host_id=abcdefg -v`, // same line, no quotes
`curl -s --user 'api:d2LkV78zLx!t' \
https://api.mailgun.net/v2/sandbox91d3515882ecfaa1c65be642.mailgun.org/messages`, // same line, single quotes
`curl -s -v --user "j.smith:dB2yF6@qL9vZm1P#4J" "https://api.contoso.org/user/me"`, // same line, double quotes
`curl -X POST --user "{acd3c08b-74e8-4f44-a2d0-80694le24f46}":"{ZqL5kVrX1n8tA2}" --header "Accept: application/json" --data "{\"text\":\"Hello, world\",\"source\":\"en\",\"target\":\"es\"}" https://gateway.watsonplatform.net/language-translator/api`,
`curl --user kevin:'pRf7vG2h1L8nQkW9' -iX PATCH -H "Content-Type: application/json" -d`, // same line, mixed quoting
`$ curl https://api.dropbox.com/oauth2/token \
--user c28wlsosanujy2z:qgsnai0xokrw4j1 --data grant_type=authorization_code`, // different line
// TODO
//` curl -s --insecure --url "imaps://whatever.imap.server" --user\
//"myuserid:mypassword" --request "STATUS INBOX (UNSEEN)"`,
}
fps := []string{
// short
`curl -i -u 'test:test'`,
` curl -sL --user "$1:$2" "$3" > "$4"`, // environment variable
`curl -u <user:password> https://test.com/endpoint`, // placeholder
`curl --user neo4j:[PASSWORD] http://[IP]:7474/db/data/`, // placeholder
`curl -u "myusername" http://localhost:15130/api/check_user/`, // no password
`curl -u username:token`,
`curl -u "${_username}:${_password}"`,
`curl -u "${username}":"${password}"`,
`curl -k -X POST -I -u "SRVC_JENKINS:${APPID}"`,
`curl -u ":" https://localhost:9200`, // empty username and password
// long
`curl -sw '%{http_code}' -X POST --user '$USERNAME:$PASSWORD' $GItHUB_API_URL/$GIT_COMMIT --data`,
`curl --user "xxx:yyy"`,
` curl -sL --user "$GITHUB_USERNAME:$GITHUB_PASSWORD" "$GITHUB_URL" > "$TESTS_PATH"`, // environment variable
// variable interpolation
`curl --silent --fail {{- if and $.Values.username $.Values.password }} --user "{{ $.Values.username }}:{{ $.Values.password }}"`,
`curl -XGET -i -u "${{ env.ELK_ID }}:${{ build.env.ELK_PASS }}"`,
`curl -XGET -i -u "${{needs.vault.outputs.account_id}}:${{needs.vault.outputs.account_password}}"`,
`curl -XGET -i -u "${{ steps.vault.outputs.account_id }}:${{ steps.vault.outputs.account_password }}"`,
`curl -X POST --user "$(cat ./login.txt):$(cat ./password.txt)"`, // command
`curl http://127.0.0.1:5000/file --user user:pass --digest # digest auth`, // placeholder
` curl -X GET --insecure --user "username:password" \`, // placeholder
`curl --silent --insecure --user ${f5user}:${f5pass} \`, // placeholder
`curl --insecure --ssl-reqd "smtps://smtp.gmail.com" --mail-from "src@gmail.com" --mail-rcpt "dst@gmail.com" --user "src@gmail.com" --upload-file out.txt`, // no password
// different command
`#HTTP command line test
curl -X POST -H "Content-Type: application/json" -d '{"id":12345,"geo":{"latitude":28.50,"longitude":-81.14}}' http://<ip>:8080/serve
#UDP command line test
echo -n '{"type":"serve","channel":"/","data":{"site_id":8,"post_id":12345,"geo":{"lat":28.50,"long":-81.14}}}' >/dev/udp/127.0.0.1/41234
#UDP Listener (for confirmation)
nc -u -l 41234`,
}
return utils.Validate(r, tps, fps)
}
// https://curl.se/docs/manpage.html#-H
func CurlHeaderAuth() *config.Rule {
// language=regexp
authPat := `(?i)(?:Authorization:[ \t]{0,5}(?:Basic[ \t]([a-z0-9+/]{8,}={0,3})|(?:Bearer|(?:Api-)?Token)[ \t]([\w=~@.+/-]{8,})|([\w=~@.+/-]{8,}))|(?:(?:X-(?:[a-z]+-)?)?(?:Api-?)?(?:Key|Token)):[ \t]{0,5}([\w=~@.+/-]{8,}))`
r := config.Rule{
RuleID: "curl-auth-header",
Description: "Discovered a potential authorization token provided in a curl command header, which could compromise the curl accessed resource.",
Regex: regexp.MustCompile(
// language=regexp
fmt.Sprintf(`\bcurl\b(?:.*?|.*?(?:[\r\n]{1,2}.*?){1,5})[ \t\n\r](?:-H|--header)(?:=|[ \t]{0,5})(?:"%s"|'%s')(?:\B|\s|\z)`, authPat, authPat)),
Entropy: 2.75,
Keywords: []string{"curl"},
//Allowlists: []*config.Allowlist{
// {
// Regexes: []*regexp.Regexp{},
// },
//},
}
tps := []string{
`curl --header 'Authorization: 5eb4223e-5008-46e5-be67-c7b8f2732305'`,
// Short flag.
`curl -H 'Authorization: Basic YnJvd3Nlcjo=' \`, // same line, single quotes
// TODO: Handle short flags combined.
//`TOKEN=$(curl -sH "Authorization: Basic $BASIC_TOKEN" "https://$REGISTRY/oauth2/token?service=$REGISTRY&scope=repository:$REPO:pull" | jq -r .access_token)`,
// Long flag.
`curl -k -X POST --header "Authorization: Basic djJlNEpYa0NJUHZ5a2FWT0VRXzRqZmZUdDkwYTp2emNBZGFzZWpmlWZiUDc2VUJjNDNNVDExclVh" "https://api-qa.example.com:8243/token" -d "grant_type=client_credentials"`, // same line, double quotes
// Basic auth.
`curl -X POST -H "Content-Type: application/json" \
-H "Authorization: Basic MzUzYjMwMmM0NDU3NGY1NjUwNDU2ODdlNTM0ZTdkNmE6Mjg2OTI0Njk3ZTYxNWE2NzJhNjQ2YTQ5MzU0NTY0NmM=" \
-d '{"user":{"emailAddress":"test@example.com"}, "password":"password"}' \
'http://localhost:8080/oauth2-provider/v1.0/users'`, // different line, double quotes
`#curl -X POST \
# https://api.mailgun.net/v3/sandbox7dbcabccd4314c123e8b23599d35f5b6.mailgun.org/messages \
# -H 'Authorization: Basic YXBpOmtleS1hN2MzNDJ3MzNhNWQxLTU2M2U3MjlwLTZhYjI3YzYzNzM0Ng==' \
# -F from='Excited User <mailgun@sandbox7dbc123bccd4314c0aae8b23599d35f5b6.mailgun.org>' \
# -F to='joe@example.com' \
# -F subject='Hello' \
# -F text='Testing some Mailgun awesomness!'`, // different line, single quotes
// Bearer auth
`# curl -X GET "http://localhost:3000/api/cron/status" -H "Authorization: Bearer cfcabd11c7ed9a41b1a3e063c32d5114"`, // same line, double quotes
`curl -X PUT -H 'Authorization: Bearer jC+6TUUjCNHcVtAXpcqBCgxnA8r+qD6MatnYaf/+289y7HWpK0BWPyLHv/K4DMN32fufwmeVVjlo8zjgBh8kx3GfS6IqO70w1DVMSCTwX7fhEpiXaxzv0mhSMHDX9Kw63Q6DkavUWUV+MDNhCF5wGQrcdQNncVRF3YkuDHDT/xw2YWyZ/DX8k+gAYiC8gcD8Ueg0ljBVS1IDwPjuGoFPESJVxYr0MDPF2D8Pn2S5rq692U4D9ZLuluS46VA4DK6ig5P7QM5XVXi4V7vXM8qpN/zqneyz+w4PUh6NIX7QG6JczMhYd9maWRWVat5jDdyII63P6sNAy9QZjw+ClW211Q==' -d 'user={"account":"user@domain.com", "roles":["user"]}' http://127.0.0.1:8443/desks/1/occupy`, // same line, single quotes
`curl https://api.openai.com/v1/chat/completions \
-H "Content-Type: application/json" \
-H "Authorization: Bearer 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" \`, // different line, double quotes
`curl -X GET "https://api.cloudflare.com/client/v4/user/tokens/verify" \
-H "Authorization: Bearer _FXNljbSRYMWx3TWrd7lgKhLtVZX6iskC8Wcbb4b" \
-H "Content-Type:application/json"`,
`curl -H "Authorization: Bearer sha256~bRLFnzd59Z3XpZH5_seJPHALOuvbWiKwbFKSsoALkgp"`,
// Token auth
`curl -H "Authorization: Api-Token 22cb987851bc5659l29114c62e60c79abd0d2c08" --request PUT https://appsecclass.report/api/use/635`, // token
`curl -H "Authorization: Token 22cb987851bc5659229114c62e60c79abd0d2c08" --request PUT https://appsecclass.report/api/use/635`, // token
// Nothing
`curl -L -H "Authorization:eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJjb25maWRlbmNlIjowLjh9.kvRPfjAhLhtRTczoRgctVGp7KY1QVH3UBZM-gM0x8ec" service1.local -> correct jwt `, // no prefix
`curl -L -H "Authorization: sha256~bRLFnzd5@=-.a+/hgdS"`, // no prefix
// Non-authorization headers.
`curl -X GET \
-H "apikey: c4ed6c21-9dd5-4a05-8e3f-c56d1151cce8" \
-H "Accept: application/json" \`, // apikey
`curl -X POST --header "Api-Token: Sk94HG7f6KB"`, // api-token
`curl -XPOST http://localhost:8080/api/tasks -H "Content-Type: application/x-www-form-urlencoded; charset=UTF-8" -H "Token: 3fea6af1349166ea" -d "content=hello-curl"`, // token
`curl -X GET https://octopus.corp.net/
-H "X-Octopus-ApiKey: 3a16750d-d363-41a4-8ebd-035408f7730f" \`, // X-$thing-ApiKey
}
fps := []string{
// Placeholders
`curl https://example.com/micropub -d h=entry -d "content=Hello World" -H "Authorization: Bearer XXXXXXXXXXXX"`,
`curl -X POST https://accounts.spotify.com/api/token -d grant_type=client_credentials --header "Authorization: Basic ..."`,
`curl \
-H "Authorization: Bearer <Openverse API token>" \
"https://api.openverse.org/v1/audio/?q=test"`,
`curl -v -v -v -X POST https://domain/api/v1/authentication/sso/login-url/ \
-H 'Content-Type: application/json' \
-H "Authorization: Token **********" \
-d '{"username": "test", "next": "/luna/"}'`,
// Variables
`curl -XPOST http://localhost:8080/api/token -H "Authorization: basic {base64(email:password[\n])}" => token`, // same line, invalid base64
`curl -X GET \
-H "apikey: $API_KEY" \
-H "Accept: $FORMAT" \
"$API_URL/rest/v1/stats_derniere_labellisation"`, // API Key placeholder
`$ curl -X POST "http://localhost:8000/v1/chat/completions" \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $API_KEY" \
-d '{
"model": "chatglm3-6b-32k",
"messages": [{"role": "system", "content": "You are a helpful assistant."}, {"role": "user", "content": "Hello!"}]
}'`, // different line, placeholder
`curl -X GET -H "Content-Type: application/json" -H "Authorization: Bearer $(gcloud auth print-access-token)" https://workflowexecutions.googleapis.com/v1/projects/244283331594/locations/us-central1/workflows/sample-workflow/executions/43c925aa-514a-44c1-a0a4-a9f8f26fd2cb/callbacks/1705791f-d446-4e92-a6d0-a13622422e80_31864a51-8c13-4b03-ad4d-945cdc8d0631`, // script
// Not valid BASIC
`curl -X POST -H "Content-Type: application/json" -H "Authorization: Basic eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJjb25maWRlbmNlIjowLjh9.kvRPfjAhLhtRTczoRgctVGp7KY1QVH3UBZM-gM0x8ec" \`,
}
return utils.Validate(r, tps, fps)
}
+26
View File
@@ -0,0 +1,26 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func Databricks() *config.Rule {
// define rule
r := config.Rule{
RuleID: "databricks-api-token",
Description: "Uncovered a Databricks API token, which may compromise big data analytics platforms and sensitive data processing.",
Regex: utils.GenerateUniqueTokenRegex(`dapi[a-f0-9]{32}(?:-\d)?`, false),
Entropy: 3,
Keywords: []string{"dapi"},
}
// validate
tps := utils.GenerateSampleSecrets("databricks", "dapi"+secrets.NewSecret(utils.Hex("32")))
tps = append(tps, `token = dapif13ac4b49d1cb31f69f678e39602e381-2`) // gitleaks:ignore
fps := []string{
`DATABRICKS_TOKEN=dapi123456789012345678a9bc01234defg5`,
}
return utils.Validate(r, tps, fps)
}
+24
View File
@@ -0,0 +1,24 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func DatadogtokenAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "datadog-access-token",
Description: "Detected a Datadog Access Token, potentially risking monitoring and analytics data exposure and manipulation.",
Regex: utils.GenerateSemiGenericRegex([]string{"datadog"},
utils.AlphaNumeric("40"), true),
Keywords: []string{
"datadog",
},
}
// validate
tps := utils.GenerateSampleSecrets("datadog", secrets.NewSecret(utils.AlphaNumeric("40")))
return utils.Validate(r, tps, nil)
}
@@ -0,0 +1,28 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func DefinedNetworkingAPIToken() *config.Rule {
// Define Rule
r := config.Rule{
// Human redable description of the rule
Description: "Identified a Defined Networking API token, which could lead to unauthorized network operations and data breaches.",
// Unique ID for the rule
RuleID: "defined-networking-api-token",
// Regex used for detecting secrets. See regex section below for more details
Regex: utils.GenerateSemiGenericRegex([]string{"dnkey"}, `dnkey-[a-z0-9=_\-]{26}-[a-z0-9=_\-]{52}`, true),
// Keywords used for string matching on fragments (think of this as a prefilter)
Keywords: []string{"dnkey"},
}
// validate
tps := utils.GenerateSampleSecrets("dnkey", "dnkey-"+secrets.NewSecret(utils.AlphaNumericExtended("26"))+"-"+secrets.NewSecret(utils.AlphaNumericExtended("52")))
return utils.Validate(r, tps, nil)
}
+46
View File
@@ -0,0 +1,46 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func DigitalOceanPAT() *config.Rule {
r := config.Rule{
RuleID: "digitalocean-pat",
Description: "Discovered a DigitalOcean Personal Access Token, posing a threat to cloud infrastructure security and data privacy.",
Regex: utils.GenerateUniqueTokenRegex(`dop_v1_[a-f0-9]{64}`, false),
Entropy: 3,
Keywords: []string{"dop_v1_"},
}
tps := utils.GenerateSampleSecrets("do", "dop_v1_"+secrets.NewSecret(utils.Hex("64")))
return utils.Validate(r, tps, nil)
}
func DigitalOceanOAuthToken() *config.Rule {
r := config.Rule{
RuleID: "digitalocean-access-token",
Description: "Found a DigitalOcean OAuth Access Token, risking unauthorized cloud resource access and data compromise.",
Entropy: 3,
Regex: utils.GenerateUniqueTokenRegex(`doo_v1_[a-f0-9]{64}`, false),
Keywords: []string{"doo_v1_"},
}
tps := utils.GenerateSampleSecrets("do", "doo_v1_"+secrets.NewSecret(utils.Hex("64")))
return utils.Validate(r, tps, nil)
}
func DigitalOceanRefreshToken() *config.Rule {
r := config.Rule{
Description: "Uncovered a DigitalOcean OAuth Refresh Token, which could allow prolonged unauthorized access and resource manipulation.",
RuleID: "digitalocean-refresh-token",
Regex: utils.GenerateUniqueTokenRegex(`dor_v1_[a-f0-9]{64}`, true),
Keywords: []string{"dor_v1_"},
}
tps := utils.GenerateSampleSecrets("do", "dor_v1_"+secrets.NewSecret(utils.Hex("64")))
return utils.Validate(r, tps, nil)
}
+61
View File
@@ -0,0 +1,61 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func DiscordAPIToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "discord-api-token",
Description: "Detected a Discord API key, potentially compromising communication channels and user data privacy on Discord.",
Regex: utils.GenerateSemiGenericRegex([]string{"discord"}, utils.Hex("64"), true),
Keywords: []string{"discord"},
}
// validate
tps := utils.GenerateSampleSecrets("discord", secrets.NewSecret(utils.Hex("64")))
return utils.Validate(r, tps, nil)
}
func DiscordClientID() *config.Rule {
// define rule
r := config.Rule{
RuleID: "discord-client-id",
Description: "Identified a Discord client ID, which may lead to unauthorized integrations and data exposure in Discord applications.",
Regex: utils.GenerateSemiGenericRegex([]string{"discord"}, utils.Numeric("18"), true),
Entropy: 2,
Keywords: []string{"discord"},
}
// validate
tps := utils.GenerateSampleSecrets("discord", secrets.NewSecret(utils.Numeric("18")))
fps := []string{
// Low entropy
`discord=000000000000000000`,
}
return utils.Validate(r, tps, fps)
}
func DiscordClientSecret() *config.Rule {
// define rule
r := config.Rule{
RuleID: "discord-client-secret",
Description: "Discovered a potential Discord client secret, risking compromised Discord bot integrations and data leaks.",
Regex: utils.GenerateSemiGenericRegex([]string{"discord"}, utils.AlphaNumericExtended("32"), true),
Entropy: 2,
Keywords: []string{"discord"},
}
// validate
tps := utils.GenerateSampleSecrets("discord", secrets.NewSecret(utils.Numeric("32")))
fps := []string{
// Low entropy
`discord=00000000000000000000000000000000`,
// TODO:
//`discord=01234567890123456789012345678901`,
}
return utils.Validate(r, tps, fps)
}
+26
View File
@@ -0,0 +1,26 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func Doppler() *config.Rule {
// define rule
r := config.Rule{
RuleID: "doppler-api-token",
Description: "Discovered a Doppler API token, posing a risk to environment and secrets management security.",
Regex: regexp.MustCompile(`dp\.pt\.(?i)[a-z0-9]{43}`),
Entropy: 2,
Keywords: []string{`dp.pt.`},
}
// validate
tps := utils.GenerateSampleSecrets("doppler", "dp.pt."+secrets.NewSecret(utils.AlphaNumeric("43")))
return utils.Validate(r, tps, nil)
}
// TODO add additional doppler formats:
// https://docs.doppler.com/reference/auth-token-formats
+24
View File
@@ -0,0 +1,24 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func DroneciAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "droneci-access-token",
Description: "Detected a Droneci Access Token, potentially compromising continuous integration and deployment workflows.",
Regex: utils.GenerateSemiGenericRegex([]string{"droneci"}, utils.AlphaNumeric("32"), true),
Keywords: []string{
"droneci",
},
}
// validate
tps := utils.GenerateSampleSecrets("droneci", secrets.NewSecret(utils.AlphaNumeric("32")))
return utils.Validate(r, tps, nil)
}
+48
View File
@@ -0,0 +1,48 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func DropBoxAPISecret() *config.Rule {
// define rule
r := config.Rule{
Description: "Identified a Dropbox API secret, which could lead to unauthorized file access and data breaches in Dropbox storage.",
RuleID: "dropbox-api-token",
Regex: utils.GenerateSemiGenericRegex([]string{"dropbox"}, utils.AlphaNumeric("15"), true),
Keywords: []string{"dropbox"},
}
// validate
tps := utils.GenerateSampleSecrets("dropbox", secrets.NewSecret(utils.AlphaNumeric("15")))
return utils.Validate(r, tps, nil)
}
func DropBoxShortLivedAPIToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "dropbox-short-lived-api-token",
Description: "Discovered a Dropbox short-lived API token, posing a risk of temporary but potentially harmful data access and manipulation.",
Regex: utils.GenerateSemiGenericRegex([]string{"dropbox"}, `sl\.[a-z0-9\-=_]{135}`, true),
Keywords: []string{"dropbox"},
}
// validate TODO
return &r
}
func DropBoxLongLivedAPIToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "dropbox-long-lived-api-token",
Description: "Found a Dropbox long-lived API token, risking prolonged unauthorized access to cloud storage and sensitive data.",
Regex: utils.GenerateSemiGenericRegex([]string{"dropbox"}, `[a-z0-9]{11}(AAAAAAAAAA)[a-z0-9\-_=]{43}`, true),
Keywords: []string{"dropbox"},
}
// validate TODO
return &r
}
+23
View File
@@ -0,0 +1,23 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func Duffel() *config.Rule {
// define rule
r := config.Rule{
RuleID: "duffel-api-token",
Description: "Uncovered a Duffel API token, which may compromise travel platform integrations and sensitive customer data.",
Regex: regexp.MustCompile(`duffel_(?:test|live)_(?i)[a-z0-9_\-=]{43}`),
Entropy: 2,
Keywords: []string{"duffel_"},
}
// validate
tps := utils.GenerateSampleSecrets("duffel", "duffel_test_"+secrets.NewSecret(utils.AlphaNumericExtended("43")))
return utils.Validate(r, tps, nil)
}
+23
View File
@@ -0,0 +1,23 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func Dynatrace() *config.Rule {
// define rule
r := config.Rule{
RuleID: "dynatrace-api-token",
Description: "Detected a Dynatrace API token, potentially risking application performance monitoring and data exposure.",
Regex: regexp.MustCompile(`dt0c01\.(?i)[a-z0-9]{24}\.[a-z0-9]{64}`),
Entropy: 4,
Keywords: []string{"dt0c01."},
}
// validate
tps := utils.GenerateSampleSecrets("dynatrace", "dt0c01."+secrets.NewSecret(utils.AlphaNumeric("24"))+"."+secrets.NewSecret(utils.AlphaNumeric("64")))
return utils.Validate(r, tps, nil)
}
+55
View File
@@ -0,0 +1,55 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func EasyPost() *config.Rule {
// define rule
r := config.Rule{
RuleID: "easypost-api-token",
Description: "Identified an EasyPost API token, which could lead to unauthorized postal and shipment service access and data exposure.",
Regex: regexp.MustCompile(`\bEZAK(?i)[a-z0-9]{54}\b`),
Entropy: 2,
Keywords: []string{"EZAK"},
}
// validate
tps := utils.GenerateSampleSecrets("EZAK", "EZAK"+secrets.NewSecret(`[a-zA-Z0-9]{54}`))
tps = append(tps,
"EZAK"+secrets.NewSecret(`[a-zA-Z0-9]{54}`),
"example.com?t=EZAK"+secrets.NewSecret(`[a-zA-Z0-9]{54}`)+"&q=1",
)
fps := []string{
// random base64 encoded string
`...6wqX6fNUXA/rYqRvfQ+EZAKGqQRiRyqAFRQshGPWOIAwNWGORfKHSBnVNFtVmWYoW6PH23lkqbbDWep95C/3VmWq/edti6...`, // gitleaks:allow
}
return utils.Validate(r, tps, fps)
}
func EasyPostTestAPI() *config.Rule {
// define rule
r := config.Rule{
RuleID: "easypost-test-api-token",
Description: "Detected an EasyPost test API token, risking exposure of test environments and potentially sensitive shipment data.",
Regex: regexp.MustCompile(`\bEZTK(?i)[a-z0-9]{54}\b`),
Entropy: 2,
Keywords: []string{"EZTK"},
}
// validate
tps := utils.GenerateSampleSecrets("EZTK", secrets.NewSecret(`EZTK[a-zA-Z0-9]{54}`))
tps = append(tps, secrets.NewSecret(`EZTK[a-zA-Z0-9]{54}`))
tps = append(tps,
"EZTK"+secrets.NewSecret(`[a-zA-Z0-9]{54}`),
"example.com?t=EZTK"+secrets.NewSecret(`[a-zA-Z0-9]{54}`)+"&q=1",
)
fps := []string{
// random base64 encoded string
`...6wqX6fNUXA/rYqRvfQ+EZTKGqQRiRyqAFRQshGPWOIAwNWGORfKHSBnVNFtVmWYoW6PH23lkqbbDWep95C/3VmWq/edti6...`, // gitleaks:allow
}
return utils.Validate(r, tps, fps)
}
+34
View File
@@ -0,0 +1,34 @@
package rules
import (
"fmt"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func EtsyAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "etsy-access-token",
Description: "Found an Etsy Access Token, potentially compromising Etsy shop management and customer data.",
Regex: utils.GenerateSemiGenericRegex([]string{"(?-i:ETSY|[Ee]tsy)"}, utils.AlphaNumeric("24"), true),
Entropy: 3,
Keywords: []string{
"etsy",
},
}
// validate
tps := utils.GenerateSampleSecrets("ETSY", secrets.NewSecret(utils.AlphaNumeric("24")))
tps = append(tps, utils.GenerateSampleSecrets("etsy", secrets.NewSecret(utils.AlphaNumeric("24")))...)
tps = append(tps, utils.GenerateSampleSecrets("Etsy", secrets.NewSecret(utils.AlphaNumeric("24")))...)
fps := []string{
fmt.Sprintf(`SetSysctl = "%s"`, secrets.NewSecret(utils.AlphaNumeric("24"))),
` if err := sysctl.SetSysctl(sysctlBridgeCallIPTables); err != nil {`,
`g6Rib2R5hqhkZXRhY2hlZMOpaGFzaF90eXBlCqNrZXnEIwEgETSYcPQGcaAxl8vuQDLahSfhxkEEHu2flbF9ErAooEoKp3BheWxvYWTFAwB7ImJvZHkiOnsia2V5Ijp7ImVsZGVzdF9raWQiOiIwMTIwMTEzNDk4NzBmNDA2NzFhMDMxOTdjYmVlNDAzMmRhODUyN2UxYzY0MTA0MWVlZDlmOTViMTdkMTJiMDI4YTA0YTBhIiwiaG9zdCI6ImtleWJhc2UuaW8iLCJraWQiOiIwMTIwMTEzNDk4NzBmNDA2NzFhMDMxOTdjYmVlNDAzMmRhODUyN2UxYzY0MTA0MWVlZDlmOTViMTdkMTJiMDI4YTA0YTBhIiwidWlkIjoiYzUyZjc2M2MxNzYyNWZiMTI5YWU1ZDZmZThhMGUzMTkiLCJ1c2VybmFtZSI6ImttYXJla3NwYXJ0eiJ9LCJzZXJ2aWNlIjp7Imhvc3RuYW1lIjoia3lsZS5tYXJlay1zcGFydHoub3JnIiwicHJvdG9jb2wiOiJodHRwOiJ9LCJ0eXBlIjoid2ViX3NlcnZpY2VfYmluZGluZyIsInZlcnNpb24iOjF9LCJjbGllbnQiOnsibmFtZSI6ImtleWJhc2UuaW8gZ28gY2xpZW50IiwidmVyc2lvbiI6IjEuMC4xNCJ9LCJjdGltZSI6MTQ1ODU5MDYyMSwiZXhwaXJlX2luIjo1MDQ1NzYwMDAsIm1lcmtsZV9yb290Ijp7ImN0aW1lIjoxNDU4NTkwNTgzLCJoYXNoIjoiODQ0ZWRkNGU0OTQ3MWUzNWQxZTFkOTM5YTc0ZjUwMDc5Nzg3NzljMTAwYzY1NGE2OGI1NDNhYzY2Y2NlYTQ1MGFjNTllNmY3Yjc4ZGZiN2MyYzdjMmYwMzJiYTA2MzdjMzVjZDk1ZGYyZmRiNjFlNjgxMjVmNDkxNjVlZDkwNzMiLCJzZXFubyI6NDE3Mjk5fSwicHJldiI6IjdmNWFkMGZlZmQxNjM4ZjBlOTc1MTk3NzA5YTk2OTVkZmQ1NzU0MTA4NTYxZGUzMDM0ODc2NDcxODdhMDkyYzUiLCJzZXFubyI6OSwidGFnIjoic2lnbmF0dXJlIn2jc2lnxEDDVCB/SdOzo+BznIUCCa5DgISbH+0noUjyAJ4r0sH/tj8lYNpHw3WR93SBCufeElsl7KrxVdg5qU5ADYj26wgOqHNpZ190eXBlIKN0YWfNAgKndmVyc2lvbgE=`,
`in XCBuild.XCBBuildServiceSession.setSystemInfo(operatingSystemVersion: __C.NSOperatingSystemVersion, productBuildVersion: Swift.String, nativeArchitecture: Swift.String, completion: (Swift.Bool) -> ()) -> ()`,
}
return utils.Validate(r, tps, fps)
}
+78
View File
@@ -0,0 +1,78 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
// This rule includes both App Secret and Client Access Token
// https://developers.facebook.com/docs/facebook-login/guides/access-tokens/
func FacebookSecret() *config.Rule {
// define rule
r := config.Rule{
RuleID: "facebook-secret",
Description: "Discovered a Facebook Application secret, posing a risk of unauthorized access to Facebook accounts and personal data exposure.",
Regex: utils.GenerateSemiGenericRegex([]string{"facebook"}, utils.Hex("32"), true),
Entropy: 3,
Keywords: []string{"facebook"},
}
// validate
tps := utils.GenerateSampleSecrets("facebook", secrets.NewSecret(utils.Hex("32")))
tps = append(tps,
`facebook_app_secret = "6dca6432e45d933e13650d1882bd5e69"`, // gitleaks:allow
`facebook_client_access_token: 26f5fd13099f2c1331aafb86f6489692`, // gitleaks:allow
)
return utils.Validate(r, tps, nil)
}
// https://developers.facebook.com/docs/facebook-login/guides/access-tokens/#apptokens
func FacebookAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "facebook-access-token",
Description: "Discovered a Facebook Access Token, posing a risk of unauthorized access to Facebook accounts and personal data exposure.",
Regex: utils.GenerateUniqueTokenRegex(`\d{15,16}(\||%)[0-9a-z\-_]{27,40}`, true),
Keywords: []string{"facebook"},
Entropy: 3,
}
// validate
tps := []string{
`{"facebook access_token":"911602140448729|AY-lRJZq9BoDLobvAiP25L7RcMg","token_type":"bearer"}`, // gitleaks:allow
`facebook 1308742762612587|rhoK1cbv0DOU_RTX_87O4MkX7AI`, // gitleaks:allow
`facebook 1477036645700765|wRPf2v3mt2JfMqCLK8n7oltrEmc`, // gitleaks:allow
}
return utils.Validate(r, tps, nil)
}
// https://developers.facebook.com/docs/facebook-login/guides/access-tokens/#pagetokens
func FacebookPageAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "facebook-page-access-token",
Description: "Discovered a Facebook Page Access Token, posing a risk of unauthorized access to Facebook accounts and personal data exposure.",
Regex: utils.GenerateUniqueTokenRegex("EAA[MC](?i)[a-z0-9]{100,}", false),
Entropy: 4,
Keywords: []string{"EAAM", "EAAC"},
}
// validate
tps := []string{
`EAAM9GOnCB9kBO2frzOAWGN2zMnZClQshlWydZCrBNdodesbwimx1mfVJgqZBP5RSpMfUzWhtjTTXHG5I1UlvlwRZCgjm3ZBVGeTYiqAAoxyED6HaUdhpGVNoPUwAuAWWFsi9OvyYBQt22DGLqMIgD7VktuCTTZCWKasz81Q822FPhMTB9VFFyClNzQ0NLZClt9zxpsMMrUZCo1VU1rL3CKavir5QTfBjfCEzHNlWAUDUV2YZD`, // gitleaks:allow
`EAAM9GOnCB9kBO2zXpAtRBmCrsPPjdA3KeBl4tqsEpcYd09cpjm9MZCBIklZBjIQBKGIJgFwm8IE17G5pipsfRBRBEHMWxvJsL7iHLUouiprxKRQfAagw8BEEDucceqxTiDhVW2IZAQNNbf0d1JhcapAGntx5S1Csm4j0GgZB3DuUfI2HJ9aViTtdfH2vjBy0wtpXm2iamevohGfoF4NgyRHusDLjqy91uYMkfrkc`, // gitleaks:allow
`- name: FACEBOOK_TOKEN
value: "EAACEdEose0cBA1bad3afsf286JZCOV1XmV4NobAXqUXZA7U9F1UaaOdQZABvz73030MJoC3gGoQrE8IEoMl4gFA6MmQadlJQBqtRsgIcIhtelIJOJaew"`, // gitleaks:allow
}
fps := []string{
`eaaaC0b75a9329fded2ffa9a02b47e0117831b82`,
`"strict-uri-encode@npm:^2.0.0":
version: 2.0.0
resolution: "strict-uri-encode@npm:2.0.0"
checksum: eaac4cf978b6fbd480f1092cab8b233c9b949bcabfc9b598dd79a758f7243c28765ef7639c876fa72940dac687181b35486ea01ff7df3e65ce3848c64822c581
languageName: node
linkType: hard`,
}
return utils.Validate(r, tps, fps)
}
+22
View File
@@ -0,0 +1,22 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func FastlyAPIToken() *config.Rule {
// define rule
r := config.Rule{
Description: "Uncovered a Fastly API key, which may compromise CDN and edge cloud services, leading to content delivery and security issues.",
RuleID: "fastly-api-token",
Regex: utils.GenerateSemiGenericRegex([]string{"fastly"}, utils.AlphaNumericExtended("32"), true),
Keywords: []string{"fastly"},
}
// validate
tps := utils.GenerateSampleSecrets("fastly", secrets.NewSecret(utils.AlphaNumericExtended("32")))
return utils.Validate(r, tps, nil)
}
+37
View File
@@ -0,0 +1,37 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func FinicityClientSecret() *config.Rule {
// define rule
r := config.Rule{
Description: "Identified a Finicity Client Secret, which could lead to compromised financial service integrations and data breaches.",
RuleID: "finicity-client-secret",
Regex: utils.GenerateSemiGenericRegex([]string{"finicity"}, utils.AlphaNumeric("20"), true),
Keywords: []string{"finicity"},
}
// validate
tps := utils.GenerateSampleSecrets("finicity", secrets.NewSecret(utils.AlphaNumeric("20")))
return utils.Validate(r, tps, nil)
}
func FinicityAPIToken() *config.Rule {
// define rule
r := config.Rule{
Description: "Detected a Finicity API token, potentially risking financial data access and unauthorized financial operations.",
RuleID: "finicity-api-token",
Regex: utils.GenerateSemiGenericRegex([]string{"finicity"}, utils.Hex("32"), true),
Keywords: []string{"finicity"},
}
// validate
tps := utils.GenerateSampleSecrets("finicity", secrets.NewSecret(utils.Hex("32")))
return utils.Validate(r, tps, nil)
}
+24
View File
@@ -0,0 +1,24 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func FinnhubAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "finnhub-access-token",
Description: "Found a Finnhub Access Token, risking unauthorized access to financial market data and analytics.",
Regex: utils.GenerateSemiGenericRegex([]string{"finnhub"}, utils.AlphaNumeric("20"), true),
Keywords: []string{
"finnhub",
},
}
// validate
tps := utils.GenerateSampleSecrets("finnhub", secrets.NewSecret(utils.AlphaNumeric("20")))
return utils.Validate(r, tps, nil)
}
+24
View File
@@ -0,0 +1,24 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func FlickrAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "flickr-access-token",
Description: "Discovered a Flickr Access Token, posing a risk of unauthorized photo management and potential data leakage.",
Regex: utils.GenerateSemiGenericRegex([]string{"flickr"}, utils.AlphaNumeric("32"), true),
Keywords: []string{
"flickr",
},
}
// validate
tps := utils.GenerateSampleSecrets("flickr", secrets.NewSecret(utils.AlphaNumeric("32")))
return utils.Validate(r, tps, nil)
}
+53
View File
@@ -0,0 +1,53 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func FlutterwavePublicKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "flutterwave-public-key",
Description: "Detected a Finicity Public Key, potentially exposing public cryptographic operations and integrations.",
Regex: regexp.MustCompile(`FLWPUBK_TEST-(?i)[a-h0-9]{32}-X`),
Entropy: 2,
Keywords: []string{"FLWPUBK_TEST"},
}
// validate
tps := utils.GenerateSampleSecrets("flutterwavePubKey", "FLWPUBK_TEST-"+secrets.NewSecret(utils.Hex("32"))+"-X")
return utils.Validate(r, tps, nil)
}
func FlutterwaveSecretKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "flutterwave-secret-key",
Description: "Identified a Flutterwave Secret Key, risking unauthorized financial transactions and data breaches.",
Regex: regexp.MustCompile(`FLWSECK_TEST-(?i)[a-h0-9]{32}-X`),
Entropy: 2,
Keywords: []string{"FLWSECK_TEST"},
}
// validate
tps := utils.GenerateSampleSecrets("flutterwavePubKey", "FLWSECK_TEST-"+secrets.NewSecret(utils.Hex("32"))+"-X")
return utils.Validate(r, tps, nil)
}
func FlutterwaveEncKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "flutterwave-encryption-key",
Description: "Uncovered a Flutterwave Encryption Key, which may compromise payment processing and sensitive financial information.",
Regex: regexp.MustCompile(`FLWSECK_TEST-(?i)[a-h0-9]{12}`),
Entropy: 2,
Keywords: []string{"FLWSECK_TEST"},
}
// validate
tps := utils.GenerateSampleSecrets("flutterwavePubKey", "FLWSECK_TEST-"+secrets.NewSecret(utils.Hex("12")))
return utils.Validate(r, tps, nil)
}
+57
View File
@@ -0,0 +1,57 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
// https://fly.io/docs/security/tokens/
// https://github.com/trufflesecurity/trufflehog/pull/2381/files#r1565860579
// https://github.com/superfly/macaroon-elixir/blob/8b42043b0a24aada5c8b8eb8505dbf1590557f1b/test/vectors.json#L7
func FlyIOAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "flyio-access-token",
Description: "Uncovered a Fly.io API key", // TODO
Regex: utils.GenerateUniqueTokenRegex(`(?:fo1_[\w-]{43}|fm1[ar]_[a-zA-Z0-9+\/]{100,}={0,3}|fm2_[a-zA-Z0-9+\/]{100,}={0,3})`, false),
Entropy: 4,
Keywords: []string{"fo1_", "fm1", "fm2_"},
}
// validate
// fo1_
tps := utils.GenerateSampleSecrets("fly", secrets.NewSecret(`fo1_[\w-]{43}`))
tps = append(tps,
`Fly access token: fo1_8rz-j7r2eqJ2U7affEOO3HJN0j63DInyog3eV-glQSc
`,
`=============================================================================================================
fo1_BtKlzvfztw0M2hlLgTdsfPgDFiwM2jJjQXXy6I2pjuQ
fly deploy`)
// fm1
tps = append(tps, utils.GenerateSampleSecrets("fly", secrets.NewSecret(`fm1[ar]_[a-zA-Z0-9+\/]{100,}={0,3}`))...)
tps = append(tps,
`ENV FLY_API_TOKEN="FlyV1 fm1r_lJPECAAAAAAAAMqcxBBLMJKXYKJiT0CI58XmukX/wrVodHlwczovL2FwaS5mbHkuaW8vdjGWAJLOAAFmXh8Lk7lodHRwczovL2FwaS5mbHkuaW8vYWFhL3YxxDy5OfA2M6K6aLEoEDKxehojbj+8ZT9IrXCF5sL/r8m6/1gylwySsNxpD40wnpd/G2ZdjwVaQev1kEuFUgzERxPbtWHDNa+NYIZwbKN6b7/JxdbUprq0M10HI4fwtlxhqhdA/mMaMw70EC4TsfJyghIL98KP4ry5AaXiroRdjrSsFExc/xRCDZKUA5GBzgATuNsfBZGCp2J1aWxkZXIfondnHwHEIMa6NWc4b52S+UY7vjPdwKrz00Uzrc1830mOHzQNLun7,fm1a_lJPERxPbtWHDNa+NYIZwbKN6b7/JxdbUprq0M10HI4fwtlxhqhdA/mMaMw70EC4TsfJyghIL98KP4ry4AaXiroRdjrSsFExc/xRCxBCVlAoRzKV/+qYkxuipIbIcw7lodHRwczovL2FwaS5mbHkuaW8vYWFhL3YxlgSSzmS4Y7nPAAAAASCwgdcKkc4AAUktDMQQURck2h+upbiOrW66Nf5SA8QgrD03xlWju1WQi0AUhlk7YYFzOLDfhRyJ6nEziO37NUE="`,
)
// fm2
tps = append(tps, utils.GenerateSampleSecrets("fly", secrets.NewSecret(`fm2_[a-zA-Z0-9+\/]{100,}={0,3}`))...)
tps = append(tps,
`# FLY_API_TOKEN: FlyV1 fm2_lJPECAAAAAAAAyZtxBD1hSZ7L5leXsj64ZbDlkm/wrVodHRwczovL2FwaS5mbHkuaW8vdjGWAJLOAAwMDB8Lk7lodHRwczovL2FwaS5mbHkuaW8vYWFhL3YxxDwDnhgJj/ML/nRKMiAYgnvXfNacrGWffj5TdfgGY2LU0ZetT7WzTLQQMO8cN2nRTztl/xLjnnZg5pBwFonETmhNA6Yl0X1tatt8ezA0UjVQiJr93VQ7qAmD5GG2Ce5txhbQv3tmIGsvaC7BOkIqAiR273bhZkO44AYsrCPr2XF8W6Twk7NyU+3UUeDwjw2SlAORgc4APu7vHwWRgqdidWlsZGVyH6J3Zx8BxCAlmLbu1HQDg8ZAGKKmEt4Mbnbqli6lbzBDHsawhcUF4A==,fm2_lJPETmhNA6Yl0X1tatt8ezA0UjVQiJr93VQ7qAmD5GG2Ce5txhbQv3tmIGsvaC7BOkIqAij273bhZkO44AYsrCPr2XF8W6Twk7NyU+3UUeDwj8QQbn07DOV+7SmoLj/uT+dbr8O5aHR0cHM6Ly9hcGkuZmx5LmlvL2FhYS92MZgEks5mqfbvzwAAAAE9PYz9F84AC7QACpHOAAu0AAzEEFfW3B+SzffV/KrAYa8qqpnEIIlD6DqZMZQ9Kt7fEenCCOLA+tUSJ+kmEFIUcc83npOI`,
`"BindToParentToken": "FlyV1 fm2_lJPEEKnzKy0lkwV3B+WIlmrdwejEEFv5qmevHU4fMs+2Gr6oOiPC2SAyOTc0NWI4ZmJlNjBlNjJmZTgzNTkxOThhZWE4MjY0M5IMxAMBAgPEIH7VG8u74KwO62hmx8SZO8WaU5o1g3W2IVc7QN6T1VTr",`,
)
fps := []string{
// fo1_
`resource "doppler_integration_flyio" "prod" {
name = "TF Fly.io"
api_key = "fo1_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
}`, // https://github.com/DopplerHQ/terraform-provider-doppler/blob/a012e1a7903cce391be511b391850b29ebfdeb68/docs/resources/integration_flyio.md?plain=1#L17
`pub const MINIDUMP_SYSMEMINFO1_PERF_CCTOTALDIRTYPAGES_CCDIRTYPAGETHRESHOLD: u32 = 4u32;`, // https://github.com/microsoft/windows-rs/blob/0f7466c34e774e547d21c579b58b60168c4ee6bc/crates/libs/sys/src/Windows/Win32/System/Diagnostics/Debug/mod.rs#L1258
`<input type="hidden" name="authenticity_token" value="7SWa-Fo1_hsC6oovfBsJFLGPUl2EhkSWPbJhWANwgaJWBDl1vxd9VNqXTNAefsJqzIRYaZEfYZLffa31rw8zJA" autocomplete="off" />`,
// fm1
`signature":"I7l2ZXhw9ajjIE2w9tjHNvYjcHg7E2qldMMhoQKjborcWIj8c40rMj83venoy6gXsg6V6B7dlBWxUmzYJR3lJKGECtCSM5BqBvWhL6wX2CN2lZlvwNCyPjG4PCt5MAK1yV1Xv4fqfz8EfT_U49vOzfM1a_nfhXOzrvdg9XgLkAotWBI31vPKjMBrvPqiLcZ12MDNTSK7ubRpVaehSNxiGYHpLhWTkun9qm_APYYXJBjhJYkej50Qcp7Ou8fs3kH02prYIJt4JbWelr5vUDkgMH3AwEx1eYu5NI_8sESlqosl1nhSDx7zq3X1FV1iJlAYCNwGWzW1tjo8PCaJrIHVZZnhBPMN-6ahmOpKb8GViqd4fCQuNe4VUSOeJg8i97kMuk-4r7hwIubR0XfCGzxr7uGDQBdFANi3c4dLlzBAJNifa6b_hT4Xzqja6RCFSv6Cnalyx3hbSkjbyThnXFavJIiR7cvgTcdECg9VxkaxqqRhfAkLAS3hpXQAIYL_bw61M3LN37WHwdgxN_6yZhbSbOsYPmTxiWvdlDaCP_iaCgXgJNfdQ6kep_I89slynE9gdDZ6NSjFJH2Soml4pR6HnQKPjA3OpoTwPSmZjxXY5I78xvrRqRkjdnVzeufqG8LyA-sAEtC0G_312JOxV4GZINquPGk1qFx8WN59Rxw28Tg",`,
// fm2
`<p><span class="emoji">🗣️</span> Adobe illustrator软件基础精讲课程<br><br><span class="emoji">🏷️</span> <a href="https://t.me/abskoop/8565?q=%23%E8%AE%BE%E8%AE%A1%E5%B8%88">#设计师</a> <a href="https://t.me/abskoop/8565?q=%23%E8%B5%84%E6%BA%90">#资源</a> <a href="https://t.me/abskoop/8565?q=%23%E5%A4%B8%E5%85%8B%E7%BD%91%E7%9B%98">#夸克网盘</a><br><br><span class="emoji">👉</span> <a href="https://www.ahhhhfs.com/62409/" target="_blank" rel="noopener">https://www.ahhhhfs.com/62409/</a></p><img src="https://cdn5.cdn-telegram.org/file/uGoDMy0VXMbL1nki9OT0VbJYtfURvDNLurptsQVuhuzF45tNfm2_z5wgR7CnL7lTZ4bbotjXZtiLWvolNQqWBRFWkcidtzSyhWvta9yPB3E2uyvfJvGpditkaLVIiCCXt9BhFBEdgkXa8ODaM7geHK3pW0tmO_IViHBnG8VZqVfDpaQW0W9IRAUwGv2mPZWVRysPJyDSIuY9b-_3ElUml-Xlpm1r8EDcm9Q2WCTCOYur7Gmef4imQ5D-DLTviqmoONgQDLA10WVS3CApXBK4ADSjoIUeMck62owtjElSXnEYMaSGI_OE3B21QplsspPbPlXVUBScLfLOFb9tn-34tw.jpg" width="800" height="533" referrerpolicy="no-referrer">`,
}
return utils.Validate(r, tps, fps)
}
+22
View File
@@ -0,0 +1,22 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func FrameIO() *config.Rule {
// define rule
r := config.Rule{
Description: "Found a Frame.io API token, potentially compromising video collaboration and project management.",
RuleID: "frameio-api-token",
Regex: regexp.MustCompile(`fio-u-(?i)[a-z0-9\-_=]{64}`),
Keywords: []string{"fio-u-"},
}
// validate
tps := utils.GenerateSampleSecrets("frameio", "fio-u-"+secrets.NewSecret(utils.AlphaNumericExtended("64")))
return utils.Validate(r, tps, nil)
}
+47
View File
@@ -0,0 +1,47 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func Freemius() *config.Rule {
// define rule
r := config.Rule{
RuleID: "freemius-secret-key",
Description: "Detected a Freemius secret key, potentially exposing sensitive information.",
Regex: regexp.MustCompile(`(?i)["']secret_key["']\s*=>\s*["'](sk_[\S]{29})["']`),
Keywords: []string{"secret_key"},
Path: regexp.MustCompile(`(?i)\.php$`),
}
// validate
tps := map[string]string{
"file.php": `$config = array(
"secret_key" => "sk_ubb4yN3mzqGR2x8#P7r5&@*xC$utE",
);`,
}
// It's only used in PHP SDK snippet.
// see https://freemius.com/help/documentation/wordpress-sdk/integrating-freemius-sdk/
fps := map[string]string{
// Invalid format: missing quotes around `secret_key`.
"foo.php": `$config = array(
secret_key => "sk_abcdefghijklmnopqrstuvwxyz123",
);`,
// Invalid format: missing quotes around the key value.
"bar.php": `$config = array(
"secret_key" => sk_abcdefghijklmnopqrstuvwxyz123,
);`,
// Invalid: different key name.
"baz.php": `$config = array(
"other_key" => "sk_abcdefghijklmnopqrstuvwxyz123",
);`,
// Invalid: file extension, should validate only .php files.
"foo.html": `$config = array(
"secret_key" => "sk_ubb4yN3mzqGR2x8#P7r5&@*xC$utE",
);`,
}
return utils.ValidateWithPaths(r, tps, fps)
}
+24
View File
@@ -0,0 +1,24 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func FreshbooksAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "freshbooks-access-token",
Description: "Discovered a Freshbooks Access Token, posing a risk to accounting software access and sensitive financial data exposure.",
Regex: utils.GenerateSemiGenericRegex([]string{"freshbooks"}, utils.AlphaNumeric("64"), true),
Keywords: []string{
"freshbooks",
},
}
// validate
tps := utils.GenerateSampleSecrets("freshbooks", secrets.NewSecret(utils.AlphaNumeric("64")))
return utils.Validate(r, tps, nil)
}
+90
View File
@@ -0,0 +1,90 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
// TODO this one could probably use some work
func GCPServiceAccount() *config.Rule {
// define rule
r := config.Rule{
Description: "Google (GCP) Service-account",
RuleID: "gcp-service-account",
Regex: regexp.MustCompile(`\"type\": \"service_account\"`),
Keywords: []string{`\"type\": \"service_account\"`},
}
// validate
tps := []string{
`"type": "service_account"`,
}
return utils.Validate(r, tps, nil)
}
func GCPAPIKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "gcp-api-key",
Description: "Uncovered a GCP API key, which could lead to unauthorized access to Google Cloud services and data breaches.",
Regex: utils.GenerateUniqueTokenRegex(`AIza[\w-]{35}`, false),
Entropy: 4,
Keywords: []string{"AIza"},
Allowlists: []*config.Allowlist{
{
Regexes: []*regexp.Regexp{
// example keys from https://github.com/firebase/firebase-android-sdk
regexp.MustCompile(`AIzaSyabcdefghijklmnopqrstuvwxyz1234567`),
regexp.MustCompile(`AIzaSyAnLA7NfeLquW1tJFpx_eQCxoX-oo6YyIs`),
regexp.MustCompile(`AIzaSyCkEhVjf3pduRDt6d1yKOMitrUEke8agEM`),
regexp.MustCompile(`AIzaSyDMAScliyLx7F0NPDEJi1QmyCgHIAODrlU`),
regexp.MustCompile(`AIzaSyD3asb-2pEZVqMkmL6M9N6nHZRR_znhrh0`),
regexp.MustCompile(`AIzayDNSXIbFmlXbIE6mCzDLQAqITYefhixbX4A`),
regexp.MustCompile(`AIzaSyAdOS2zB6NCsk1pCdZ4-P6GBdi_UUPwX7c`),
regexp.MustCompile(`AIzaSyASWm6HmTMdYWpgMnjRBjxcQ9CKctWmLd4`),
regexp.MustCompile(`AIzaSyANUvH9H9BsUccjsu2pCmEkOPjjaXeDQgY`),
regexp.MustCompile(`AIzaSyA5_iVawFQ8ABuTZNUdcwERLJv_a_p4wtM`),
regexp.MustCompile(`AIzaSyA4UrcGxgwQFTfaI3no3t7Lt1sjmdnP5sQ`),
regexp.MustCompile(`AIzaSyDSb51JiIcB6OJpwwMicseKRhhrOq1cS7g`),
regexp.MustCompile(`AIzaSyBF2RrAIm4a0mO64EShQfqfd2AFnzAvvuU`),
regexp.MustCompile(`AIzaSyBcE-OOIbhjyR83gm4r2MFCu4MJmprNXsw`),
regexp.MustCompile(`AIzaSyB8qGxt4ec15vitgn44duC5ucxaOi4FmqE`),
regexp.MustCompile(`AIzaSyA8vmApnrHNFE0bApF4hoZ11srVL_n0nvY`),
},
},
},
}
// validate
tps := utils.GenerateSampleSecrets("gcp", secrets.NewSecret(`AIza[\w-]{35}`))
tps = append(tps,
// non-word character at end
`AIzaSyNHxIf32IQ1a1yjl3ZJIqKZqzLAK1XhDk-`, // gitleaks:allow
)
fps := []string{
`GWw4hjABFzZCGiRpmlDyDdo87Jn9BN9THUA47muVRNunLxsa82tMAdvmrhOqNkRKiYMEAFbTJAIzaTesb6Tscfcni8vIpWZqNCXFDFslJtVSvFDq`, // text boundary start
`AIzaTesb6Tscfcni8vIpWZqNCXFDFslJtVSvFDqabcd123`, // text boundary end
`apiKey: "AIzaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"`, // not enough entropy
`AIZASYCO2CXRMC9ELSKLHLHRMBSWDEVEDZTLO2O`, // incorrect case
// example keys from https://github.com/firebase/firebase-android-sdk
`AIzaSyabcdefghijklmnopqrstuvwxyz1234567`,
`AIzaSyAnLA7NfeLquW1tJFpx_eQCxoX-oo6YyIs`,
`AIzaSyCkEhVjf3pduRDt6d1yKOMitrUEke8agEM`,
`AIzaSyDMAScliyLx7F0NPDEJi1QmyCgHIAODrlU`,
`AIzaSyD3asb-2pEZVqMkmL6M9N6nHZRR_znhrh0`,
`AIzayDNSXIbFmlXbIE6mCzDLQAqITYefhixbX4A`,
`AIzaSyAdOS2zB6NCsk1pCdZ4-P6GBdi_UUPwX7c`,
`AIzaSyASWm6HmTMdYWpgMnjRBjxcQ9CKctWmLd4`,
`AIzaSyANUvH9H9BsUccjsu2pCmEkOPjjaXeDQgY`,
`AIzaSyA5_iVawFQ8ABuTZNUdcwERLJv_a_p4wtM`,
`AIzaSyA4UrcGxgwQFTfaI3no3t7Lt1sjmdnP5sQ`,
`AIzaSyDSb51JiIcB6OJpwwMicseKRhhrOq1cS7g`,
`AIzaSyBF2RrAIm4a0mO64EShQfqfd2AFnzAvvuU`,
`AIzaSyBcE-OOIbhjyR83gm4r2MFCu4MJmprNXsw`,
`AIzaSyB8qGxt4ec15vitgn44duC5ucxaOi4FmqE`,
`AIzaSyA8vmApnrHNFE0bApF4hoZ11srVL_n0nvY`,
}
return utils.Validate(r, tps, fps)
}
+299
View File
@@ -0,0 +1,299 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func GenericCredential() *config.Rule {
// define rule
r := config.Rule{
RuleID: "generic-api-key",
Description: "Detected a Generic API Key, potentially exposing access to various services and sensitive operations.",
Regex: utils.GenerateSemiGenericRegex([]string{
"access",
"auth",
`(?-i:[Aa]pi|API)`,
"credential",
"creds",
"key",
"passw(?:or)?d",
"secret",
"token",
}, `[\w.=-]{10,150}|[a-z0-9][a-z0-9+/]{11,}={0,3}`, true),
Keywords: []string{
"access",
"api",
"auth",
"key",
"credential",
"creds",
"passwd",
"password",
"secret",
"token",
},
Entropy: 3.5,
Allowlists: []*config.Allowlist{
{
// NOTE: this is a goofy hack to get around the fact there golang's regex engine does not support positive lookaheads.
// Ideally we would want to ensure the secret contains both numbers and alphabetical characters, not just alphabetical characters.
Regexes: []*regexp.Regexp{
regexp.MustCompile(`^[a-zA-Z_.-]+$`),
},
},
{
Description: "Allowlist for Generic API Keys",
MatchCondition: config.AllowlistMatchOr,
RegexTarget: "match",
Regexes: []*regexp.Regexp{
regexp.MustCompile(`(?i)(?:` +
// Access
`access(?:ibility|or)` +
`|access[_.-]?id` +
`|random[_.-]?access` +
// API
`|api[_.-]?(?:id|name|version)` + // id/name/version -> not a secret
`|rapid|capital` + // common words containing "api"
`|[a-z0-9-]*?api[a-z0-9-]*?:jar:` + // Maven META-INF dependencies that contain "api" in the name.
// Auth
`|author` +
`|X-MS-Exchange-Organization-Auth` + // email header
`|Authentication-Results` + // email header
// Credentials
`|(?:credentials?[_.-]?id|withCredentials)` + // Jenkins plugins
// Key
`|(?:bucket|foreign|hot|idx|natural|primary|pub(?:lic)?|schema|sequence)[_.-]?key` +
`|(?:turkey)` +
`|key[_.-]?(?:alias|board|code|frame|id|length|mesh|name|pair|press(?:ed)?|ring|selector|signature|size|stone|storetype|word|up|down|left|right)` +
// Azure KeyVault
`|key[_.-]?vault[_.-]?(?:id|name)|keyVaultToStoreSecrets` +
`|key(?:store|tab)[_.-]?(?:file|path)` +
`|issuerkeyhash` + // part of ssl cert
`|(?-i:[DdMm]onkey|[DM]ONKEY)|keying` + // common words containing "key"
// Secret
`|(?:secret)[_.-]?(?:length|name|size)` + // name of e.g. env variable
`|UserSecretsId` + // https://learn.microsoft.com/en-us/aspnet/core/security/app-secrets?view=aspnetcore-8.0&tabs=linux
// Token
`|(?:csrf)[_.-]?token` +
`|(?:io\.jsonwebtoken[ \t]?:[ \t]?[\w-]+)` + // Maven library coordinates. (e.g., https://mvnrepository.com/artifact/io.jsonwebtoken/jjwt)
// General
`|(?:api|credentials|token)[_.-]?(?:endpoint|ur[il])` +
`|public[_.-]?token` +
`|(?:key|token)[_.-]?file` +
// Empty variables capturing the next line (e.g., .env files)
`|(?-i:(?:[A-Z_]+=\n[A-Z_]+=|[a-z_]+=\n[a-z_]+=)(?:\n|\z))` +
`|(?-i:(?:[A-Z.]+=\n[A-Z.]+=|[a-z.]+=\n[a-z.]+=)(?:\n|\z))` +
`)`),
},
StopWords: append(DefaultStopWords,
"6fe4476ee5a1832882e326b506d14126", // https://github.com/yarnpkg/berry/issues/6201
),
},
{
RegexTarget: "line",
Regexes: []*regexp.Regexp{
// Docker build secrets (https://docs.docker.com/build/building/secrets/#using-build-secrets).
regexp.MustCompile(`--mount=type=secret,`),
// https://github.com/gitleaks/gitleaks/issues/1800
regexp.MustCompile(`import[ \t]+{[ \t\w,]+}[ \t]+from[ \t]+['"][^'"]+['"]`),
},
},
{
MatchCondition: config.AllowlistMatchAnd,
RegexTarget: "line",
Regexes: []*regexp.Regexp{
regexp.MustCompile(`LICENSE[^=]*=\s*"[^"]+`),
regexp.MustCompile(`LIC_FILES_CHKSUM[^=]*=\s*"[^"]+`),
regexp.MustCompile(`SRC[^=]*=\s*"[a-zA-Z0-9]+`),
},
Paths: []*regexp.Regexp{
regexp.MustCompile(`\.bb$`),
regexp.MustCompile(`\.bbappend$`),
regexp.MustCompile(`\.bbclass$`),
regexp.MustCompile(`\.inc$`),
},
},
},
}
// validate
tps := utils.GenerateSampleSecrets("generic", "CLOJARS_34bf0e88955ff5a1c328d6a7491acc4f48e865a7b8dd4d70a70749037443") //gitleaks:allow
tps = append(tps, utils.GenerateSampleSecrets("generic", "Zf3D0LXCM3EIMbgJpUNnkRtOfOueHznB")...)
tps = append(tps,
// Access
`'access_token': 'eyJ0eXAioiJKV1slS3oASx=='`,
// API
`some_api_token_123 = "`+newPlausibleSecret(`[a-zA-Z0-9]{60}`)+`"`,
// Auth
`"user_auth": "am9obmRvZTpkMDY5NGIxYi1jMTcxLTQ4ODYt+TMyYS0wMmUwOWQ1/mIwNjc="`,
// Credentials
`"credentials" : "0afae57f3ccfd9d7f5767067bc48b30f719e271ba470488056e37ab35d4b6506"`,
`creds = `+newPlausibleSecret(`[a-zA-Z0-9]{30}`),
// Key
`private-key: `+newPlausibleSecret(`[a-zA-Z0-9\-_.=]{100}`),
// Password
`passwd = `+newPlausibleSecret(`[a-zA-Z0-9\-_.=]{30}`),
// TODO: `ID=dbuser;password=` + newPlausibleSecret(`[a-zA-Z0-9+/]{30}={0,3}`) + `;"`,
// Secret
`"client_secret" : "6da89121079f83b2eb6acccf8219ea982c3d79bccc3e9c6a85856480661f8fde",`,
`mySecretString=`+newPlausibleSecret(`[a-zA-Z0-9]{30}`),
`todo_secret_do_not_commit = `+newPlausibleSecret(`[a-zA-Z0-9]{30}`),
// Token
` utils.GetEnvOrDefault("api_token", "dafa7817-e246-48f3-91a7-e87653d587b8")`,
// `"env": {
//"API_TOKEN": "Lj2^5O%xi214"`,
)
fps := []string{
// Access
`"accessor":"rA1wk0Y45YCufyfq",`,
`report_access_id: e8e4df51-2054-49b0-ab1c-516ac95c691d`,
`accessibilityYesOptionId = "0736f5ef-7e88-499a-80cc-90c85d2a5180"`,
`_RandomAccessIterator>
_LIBCPP_CONSTEXPR_AFTER_CXX11 `,
// API
`this.ultraPictureBox1.Name = "ultraPictureBox1";`,
`rapidstring:marm64-uwp=fail`,
`event-bus-message-api:rc0.15.0_20231217_1420-SNAPSHOT'`,
`COMMUNICATION_API_VERSION=rc0.13.0_20230412_0712-SNAPSHOT`,
`MantleAPI_version=9a038989604e8da62ecddbe2094b16ce1b778be1`,
`[DEBUG] org.slf4j.slf4j-api:jar:1.7.8.:compile (version managed from default)`,
`[DEBUG] org.neo4j.neo4j-graphdb-api:jar:3.5.12:test`,
`apiUrl=apigee.corpint.com`,
`X-API-Name": "NRG0-Hermes-INTERNAL-API",`,
// TODO: Jetbrains IML files (requires line-level allowlist).
// `<orderEntry type="library" scope="PROVIDED" name="Maven: org.apache.directory.api:api-asn1-api:1.0.0-M20" level="projcet" />`
// Auth
`author = "james.fake@ymail.com",`,
`X-MS-Exchange-Organization-AuthSource: sm02915.int.contoso.com`,
`Authentication-Results: 5h.ca.iphmx.com`,
// Credentials
`withCredentials([usernamePassword(credentialsId: '29f63271-dc2f-4734-8221-5b31b5169bac', usernameVariable: 'USERNAME', passwordVariable: 'PASSWORD')]) {`,
`credentialsId: 'ff083f76-7804-4ef1-80e4-fe975bb9141b'`,
`jobCredentialsId: 'f4aeb6bc-2a25-458a-8111-9be9e502c0e7'`,
` "credentialId": "B9mTcFSck2LzJO2S3ols63",`,
`environment {
CREDENTIALS_ID = "K8S_CRED"
}`,
`dev.credentials.url=dev-lb1.api.f4ke.com:5215`,
// Key
`keyword: "Befaehigung_P2"`,
`public_key = "9Cnzj4p4WGeKLs1Pt8QuKUpRKfFLfRYC9AIKjbJTWit"`,
`pub const X509_pubkey_st = struct_X509_pubkey_st;`,
`|| pIdxKey->default_rc==0`,
`monkeys-audio:mx64-uwp=fail`,
`primaryKey=` + newPlausibleSecret(`[a-zA-Z0-9\-_.=]{30}`),
`foreignKey=` + newPlausibleSecret(`[a-zA-Z0-9\-_.=]{30}`),
`key_down_event=` + newPlausibleSecret(`[a-zA-Z0-9\-_.=]{30}`),
`issuerKeyHash=` + newPlausibleSecret(`[a-zA-Z0-9\-_.=]{30}`),
`<entry key="jetbrains.mps.v8_elimination" value="executed" />`,
`minisat-master-keying:x64-uwp=fail`,
`IceSSL.KeyFile=s_rsa1024_priv.pem`,
`"bucket_key": "SalesResults-1.2"`,
`<key tag="SecurityIdentifier" name="SecurityIdentifier" type="STRING" />`,
// `packageKey":` + newPlausibleSecret(`[a-zA-Z0-9\-_.=]{30}`),
`schemaKey = 'DOC_Vector_5_32'`,
`sequenceKey = "18"`,
`app.keystore.file=env/cert.p12`,
`-DKEYTAB_FILE=/tmp/app.keytab`,
` doc.Security.KeySize = PdfEncryptionKeySize.Key128Bit;`,
`o.keySelector=n,o.haKey=!1,`,
// TODO: Requires line-level allowlists.
` "key_name": "prod5zyxlmy-cmk",`,
` "kms_key_id": "555ea4a3-d53a-4412-9c66-3a7cb667b0d6",`,
` "key_vault_name": "web21prqodx24021",`,
` keyVaultToStoreSecrets: cmp2-qat-1208358310`, // e.g., https://github.com/2uasimojo/community-operators-prod/blob/9e51e4c8e0b5caaa3087e8e18e6fb918b2c36643/operators/azure-service-operator/1.0.59040/manifests/azure.microsoft.com_cosmosdbs.yaml#L50
`,apiKey:"6fe4476ee5a1832882e326b506d14126",`,
`const validKeyChars = "0123456789abcdefghijklmnopqrstuvwxyz_-."`,
`const keyStr = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789"`,
`key_length = XSalsa20.key_length`,
`pub const SN_id_Gost28147_89_None_KeyMeshing = "id-Gost28147-89-None-KeyMeshing"`,
`KeyPair = X25519.KeyPair`,
`BlindKeySignatures = Ed25519.BlindKeySignatures`,
`AVEncVideoMaxKeyframeDistance, "2987123a-ba93-4704-b489-ec1e5f25292c"`,
` keyPressed = kVK_Return.u16`,
`timezone_mapping = {
"Turkey Standard Time": "Europe/Istanbul",
}`, // https://github.com/gitleaks/gitleaks/issues/1799
// `<add key="SchemaTable" value="G:\SchemaTable.xml" />`,
//` { key: '9df21e95-3848-409d-8f94-c675cdfee839', value: 'Americas' },`,
// `<TAR key="REF_ID_923.properties" value="/opts/config/alias/"/>`,
// `secret:
// secretName: app-decryption-secret
// items:
// - key: app-k8s.yml
// path: app-k8s.yml`,
// TODO: https://learn.microsoft.com/en-us/windows/apps/design/style/xaml-theme-resources
//`<Color x:Key="NormalBrushGradient1">#FFBAE4FF</Color>`,
// Password
`password combination.
R5: Regulatory--21`,
`PuttyPassword=0`,
// Secret
`LLM_SECRET_NAME = "NEXUS-GPT4-API-KEY"`,
` <UserSecretsId>79a3edd0-2092-40a2-a04d-dcb46d5ca9ed</UserSecretsId>`,
`secret_length = X25519.secret_length`,
`secretSize must be >= XXH3_SECRET_SIZE_MIN`,
`# get build time secret for authentication
#RUN --mount=type=secret,id=jfrog_secret \
# JFROG_SECRET = $(cat /run/secrets/jfrog_secret) && \`,
// Token
` access_token_url='https://github.com/login/oauth/access_token',`,
`publicToken = "9Cnzj4p4WGeKLs1Pt8QuKUpRKfFLfRYC9AIKjbJTWit"`,
`<SourceFile SourceLocation="F:\Extracts\" TokenFile="RTL_INST_CODE.cer">`,
`notes = "Maven - io.jsonwebtoken:jjwt-jackson-0.11.2"`,
`csrf-token=Mj2qykJO5rELyHgezQ69nzUX0i3OH67V7+V4eUrLfpuyOuxmiW9rhROG/Whikle15syazJOkrjJa3U2AbhIvUw==`,
// TODO: `TOKEN_AUDIENCE = "25872395-ed3a-4703-b647-22ec53f3683c"`,
// General
`clientId = "73082700-1f09-405b-80d0-3131bfd6272d"`,
`GITHUB_API_KEY=
DYNATRACE_API_KEY=`,
`snowflake.password=
jdbc.snowflake.url=`,
`import { chain_Anvil1_Key, chain_Anvil2_Key } from '../blockchain-tests/pallets/supported-chains/consts';`,
// Yocto/BitBake
`SRCREV_moby = "43fc912ef59a83054ea7f6706df4d53a7dea4d80"`,
`LIC_FILES_CHKSUM = "file://${WORKDIR}/license.html;md5=5c94767cedb5d6987c902ac850ded2c6"`,
}
return utils.Validate(r, tps, fps)
}
func newPlausibleSecret(regex string) string {
allowList := &config.Allowlist{StopWords: DefaultStopWords}
// attempt to generate a random secret,
// retrying until it contains at least one digit and no stop words
// TODO: currently the DefaultStopWords list contains many short words,
// so there is a significant chance of generating a secret that contains a stop word
for {
secret := secrets.NewSecret(regex)
if !regexp.MustCompile(`[1-9]`).MatchString(secret) {
continue
}
if ok, _ := allowList.ContainsStopWord(secret); ok {
continue
}
return secret
}
}
+111
View File
@@ -0,0 +1,111 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
var githubAllowlist = []*config.Allowlist{
{
Paths: []*regexp.Regexp{
// https://github.com/octokit/auth-token.js/?tab=readme-ov-file#createtokenauthtoken-options
regexp.MustCompile(`(?:^|/)@octokit/auth-token/README\.md$`),
},
},
}
func GitHubPat() *config.Rule {
// define rule
r := config.Rule{
RuleID: "github-pat",
Description: "Uncovered a GitHub Personal Access Token, potentially leading to unauthorized repository access and sensitive content exposure.",
Regex: regexp.MustCompile(`ghp_[0-9a-zA-Z]{36}`),
Entropy: 3,
Keywords: []string{"ghp_"},
Allowlists: githubAllowlist,
}
// validate
tps := utils.GenerateSampleSecrets("github", "ghp_"+secrets.NewSecret(utils.AlphaNumeric("36")))
fps := []string{
"ghp_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
}
return utils.Validate(r, tps, fps)
}
func GitHubFineGrainedPat() *config.Rule {
// define rule
r := config.Rule{
RuleID: "github-fine-grained-pat",
Description: "Found a GitHub Fine-Grained Personal Access Token, risking unauthorized repository access and code manipulation.",
Regex: regexp.MustCompile(`github_pat_\w{82}`),
Entropy: 3,
Keywords: []string{"github_pat_"},
}
// validate
tps := utils.GenerateSampleSecrets("github", "github_pat_"+secrets.NewSecret(utils.AlphaNumeric("82")))
fps := []string{
"github_pat_xxxxxxxxxxxxxxxxxxxxxx_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
}
return utils.Validate(r, tps, fps)
}
func GitHubOauth() *config.Rule {
// define rule
r := config.Rule{
RuleID: "github-oauth",
Description: "Discovered a GitHub OAuth Access Token, posing a risk of compromised GitHub account integrations and data leaks.",
Regex: regexp.MustCompile(`gho_[0-9a-zA-Z]{36}`),
Entropy: 3,
Keywords: []string{"gho_"},
}
// validate
tps := utils.GenerateSampleSecrets("github", "gho_"+secrets.NewSecret(utils.AlphaNumeric("36")))
fps := []string{
"gho_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
}
return utils.Validate(r, tps, fps)
}
func GitHubApp() *config.Rule {
// define rule
r := config.Rule{
RuleID: "github-app-token",
Description: "Identified a GitHub App Token, which may compromise GitHub application integrations and source code security.",
Regex: regexp.MustCompile(`(?:ghu|ghs)_[0-9a-zA-Z]{36}`),
Entropy: 3,
Keywords: []string{"ghu_", "ghs_"},
Allowlists: githubAllowlist,
}
// validate
tps := utils.GenerateSampleSecrets("github", "ghs_"+secrets.NewSecret(utils.AlphaNumeric("36")))
tps = append(tps, utils.GenerateSampleSecrets("github", "ghu_"+secrets.NewSecret(utils.AlphaNumeric("36")))...)
fps := []string{
"ghu_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
"ghs_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
}
return utils.Validate(r, tps, fps)
}
func GitHubRefresh() *config.Rule {
// define rule
r := config.Rule{
RuleID: "github-refresh-token",
Description: "Detected a GitHub Refresh Token, which could allow prolonged unauthorized access to GitHub services.",
Regex: regexp.MustCompile(`ghr_[0-9a-zA-Z]{36}`),
Entropy: 3,
Keywords: []string{"ghr_"},
}
// validate
tps := utils.GenerateSampleSecrets("github", "ghr_"+secrets.NewSecret(utils.AlphaNumeric("36")))
fps := []string{
"ghr_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
}
return utils.Validate(r, tps, fps)
}
+222
View File
@@ -0,0 +1,222 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
// overview with all GitLab tokens:
// https://docs.gitlab.com/ee/security/tokens/index.html#token-prefixes
func GitlabCiCdJobToken() *config.Rule {
r := config.Rule{
RuleID: "gitlab-cicd-job-token",
Description: "Identified a GitLab CI/CD Job Token, potential access to projects and some APIs on behalf of a user while the CI job is running.",
Regex: regexp.MustCompile(`glcbt-[0-9a-zA-Z]{1,5}_[0-9a-zA-Z_-]{20}`),
Entropy: 3,
Keywords: []string{"glcbt-"},
}
tps := utils.GenerateSampleSecrets("gitlab", "glcbt-"+secrets.NewSecret(utils.AlphaNumeric("5"))+"_"+secrets.NewSecret(utils.AlphaNumeric("20")))
return utils.Validate(r, tps, nil)
}
func GitlabDeployToken() *config.Rule {
r := config.Rule{
Description: "Identified a GitLab Deploy Token, risking access to repositories, packages and containers with write access.",
RuleID: "gitlab-deploy-token",
Regex: regexp.MustCompile(`gldt-[0-9a-zA-Z_\-]{20}`),
Entropy: 3,
Keywords: []string{"gldt-"},
}
tps := []string{
utils.GenerateSampleSecret("gitlab", "gldt-"+secrets.NewSecret(utils.AlphaNumeric("20"))),
}
return utils.Validate(r, tps, nil)
}
func GitlabFeatureFlagClientToken() *config.Rule {
r := config.Rule{
RuleID: "gitlab-feature-flag-client-token",
Description: "Identified a GitLab feature flag client token, risks exposing user lists and features flags used by an application.",
Regex: regexp.MustCompile(`glffct-[0-9a-zA-Z_\-]{20}`),
Entropy: 3,
Keywords: []string{"glffct-"},
}
tps := utils.GenerateSampleSecrets("gitlab", "glffct-"+secrets.NewSecret(utils.AlphaNumeric("20")))
return utils.Validate(r, tps, nil)
}
func GitlabFeedToken() *config.Rule {
r := config.Rule{
RuleID: "gitlab-feed-token",
Description: "Identified a GitLab feed token, risking exposure of user data.",
Regex: regexp.MustCompile(`glft-[0-9a-zA-Z_\-]{20}`),
Entropy: 3,
Keywords: []string{"glft-"},
}
tps := utils.GenerateSampleSecrets("gitlab", "glft-"+secrets.NewSecret(utils.AlphaNumeric("20")))
return utils.Validate(r, tps, nil)
}
func GitlabIncomingMailToken() *config.Rule {
r := config.Rule{
RuleID: "gitlab-incoming-mail-token",
Description: "Identified a GitLab incoming mail token, risking manipulation of data sent by mail.",
Regex: regexp.MustCompile(`glimt-[0-9a-zA-Z_\-]{25}`),
Entropy: 3,
Keywords: []string{"glimt-"},
}
tps := utils.GenerateSampleSecrets("gitlab", "glimt-"+secrets.NewSecret(utils.AlphaNumeric("25")))
return utils.Validate(r, tps, nil)
}
func GitlabKubernetesAgentToken() *config.Rule {
r := config.Rule{
RuleID: "gitlab-kubernetes-agent-token",
Description: "Identified a GitLab Kubernetes Agent token, risking access to repos and registry of projects connected via agent.",
Regex: regexp.MustCompile(`glagent-[0-9a-zA-Z_\-]{50}`),
Entropy: 3,
Keywords: []string{"glagent-"},
}
tps := utils.GenerateSampleSecrets("gitlab", "glagent-"+secrets.NewSecret(utils.AlphaNumeric("50")))
return utils.Validate(r, tps, nil)
}
func GitlabOauthAppSecret() *config.Rule {
r := config.Rule{
RuleID: "gitlab-oauth-app-secret",
Description: "Identified a GitLab OIDC Application Secret, risking access to apps using GitLab as authentication provider.",
Regex: regexp.MustCompile(`gloas-[0-9a-zA-Z_\-]{64}`),
Entropy: 3,
Keywords: []string{"gloas-"},
}
tps := utils.GenerateSampleSecrets("gitlab", "gloas-"+secrets.NewSecret(utils.AlphaNumeric("64")))
return utils.Validate(r, tps, nil)
}
func GitlabPat() *config.Rule {
r := config.Rule{
RuleID: "gitlab-pat",
Description: "Identified a GitLab Personal Access Token, risking unauthorized access to GitLab repositories and codebase exposure.",
Regex: regexp.MustCompile(`glpat-[\w-]{20}`),
Entropy: 3,
Keywords: []string{"glpat-"},
}
// validate
tps := utils.GenerateSampleSecrets("gitlab", "glpat-"+secrets.NewSecret(utils.AlphaNumeric("20")))
fps := []string{
"glpat-XXXXXXXXXXX-XXXXXXXX",
}
return utils.Validate(r, tps, fps)
}
func GitlabPatRoutable() *config.Rule {
r := config.Rule{
RuleID: "gitlab-pat-routable",
Description: "Identified a GitLab Personal Access Token (routable), risking unauthorized access to GitLab repositories and codebase exposure.",
Regex: regexp.MustCompile(`\bglpat-[0-9a-zA-Z_-]{27,300}\.[0-9a-z]{2}[0-9a-z]{7}\b`),
Entropy: 4,
Keywords: []string{"glpat-"},
}
// validate
tps := utils.GenerateSampleSecrets("gitlab", "glpat-"+secrets.NewSecret(utils.AlphaNumeric("27"))+"."+secrets.NewSecret(utils.AlphaNumeric("2"))+secrets.NewSecret(utils.AlphaNumeric("7")))
fps := []string{
"glpat-xxxxxxxx-xxxxxxxxxxxxxxxxxx.xxxxxxxxx",
}
return utils.Validate(r, tps, fps)
}
func GitlabPipelineTriggerToken() *config.Rule {
r := config.Rule{
RuleID: "gitlab-ptt",
Description: "Found a GitLab Pipeline Trigger Token, potentially compromising continuous integration workflows and project security.",
Regex: regexp.MustCompile(`glptt-[0-9a-f]{40}`),
Entropy: 3,
Keywords: []string{"glptt-"},
}
// validate
tps := utils.GenerateSampleSecrets("gitlab", "glptt-"+secrets.NewSecret(utils.Hex("40")))
fps := []string{
"glptt-xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
}
return utils.Validate(r, tps, fps)
}
func GitlabRunnerRegistrationToken() *config.Rule {
r := config.Rule{
RuleID: "gitlab-rrt",
Description: "Discovered a GitLab Runner Registration Token, posing a risk to CI/CD pipeline integrity and unauthorized access.",
Regex: regexp.MustCompile(`GR1348941[\w-]{20}`),
Entropy: 3,
Keywords: []string{"GR1348941"},
}
tps := utils.GenerateSampleSecrets("gitlab", "GR1348941"+secrets.NewSecret(utils.AlphaNumeric("20")))
fps := []string{
"GR134894112312312312312312312",
"GR1348941XXXXXXXXXXXXXXXXXXXX",
}
return utils.Validate(r, tps, fps)
}
func GitlabRunnerAuthenticationToken() *config.Rule {
r := config.Rule{
RuleID: "gitlab-runner-authentication-token",
Description: "Discovered a GitLab Runner Authentication Token, posing a risk to CI/CD pipeline integrity and unauthorized access.",
Regex: regexp.MustCompile(`glrt-[0-9a-zA-Z_\-]{20}`),
Entropy: 3,
Keywords: []string{"glrt-"},
}
tps := utils.GenerateSampleSecrets("gitlab", "glrt-"+secrets.NewSecret(utils.AlphaNumeric("20")))
return utils.Validate(r, tps, nil)
}
func GitlabRunnerAuthenticationTokenRoutable() *config.Rule {
r := config.Rule{
RuleID: "gitlab-runner-authentication-token-routable",
Description: "Discovered a GitLab Runner Authentication Token (Routable), posing a risk to CI/CD pipeline integrity and unauthorized access.",
Regex: regexp.MustCompile(`\bglrt-t\d_[0-9a-zA-Z_\-]{27,300}\.[0-9a-z]{2}[0-9a-z]{7}\b`),
Entropy: 4,
Keywords: []string{"glrt-"},
}
tps := utils.GenerateSampleSecrets("gitlab", "glrt-t"+secrets.NewSecret(utils.Numeric("1"))+"_"+secrets.NewSecret(utils.AlphaNumeric("27"))+"."+secrets.NewSecret(utils.AlphaNumeric("2"))+secrets.NewSecret(utils.AlphaNumeric("7")))
fps := []string{
"glrt-tx_xxxxxxxxxxxxxxxxxxxxxxxxxxx.xxxxxxxxx",
}
return utils.Validate(r, tps, fps)
}
func GitlabScimToken() *config.Rule {
r := config.Rule{
RuleID: "gitlab-scim-token",
Description: "Discovered a GitLab SCIM Token, posing a risk to unauthorized access for a organization or instance.",
Regex: regexp.MustCompile(`glsoat-[0-9a-zA-Z_\-]{20}`),
Entropy: 3,
Keywords: []string{"glsoat-"},
}
tps := utils.GenerateSampleSecrets("gitlab", "glsoat-"+secrets.NewSecret(utils.AlphaNumeric("20")))
return utils.Validate(r, tps, nil)
}
func GitlabSessionCookie() *config.Rule {
r := config.Rule{
RuleID: "gitlab-session-cookie",
Description: "Discovered a GitLab Session Cookie, posing a risk to unauthorized access to a user account.",
Regex: regexp.MustCompile(`_gitlab_session=[0-9a-z]{32}`),
Entropy: 3,
Keywords: []string{"_gitlab_session="},
}
// validate
tps := utils.GenerateSampleSecrets("gitlab", "_gitlab_session="+secrets.NewSecret(utils.AlphaNumeric("32")))
return utils.Validate(r, tps, nil)
}
+25
View File
@@ -0,0 +1,25 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func GitterAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "gitter-access-token",
Description: "Uncovered a Gitter Access Token, which may lead to unauthorized access to chat and communication services.",
Regex: utils.GenerateSemiGenericRegex([]string{"gitter"},
utils.AlphaNumericExtendedShort("40"), true),
Keywords: []string{
"gitter",
},
}
// validate
tps := utils.GenerateSampleSecrets("gitter", secrets.NewSecret(utils.AlphaNumericExtendedShort("40")))
return utils.Validate(r, tps, nil)
}
+25
View File
@@ -0,0 +1,25 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func GoCardless() *config.Rule {
// define rule
r := config.Rule{
RuleID: "gocardless-api-token",
Description: "Detected a GoCardless API token, potentially risking unauthorized direct debit payment operations and financial data exposure.",
Regex: utils.GenerateSemiGenericRegex([]string{"gocardless"}, `live_(?i)[a-z0-9\-_=]{40}`, true),
Keywords: []string{
"live_",
"gocardless",
},
}
// validate
tps := utils.GenerateSampleSecrets("gocardless", "live_"+secrets.NewSecret(utils.AlphaNumericExtended("40")))
return utils.Validate(r, tps, nil)
}
+80
View File
@@ -0,0 +1,80 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func GrafanaApiKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "grafana-api-key",
Description: "Identified a Grafana API key, which could compromise monitoring dashboards and sensitive data analytics.",
Regex: utils.GenerateUniqueTokenRegex(`eyJrIjoi[A-Za-z0-9]{70,400}={0,3}`, true),
Entropy: 3,
Keywords: []string{"eyJrIjoi"},
}
// validate
tps := utils.GenerateSampleSecrets("grafana-api-key", "eyJrIjoi"+secrets.NewSecret(utils.AlphaNumeric("70")))
return utils.Validate(r, tps, nil)
}
func GrafanaCloudApiToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "grafana-cloud-api-token",
Description: "Found a Grafana cloud API token, risking unauthorized access to cloud-based monitoring services and data exposure.",
Regex: utils.GenerateUniqueTokenRegex(`glc_[A-Za-z0-9+/]{32,400}={0,3}`, true),
Entropy: 3,
Keywords: []string{"glc_"},
}
// validate
tps := utils.GenerateSampleSecrets("grafana-cloud-api-token", "glc_"+secrets.NewSecret(utils.AlphaNumeric("32")))
tps = append(tps,
utils.GenerateSampleSecret("grafana-cloud-api-token",
"glc_"+
secrets.NewSecret(utils.AlphaNumeric("32"))),
`loki_key: glc_eyJvIjoiNzQ0NTg3IiwibiI7InN0YWlrLTQ3NTgzMC1obC13cml0ZS1oYW5kc29uJG9raSIsImsiOiI4M2w3cmdYUlBoMTUyMW1lMU023nl5UDUiLCJtIjp7IOIiOiJ1cyJ9fQ==`,
// TODO:
//` loki:
//endpoint: https://322137:glc_eyJvIjoiNzQ0NTg3IiwibiI7InN0YWlrLTQ3NTgzMC1obC13cml0ZS1oYW5kc29uJG9raSIsImsiOiI4M2w3cmdYUlBoMTUyMW1lMU023nl5UDUiLCJtIjp7IOIiOiJ1cyJ9fQ==@logs-prod4.grafana.net/loki/api/v1/push`,
)
fps := []string{
// Low entropy.
`glc_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx`,
` API_KEY="glc_111111111111111111111111111111111111111111="`,
// Invalid.
`static void GLC_CreateLightmapTextureArray(void);
static void GLC_CreateLightmapTexturesIndividual(void);
void GLC_UploadLightmap(int textureUnit, int lightmapnum);`,
`// Alias models
void GLC_StateBeginUnderwaterAliasModelCaustics(texture_ref base_texture, texture_ref caustics_texture)
{`,
}
return utils.Validate(r, tps, fps)
}
func GrafanaServiceAccountToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "grafana-service-account-token",
Description: "Discovered a Grafana service account token, posing a risk of compromised monitoring services and data integrity.",
Regex: utils.GenerateUniqueTokenRegex(`glsa_[A-Za-z0-9]{32}_[A-Fa-f0-9]{8}`, true),
Entropy: 3,
Keywords: []string{"glsa_"},
}
// validate
tps := utils.GenerateSampleSecrets("grafana-service-account-token", "glsa_"+secrets.NewSecret(utils.AlphaNumeric("32"))+"_"+secrets.NewSecret(utils.Hex("8")))
tps = append(tps,
`'Authorization': 'Bearer glsa_pITqMOBIfNH2KL4PkXJqmTyQl0D9QGxF_486f63e1'`,
)
fps := []string{
"glsa_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX_AAAAAAAA",
}
return utils.Validate(r, tps, fps)
}
+25
View File
@@ -0,0 +1,25 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func HarnessApiKey() *config.Rule {
// Define rule for Harness Personal Access Token (PAT) and Service Account Token (SAT)
r := config.Rule{
Description: "Identified a Harness Access Token (PAT or SAT), risking unauthorized access to a Harness account.",
RuleID: "harness-api-key",
Regex: regexp.MustCompile(`(?:pat|sat)\.[a-zA-Z0-9_-]{22}\.[a-zA-Z0-9]{24}\.[a-zA-Z0-9]{20}`),
Keywords: []string{"pat.", "sat."},
}
// Generate a sample secret for validation
tps := utils.GenerateSampleSecrets("harness", "pat."+secrets.NewSecret(utils.AlphaNumeric("22"))+"."+secrets.NewSecret(utils.AlphaNumeric("24"))+"."+secrets.NewSecret(utils.AlphaNumeric("20")))
tps = append(tps, utils.GenerateSampleSecrets("harness", "sat."+secrets.NewSecret(utils.AlphaNumeric("22"))+"."+secrets.NewSecret(utils.AlphaNumeric("24"))+"."+secrets.NewSecret(utils.AlphaNumeric("20")))...)
// validate the rule
return utils.Validate(r, tps, nil)
}
+58
View File
@@ -0,0 +1,58 @@
package rules
import (
"fmt"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func HashiCorpTerraform() *config.Rule {
// define rule
r := config.Rule{
RuleID: "hashicorp-tf-api-token",
Description: "Uncovered a HashiCorp Terraform user/org API token, which may lead to unauthorized infrastructure management and security breaches.",
Regex: regexp.MustCompile(`(?i)[a-z0-9]{14}\.(?-i:atlasv1)\.[a-z0-9\-_=]{60,70}`),
Entropy: 3.5,
Keywords: []string{"atlasv1"},
}
// validate
tps := utils.GenerateSampleSecrets("hashicorpToken", secrets.NewSecret(utils.Hex("14"))+".atlasv1."+secrets.NewSecret(utils.AlphaNumericExtended("60,70")))
tps = append(tps,
`#token = "hE1hlYILrSqpqh.atlasv1.ARjZuyzl33F71WR55s6ln5GQ1HWIwTDDH3MiRjz7OnpCfaCb1RCF5zGaSncCWmJdcYA"`,
)
fps := []string{
`token = "xxxxxxxxxxxxxx.atlasv1.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"`, // low entropy
}
return utils.Validate(r, tps, fps)
}
func HashicorpField() *config.Rule {
keywords := []string{"administrator_login_password", "password"}
// define rule
r := config.Rule{
RuleID: "hashicorp-tf-password",
Description: "Identified a HashiCorp Terraform password field, risking unauthorized infrastructure configuration and security breaches.",
Regex: utils.GenerateSemiGenericRegex(keywords, fmt.Sprintf(`"%s"`, utils.AlphaNumericExtended("8,20")), true),
Entropy: 2,
Path: regexp.MustCompile(`(?i)\.(?:tf|hcl)$`),
Keywords: keywords,
}
tps := map[string]string{
// Example from: https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs/resources/sql_server.html
"file.tf": "administrator_login_password = " + `"thisIsDog11"`,
// https://registry.terraform.io/providers/petoju/mysql/latest/docs
"file.hcl": "password = " + `"rootpasswd"`,
}
fps := map[string]string{
"file.tf": "administrator_login_password = var.db_password",
"file.hcl": `password = "${aws_db_instance.default.password}"`,
"unrelated.js": "password = " + `"rootpasswd"`,
}
return utils.ValidateWithPaths(r, tps, fps)
}
@@ -0,0 +1,67 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func VaultServiceToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "vault-service-token",
Description: "Identified a Vault Service Token, potentially compromising infrastructure security and access to sensitive credentials.",
Regex: utils.GenerateUniqueTokenRegex(`(?:hvs\.[\w-]{90,120}|s\.(?i:[a-z0-9]{24}))`, false),
Entropy: 3.5,
Keywords: []string{"hvs.", "s."},
Allowlists: []*config.Allowlist{
{
Regexes: []*regexp.Regexp{
// https://github.com/gitleaks/gitleaks/issues/1490#issuecomment-2334166357
regexp.MustCompile(`s\.[A-Za-z]{24}`),
},
},
},
}
// validate
tps := []string{
// Old
utils.GenerateSampleSecret("vault", secrets.NewSecret(`s\.[0-9][a-zA-Z0-9]{23}`)),
`token: s.ZC9Ecf4M5g9o34Q6RkzGsj0z`,
// New
utils.GenerateSampleSecret("vault", secrets.NewSecret(`hvs\.[0-9][\w\-]{89}`)),
`-vaultToken hvs.CAESIP2jTxc9S2K7Z6CtcFWQv7-044m_oSsxnPE1H3nF89l3GiYKHGh2cy5sQmlIZVNyTWJNcDRsYWJpQjlhYjVlb1cQh6PL8wEYAg"`, // longer than 100 chars
}
fps := []string{
// Old
` credentials: new AWS.SharedIniFileCredentials({ profile: '<YOUR_PROFILE>' })`, // word boundary start
`INFO 4 --- [ main] o.s.b.f.s.DefaultListableBeanFactory : Overriding bean definition for bean`, // word boundary end
`s.xxxxxxxxxxxxxxxxxxxxxxxx`, // low entropy
`s.THISSTRINGISALLUPPERCASE`, // uppercase
`s.thisstringisalllowercase`, // lowercase
`s.AcceptanceTimeoutSeconds `, // pascal-case
`s.makeKubeConfigController = args`, // camel-case
// New
`hvs.xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx`, // low entropy
}
return utils.Validate(r, tps, fps)
}
func VaultBatchToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "vault-batch-token",
Description: "Detected a Vault Batch Token, risking unauthorized access to secret management services and sensitive data.",
Regex: utils.GenerateUniqueTokenRegex(`hvb\.[\w-]{138,300}`, false),
Entropy: 4,
Keywords: []string{"hvb."},
}
// validate
tps := utils.GenerateSampleSecrets("vault", "hvb."+secrets.NewSecret(utils.AlphaNumericExtendedShort("138")))
tps = append(tps, `hvb.AAAAAQJgxDgqsGNorpoOR7hPZ5SU-ynBvCl764jyRP_fnX7WvkdkDzGjbLNGdPdtlY33Als2P36yDZueqzfdGw9RsaTeaYXSH7E4RYSWuRoQ9YRKIw8o7mDDY2ZcT3KOB7RwtW1w1FN2eDqcy_sbCjXPaM1iBVH-mqMSYRmRd2nb5D1SJPeBzIYRqSglLc31wUGN7xEzyrKUczqOKsIcybQA`) // gitleaks:allow
return utils.Validate(r, tps, nil)
}
+45
View File
@@ -0,0 +1,45 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func Heroku() *config.Rule {
// define rule
r := config.Rule{
Description: "Detected a Heroku API Key, potentially compromising cloud application deployments and operational security.",
RuleID: "heroku-api-key",
Regex: utils.GenerateSemiGenericRegex([]string{"heroku"}, utils.Hex8_4_4_4_12(), true),
Keywords: []string{"heroku"},
}
// validate
tps := utils.GenerateSampleSecrets("heroku", secrets.NewSecret(utils.Hex8_4_4_4_12()))
tps = append(tps,
`const HEROKU_KEY = "12345678-ABCD-ABCD-ABCD-1234567890AB"`, // gitleaks:allow
`heroku_api_key = "832d2129-a846-4e27-99f4-7004b6ad53ef"`, // gitleaks:allow
)
return utils.Validate(r, tps, nil)
}
func HerokuV2() *config.Rule {
// define rule
r := config.Rule{
Description: "Detected a Heroku API Key, potentially compromising cloud application deployments and operational security.",
RuleID: "heroku-api-key-v2",
Regex: utils.GenerateUniqueTokenRegex(`(HRKU-AA[0-9a-zA-Z_-]{58})`, false),
Entropy: 4,
Keywords: []string{"HRKU-AA"},
}
// validate
tps := utils.GenerateSampleSecrets("heroku", secrets.NewSecret(`\b(HRKU-AA[0-9a-zA-Z_-]{58})\b`))
tps = append(tps,
`const KEY = "HRKU-AAlQ1aVoHDujJ9QsDHdHlHO0hbzhoERRSO45ZQusSYHg_____w4_hLrAym_u""`,
`API_Key = "HRKU-AAy9Ppr_HD2pPuTyIiTYInO0hbzhoERRSO93ZQusSYHgaD7_WQ07FnF7L9FX"`,
)
return utils.Validate(r, tps, nil)
}
+26
View File
@@ -0,0 +1,26 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func HubSpot() *config.Rule {
// define rule
r := config.Rule{
Description: "Found a HubSpot API Token, posing a risk to CRM data integrity and unauthorized marketing operations.",
RuleID: "hubspot-api-key",
Regex: utils.GenerateSemiGenericRegex([]string{"hubspot"},
`[0-9A-F]{8}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{12}`, true),
Keywords: []string{"hubspot"},
}
// validate
tps := utils.GenerateSampleSecrets("hubspot", secrets.NewSecret(utils.Hex8_4_4_4_12()))
tps = append(tps,
`const hubspotKey = "12345678-ABCD-ABCD-ABCD-1234567890AB"`, // gitleaks:allow
)
return utils.Validate(r, tps, nil)
}
+116
View File
@@ -0,0 +1,116 @@
package rules
import (
"fmt"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
// Reference: https://huggingface.co/docs/hub/security-tokens
//
// Old tokens have the prefix `api_`, however, I am not sure it's worth detecting them as that would be high noise.
// https://huggingface.co/docs/api-inference/quicktour
func HuggingFaceAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "huggingface-access-token",
Description: "Discovered a Hugging Face Access token, which could lead to unauthorized access to AI models and sensitive data.",
Regex: utils.GenerateUniqueTokenRegex("hf_(?i:[a-z]{34})", false),
Entropy: 2,
Keywords: []string{
"hf_",
},
}
// validate
tps := utils.GenerateSampleSecrets("huggingface", "hf_"+secrets.NewSecret("[a-zA-Z]{34}"))
tps = append(tps,
`huggingface-cli login --token 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`,
`huggingface-cli login --token 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`,
`huggingface-cli login --token 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`,
`huggingface-cli login --token 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`,
`huggingface-cli login --token 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`,
`huggingface-cli login --token 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`,
`huggingface-cli login --token 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`,
`huggingface-cli login --token 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`,
`-H "Authorization: Bearer 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"`,
`DEV=1 HF_TOKEN=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 poetry run python app.py`,
`use_auth_token='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')`,
`CI_HUB_USER_TOKEN = "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"`,
`- Change line 5 and add your Hugging Face token, that is, instead of 'hf_token = "ADD_YOUR_HUGGING_FACE_TOKEN_HERE"', you will need to change it to something like'hf_token = "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"'`,
//TODO: ` " hf_token = \"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\"\n",`,
`# Not critical, only usable on the sandboxed CI instance.
TOKEN = "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"`,
` parser.add_argument("--hf_token", type=str, default='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', help="Hugging Face Access Token to access PyAnnote gated models")`,
)
fps := []string{
`- (id)hf_requiredCharacteristicTypesForDisplayMetadata;`,
`amazon.de#@#div[data-cel-widget="desktop-rhf_SponsoredProductsRemoteRHFSearchEXPSubsK2ClickPagination"]`,
` _kHMSymptomhf_generatedByHomeAppForDebuggingPurposesKey,`,
` #define OSCHF_DebugGetExpectedAverageCrystalAmplitude NOROM_OSCHF_DebugGetExpectedAverageCrystalAmplitude`,
` M_UINT (ServingCellPriorityParametersDescription_t, H_PRIO, 2, &hf_servingcellpriorityparametersdescription_h_prio),`,
`+HWI-ST565_0092:4:1101:5508:5860#ACTTGA/1
bb_eeeeegfgffhiiiiiiiiiiihiiiiicgafhf_eefghihhiiiifhifhhdhifhiiiihifdgdhggf\bbceceedbcd
@HWI-ST565_0092:4:1101:7621:5770#ACTTGA/1`,
`y{}x|~|}{~}}~|~}||~|{|{}{|~z{}{{|{||{|}|{}{~|y}vjoePbUBJ7&;"; <; :;?!!;<7%$IACa_ecghbfbaebejhahfbhf_ddbficghbgfbhhcghdghfhigiifhhehhdggcgfchf_fgcei^[[.40&54"5666 6`,
` change_dir(cwd)
subdirs = glob.glob('HF_CAASIMULIAComputeServicesBuildTime.HF*.Linux64')
if len(subdirs) == 1:`,
` os.environ.get("HF_AUTH_TOKEN",
"hf_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"),`,
`# HuggingFace API Token https://huggingface.co/settings/tokens
HUGGINGFACE_API_TOKEN=hf_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx,`,
}
return utils.Validate(r, tps, fps)
}
// Will be deprecated Aug 1st, 2023.
func HuggingFaceOrganizationApiToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "huggingface-organization-api-token",
Description: "Uncovered a Hugging Face Organization API token, potentially compromising AI organization accounts and associated data.",
Regex: utils.GenerateUniqueTokenRegex("api_org_(?i:[a-z]{34})", false),
Entropy: 2,
Keywords: []string{
"api_org_",
},
}
// validate
tps := utils.GenerateSampleSecrets("huggingface", "api_org_"+secrets.NewSecret("[a-zA-Z]{34}"))
tps = append(tps,
`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`,
"`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`",
`\'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'\`,
//TODO: `\"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\"`,
//TODO: `,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,`,
//TODO: `(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)`,
//TODO: `<foo>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</foo>`,
`def test_private_space(self):
hf_token = "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" # Intentionally revealing this key for testing purposes
io = gr.load(`,
`hf_token = "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" # Intentionally revealing this key for testing purposes`,
`"news_train_dataset = datasets.load_dataset('nlpHakdang/aihub-news30k', data_files = \"train_news_text.csv\", use_auth_token='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')\n",`,
`os.environ['HUGGINGFACEHUB_API_TOKEN'] = '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'`,
fmt.Sprintf("api_org_%s", secrets.NewSecret(`[a-zA-Z]{34}`)),
)
fps := []string{
`public static final String API_ORG_EXIST = "APIOrganizationExist";`,
`const api_org_controller = require('../../controllers/api/index').organizations;`,
`API_ORG_CREATE("https://qyapi.weixin.qq.com/cgi-bin/department/create?access_token=ACCESS_TOKEN"),`,
`def test_internal_api_org_inclusion_with_href(api_name, href, expected, monkeypatch, called_with):
monkeypatch.setattr("requests.sessions.Session.request", called_with)`,
` def _api_org_96726c78_4ae3_402f_b08b_7a78c6903d2a(self, method, url, body, headers):
body = self.fixtures.load("api_org_96726c78_4ae3_402f_b08b_7a78c6903d2a.xml")
return httplib.OK, body, headers, httplib.responses[httplib.OK]`,
`<p>You should see a token <code>hf_xxxxx</code> (old tokens are <code>api_XXXXXXXX</code> or <code>api_org_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX</code>).</p>`,
` From Hugging Face docs:
You should see a token hf_xxxxx (old tokens are api_XXXXXXXX or api_org_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx).
If you do not submit your API token when sending requests to the API, you will not be able to run inference on your private models.`,
}
return utils.Validate(r, tps, fps)
}
+42
View File
@@ -0,0 +1,42 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func InfracostAPIToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "infracost-api-token",
Description: "Detected an Infracost API Token, risking unauthorized access to cloud cost estimation tools and financial data.",
Regex: utils.GenerateUniqueTokenRegex(`ico-[a-zA-Z0-9]{32}`, false),
Entropy: 3,
Keywords: []string{"ico-"},
}
// validate
tps := utils.GenerateSampleSecrets("ico", "ico-"+secrets.NewSecret("[A-Za-z0-9]{32}"))
tps = append(tps,
` variable {
name = "INFRACOST_API_KEY"
secret_value = "ico-mlCr1Mn3SRcRiZMObUZOTHLcgtH2Lpgt"
is_secret = true
}`,
// TODO: New format with longer keys?
// ` headers = {
//'X-Api-Key': 'ico-EeDdSfctrmjD14f45f45te5gJ7l6lw4o6M36sXT62a6',
//'Content-Type': 'application/json',
//}`,
)
fps := []string{
// Low entropy
`ico-XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX`,
// Invalid
`http://assets.r7.com/assets/media_box_tv_tres_colunas/video_box.ico-7a388b69018576d24b59331fd60aab0c.png`,
`https://explosivelab.notion.site/Pianificazione-Nerdz-Ng-pubblico-1bc826ecc0994dd8915be97fc3489cde?pvs=74`,
`http://ece252-2.uwaterloo.ca:2540/image?q=gAAAAABdHkoqb9ZaJ3q4dlzEvTgG9WYwKcD9Aw7OUXeFicO-5M5IdNDjHBpKw7KBK3nCVqtuga4yzUaFEpJn8BqA1LzZprIJBw==`,
}
return utils.Validate(r, tps, fps)
}
+22
View File
@@ -0,0 +1,22 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func Intercom() *config.Rule {
// define rule
r := config.Rule{
Description: "Identified an Intercom API Token, which could compromise customer communication channels and data privacy.",
RuleID: "intercom-api-key",
Regex: utils.GenerateSemiGenericRegex([]string{"intercom"}, utils.AlphaNumericExtended("60"), true),
Keywords: []string{"intercom"},
}
// validate
tps := utils.GenerateSampleSecrets("intercom", secrets.NewSecret(utils.AlphaNumericExtended("60")))
return utils.Validate(r, tps, nil)
}
+31
View File
@@ -0,0 +1,31 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func Intra42ClientSecret() *config.Rule {
// define rule
r := config.Rule{
Description: "Found a Intra42 client secret, which could lead to unauthorized access to the 42School API and sensitive data.",
RuleID: "intra42-client-secret",
Regex: utils.GenerateUniqueTokenRegex(`s-s4t2(?:ud|af)-(?i)[abcdef0123456789]{64}`, false),
Entropy: 3,
Keywords: []string{
"intra",
"s-s4t2ud-",
"s-s4t2af-",
},
}
// validate
tps := []string{
"clientSecret := \"s-s4t2ud-" + secrets.NewSecret(utils.Hex("64")) + "\"",
"clientSecret := \"s-s4t2af-" + secrets.NewSecret(utils.Hex("64")) + "\"",
"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", // gitleaks:allow
"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", // gitleaks:allow
}
return utils.Validate(r, tps, nil)
}
+64
View File
@@ -0,0 +1,64 @@
package rules
import (
"fmt"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func JFrogAPIKey() *config.Rule {
keywords := []string{"jfrog", "artifactory", "bintray", "xray"}
// Define Rule
r := config.Rule{
// Human readable description of the rule
Description: "Found a JFrog API Key, posing a risk of unauthorized access to software artifact repositories and build pipelines.",
// Unique ID for the rule
RuleID: "jfrog-api-key",
// Regex capture group for the actual secret
// Regex used for detecting secrets. See regex section below for more details
Regex: utils.GenerateSemiGenericRegex(keywords, utils.AlphaNumeric("73"), true),
// Keywords used for string matching on fragments (think of this as a prefilter)
Keywords: keywords,
}
// validate
tps := []string{
fmt.Sprintf("--set imagePullSecretJfrog.password=%s", secrets.NewSecret(utils.AlphaNumeric("73"))),
}
return utils.Validate(r, tps, nil)
}
func JFrogIdentityToken() *config.Rule {
keywords := []string{"jfrog", "artifactory", "bintray", "xray"}
// Define Rule
r := config.Rule{
// Human readable description of the rule
Description: "Discovered a JFrog Identity Token, potentially compromising access to JFrog services and sensitive software artifacts.",
// Unique ID for the rule
RuleID: "jfrog-identity-token",
// Regex capture group for the actual secret
// Regex used for detecting secrets. See regex section below for more details
Regex: utils.GenerateSemiGenericRegex(keywords, utils.AlphaNumeric("64"), true),
// Keywords used for string matching on fragments (think of this as a prefilter)
Keywords: keywords,
}
// validate
tps := utils.GenerateSampleSecrets("jfrog", secrets.NewSecret(utils.AlphaNumeric("64")))
tps = append(tps, utils.GenerateSampleSecrets("artifactory", secrets.NewSecret(utils.AlphaNumeric("64")))...)
tps = append(tps, utils.GenerateSampleSecrets("bintray", secrets.NewSecret(utils.AlphaNumeric("64")))...)
tps = append(tps, utils.GenerateSampleSecrets("xray", secrets.NewSecret(utils.AlphaNumeric("64")))...)
tps = append(tps, fmt.Sprintf("\"artifactory\", \"%s\"", secrets.NewSecret(utils.AlphaNumeric("64"))))
return utils.Validate(r, tps, nil)
}
+194
View File
@@ -0,0 +1,194 @@
package rules
import (
b64 "encoding/base64"
"fmt"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func JWT() *config.Rule {
// define rule
r := config.Rule{
Description: "Uncovered a JSON Web Token, which may lead to unauthorized access to web applications and sensitive user data.",
RuleID: "jwt",
Regex: utils.GenerateUniqueTokenRegex(`ey[a-zA-Z0-9]{17,}\.ey[a-zA-Z0-9\/\\_-]{17,}\.(?:[a-zA-Z0-9\/\\_-]{10,}={0,2})?`, false),
Entropy: 3,
Keywords: []string{"ey"},
}
// validate
tps := utils.GenerateSampleSecrets("jwt", secrets.NewSecret(`ey[a-zA-Z0-9]{17,}\.ey[a-zA-Z0-9\/\\_-]{17,}\.(?:[a-zA-Z0-9\/\\_-]{10,}={0,2})?`))
tps = append(tps,
`eyJhbGciOieeeiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwic3ViZSI6IjEyMzQ1Njc4OTAiLCJuYW1lZWEiOiJKb2huIERvZSIsInN1ZmV3YWZiIjoiMTIzNDU2Nzg5MCIsIm5hbWVmZWF3ZnciOiJKb2huIERvZSIsIm5hbWVhZmV3ZmEiOiJKb2huIERvZSIsInN1ZndhZndlYWIiOiIxMjM0NTY3ODkwIiwibmFtZWZ3YWYiOiJKb2huIERvZSIsInN1YmZ3YWYiOiIxMjM0NTY3ODkwIiwibmFtZndhZSI6IkpvaG4gRG9lIiwiaWZ3YWZhYXQiOjE1MTYyMzkwMjJ9.a_5icKBDo-8EjUlrfvz2k2k-FYaindQ0DEYNrlsnRG0==`, // gitleaks:allow
`JWT := eyJhbGciOieeeiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwic3ViZSI6IjEyMzQ1Njc4OTAiLCJuYW1lZWEiOiJKb2huIERvZSIsInN1ZmV3YWZiIjoiMTIzNDU2Nzg5MCIsIm5hbWVmZWF3ZnciOiJKb2huIERvZSIsIm5hbWVhZmV3ZmEiOiJKb2huIERvZSIsInN1ZndhZndlYWIiOiIxMjM0NTY3ODkwIiwibmFtZWZ3YWYiOiJKb2huIERvZSIsInN1YmZ3YWYiOiIxMjM0NTY3ODkwIiwibmFtZndhZSI6IkpvaG4gRG9lIiwiaWZ3YWZhYXQiOjE1MTYyMzkwMjJ9.a_5icKBDo-8EjUlrfvz2k2k-FYaindQ0DEYNrlsnRG0`, // gitleaks:allow
`"access_token": "eyJhbGciOiJIUzUxMiIsInR5cCI6IkpXVCJ9.eyJhY2Nlc3NLZXkiOiJRMzFDVlMxUFNDSjRPVEsyWVZFTSIsImF0X2hhc2giOiI4amItZFE2OXRtZEVueUZaMUttNWhnIiwiYXVkIjoiZXhhbXBsZS1hcHAiLCJlbWFpbCI6ImFkbWluQGV4YW1wbGUuY29tIiwiZW1haWxfdmVyaWZpZWQiOnRydWUsImV4cCI6IjE1OTQ2MDAxODIiLCJpYXQiOjE1OTQ1ODkzODQsImlzcyI6Imh0dHA6Ly8xMjcuMC4wLjE6NTU1Ni9kZXgiLCJuYW1lIjoiYWRtaW4iLCJzdWIiOiJDaVF3T0dFNE5qZzBZaTFrWWpnNExUUmlOek10T1RCaE9TMHpZMlF4TmpZeFpqVTBOallTQld4dlkyRnMifQ.nrbzIJz99Om7TvJ04jnSTmhvlM7aR9hMM1Aqjp2ONJ1UKYCvegBLrTu6cYR968_OpmnAGJ8vkd7sIjUjtR4zbw"`, // gitleaks:allow
`https://dai2-playlistserver.aws.syncbak.com/cpl/20980038/dai2v5/1.0/7b2264657669636554797065223a387d/master.m3u8?access_token=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCIsImtpZCI6IkdyYXkyMDE2MDgyOSJ9.eyJtaWQiOiIyMDk4MDAzOCIsImNpZCI6MjE5MDMsInNpZCI6MTU4LCJtZDUiOiIwN2QxMmRjNjAwOTM2MGI0MmY3NjNkNTRiMWIwZjI1NCIsImlhdCI6MTY2MDkxMzU2MCwiZXhwIjoxNjkyNDQ5NTYwLCJpc3MiOiJTeW5jYmFrIChURykifQ.JrWVgwzIn_RcNuWhkzIjr1i4qjXU1v4n0KFrSzoTQvQ`, // gitleaks:allow `
`"SessionToken": "eyJhbGciOiJIUzUxMiIsInR5cCI6IkpXVCJ9.eyJhY2Nlc3NLZXkiOiI2TjJCQUxYN0VMTzgyN0RYUzNHSyIsImFjciI6IjAiLCJhdWQiOiJhY2NvdW50IiwiYXV0aF90aW1lIjoxNTY5OTEwNTUyLCJhenAiOiJhY2NvdW50IiwiZW1haWxfdmVyaWZpZWQiOmZhbHNlLCJleHAiOjE1Njk5MTQ1NTQsImlhdCI6MTU2OTkxMDk1NCwiaXNzIjoiaHR0cDovL2xvY2FsaG9zdDo4MDgxL2F1dGgvcmVhbG1zL2RlbW8iLCJqdGkiOiJkOTk4YTBlZS01NDk2LTQ4OWYtYWJlMi00ZWE5MjJiZDlhYWYiLCJuYmYiOjAsInBvbGljeSI6InJlYWR3cml0ZSIsInByZWZlcnJlZF91c2VybmFtZSI6Im5ld3VzZXIxIiwic2Vzc2lvbl9zdGF0ZSI6IjJiYTAyYTI2LWE5MTUtNDUxNC04M2M1LWE0YjgwYjc4ZTgxNyIsInN1YiI6IjY4ZmMzODVhLTA5MjItNGQyMS04N2U5LTZkZTdhYjA3Njc2NSIsInR5cCI6IklEIn0._UG_-ZHgwdRnsp0gFdwChb7VlbPs-Gr_RNUz9EV7TggCD59qjCFAKjNrVHfOSVkKvYEMe0PvwfRKjnJl3A_mBA",`, // gitleaks:allow
`2020/11/04 21:08:40 Access Token:
"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJ1c2VyX2lkIjoiYTAwYzI3ZDEtYjVhYS00NjU0LWFmMTYtYjExNzNkZTY1NjI5Iiwicm9sZXMiOlsiYWRtaW4iXSwiaWF0IjoxNjA0NTE2OTIwLCJleHAiOjE2MDQ1MTc4MjAsImp0aSI6IjYzNmVmMDc0LTE2MzktNGJhZi1hNGNiLTQ4ZDM4NGMxMzliYSIsImlzcyI6Im15YXBwIn0.T9B0zG0AHShO5JfQgrMQBlToH33KHgp8nLMPFpN6QmM"`, // gitleaks:allow
`"idToken": "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsImtpZCI6Ik56azVNREl5TVRnNFJqWTBORGswT0VJM1JrRXpORGN4UmtVMU1FWXdNemczT1VKQlFqRTBNZyJ9.eyJuaWNrbmFtZSI6InRlc3QtaW50ZXJhY3RpdmUtY2xpIiwibmFtZSI6IlRlc3RpbmcgSW50ZXJhY3RpdmUgQ2xpIiwicGljdHVyZSI6Imh0dHBzOi8vaW50ZXJhdGNpdmUuY2xpL3Rlc3RpbmcucG5nIiwidXBkYXRlZF9hdCI6IjIwMTktMDktMTZUMTU6MTg6NDMuOTk5WiIsImVtYWlsIjoidGVzdGluZ0BpbnRlcmFjdGl2ZS5jbGkiLCJlbWFpbF92ZXJpZmllZCI6dHJ1ZSwiaXNzIjoiaHR0cHM6Ly9zZXJ2ZXJsZXNzaW5jLmF1dGgwLmNvbS8iLCJzdWIiOiJ0ZXN0LWludGVyYWN0aXZlLWNsaSIsImF1ZCI6IlhYWFhYWFhYWFhYWFhYWFhYWFhYWFhYWFhYWFhYWFhYIiwiaWF0IjoxNTYwMDAwMDAwLCJleHAiOjMwMDAwMDAwMDB9.GcNQtWSxv9CHTABw-HIjYSvRxTEapDUDqIIWRGmz01XmShQxRGOHRuUg1NKU4w9MpOlB6txHKs8UWd2eZkzw_Z4QmIuLyAVhVklpWP2-xeysPLUyqVTgqAg8kgIUAwdKjmrdpQqHhGd-Q1BIX62-E-qKKx8prmADSw_hgmuvlMuSCa1ajCnfyUXycQxDmbFrvjd24lJER0FSpB2nWWW3KxZ_UBX-TuVmiEtRXg9GYeSv6oIU78PrIhYgJ0QjERRF1yAYamIXNRs-KZ7Z4YiFNC4uKzFH1524pZkS4Q0-pweIvBrrsjekz-vEYcbaVG1zAxDu_yNrYPk5phCy8MHTrQ",`, // gitleaks:allow
`TokenIssuer1WithAzp = "eyJhbGciOiJSUzI1NiIsImtpZCI6InRUX3c5TFJOclk3d0phbEdzVFlTdDdydXRaaTg2R3Z5YzBFS1I0Q2FRQXciLCJ0eXAiOiJKV1QifQ.eyJhenAiOiJiYXIiLCJleHAiOjQ3MzQxMjU0NTMsImlhdCI6MTU4MDUyNTQ1MywiaXNzIjoidGVzdC1pc3N1ZXItMUBpc3Rpby5pbyIsInN1YiI6InN1Yi0xIn0.SO4qjRJPYItkpGGpCDfEhaUfdthO8L9b_aawao4dJKyqqXN0uYdsJau_JZzyPQ1emAmJP7VyjwELrlszA6xV65na_O-eny23iwhEoroChQMpcr9DWqSUBUfpbHSPFAjUv38SUbQfLgar0HrMxQlTAzB0vyzn2g6-cukP469ZlOUmzvi9b4UpolTLp_WPgEHKjZw8CL56CcuJqBIKgfn0M7ta2bY_qx-UrsEW0CqnXol7vhXuDAfMeWZYKuDP8qc2VH1T6wpO2JnZ0EaNDuZfQLOWFYKsFGlaYcus9j462AfJQBSFQTbkIjkvKMK6aI_rMEesAnJr2eei1UYi14JYiQ"`, // gitleaks:allow
`eyJhbGciOiJSUzI1NiIsImtpZCI6IkRIRmJwb0lVcXJZOHQyenBBMnFYZkNtcjVWTzVaRXI0UnpIVV8tZW52dlEiLCJ0eXAiOiJKV1QifQ.eyJleHAiOjM1MzczOTExMDQsImdyb3VwcyI6WyJncm91cDEiLCJncm91cDIiXSwiaWF0IjoxNTM3MzkxMTA0LCJpc3MiOiJ0ZXN0aW5nQHNlY3VyZS5pc3Rpby5pbyIsInNjb3BlIjpbInNjb3BlMSIsInNjb3BlMiJdLCJzdWIiOiJ0ZXN0aW5nQHNlY3VyZS5pc3Rpby5pbyJ9.EdJnEZSH6X8hcyEii7c8H5lnhgjB5dwo07M5oheC8Xz8mOllyg--AHCFWHybM48reunF--oGaG6IXVngCEpVF0_P5DwsUoBgpPmK1JOaKN6_pe9sh0ZwTtdgK_RP01PuI7kUdbOTlkuUi2AO-qUyOm7Art2POzo36DLQlUXv8Ad7NBOqfQaKjE9ndaPWT7aexUsBHxmgiGbz1SyLH879f7uHYPbPKlpHU6P9S-DaKnGLaEchnoKnov7ajhrEhGXAQRukhDPKUHO9L30oPIr5IJllEQfHYtt6IZvlNUGeLUcif3wpry1R5tBXRicx2sXMQ7LyuDremDbcNy_iE76Upg`, // gitleaks:allow
`python examples/cli.py eyJhbGciOiJIUzI1NiJ9.eyJJc3N1ZXIiOiJJc3N1ZXIiLCJVc2VybmFtZSI6IkJhZFNlY3JldHMiLCJleHAiOjE1OTMxMzM0ODMsImlhdCI6MTQ2NjkwMzA4M30.ovqRikAo_0kKJ0GVrAwQlezymxrLGjcEiW_s3UJMMCo`, // gitleaks:allow
`"Authorization": "Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiJ1c2VybmFtZTpib2IifQ.HcfCW67Uda-0gz54ZWTqmtgJnZeNem0Q757eTa9EZuw"`, // gitleaks:allow
`"value": "Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE1ODk1ODU1NjN9.PtfDS1niGoZ7pV6kplI-_q1fVKLnknQ3IwcrLZhoVCU",`, // gitleaks:allow
`// authorization: 'eyJhbGciOiJIUzUxMiIsImlhdCI6MTU3Njk5Njc5OSwiZXhwIjoxNTg0ODU5MTk5fQ.eyJ1aWQiOjQ1NzQyN30.0ei5UE6OgLBzN2_IS7xUIbIfW_S1Wzl42q2UeusbboxuzvctO_4Mz6YRr6f0PBLUVZMETxt8F0_4-yqIJ3_kUQ',`, // gitleaks:allow
`eyJhbGciOiJSUzI1NiIsImtpZCI6IiJ9.eyJpc3MiOiJrdWJlcm5ldGVzL3NlcnZpY2VhY2NvdW50Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9uYW1lc3BhY2UiOiJrdWJlLXN5c3RlbSIsImt1YmVybmV0ZXMuaW8vc2VydmljZWFjY291bnQvc2VjcmV0Lm5hbWUiOiJpc3Rpby1jbmktdG9rZW4tcGpwYnciLCJrdWJlcm5ldGVzLmlvL3NlcnZpY2VhY2NvdW50L3NlcnZpY2UtYWNjb3VudC5uYW1lIjoiaXN0aW8tY25pIiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9zZXJ2aWNlLWFjY291bnQudWlkIjoiZmY2MDY0ODAtY2MxMC0xMWU4LTkxYzctMDAwYWY3MGE5YmE4Iiwic3ViIjoic3lzdGVtOnNlcnZpY2VhY2NvdW50Omt1YmUtc3lzdGVtOmlzdGlvLWNuaSJ9.0YHfuEwYn6tbtgy1YOhOjEtuQ8TnvmA_1RkuggfVGigMpCMGoOkIWwxpeDVXZm7dNwRmQVwLhchA3MeXz0QGRmStLa-VncedkmPOGSC-FyPvPybhZI53w3nhIVU3Vkh9_s-E2H2zFTwRQthxlDAlldNqEHpM9fINIVs0Z3bAogz2DYHwerSOtfZU-6d8b5nn73gnNhl6zBJ_0qg22SZjc6TrDYk--WwjUbU5_OIW6YxEmFnNVqfSeCrpg18IiJCsB0XRkixgu46Ev63jsrJ1vi41PVvBN79X7F-SiNNwTqwACRZvlX1zRw_GV7o4iPvnKn685WLOyMfoB5K6hSxrpQ`, // gitleaks:allow
`const TestKubernetesJWT_A = "eyJhbGciOiJSUzI1NiIsImtpZCI6IiJ9.eyJpc3MiOiJrdWJlcm5ldGVzL3NlcnZpY2VhY2NvdW50Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9uYW1lc3BhY2UiOiJkZWZhdWx0Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9zZWNyZXQubmFtZSI6ImFkbWluLXRva2VuLXFsejQyIiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9zZXJ2aWNlLWFjY291bnQubmFtZSI6ImFkbWluIiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9zZXJ2aWNlLWFjY291bnQudWlkIjoiNzM4YmMyNTEtNjUzMi0xMWU5LWI2N2YtNDhlNmM4YjhlY2I1Iiwic3ViIjoic3lzdGVtOnNlcnZpY2VhY2NvdW50OmRlZmF1bHQ6YWRtaW4ifQ.ixMlnWrAG7NVuTTKu8cdcYfM7gweS3jlKaEsIBNGOVEjPE7rtXtgMkAwjQTdYR08_0QBjkgzy5fQC5ZNyglSwONJ-bPaXGvhoH1cTnRi1dz9H_63CfqOCvQP1sbdkMeRxNTGVAyWZT76rXoCUIfHP4LY2I8aab0KN9FTIcgZRF0XPTtT70UwGIrSmRpxW38zjiy2ymWL01cc5VWGhJqVysmWmYk3wNp0h5N57H_MOrz4apQR4pKaamzskzjLxO55gpbmZFC76qWuUdexAR7DT2fpbHLOw90atN_NlLMY-VrXyW3-Ei5EhYaVreMB9PSpKwkrA4jULITohV-sxpa1LA"`, // gitleaks:allow
`string: grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer&assertion=eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJpc3MiOiJkZXYtdG8tYW5hbHl0aWMtYXBpLW1hYy10ZXN0QGRldnRvLTE3NTQxOS5pYW0uZ3NlcnZpY2VhY2NvdW50LmNvbSIsImF1ZCI6Imh0dHBzOi8vd3d3Lmdvb2dsZWFwaXMuY29tL29hdXRoMi92NC90b2tlbiIsImV4cCI6MTUxOTIyOTAxOSwiaWF0IjoxNTE5MjI4ODk5LCJzY29wZSI6Imh0dHBzOi8vd3d3Lmdvb2dsZWFwaXMuY29tL2F1dGgvYW5hbHl0aWNzLnJlYWRvbmx5In0.V8CSfSS7sKfoE5857jE9WDrGFHF1CyRr3cZpdUv9MjaaTcPRSLuNxB8yrxRP_7hNmlRgx_KdUzBgDJp3M_9tU4rZgFaIC7-bctvz_0rqbnMqSTniHYNGo7w__zO0bRaTpR3ILOfoxCQLcVC-tA4eCIMzRCznkY0VAaoLM7K-hnwQz6fCqSF31fmOwzAdVBPi5qnMETogh_7SiHn4WNUYI0FQf5SFLhcCbBZtORcbANe9hXp9po2P-VTBqs6u9dAZw5kZ2c1l5zbzrjYp5VcYl1XQFQTxP2zgMxhpX3k1UH9ObggOMUxvASyLbPZ7viOPKRlFxkAAHPTN2N1FYbpVeA`, // gitleaks:allow
`eyJhbGciOiJSUzI1NiIsImtpZCI6IlM1WGxrRnVIclJRaEVDbmg3cndZZFVTRTFpT0lfQzZsZ2NXbHZoOS1pbVUifQ.eyJpc3MiOiJrdWJlcm5ldGVzL3NlcnZpY2VhY2NvdW50Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9uYW1lc3BhY2UiOiJrdWJlcm5ldGVzLWRhc2hib2FyZCIsImt1YmVybmV0ZXMuaW8vc2VydmljZWFjY291bnQvc2VjcmV0Lm5hbWUiOiJhZG1pbi11c2VyLXRva2VuLWo1a3B2Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9zZXJ2aWNlLWFjY291bnQubmFtZSI6ImFkbWluLXVzZXIiLCJrdWJlcm5ldGVzLmlvL3NlcnZpY2VhY2NvdW50L3NlcnZpY2UtYWNjb3VudC51aWQiOiJiZTZjZmUwZS0yYzFhLTRkNTYtYmVkMC1jYWRmYjYxNzA1N2YiLCJzdWIiOiJzeXN0ZW06c2VydmljZWFjY291bnQ6a3ViZXJuZXRlcy1kYXNoYm9hcmQ6YWRtaW4tdXNlciJ9.LaBPEh6Qantd8tAc0X5DY9dDwUqZpxu38FHnp9TSJw-ghs3TsjrscFulUeEAtp2ng3ElLcU4SbNKPGJflF2dyW9Tmfn-Kt_6Jwq8HQ9GOCwAicEz0JVireHA7EWhATzuT56eO6MTe-2j5bpGnPQRJJtQ8AbtAN3nVK7RPjSzmc8Ppqx1z5i4oCGwiyRlGwqT-FkCtQLbQaQ4XmrASQoN4pJ_OBy5slztUhk32HdGP6pQx5c-nfei-of_4ij_fHrP0xEEfmVVvXqi9WKv1PLkQ3qTiSFDzv8M2sE4T6XmCGBbw7gyHzEGSpOAPZr00bX_YMCUvEF0lyP4YK696xWCBA`, // gitleaks:allow
`$ curl "http://admin:password@127.0.0.1:8080/api/v2/token"
{"access_token":"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOlsiQVBJIl0sImV4cCI6MTYxMzMzNTI2MSwianRpIjoiYzBrb2gxZmNkcnBjaHNzMGZwZmciLCJuYmYiOjE2MTMzMzQ2MzEsInBlcm1pc3Npb25zIjpbIioiXSwic3ViIjoiYUJ0SHUwMHNBUmxzZ29yeEtLQ1pZZWVqSTRKVTlXbThHSGNiVWtWVmc1TT0iLCJ1c2VybmFtZSI6ImFkbWluIn0.WiyqvUF-92zCr--y4Q_sxn-tPnISFzGZd_exsG-K7ME","expires_at":"2021-02-14T20:41:01Z"}`, // gitleaks:allow
`curl -H "Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhdWQiOlsiQVBJIl0sImV4cCI6MTYxMzMzNTI2MSwianRpIjoiYzBrb2gxZmNkcnBjaHNzMGZwZmciLCJuYmYiOjE2MTMzMzQ2MzEsInBlcm1pc3Npb25zIjpbIioiXSwic3ViIjoiYUJ0SHUwMHNBUmxzZ29yeEtLQ1pZZWVqSTRKVTlXbThHSGNiVWtWVmc1TT0iLCJ1c2VybmFtZSI6ImFkbWluIn0.WiyqvUF-92zCr--y4Q_sxn-tPnISFzGZd_exsG-K7ME" "http://127.0.0.1:8080/api/v2/dumpdata?output-data=1"`, // gitleaks:allow
`"authorization": "Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJyb2xlIjoiZ3Vlc3QiLCJzdWIiOiJZV3hwWTJVPSIsIm5iZiI6MTUxNDg1MTEzOSwiZXhwIjoxNjQxMDgxNTM5fQ.K5DnnbbIOspRbpCr2IKXE9cPVatGOCBrBQobQmBmaeU"`, // gitleaks:allow
`{"signatures": [ "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJmaWxlcyI6W3sibmFtZSI6Ii5tYW5pZmVzdCIsImhhc2giOiJjMjEzMTU0NGM3MTZhMjVhNWUzMWY1MDQzMDBmNTI0MGU4MjM1Y2FkYjlhNTdmMGJkMWI2ZjRiZDc0YjI2NjEyIiwiYWxnb3JpdGhtIjoiU0hBMjU2In0seyJuYW1lIjoicm9sZXMvYmluZGluZ3MvZGF0YS5qc29uIiwiaGFzaCI6IjQyY2ZlNjc2OGI1N2JiNWY3NTAzYzE2NWMyOGRkMDdhYzViODEzNTU0ZWJjODUwZjJjYzM1ODQzZTcxMzdiMWQifV0sImlhdCI6MTU5MjI0ODAyNywiaXNzIjoiSldUU2VydmljZSIsImtleWlkIjoibXlQdWJsaWNLZXkiLCJzY29wZSI6IndyaXRlIn0.ZjtUgXC6USwmhv4XP9gFH6MzZwpZrGpAL_2sTK1P-mg"]}`, // gitleaks:allow
`"id_token": "eyJ4NXQiOiJOVEF4Wm1NeE5ETXlaRGczTVRVMVpHTTBNekV6T0RKaFpXSTRORE5sWkRVMU9HRmtOakZpTVEiLCJraWQiOiJOVEF4Wm1NeE5ETXlaRGczTVRVMVpHTTBNekV6T0RKaFpXSTRORE5sWkRVMU9HRmtOakZpTVEiLCJhbGciOiJSUzI1NiJ9.eyJhdWQiOiJQb0VnWFA2dVZPNDVJc0VOUm5nRFhqNUF1NVlhIiwiYXpwIjoiUG9FZ1hQNnVWTzQ1SXNFTlJuZ0RYajVBdTVZYSIsImlzcyI6Imh0dHBzOlwvXC9sb2NhbGhvc3Q6OTQ0M1wvb2F1dGgyXC90b2tlbiIsImV4cCI6MTUzNDg5MTc3OCwiaWF0IjoxNTM0ODg4MTc4LCJqdGkiOiIxODQ0MzI5Yy1kNjVhLTQ4YTMtODIyOC05ZGY3M2ZlODNkNTYifQ.ELZ8ujk2Xp9xTGgMqnCa5ehuimaAPXWlSCW5QeBbTJIT4M5OB_2XEVIV6p89kftjUdKu50oiYe4SbfrxmLm6NGSGd2qxkjzJK3SRKqsrmVWEn19juj8fz1neKtUdXVHuSZu6ws_bMDy4f_9hN2Jv9dFnkoyeNT54r4jSTJ4A2FzN2rkiURheVVsc8qlm8O7g64Az-5h4UGryyXU4zsnjDCBKYk9jdbEpcUskrFMYhuUlj1RWSASiGhHHHDU5dTRqHkVLIItfG48k_fb-ehU60T7EFWH1JBdNjOxM9oN_yb0hGwOjLUyCUJO_Y7xcd5F4dZzrBg8LffFmvJ09wzHNtQ",`, // gitleaks:allow
` # The following default key is generated by the local Supabase start and doesn't change
- SUPABASE_SERVICE_ROLE_KEY=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJzdXBhYmFzZS1kZW1vIiwicm9sZSI6ImFub24iLCJleHAiOjE5ODM4MTI5OTZ9.CRXP1A7WOeoJeXxjNni43kdQwgnWNReilDMblYTn_I0`, // gitleaks:allow
`Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJhIjoxLCJiIjoyLCJjIjozfQ.hxhGCCCmGV9nT1slief1WgEsOsfdnlVizNrODxfh1M8`, // gitleaks:allow
`--header 'Authorization: Bearer eyJhbGciOiJIUzI1NiJ9.eyJhY3RvclR5cGUiOiJVU0VSIiwiYWN0b3JJZCI6ImRhdGFodWIiLCJ0eXBlIjoiUEVSU09OQUwiLCJ2ZXJzaW9uIjoiMSIsImV4cCI6MTY1MDY2MDY1NSwianRpIjoiM2E4ZDY3ZTItOTM5Yi00NTY3LWE0MjYtZDdlMDA1ZGU3NjJjIiwic3ViIjoiZGF0YWh1YiIsImlzcyI6ImRhdGFodWItbWV0YWRhdGEtc2VydmljZSJ9.pp_vW2u1tiiTT7U0nDF2EQdcayOMB8jatiOA8Je4JJA' \`, // gitleaks:allow
`"Cookie": "auth-token=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpZCI6NDIxMTEsImlzQWRtaW4iOmZhbHNlLCJnaXRodWJJZCI6ImR5ZXhwbG9kZSIsImFwcFJvbGVzIjpbInVzZXIiXSwicm9sZXMiOnsiNDciOiJzdHVkZW50IiwiNTYiOiJzdHVkZW50In0sImNvdXJzZXNSb2xlcyI6eyI0NyI6WyJzdHVkZW50Il0sIjU2IjpbInN0dWRlbnQiXX0sImNvdXJzZXMiOnsiNDciOnsibWVudG9ySWQiOm51bGwsInN0dWRlbnRJZCI6NjY3OTMsInJvbGVzIjpbInN0dWRlbnQiXX0sIjU2Ijp7Im1lbnRvcklkIjpudWxsLCJzdHVkZW50SWQiOjYzMzk4LCJyb2xlcyI6WyJzdHVkZW50Il19fSwiaWF0IjoxNjQ1MjA5NzI2LCJleHAiOjE2NDUzODI1MjZ9.btpYeSioEDUNMI6bAPqgu5zndA8XR5DT8P9U9kotOEA",`, // gitleaks:allow
`<li> <a class="cbtn btn-grad-s btn-shadow btn-width"
target="_blank"
href="https://demo.kuboard.cn/dashboard?k8sToken=eyJhbGciOiJSUzI1NiIsImtpZCI6InZ6SzVqZFNJOXZFMmxQSkhXamNBcFY4RU9FR0RvSUR5bzJIY0NwVG1zODQifQ.eyJpc3MiOiJrdWJlcm5ldGVzL3NlcnZpY2VhY2NvdW50Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9uYW1lc3BhY2UiOiJrdWJlLXN5c3RlbSIsImt1YmVybmV0ZXMuaW8vc2VydmljZWFjY291bnQvc2VjcmV0Lm5hbWUiOiJrdWJvYXJkLXZpZXdlci10b2tlbi0yOW40cyIsImt1YmVybmV0ZXMuaW8vc2VydmljZWFjY291bnQvc2VydmljZS1hY2NvdW50Lm5hbWUiOiJrdWJvYXJkLXZpZXdlciIsImt1YmVybmV0ZXMuaW8vc2VydmljZWFjY291bnQvc2VydmljZS1hY2NvdW50LnVpZCI6IjQzMWMwNmYyLTNiNTAtNGEyMy1hYjM1LTkyNDQwNTQ2NzFkZCIsInN1YiI6InN5c3RlbTpzZXJ2aWNlYWNjb3VudDprdWJlLXN5c3RlbTprdWJvYXJkLXZpZXdlciJ9.kgwTa6t00gNC0vgr6HOvCqkDghPcW-jVDg-_K6WLy97ppb9jvaqVz-AxXzF7mJqXnNetbJw-8-x_L3ogSsDlTKmRucao96VA2tPKxel8pM04J8MU0ZmYgWhTJelibbxmQK3jwGM4x32bckOOvmtumcXdsBRN0z1SZ1iu4H0VoaswhfoFS4ZJKoe61xyqoDhQx4RLCVJh_-Uctd5RCcPLWFEk-BHqC8vUTy8QcRst6RIIozQdTqsv7Xs6bH6dHrHFS--eVVTH2orQdm8znuUFhlqFOOjmCIMzIlaUQC_SO9URIGYOs0jrk27N9KC0HvQ5dLgFmwyNJ0Gu7cYi23NP1A">
在线演示</a></li>`, // gitleaks:allow
`eyJhbGciOiJSUzI1NiIsImtpZCI6IlM1WGxrRnVIclJRaEVDbmg3cndZZFVTRTFpT0lfQzZsZ2NXbHZoOS1pbVUifQ.eyJpc3MiOiJrdWJlcm5ldGVzL3NlcnZpY2VhY2NvdW50Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9uYW1lc3BhY2UiOiJrdWJlcm5ldGVzLWRhc2hib2FyZCIsImt1YmVybmV0ZXMuaW8vc2VydmljZWFjY291bnQvc2VjcmV0Lm5hbWUiOiJhZG1pbi11c2VyLXRva2VuLWo1a3B2Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9zZXJ2aWNlLWFjY291bnQubmFtZSI6ImFkbWluLXVzZXIiLCJrdWJlcm5ldGVzLmlvL3NlcnZpY2VhY2NvdW50L3NlcnZpY2UtYWNjb3VudC51aWQiOiJiZTZjZmUwZS0yYzFhLTRkNTYtYmVkMC1jYWRmYjYxNzA1N2YiLCJzdWIiOiJzeXN0ZW06c2VydmljZWFjY291bnQ6a3ViZXJuZXRlcy1kYXNoYm9hcmQ6YWRtaW4tdXNlciJ9.LaBPEh6Qantd8tAc0X5DY9dDwUqZpxu38FHnp9TSJw-ghs3TsjrscFulUeEAtp2ng3ElLcU4SbNKPGJflF2dyW9Tmfn-Kt_6Jwq8HQ9GOCwAicEz0JVireHA7EWhATzuT56eO6MTe-2j5bpGnPQRJJtQ8AbtAN3nVK7RPjSzmc8Ppqx1z5i4oCGwiyRlGwqT-FkCtQLbQaQ4XmrASQoN4pJ_OBy5slztUhk32HdGP6pQx5c-nfei-of_4ij_fHrP0xEEfmVVvXqi9WKv1PLkQ3qTiSFDzv8M2sE4T6XmCGBbw7gyHzEGSpOAPZr00bX_YMCUvEF0lyP4YK696xWCBA`, // gitleaks:allow
`eyJhbGciOiJSUzI1NiJ9.eyJ1c2VybmFtZSI6IlRlc3QiLCJsb2dnZWQtaW4tdXNlciI6eyJzY29wZWRQZXJtaXNzaW9uIjpbXSwicGVybWlzc2lvbnMiOlsiQS5hZG1pbl9jdXN0b21lcl9kZWxldGUiLCJBLm5vcm1hbF91c2VyX2FwcCIsIkEubm9ybWFsX3VzZXJfY29uZmlndXJhdGlvbiIsIkEubm9ybWFsX3VzZXJfd2VsY29tZV9jb250cm9scyIsIkEubm9ybWFsX3VzZXJfb3JkZXIiLCJBLm5vcm1hbF91c2VyX3NlYXJjaCIsIkEubm9ybWFsX3VzZXJfc2VhcmNoX3BjIiwiQS5ub3JtYWxfdXNlcl9zZWFyY2hfcHJpdmF0ZSIsIkEubm9ybWFsX3VzZXJfcHJpY2luZyIsIkEubm9ybWFsX3VzZXJfcHJpdmF0ZSIsIkEubm9ybWFsX3VzZXJfY29tbWVyY2lhbCIsIkEubm9ybWFsX3VzZXJfcGMiXSwibmFtZSI6WyJUZXN0Il0sIm1haWwiOlsiVGVzdEBleGFtcGxlLmNvbSJdLCJvcmdhbml6YXRpb24iOlsiWC1YeHh4eHguMTIzNCJdLCJsb2NhdGlvbiI6WyIxMjMyMSJdLCJ1bml0IjpbIjEwMyJdLCJjb3VudHJ5IjpbIkNOIl0sInVzZXJUeXBlIjoiZW1wbG95ZWUifSwiaWRlbnRpdHktaWQiOiJNb2NrIn0.EK5TbwsIgde3mT3n7NK2W7TCvpgQQLzshvPPANRQeUmKOv2AWbo_7vNEDTSkwUlaHRN3-dknv8F95p5MsGTzH6Uva8aOPJG6JdBIoYX_ud3aBN-hY1i2Xpf8pqjeINfY3_gDNAB9gdMznEej2uqhPwUXmZtcuWPdUCCeNqPJbRUAJeVXxLr_JtQzO2jmuwNY_YYp7KaEIANZwG1spvLuIGZ0HA03u8ye9c2lfqYcjgfIkjMrwgWPamR7joZOZPdQSO2EHrF7bUWMjRNY-FF5V7tOjEijkknE_nDq5THcEvx1seHYFdFNwy9LSSGGPVmZMKTKQ3UUlZZyBMXcOpOA9w`, // gitleaks:allow
// TODO: Detect newlines or escapes (\)?
// https://github.com/mongodb/mongo/blob/1960b792ade4e179ddc6113a3cd400e9492ca11d/src/mongo/crypto/README.JWT.md?plain=1#L115-L117
// TODO: Detect empty claims section?
// `eyJhbGciOiJFQ0RILUVTIiwiZW5jIjoiQTI1NkdDTSIsImVwayI6eyJrdHkiOiJFQyIsImNydiI6IlAtMzg0Iiwia2V5X29wcyI6W10sImV4dCI6dHJ1ZSwieCI6IllUcEY3bGtTc3JvZVVUVFdCb21LNzBTN0FhVTJyc0ptMURpZ1ZzbjRMY2F5eUxFNFBabldkYmFVcE9jQVV5a1ciLCJ5IjoiLU5pS3loUktjSk52Nm02Z0ZJUWc4cy1Xd1VXUW9uT3A5dkQ4cHpoa2tUU3U2RzFlU2FUTVlhZGltQ2Q4V0ExMSJ9LCJhcHUiOiIiLCJhcHYiOiIifQ`,
`String tokenWithNoneAlg = "eyJhbGciOiJub25lIn0.eyJzdWIiOiJ0ZXN0LXVzZXIifQ.";`, // gitleaks:allow
`# Req: Invoke-RestMethod -Uri 'http://localhost:8085/users' -Headers @{ 'X-API-KEY' = 'eyJhbGciOiJub25lIn0.eyJ1c2VybmFtZSI6Im1vcnR5Iiwic3ViIjoiMTIzIn0.' }`, // gitleaks:allow
)
fps := []string{}
return utils.Validate(r, tps, fps)
}
func JWTBase64() *config.Rule {
// define rule
r := config.Rule{
RuleID: "jwt-base64",
Description: "Detected a Base64-encoded JSON Web Token, posing a risk of exposing encoded authentication and data exchange information.",
Regex: regexp.MustCompile(
`\bZXlK(?:(?P<alg>aGJHY2lPaU)|(?P<apu>aGNIVWlPaU)|(?P<apv>aGNIWWlPaU)|(?P<aud>aGRXUWlPaU)|(?P<b64>aU5qUWlP)|(?P<crit>amNtbDBJanBi)|(?P<cty>amRIa2lPaU)|(?P<epk>bGNHc2lPbn)|(?P<enc>bGJtTWlPaU)|(?P<jku>cWEzVWlPaU)|(?P<jwk>cWQyc2lPb)|(?P<iss>cGMzTWlPaU)|(?P<iv>cGRpSTZJ)|(?P<kid>cmFXUWlP)|(?P<key_ops>clpYbGZiM0J6SWpwY)|(?P<kty>cmRIa2lPaUp)|(?P<nonce>dWIyNWpaU0k2)|(?P<p2c>d01tTWlP)|(?P<p2s>d01uTWlPaU)|(?P<ppt>d2NIUWlPaU)|(?P<sub>emRXSWlPaU)|(?P<svt>emRuUWlP)|(?P<tag>MFlXY2lPaU)|(?P<typ>MGVYQWlPaUp)|(?P<url>MWNtd2l)|(?P<use>MWMyVWlPaUp)|(?P<ver>MlpYSWlPaU)|(?P<version>MlpYSnphVzl1SWpv)|(?P<x>NElqb2)|(?P<x5c>NE5XTWlP)|(?P<x5t>NE5YUWlPaU)|(?P<x5ts256>NE5YUWpVekkxTmlJNkl)|(?P<x5u>NE5YVWlPaU)|(?P<zip>NmFYQWlPaU))[a-zA-Z0-9\/\\_+\-\r\n]{40,}={0,2}`),
Entropy: 2,
Keywords: []string{"zxlk"},
}
tps := generateTestValues()
fps := []string{
`-----BEGIN PGP PUBLIC KEY BLOCK-----
Version: GnuPG/MacGPG2 v2
Comment: GPGTools - https://gpgtools.org
mQENBFOrMNcBCAC+gLI4s3bUkobS5NpOQbWfjWXbqC0Ixpc5bZYDOvsmfstmswna
UWUXkRH9RONabzrAu4TGvW0f5DkC2fuWWHJhZWEccn+VE83+avMZN4/mzldSXPNX
A6F7+wHb1DjG+FCDcxMghkwDjGc16LOtZGufUo5iRQaC5pmNBOgDWdiObGPKOTEL
/uU8zLtKi2cibbkhRm22IGOzGyZMZN6zvEtPzlCp3eZEGMW0Ig+kbl6SaSDrSJNK
wElYcr/kJ9QF6CQ2iwZCGeL2jH5QaOi5uj1LXONpCd9nPeyDXc+Z20gXZiqkwRLc
IBPKza6hq/+4nwHBq8DNLv0W4xNC59jLbIhpABEBAAG0LEZyYW5rIE5vdGhhZnQg
PGZub3RoYWZ0QGFsdW1uaS5zdGFuZm9yZC5lZHU+iQE9BBMBCgAnBQJTqzDXAhsD
BQkHhh+ABQsJCAcDBRUKCQgLBRYCAwEAAh4BAheAAAoJECqYOYG1w7FJOr4IAK8x
ec4jbjd6jkKe0YJGdPzg6TM73ISV5VrUlJX7O3jgxHB4M8KIHN/8A/+ZxLk7WM96
iq0C8atWHkCkQBtNduWhzAFccQlpxrrb18T5/oItcrmX9Dx2H5WeIl4WAoqe0MTk
iMPv29RMMH9RJvXL0ihuuH4Z0VxV5nurI9QmGzG69QOzfP9qY1EfQEceO7OqXXvY
vvBEUbmWshLuHJ6tOQY5ib3+aLO7m+yJTgJ7s6DHBDqLhqJPW0g7jiJcrDhYXsoS
JMMhMdUhckeZfTXm1N3Dc+/t9/E8NZjdZ2q/ZZzvygC4mu0uihwBKFqoFvXCHRaW
Rf4uYxE+/Upna/mbXQi5AQ0EU6sw1wEIALSp9Cc4t/F2k+rwEfEMXihXLcLM9Dmh
ukz++kMSCSuq4QHE+I4rLda/lVSNJCXaXrGVkzJuzmpEeQFdhr6nLW9ZYhzK8FIc
YyfsYTQxXUVf5W4e/XfKNoG9lrwQd5XHxJTBJ57XjjoWJYPQ69NWH8622foOBpux
xewgR2LEFgl+ksu7aQL4cQif6D3dko3EiIf1t0LDBXxFEREFCg+vkDFsDIW5bdaI
mDYwewGj7dAPLuo0sx1We+uBxb+j30xw/ASDOBhO3ratQWs+4w2FC7gw7cuf0CJC
/hMEw8nloGsIbqBmAnLdlQBxkfFG9DqRBNdSUM8xI66F0eGaaPHJ/S8AEQEAAYkB
JQQYAQoADwUCU6sw1wIbDAUJB4YfgAAKCRAqmDmBtcOxSZvvB/4w6S5YZQUmDVYK
9HPOm49qWxGPd5dLHr2g388sJ4LDK98Q9oicHgf2R35OXTyqhv4kFJL3eukQ6oLW
QOqQKLRycrQUu7eSESAiVmJ1gbuXLAWJmvUABGSYzj3BjWQRexYW/MZ51XqNftF9
oOSAoFWrdqeJbHoxPTXIb6P8EWk4Ei2j2bSIfBBSbBMSB6Kfk9IjpISM8+97RS5o
6605rmM5MY1Lz8cq8AZIYJs/MnUCZrpQ0c9QSWrflHAeWAy6xMGfdSynbEExQ4z8
AIfKWMro74nRFbAnv/BzrF2R8uHmdE7T6q9ZZsAydlaxQbdmyhCeGAdw93CwAypb
vHVobJ8A
=mIC1
-----END PGP PUBLIC KEY BLOCK-----`,
}
return utils.Validate(r, tps, fps)
}
func generateTestValues() []string {
// Sample JWT from RFC-7519
jwtSuffix := ".eyJpc3MiOiJqb2UiLA0KICJleHAiOjEzMDA4MTkzODAsDQogImh0dHA6Ly9leGFtcGxlLmNvbS9pc19yb290Ijp0cnVlfQ.dBjftJeZ4CVP-mB92K27uhbUJU1p1r_wW1gFWFOEjXk"
// Validate known header parameters
// https://www.iana.org/assignments/jose/jose.xhtml
headers := map[string][]string{
"alg": {
`"ES256"`,
`"ES384"`,
`"ES512"`,
`"ECDH-ES"`,
`"HS256"`,
`"HS384"`,
`"HS512"`,
`"RS256"`,
`"RS384"`,
`"RS512"`,
`"PS256"`,
`"PS384"`, `"PS512"`,
`"none"`,
// Nonstandard
`"A128KW"`,
`"ECDH-ES+A256KW"`,
`"RSA-OAEP"`,
},
"apu": {`"Tx9qG69ZfodhRos-8qfhTPc6ZFnNUcgNDVdHqX1UR3s"`, `"RfXdxTfIzilWBzWWX3ovHBDzgDcLNy0BFJWSxa0dqnw"`},
"apv": {`"ZGlkOmVsZW06cm9wc3RlbjpFa"`, `"ZGlkOmtleTp6Nk1rak1TWWF1dU1neDlhekV5VW5UVzVvNWpGUmtiQnU1VDgzZjM5dU53bnNHbW0jejZMU29HdFpTclVNWnVkQWFnekVmWWY3azhqSFpjR0Q3OVNveDd2NHdDa0RLTlN3"`},
"aud": {`"https://vault.example.com"`, `"http://example.com"`},
"b64": {`true`, `false`},
"crit": {`["exp"]`},
"cty": {`"example"`, `"json"`},
"epk": {`{"crv":"X25519","kty":"OKP","x":"Tx9qG69ZfodhRos-8qfhTPc6ZFnNUcgNDVdHqX1UR3s"}`, `{"kty":"OKP","crv":"X25519","x":"RfXdxTfIzilWBzWWX3ovHBDzgDcLNy0BFJWSxa0dqnw"}`},
"enc": {`"A256GCM"`, `"A256CBC-HS512"`, `"A128CBC-HS256"`},
"jku": {`"https://c2id.com/jwks.json"`},
"jwk": {`{"crv":"P-256","kid":"DB2X:GSG2:72H3:AE3R:KCMI:Y77E:W7TF:ERHK:V5HR:JJ2Y:YMS6:HFGJ","kty":"EC","x":"jyr9-xZBorSC9fhqNsmfU_Ud31wbaZ-bVGz0HmySvbQ","y":"vkE6qZCCvYRWjSUwgAOvibQx_s8FipYkAiHS0VnAFNs"}`, `{"kty":"RSA","n":"jyTwiSJACtW_SW-aiihQS5Y5QR704zUwjhlevY0oK-y5wP7SlIc2hq2OPVRarCzjhOxZl2AQFzM5VCR7xRDcnIn9t_pl7Mgsnx9hKDS9yQ24YXzhQ4cMEVVuqwcHvXqPdWDSoCZ1ccMqiiPyBSNGQTXMPY5PBxMOR47XwOb4eNMOPqnzVio3MEtL2wphtEonP3MY6pxJJzzel04wSCRZ4n06reqwER3KwRFPnRpRxAgmSEot5IBLIT3jj-amT5sD7YoUDbPmLk23zgDBIhX88fkClilg1W-fUi1XxYZomEPGvV7OrE1yszt4YDPqKgjJT8t2JPy__1ri-8rZgSxn5Q","e":"AQAB"`},
"iss": {`"http://localhost:8087/realms/grafana"`, `"kubernetes/serviceaccount"`},
"iv": {`"zjJPRrj0TGez9JYkChTrB3iqKoDkiBhn"`, `"10PlAIteHLVABtt"`},
"kid": {`"my_key_id"`, `"did:example:123#zC1Rnuvw9rVa6E5TKF4uQVRuQuaCpVgB81Um2u17Fu7UK"`},
"key_ops": {`["sign"]`, `["decrypt"]`, `["encrypt"]`},
"kty": {`"EC"`, `"RSA"`},
"nonce": {`"Os_sBjfWzVZenwwjvLrwXA"`, `"LDDZAGcBuKYpuNlFTCxPYw"`},
"p2c": {`4096`, `1000`},
"p2s": {`"c_ORk4HSsqZD2LvVeCUHqg"`},
"ppt": {`"foo"`},
"sub": {`"project_path:my-group/my-project:ref_type:branch:ref:feature-branch-1"`, `"1234567890"`},
// I cannot find any real-world examples of the svt header
// and the RFC doesn't seem to explicitly state the content.
"svt": {``},
"tag": {`"h6mJqHn33oCsDd5X57MI-g"`},
"typ": {`"JWT"`, `"JWK"`, `"JSOE"`, `"JSON"`, `"plain"`},
"url": {`"https://example.com"`},
"use": {`"enc"`, `"sig"`},
"ver": {`"2"`, `"3"`},
"version": {`"2"`, `"3"`},
"x5c": {`["MIICmzCCAYMCBgF4HR7HNDANBgkqhkiG9w0BAQsFADARMQ8wDQYDVQQDDAZtYXN0ZXIwHhcNMjEwMzEwMTcwOTE5WhcNMzEwMzEwMTcxMDU5WjARMQ8wDQYDVQQDDAZtYXN0ZXIwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDCpLzXHp8i09R2HU5YJPyncC4tiAWWmaDrVZenqynWlWKOjIXb0Y5JoP3ET68u16Bf7mHQGc/u9rRvCw4A92HpJ15WyUSJ80YcK0gPTE0Woc1ZxdK3h4t9AoA8VSrROwQ77w/VAdGrrJ4bwkAVrFqSRpqAsW5XxV3/bU8YkVaG8mh0kuFf/5ib0vxdSkg+mz+ZCuIxQ5YN77kNaMecO19XuaBo7FsG9WjfCPxXYuajkuLgdptPgwTN4np70h0WjaSP/jhjL2ixf48w+27wFDP+ic+B/TCOtVa3fj1GPo6RLxHGU0Zh64jFhmvRM6E/kX7IQ+FJcOwp1VPA9/vMABopAgMBAAEwDQYJKoZIhvcNAQELBQADggEBALILq1Z4oQNJZEUt24VZcvknsWtQtvPxl3JNcBQgDR5/IMgl5VndRZ9OT56KUqrR5xRsWiCvh5Lgv4fUEzAAo9ToiPLub1SKP063zWrvfgi3YZ19bty0iXFm7l2cpQ3ejFV7WpcdLJE0lapFdPLo6QaRdgNu/1p4vbYg7zSK1fQ0OY5b3ajhAx/bhWlrN685owRbO5/r4rUOa6oo9l4Qn7jUxKUx4rcoe7zUM7qrpOPqKvn0DBp3n1/+9pOZXCjIfZGvYwP5NhzBDCkRzaXcJHlOqWzMBzyovVrzVmUilBcj+EsTYJs0gVXKzduX5zO6YWhFs23lu7AijdkxTY65YM0="]`},
"x5t": {`"IYIeevIT57t8ppUejM42Bqx6f3I"`},
"x5t#S256": {`"TuOrBy2NcTlFSWuZ8Kh8W8AjQagb4fnfP1SlKMO8-So"`},
"x5u": {`"https://tel.example.org/passport.cer"`},
"zip": {`"DEF"`},
}
var examples []string
for key, values := range headers {
for _, value := range values {
header := fmt.Sprintf(`{"%s":%s}`, key, value)
jwt := []byte(b64.RawURLEncoding.EncodeToString([]byte(header)) + jwtSuffix)
examples = append(examples, b64.StdEncoding.EncodeToString(jwt))
examples = append(examples, b64.RawStdEncoding.EncodeToString(jwt))
examples = append(examples, b64.URLEncoding.EncodeToString(jwt))
examples = append(examples, b64.RawURLEncoding.EncodeToString(jwt))
}
}
return examples
}
+25
View File
@@ -0,0 +1,25 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func KrakenAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "kraken-access-token",
Description: "Identified a Kraken Access Token, potentially compromising cryptocurrency trading accounts and financial security.",
Regex: utils.GenerateSemiGenericRegex([]string{"kraken"},
utils.AlphaNumericExtendedLong("80,90"), true),
Keywords: []string{
"kraken",
},
}
// validate
tps := utils.GenerateSampleSecrets("kraken", secrets.NewSecret(utils.AlphaNumericExtendedLong("80,90")))
return utils.Validate(r, tps, nil)
}
+463
View File
@@ -0,0 +1,463 @@
package rules
import (
"fmt"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
// KubernetesSecret validates if we detected a kubernetes secret which contains data!
func KubernetesSecret() *config.Rule {
// Only match basic variations of `kind: secret`, we don't want things like `kind: ExternalSecret`.
//language=regexp
kindPat := `\bkind:[ \t]*["']?\bsecret\b["']?`
// Only matches values (`key: value`) under `data:` that are:
// - valid base64 characters
// - longer than 10 characters (no "YmFyCg==")
//language=regexp
dataPat := `\bdata:(?s:.){0,100}?\s+([\w.-]+:(?:[ \t]*(?:\||>[-+]?)\s+)?[ \t]*(?:["']?[a-z0-9+/]{10,}={0,3}["']?|\{\{[ \t\w"|$:=,.-]+}}|""|''))`
// define rule
r := config.Rule{
RuleID: "kubernetes-secret-yaml",
Description: "Possible Kubernetes Secret detected, posing a risk of leaking credentials/tokens from your deployments",
Regex: regexp.MustCompile(fmt.Sprintf(
//language=regexp
`(?i)(?:%s(?s:.){0,200}?%s|%s(?s:.){0,200}?%s)`, kindPat, dataPat, dataPat, kindPat)),
Keywords: []string{
"secret",
},
// Kubernetes secrets are usually yaml files.
Path: regexp.MustCompile(`(?i)\.ya?ml$`),
Allowlists: []*config.Allowlist{
{
Regexes: []*regexp.Regexp{
// Ignore empty or placeholder values.
// variable: {{ .Values.Example }} (https://helm.sh/docs/chart_template_guide/variables/)
// variable: ""
// variable: ''
regexp.MustCompile(`[\w.-]+:(?:[ \t]*(?:\||>[-+]?)\s+)?[ \t]*(?:\{\{[ \t\w"|$:=,.-]+}}|""|'')`),
},
},
{
// Avoid overreach between directives.
RegexTarget: "match",
Regexes: []*regexp.Regexp{
regexp.MustCompile(`(kind:(?s:.)+\n---\n(?s:.)+\bdata:|data:(?s:.)+\n---\n(?s:.)+\bkind:)`),
},
},
},
}
// validate
tps := map[string]string{
"base64-characters.yaml": `
apiVersion: v1
kind: Secret
data:
password: AAAAAAAAAAC7hjsA+H3owFygUv4w5B67lcSx14zff9FCPADiNbSwYWgE+O7Dhiy5tkRecs21ljjofvebe6xsYlA4cVmght0=`,
"comment.yaml": `
apiVersion: v1
kind: Secret
metadata:
name: heketi-secret
namespace: default
data:
# base64 encoded password. E.g.: echo -n "mypassword" | base64
key: bXlwYXNzd29yZA==`,
// The "data"-key is before the identifier "kind: Secret"
"before-kubernetes.yaml": `apiVersion: v1
data:
extra: YWRtaW46cGFzc3dvcmQ=
kind: secret
metadata:
name: secret-sa-sample
annotations:
kubernetes.io/service-account.name: 'sa-name'`,
"before-kubernetes.yml": `apiVersion: v1
data:
password: UyFCXCpkJHpEc2I9
username: YWRtaW4=
kind: Secret
metadata:
creationTimestamp: '2022-06-28T17:44:13Z'
name: db-user-pass
namespace: default
type: Opaque`,
"before-comment.yml": `apiVersion: v1
data:
# the data is abbreviated in this example
password: UyFCXCpkJHpEc2I9
username: YWRtaW4=
kind: Secret
metadata:
creationTimestamp: '2022-06-28T17:44:13Z'
name: db-user-pass
namespace: default
type: Opaque`,
"before-quoted-1.yaml": `apiVersion: 'v1'
data:
extra: 'YWRtaW46cGFzc3dvcmQ='
kind: 'Secret'
metadata:
name: 'secret-sa-sample'
annotations:
kubernetes.io/service-account.name: 'sa-name'`,
"before-quoted-2.yaml": `apiVersion: "v1"
data:
extra: "YWRtaW46cGFzc3dvcmQ="
kind: "secret"
metadata:
name: "secret-sa-sample"
annotations:
kubernetes.io/service-account.name: "sa-name"`,
"before-multiline-literal.yaml": `apiVersion: v1
data:
.dockercfg: |
eyJhdXRocyI6eyJodHRwczovL2V4YW1wbGUvdjEvIjp7ImF1dGgiOiJvcGVuc2VzYW1lIn19fQo=
metadata:
name: secret-dockercfg
type: kubernetes.io/dockercfg
kind: Secret
`,
"before-multiline-folded.yaml": `apiVersion: v1
data:
.dockercfg: >
eyJhdXRocyI6eyJodHRwczovL2V4YW1wbGUvdjEvIjp7ImF1dGgiOiJvcGVuc2VzYW1lIn19fQo=
metadata:
name: secret-dockercfg
type: kubernetes.io/dockercfg
kind: Secret`,
// Sample Kubernetes Secret from https://kubernetes.io/docs/concepts/configuration/secret/
// The "data"-key is after the identifier "kind: Secret"
"after-kubernetes.yaml": `apiVersion: v1
kind: secret
data:
extra: YWRtaW46cGFzc3dvcmQ=
metadata:
name: secret-sa-sample
annotations:
kubernetes.io/service-account.name: 'sa-name'`,
"after-kubernetes.yml": `apiVersion: v1
kind: Secret
metadata:
name: ca-secret
type: Opaque
data:
ca.pem: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUR4RENDQXF5Z0F3SUJBZ0lVV3pqUDl5RUk0eHlRSnBzVHVERU4yV2ROaUFzd0RRWUpLb1pJaHZjTkFRRUwKQlFBd2FERUxNQWtHQTFVRUJoTUNWVk14RHpBTkJnTlZCQWdUQms5eVpXZHZiakVSTUE4R0ExVUVCeE1JVUc5eQpkR3hoYm1ReEV6QVJCZ05WQkFvVENrdDFZbVZ5Ym1WMFpYTXhDekFKQmdOVkJBc1RBa05CTVJNd0VRWURWUVFECkV3cExkV0psY201bGRHVnpNQjRYRFRFMk1EZ3hNVEUyTkRnd01Gb1hEVEl4TURneE1ERTJORGd3TUZvd2FERUwKTUFrR0ExVUVCaE1DVlZNeER6QU5CZ05WQkFnVEJrOXlaV2R2YmpFUk1BOEdBMVVFQnhNSVVHOXlkR3hoYm1ReApFekFSQmdOVkJBb1RDa3QxWW1WeWJtVjBaWE14Q3pBSkJnTlZCQXNUQWtOQk1STXdFUVlEVlFRREV3cExkV0psCmNtNWxkR1Z6TUlJQklqQU5CZ2txaGtpRzl3MEJBUUVGQUFPQ0FROEFNSUlCQ2dLQ0FRRUF3QkhNOGN6anc0Q1cKK05wbklhV012RzZlcVhtelNZT20vbHdaNUhOMnVLck9xaTNHYUUyTjFKd2tzcGRmMXNOUGFZMHdPR2xkbURIZgoxSnlyTW8rUFdLVUVjWko1WGE4Vm02d2I0MlpjczN3MEp5dlEzWFJjaDQyMFJRWGRKayszcmMybWRvSVRkL0lmCnZjWms0N0RzQTMrQU5QSUlSTzdWRmZpS1JNRFpTUDR1OThnVjI2eW1zbjc0TzFVKzNVUHR1TEFTVTFLck9FTk4KR01FWG0ydTJpdmVvbTJrbjFlZTZuM1hCR1o2bU52cUNPdWUxRXdza0gvWkhoUVh1UDgyV1U5dVk0aGVORnoyQwpBNmR0Q0Q0c3Z6eHc3ZFQ2cVhsV0ZIWUYrc3VLVDhXNkczd3NkOWxzV0ZVY0ZWL0lwaTVobEVaTWprNFNoY3RqCjdpYnlrRURKM1FJREFRQUJvMll3WkRBT0JnTlZIUThCQWY4RUJBTUNBUVl3RWdZRFZSMFRBUUgvQkFnd0JnRUIKL3dJQkFqQWRCZ05WSFE0RUZnUVVOdnhRZ3o5ZTNXS2VscU1KTmZXNE1KUHYzc0V3SHdZRFZSMGpCQmd3Rm9BVQpOdnhRZ3o5ZTNXS2VscU1KTmZXNE1KUHYzc0V3RFFZSktvWklodmNOQVFFTEJRQURnZ0VCQUp1TUhYUms1TEVyCmxET1p4Mm9aRUNQZ29reXMzSGJsM05oempXd2pncXdxNVN6a011V3QrUnVkdnRTK0FUQjFtTjRjYTN0eSt2bWcKT09heTkvaDZoditmSE5jZHpYdWR5dFZYZW1KN3F4ZFoxd25DUUcwdnpqOWRZY0xFSGpJWi94dU1jNlY3dnJ4YwpSc0preGp5aE01UXBmRHd0eVZKeGpkUmVBZ0huSyswTkNieHdtQ3cyRGIvOXpudm9LWGk4TEQwbkQzOFQxY3R3CmhmdGxwTmRoZXFNRlpEZXBuTUYwY2g2cHo5TFV5Mkh1cnhrV2dkWVNjY2VNU0hPTzBMcG4xeVVBMWczOTJhUjUKWk81Zm5KMW95Vm1LVWFCeDJCMndsSVlUSXlES1ZiMnY1UXNHbnYvRHVTMDZhcmVLTmsvTGpHRTRlMXlHOHJkcwpacnZHMzNvUmtEbz0KLS0tLS1FTkQgQ0VSVElGSUNBVEUtLS0tLQo=
`,
"after-comment.yml": `apiVersion: v1
kind: Secret
metadata:
creationTimestamp: '2022-06-28T17:44:13Z'
name: db-user-pass
namespace: default
type: Opaque
data:
# the data is abbreviated in this example
password: UyFCXCpkJHpEc2I9
username: YWRtaW4=
`,
"after-quoted-1.yaml": `apiVersion: 'v1'
kind: 'Secret'
data:
password: 'UyFCXCpkJHpEc2I9'
username: 'YWRtaW4='
metadata:
name: 'db-user-pass'
namespace: 'default'
type: 'Opaque'`,
"after-quoted-2.yaml": `apiVersion: "v1"
kind: "Secret"
data:
password: "UyFCXCpkJHpEc2I9"
username: "YWRtaW4="
metadata:
name: "db-user-pass"
namespace: "default"
type: "Opaque"`,
"after-multiline-literal.yaml": `apiVersion: v1
kind: Secret
metadata:
name: secret-dockercfg
type: kubernetes.io/dockercfg
data:
.dockercfg: |
eyJhdXRocyI6eyJodHRwczovL2V4YW1wbGUvdjEvIjp7ImF1dGgiOiJvcGVuc2VzYW1lIn19fQo=
`,
"after-multiline-folded.yaml": `apiVersion: v1
kind: Secret
metadata:
name: secret-dockercfg
type: kubernetes.io/dockercfg
data:
.dockercfg: >
eyJhdXRocyI6eyJodHRwczovL2V4YW1wbGUvdjEvIjp7ImF1dGgiOiJvcGVuc2VzYW1lIn19fQo=`,
}
fps := map[string]string{
"empty-quotes1.yml": `apiVersion: v1
kind: Secret
metadata:
name: registry-auth-data
type: Opaque
data:
htpasswd: ''
`,
"empty-quotes2.yml": `apiVersion: v1
kind: Secret
metadata:
name: registry-auth-data
type: Opaque
data:
htpasswd: ""
`,
"overly-permissive1.yaml": `apiVersion: v1
kind: Secret
metadata:
name: registry-auth-data
type: Opaque
data:
htpasswd: {{ htpasswd }}
---
apiVersion: v1
kind: ReplicationController`,
"overly-permissive2.yaml": `apiVersion: v1
kind: Secret
metadata:
labels:
k8s-app: kubernetes-dashboard
addonmanager.kubernetes.io/mode: EnsureExists
name: kubernetes-dashboard-csrf
namespace: kubernetes-dashboard
type: Opaque
data:
csrf: ""
---
apiVersion: v1
kind: Secret
metadata:
labels:
k8s-app: kubernetes-dashboard
addonmanager.kubernetes.io/mode: EnsureExists
name: kubernetes-dashboard-key-holder
namespace: kubernetes-dashboard
type: Opaque
`,
"overly-permissive3.yaml": ` kind: Secret
target:
name: mysecret
creationPolicy: Owner
---
kind: ConfigMap
data:
conversionStrategy: Default
decodingStrategy: None
key: secret/mysecret
property: foo
secretKey: foo`,
// https://github.com/gitleaks/gitleaks/issues/1644
"wrong-kind.yaml": `apiVersion: external-secrets.io/v1beta1
kind: ExternalSecret
metadata:
name: example
namespace: example-ns
spec:
refreshInterval: 15s
secretStoreRef:
name: example
kind: SecretStore
target:
name: mysecret
creationPolicy: Owner
data:
- remoteRef:
conversionStrategy: Default
decodingStrategy: None
key: secret/mysecret
property: foo
secretKey: foo
`,
"sopssecret.yaml": `apiVersion: isindir.github.com/v1alpha3
kind: SopsSecret
metadata:
name: app1-sopssecret
namespace: test
spec:
suspend: false
secretTemplates:
- name: ENC[AES256_GCM,data:W3PiZ6lD6bpfAdI=,iv:2qF98ZkchgfWF4tZo8fok6zY0ZLNRV3wFpl8n2iyC7I=,tag:FzoL+CZHkLEqfWKniRApBA==,type:str]
labels:
app: ENC[AES256_GCM,data:t9ujIQ==,iv:slZBpmKF+DOg/wVBWmq5iTqkRBZUMao0a3MdoxzJs3s=,tag:xJyhdJ4rn/cB/4mxHzmGig==,type:str]
stringData:
db-password: ENC[AES256_GCM,data:O+5l4g==,iv:c/dS4BCBMbnKsXYuzBuCuVQt8RV9bOv5HgdpL+iwmns=,tag:KkQfh6OymvCt4uC13p318g==,type:str]
sops:
kms: []
gcp_kms: []
azure_kv: []
hc_vault: []
lastmodified: '2021-10-21T10:56:37Z'
mac: ENC[AES256_GCM,data:Tl1V1PuI5tZ0Hu3qxxzpDNeKQkuW0g/x/Mlp1yM6HaBqDr+r2FukLdYSYqjjJ3A8g+YkpvMib50M7j0V7zoX9sgCvMKEg86pRsWtThv8n/L+bsjClVTqnhJ9nfYlaPOMlvggbiMOE5hXPIuVz8WXYoVYJ2cVNCd/GfwOraUmj7I=,iv:n7HVI13okfbW3FS/ZsJ2GNmibudxc/TlkLa3umQQ+vc=,tag:R4ikep1wlxlDWlODJqFHHw==,type:str]
pgp:
- created_at: '2021-10-21T10:56:37Z'
enc: |
-----BEGIN PGP MESSAGE-----
hQGMA3muqimBu2IIAQwAkhR19/6roLq06oaD12vqDMes3/8FweAHxa6TLKg+LRjp
2/ntiRJHPBP9DYYFZbkTo8lAmIdVF7KfGIqWgPm5JiNhqfVRhyGPCRgBE7+I8qH6
EML9Vo/76kJLHtIjs5rOg7OXgwwitaibs1q6uyVY8TuaGXYIOO1iwL9xVtbayIry
NMQd1tFcNb6Vb86Plqm+T1VnSOJMUvryxrLelx89UNM0ctepyVu6YY9jpBjV0QLJ
NqNkKAGIMv3RNa9bZHTwveo9T0oXtFnk5H33BxH0ky/DGpD+5Ch1YgbzbqVnr+Bm
RX0R/GRhS9IDInd+eiyVX6y3LR5di0fc8TuK43+96wTG+2+ck+lbMrkHYsL2UJNv
bAjlOWmIcL4UwGlEOj4EzwcEx+xP3dq57pJ+DasfNwVqps2Kk+ofodR7d6gx7ELH
UQmLypCtkRic9v8fVSA2vEL8hAlg9bT8tpHLhHMOwe228cL5dTzFD60RoP+ovRar
jIU59Pnu1bnM4pXWEVA20l4BzJ8Fd6gj3TfAg/7Mat+dnTaUwnPgRSybFn0ZZHMW
RJDBPkMGFfSGRDfLeD37d61mI31360/w/61LaVp1sdDYodBJCRZFA1YzbqZcxnDl
YRjRmpcVRnO+o72CnU/P
=V4l4
-----END PGP MESSAGE-----
fp: 73019E949C1D3C3D1BE8B718C7CD51A565AB592C
encrypted_suffix: Templates
version: 3.6.1`, // https://github.com/luca-iachini/argocd-test/blob/af0c8eaba270bc918108c8bc3b909f26a4fe995d/kustomize/base/app1/secrets.enc.yaml#L4
// The "data"-key is before the identifier "kind: Secret"
"before-min-length.yaml": `apiVersion: v1
data:
extra: YmFyCg==
kind: secret
metadata:
name: secret-sa-sample
annotations:
kubernetes.io/service-account.name: 'sa-name'`,
"before-template.yaml": `apiVersion: v1
data:
password: {{ .Values.Password }}
kind: secret
metadata:
name: secret-sa-sample
annotations:
kubernetes.io/service-account.name: 'sa-name'`,
"before-externalsecret1.yml": `apiVersion: 'kubernetes-client.io/v1'
metadata:
name: actions-exporter
namespace: github-actions-exporter
spec:
backendType: secretsManager
data:
- key: MySecretManagerKey
name: github_token
property: github_token
kind: ExternalSecret
`,
"before-externalsecret2.yml": `apiVersion: external-secrets.io/v1beta1
spec:
secretStoreRef:
kind: ClusterSecretStore
name: aws-secretsmanager
refreshInterval: 1h
target:
creationPolicy: Owner
data:
- secretKey: api-key
remoteRef:
key: my-secrets-manager-secret
metadata:
name: api-key
namespace: my-namespace
kind: ExternalSecret
`,
"before-sopssecret.yml": `apiVersion: isindir.github.com/v1alpha3
spec:
secretTemplates:
- name: my-secret-name-1
labels:
label1: value1
annotations:
key1: value1
data:
data-name1: ZGF0YS12YWx1ZTE=
data-nameM: ZGF0YS12YWx1ZU0=
kind: SopsSecret
metadata:
name: sopssecret-sample
`, // https://github.com/isindir/sops-secrets-operator/blob/8aaf8bb368dc841a2d57f251bd839f08216a9328/config/samples/isindir_v1alpha3_sopssecret.yaml#L4
// The "data"-key is after the identifier "kind: Secret"
"after-min-length.yaml": `apiVersion: v1
kind: secret
data:
extra: YmFyCg==
metadata:
name: secret-sa-sample
annotations:
kubernetes.io/service-account.name: 'sa-name'`,
"after-externalsecret1.yml": `apiVersion: 'kubernetes-client.io/v1'
kind: ExternalSecret
metadata:
name: actions-exporter
namespace: github-actions-exporter
spec:
backendType: secretsManager
data:
- key: MySecretManagerKey
name: github_token
property: github_token
- key: MySecretManagerKey`,
"after-externalsecret2.yml": `apiVersion: external-secrets.io/v1beta1
kind: ExternalSecret
metadata:
name: api-key
namespace: my-namespace
spec:
secretStoreRef:
kind: ClusterSecretStore
name: aws-secretsmanager
refreshInterval: 1h
target:
creationPolicy: Owner
data:
- secretKey: api-key
remoteRef:
key: my-secrets-manager-secret`,
"after-sopssecret.yml": `apiVersion: isindir.github.com/v1alpha3
kind: SopsSecret
metadata:
name: sopssecret-sample
spec:
secretTemplates:
- name: my-secret-name-0
labels:
label0: value0
labelK: valueK
annotations:
key0: value0
keyN: valueN
stringData:
data-name0: data-value0
data-nameL: data-valueL
- name: my-secret-name-1
labels:
label1: value1
annotations:
key1: value1
data:
data-name1: ZGF0YS12YWx1ZTE=
data-nameM: ZGF0YS12YWx1ZU0=`,
"after-empty-data.yaml": `apiVersion: v1
kind: Secret
metadata:
labels:
k8s-app: kubernetes-dashboard
addonmanager.kubernetes.io/mode: EnsureExists
name: kubernetes-dashboard-csrf
namespace: kubernetes-dashboard
type: Opaque
data:
csrf: ""
`,
}
return utils.ValidateWithPaths(r, tps, fps)
}
+41
View File
@@ -0,0 +1,41 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func KucoinAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "kucoin-access-token",
Description: "Found a Kucoin Access Token, risking unauthorized access to cryptocurrency exchange services and transactions.",
Regex: utils.GenerateSemiGenericRegex([]string{"kucoin"}, utils.Hex("24"), true),
Keywords: []string{
"kucoin",
},
}
// validate
tps := utils.GenerateSampleSecrets("kucoin", secrets.NewSecret(utils.Hex("24")))
return utils.Validate(r, tps, nil)
}
func KucoinSecretKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "kucoin-secret-key",
Description: "Discovered a Kucoin Secret Key, which could lead to compromised cryptocurrency operations and financial data breaches.",
Regex: utils.GenerateSemiGenericRegex([]string{"kucoin"}, utils.Hex8_4_4_4_12(), true),
Keywords: []string{
"kucoin",
},
}
// validate
tps := utils.GenerateSampleSecrets("kucoin", secrets.NewSecret(utils.Hex8_4_4_4_12()))
return utils.Validate(r, tps, nil)
}
+24
View File
@@ -0,0 +1,24 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func LaunchDarklyAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "launchdarkly-access-token",
Description: "Uncovered a Launchdarkly Access Token, potentially compromising feature flag management and application functionality.",
Regex: utils.GenerateSemiGenericRegex([]string{"launchdarkly"}, utils.AlphaNumericExtended("40"), true),
Keywords: []string{
"launchdarkly",
},
}
// validate
tps := utils.GenerateSampleSecrets("launchdarkly", secrets.NewSecret(utils.AlphaNumericExtended("40")))
return utils.Validate(r, tps, nil)
}
+38
View File
@@ -0,0 +1,38 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func LinearAPIToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "linear-api-key",
Description: "Detected a Linear API Token, posing a risk to project management tools and sensitive task data.",
Regex: regexp.MustCompile(`lin_api_(?i)[a-z0-9]{40}`),
Entropy: 2,
Keywords: []string{"lin_api_"},
}
// validate
tps := utils.GenerateSampleSecrets("linear", "lin_api_"+secrets.NewSecret(utils.AlphaNumeric("40")))
return utils.Validate(r, tps, nil)
}
func LinearClientSecret() *config.Rule {
// define rule
r := config.Rule{
RuleID: "linear-client-secret",
Description: "Identified a Linear Client Secret, which may compromise secure integrations and sensitive project management data.",
Regex: utils.GenerateSemiGenericRegex([]string{"linear"}, utils.Hex("32"), true),
Entropy: 2,
Keywords: []string{"linear"},
}
// validate
tps := utils.GenerateSampleSecrets("linear", secrets.NewSecret(utils.Hex("32")))
return utils.Validate(r, tps, nil)
}
+47
View File
@@ -0,0 +1,47 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func LinkedinClientID() *config.Rule {
// define rule
r := config.Rule{
RuleID: "linkedin-client-id",
Description: "Found a LinkedIn Client ID, risking unauthorized access to LinkedIn integrations and professional data exposure.",
Regex: utils.GenerateSemiGenericRegex([]string{"linked[_-]?in"}, utils.AlphaNumeric("14"), true),
Entropy: 2,
Keywords: []string{
"linkedin",
"linked_in",
"linked-in",
},
}
// validate
tps := utils.GenerateSampleSecrets("linkedin", secrets.NewSecret(utils.AlphaNumeric("14")))
return utils.Validate(r, tps, nil)
}
func LinkedinClientSecret() *config.Rule {
// define rule
r := config.Rule{
RuleID: "linkedin-client-secret",
Description: "Discovered a LinkedIn Client secret, potentially compromising LinkedIn application integrations and user data.",
Regex: utils.GenerateSemiGenericRegex([]string{
"linked[_-]?in",
}, utils.AlphaNumeric("16"), true),
Entropy: 2,
Keywords: []string{
"linkedin",
"linked_in",
"linked-in",
},
}
// validate
tps := utils.GenerateSampleSecrets("linkedin", secrets.NewSecret(utils.AlphaNumeric("16")))
return utils.Validate(r, tps, nil)
}
+43
View File
@@ -0,0 +1,43 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func LobPubAPIToken() *config.Rule {
// define rule
r := config.Rule{
Description: "Detected a Lob Publishable API Key, posing a risk of exposing mail and print service integrations.",
RuleID: "lob-pub-api-key",
Regex: utils.GenerateSemiGenericRegex([]string{"lob"}, `(test|live)_pub_[a-f0-9]{31}`, true),
Keywords: []string{
"test_pub",
"live_pub",
"_pub",
},
}
// validate
tps := utils.GenerateSampleSecrets("lob", "test_pub_"+secrets.NewSecret(utils.Hex("31")))
return utils.Validate(r, tps, nil)
}
func LobAPIToken() *config.Rule {
// define rule
r := config.Rule{
Description: "Uncovered a Lob API Key, which could lead to unauthorized access to mailing and address verification services.",
RuleID: "lob-api-key",
Regex: utils.GenerateSemiGenericRegex([]string{"lob"}, `(live|test)_[a-f0-9]{35}`, true),
Keywords: []string{
"test_",
"live_",
},
}
// validate
tps := utils.GenerateSampleSecrets("lob", "test_"+secrets.NewSecret(utils.Hex("35")))
return utils.Validate(r, tps, nil)
}
+35
View File
@@ -0,0 +1,35 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func LookerClientID() *config.Rule {
// define rule
r := config.Rule{
Description: "Found a Looker Client ID, risking unauthorized access to a Looker account and exposing sensitive data.",
RuleID: "looker-client-id",
Regex: utils.GenerateSemiGenericRegex([]string{"looker"}, utils.AlphaNumeric("20"), true),
Keywords: []string{"looker"},
}
// validate
tps := utils.GenerateSampleSecrets("looker", secrets.NewSecret(utils.AlphaNumeric("20")))
return utils.Validate(r, tps, nil)
}
func LookerClientSecret() *config.Rule {
// define rule
r := config.Rule{
Description: "Found a Looker Client Secret, risking unauthorized access to a Looker account and exposing sensitive data.",
RuleID: "looker-client-secret",
Regex: utils.GenerateSemiGenericRegex([]string{"looker"}, utils.AlphaNumeric("24"), true),
Keywords: []string{"looker"},
}
// validate
tps := utils.GenerateSampleSecrets("looker", secrets.NewSecret(utils.AlphaNumeric("24")))
return utils.Validate(r, tps, nil)
}
+32
View File
@@ -0,0 +1,32 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func MailChimp() *config.Rule {
// define rule
r := config.Rule{
RuleID: "mailchimp-api-key",
Description: "Identified a Mailchimp API key, potentially compromising email marketing campaigns and subscriber data.",
Regex: utils.GenerateSemiGenericRegex([]string{"MailchimpSDK.initialize", "mailchimp"}, utils.Hex("32")+`-us\d\d`, true),
Keywords: []string{
"mailchimp",
},
}
// validate
tps := utils.GenerateSampleSecrets("mailchimp", secrets.NewSecret(utils.Hex("32"))+"-us20")
tps = append(tps,
`mailchimp_api_key: cefa780880ba5f5696192a34f6292c35-us18`, // gitleaks:allow
`MAILCHIMPE_KEY = "b5b9f8e50c640da28993e8b6a48e3e53-us18"`, // gitleaks:allow
)
fps := []string{
// False Negative
`MailchimpSDK.initialize(token: 3012a5754bbd716926f99c028f7ea428-us18)`, // gitleaks:allow
}
return utils.Validate(r, tps, fps)
}
+58
View File
@@ -0,0 +1,58 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func MailGunPrivateAPIToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "mailgun-private-api-token",
Description: "Found a Mailgun private API token, risking unauthorized email service operations and data breaches.",
Regex: utils.GenerateSemiGenericRegex([]string{"mailgun"}, `key-[a-f0-9]{32}`, true),
Keywords: []string{
"mailgun",
},
}
// validate
tps := utils.GenerateSampleSecrets("mailgun", "key-"+secrets.NewSecret(utils.Hex("32")))
return utils.Validate(r, tps, nil)
}
func MailGunPubAPIToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "mailgun-pub-key",
Description: "Discovered a Mailgun public validation key, which could expose email verification processes and associated data.",
Regex: utils.GenerateSemiGenericRegex([]string{"mailgun"}, `pubkey-[a-f0-9]{32}`, true),
Keywords: []string{
"mailgun",
},
}
// validate
tps := utils.GenerateSampleSecrets("mailgun", "pubkey-"+secrets.NewSecret(utils.Hex("32")))
return utils.Validate(r, tps, nil)
}
func MailGunSigningKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "mailgun-signing-key",
Description: "Uncovered a Mailgun webhook signing key, potentially compromising email automation and data integrity.",
Regex: utils.GenerateSemiGenericRegex([]string{"mailgun"}, `[a-h0-9]{32}-[a-h0-9]{8}-[a-h0-9]{8}`, true),
Keywords: []string{
"mailgun",
},
}
// validate
tps := utils.GenerateSampleSecrets("mailgun", secrets.NewSecret(utils.Hex("32"))+"-00001111-22223333")
return utils.Validate(r, tps, nil)
}
+22
View File
@@ -0,0 +1,22 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func MapBox() *config.Rule {
// define rule
r := config.Rule{
Description: "Detected a MapBox API token, posing a risk to geospatial services and sensitive location data exposure.",
RuleID: "mapbox-api-token",
Regex: utils.GenerateSemiGenericRegex([]string{"mapbox"}, `pk\.[a-z0-9]{60}\.[a-z0-9]{22}`, true),
Keywords: []string{"mapbox"},
}
// validate
tps := utils.GenerateSampleSecrets("mapbox", "pk."+secrets.NewSecret(utils.AlphaNumeric("60"))+"."+secrets.NewSecret(utils.AlphaNumeric("22")))
return utils.Validate(r, tps, nil)
}
+24
View File
@@ -0,0 +1,24 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func MattermostAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "mattermost-access-token",
Description: "Identified a Mattermost Access Token, which may compromise team communication channels and data privacy.",
Regex: utils.GenerateSemiGenericRegex([]string{"mattermost"}, utils.AlphaNumeric("26"), true),
Keywords: []string{
"mattermost",
},
}
// validate
tps := utils.GenerateSampleSecrets("mattermost", secrets.NewSecret(utils.AlphaNumeric("26")))
return utils.Validate(r, tps, nil)
}
+21
View File
@@ -0,0 +1,21 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/config"
)
func MaxMindLicenseKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "maxmind-license-key",
Description: "Discovered a potential MaxMind license key.",
Regex: utils.GenerateUniqueTokenRegex(`[A-Za-z0-9]{6}_[A-Za-z0-9]{29}_mmk`, false),
Entropy: 4,
Keywords: []string{"_mmk"},
}
// validate
tps := utils.GenerateSampleSecrets("maxmind", `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`) // gitleaks:allow
return utils.Validate(r, tps, nil)
}
+29
View File
@@ -0,0 +1,29 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func Meraki() *config.Rule {
// define rule
r := config.Rule{
RuleID: "cisco-meraki-api-key",
Description: "Cisco Meraki is a cloud-managed IT solution that provides networking, security, and device management through an easy-to-use interface.",
Regex: utils.GenerateSemiGenericRegex([]string{`(?-i:[Mm]eraki|MERAKI)`}, `[0-9a-f]{40}`, false),
Entropy: 3,
Keywords: []string{"meraki"},
}
// validate
tps := utils.GenerateSampleSecrets("meraki", secrets.NewSecret(utils.Hex("40")))
fps := []string{
`meraki: aaaaaaaaaa1111111111bbbbbbbbbb2222222222`, // low entropy
`meraki-api-key: acdeFf05b1a6d4c890237bf08c5e6e8d2b4d0f2e`, // invalid case
`meraki: abdefghjk0123456789mnopqrstuvwx12345678`, // invalid character
`meraki_token = 5cb4a5f04cd412fe946667b17f0129ba17aeb2e0c7b5b7264efcebf7d022bfe2R21`, // invalid length
`ReactNativeCameraKit: f15a5a04b0f6dc6073e6db0296e6ef2d8b8d2522`,
}
return utils.Validate(r, tps, fps)
}
+50
View File
@@ -0,0 +1,50 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func MessageBirdAPIToken() *config.Rule {
// define rule
r := config.Rule{
Description: "Found a MessageBird API token, risking unauthorized access to communication platforms and message data.",
RuleID: "messagebird-api-token",
Regex: utils.GenerateSemiGenericRegex([]string{"message[_-]?bird"}, utils.AlphaNumeric("25"), true),
Keywords: []string{
"messagebird",
"message-bird",
"message_bird",
},
}
// validate
tps := utils.GenerateSampleSecrets("messagebird", secrets.NewSecret(utils.AlphaNumeric("25")))
tps = append(tps, utils.GenerateSampleSecrets("message-bird", secrets.NewSecret(utils.AlphaNumeric("25")))...)
tps = append(tps, utils.GenerateSampleSecrets("message_bird", secrets.NewSecret(utils.AlphaNumeric("25")))...)
return utils.Validate(r, tps, nil)
}
func MessageBirdClientID() *config.Rule {
// define rule
r := config.Rule{
Description: "Discovered a MessageBird client ID, potentially compromising API integrations and sensitive communication data.",
RuleID: "messagebird-client-id",
Regex: utils.GenerateSemiGenericRegex([]string{"message[_-]?bird"}, utils.Hex8_4_4_4_12(), true),
Keywords: []string{
"messagebird",
"message-bird",
"message_bird",
},
}
// validate
tps := utils.GenerateSampleSecrets("MessageBird", "12345678-ABCD-ABCD-ABCD-1234567890AB") // gitleaks:allow
tps = append(tps,
`const MessageBirdClientID = "12345678-ABCD-ABCD-ABCD-1234567890AB"`, // gitleaks:allow
)
return utils.Validate(r, tps, nil)
}
+25
View File
@@ -0,0 +1,25 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func NetlifyAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "netlify-access-token",
Description: "Detected a Netlify Access Token, potentially compromising web hosting services and site management.",
Regex: utils.GenerateSemiGenericRegex([]string{"netlify"},
utils.AlphaNumericExtended("40,46"), true),
Keywords: []string{
"netlify",
},
}
// validate
tps := utils.GenerateSampleSecrets("netlify", secrets.NewSecret(utils.AlphaNumericExtended("40,46")))
return utils.Validate(r, tps, nil)
}
+93
View File
@@ -0,0 +1,93 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func NewRelicUserID() *config.Rule {
// define rule
r := config.Rule{
RuleID: "new-relic-user-api-key",
Description: "Discovered a New Relic user API Key, which could lead to compromised application insights and performance monitoring.",
Regex: utils.GenerateSemiGenericRegex([]string{
"new-relic",
"newrelic",
"new_relic",
}, `NRAK-[a-z0-9]{27}`, true),
Keywords: []string{
"NRAK",
},
}
// validate
tps := utils.GenerateSampleSecrets("new-relic", "NRAK-"+secrets.NewSecret(utils.AlphaNumeric("27")))
return utils.Validate(r, tps, nil)
}
func NewRelicUserKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "new-relic-user-api-id",
Description: "Found a New Relic user API ID, posing a risk to application monitoring services and data integrity.",
Regex: utils.GenerateSemiGenericRegex([]string{
"new-relic",
"newrelic",
"new_relic",
}, utils.AlphaNumeric("64"), true),
Keywords: []string{
"new-relic",
"newrelic",
"new_relic",
},
}
// validate
tps := utils.GenerateSampleSecrets("new-relic", secrets.NewSecret(utils.AlphaNumeric("64")))
return utils.Validate(r, tps, nil)
}
func NewRelicBrowserAPIKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "new-relic-browser-api-token",
Description: "Identified a New Relic ingest browser API token, risking unauthorized access to application performance data and analytics.",
Regex: utils.GenerateSemiGenericRegex([]string{
"new-relic",
"newrelic",
"new_relic",
}, `NRJS-[a-f0-9]{19}`, true),
Keywords: []string{
"NRJS-",
},
}
// validate
tps := utils.GenerateSampleSecrets("new-relic", "NRJS-"+secrets.NewSecret(utils.Hex("19")))
return utils.Validate(r, tps, nil)
}
func NewRelicInsertKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "new-relic-insert-key",
Description: "Discovered a New Relic insight insert key, compromising data injection into the platform.",
Regex: utils.GenerateSemiGenericRegex([]string{
"new-relic",
"newrelic",
"new_relic",
}, `NRII-[a-z0-9-]{32}`, true),
Keywords: []string{
"NRII-",
},
}
// validate
tps := utils.GenerateSampleSecrets("new-relic", "NRII-"+secrets.NewSecret(utils.Hex("32")))
return utils.Validate(r, tps, nil)
}
+39
View File
@@ -0,0 +1,39 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/config"
)
func Notion() *config.Rule {
// Define the identifiers that match the Keywords
identifiers := []string{"ntn_"}
// Define the regex pattern for Notion API token
secretRegex := `ntn_[0-9]{11}[A-Za-z0-9]{32}[A-Za-z0-9]{3}`
regex := utils.GenerateUniqueTokenRegex(secretRegex, false)
r := config.Rule{
Description: "Notion API token",
RuleID: "notion-api-token",
Regex: regex,
Entropy: 4,
Keywords: identifiers,
}
// validate
tps := []string{
"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",
"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",
"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",
}
fps := []string{
"ntn_12345678901",
"ntn_123456789012345678901234567890123456789012345678901234567890",
"ntn_12345678901abc",
}
return utils.Validate(r, tps, fps)
}
+24
View File
@@ -0,0 +1,24 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func NPM() *config.Rule {
// define rule
r := config.Rule{
RuleID: "npm-access-token",
Description: "Uncovered an npm access token, potentially compromising package management and code repository access.",
Regex: utils.GenerateUniqueTokenRegex(`npm_[a-z0-9]{36}`, true),
Entropy: 2,
Keywords: []string{
"npm_",
},
}
// validate
tps := utils.GenerateSampleSecrets("npmAccessToken", "npm_"+secrets.NewSecret(utils.AlphaNumeric("36")))
return utils.Validate(r, tps, nil)
}
+48
View File
@@ -0,0 +1,48 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
func NugetConfigPassword() *config.Rule {
r := config.Rule{
Description: "Identified a password within a Nuget config file, potentially compromising package management access.",
RuleID: "nuget-config-password",
Regex: regexp.MustCompile(`(?i)<add key=\"(?:(?:ClearText)?Password)\"\s*value=\"(.{8,})\"\s*/>`),
Path: regexp.MustCompile(`(?i)nuget\.config$`),
Keywords: []string{"<add key="},
Entropy: 1,
Allowlists: []*config.Allowlist{
{
Regexes: []*regexp.Regexp{
// samples from https://learn.microsoft.com/en-us/nuget/reference/nuget-config-file
regexp.MustCompile(`33f!!lloppa`),
regexp.MustCompile(`hal\+9ooo_da!sY`),
// exclude environment variables
regexp.MustCompile(`^\%\S.*\%$`),
},
},
},
}
tps := map[string]string{
"nuget.config": `<add key="Password" value="CleartextPassword1" />`,
"Nuget.config": `<add key="ClearTextPassword" value="CleartextPassword1" />`,
"Nuget.Config": `<add key="ClearTextPassword" value="TestSourcePassword" />`,
"Nuget.COnfig": `<add key="ClearTextPassword" value="TestSource-Password" />`,
"Nuget.CONfig": `<add key="ClearTextPassword" value="TestSource%Password" />`,
"Nuget.CONFig": `<add key="ClearTextPassword" value="TestSource%Password%" />`,
}
fps := map[string]string{
"some.xml": `<add key="Password" value="CleartextPassword1" />`, // wrong filename
"nuget.config": `<add key="ClearTextPassword" value="XXXXXXXXXXX" />`, // low entropy
"Nuget.config": `<add key="ClearTextPassword" value="abc" />`, // too short
"Nuget.Config": `<add key="ClearTextPassword" value="%TestSourcePassword%" />`, // environment variable
"NUget.Config": `<add key="ClearTextPassword" value="33f!!lloppa" />`, // known sample
"NUGet.Config": `<add key="ClearTextPassword" value="hal+9ooo_da!sY" />`, // known sample
}
return utils.ValidateWithPaths(r, tps, fps)
}
+28
View File
@@ -0,0 +1,28 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func NytimesAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "nytimes-access-token",
Description: "Detected a Nytimes Access Token, risking unauthorized access to New York Times APIs and content services.",
Regex: utils.GenerateSemiGenericRegex([]string{
"nytimes", "new-york-times,", "newyorktimes"},
utils.AlphaNumericExtended("32"), true),
Keywords: []string{
"nytimes",
"new-york-times",
"newyorktimes",
},
}
// validate
tps := utils.GenerateSampleSecrets("nytimes", secrets.NewSecret(utils.AlphaNumeric("32")))
return utils.Validate(r, tps, nil)
}
@@ -0,0 +1,32 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func OctopusDeployApiKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "octopus-deploy-api-key",
Description: "Discovered a potential Octopus Deploy API key, risking application deployments and operational security.",
Regex: utils.GenerateUniqueTokenRegex(`API-[A-Z0-9]{26}`, false),
Entropy: 3,
Keywords: []string{"api-"},
}
// validate
tps := []string{
utils.GenerateSampleSecret("octopus", secrets.NewSecret(`API-[A-Z0-9]{26}`)),
`set apikey="API-ZNRMR7SL6L3ATMOIK7GKJDKLPY"`, // gitleaks:allow
}
fps := []string{
// Invalid start
`msgstr "GSSAPI-VIRHEKAPSELOINTIMERKKIJONO."`,
`https://sonarcloud.io/api/project_badges/measure?project=Garden-Coin_API-CalculadoraDeInvestimentos&metric=alert_status`,
`https://fog-ringer-f42.notion.site/API-BD80F56CDC1441E6BF6011AB6D852875`, // Invalid end
`<iframe src="./archive/gifs/api-c99e353f761d318322c853c03e.gif"> </iframe>`, // Wrong case
}
return utils.Validate(r, tps, fps)
}
+34
View File
@@ -0,0 +1,34 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func OktaAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "okta-access-token",
Description: "Identified an Okta Access Token, which may compromise identity management services and user authentication data.",
Regex: utils.GenerateSemiGenericRegex([]string{`(?-i:[Oo]kta|OKTA)`}, `00[\w=\-]{40}`, false),
Entropy: 4,
Keywords: []string{
"okta",
},
}
// validate
tps := utils.GenerateSampleSecrets("okta", secrets.NewSecret(`00[\w=\-]{40}`))
tps = append(tps,
`"oktaApiToken": "00ebObu4zSNkyc6dimLvUwq4KpTEop-PCEnnfSTpD3",`, // gitleaks:allow
` var OktaApiToken = "00fWkOjwwL9xiFd-Vfgm_ePATIRxVj852Iblbb1DS_";`, // gitleaks:allow
)
fps := []string{
`oktaKey = 00000000000000000000000000000000000TUVWXYZ`, // low entropy
`rookTable = 0023452Lllk2KqjLBvaxANWEgTd7bqjsxjo8aZj0wd`, // wrong case
}
return utils.Validate(r, tps, fps)
}
// TODO: Okta client secret?
+37
View File
@@ -0,0 +1,37 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func OpenAI() *config.Rule {
// define rule
r := config.Rule{
RuleID: "openai-api-key",
Description: "Found an OpenAI API Key, posing a risk of unauthorized access to AI services and data manipulation.",
Regex: utils.GenerateUniqueTokenRegex(`sk-(?:proj|svcacct|admin)-(?:[A-Za-z0-9_-]{74}|[A-Za-z0-9_-]{58})T3BlbkFJ(?:[A-Za-z0-9_-]{74}|[A-Za-z0-9_-]{58})\b|sk-[a-zA-Z0-9]{20}T3BlbkFJ[a-zA-Z0-9]{20}`, false),
Entropy: 3,
Keywords: []string{
"T3BlbkFJ",
},
}
// validate
tps := append(utils.GenerateSampleSecrets("openaiApiKey", "sk-"+secrets.NewSecret(utils.AlphaNumeric("20"))+"T3BlbkFJ"+secrets.NewSecret(utils.AlphaNumeric("20"))),
[]string{
"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",
"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",
"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",
"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",
"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",
"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",
"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",
"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",
"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",
}...)
return utils.Validate(r, tps, nil)
}
+37
View File
@@ -0,0 +1,37 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
"github.com/zricethezav/gitleaks/v8/regexp"
)
// OpenShift 4 user tokens are prefixed with `sha256~`.
// https://docs.redhat.com/en/documentation/openshift_container_platform/4.10/html-single/authentication_and_authorization/index#oauth-view-details-tokens_managing-oauth-access-tokens
func OpenshiftUserToken() *config.Rule {
r := config.Rule{
RuleID: "openshift-user-token",
Description: "Found an OpenShift user token, potentially compromising an OpenShift/Kubernetes cluster.",
// TODO: Do tokens vary in length or are they always 43?
Regex: regexp.MustCompile(`\b(sha256~[\w-]{43})(?:[^\w-]|\z)`),
Entropy: 3.5,
Keywords: []string{
"sha256~",
},
}
// validate
tps := utils.GenerateSampleSecrets("oc", secrets.NewSecret("sha256~[\\w-]{43}"))
tps = append(tps,
`Authorization: Bearer sha256~kV46hPnEYhCWFnB85r5NrprAxggzgb6GOeLbgcKNsH0`, // https://github.com/openshift/console/blob/edae2305e01c2e0e8c33727af720ef960088eee3/dynamic-demo-plugin/README.md?plain=1#L114
`oc login --token=sha256~ZBMKw9VAayhdnyANaHvjJeXDiGwA7Fsr5gtLKj3-eh- `, // https://github.com/IBM/tekton-tutorial-openshift/blob/2a97d22ba282accad50821bca069210ea89de706/docs/lab1/0_setup.md?plain=1#L85
"sha256~"+secrets.NewSecret(`[\w-]{43}`),
)
fps := []string{
`--set kraken.kubeconfig.token.token="sha256~XXXXXXXXXX_PUT_YOUR_TOKEN_HERE_XXXXXXXXXXXX" \`, // https://github.com/krkn-chaos/krkn/blob/f3933f0e6239824eb9b5c46ff0e5d503b8465d6a/docs/index.md?plain=1#L307
`oc login --token=sha256~_xxxxxx_xxxxxxxxxxxxxxxxxxxxxx-xxxxxxxxxx-X \
--server=https://api.${zone}.appuio.cloud:6443`,
}
return utils.Validate(r, tps, fps)
}
+27
View File
@@ -0,0 +1,27 @@
package rules
import (
"regexp"
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/config"
)
func PerplexityAPIKey() *config.Rule {
// Define Rule
r := config.Rule{
RuleID: "perplexity-api-key",
Description: "Detected a Perplexity API key, which could lead to unauthorized access to Perplexity AI services and data exposure.",
Regex: regexp.MustCompile(`\b(pplx-[a-zA-Z0-9]{48})(?:[\x60'"\s;]|\\[nr]|$|\b)`),
Keywords: []string{"pplx-"},
Entropy: 4.0,
}
// validate
tps := utils.GenerateSampleSecrets("perplexity", "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'")
fps := []string{
"PERPLEXITY_API_KEY=pplx-xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
}
return utils.Validate(r, tps, fps)
}
+61
View File
@@ -0,0 +1,61 @@
package rules
import (
"github.com/zricethezav/gitleaks/v8/cmd/generate/config/utils"
"github.com/zricethezav/gitleaks/v8/cmd/generate/secrets"
"github.com/zricethezav/gitleaks/v8/config"
)
func PlaidAccessID() *config.Rule {
// define rule
r := config.Rule{
RuleID: "plaid-client-id",
Description: "Uncovered a Plaid Client ID, which could lead to unauthorized financial service integrations and data breaches.",
Regex: utils.GenerateSemiGenericRegex([]string{"plaid"}, utils.AlphaNumeric("24"), true),
Entropy: 3.5,
Keywords: []string{
"plaid",
},
}
// validate
tps := utils.GenerateSampleSecrets("plaid", secrets.NewSecret(`[a-zA-Z0-9]{24}`))
return utils.Validate(r, tps, nil)
}
func PlaidSecretKey() *config.Rule {
// define rule
r := config.Rule{
RuleID: "plaid-secret-key",
Description: "Detected a Plaid Secret key, risking unauthorized access to financial accounts and sensitive transaction data.",
Regex: utils.GenerateSemiGenericRegex([]string{"plaid"}, utils.AlphaNumeric("30"), true),
Entropy: 3.5,
Keywords: []string{
"plaid",
},
}
// validate
tps := utils.GenerateSampleSecrets("plaid", secrets.NewSecret(utils.AlphaNumeric("30")))
return utils.Validate(r, tps, nil)
}
func PlaidAccessToken() *config.Rule {
// define rule
r := config.Rule{
RuleID: "plaid-api-token",
Description: "Discovered a Plaid API Token, potentially compromising financial data aggregation and banking services.",
Regex: utils.GenerateSemiGenericRegex([]string{"plaid"},
"access-(?:sandbox|development|production)-"+utils.Hex8_4_4_4_12(), true),
Keywords: []string{
"plaid",
},
}
// validate
tps := utils.GenerateSampleSecrets("plaid", secrets.NewSecret("access-(?:sandbox|development|production)-"+utils.Hex8_4_4_4_12()))
return utils.Validate(r, tps, nil)
}

Some files were not shown because too many files have changed in this diff Show More