Skip to content

fix: preserve multiline SSL environment values in standalone YAML - #14074

Open
ruanweihong-aaa wants to merge 3 commits into
apache:masterfrom
ruanweihong-aaa:codex/fix-standalone-yaml-multiline-ssl
Open

ruanweihong-aaa wants to merge 3 commits into
apache:masterfrom
ruanweihong-aaa:codex/fix-standalone-yaml-multiline-ssl

Conversation

@ruanweihong-aaa

Copy link
Copy Markdown
Contributor

Description

Standalone YAML expands environment variables before parsing. Raw multiline PEM values can therefore cause YAML parse errors or have their newlines folded, preventing SSL resources from loading.

This change preserves multiline values when a complete environment reference is used in an SSL resource's cert, key, certs/keys array item, or client.ca.

For example, SERVER_CERT and SERVER_KEY can contain original multiline PEM:

ssls:
  - id: example
    snis: ["example.com"]
    cert: "${{SERVER_CERT}}"
    key: "${{SERVER_KEY}}"
#END

The loader builds a temporary discovery copy, identifies supported fields, and protects the corresponding variable occurrences with placeholders during the final YAML parse. It checks scalar source locations and final field paths before restoring the original values, preventing accidental replacement of user content.

CLI validation and runtime file reload share the same helper. No new dependency or configuration switch is introduced.

Compatibility and supported scope

  • Supports complete quoted or unquoted references in block-style and flow-style YAML.
  • Supports anchors and merges whose protected values are used only in supported SSL fields.
  • Preserves existing single-line substitution, YAML type inference, and literal \n escape handling.
  • Preserves existing folding and structure-expansion behavior for non-SSL multiline fields.
  • Reuses existing variable lookup, defaults, missing-variable errors, and exported-variable tracking.
  • Falls back to the existing loading behavior when discovery is ambiguous, protected references are shared with non-SSL fields, or final checks fail. These fallback cases do not receive the new multiline protection.
  • Does not add protection for embedded references or references inside literal/folded block scalars.
  • Preserves legacy expansion when an entire configuration is supplied through one variable; values introduced by another variable are not recursively expanded.

JSON and bootstrap config.yaml processing are unchanged. $ENV:// remains an existing alternative. This change does not bypass SSL schema or certificate validation.

Related issue

Related to #14038.

Validation

Tested using apache/apisix:3.19.0-ubuntu with the working-tree candidate mounted:

  • 24/24 focused regressions passed under plain LuaJIT.
  • 24/24 focused regressions passed under OpenResty.
  • Confirmed that stock CLI initialization rejects block-style unquoted multiline PEM.
  • Verified candidate startup with quoted PEM using the served certificate's SHA-256 fingerprint.
  • Verified that live YAML reload with unquoted flow references serves a different certificate.
  • Verified reload using the existing literal-backslash-n PEM format.
  • Verified explicit candidate apisix init.
  • Covered marker collisions, YAML escapes, structural substitution, shared anchors, and cyclic aliases.
  • Changed-file Lua lint passed with 0 warnings and 0 errors across four Lua files.
  • git diff --check and patch reverse-apply checks passed.

The full project test suite remains unverified. The release image lacks make and the complete project test environment; full-suite validation requires CI.

Checklist

  • I have explained the need for this PR and the problem it solves.
  • I have explained the changes.
  • I have added tests corresponding to this change.
  • I have updated the documentation.
  • I have verified that this change is backward compatible.

The compatibility checkbox remains open pending full CI validation and maintainer review of the documented fallback behavior.

@ruanweihong-aaa
ruanweihong-aaa marked this pull request as ready for review October 25, 2026 14:33
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant