기술 블로그2026년 3월 12일Daniel Park2 조회

Perfect Defense Against Python RCE Vulnerabilities: A Practical Guide to Integrating Bandit and DevSecOps

RCE vulnerabilities in Python applications pose a serious security threat, making effective defense strategies essential. This article presents practical approaches to preventing Python RCE, from static analysis using Bandit to CI/CD pipeline integration and in-depth defense through SeekersLab solutions.

#Python Security#RCE Defense#Bandit Usage Guide#DevSecOps#SAST#Cloud Security#SeekersLab
Perfect Defense Against Python RCE Vulnerabilities: A Practical Guide to Integrating Bandit and DevSecOps
Daniel Park

Daniel Park

2026년 3월 12일

With the recent increase in software supply chain attacks, Remote Code Execution (RCE) vulnerabilities in applications based on dynamic languages like Python are emerging as a serious security threat. These vulnerabilities can allow attackers to execute arbitrary code on a system, leading to fatal consequences such as data breaches, system destruction, and denial of service. Particular caution is required in cloud environments, where a small RCE vulnerability can become a conduit for spreading to the entire infrastructure. This article seeks to deeply understand the nature of Python RCE vulnerabilities and explore ways to leverage Bandit, a Static Application Security Testing (SAST) tool, for effective prevention and detection. Furthermore, we aim to present strategies for strengthening security throughout the development lifecycle and practical methods for building a defense architecture.

From an architectural perspective, Python is used in a wide range of fields such as web applications, data science, AI/machine learning, and automation scripts, thanks to its flexibility and vast library ecosystem. Behind this convenience lie potential security risks that attackers can exploit. Specifically, improper use of functions like eval(), exec(), deserialization of the pickle module, and subprocess calls are prime examples of elements that can lead to RCE vulnerabilities. With the proliferation of Shift-Left Security and DevSecOps culture in the industry, considering security from the early stages of development has become crucial, further emphasizing the role of SAST tools.

From a practical standpoint, a key concern is the tendency for security reviews to be pushed to a lower priority as development speed rapidly increases. This allows potential vulnerabilities to reach the production environment, ultimately leading to situations that require greater cost and effort to resolve. Therefore, effectively integrating security validation steps into the development pipeline is essential, which involves a cultural shift beyond mere tool adoption. We hope this guide provides practical insights that can significantly enhance the security posture of Python-based services.

Understanding the Essence of Python RCE Vulnerabilities

Remote Code Execution (RCE) refers to a vulnerability that allows an attacker to remotely execute arbitrary code on a target system. In a Python environment, the primary vectors for RCE typically arise when user input is not properly validated before executing system commands or passing it directly to dangerous functions. Common examples include:

  • eval() and exec() Functions Improper Use: These are powerful functions for executing string-based code, but passing unvalidated external input can allow attackers to execute arbitrary code.
  • pickle Module Deserialization Vulnerability: If a serialized Python object contains malicious elements during deserialization, it can lead to arbitrary code execution. pickle data from untrusted sources should never be deserialized.
  • External Command Execution via subprocess Module: If user input is directly included in functions that execute external commands, such as subprocess.run() or os.system(), it can lead to Command Injection vulnerabilities. The shell=True option, in particular, is highly dangerous.
  • Template Engine Vulnerabilities: Template engines used in web frameworks like Jinja2 and Mako can also lead to RCE through Server-Side Template Injection (SSTI).

From an architectural perspective, these vulnerabilities mostly occur where 'Trust Boundaries' are broken. This means all input from external sources should be thoroughly validated and sanitized, based on the premise that it is inherently untrustworthy. Below is a simple RCE code example that exploits the eval() function.

# 취약한 코드 예시
def calculate_expression(expression):
    return eval(expression)
# 공격자가 입력할 수 있는 악성 페이로드
# __import__('os').system('ls -al')는 현재 디렉토리의 파일 목록을 실행시킵니다.
# 실제 공격에서는 더 파괴적인 명령어가 사용될 수 있습니다.
malicious_payload = "__import__('os').system('ls -al')"
result = calculate_expression(malicious_payload)
print(result)

Such code patterns can be easily overlooked during development, making it crucial to detect them proactively using static analysis tools. Through an RCE vulnerability, an attacker can gain complete control over the system, including executing operating system commands, reading/writing files, and establishing network connections. This can lead to severe consequences such as data breaches, system incapacitation, and ransomware infection.

Static Application Security Testing (SAST) and the Role of Bandit

Static Application Security Testing (SAST) is a technique for finding security vulnerabilities by analyzing source code without executing it. This is a core component of the Shift-Left Security strategy, which aims to minimize remediation costs by discovering vulnerabilities early in the development phase, specifically when code is being written. In the Python ecosystem, Bandit is a prominent open-source tool that fulfills this SAST role.

From a practical perspective, a crucial aspect is that Bandit scans code based on a defined set of rules to identify potential security vulnerabilities within Python code. This is highly effective for automatically detecting specific function usage patterns or calls to dangerous modules, similar to those involved in RCE. Bandit offers the following features to help developers write more secure code:

  • Rule-based Analysis: It analyzes code patterns using predefined rules (e.g., B101 for exec, B301 for pickle).
  • Support for Various Output Formats: It reports analysis results in various formats such as JSON, XML, and HTML, making it easy to integrate into CI/CD pipelines.
  • Customizability: Specific rules can be enabled/disabled, or trust levels can be adjusted to suit project characteristics.

Installing and running Bandit is very simple. You can install it using the following command:

pip install bandit

After installation, you can run Bandit in your project directory to analyze the code.

bandit -r your_project_directory/

In the command above, the -r option means to recursively scan the specified directory. Bandit outputs a detailed report that includes potential vulnerabilities found in the code, their descriptions, and risk levels. This report serves as crucial information for development teams to quickly identify and rectify issues.

In-depth Analysis of Bandit's Key Features and Detection Rules

Bandit provides a set of rules for detecting various types of Python security vulnerabilities, many of which identify patterns directly related to RCE. From operational experience, a deep understanding and proper utilization of these rules are crucial for reducing false positives and enhancing actual security effectiveness.

The following are key Bandit rules related to RCE and their descriptions:

Rule IDDescriptionRelated RCE VectorSeverity (Default)
B101Use of execArbitrary code executionHigh
B102Use of evalArbitrary code executionHigh
B301Use of pickle or cPickle moduleDeserialization vulnerabilityMedium
B302Use of marshal moduleDeserialization vulnerabilityMedium
B603Use of shell=True in subprocess.PopenCommand InjectionHigh
B607Use of os.systemCommand InjectionHigh

Each rule targets a specific code pattern, and Bandit raises a warning when it finds this pattern. However, not all warnings may represent actual exploitable vulnerabilities. For example, if eval() is used but only applied to strings generated from trusted internal sources, it might not be an issue. In such cases, Bandit's configuration files can be used to manage false positives and improve analysis efficiency.

Through configuration files like bandit.yaml, you can disable specific rules or specify files and directories to exclude from scanning. Additionally, you can add # nosec comments within the code to instruct Bandit to ignore warnings on particular lines. This is an important method for maintaining development flexibility while increasing the accuracy of security analysis.

# bandit.yaml 예시
profiles:
  high_security:
    include: 
      - B101
      - B102
      - B301
      - B603
      - B607
    exclude:
      - B302 # marshal 모듈은 사용하지 않으므로 제외
exclude_dirs:
  - tests/
  - docs/
# Bandit 실행 시:
# bandit -c bandit.yaml -r your_project_directory/

Strategies for Integrating Bandit into CI/CD Pipelines

From an architectural perspective, the core of DevSecOps is to automate security validation by integrating it into the early stages of the development process. Integrating Bandit into the CI/CD (Continuous Integration/Continuous Delivery) pipeline is one of the most effective strategies for defending against Python RCE vulnerabilities. This enables automatic security scans every time code changes occur, allowing for immediate identification and remediation of potential issues.

There are various ways to integrate Bandit into the CI/CD pipeline:

  • Version Control System (VCS) Hooks: Git Pre-Commit hooks can be used to enforce Bandit scans locally before developers commit their code.
  • CI Platform Integration: Add a Bandit scan step to the build pipeline of CI platforms like Jenkins, GitLab CI, or GitHub Actions. When code is pushed to the repository, a scan is automatically triggered, and the build can be failed or warnings issued based on the vulnerabilities found.
  • Pull Request (PR) Review: Run a Bandit scan when a PR is created and post the results as PR comments, allowing code reviewers and developers to review and discuss vulnerabilities.

The following is a simple example of integrating Bandit scans into a Python project using GitHub Actions:

# .github/workflows/bandit_scan.yml
name: Bandit Security Scan
on:
  push:
    branches:
      - main
  pull_request:
    branches:
      - main
jobs:
  bandit-scan:
    runs-on: ubuntu-latest
    steps:
    - name: Checkout code
      uses: actions/checkout@v4
    - name: Set up Python
      uses: actions/setup-python@v5
      with:
        python-version: '3.x'
    - name: Install dependencies
      run: |
        python -m pip install --upgrade pip
        pip install bandit
    - name: Run Bandit scan
      run: |
        bandit -r . -f html -o bandit_report.html || true # 취약점이 있어도 빌드 실패하지 않도록 || true 추가
        # Critical/High 등급 취약점 발견 시 빌드 실패 설정 예시:
        # bandit -r . -ll -iii --confidence-level HIGH || exit 1
    - name: Upload Bandit report
      uses: actions/upload-artifact@v4
      with:
        name: bandit-report
        path: bandit_report.html

This automated approach compels developers not to miss security issues and helps security experts focus on critical areas without manually reviewing all code. Consequently, it contributes to increasing the efficiency of the development process and improving security quality.

Defense-in-Depth Strategy: Code Guardrails for RCE Prevention

From operational experience, it is difficult to completely defend against all vulnerabilities, including RCE, with a single SAST tool. A multi-layered Defense-in-Depth strategy is essential for RCE prevention. Secure coding practices must be established at the code level, and security guardrails must be built at the infrastructure level. The following are key defense-in-depth strategies:

  • Input Validation and Sanitization: All input from external sources must be thoroughly validated using a whitelist approach, and unauthorized characters or patterns should be removed. It is crucial to allow only the minimum necessary data, following the Principle of Least Privilege.
  • Safe Function and Library Usage: Minimize the use of dangerous functions like eval(), exec(), and pickle. If their use is unavoidable, they must be utilized only within a secure context. When using external libraries, ensure there are no known vulnerabilities and maintain up-to-date versions.
  • Container Security Enhancement: When deploying applications in container environments like Docker and Kubernetes, the attack surface must be reduced through container image scanning, runtime security hardening (e.g., Seccomp, AppArmor), and network segmentation. SeekersLab's FRIIM CWPP provides functionalities to detect and block anomalous behavior and vulnerabilities in container runtime environments, protecting against RCE threats.
  • Web Application Firewall (WAF) Integration: A WAF can effectively defend against web-based attacks like RCE by detecting and blocking malicious requests flowing into web applications preemptively.
  • Application of Least Privilege Principle: The processes and users under which an application runs should have only the minimum necessary privileges. This minimizes the impact an attacker can have on the system even if an RCE attack succeeds.

Such a multi-faceted approach enhances overall security strength by enabling detection and blocking at other layers, even if an attacker bypasses one layer of defense. FRIIM CNAPP supports this integrated security strategy for cloud-native environments, providing comprehensive security visibility and control from the development phase to runtime.

RCE Threat Detection and Response with Seekurity SIEM/SOAR

Prevention at the code level and defensive guardrails at the infrastructure level are essential, but not all attacks can be 100% prevented. Therefore, it is crucial to establish a system for rapid detection and response in case an RCE attack succeeds. Seekurity SIEM and Seekurity SOAR play a pivotal role in such threat detection and response.

Seekurity SIEM centrally collects and analyzes various security events, including application logs, system logs, and network flow data. When an RCE attack occurs, the following anomalous behaviors may be recorded in system or application logs, and Seekurity SIEM detects these patterns:

  • When a normal application process executes an unusual shell command (e.g., bash, sh, powershell)
  • Unexpected process creation or file modification attempts
  • Abnormal communication attempts from within an application container to external IP addresses

Seekurity SIEM's correlation analysis engine integrates and analyzes these heterogeneous logs to accurately identify RCE attack indicators and issue real-time alerts to security personnel. For example, RCE attempts can be detected using a hypothetical SIEM rule like the following:

{
  "rule_id": "RCE-Python-Shell-Exec",
  "name": "Python Process Executing Shell Command",
  "description": "Detects a Python process spawning an unexpected shell or command execution.",
  "severity": "Critical",
  "query": "event.source:application AND process.name:python AND process.command_line:(sh OR bash OR powershell OR cmd) AND NOT process.command_line:(\"script.py\" OR \"normal_utility\")",
  "tags": ["rce", "python", "command_injection"]
}

When such a rule is triggered, Seekurity SOAR automatically integrates to take rapid response actions according to defined playbooks. For example, automated responses such as isolating the detected server from the network, forcefully terminating the process, and immediately dispatching notifications to the incident response team are possible. In this way, Seekurity SIEM/SOAR plays a critical role in reducing RCE attack detection time and enabling effective initial response without manual intervention, thereby minimizing damage.

Troubleshooting / Problem Solving

When applying SAST tools like Bandit in practice, you may encounter several common issues. Effectively resolving these problems is essential for maximizing tool utility and maintaining development productivity.

  • False Positive Management: Since Bandit detects vulnerabilities based on code patterns, false positives can occur where warnings are shown for code that is not actually problematic. In such cases, you can reduce false positives by using # nosec comments to ignore warnings on specific lines or by disabling particular rules in the bandit.yaml configuration file. It is crucial not just to ignore warnings but to thoroughly review whether the code poses a real security risk before making a decision.
  • Performance Issues with Large Codebases: As projects grow in size, Bandit scans can take longer, potentially creating bottlenecks in the CI/CD pipeline. In such situations, consider minimizing the target directories for scanning or utilizing incremental scanning features to scan only changed files. Additionally, scan time can be reduced by excluding unnecessary rules, such as with bandit --skip Bxxx.
  • Environment Dependency Issues: Bandit installation and execution problems can arise depending on the Python environment. Managing independent Python environments and dependencies per project using virtual environments (virtualenv, Poetry, PDM, etc.) can effectively resolve these issues.

It is important to note that Bandit only performs static analysis of source code. This has limitations in detecting dynamic vulnerabilities or logical flaws that occur at runtime. Therefore, Bandit must be used in conjunction with DAST (Dynamic Application Security Testing) tools, manual code reviews, and runtime security monitoring (e.g., Seekurity SIEM/SOAR) to establish a truly near-perfect defense system.

Practical Application / Case Study

A large e-commerce company operating a Python-based microservice architecture was struggling with security vulnerability management due to rapid development cycles and collaboration among numerous development teams. Specifically, critical vulnerabilities like RCE were repeatedly unnoticed during the development phase and made their way into the production environment, exposing the company to risks of service disruption and data breaches.

Situation Before Adoption:

  • Security coding standards were lacking across development teams, leading to frequent use of dangerous functions like eval() and os.system().
  • Security vulnerabilities were primarily discovered during QA or post-monitoring phases, resulting in high remediation costs and frequent release delays.
  • Manual code reviews by the security team alone struggled to cover all vulnerabilities in the extensive codebase.

After Adopting Bandit and DevSecOps:

This company decided to integrate Bandit into its CI/CD pipeline as part of a Shift-Left Security strategy. Pre-Commit hooks were configured in the Git repositories of all Python projects, and Bandit scans were set up to run automatically via GitHub Actions whenever a Pull Request was created. Furthermore, if Critical or High-severity vulnerabilities were detected, PR merges were blocked, effectively preventing their introduction into production.

Improvement Effects and ROI:

  • Reduced Security Vulnerabilities: Within 3 months of adoption, the number of RCE-related vulnerabilities discovered in the development phase decreased by over 60%.
  • Accelerated Development Pipeline: By fixing vulnerabilities in the early development stages, the frequency of security defect discovery during the QA phase decreased, significantly reducing release delays.
  • Security Cost Savings: Considering that the cost of fixing vulnerabilities in a production environment (emergency patches, service interruptions, etc.) is much higher than fixing them in early stages, significant cost savings were achieved.
  • Enhanced Developer Security Awareness: Through automated feedback, developers themselves recognized the importance of secure coding, and a culture of writing safe code was established.

Thus, Bandit contributed not only as a vulnerability finding tool but also to transforming the development culture itself and ensuring business continuity. Furthermore, this company is strengthening its capability to detect and analyze new forms of malicious code patterns and zero-day attack attempts by adopting the KYRA AI Sandbox.

Future Outlook

Python application security in cloud environments must evolve in step with continuously developing threats. The advancement of AI and machine learning technologies is expected to further enhance the accuracy of SAST tools and contribute to reducing false positives. Moreover, as Supply Chain Security becomes increasingly important, SAST tools are likely to evolve beyond merely analyzing proprietary code to become a part of a broader Supply Chain Security Platform (SSCP) that integrally manages vulnerabilities in open-source libraries and dependencies.

From an architectural perspective, application security is no longer an isolated domain. The importance of integrated security platforms (CNAPP) that organically link with overall cloud-native security, including Cloud Security Posture Management (CSPM), Container Workload Protection Platform (CWPP), and Cloud Infrastructure Entitlement Management (CIEM), will be further emphasized. Developers must keep pace with these changes by continuously acquiring security knowledge and actively adopting the latest security tools and technologies.

From operational experience, such integrated solutions cover the entire security lifecycle from early development to runtime, maximizing security visibility and enabling automated responses. Ultimately, they strengthen defense capabilities against complex threats like Python RCE and form the foundation for building a safe and trustworthy software development environment.

Conclusion

RCE vulnerabilities in Python applications are a significant threat that cannot be overlooked in modern software development. Effectively defending against and managing these is a critical task directly related to a company's business continuity and data protection. The key points covered in this article are summarized as follows:

  • Python RCE can occur through various vectors, including eval(), pickle, and subprocess, with the absence of input validation being a primary cause.
  • Bandit is a highly effective SAST tool for statically analyzing and identifying potential RCE vulnerabilities in Python code.
  • Integrating Bandit into the CI/CD pipeline and building a defense-in-depth strategy is central to DevSecOps, resolving security issues in the early development stages and thereby reducing costs and effort.
  • SeekersLab's FRIIM CNAPP/CWPP provides integrated security in cloud-native environments, while Seekurity SIEM/SOAR offers detection and automated response to runtime RCE threats, strengthening the defense system.

From a practical standpoint, close collaboration between development and security teams is crucial to establish security automation. SAST tools like Bandit can be a powerful starting point for such collaboration. This goes beyond merely adopting tools; it hinges on embedding security as an essential part of the development process. To safely operate Python-based services in a cloud environment, a wise approach involves continuous efforts to enhance security combined with the adoption of integrated security platforms like FRIIM CNAPP, to secure comprehensive security capabilities. These efforts form an indispensable foundation for building a safe and innovative digital environment.

최신 소식 받기

최신 보안 인사이트를 이메일로 받아보세요.

태그

#Python Security#RCE Defense#Bandit Usage Guide#DevSecOps#SAST#Cloud Security#SeekersLab