Repository navigation
feat(helm): make gateway PVC size and StorageClass configurable #3216
Description
User Story
As a Kubernetes platform operator deploying the OpenShell gateway through Helm, I want to select the gateway PVC's size and StorageClass, so that encrypted gateway state lands on the cluster's retained stateful storage with capacity appropriate to the deployment.
Problem Statement
OpenShell Helm chart 0.0.116 hard-codes the StatefulSet volumeClaimTemplates request to 1Gi and does not set or expose storageClassName. The chart exposes workspace PVC size/class values, but not the gateway database claim.
Impact / Why This Matters
Without chart values, operators must accept the cluster's default StorageClass and fixed capacity or carry a post-render patch. This can put the gateway's encrypted credential database and control-plane state on an unintended storage tier. A later correction may require StatefulSet/PVC migration because volumeClaimTemplates fields are immutable in common upgrade paths. Post-render patches are also coupled to the template's claim order.
Proposed Design
Expose a small gateway persistence block in Helm values, for example:
persistence:
size: 1Gi
storageClassName: ""The existing observable behavior should remain the default: a 1Gi claim using the cluster's default StorageClass when no values are set. Setting these values should render the requested capacity and storageClassName into the gateway StatefulSet. Naming is illustrative; the important user workflow is being able to declare both fields without a post-renderer.
Acceptance Criteria
- The gateway PVC request size is configurable through a documented chart value.
- The gateway PVC StorageClass is configurable through a documented chart value.
- Omitting the new values preserves the current
1Gi/default-StorageClass behavior. -
helm templatetests cover default and overridden values. - Upgrade documentation notes the StatefulSet/PVC immutability implications for existing releases.
Alternatives Considered
- Use the cluster's default StorageClass and expand the claim later. This does not guarantee the required retention/storage tier and depends on expansion support.
- Pre-create a PVC. The StatefulSet currently owns a
volumeClaimTemplateand has no existing-claim workflow. - Carry a Flux/Helm post-render patch. This works, but is coupled to the StatefulSet resource name and claim index, and it shifts a normal storage choice out of the chart's supported interface.
Agent Investigation
- Verified the behavior against the released chart
0.0.116at OCI digestsha256:df55cd1538bdfb7836834c30dfcf8373b85ffea83bbfd70d50dbe69407a0d2b3. - Rendering with production values still produces
resources.requests.storage: 1Giand nostorageClassNameuntil a post-render patch is applied. - Searched open and closed issues for Helm persistence,
volumeClaimTemplates, storage size, and StorageClass; no existing issue matched this gateway PVC gap.
Checklist
- I've reviewed existing issues and the architecture docs
- This is a design proposal, not a "please build this" request
Activity
lunarwhite commentedon Sep 14, 2026
I'd like to work on this.
Implementation Plan
Issue type:
featComplexity: Low
Confidence: High — clear path
Summary
Expose the gateway StatefulSet claim's request size and
storageClassNameasserver.databaseStorageSizeandserver.databaseStorageClass, rendering both intotemplates/statefulset.yaml. Empty defaults preserve the current1Girequest againstthe cluster's default StorageClass.
accessModesstays hard-coded atReadWriteOnce.Scope
deploy/helm/openshell/values.yaml: add both keys underserver:, adjacent todbUrl(line 221), with helm-docs
# --comments following the idiom ofserver.workspaceStorageClass(lines 241-245).deploy/helm/openshell/templates/statefulset.yaml: render both into the claim spec(line 26).
deploy/helm/openshell/tests/gateway_persistence_test.yaml(new): default andoverridden rendering.
deploy/helm/openshell/README.md.gotmpl: a#### Database PVC storagesubsectionunder
### Database backend(line 80) covering both values, thevolumeClaimTemplatesimmutability constraint, and how to change storage on an existing release.
deploy/helm/openshell/README.md: regenerated bymise run helm:docs;mise run helm:docs:checkis a required CI gate.docs/kubernetes/setup.mdx: both values in theConfigure Chart Valuestable(line 187) plus a
<Warning>pointing at the chart README for the storage-changeprocedure.
skills/debug-openshell-cluster/SKILL.md: amend the existing PVC-unbound row(line 740) to name the new StorageClass value, mirroring line 741, and add a row for the
forbidden-update upgrade failure.
Implementation Steps
statefulset.yamllines 22-26:gateway_pod_security_context_test.yaml, listing bothtemplates/gateway-config.yamland
templates/statefulset.yamlbecause_gateway-workload.tplline 14 checksums theconfig template.
setup.mdxrows and warning, regenerate the README,and amend the debug-skill rows.
Test Plan
gateway_persistence_test.yaml— the default render assertsstorageequals1GiandnotExistsonstorageClassName; an overridden renderasserts both values. The Deployment path has no PVC, and
gateway_config_test.yamllines 673-677 already assert that.
mise run helm:lintre-renders everyci/values-*.yamloverlay, none of which set storage keys.
e2e/change. Default rendering is unchanged.Risks & Open Questions
databaseStorageClassomits the field rather than setting"", so the chartoffers no way to request the disable-dynamic-provisioning semantics.
volumeClaimTemplatesis immutable on existing StatefulSets. Growing a claim isin-place PVC expansion where the StorageClass sets
allowVolumeExpansion, followed by anorphan-recreate so the template matches; changing StorageClass requires copying the data
to a new claim, because a recreated StatefulSet re-adopts existing claims unchanged.
Documented, per the acceptance criteria.
workload.kind=deploymentis a silent no-op. Documentedrather than guarded, because the HA overlay legitimately toggles
workload.kindfrom ashared values file.
Documentation Impact
deploy/helm/openshell/README.md.gotmpland the regeneratedREADME.md— theDatabase PVC storagesubsection plus the generated values rows.docs/kubernetes/setup.mdx— two values rows and the immutability warning.skills/debug-openshell-cluster/SKILL.md— one amended and one new troubleshooting row.docs/reference/gateway-config.mdxchange: these values render into theStatefulSet, not
gateway.toml.Revision 1 — initial plan
feat(helm): make gateway PVC size and StorageClass configurable