Feature Specification: Resource generateFiles
Created: 2026-10-07
Status: Implemented
Input: Reconstructed from the code of core/resources/generateFiles/ and its wiring in core/setups/ at 093e68b6f, pull requests #1184 and #1238, and issues #527, #1205 and #1206.
User Scenarios & Testing (mandatory)
The generateFiles resource gives a component generated values, such as
passwords and key pairs, that stay the same across rebuilds and that each
node that needs them can read. It also logs each node in to OpenBao. The
shared rules are in the resource family spec.
User Story 1 - Generate a secret once and read it on every node (Priority: P1)
Most components need secrets that nobody types in, often shared between
nodes. A component states an instance with its files and a generator
script. The vars provider runs the script once, stores the files in
OpenBao KV and renders them on each node that reads them.
Independent Test: a unit test of the resource, and contract tests of the
vars provider with a local and an OpenBao backend.
Acceptance Scenarios:
- Given an instance with a file, When the deployment evaluates, Then each file becomes a file secret of the
varsprovider, and a reader gets the path of the rendered file. - Given a script with dependencies, When the generator runs, Then it reads the files of each dependency and writes each of its own files.
User Story 2 - Log a node in to OpenBao with its SPIRE identity (Priority: P1)
Without a login, no secret renders on the node. The login logs in with certificate auth with the SPIRE SVID of the node, writes a token for the services that call OpenBao directly, and publishes the SVID pair. The OpenBao agent logs in by itself with that pair as the same role. The login repeats periodically.
Independent Test: a unit test of the agent configuration, and a VM test in which the agent renders a secret without a token file and a new login does not restart the agent.
Acceptance Scenarios:
- Given a healthy SPIRE agent, When the login runs, Then it logs in as the role of the node, writes the token atomically, and reloads or restarts the credential service but not the OpenBao agent.
- Given a SPIRE agent that stays unhealthy past a deadline, When the deadline comes, Then the login fails permanently.
- Given a new SVID pair, When the agent logs in again at the end of its token lifetime, Then it uses the new pair.
User Story 3 - Grow an instance without new values for the old files (Priority: P2)
A new file must not rotate a secret that is in use. An independent instance generates only its missing files. An atomic instance refuses a partial state.
Independent Test: a contract test of an independent instance.
User Story 4 - Grant access to vars a node does not generate (Priority: P3)
Some applications write their own vars, or only read the vars of another node. The request names these instances, and the setup grants the matching OpenBao write or read access with no generator, so the grants follow the requests and not a roster kept by hand.
Independent Test: no test covers this alone.
Edge Cases
- The agent trusts the configured CA only for an HTTPS address with a CA set.
- A node without an SVID pair, as in a test with a static token, logs the agent in with a token file.
- The SVID pair is not published yet: the agent login fails and retries after a short backoff, and the agent does not exit.
- The SVID expires before the token: the renewals fail, and near the end of the token lifetime the agent logs in again with the pair on disk.
- A node with no request still gets the agent, for example for the OIDC client secret.
- Two imports of the consumer module merge into one, because all nodes use the same OpenBao settings.
- The generator sees only its declared runtime inputs. A script that uses another program fails at run time.
Requirements (mandatory)
Functional Requirements
- FR-001: The request MUST accept the instances to generate, the instances that the node writes and the instances that the node only reads.
- FR-002: An instance MUST accept its files, a script, its runtime inputs, its dependencies and whether it is independent (atomic by default).
- FR-003: A file MUST accept whether it is secret (secret by default), an owner, a group and a mode. A file MUST be readable only by
rootby default. - FR-004: The policy MUST accept
routing, the OpenBao address, a token file, a CA and extra modules for each node, and MUST expose the consumer module. - FR-005:
processMUST merge the instances of all apps by instance name. - FR-006:
applyMUST emit nothing for an empty set of instances. - FR-007: The consumer module MUST default to the
varsprovider with theopenbaobackend, and to the OpenBao agent for environment secrets. - FR-008: With an SVID pair, the agent MUST log in with certificate auth with that pair as the role of the node, and MUST read the pair again at each login. Otherwise it MUST log in with the token file. It MUST NOT present a client certificate outside the login, and MUST start only when the network is online.
- FR-009: The login MUST restart after a failure without a start limit, except after the permanent failure at the SPIRE deadline.
- FR-010: The agent MUST restart after a failure without a start limit, because a missing CA stops it.
- FR-011: The services that upload vars and that render credentials MUST start after the login.
- FR-012: The login MUST read the SVID from the public socket of the local SPIRE agent.
Key Entities
- Instance: a named set of files with one generator. Its secret and public files are stored apart.
- Consumer module: the OpenBao agent and the credential service of a node.
Success Criteria (mandatory)
Measurable Outcomes
- SC-001: The unit test of the resource passes.
- SC-002: The contract tests of the
varsprovider, for both backends and for independent instances, pass. - SC-003: A VM test passes in which a generator runs with exactly its declared runtime inputs.
Assumptions
- The OpenBao address is the mTLS listener of OpenBao, not nginx, because nginx removes the client certificate.
- The login role is the cert-auth label of the node and the SVID name is the node name, as in setups and wiring.
postgresql,redisandgaragerender their credentials through this agent.