diff --git a/DECISIONS.md b/DECISIONS.md index f05efb6..e7a142d 100644 --- a/DECISIONS.md +++ b/DECISIONS.md @@ -121,3 +121,9 @@ Also adds `tzdata` to Noble's distro `extraPackages` (matching Jammy). FB3 relie **Decision:** The `update-repo` job in `publish-fork.yaml` only commits and pushes regenerated `generated/` and `README.md` when running on the fork's default branch (`github.event.repository.default_branch`). Dispatches on PR or feature branches still run `Invoke-Build Prepare` and `Invoke-Build Update-Readme` (so a template-substitution regression still fails the workflow) but skip the `git commit` / `git push`. Amends D-014 for the publish-fork case; `publish.yaml` (the official-repo publish) is unchanged. **Rationale:** `publish-fork.yaml` passes `-Registry 'ghcr.io/'` to `Update-Readme`, which substitutes the fork's registry into the README table header. The previous unguarded auto-commit pushed that fork-specific README back to whatever branch was dispatched, including branches with open upstream PRs — directly polluting the PR diff with content that must not land upstream, and breaking GitHub's linear rebase when the upstream master had its own concurrent `README.md` changes (observed during PR #43, which required a force-pushed clean rebase to unblock). Branch-gating preserves D-014's "generated/ tracked in git" invariant on the fork's default branch while keeping PR/feature branches diff-clean against upstream. Confines the `-Registry` rewrite to the only place the fork wants it (its own showcased README on `master`). + +## D-020: Non-root capable image, root remains the default user + +**Decision:** The image keeps running as `root` by default (no `USER` directive), but also supports running as `firebird` (UID 84) or as any UID with GID 0. Runtime-writable paths — `/opt/firebird` itself, `firebird.conf`, `SYSDBA.password`, `firebird.log`, `fb_guard`, `replication.log`, `security*.fdb`, `/tmp/firebird` and `$FIREBIRD_DATA` — are owned by `firebird:0` with group permissions equal to owner permissions (`g=u`). Binaries, libraries and plugins stay owned by `root`. The installer's leftover lock and shared memory files in `/tmp/firebird` are removed at build time. Every local `isql` connection in the entrypoint names its user explicitly (`-user SYSDBA`, or `FIREBIRD_USER` in `process_sql`). A non-root user without write access gets a warning on startup. + +**Rationale:** Requested in [issue #46](https://github.com/FirebirdSQL/firebird-docker/issues/46) (security policies requiring non-root containers; OpenShift). OpenShift's `restricted` SCC ignores the image's `USER` and injects a random UID with GID 0, so group-0 ownership is what makes it work, not a `USER` line; owner `firebird` keeps `--user firebird` working with GID 84. Local (embedded) connections take the OS user name as the Firebird user: `root` is mapped to SYSDBA, but UID 84 becomes `FIREBIRD` and a random UID has no name at all, which made `CREATE USER` fail and changed database/object ownership. `$FIREBIRD_DATA` is a `VOLUME`, so its ownership must be set in the image layer. Changing the default to `USER firebird` was rejected for now: existing volumes and bind mounts contain root-owned databases which a non-root container cannot open, so it would break deployments on upgrade. It belongs in a major release with explicit release notes. diff --git a/README.md b/README.md index afa59ea..a230a0a 100644 --- a/README.md +++ b/README.md @@ -323,6 +323,27 @@ Alternatively, you can use the same time zone as your host system by mapping the +## Running as a non-root user + +The container runs as `root` by default. It can also run as a non-root user, without any change in behavior: + +- as the `firebird` user (UID `84`), e.g. `docker run --user firebird ...`; or +- as **any** UID with GID `0` (`root` group), e.g. `docker run --user 12345:0 ...`. This is how OpenShift runs containers under its default `restricted` security context constraint, which assigns a random UID. + +```yaml +# Kubernetes + securityContext: + runAsNonRoot: true + runAsUser: 84 # or any UID... + runAsGroup: 0 # ...as long as the group is 0 +``` + +Other UID/GID combinations are not supported: the entrypoint shows a warning and Firebird cannot write its runtime files. + +> **IMPORTANT:** When using a bind mount or a pre-existing volume for `/var/lib/firebird/data`, it must be writable by the chosen user. Databases created while running as `root` are owned by `root`, and a non-root container cannot open them until you change their ownership (e.g. `chown -R 84:0` on the data directory). + + + ## Backup and Restore ### For online databases diff --git a/generated/3.0.10/bookworm/Dockerfile b/generated/3.0.10/bookworm/Dockerfile index 33a9de5..c8bc90a 100644 --- a/generated/3.0.10/bookworm/Dockerfile +++ b/generated/3.0.10/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.10/bookworm/entrypoint.sh b/generated/3.0.10/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.10/bookworm/entrypoint.sh +++ b/generated/3.0.10/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.10/bullseye/Dockerfile b/generated/3.0.10/bullseye/Dockerfile index 923d45e..121876e 100644 --- a/generated/3.0.10/bullseye/Dockerfile +++ b/generated/3.0.10/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.10/bullseye/entrypoint.sh b/generated/3.0.10/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.10/bullseye/entrypoint.sh +++ b/generated/3.0.10/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.10/jammy/Dockerfile b/generated/3.0.10/jammy/Dockerfile index 3a3bb1d..b1e6bb6 100644 --- a/generated/3.0.10/jammy/Dockerfile +++ b/generated/3.0.10/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.10/jammy/entrypoint.sh b/generated/3.0.10/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.10/jammy/entrypoint.sh +++ b/generated/3.0.10/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.10/noble/Dockerfile b/generated/3.0.10/noble/Dockerfile index 6a38647..3200e4a 100644 --- a/generated/3.0.10/noble/Dockerfile +++ b/generated/3.0.10/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.10/noble/entrypoint.sh b/generated/3.0.10/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.10/noble/entrypoint.sh +++ b/generated/3.0.10/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.10/trixie/Dockerfile b/generated/3.0.10/trixie/Dockerfile index 9c0b884..a85e86b 100644 --- a/generated/3.0.10/trixie/Dockerfile +++ b/generated/3.0.10/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.10/trixie/entrypoint.sh b/generated/3.0.10/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.10/trixie/entrypoint.sh +++ b/generated/3.0.10/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.11/bookworm/Dockerfile b/generated/3.0.11/bookworm/Dockerfile index 652383c..18f74a5 100644 --- a/generated/3.0.11/bookworm/Dockerfile +++ b/generated/3.0.11/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.11/bookworm/entrypoint.sh b/generated/3.0.11/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.11/bookworm/entrypoint.sh +++ b/generated/3.0.11/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.11/bullseye/Dockerfile b/generated/3.0.11/bullseye/Dockerfile index 0f4a13c..8bb0ab3 100644 --- a/generated/3.0.11/bullseye/Dockerfile +++ b/generated/3.0.11/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.11/bullseye/entrypoint.sh b/generated/3.0.11/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.11/bullseye/entrypoint.sh +++ b/generated/3.0.11/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.11/jammy/Dockerfile b/generated/3.0.11/jammy/Dockerfile index 2dd64b2..32bf277 100644 --- a/generated/3.0.11/jammy/Dockerfile +++ b/generated/3.0.11/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.11/jammy/entrypoint.sh b/generated/3.0.11/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.11/jammy/entrypoint.sh +++ b/generated/3.0.11/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.11/noble/Dockerfile b/generated/3.0.11/noble/Dockerfile index 3c2e520..9998d97 100644 --- a/generated/3.0.11/noble/Dockerfile +++ b/generated/3.0.11/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.11/noble/entrypoint.sh b/generated/3.0.11/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.11/noble/entrypoint.sh +++ b/generated/3.0.11/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.11/trixie/Dockerfile b/generated/3.0.11/trixie/Dockerfile index c5ed8c1..ada64f2 100644 --- a/generated/3.0.11/trixie/Dockerfile +++ b/generated/3.0.11/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.11/trixie/entrypoint.sh b/generated/3.0.11/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.11/trixie/entrypoint.sh +++ b/generated/3.0.11/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.12/bookworm/Dockerfile b/generated/3.0.12/bookworm/Dockerfile index 7861cfc..2d1c957 100644 --- a/generated/3.0.12/bookworm/Dockerfile +++ b/generated/3.0.12/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.12/bookworm/entrypoint.sh b/generated/3.0.12/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.12/bookworm/entrypoint.sh +++ b/generated/3.0.12/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.12/bullseye/Dockerfile b/generated/3.0.12/bullseye/Dockerfile index 8cca737..826d326 100644 --- a/generated/3.0.12/bullseye/Dockerfile +++ b/generated/3.0.12/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.12/bullseye/entrypoint.sh b/generated/3.0.12/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.12/bullseye/entrypoint.sh +++ b/generated/3.0.12/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.12/jammy/Dockerfile b/generated/3.0.12/jammy/Dockerfile index e7d841a..de7bb3d 100644 --- a/generated/3.0.12/jammy/Dockerfile +++ b/generated/3.0.12/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.12/jammy/entrypoint.sh b/generated/3.0.12/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.12/jammy/entrypoint.sh +++ b/generated/3.0.12/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.12/noble/Dockerfile b/generated/3.0.12/noble/Dockerfile index e8883d0..f56492b 100644 --- a/generated/3.0.12/noble/Dockerfile +++ b/generated/3.0.12/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.12/noble/entrypoint.sh b/generated/3.0.12/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.12/noble/entrypoint.sh +++ b/generated/3.0.12/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.12/trixie/Dockerfile b/generated/3.0.12/trixie/Dockerfile index 3f2b4d7..d991550 100644 --- a/generated/3.0.12/trixie/Dockerfile +++ b/generated/3.0.12/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.12/trixie/entrypoint.sh b/generated/3.0.12/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.12/trixie/entrypoint.sh +++ b/generated/3.0.12/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.13/bookworm/Dockerfile b/generated/3.0.13/bookworm/Dockerfile index 8fc958c..4c455cd 100644 --- a/generated/3.0.13/bookworm/Dockerfile +++ b/generated/3.0.13/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.13/bookworm/entrypoint.sh b/generated/3.0.13/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.13/bookworm/entrypoint.sh +++ b/generated/3.0.13/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.13/bullseye/Dockerfile b/generated/3.0.13/bullseye/Dockerfile index 6a33d34..ea8f888 100644 --- a/generated/3.0.13/bullseye/Dockerfile +++ b/generated/3.0.13/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.13/bullseye/entrypoint.sh b/generated/3.0.13/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.13/bullseye/entrypoint.sh +++ b/generated/3.0.13/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.13/jammy/Dockerfile b/generated/3.0.13/jammy/Dockerfile index 9afb0b4..c8d9c8f 100644 --- a/generated/3.0.13/jammy/Dockerfile +++ b/generated/3.0.13/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.13/jammy/entrypoint.sh b/generated/3.0.13/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.13/jammy/entrypoint.sh +++ b/generated/3.0.13/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.13/noble/Dockerfile b/generated/3.0.13/noble/Dockerfile index dff334e..6d13531 100644 --- a/generated/3.0.13/noble/Dockerfile +++ b/generated/3.0.13/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.13/noble/entrypoint.sh b/generated/3.0.13/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.13/noble/entrypoint.sh +++ b/generated/3.0.13/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.13/trixie/Dockerfile b/generated/3.0.13/trixie/Dockerfile index 5f9f67c..99ef77b 100644 --- a/generated/3.0.13/trixie/Dockerfile +++ b/generated/3.0.13/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.13/trixie/entrypoint.sh b/generated/3.0.13/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.13/trixie/entrypoint.sh +++ b/generated/3.0.13/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.14/bookworm/Dockerfile b/generated/3.0.14/bookworm/Dockerfile index 4c850b0..c12a6ba 100644 --- a/generated/3.0.14/bookworm/Dockerfile +++ b/generated/3.0.14/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.14/bookworm/entrypoint.sh b/generated/3.0.14/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.14/bookworm/entrypoint.sh +++ b/generated/3.0.14/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.14/bullseye/Dockerfile b/generated/3.0.14/bullseye/Dockerfile index 4779946..1bfe48d 100644 --- a/generated/3.0.14/bullseye/Dockerfile +++ b/generated/3.0.14/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.14/bullseye/entrypoint.sh b/generated/3.0.14/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.14/bullseye/entrypoint.sh +++ b/generated/3.0.14/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.14/jammy/Dockerfile b/generated/3.0.14/jammy/Dockerfile index 1c3c449..8e1f7c7 100644 --- a/generated/3.0.14/jammy/Dockerfile +++ b/generated/3.0.14/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.14/jammy/entrypoint.sh b/generated/3.0.14/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.14/jammy/entrypoint.sh +++ b/generated/3.0.14/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.14/noble/Dockerfile b/generated/3.0.14/noble/Dockerfile index eafebd0..98144fe 100644 --- a/generated/3.0.14/noble/Dockerfile +++ b/generated/3.0.14/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.14/noble/entrypoint.sh b/generated/3.0.14/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.14/noble/entrypoint.sh +++ b/generated/3.0.14/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.14/trixie/Dockerfile b/generated/3.0.14/trixie/Dockerfile index 96f3f62..4f9fa8f 100644 --- a/generated/3.0.14/trixie/Dockerfile +++ b/generated/3.0.14/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.14/trixie/entrypoint.sh b/generated/3.0.14/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.14/trixie/entrypoint.sh +++ b/generated/3.0.14/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.9/bookworm/Dockerfile b/generated/3.0.9/bookworm/Dockerfile index 1edf8d1..b9c2ca7 100644 --- a/generated/3.0.9/bookworm/Dockerfile +++ b/generated/3.0.9/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.9/bookworm/entrypoint.sh b/generated/3.0.9/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.9/bookworm/entrypoint.sh +++ b/generated/3.0.9/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.9/bullseye/Dockerfile b/generated/3.0.9/bullseye/Dockerfile index 8c9760f..a005e55 100644 --- a/generated/3.0.9/bullseye/Dockerfile +++ b/generated/3.0.9/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.9/bullseye/entrypoint.sh b/generated/3.0.9/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.9/bullseye/entrypoint.sh +++ b/generated/3.0.9/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.9/jammy/Dockerfile b/generated/3.0.9/jammy/Dockerfile index a650711..740f2a6 100644 --- a/generated/3.0.9/jammy/Dockerfile +++ b/generated/3.0.9/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.9/jammy/entrypoint.sh b/generated/3.0.9/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.9/jammy/entrypoint.sh +++ b/generated/3.0.9/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.9/noble/Dockerfile b/generated/3.0.9/noble/Dockerfile index e151d28..c7cfe20 100644 --- a/generated/3.0.9/noble/Dockerfile +++ b/generated/3.0.9/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.9/noble/entrypoint.sh b/generated/3.0.9/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.9/noble/entrypoint.sh +++ b/generated/3.0.9/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/3.0.9/trixie/Dockerfile b/generated/3.0.9/trixie/Dockerfile index 7362a0b..118037b 100644 --- a/generated/3.0.9/trixie/Dockerfile +++ b/generated/3.0.9/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/3.0.9/trixie/entrypoint.sh b/generated/3.0.9/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/3.0.9/trixie/entrypoint.sh +++ b/generated/3.0.9/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.0/bookworm/Dockerfile b/generated/4.0.0/bookworm/Dockerfile index fd0f375..ad21d0d 100644 --- a/generated/4.0.0/bookworm/Dockerfile +++ b/generated/4.0.0/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.0/bookworm/entrypoint.sh b/generated/4.0.0/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.0/bookworm/entrypoint.sh +++ b/generated/4.0.0/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.0/bullseye/Dockerfile b/generated/4.0.0/bullseye/Dockerfile index e46610c..7df5214 100644 --- a/generated/4.0.0/bullseye/Dockerfile +++ b/generated/4.0.0/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.0/bullseye/entrypoint.sh b/generated/4.0.0/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.0/bullseye/entrypoint.sh +++ b/generated/4.0.0/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.0/jammy/Dockerfile b/generated/4.0.0/jammy/Dockerfile index 4e92ede..5ec2193 100644 --- a/generated/4.0.0/jammy/Dockerfile +++ b/generated/4.0.0/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.0/jammy/entrypoint.sh b/generated/4.0.0/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.0/jammy/entrypoint.sh +++ b/generated/4.0.0/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.0/noble/Dockerfile b/generated/4.0.0/noble/Dockerfile index bb272eb..c3b9cf4 100644 --- a/generated/4.0.0/noble/Dockerfile +++ b/generated/4.0.0/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.0/noble/entrypoint.sh b/generated/4.0.0/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.0/noble/entrypoint.sh +++ b/generated/4.0.0/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.0/trixie/Dockerfile b/generated/4.0.0/trixie/Dockerfile index ead67a4..a709146 100644 --- a/generated/4.0.0/trixie/Dockerfile +++ b/generated/4.0.0/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.0/trixie/entrypoint.sh b/generated/4.0.0/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.0/trixie/entrypoint.sh +++ b/generated/4.0.0/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.1/bookworm/Dockerfile b/generated/4.0.1/bookworm/Dockerfile index b07bb8c..eee42d7 100644 --- a/generated/4.0.1/bookworm/Dockerfile +++ b/generated/4.0.1/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.1/bookworm/entrypoint.sh b/generated/4.0.1/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.1/bookworm/entrypoint.sh +++ b/generated/4.0.1/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.1/bullseye/Dockerfile b/generated/4.0.1/bullseye/Dockerfile index d685b6c..a33df5f 100644 --- a/generated/4.0.1/bullseye/Dockerfile +++ b/generated/4.0.1/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.1/bullseye/entrypoint.sh b/generated/4.0.1/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.1/bullseye/entrypoint.sh +++ b/generated/4.0.1/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.1/jammy/Dockerfile b/generated/4.0.1/jammy/Dockerfile index dcdf5cc..8338069 100644 --- a/generated/4.0.1/jammy/Dockerfile +++ b/generated/4.0.1/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.1/jammy/entrypoint.sh b/generated/4.0.1/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.1/jammy/entrypoint.sh +++ b/generated/4.0.1/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.1/noble/Dockerfile b/generated/4.0.1/noble/Dockerfile index a0c96fb..f0190c4 100644 --- a/generated/4.0.1/noble/Dockerfile +++ b/generated/4.0.1/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.1/noble/entrypoint.sh b/generated/4.0.1/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.1/noble/entrypoint.sh +++ b/generated/4.0.1/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.1/trixie/Dockerfile b/generated/4.0.1/trixie/Dockerfile index e05defa..d7d247e 100644 --- a/generated/4.0.1/trixie/Dockerfile +++ b/generated/4.0.1/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.1/trixie/entrypoint.sh b/generated/4.0.1/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.1/trixie/entrypoint.sh +++ b/generated/4.0.1/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.2/bookworm/Dockerfile b/generated/4.0.2/bookworm/Dockerfile index d72ad5f..27e124c 100644 --- a/generated/4.0.2/bookworm/Dockerfile +++ b/generated/4.0.2/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.2/bookworm/entrypoint.sh b/generated/4.0.2/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.2/bookworm/entrypoint.sh +++ b/generated/4.0.2/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.2/bullseye/Dockerfile b/generated/4.0.2/bullseye/Dockerfile index ffec909..07f4993 100644 --- a/generated/4.0.2/bullseye/Dockerfile +++ b/generated/4.0.2/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.2/bullseye/entrypoint.sh b/generated/4.0.2/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.2/bullseye/entrypoint.sh +++ b/generated/4.0.2/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.2/jammy/Dockerfile b/generated/4.0.2/jammy/Dockerfile index 054feb1..b33b6c8 100644 --- a/generated/4.0.2/jammy/Dockerfile +++ b/generated/4.0.2/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.2/jammy/entrypoint.sh b/generated/4.0.2/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.2/jammy/entrypoint.sh +++ b/generated/4.0.2/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.2/noble/Dockerfile b/generated/4.0.2/noble/Dockerfile index ff8914e..fff758b 100644 --- a/generated/4.0.2/noble/Dockerfile +++ b/generated/4.0.2/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.2/noble/entrypoint.sh b/generated/4.0.2/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.2/noble/entrypoint.sh +++ b/generated/4.0.2/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.2/trixie/Dockerfile b/generated/4.0.2/trixie/Dockerfile index 877ca13..9b7b207 100644 --- a/generated/4.0.2/trixie/Dockerfile +++ b/generated/4.0.2/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.2/trixie/entrypoint.sh b/generated/4.0.2/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.2/trixie/entrypoint.sh +++ b/generated/4.0.2/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.3/bookworm/Dockerfile b/generated/4.0.3/bookworm/Dockerfile index 4884ae3..08cea52 100644 --- a/generated/4.0.3/bookworm/Dockerfile +++ b/generated/4.0.3/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.3/bookworm/entrypoint.sh b/generated/4.0.3/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.3/bookworm/entrypoint.sh +++ b/generated/4.0.3/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.3/bullseye/Dockerfile b/generated/4.0.3/bullseye/Dockerfile index 03484db..4b9353c 100644 --- a/generated/4.0.3/bullseye/Dockerfile +++ b/generated/4.0.3/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.3/bullseye/entrypoint.sh b/generated/4.0.3/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.3/bullseye/entrypoint.sh +++ b/generated/4.0.3/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.3/jammy/Dockerfile b/generated/4.0.3/jammy/Dockerfile index 6d8cae3..7491efa 100644 --- a/generated/4.0.3/jammy/Dockerfile +++ b/generated/4.0.3/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.3/jammy/entrypoint.sh b/generated/4.0.3/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.3/jammy/entrypoint.sh +++ b/generated/4.0.3/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.3/noble/Dockerfile b/generated/4.0.3/noble/Dockerfile index 6e9e7b8..467989a 100644 --- a/generated/4.0.3/noble/Dockerfile +++ b/generated/4.0.3/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.3/noble/entrypoint.sh b/generated/4.0.3/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.3/noble/entrypoint.sh +++ b/generated/4.0.3/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.3/trixie/Dockerfile b/generated/4.0.3/trixie/Dockerfile index 3d03792..37fa261 100644 --- a/generated/4.0.3/trixie/Dockerfile +++ b/generated/4.0.3/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.3/trixie/entrypoint.sh b/generated/4.0.3/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.3/trixie/entrypoint.sh +++ b/generated/4.0.3/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.4/bookworm/Dockerfile b/generated/4.0.4/bookworm/Dockerfile index 9a355b5..c01bd0c 100644 --- a/generated/4.0.4/bookworm/Dockerfile +++ b/generated/4.0.4/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.4/bookworm/entrypoint.sh b/generated/4.0.4/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.4/bookworm/entrypoint.sh +++ b/generated/4.0.4/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.4/bullseye/Dockerfile b/generated/4.0.4/bullseye/Dockerfile index 84ca99f..6dfe627 100644 --- a/generated/4.0.4/bullseye/Dockerfile +++ b/generated/4.0.4/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.4/bullseye/entrypoint.sh b/generated/4.0.4/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.4/bullseye/entrypoint.sh +++ b/generated/4.0.4/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.4/jammy/Dockerfile b/generated/4.0.4/jammy/Dockerfile index f0c5992..0ae464e 100644 --- a/generated/4.0.4/jammy/Dockerfile +++ b/generated/4.0.4/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.4/jammy/entrypoint.sh b/generated/4.0.4/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.4/jammy/entrypoint.sh +++ b/generated/4.0.4/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.4/noble/Dockerfile b/generated/4.0.4/noble/Dockerfile index 51ef49f..736ed3f 100644 --- a/generated/4.0.4/noble/Dockerfile +++ b/generated/4.0.4/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.4/noble/entrypoint.sh b/generated/4.0.4/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.4/noble/entrypoint.sh +++ b/generated/4.0.4/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.4/trixie/Dockerfile b/generated/4.0.4/trixie/Dockerfile index 2906a6e..1867673 100644 --- a/generated/4.0.4/trixie/Dockerfile +++ b/generated/4.0.4/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.4/trixie/entrypoint.sh b/generated/4.0.4/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.4/trixie/entrypoint.sh +++ b/generated/4.0.4/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.5/bookworm/Dockerfile b/generated/4.0.5/bookworm/Dockerfile index e9b450f..1753a77 100644 --- a/generated/4.0.5/bookworm/Dockerfile +++ b/generated/4.0.5/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.5/bookworm/entrypoint.sh b/generated/4.0.5/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.5/bookworm/entrypoint.sh +++ b/generated/4.0.5/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.5/bullseye/Dockerfile b/generated/4.0.5/bullseye/Dockerfile index fa82a48..d215647 100644 --- a/generated/4.0.5/bullseye/Dockerfile +++ b/generated/4.0.5/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.5/bullseye/entrypoint.sh b/generated/4.0.5/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.5/bullseye/entrypoint.sh +++ b/generated/4.0.5/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.5/jammy/Dockerfile b/generated/4.0.5/jammy/Dockerfile index ef6f30d..9b03062 100644 --- a/generated/4.0.5/jammy/Dockerfile +++ b/generated/4.0.5/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.5/jammy/entrypoint.sh b/generated/4.0.5/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.5/jammy/entrypoint.sh +++ b/generated/4.0.5/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.5/noble/Dockerfile b/generated/4.0.5/noble/Dockerfile index 35e9467..01919b5 100644 --- a/generated/4.0.5/noble/Dockerfile +++ b/generated/4.0.5/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.5/noble/entrypoint.sh b/generated/4.0.5/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.5/noble/entrypoint.sh +++ b/generated/4.0.5/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.5/trixie/Dockerfile b/generated/4.0.5/trixie/Dockerfile index 105e14e..c29e1f1 100644 --- a/generated/4.0.5/trixie/Dockerfile +++ b/generated/4.0.5/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.5/trixie/entrypoint.sh b/generated/4.0.5/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.5/trixie/entrypoint.sh +++ b/generated/4.0.5/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.6/bookworm/Dockerfile b/generated/4.0.6/bookworm/Dockerfile index f64e601..25d0ff1 100644 --- a/generated/4.0.6/bookworm/Dockerfile +++ b/generated/4.0.6/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.6/bookworm/entrypoint.sh b/generated/4.0.6/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.6/bookworm/entrypoint.sh +++ b/generated/4.0.6/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.6/bullseye/Dockerfile b/generated/4.0.6/bullseye/Dockerfile index 733b01b..c2d3e9c 100644 --- a/generated/4.0.6/bullseye/Dockerfile +++ b/generated/4.0.6/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.6/bullseye/entrypoint.sh b/generated/4.0.6/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.6/bullseye/entrypoint.sh +++ b/generated/4.0.6/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.6/jammy/Dockerfile b/generated/4.0.6/jammy/Dockerfile index 2e507c4..824835d 100644 --- a/generated/4.0.6/jammy/Dockerfile +++ b/generated/4.0.6/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.6/jammy/entrypoint.sh b/generated/4.0.6/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.6/jammy/entrypoint.sh +++ b/generated/4.0.6/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.6/noble/Dockerfile b/generated/4.0.6/noble/Dockerfile index 7469096..2d09823 100644 --- a/generated/4.0.6/noble/Dockerfile +++ b/generated/4.0.6/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.6/noble/entrypoint.sh b/generated/4.0.6/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.6/noble/entrypoint.sh +++ b/generated/4.0.6/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.6/trixie/Dockerfile b/generated/4.0.6/trixie/Dockerfile index cb094ff..beaf27d 100644 --- a/generated/4.0.6/trixie/Dockerfile +++ b/generated/4.0.6/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.6/trixie/entrypoint.sh b/generated/4.0.6/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.6/trixie/entrypoint.sh +++ b/generated/4.0.6/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.7/bookworm/Dockerfile b/generated/4.0.7/bookworm/Dockerfile index cb02b6e..dba350c 100644 --- a/generated/4.0.7/bookworm/Dockerfile +++ b/generated/4.0.7/bookworm/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.7/bookworm/entrypoint.sh b/generated/4.0.7/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.7/bookworm/entrypoint.sh +++ b/generated/4.0.7/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.7/bullseye/Dockerfile b/generated/4.0.7/bullseye/Dockerfile index d490cad..ed8750b 100644 --- a/generated/4.0.7/bullseye/Dockerfile +++ b/generated/4.0.7/bullseye/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.7/bullseye/entrypoint.sh b/generated/4.0.7/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.7/bullseye/entrypoint.sh +++ b/generated/4.0.7/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.7/jammy/Dockerfile b/generated/4.0.7/jammy/Dockerfile index 914f687..7b5a713 100644 --- a/generated/4.0.7/jammy/Dockerfile +++ b/generated/4.0.7/jammy/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.7/jammy/entrypoint.sh b/generated/4.0.7/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.7/jammy/entrypoint.sh +++ b/generated/4.0.7/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.7/noble/Dockerfile b/generated/4.0.7/noble/Dockerfile index b3a5c6b..b5d4f19 100644 --- a/generated/4.0.7/noble/Dockerfile +++ b/generated/4.0.7/noble/Dockerfile @@ -121,10 +121,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.7/noble/entrypoint.sh b/generated/4.0.7/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.7/noble/entrypoint.sh +++ b/generated/4.0.7/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/4.0.7/trixie/Dockerfile b/generated/4.0.7/trixie/Dockerfile index 2d006c0..be0b15e 100644 --- a/generated/4.0.7/trixie/Dockerfile +++ b/generated/4.0.7/trixie/Dockerfile @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/4.0.7/trixie/entrypoint.sh b/generated/4.0.7/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/4.0.7/trixie/entrypoint.sh +++ b/generated/4.0.7/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.0/bookworm/Dockerfile b/generated/5.0.0/bookworm/Dockerfile index 785100b..287d9d9 100644 --- a/generated/5.0.0/bookworm/Dockerfile +++ b/generated/5.0.0/bookworm/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.0/bookworm/entrypoint.sh b/generated/5.0.0/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.0/bookworm/entrypoint.sh +++ b/generated/5.0.0/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.0/bullseye/Dockerfile b/generated/5.0.0/bullseye/Dockerfile index a9fcc69..256fbbe 100644 --- a/generated/5.0.0/bullseye/Dockerfile +++ b/generated/5.0.0/bullseye/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.0/bullseye/entrypoint.sh b/generated/5.0.0/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.0/bullseye/entrypoint.sh +++ b/generated/5.0.0/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.0/jammy/Dockerfile b/generated/5.0.0/jammy/Dockerfile index 0266f19..c068239 100644 --- a/generated/5.0.0/jammy/Dockerfile +++ b/generated/5.0.0/jammy/Dockerfile @@ -125,10 +125,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.0/jammy/entrypoint.sh b/generated/5.0.0/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.0/jammy/entrypoint.sh +++ b/generated/5.0.0/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.0/noble/Dockerfile b/generated/5.0.0/noble/Dockerfile index f541232..26ca720 100644 --- a/generated/5.0.0/noble/Dockerfile +++ b/generated/5.0.0/noble/Dockerfile @@ -125,10 +125,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.0/noble/entrypoint.sh b/generated/5.0.0/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.0/noble/entrypoint.sh +++ b/generated/5.0.0/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.0/trixie/Dockerfile b/generated/5.0.0/trixie/Dockerfile index 1a0f1ca..f879ee4 100644 --- a/generated/5.0.0/trixie/Dockerfile +++ b/generated/5.0.0/trixie/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.0/trixie/entrypoint.sh b/generated/5.0.0/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.0/trixie/entrypoint.sh +++ b/generated/5.0.0/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.1/bookworm/Dockerfile b/generated/5.0.1/bookworm/Dockerfile index f12214e..6f94307 100644 --- a/generated/5.0.1/bookworm/Dockerfile +++ b/generated/5.0.1/bookworm/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.1/bookworm/entrypoint.sh b/generated/5.0.1/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.1/bookworm/entrypoint.sh +++ b/generated/5.0.1/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.1/bullseye/Dockerfile b/generated/5.0.1/bullseye/Dockerfile index 9eb494c..c781c7b 100644 --- a/generated/5.0.1/bullseye/Dockerfile +++ b/generated/5.0.1/bullseye/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.1/bullseye/entrypoint.sh b/generated/5.0.1/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.1/bullseye/entrypoint.sh +++ b/generated/5.0.1/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.1/jammy/Dockerfile b/generated/5.0.1/jammy/Dockerfile index b232966..e761853 100644 --- a/generated/5.0.1/jammy/Dockerfile +++ b/generated/5.0.1/jammy/Dockerfile @@ -125,10 +125,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.1/jammy/entrypoint.sh b/generated/5.0.1/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.1/jammy/entrypoint.sh +++ b/generated/5.0.1/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.1/noble/Dockerfile b/generated/5.0.1/noble/Dockerfile index 712a51f..7685c26 100644 --- a/generated/5.0.1/noble/Dockerfile +++ b/generated/5.0.1/noble/Dockerfile @@ -125,10 +125,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.1/noble/entrypoint.sh b/generated/5.0.1/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.1/noble/entrypoint.sh +++ b/generated/5.0.1/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.1/trixie/Dockerfile b/generated/5.0.1/trixie/Dockerfile index f470973..04b34da 100644 --- a/generated/5.0.1/trixie/Dockerfile +++ b/generated/5.0.1/trixie/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.1/trixie/entrypoint.sh b/generated/5.0.1/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.1/trixie/entrypoint.sh +++ b/generated/5.0.1/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.2/bookworm/Dockerfile b/generated/5.0.2/bookworm/Dockerfile index 6fb9081..8612057 100644 --- a/generated/5.0.2/bookworm/Dockerfile +++ b/generated/5.0.2/bookworm/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.2/bookworm/entrypoint.sh b/generated/5.0.2/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.2/bookworm/entrypoint.sh +++ b/generated/5.0.2/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.2/bullseye/Dockerfile b/generated/5.0.2/bullseye/Dockerfile index 0de59be..ba9b561 100644 --- a/generated/5.0.2/bullseye/Dockerfile +++ b/generated/5.0.2/bullseye/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.2/bullseye/entrypoint.sh b/generated/5.0.2/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.2/bullseye/entrypoint.sh +++ b/generated/5.0.2/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.2/jammy/Dockerfile b/generated/5.0.2/jammy/Dockerfile index 14c6815..0bf40a8 100644 --- a/generated/5.0.2/jammy/Dockerfile +++ b/generated/5.0.2/jammy/Dockerfile @@ -125,10 +125,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.2/jammy/entrypoint.sh b/generated/5.0.2/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.2/jammy/entrypoint.sh +++ b/generated/5.0.2/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.2/noble/Dockerfile b/generated/5.0.2/noble/Dockerfile index dacf5b6..7405faf 100644 --- a/generated/5.0.2/noble/Dockerfile +++ b/generated/5.0.2/noble/Dockerfile @@ -125,10 +125,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.2/noble/entrypoint.sh b/generated/5.0.2/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.2/noble/entrypoint.sh +++ b/generated/5.0.2/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.2/trixie/Dockerfile b/generated/5.0.2/trixie/Dockerfile index 4b17087..3df5c94 100644 --- a/generated/5.0.2/trixie/Dockerfile +++ b/generated/5.0.2/trixie/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.2/trixie/entrypoint.sh b/generated/5.0.2/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.2/trixie/entrypoint.sh +++ b/generated/5.0.2/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.3/bookworm/Dockerfile b/generated/5.0.3/bookworm/Dockerfile index cba1ef7..91b933e 100644 --- a/generated/5.0.3/bookworm/Dockerfile +++ b/generated/5.0.3/bookworm/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.3/bookworm/entrypoint.sh b/generated/5.0.3/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.3/bookworm/entrypoint.sh +++ b/generated/5.0.3/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.3/bullseye/Dockerfile b/generated/5.0.3/bullseye/Dockerfile index c397c41..538c4e5 100644 --- a/generated/5.0.3/bullseye/Dockerfile +++ b/generated/5.0.3/bullseye/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.3/bullseye/entrypoint.sh b/generated/5.0.3/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.3/bullseye/entrypoint.sh +++ b/generated/5.0.3/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.3/jammy/Dockerfile b/generated/5.0.3/jammy/Dockerfile index 52eed8d..693e515 100644 --- a/generated/5.0.3/jammy/Dockerfile +++ b/generated/5.0.3/jammy/Dockerfile @@ -125,10 +125,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.3/jammy/entrypoint.sh b/generated/5.0.3/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.3/jammy/entrypoint.sh +++ b/generated/5.0.3/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.3/noble/Dockerfile b/generated/5.0.3/noble/Dockerfile index f47b26d..a1a8a76 100644 --- a/generated/5.0.3/noble/Dockerfile +++ b/generated/5.0.3/noble/Dockerfile @@ -125,10 +125,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.3/noble/entrypoint.sh b/generated/5.0.3/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.3/noble/entrypoint.sh +++ b/generated/5.0.3/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.3/trixie/Dockerfile b/generated/5.0.3/trixie/Dockerfile index 0df8a3a..fe931f3 100644 --- a/generated/5.0.3/trixie/Dockerfile +++ b/generated/5.0.3/trixie/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.3/trixie/entrypoint.sh b/generated/5.0.3/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.3/trixie/entrypoint.sh +++ b/generated/5.0.3/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.4/bookworm/Dockerfile b/generated/5.0.4/bookworm/Dockerfile index 1c9b378..0ba73a9 100644 --- a/generated/5.0.4/bookworm/Dockerfile +++ b/generated/5.0.4/bookworm/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.4/bookworm/entrypoint.sh b/generated/5.0.4/bookworm/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.4/bookworm/entrypoint.sh +++ b/generated/5.0.4/bookworm/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.4/bullseye/Dockerfile b/generated/5.0.4/bullseye/Dockerfile index 3e63ebe..6e9a37c 100644 --- a/generated/5.0.4/bullseye/Dockerfile +++ b/generated/5.0.4/bullseye/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.4/bullseye/entrypoint.sh b/generated/5.0.4/bullseye/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.4/bullseye/entrypoint.sh +++ b/generated/5.0.4/bullseye/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.4/jammy/Dockerfile b/generated/5.0.4/jammy/Dockerfile index bb11a63..1ef0587 100644 --- a/generated/5.0.4/jammy/Dockerfile +++ b/generated/5.0.4/jammy/Dockerfile @@ -125,10 +125,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.4/jammy/entrypoint.sh b/generated/5.0.4/jammy/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.4/jammy/entrypoint.sh +++ b/generated/5.0.4/jammy/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.4/noble/Dockerfile b/generated/5.0.4/noble/Dockerfile index fa12063..034da54 100644 --- a/generated/5.0.4/noble/Dockerfile +++ b/generated/5.0.4/noble/Dockerfile @@ -125,10 +125,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.4/noble/entrypoint.sh b/generated/5.0.4/noble/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.4/noble/entrypoint.sh +++ b/generated/5.0.4/noble/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/generated/5.0.4/trixie/Dockerfile b/generated/5.0.4/trixie/Dockerfile index 2d6ae21..9344009 100644 --- a/generated/5.0.4/trixie/Dockerfile +++ b/generated/5.0.4/trixie/Dockerfile @@ -124,10 +124,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/generated/5.0.4/trixie/entrypoint.sh b/generated/5.0.4/trixie/entrypoint.sh index 21a0cfa..311b947 100644 --- a/generated/5.0.4/trixie/entrypoint.sh +++ b/generated/5.0.4/trixie/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/src/Dockerfile.template b/src/Dockerfile.template index f1764a5..352c801 100644 --- a/src/Dockerfile.template +++ b/src/Dockerfile.template @@ -120,10 +120,23 @@ ENV PATH=/opt/firebird/bin:$PATH # Data directory ENV FIREBIRD_DATA=/var/lib/firebird/data + +# Non-root support: runtime-writable paths are owned by 'firebird' with group 0 (root), and group permissions equal +# owner permissions. The image still runs as root by default, but it also runs as 'firebird' (--user firebird) or as +# an arbitrary UID with GID 0 (OpenShift restricted SCC). Binaries, libraries and plugins stay owned by root. +# The data directory is a VOLUME: its ownership must be set here, in the image layer. +# Lock and shared memory files left in /tmp/firebird by the installer are removed (Firebird recreates them at runtime). +# See DECISIONS.md D-020 and https://github.com/FirebirdSQL/firebird-docker/issues/46 RUN set -eux; \ mkdir -p "$FIREBIRD_DATA"; \ - chown -R firebird:firebird "$FIREBIRD_DATA"; \ - chmod 755 "$FIREBIRD_DATA" + rm -rf /tmp/firebird/*; \ + cd /opt/firebird; \ + for f in . SYSDBA.password firebird.conf firebird.log fb_guard replication.log security*.fdb /tmp/firebird "$FIREBIRD_DATA"; do \ + if [ -e "$f" ]; then \ + chown firebird:0 "$f"; \ + chmod g=u,o-w "$f"; \ + fi; \ + done VOLUME $FIREBIRD_DATA # Entrypoint diff --git a/src/README.md.template b/src/README.md.template index 42506ac..83041f0 100644 --- a/src/README.md.template +++ b/src/README.md.template @@ -225,6 +225,27 @@ Alternatively, you can use the same time zone as your host system by mapping the +## Running as a non-root user + +The container runs as `root` by default. It can also run as a non-root user, without any change in behavior: + +- as the `firebird` user (UID `84`), e.g. `docker run --user firebird ...`; or +- as **any** UID with GID `0` (`root` group), e.g. `docker run --user 12345:0 ...`. This is how OpenShift runs containers under its default `restricted` security context constraint, which assigns a random UID. + +```yaml +# Kubernetes + securityContext: + runAsNonRoot: true + runAsUser: 84 # or any UID... + runAsGroup: 0 # ...as long as the group is 0 +``` + +Other UID/GID combinations are not supported: the entrypoint shows a warning and Firebird cannot write its runtime files. + +> **IMPORTANT:** When using a bind mount or a pre-existing volume for `/var/lib/firebird/data`, it must be writable by the chosen user. Databases created while running as `root` are owned by `root`, and a non-root container cannot open them until you change their ownership (e.g. `chown -R 84:0` on the data directory). + + + ## Backup and Restore ### For online databases diff --git a/src/entrypoint.sh b/src/entrypoint.sh index 21a0cfa..311b947 100644 --- a/src/entrypoint.sh +++ b/src/entrypoint.sh @@ -107,6 +107,25 @@ indent() { sed 's/^/ /'; } +# Warns when a non-root user cannot write to Firebird runtime files. +# Supported non-root users are 'firebird' and any UID with GID 0 (e.g. OpenShift restricted SCC). +check_permissions() { + if [ "$(id -u)" = '0' ]; then + return + fi + + if [ ! -w /opt/firebird ] || [ ! -w "$FIREBIRD_DATA" ]; then + # [Tabs ahead] + cat >&2 <<-EOL + ----- + WARNING: Running as UID $(id -u) / GID $(id -g), which cannot write to /opt/firebird or $FIREBIRD_DATA. + + Run the container as root, as user 'firebird' (UID 84), or as any UID with GID 0. + ----- + EOL + fi +} + # Set Firebird configuration parameters from environment variables. set_config() { read_from_file_or_env 'FIREBIRD_USE_LEGACY_AUTH' @@ -203,7 +222,7 @@ create_user() { escaped_password=$(escape_sql_string "$FIREBIRD_PASSWORD") # [Tabs ahead] - /opt/firebird/bin/isql -b security.db <<-EOL + /opt/firebird/bin/isql -b -user SYSDBA security.db <<-EOL CREATE OR ALTER USER ${quoted_user} PASSWORD '${escaped_password}' GRANT ADMIN ROLE; @@ -221,6 +240,9 @@ process_sql() { # authentication, and the server then normalizes the name exactly like it # normalized the database owner name, so DDL permissions work in init scripts. isql_command+=( -u "$(unquote_sql_identifier "$(quote_sql_identifier "$FIREBIRD_USER")")" -p "$FIREBIRD_PASSWORD" ) + else + # Local connections otherwise take the OS user name, which is SYSDBA only for root. + isql_command+=( -u SYSDBA ) fi if [ -n "$FIREBIRD_DATABASE" ]; then @@ -302,7 +324,7 @@ create_db() { [ -n "$FIREBIRD_DATABASE_DEFAULT_CHARSET" ] && default_charset="DEFAULT CHARACTER SET $FIREBIRD_DATABASE_DEFAULT_CHARSET" # [Tabs ahead] - /opt/firebird/bin/isql -b -q <<-EOL + /opt/firebird/bin/isql -b -q -user SYSDBA <<-EOL CREATE DATABASE '${escaped_database}' $user_and_password $page_size @@ -345,6 +367,7 @@ run_daemon_and_wait() { # main() # if [ "$1" = 'firebird' ]; then + check_permissions set_config set_sysdba diff --git a/src/image.tests.ps1 b/src/image.tests.ps1 index 3689c07..5d7d6b5 100644 --- a/src/image.tests.ps1 +++ b/src/image.tests.ps1 @@ -2,11 +2,14 @@ # Functions # +# Data directory for test containers. Same ownership and mode as in the image layer (firebird:0, 0775). +$dataTmpfs = '/var/lib/firebird/data:uid=84,gid=0,mode=0775' + # Run commands in a container and return. function Invoke-Container([string[]]$DockerParameters, [string[]]$ImageParameters) { assert $env:FULL_IMAGE_NAME "'FULL_IMAGE_NAME' environment variable must be set to the image name to test." - $allParameters = @('run', '--tmpfs', '/var/lib/firebird/data', '--rm'; $DockerParameters; $env:FULL_IMAGE_NAME) + $allParameters = @('run', '--tmpfs', $dataTmpfs, '--rm'; $DockerParameters; $env:FULL_IMAGE_NAME) if ($ImageParameters) { # Do not append a $null as last parameter if $ImageParameters is empty $allParameters += $ImageParameters @@ -21,7 +24,7 @@ function Invoke-Container([string[]]$DockerParameters, [string[]]$ImageParameter function Use-Container([string[]]$Parameters, [Parameter(Mandatory)][ScriptBlock]$ScriptBlock) { assert $env:FULL_IMAGE_NAME "'FULL_IMAGE_NAME' environment variable must be set to the image name to test." - $allParameters = @('run'; $Parameters; '--tmpfs', '/var/lib/firebird/data', '--detach', $env:FULL_IMAGE_NAME) + $allParameters = @('run'; $Parameters; '--tmpfs', $dataTmpfs, '--detach', $env:FULL_IMAGE_NAME) Write-Verbose 'Starting container... Command line is' Write-Verbose " docker $allParameters" @@ -594,4 +597,101 @@ task Tag_correctness_via_docker_inspect { assert ($null -ne $version) "Expected 'org.opencontainers.image.version' label to be set." # Accept either a semver release (e.g. '5.0.3') or a snapshot tag (e.g. '5-snapshot', '6-snapshot') assert ($version -match '^\d+\.\d+\.\d+$' -or $version -match '^\d+-snapshot$') "Expected version label '$version' to be semver or snapshot format." -} \ No newline at end of file +} + +# +# Non-root support -- https://github.com/FirebirdSQL/firebird-docker/issues/46 +# + +task Runtime_paths_are_owned_by_firebird_and_group_root { + # Runs 'stat' directly (not via Invoke-Container) to see the data directory as shipped in the image layer, not a tmpfs. + $paths = '/opt/firebird', '/opt/firebird/firebird.conf', '/opt/firebird/firebird.log', '/opt/firebird/fb_guard', '/tmp/firebird', '/var/lib/firebird/data' + $stats = docker run --rm --entrypoint stat $env:FULL_IMAGE_NAME -c '%U %g %A %n' @paths + assert ($LastExitCode -eq 0) "Expected 'stat' to succeed on all runtime paths." + + $stats | ForEach-Object { + $owner, $gid, $mode, $path = $_ -split ' ' + assert ($owner -eq 'firebird') "Expected '$path' to be owned by 'firebird', got '$owner'." + assert ($gid -eq '0') "Expected '$path' to have group 0 (root), got '$gid'." + assert ($mode.Substring(1, 3) -eq $mode.Substring(4, 3)) "Expected '$path' to have group permissions equal to owner permissions, got '$mode'." + } + + # Binaries must stay owned by root. + docker run --rm --entrypoint stat $env:FULL_IMAGE_NAME -c '%U' /opt/firebird/bin/firebird | + Contains -Pattern '^root$' -ErrorMessage "Expected Firebird binaries to stay owned by root." +} + +# Runs the whole initialization path (config, SYSDBA password, user, database, init scripts) as the given user. +function Test-NonRootInitialization([Parameter(Mandatory)][string]$User) { + $initDbFolder = New-TemporaryDirectory + try { + @' + CREATE TABLE init_check (id INTEGER NOT NULL PRIMARY KEY); +'@ | Out-File "$initDbFolder/10-init.sql" + + Use-Container -Parameters '--user', $User, '-e', 'FIREBIRD_CONF_WireCrypt=Enabled', '-e', 'FIREBIRD_ROOT_PASSWORD=passw0rd', '-e', 'FIREBIRD_USER=alice', '-e', 'FIREBIRD_PASSWORD=bird', '-e', 'FIREBIRD_DATABASE=test.fdb', '-v', "$($initDbFolder):/docker-entrypoint-initdb.d/" { + param($cId) + + $expectedUid = ($User -split ':')[0] + $serverUid = docker exec $cId ps -o uid= -C firebird + assert ($serverUid.Trim() -eq $expectedUid) "Expected Firebird server to run as UID $expectedUid, got '$serverUid'." + + $logs = docker logs $cId 2>&1 + $logs | Contains -Pattern 'WireCrypt = Enabled' -ErrorMessage "Expected FIREBIRD_CONF_WireCrypt to be applied when running as '$User'." + $logs | ContainsExactly -Pattern 'WARNING' -ExpectedCount 0 -ErrorMessage "Expected no permission warning when running as '$User'." + + 'SELECT 1 FROM rdb$database;' | + docker exec -i $cId isql -b -q -u SYSDBA -p passw0rd inet:///var/lib/firebird/data/test.fdb | + ExitCodeIs -ExpectedValue 0 -ErrorMessage "Expected successful login with new SYSDBA password when running as '$User'." + + docker exec $cId test -f /opt/firebird/SYSDBA.password | + ExitCodeIs -ExpectedValue 1 -ErrorMessage "Expected SYSDBA.password file to be removed when running as '$User'." + + # Init script must have been executed as 'alice' + 'SET LIST ON; SELECT rdb$owner_name AS table_owner FROM rdb$relations WHERE rdb$relation_name = ''INIT_CHECK'';' | + docker exec -i $cId isql -b -q -u alice -p bird inet:///var/lib/firebird/data/test.fdb | + Contains -Pattern 'TABLE_OWNER(\s+)ALICE' -ErrorMessage "Expected init script to create table 'init_check' owned by 'alice' when running as '$User'." + } + } + finally { + Remove-Item $initDbFolder -Force -Recurse + } +} + +task Can_run_as_firebird_user { + Test-NonRootInitialization -User '84:84' +} + +task Can_run_as_arbitrary_uid_with_group_root { + # OpenShift restricted SCC: random UID, no /etc/passwd entry, GID 0. + Test-NonRootInitialization -User '12345:0' +} + +task Without_FIREBIRD_USER_database_is_owned_by_SYSDBA_for_any_user { + # Local connections would otherwise take the OS user name (e.g. 'FIREBIRD' for UID 84), not SYSDBA. + $initDbFolder = New-TemporaryDirectory + try { + @' + CREATE TABLE init_check (id INTEGER NOT NULL PRIMARY KEY); +'@ | Out-File "$initDbFolder/10-init.sql" + + foreach ($user in '0:0', '84:84', '12345:0') { + Use-Container -Parameters '--user', $user, '-e', 'FIREBIRD_DATABASE=test.fdb', '-v', "$($initDbFolder):/docker-entrypoint-initdb.d/" { + param($cId) + + 'SET LIST ON; SELECT rdb$owner_name AS table_owner FROM rdb$relations WHERE rdb$relation_name = ''INIT_CHECK'';' | + docker exec -i $cId isql -b -q -u SYSDBA /var/lib/firebird/data/test.fdb | + Contains -Pattern 'TABLE_OWNER(\s+)SYSDBA' -ErrorMessage "Expected init script to create table 'init_check' owned by SYSDBA when running as '$user'." + } + } + } + finally { + Remove-Item $initDbFolder -Force -Recurse + } +} + +task Unsupported_user_shows_permission_warning { + # A UID which is neither 'firebird' nor in group 0 cannot write runtime files. + $($stdout = Invoke-Container -DockerParameters '--user', '1000:1000', '-e', 'FIREBIRD_CONF_WireCrypt=Enabled') 2>&1 | + Contains -Pattern 'WARNING: Running as UID 1000 / GID 1000' -ErrorMessage "Expected permission warning when running as an unsupported user." +}