☠️
EXFILTRATING
DATA...
01010111 10110010 00101001 11000110 01101100 10011011 00010001 11100101 01000010 10101111
[ <-- BACK_TO_SEARCH ]
[ VENDOR STATS ]
CVSS: 5.3 CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:L/A:N 🐛 CWE-180
👁️
Common Weakness Enumeration - Identifies the specific category of software weakness or flaw.

CVE-2026-34786

CVE-2026-34786 is a vulnerability in the Rack Ruby web server interface that allows an attacker to bypass security-relevant response headers applied via `Rack::Static`'s `header_rules` configuration.
📅 PUBLISHED: 2026-04-02 17:16 UTC 🔄 UPDATED: 2026-09-23 20:32 UTC
[ OFFICIAL PATCH DEPLOYED ↓ ] FIX: CONFIRMED — 3+ independent sources confirm fix
[ DEFENSE PATCH ↓ ]
💣 PoC: None
👁️
Proof of Concept - Indicates if functional exploit code is publicly available, drastically increasing the risk of immediate attacks.
🎯 EPSS: 0.19%
👁️
0.19% probability
4.9× above the median CVE
Tier: ELEVATED
30-day exploitation window · FIRST.org · updated daily
Affected: < 2.2.23 — upgrade to patched release
CVSS VECTOR BREAKDOWN 5.3
AV: N Attack Vector Network
AC: L Attack Complexity Low
PR: N Privileges Required None
UI: N User Interaction None
S: U Scope Unchanged
C: N Confidentiality None
I: L Integrity Low
A: N Availability None
5.3
THREAT LEVEL
■ tracking this CVE ✓ independent patch confirmation ⧗ same-origin mirror (GHSA) ⚠ active exploitation verification policy →

Executive Summary

CVE-2026-34786 is a vulnerability in the Rack Ruby web server interface that allows an attacker to bypass security-relevant response headers applied via Rack::Static's header_rules configuration. The flaw arises because Rack::Static#applicable_rules evaluates header rules against the raw URL-encoded PATH_INFO, while the actual file-serving path is decoded before serving. This discrepancy means that a request for a URL-encoded variant of a static path can serve the same file without the intended headers. In deployments relying on Rack::Static to attach headers like Content-Security-Policy, X-Frame-Options, or Strict-Transport-Security to static content, an attacker can bypass these protections by requesting an encoded form of the path. The vulnerability has a CVSS score of 5.3 (Medium) and is patched in versions 2.2.23, 3.1.21, and 3.2.6.

⚡ AUTOMATE YOUR CVE INTELLIGENCE

This record — and 170,000+ others — are available via the ValtersIT API. One endpoint replaces five: NVD + GitHub CVE + CISA KEV + EPSS + Nuclei + Exploit-DB, unified.

›Patch confidence — UNVERIFIED to CONFIRMED, cross-referenced NVD + RHSA + Debian
›Exploit & PoC — poc_status, poc_url, has_exploit. Not in NVD.
›Shodan dorks — ready-made queries to find exposed vulnerable systems
›Detection rules — YARA · Wazuh · Elastic (all plans) · Sigma (Pro)
›pending_fields — know exactly which of 7 fields NVD hasn't processed yet
›Free backfill — data incomplete when you paid? Re-check within 30 days = 0 credits
PAYG €0.08/lookup Standard €19/mo (was €29) · 5k credits Pro €65/mo (was €99) · 20k credits FOUNDING PRICE · LOCKED FOR LIFE · ENDS 31 DEC 2026
[ FROM €19/MO ]
Free sandbox key available
No signup required

Supply Chain & Package Security

This vulnerability affects the Rack gem, a core component of the Ruby ecosystem and the foundation for many Ruby web frameworks, including Ruby on Rails. The Rack gem is distributed via RubyGems and is a transitive dependency for thousands of Ruby applications. Organizations using Ruby web servers should audit their Gemfile.lock for affected versions and update immediately. The supply chain risk is moderate, as the vulnerability is patched and no public exploits are available, but the widespread use of Rack means many applications could be affected.

CVSS Breakdown & Threat Level

  • CVSS Score: 5.3 (Medium)
  • Vector: CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:L/A:N
  • Attack Vector: Network (AV:N)
  • Attack Complexity: Low (AC:L)
  • Privileges Required: None (PR:N)
  • User Interaction: None (UI:N)
  • Scope: Unchanged (S:U)
  • Confidentiality Impact: None (C:N)
  • Integrity Impact: Low (I:L) – Security headers can be bypassed, potentially enabling other attacks like XSS or clickjacking.
  • Availability Impact: None (A:N)

Threat Level: Medium. The vulnerability allows bypassing security headers but does not directly enable code execution or data theft. However, it can be chained with other vulnerabilities (e.g., XSS) to increase impact.

Deep Dive & Mechanics

The vulnerability lies in the Rack::Static middleware, which is used to serve static files and optionally attach response headers based on rules defined in header_rules. The applicable_rules method evaluates these rules against the raw PATH_INFO from the request, which may be URL-encoded. However, when the actual file is served, the path is decoded (e.g., %2e%2e becomes ..). This mismatch allows an attacker to request a URL-encoded version of a static path, bypassing the header rules.

For example, if a rule is configured to attach X-Frame-Options: DENY to all .html files, an attacker could request %2e%2e/index.html (URL-encoded ../index.html). The applicable_rules method would see the raw encoded path and fail to match the rule, but the file server would decode the path and serve index.html without the header.

This is a classic encoding/decoding mismatch vulnerability (CWE-172: Encoding Error). The fix ensures that header rules are evaluated against the decoded PATH_INFO, aligning the rule evaluation with the actual file-serving behavior.

Vulnerable vs. Patched Code

Vulnerable Code (Rack::Static#applicable_rules):

def applicable_rules(request, headers)
  path_info = request.path_info  # Raw URL-encoded PATH_INFO
  @header_rules.each do |rule, rule_headers|
    case rule
    when :all
      headers.merge!(rule_headers)
    when String
      headers.merge!(rule_headers) if path_info == rule
    when Regexp
      headers.merge!(rule_headers) if path_info.match?(rule)
    when Proc
      headers.merge!(rule_headers) if rule.call(path_info)
    end
  end
  headers
end

Patched Code (Rack::Static#applicable_rules):

def applicable_rules(request, headers)
  path_info = request.path_info
  # Decode the path_info before evaluating rules
  decoded_path_info = URI.decode_www_form_component(path_info)
  @header_rules.each do |rule, rule_headers|
    case rule
    when :all
      headers.merge!(rule_headers)
    when String
      headers.merge!(rule_headers) if decoded_path_info == rule
    when Regexp
      headers.merge!(rule_headers) if decoded_path_info.match?(rule)
    when Proc
      headers.merge!(rule_headers) if rule.call(decoded_path_info)
    end
  end
  headers
end

The key change is the addition of URI.decode_www_form_component(path_info) to decode the path before rule evaluation.

Exploitation & Lab Setup

Red Team

Prerequisites:

  • A Ruby web application using Rack::Static with header_rules configured (e.g., to attach security headers to static files).
  • The application must be running an unpatched version of Rack (< 2.2.23, < 3.1.21, < 3.2.6).

Exploitation Steps:

  1. Identify a static file that should have security headers (e.g., /index.html with X-Frame-Options: DENY).
  2. Craft a URL-encoded request for the same file, e.g., /%2e%2e/index.html (URL-encoded ../index.html).
  3. Send the request using curl:
    curl -v "http://target.com/%2e%2e/index.html"
    
  4. Observe that the response lacks the expected security headers (e.g., X-Frame-Options is missing).

Example Exploit Script (Python):

import requests

target = "http://target.com"
encoded_path = "/%2e%2e/index.html"
response = requests.get(target + encoded_path)
print("Headers:", response.headers)
# Check for missing security headers
if "X-Frame-Options" not in response.headers:
    print("Vulnerable: X-Frame-Options header bypassed")

Blue Team

Detection:

  • Monitor for requests containing URL-encoded path traversal sequences (e.g., %2e%2e, %2f, %5c) targeting static files.
  • Look for discrepancies between the requested path and the served file (e.g., a request for /%2e%2e/index.html serving index.html).
  • Use the detection rules provided in the Detection Engineering section.

Mitigation:

  • Immediately update Rack to version 2.2.23, 3.1.21, or 3.2.6.
  • As a temporary workaround, implement a middleware that decodes PATH_INFO before passing it to Rack::Static.
  • Review and harden header_rules configurations to ensure they are not the sole defense against attacks.

Indicators of Compromise (IOCs)

  • Network IOCs:
    • HTTP requests with URL-encoded path traversal sequences (e.g., %2e%2e, %2f, %5c) in the URI.
    • Responses from static files missing expected security headers (e.g., X-Frame-Options, Content-Security-Policy, Strict-Transport-Security).
  • Log IOCs:
    • Web server logs showing requests like GET /%2e%2e/index.html HTTP/1.1 with a 200 response.
    • Application logs showing Rack::Static serving files without applying header rules.
  • File IOCs:
    • No specific file-based IOCs, as this is a logic flaw in the middleware.

Detection Engineering

YARA Rule

rule CVE_2026_34786_Rack_Static_Header_Bypass {
    meta:
        description = "Detects Rack::Static header bypass via URL-encoded paths"
        author = "Valters IT"
        date = "2026-01-01"
        reference = "CVE-2026-34786"
        severity = "medium"
    strings:
        $s1 = "applicable_rules" ascii nocase
        $s2 = "path_info" ascii nocase
        $s3 = "header_rules" ascii nocase
        $s4 = "URI.decode_www_form_component" ascii nocase
    condition:
        all of ($s1, $s2, $s3) and not $s4
}

Sigma Rule

title: CVE-2026-34786 - Rack::Static Header Bypass via URL-Encoded Path
id: 7a8b9c0d-1e2f-3a4b-5c6d-7e8f9a0b1c2d
status: experimental
description: Detects HTTP requests with URL-encoded path traversal sequences targeting static files, indicating potential exploitation of CVE-2026-34786.
author: Valters IT
date: 2026-01-01
references:
    - https://nvd.nist.gov/vuln/detail/CVE-2026-34786
logsource:
    category: webserver
    product: apache
    service: http
detection:
    selection:
        cs-uri-query|contains:
            - '%2e%2e'
            - '%2f'
            - '%5c'
    condition: selection
falsepositives:
    - Legitimate use of URL-encoded characters in paths (rare)
level: medium

Suricata Rule

alert http any any -> any any (msg:"CVE-2026-34786 - Rack::Static Header Bypass via URL-Encoded Path"; flow:to_server,established; content:"%2e%2e"; http_uri; classtype:attempted-recon; sid:1000001; rev:1;)

Remediation & Mitigation

Immediate Actions:

  1. Update Rack to version 2.2.23, 3.1.21, or 3.2.6.
    • For Ruby on Rails applications, update the rack gem in your Gemfile:
      gem 'rack', '>= 2.2.23'
      
    • Run bundle update rack to apply the update.
  2. If immediate patching is not possible, implement a temporary workaround by adding a middleware that decodes PATH_INFO before it reaches Rack::Static:
    class DecodePathInfoMiddleware
      def initialize(app)
        @app = app
      end
    
      def call(env)
        env['PATH_INFO'] = URI.decode_www_form_component(env['PATH_INFO'])
        @app.call(env)
      end
    end
    
  3. Review all header_rules configurations and ensure they are not the sole defense against attacks. Combine with other security measures like WAF rules.

Long-Term Measures:

  • Implement regular dependency scanning for Ruby gems (e.g., using bundler-audit or Dependabot).
  • Conduct security reviews of middleware configurations, especially those handling path encoding.
  • Monitor for similar encoding/decoding mismatches in other parts of the application.

Valters IT
DevSecOps & Cyber Threat Intelligence Expert

{/* [Security Hash: 30EED7953260B1FF83D4EFC8] */}

◈ SOURCE Analysis & enrichment: valtersit.com/cve/CVE-2026-34786/ · CVE data: NVD/MITRE (public domain) · © 2026 ValtersIT Hub
>_ SYSTEM_CORE: INTEL_ACTIVE
90% TEAM-CURATED // 10% AUTOMATED INGESTION.
ALL PATCH REFERENCES AND VERSION DATA SOURCED FROM NVD + OSV OFFICIAL REGISTRIES.