Skip to content

kriskimmerle/vibeguard

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

2 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

vibeguard

Vibe-Coded Python Security Linter

Python 3.9+ License: MIT

Catches security antipatterns that AI code generators commonly introduce. AI has predictable failure modes that traditional linters like Bandit don't specifically target.

The Problem

AI-generated code has a ~25% rate of security flaws (DEV Community 2026). These aren't random bugs - AI makes predictable mistakes:

  • Using MD5/SHA1 for password hashing
  • Hardcoding secrets in obvious variable names
  • Using eval() on user input
  • SQL injection via f-strings
  • shell=True in subprocess calls
  • Non-constant-time password comparison
  • YAML deserialization without SafeLoader

Traditional linters catch some of these, but vibeguard focuses specifically on AI's failure patterns.

Installation

pip install vibeguard

Or run directly (zero dependencies):

curl -O https://raw.githubusercontent.com/kriskimmerle/vibeguard/main/vibeguard.py
python vibeguard.py app.py

Quick Start

# Scan a single file
vibeguard app.py

# Scan a directory
vibeguard src/

# CI mode - fail if score below 75
vibeguard . --check --min-score 75

# JSON output
vibeguard . --format json

# Ignore specific rules
vibeguard . --ignore VG16 --ignore VG03

Example Output

======================================================================
vibeguard - Vibe-Coded Python Security Linter
======================================================================
Files scanned: 5
Total findings: 4
Security Score: 55/100 (Grade: D)

Findings by severity:
  CRITICAL: 2
  HIGH: 1
  MEDIUM: 1

----------------------------------------------------------------------
📄 app.py

  🔴 Line 12: [VG01] CRITICAL
     Using hashlib.md5 for password hashing - use bcrypt, argon2, or scrypt instead
     Fix: Replace with: from passlib.hash import argon2; argon2.hash(password)

  🔴 Line 28: [VG06] CRITICAL
     SQL query using f-string - SQL injection vulnerability
     Fix: Use parameterized queries: cursor.execute('SELECT * FROM t WHERE id = ?', (id,))

  🟠 Line 45: [VG07] HIGH
     shell=True with subprocess - command injection risk
     Fix: Use shell=False with a list of arguments: subprocess.run(['cmd', 'arg1'])

======================================================================
⚠️  Security issues found - review and fix before deployment!

Detection Rules

Rule Severity Description
VG01 CRITICAL MD5/SHA1 used for password hashing
VG02 HIGH ECB mode in encryption (insecure)
VG03 HIGH Weak random (random module) for security
VG04 HIGH Hardcoded IV/salt/nonce
VG05 CRITICAL eval/exec/compile usage
VG06 CRITICAL SQL injection via string formatting
VG07 HIGH shell=True or os.system()
VG08 CRITICAL Unsafe deserialization (pickle, marshal)
VG09 CRITICAL Hardcoded secrets/keys
VG10 HIGH Non-constant-time secret comparison
VG12 MEDIUM CORS allows all origins (*)
VG14 HIGH Sensitive data in URL parameters
VG15 HIGH Debug mode enabled
VG16 INFO LLM output usage (review for sanitization)
VG17 CRITICAL YAML load without SafeLoader

CLI Options

usage: vibeguard [-h] [--format {text,json}] [--check] [--min-score MIN_SCORE]
                 [--ignore RULE] [--exclude PATH] [--verbose] [--version]
                 [path]

positional arguments:
  path                  File or directory to scan (default: .)

options:
  -h, --help            show this help message and exit
  --format, -f {text,json}
                        Output format
  --check               Exit with code 1 if score below threshold
  --min-score MIN_SCORE Minimum score for --check (default: 60)
  --ignore, -i RULE     Rules to ignore (can repeat)
  --exclude, -e PATH    Paths to exclude (can repeat)
  --verbose, -v         Show code snippets
  --version, -V         Show version

CI/CD Integration

GitHub Actions

- name: Security scan with vibeguard
  run: |
    pip install vibeguard
    vibeguard . --check --min-score 75

Pre-commit Hook

repos:
  - repo: local
    hooks:
      - id: vibeguard
        name: vibeguard security check
        entry: vibeguard
        language: python
        types: [python]
        args: [--check, --min-score, "75"]

Why Not Just Use Bandit?

Bandit is excellent for general Python security. vibeguard focuses on patterns AI specifically gets wrong:

Pattern Bandit vibeguard
MD5 usage ✅ Warns about weak hash ✅ Warns specifically when used for passwords
Hardcoded secrets ⚠️ Some patterns ✅ Catches common AI variable names
SQL injection ✅ Basic detection ✅ Detects f-strings and .format() in execute()
LLM output handling ✅ Flags for review
YAML SafeLoader
Non-constant-time comparison ✅ Detects password/token comparisons

Use both tools together for comprehensive coverage.

API Usage

from vibeguard import scan_file, scan_directory, calculate_score

# Scan a file
result = scan_file(Path("app.py"))
for finding in result.findings:
    print(f"{finding.rule}: {finding.message}")

# Scan a directory
results = scan_directory(Path("src/"))
all_findings = [f for r in results for f in r.findings]
score = calculate_score(all_findings)
print(f"Security score: {score}/100")

Contributing

  1. Fork the repository
  2. Add new detection rules in VibeGuardVisitor
  3. Add tests for new rules
  4. Submit a pull request

References

License

MIT License - see LICENSE for details.

About

Vibe-Coded Python Security Linter - catches AI-typical security mistakes

Topics

Resources

License

Contributing

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages