Skip to content

VNX-RUBY-010: OpenSSL certificate verification disabled (VERIFY_NONE)

Reports Ruby code that sets or passes OpenSSL::SSL::VERIFY_NONE (or verify_mode = 0), disabling TLS certificate verification; comparisons, none-mode option tables, comments, strings and test files are not reported.

Updated 02 Nov 2026Checked against cli@de9b52a
Field Value
Rule ID VNX-RUBY-010
Severity High
SARIF level error
Kind sast
Languages Ruby
CWE CWE-295
CAPEC CAPEC-94
ATT&CK T1557
CWSS vector CWSS:1.0/TI:H/AP:A/AL:A/IC:N/FC:LT/RP:N/RL:A/AV:I/AS:N/IN:A/SC:A/BI:H/DI:H/EX:H/EC:N/P:H
Tags ssl tls certificate mitm ruby
Source internal/sast/rules/vnx-ruby-010.rego

Overview

This rule flags any occurrence of OpenSSL::SSL::VERIFY_NONE in Ruby source files. This constant, when assigned to the verify_mode attribute of an OpenSSL::SSL::SSLContext, instructs Ruby’s OpenSSL bindings to skip all certificate chain validation. The TLS handshake completes regardless of whether the server’s certificate is expired, self-signed, issued by an untrusted authority, or belongs to a completely different hostname.

The practical consequence is that the “S” in HTTPS provides no security guarantee. While the connection is still encrypted, the application has no assurance about the identity of the remote party. An attacker positioned on the network path, on a shared Wi-Fi network, at a compromised router, or via DNS poisoning, can terminate the TLS connection, present a fraudulent certificate, and transparently proxy all traffic. Neither the application nor its users will observe anything unusual.

This rule corresponds to CWE-295: Improper Certificate Validation.

Why This Matters

VERIFY_NONE is often introduced as a quick fix for SSL certificate errors during development, a self-signed cert, an expired cert in a staging environment, or a corporate proxy with its own root CA that is not in the system trust store. The fix makes the error disappear, and the code is sometimes committed and deployed to production without the developer realising the implication.

In production, the consequences can be severe. API credentials, OAuth tokens, webhook payloads, and user personal data transmitted over the “secured” connection are readable by anyone on the network path. For applications that call payment processors, identity providers, or internal microservices, credential theft can lead to account takeover, financial fraud, or full infrastructure compromise.

The Ruby ecosystem makes VERIFY_PEER the correct and default option for a reason: it enforces that the certificate chain is valid, trusted, and matches the hostname. Developers encountering certificate errors should fix the underlying certificate problem rather than disabling verification.

What Gets Flagged

The rule reports a .rb line (outside test and spec files) that assigns or passes OpenSSL::SSL::VERIFY_NONE, qualified or bare, or sets verify_mode to 0.

# FLAGGED: assigned to verify_mode
http.verify_mode = OpenSSL::SSL::VERIFY_NONE
ctx.verify_mode = OpenSSL::SSL::VERIFY_NONE

# FLAGGED: passed as a client option
Net::HTTP.start(uri.host, uri.port, use_ssl: true, verify_mode: OpenSSL::SSL::VERIFY_NONE)
ctx.set_params(:verify_mode => OpenSSL::SSL::VERIFY_NONE)
Faraday.new(url: base, ssl: { verify_mode: OpenSSL::SSL::VERIFY_NONE })

# FLAGGED: the global override
OpenSSL::SSL::VERIFY_PEER = OpenSSL::SSL::VERIFY_NONE

Not flagged: VERIFY_PEER, a comparison such as http.verify_mode == OpenSSL::SSL::VERIFY_NONE or defined?(OpenSSL::SSL::VERIFY_NONE), an option table entry like "none" => OpenSSL::SSL::VERIFY_NONE, comments, strings and test files. Options that disable verification without the constant (ssl: { verify: false }, HTTParty verify: false) are outside this rule.

Remediation

  1. Use OpenSSL::SSL::VERIFY_PEER (the default) for all production connections. This is the standard setting and requires no extra configuration when the server has a valid, CA-signed certificate:
# SAFE: explicit VERIFY_PEER (also the default)
http = Net::HTTP.new("api.example.com", 443)
http.use_ssl = true
http.verify_mode = OpenSSL::SSL::VERIFY_PEER
  1. If a custom CA is required (e.g., internal PKI), provide the CA bundle. Do not disable verification; instead, supply the trusted CA certificate so that validation can succeed:
# SAFE: trust a custom CA bundle without disabling verification
ctx = OpenSSL::SSL::SSLContext.new
ctx.verify_mode = OpenSSL::SSL::VERIFY_PEER
ctx.ca_file = "/etc/ssl/certs/internal-ca.crt"
  1. Fix underlying certificate issues rather than suppressing them. If the error is a hostname mismatch or an expired certificate in staging, fix the certificate. Use tools like Let’s Encrypt for free, automatically renewing certificates.

  2. Audit all HTTP client configurations. Search for verify: false, verify_ssl: false, and VERIFY_NONE across the codebase. High-level clients like Faraday, HTTParty, and RestClient all have their own certificate verification settings that must also be checked.

References

Suppressing this rule

Put a nosec comment on the line, or on line 1 to cover the whole file. Use the comment marker of the file’s language (#, //, -- or ;):

# nosec vnx-ruby-010
// nosec vnx-ruby-010

Or record an ignore rule: vulnetix ignore add --rule vnx-ruby-010 --reason "...". See Suppressing findings.

Edit this pageSources: cli/internal/sast/rules/vnx-ruby-010.rego, cli/internal/sast/docs/vnx-ruby-010.md
esc
↑ ↓ move↵ openSearches in your browser. A key like autonomy.max or a code like threshold_required jumps straight to it.