{"id":50636903,"url":"https://github.com/bluedynamics/plone-registryfromenviron","last_synced_at":"2026-06-16T14:32:34.539Z","repository":{"id":340990858,"uuid":"1168466110","full_name":"bluedynamics/plone-registryfromenviron","owner":"bluedynamics","description":"Override plone.registry values from environment variables.","archived":false,"fork":false,"pushed_at":"2026-04-20T22:28:48.000Z","size":57,"stargazers_count":0,"open_issues_count":2,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-04-21T00:31:21.188Z","etag":null,"topics":["cloudnative","plone","registry"],"latest_commit_sha":null,"homepage":"https://pypi.org/project/plone.registryfromenviron/","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/bluedynamics.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGES.md","contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-02-27T12:26:54.000Z","updated_at":"2026-04-20T22:25:25.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/bluedynamics/plone-registryfromenviron","commit_stats":null,"previous_names":["bluedynamics/plone-registryfromenviron"],"tags_count":1,"template":false,"template_full_name":null,"purl":"pkg:github/bluedynamics/plone-registryfromenviron","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bluedynamics%2Fplone-registryfromenviron","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bluedynamics%2Fplone-registryfromenviron/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bluedynamics%2Fplone-registryfromenviron/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bluedynamics%2Fplone-registryfromenviron/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/bluedynamics","download_url":"https://codeload.github.com/bluedynamics/plone-registryfromenviron/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bluedynamics%2Fplone-registryfromenviron/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":34410780,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-16T02:00:06.860Z","response_time":126,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["cloudnative","plone","registry"],"created_at":"2026-06-07T04:00:18.840Z","updated_at":"2026-06-16T14:32:34.534Z","avatar_url":"https://github.com/bluedynamics.png","language":"Python","funding_links":[],"categories":["Sysadmin"],"sub_categories":[],"readme":"# plone.registryfromenviron\n\nOverride `plone.registry` values from environment variables.\n\nPlone stores configuration in a persistent registry inside ZODB.\nThis works well for through-the-web editing, but conflicts with modern deployment practices where configuration is injected via environment variables.\n\nThis package bridges that gap, making Plone cloud-native and [12-factor app](https://12factor.net/config) friendly:\nthe same Plone image can run in development, staging and production with different settings -- controlled entirely by environment variables, no ZODB changes needed.\n\n## How it works\n\nAt import time, the package scans `os.environ` for `PLONE_REGISTRY_*` variables.\nIf any are present, it patches `plone.registry.registry.Registry.__getitem__` and `.get` so that reads consult the env-var values first, falling back to ZODB when a key is not overridden.\nIf no matching env vars are set, the package is a silent no-op with zero runtime cost.\n\nAll existing registry data is preserved — overrides are read-only and never written to ZODB.\n\n## Installation\n\nAdd the package to your Plone image / buildout / Python environment.\nThat's it — no GenericSetup profile needs to be applied and nothing is written to ZODB.\n\nThe package ships with a `plone.registryfromenviron:default` profile for backwards compatibility with 1.x, but it is an empty no-op.\nYou may leave it listed as a dependency in your own `metadata.xml` without any effect.\n\n\"Uninstalling\" means removing the package from the deployment (and restarting the processes).\nThere is no uninstall profile in 2.0.\n\n## Environment variable format\n\n```\nPLONE_REGISTRY_\u003cregistry_key\u003e=\u003cvalue\u003e\n```\n\nRegistry keys use dots (e.g. `plone.smtp_host`).\nSince dots are not allowed in environment variable names, replace each `.` with `__` (double underscore).\nSingle underscores are preserved as-is.\n\n### Examples\n\n```bash\n# plone.smtp_host = \"mail.example.com\"\nexport PLONE_REGISTRY_plone__smtp_host=mail.example.com\n\n# plone.app.theming.interfaces.IThemeSettings.enabled = False\nexport PLONE_REGISTRY_plone__app__theming__interfaces__IThemeSettings__enabled=false\n\n# plone.cachepurging.interfaces.ICachePurgingSettings.cachingProxies = [\"http://varnish:8080\"]\nexport PLONE_REGISTRY_plone__cachepurging__interfaces__ICachePurgingSettings__cachingProxies='[\"http://varnish:8080\"]'\n```\n\n## Type coercion\n\nValues are automatically coerced based on the existing registry record's field type:\n\n| Field type | Env value example | Result |\n|---|---|---|\n| Bool | `true`, `1`, `yes`, `on` | `True` |\n| Bool | `false`, `0`, `no`, `off` | `False` |\n| Int | `42` | `42` |\n| Float | `3.14` | `3.14` |\n| TextLine / Text | `hello` | `\"hello\"` |\n| List | `[\"a\", \"b\"]` | `[\"a\", \"b\"]` |\n| Tuple | `[\"a\", \"b\"]` | `(\"a\", \"b\")` |\n| Set | `[\"a\", \"b\"]` | `{\"a\", \"b\"}` |\n| Dict | `{\"key\": \"val\"}` | `{\"key\": \"val\"}` |\n\nCollection and dict values use JSON syntax.\n\n## Behavior\n\n- Environment variables are scanned **once at process startup**. Changes require a restart.\n- Activation is automatic: if `PLONE_REGISTRY_*` variables are present, the patch is applied at first import. If not, nothing happens.\n- Overrides are **read-only** — writes via the registry API still go to ZODB, but subsequent reads for overridden keys return the env value.\n- Only **existing** registry keys can be overridden (the field definition is needed for type coercion).\n- Invalid values or unknown keys are logged and silently skipped (ZODB value is used as fallback).\n- **Known limitation:** direct access via `registry.records['key'].value` bypasses the override, the same as in 1.x. Use `registry['key']`, `registry.get('key')`, or a `RecordsProxy` (all go through the patched read path).\n\n## Upgrading from 1.x\n\nVersion 2.0 drops the `portal_registry.__class__` swap approach (see [issue #1](https://github.com/bluedynamics/plone-registryfromenviron/issues/1) for the root-cause analysis).\n\nFor operators upgrading from 1.x:\n\n- **Deploy 2.0, then click \"Upgrade\" once in the Plone Add-ons control panel.** A GenericSetup upgrade step (1 → 2) clears any stale `EnvOverrideRegistry` class references from the site root and unregisters the addon from the \"Installed\" list of the control panel. Runtime activation is driven by env vars; the click only tidies up ZODB and the UI. If you do nothing, the addon keeps working correctly — the cleanup is cosmetic.\n- **No uninstall step needed.** Stop setting `PLONE_REGISTRY_*` env vars to deactivate, or remove the package from the deployment.\n- **The `plone.registryfromenviron:uninstall` profile is gone.** If your automation calls it, remove the call — it's a no-op.\n- **Activation is now import-driven, not install-step-driven.** Every pod picks up the behavior immediately on startup; no per-site install run is required anymore.\n\n## Source Code and Contributions\n\nThe source code is managed in a Git repository, with its main branches hosted on GitHub.\nIssues can be reported there too.\n\nWe'd be happy to see many forks and pull requests to make this package even better.\nWe welcome AI-assisted contributions, but expect every contributor to fully understand and be able to explain the code they submit.\nPlease don't send bulk auto-generated pull requests.\n\nMaintainers are Jens Klein, Johannes Raggam and the BlueDynamics Alliance developer team.\nWe appreciate any contribution and if a release on PyPI is needed, please just contact one of us.\nWe also offer commercial support if any training, coaching, integration or adaptations are needed.\n\n- [CHANGES.md](https://github.com/bluedynamics/plone-registryfromenviron/blob/main/CHANGES.md) -- changelog\n\n## License\n\nGPL-2.0-only\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbluedynamics%2Fplone-registryfromenviron","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fbluedynamics%2Fplone-registryfromenviron","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbluedynamics%2Fplone-registryfromenviron/lists"}