Skip to content

Commit 8c6047f

Browse files
Mossakaclaude
andauthored
fix(squid): run Squid container as non-root user (#1153)
* fix(security): run Squid container as non-root user Install gosu in the Squid container and use it to drop from root to the proxy user (UID 13) before starting Squid. The entrypoint still runs as root initially to fix mounted volume permissions, then drops privileges via `gosu proxy` before exec'ing squid. Changes: - Dockerfile: install gosu, create and chown /var/spool/squid, /var/run/squid, and /etc/squid for the proxy user - entrypoint.sh: use `exec gosu proxy squid -N -d 1` instead of `exec squid -N -d 1` Fixes #250 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(squid): ensure /run/squid.pid is writable by proxy user Squid's default pid_filename is /run/squid.pid, which is not writable by the proxy user after dropping privileges via gosu. Create and chown the pid file before starting Squid. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(squid): make squid.conf readable by proxy user The squid.conf was written with mode 0o600 (owner-only), but since Squid now runs as the proxy user via gosu, it couldn't read its own config file. Changed to 0o644 so the proxy user can read it. The docker-compose.yml retains 0o600 since it contains sensitive environment variables. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent 65f71c5 commit 8c6047f

File tree

4 files changed

+16
-9
lines changed

4 files changed

+16
-9
lines changed

containers/squid/Dockerfile

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,20 @@
11
FROM ubuntu/squid:latest
22

33
# Install additional tools for debugging, healthcheck, and SSL Bump
4+
# gosu is used to drop from root to proxy user after permission setup
45
# Retry logic handles transient 404s when Ubuntu archive supersedes package versions mid-build
56
RUN set -eux; \
6-
PKGS="curl dnsutils net-tools netcat-openbsd openssl squid-openssl"; \
7+
PKGS="curl dnsutils gosu net-tools netcat-openbsd openssl squid-openssl"; \
78
apt-get update && \
89
apt-get install -y --only-upgrade gpgv && \
910
( apt-get install -y --no-install-recommends $PKGS || \
1011
(rm -rf /var/lib/apt/lists/* && apt-get update && \
1112
apt-get install -y --no-install-recommends $PKGS) ) && \
1213
rm -rf /var/lib/apt/lists/*
1314

14-
# Create log directory and SSL database directory
15-
RUN mkdir -p /var/log/squid && \
16-
chown -R proxy:proxy /var/log/squid
15+
# Create log directory and SSL database directory, ensure proxy user owns them
16+
RUN mkdir -p /var/log/squid /var/spool/squid /var/run/squid && \
17+
chown -R proxy:proxy /var/log/squid /var/spool/squid /var/run/squid /etc/squid
1718

1819
# Copy entrypoint script
1920
COPY entrypoint.sh /usr/local/bin/entrypoint.sh

containers/squid/entrypoint.sh

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,5 +19,11 @@ if [ -d "/var/spool/squid_ssl_db" ]; then
1919
echo "[squid-entrypoint] SSL certificate database ready"
2020
fi
2121

22-
# Start Squid
23-
exec squid -N -d 1
22+
# Ensure Squid config directory and run directory are writable by proxy
23+
chown -R proxy:proxy /etc/squid /var/run/squid /var/spool/squid 2>/dev/null || true
24+
25+
# Ensure pid file is writable by proxy user (default: /run/squid.pid)
26+
touch /run/squid.pid && chown proxy:proxy /run/squid.pid
27+
28+
# Drop to proxy user and start Squid
29+
exec gosu proxy squid -N -d 1

src/docker-manager.test.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2008,11 +2008,11 @@ describe('docker-manager', () => {
20082008
// May fail after writing configs
20092009
}
20102010

2011-
// Verify squid.conf has restricted permissions
2011+
// Verify squid.conf is readable by proxy user (0o644) for non-root Squid
20122012
const squidConfPath = path.join(testDir, 'squid.conf');
20132013
if (fs.existsSync(squidConfPath)) {
20142014
const stats = fs.statSync(squidConfPath);
2015-
expect((stats.mode & 0o777).toString(8)).toBe('600');
2015+
expect((stats.mode & 0o777).toString(8)).toBe('644');
20162016
}
20172017

20182018
// Verify docker-compose.yml has restricted permissions

src/docker-manager.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1254,7 +1254,7 @@ export async function writeConfigs(config: WrapperConfig): Promise<void> {
12541254
allowHostPorts: config.allowHostPorts,
12551255
});
12561256
const squidConfigPath = path.join(config.workDir, 'squid.conf');
1257-
fs.writeFileSync(squidConfigPath, squidConfig, { mode: 0o600 });
1257+
fs.writeFileSync(squidConfigPath, squidConfig, { mode: 0o644 });
12581258
logger.debug(`Squid config written to: ${squidConfigPath}`);
12591259

12601260
// Write Docker Compose config

0 commit comments

Comments
 (0)