Enterprise Store
Platform:
| Channel | Revision | Published | Runs on |
|---|---|---|---|
| latest/stable | 7 | 16 Oct 2026 | |
| latest/edge | 8 | 17 Oct 2026 |
juju deploy enterprise-store
Deploying in airgapped mode
This page describes how to deploy the enterprise-store charm in offline /
airgapped mode, in which nothing reaches the internet. The snaps that make up
the enterprise-store are shipped in through the store-bundle resource, and
blob storage is provided by an S3 backend via the
s3-integrator charm.
For a deployment that proxies the global Snap Store, see the Proxy mode deploy guide instead.
Offline mode requires two things in addition to a proxy-mode deployment:
- The
store-bundleresource, containing the snaps to install. - The
offlineconfig set totrue - The
s3-credentialsrelation to ans3-integrator, providing blob storage. The unit stays inBlockedStatusuntil this relation is established.
Prerequisites
Controller
A Juju controller on a machine cloud (for example LXD) is required:
sudo snap install juju
sudo snap install lxd
lxd init --auto
juju bootstrap localhost <controller_name>
PostgreSQL
The charm requires a PostgreSQL database over the postgresql_client
interface. The enterprise-store needs the btree_gist extension. The charm
requests the superuser role and attempts to provision the extension itself,
but it is recommended to also enable it explicitly on the PostgreSQL charm so
the extension is available regardless of role handling:
juju config postgresql plugin_btree_gist_enable=true
The offline store bundle
Everything needed for the airgapped install ships in a single tarball,
offline-snap-store.tar.gz, produced by registering the store with the
store-admin snap using the --offline flag:
store-admin register https://offline.example.com --offline
When extracted, the tarball contains an offline-snap-store/ directory holding:
snapd_*.snap,core22_*.snapandenterprise-store_*.snap- a matching
*.assertfile for each of those snaps proxy.assert- the store assertion, applied on first bootstrap onlyregistration_bundle.b64- the base64 registration bundle for theregistration_bundleconfig option
This single tarball is used in two different places, described below.
As the store-bundle resource
Attach the tarball to the charm as-is, as the store-bundle resource. All three
snaps are installed together whenever a new tarball is attached (because
enterprise-store depends on core22), but the store assertion is applied
exactly once. Updating the snaps later therefore never recreates the store, and
update tarballs may omit proxy.assert.
Attaching can be done at deploy time with --resource (see the deploy sections
below), or on an already-deployed charm with:
juju attach-resource enterprise-store store-bundle=./offline-snap-store.tar.gz
As the registration_bundle config option
The registration_bundle config value is not the tarball itself but the
registration_bundle.b64 file contained inside it, which must first be
extracted:
tar xzf offline-snap-store.tar.gz offline-snap-store/registration_bundle.b64
Once extracted, supply the contents of that file to the charm through the
registration_bundle config option, either during deployment (via the Juju
bundle or Terraform config shown below) or afterwards on the CLI:
juju config enterprise-store \
registration_bundle="$(cat offline-snap-store/registration_bundle.b64)"
S3 storage setup
The s3-integrator needs credentials and connection details for your S3
endpoint (for example MinIO). Credentials are provided through a Juju secret:
juju add-secret s3-creds access-key="<access-key>" secret-key="<secret-key>"
juju grant-secret s3-creds s3-integrator
juju config s3-integrator \
credentials=secret:<secret-id> \
endpoint=<s3-endpoint> \
bucket=<bucket-name>
The charm maps the s3-integrator connection info onto the enterprise-store snap
configuration as follows (the same bucket is used for both the scanned and
unscanned containers, and the charm sets proxy.storage.backend to s3):
| s3-integrator field | enterprise-store snap config |
|---|---|
| access-key | proxy.storage.s3.access-key-id |
| secret-key | proxy.storage.s3.secret-access-key |
| bucket | proxy.storage.s3.unscanned-container-name |
| bucket | proxy.storage.s3.scanned-container-name |
| endpoint | proxy.storage.s3.server-url |
| region | proxy.storage.s3.region |
| s3-uri-style | proxy.storage.s3.use-path-style |
Deploy with the Juju CLI
juju deploy postgresql --channel 14/stable
juju config postgresql plugin_btree_gist_enable=true
juju deploy enterprise-store --channel stable \
--config offline=true \
--resource store-bundle=./offline-snap-store.tar.gz
juju deploy s3-integrator --channel 2/stable
juju integrate postgresql:database enterprise-store:database
juju integrate s3-integrator enterprise-store:s3-credentials
juju config enterprise-store \
registration_bundle="$(cat offline-snap-store/registration_bundle.b64)"
If the charm is already deployed, a new bundle can be attached (and updated later) with:
juju attach-resource enterprise-store store-bundle=./offline-snap-store.tar.gz
Configure the s3-integrator credentials and connection details as shown in the
S3 storage setup section.
Deploy with a Juju bundle
applications:
postgresql:
charm: postgresql
channel: 14/stable
num_units: 1
options:
plugin_btree_gist_enable: true
s3-integrator:
charm: s3-integrator
channel: 2/stable
num_units: 1
enterprise-store:
charm: /path/to/charm
num_units: 3
options:
offline: true
registration_bundle: include-file://path/to/registration_bundle.b64
resources:
store-bundle: ./offline-snap-store.tar.gz
relations:
- - postgresql:database
- enterprise-store:database
- - s3-integrator
- enterprise-store:s3-credentials
With the above example it is assumed that offline-snap-store.tar.gz is
available in the current directory.
Deploy with Terraform
The Juju Terraform provider cannot deploy a purely local .charm using the most current release (v2.3.0). Without this offline deployments are not possible using terraform. This functionality may be added at some point at which point the information would be detailed in the provider documentation
High availability and TLS
For a highly available deployment (multiple units fronted by haproxy) and for TLS termination options, see the High availability deploy guide.