class

Detector::Go::Cli

Inherits Detector < Reference < Object

Detects Go command-line applications: programs that parse argv / flags through the stdlib flag package or a CLI framework (cobra, urfave/cli, go-arg, go-flags, pflag, kong, kingpin, mitchellh/cli), or that index os.Args directly. Gates the Go CLI analyzer, which surfaces the argv / flag / env attack surface as cli:// endpoints.

Constants

ARGV_INDEX = /\bos\.Args\s*\[/

Direct argv indexing, e.g. os.Args[1].

BUILTIN_FLAG_USE = /\bflag\.(?:Parse|Args?|NArg|String(?:Var)?|Int(?:64)?(?:Var)?|Uint(?:64)?(?:Var)?|Bool(?:Var)?|Float64(?:Var)?|Duration(?:Var)?|Var)\s*\(/

A real call into the stdlib flag package (not just the bare token "flag", which appears in unrelated identifiers/comments).

CLI_LIBRARY_MARKER = Regex.union(CLI_LIBRARY_MARKERS)

Single-pass union of the library markers above. The any? includes? chain walked every non-CLI .go file nine times over.

CLI_LIBRARY_MARKERS = ["github.com/spf13/cobra", "github.com/urfave/cli", "github.com/alexflint/go-arg", "github.com/jessevdk/go-flags", "github.com/spf13/pflag", "github.com/alecthomas/kong", "github.com/mitchellh/cli", "github.com/alecthomas/kingpin", "gopkg.in/alecthomas/kingpin.v2"]

CLI framework import paths. Presence of any of these — in go.mod or a source import block — is a strong, unambiguous CLI signal.

FLAG_IMPORT = /"flag"/

The stdlib flag import line.

HTTP_LISTEN = /\b(?:http|fasthttp)\.ListenAndServe(?:TLS)?\s*\(|\.(?:ListenAndServe|RunTLS)\s*\(/

An HTTP listener: a file that uses the stdlib flag package for config AND serves HTTP is a web server, not a CLI, so the stdlib signals below don't qualify it (a real CLI framework, matched earlier, still does).

Class methods

tech_name

The tech name without needing an instance, so the registry can be read off the classes themselves rather than from a parallel list.

Source

Instance methods

applicable?(filename : String) : Bool

Cheap filename-only filter the detector pass uses to skip detect on files the detector cannot possibly match. The default true preserves prior behavior (every detector runs on every file). Override with the same predicate the body of detect starts with — e.g., filename.ends_with?(".py") for a Python framework detector — so the detector loop avoids the detect dispatch on files outside the detector's language.

On large codebases (saleor's 4255 .py files) this lifts ~100 virtual detect calls per file out of the hot loop because most detectors' inner first-line is exactly this kind of cheap filename check.

Source
detect(filename : String, file_contents : String) : Bool
Source
set_name
Source