{"id":705,"library":"semgrep","title":"Semgrep","description":"Semgrep is a fast, open-source, static analysis engine for finding bugs, detecting vulnerabilities in third-party dependencies, and enforcing code standards across over 30 programming languages. It scans code locally, without uploading it to external servers by default. As of version 1.156.0, it is actively developed with frequent (often weekly) releases, offering both a free Community Edition and a commercial AppSec Platform with enhanced features.","status":"active","version":"1.156.0","language":"python","source_language":"en","source_url":"https://github.com/semgrep/semgrep","tags":["static analysis","security","code quality","linter","SAST","SCA"],"install":[{"cmd":"pip install semgrep","lang":"bash","label":"Install Semgrep CLI"}],"dependencies":[],"imports":[{"note":"The `semgrep` PyPI package installs the command-line interface (CLI) tool. Programmatic interaction typically involves calling the `semgrep` command via Python's `subprocess` module, rather than importing Python classes from the `semgrep` package to perform scans directly.","symbol":"subprocess","correct":"import subprocess"}],"quickstart":{"code":"import subprocess\nimport json\nimport os\n\n# Create a dummy Python file to scan for demonstration\ndummy_code = \"\"\"\nimport os\n\ndef vulnerable_function(user_input):\n    # This pattern (os.system with user input) is often flagged by security rules\n    os.system(f\"echo {user_input}\") \n\ndef harmless_function():\n    print(\"Hello, Semgrep!\")\n\"\"\"\n\nfile_path = \"vulnerable_app.py\"\nwith open(file_path, \"w\") as f:\n    f.write(dummy_code)\n\nprint(f\"Created {file_path} for scanning.\")\n\ntry:\n    # Run Semgrep scan on the dummy file with a common security ruleset\n    # Use --json for machine-readable output and --error to get a non-zero exit code on findings\n    # `check=False` is used to allow inspection of output even if Semgrep exits with findings (code 1)\n    result = subprocess.run(\n        [\"semgrep\", \"scan\", \"--config\", \"p/security-audit\", file_path, \"--json\", \"--error\"],\n        capture_output=True,\n        text=True,\n        check=False \n    )\n\n    print(\"\\n--- Semgrep CLI Output (stdout) ---\")\n    print(result.stdout)\n\n    if result.stderr:\n        print(\"\\n--- Semgrep CLI Error (stderr) ---\")\n        print(result.stderr)\n\n    if result.returncode != 0:\n        print(f\"\\nSemgrep exited with non-zero code: {result.returncode}. This indicates findings or an actual error.\")\n    else:\n        print(\"\\nSemgrep exited with code 0. No findings or --error was not used/no blocking rules.\")\n\n    # Parse JSON output if available\n    try:\n        json_output = json.loads(result.stdout)\n        if json_output.get(\"results\"):\n            print(f\"\\nFound {len(json_output['results'])} security findings:\")\n            for finding in json_output[\"results\"]:\n                print(f\"  - Rule: {finding['check_id']} at {finding['start']['line']}:{finding['start']['col']}\")\n                print(f\"    Message: {finding['extra']['message']}\")\n        else:\n            print(\"\\nNo findings reported in JSON output.\")\n    except json.JSONDecodeError:\n        print(\"\\nCould not decode JSON output.\")\n\nexcept FileNotFoundError:\n    print(\"Error: 'semgrep' command not found. Please ensure Semgrep is installed and in your PATH.\")\nexcept Exception as e:\n    print(f\"An unexpected error occurred: {e}\")\nfinally:\n    # Clean up the dummy file\n    if os.path.exists(file_path):\n        os.remove(file_path)\n        print(f\"\\nCleaned up {file_path}.\")","lang":"python","description":"This quickstart demonstrates how to programmatically run a Semgrep scan on a Python file using the `subprocess` module. It creates a dummy file with a common vulnerability pattern, runs Semgrep with a security ruleset, and parses the JSON output to display findings."},"warnings":[{"fix":"Remove any usage of `semgrep install-ci`. Consult official documentation for recommended CI/CD integration patterns.","message":"The experimental and undocumented `semgrep install-ci` command was removed.","severity":"breaking","affected_versions":">=1.155.0"},{"fix":"Ensure your integrations with the Semgrep MCP server (Model Context Protocol) are updated to use OAuth for authentication.","message":"Connecting to the Semgrep MCP server via streamableHttp now requires OAuth.","severity":"breaking","affected_versions":">=1.150.0"},{"fix":"Monitor scan performance and resource consumption after upgrading. If necessary, consult Semgrep documentation for options to adjust memory policies or optimize scans.","message":"The default memory policy for Semgrep's engine was changed from 'eager' to 'balanced'. This may alter performance characteristics and resource usage for some scans.","severity":"gotcha","affected_versions":">=1.154.0"},{"fix":"To force a non-zero exit code on findings, use the `--error` flag with `semgrep scan` or configure blocking rules in the Semgrep AppSec Platform for `semgrep ci`.","message":"By default, `semgrep scan` and `semgrep ci` commands exit with code 0 even if findings are present. This can lead to silent failures in CI/CD pipelines.","severity":"gotcha","affected_versions":"All versions"},{"fix":"For comprehensive security scanning (SAST, SCA, secrets), Semgrep, Inc. strongly recommends using the commercial Semgrep AppSec Platform which includes advanced analysis capabilities and AI-assisted triage.","message":"Semgrep Community Edition (OSS) may miss many true positives for security vulnerabilities, especially those requiring cross-file, cross-function, or data-flow analysis.","severity":"gotcha","affected_versions":"All versions"},{"fix":"Ensure Semgrep is executed from the intended project directory. When specifying files to scan (e.g., using explicit paths or `.` for current directory), confirm they are accessible and correctly located relative to where Semgrep is invoked. Check for issues with bind mounts or working directories in containerized environments (like CI/CD) that might alter Semgrep's perception of the filesystem.","message":"Semgrep reported 'Nothing to scan' and warned about a mismatch between the project root and scanning root (e.g., 'project root X does not contain scanning root Y'). This means Semgrep could not find the specified files to scan.","severity":"gotcha","affected_versions":"All versions"}],"env_vars":null,"last_verified":"2026-05-12T18:01:34.302Z","next_check":"2026-06-26T00:00:00.000Z","problems":[{"fix":"Install Semgrep using your preferred package manager (e.g., `brew install semgrep` on macOS, `pip install semgrep` for Python environments) and ensure the installation path is in your system's PATH.","cause":"The Semgrep executable is not installed on your system or its installation directory is not included in your system's PATH environment variable.","error":"semgrep: command not found"},{"fix":"Provide a valid rule configuration using the `--config` flag, specifying a single rule file, a directory containing rule files, or a Semgrep registry rule (e.g., `semgrep --config auto .` or `semgrep --config path/to/rules.yaml .`).","cause":"Semgrep was executed without providing any rules to scan with, or the path specified for `--config` was invalid or pointed to an empty directory.","error":"Error: No rules specified. Use --config to specify rules."},{"fix":"Carefully review the specified rule file (<file_path>) for incorrect YAML syntax (e.g., indentation, missing colons) or structural issues. Refer to the official Semgrep documentation for correct rule writing and schema guidelines (e.g., `https://semgrep.dev/docs/writing-rules/`).","cause":"There is a syntax error in the YAML structure of the rule file, or the rule's content does not conform to Semgrep's expected rule schema.","error":"Error: failed to parse rule in <file_path>"},{"fix":"Ensure files have standard extensions for their respective languages. If Semgrep still can't detect it, you can explicitly specify the language using the `--lang` flag (e.g., `semgrep --lang python --config rules.yaml your_file`).","cause":"Semgrep could not automatically determine the programming language of the specified file, often due to an unknown file extension, or the file is empty/malformed, causing it to be skipped during the scan.","error":"WARNING: Could not find language for file <file_path>. Skipping."}],"ecosystem":"pypi","meta_description":null,"install_score":100,"install_tag":"verified","quickstart_score":80,"quickstart_tag":"verified","pypi_latest":"1.162.0","install_checks":{"last_tested":"2026-05-12","tag":"verified","tag_description":"installs cleanly on critical runtimes, fast import, recently tested","results":[{"runtime":"python:3.10-alpine","python_version":"3.10","os_libc":"alpine (musl)","variant":" $EXIT -eq 0 ","exit_code":0,"wheel_type":"wheel","failure_reason":null,"install_time_s":null,"import_time_s":0.01,"mem_mb":0.5,"disk_size":"410.9M"},{"runtime":"python:3.10-alpine","python_version":"3.10","os_libc":"alpine (musl)","variant":"default","exit_code":0,"wheel_type":null,"failure_reason":null,"install_time_s":null,"import_time_s":0.01,"mem_mb":0.5,"disk_size":"312.6M"},{"runtime":"python:3.10-slim","python_version":"3.10","os_libc":"slim (glibc)","variant":" $EXIT -eq 0 ","exit_code":0,"wheel_type":"wheel","failure_reason":null,"install_time_s":17,"import_time_s":0.01,"mem_mb":0.5,"disk_size":"407M"},{"runtime":"python:3.10-slim","python_version":"3.10","os_libc":"slim (glibc)","variant":"default","exit_code":0,"wheel_type":null,"failure_reason":null,"install_time_s":null,"import_time_s":0.01,"mem_mb":0.5,"disk_size":"313M"},{"runtime":"python:3.11-alpine","python_version":"3.11","os_libc":"alpine (musl)","variant":" $EXIT -eq 0 ","exit_code":0,"wheel_type":"wheel","failure_reason":null,"install_time_s":null,"import_time_s":0.02,"mem_mb":1,"disk_size":"421.7M"},{"runtime":"python:3.11-alpine","python_version":"3.11","os_libc":"alpine (musl)","variant":"default","exit_code":0,"wheel_type":null,"failure_reason":null,"install_time_s":null,"import_time_s":0.02,"mem_mb":1,"disk_size":"322.7M"},{"runtime":"python:3.11-slim","python_version":"3.11","os_libc":"slim (glibc)","variant":" $EXIT -eq 0 ","exit_code":0,"wheel_type":"wheel","failure_reason":null,"install_time_s":16.6,"import_time_s":0.02,"mem_mb":1,"disk_size":"418M"},{"runtime":"python:3.11-slim","python_version":"3.11","os_libc":"slim (glibc)","variant":"default","exit_code":0,"wheel_type":null,"failure_reason":null,"install_time_s":null,"import_time_s":0.02,"mem_mb":1,"disk_size":"323M"},{"runtime":"python:3.12-alpine","python_version":"3.12","os_libc":"alpine (musl)","variant":" $EXIT -eq 0 ","exit_code":0,"wheel_type":"wheel","failure_reason":null,"install_time_s":null,"import_time_s":0.02,"mem_mb":0.8,"disk_size":"411.9M"},{"runtime":"python:3.12-alpine","python_version":"3.12","os_libc":"alpine (musl)","variant":"default","exit_code":0,"wheel_type":null,"failure_reason":null,"install_time_s":null,"import_time_s":0.02,"mem_mb":0.8,"disk_size":"312.9M"},{"runtime":"python:3.12-slim","python_version":"3.12","os_libc":"slim (glibc)","variant":" $EXIT -eq 0 ","exit_code":0,"wheel_type":"wheel","failure_reason":null,"install_time_s":13.5,"import_time_s":0.02,"mem_mb":0.8,"disk_size":"408M"},{"runtime":"python:3.12-slim","python_version":"3.12","os_libc":"slim (glibc)","variant":"default","exit_code":0,"wheel_type":null,"failure_reason":null,"install_time_s":null,"import_time_s":0.02,"mem_mb":0.8,"disk_size":"313M"},{"runtime":"python:3.13-alpine","python_version":"3.13","os_libc":"alpine (musl)","variant":" $EXIT -eq 0 ","exit_code":0,"wheel_type":"wheel","failure_reason":null,"install_time_s":null,"import_time_s":0.02,"mem_mb":1,"disk_size":"411.8M"},{"runtime":"python:3.13-alpine","python_version":"3.13","os_libc":"alpine (musl)","variant":"default","exit_code":0,"wheel_type":null,"failure_reason":null,"install_time_s":null,"import_time_s":0.02,"mem_mb":1,"disk_size":"312.7M"},{"runtime":"python:3.13-slim","python_version":"3.13","os_libc":"slim (glibc)","variant":" $EXIT -eq 0 ","exit_code":0,"wheel_type":"wheel","failure_reason":null,"install_time_s":13.9,"import_time_s":0.01,"mem_mb":0.8,"disk_size":"408M"},{"runtime":"python:3.13-slim","python_version":"3.13","os_libc":"slim (glibc)","variant":"default","exit_code":0,"wheel_type":null,"failure_reason":null,"install_time_s":null,"import_time_s":0.02,"mem_mb":0.8,"disk_size":"313M"},{"runtime":"python:3.9-alpine","python_version":"3.9","os_libc":"alpine (musl)","variant":" $EXIT -eq 0 ","exit_code":0,"wheel_type":"wheel","failure_reason":null,"install_time_s":null,"import_time_s":0.01,"mem_mb":0.5,"disk_size":"250.0M"},{"runtime":"python:3.9-alpine","python_version":"3.9","os_libc":"alpine (musl)","variant":"default","exit_code":0,"wheel_type":null,"failure_reason":null,"install_time_s":null,"import_time_s":0.01,"mem_mb":0.5,"disk_size":"249.9M"},{"runtime":"python:3.9-slim","python_version":"3.9","os_libc":"slim (glibc)","variant":" $EXIT -eq 0 ","exit_code":0,"wheel_type":"wheel","failure_reason":null,"install_time_s":14.4,"import_time_s":0.01,"mem_mb":0.5,"disk_size":"251M"},{"runtime":"python:3.9-slim","python_version":"3.9","os_libc":"slim (glibc)","variant":"default","exit_code":0,"wheel_type":null,"failure_reason":null,"install_time_s":null,"import_time_s":0.01,"mem_mb":0.5,"disk_size":"250M"}]},"quickstart_checks":{"last_tested":"2026-04-24","tag":"verified","tag_description":"quickstart runs on critical runtimes, recently tested","results":[{"runtime":"python:3.10-alpine","exit_code":0},{"runtime":"python:3.10-slim","exit_code":0},{"runtime":"python:3.11-alpine","exit_code":0},{"runtime":"python:3.11-slim","exit_code":0},{"runtime":"python:3.12-alpine","exit_code":0},{"runtime":"python:3.12-slim","exit_code":0},{"runtime":"python:3.13-alpine","exit_code":0},{"runtime":"python:3.13-slim","exit_code":0},{"runtime":"python:3.9-alpine","exit_code":0},{"runtime":"python:3.9-slim","exit_code":0}]}}