Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Introduces immutability to OCI image #22

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
34 changes: 33 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -360,12 +360,20 @@ To pull the image from the GitHub Container Registry, run the following command:
sudo docker pull ghcr.io/openprinting/ghostscript-printer-app:latest
```

Create a Docker volume:
```sh
sudo docker volume create ghostscript-printer-app
```

To run the container after pulling the image from the GitHub Container Registry, use:
```sh
sudo docker run -d \
--name ghostscript-printer-app \
--network host \
-e PORT=<port> \
-v ghostscript-printer-app:/var/lib/ghostscript-printer-app \
-v /dev/bus/usb:/dev/bus/usb:ro \
--device-cgroup-rule='c 189:* rmw' \
ghcr.io/openprinting/ghostscript-printer-app:latest
```

Expand All @@ -375,20 +383,32 @@ Alternatively, you can pull the image from Docker Hub, by running:
sudo docker pull openprinting/ghostscript-printer-app
```

Create a Docker volume:
```sh
sudo docker volume create ghostscript-printer-app
```

To run the container after pulling the image from Docker Hub, use:
```sh
sudo docker run -d \
--name ghostscript-printer-app \
--network host \
-e PORT=<port> \
-v ghostscript-printer-app:/var/lib/ghostscript-printer-app \
-v /dev/bus/usb:/dev/bus/usb:ro \
--device-cgroup-rule='c 189:* rmw' \
openprinting/ghostscript-printer-app:latest
```

- `PORT` is an optional environment variable used to start the printer-app on a specified port. If not provided, it will start on the default port 8000 or, if port 8000 is busy, on 8001 and so on.
- **The container must be started in `--network host` mode** to allow the Printer-Application instance inside the container to access and discover printers available in the local network where the host system is in.
- Alternatively using the internal network of the Docker instance (`-p <port>:8000` instead of `--network host -e PORT=<port>`) only gives access to local printers running on the host system itself.
- `-v ghostscript-printer-app:/var/lib/ghostscript-printer-app` maps a volume for persistent storage.
- The following volume and device settings are crucial for USB printer access:
- `-v /dev/bus/usb:/dev/bus/usb:ro` mounts the host's USB device directory read-only inside the container for USB printer access.
- `--device-cgroup-rule='c 189:* rmw'` allows the container to read, write, and mknod to USB devices.

### Setting Up and Running gutenprint-printer-app locally
### Setting Up and Running ghostscript-printer-app locally

#### Prerequisites

Expand Down Expand Up @@ -424,18 +444,30 @@ Once the rock is built, you need to compile docker image from it.
sudo rockcraft.skopeo --insecure-policy copy oci-archive:<rock_image> docker-daemon:ghostscript-printer-app:latest
```

Create a Docker volume:
```sh
sudo docker volume create ghostscript-printer-app
```

**Run the ghostscript-printer-app Docker Container**

```sh
sudo docker run -d \
--name ghostscript-printer-app \
--network host \
-e PORT=<port> \
-v ghostscript-printer-app:/var/lib/ghostscript-printer-app \
-v /dev/bus/usb:/dev/bus/usb:ro \
--device-cgroup-rule='c 189:* rmw' \
ghostscript-printer-app:latest
```
- `PORT` is an optional environment variable used to start the printer-app on a specified port. If not provided, it will start on the default port 8000 or, if port 8000 is busy, on 8001 and so on.
- **The container must be started in `--network host` mode** to allow the Printer-Application instance inside the container to access and discover printers available in the local network where the host system is in.
- Alternatively using the internal network of the Docker instance (`-p <port>:8000` instead of `--network host -e PORT=<port>`) only gives access to local printers running on the host system itself.
- `-v ghostscript-printer-app:/var/lib/ghostscript-printer-app` maps a volume for persistent storage.
- The following volume and device settings are crucial for USB printer access:
- `-v /dev/bus/usb:/dev/bus/usb:ro` mounts the host's USB device directory read-only inside the container for USB printer access.
- `--device-cgroup-rule='c 189:* rmw'` allows the container to read, write, and mknod to USB devices.

#### Setting up

Expand Down
165 changes: 147 additions & 18 deletions rockcraft.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,11 @@ platforms:
amd64:
armhf:

run-user: _daemon_

services:
dbus:
command: /scripts/run-dbus.sh
avahi-daemon:
command: /scripts/run-avahi.sh
override: replace
on-failure: restart
startup: enabled
Expand All @@ -27,7 +29,7 @@ services:
override: replace
on-failure: shutdown
startup: enabled
after: [dbus]
after: [avahi-daemon]

parts:
pappl:
Expand Down Expand Up @@ -780,6 +782,7 @@ parts:
stage-packages:
- libsnmp40
- python3-dev
- libavahi-client-dev
organize:
ghostscript-printer-app/current/etc/hp/hplip.conf: etc/hp/hplip.conf
prime:
Expand Down Expand Up @@ -1449,32 +1452,158 @@ parts:
- usr/share/ghostscript-printer-app
- -var
- -usr/share/man
after: [avahi, pappl-retrofit, pappl, ghostscript, libcupsfilters, libppd, cups-filters, foomatic-db]

avahi:
plugin: autotools
source: https://github.com/avahi/avahi.git
source-type: git
autotools-configure-parameters:
- --prefix=/usr
- --disable-qt3
- --disable-qt4
- --disable-qt5
- --disable-gtk
- --disable-gtk3
- --disable-gdbm
- --disable-python
- --disable-pygtk
- --disable-python-dbus
- --disable-mono
- --disable-monodoc
- --disable-manpages
- --disable-xmltoman
- --with-avahi-user=_daemon_
- --with-avahi-group=_daemon_
# - --with-avahi-priv-access-group=netdev
# - --with-distro=debian
- --disable-gobject
- --datadir=/usr/share
- --libdir=/usr/lib/${CRAFT_ARCH_TRIPLET_BUILD_FOR}
- --with-systemdsystemunitdir=/usr/lib/systemd/system
- --localstatedir=/var
- --sysconfdir=/etc
build-packages:
- g++
- gcc
- gettext
- intltool
- libdaemon-dev
- libdbus-1-dev
- libevent-dev
- libexpat1-dev
- libglib2.0-dev
- libsystemd-dev
- xmltoman
override-build: |
craftctl default
# for reference sort systemd service files
sed -i \
-e 's|\(.*\)avahi-daemon -s.*|\1avahi-daemon -s --no-drop-root|g' \
-e 's|\(.*\)avahi-daemon -r.*|\1avahi-daemon -r --no-drop-root|g' \
${CRAFT_PART_INSTALL}/usr/lib/systemd/system/avahi-daemon.service
mkdir -p \
${CRAFT_PART_INSTALL}/usr/lib/systemd/system/multi-user.target.wants
ln -sf \
../avahi-daemon.service \
${CRAFT_PART_INSTALL}/usr/lib/systemd/system/multi-user.target.wants/avahi-daemon.service
build-environment:
- LD_LIBRARY_PATH: "${LD_LIBRARY_PATH:+$LD_LIBRARY_PATH:}$CRAFT_STAGE/usr/lib"
override-prime: |
set -eux
craftctl default
sed -i 's/use-ipv6=yes/use-ipv6=no/' ${CRAFT_PRIME}/etc/avahi/avahi-daemon.conf
sed -i 's|<user>messagebus</user>|<user>_daemon_</user>|; /<policy user="root">/,/<\/policy>/d' $CRAFT_PRIME/usr/share/dbus-1/system.conf
sed -i 's/<policy group="netdev">/<policy group="_daemon_">/g; s/<policy user="root">/<policy user="_daemon_">/g' $CRAFT_PRIME/usr/share/dbus-1/system.d/avahi-dbus.conf
stage-packages:
- libdaemon0
- libevent-2.1-7
- avahi-utils
- mdns-scan
# - libavahi-client3
# - libavahi-common3
stage:
- etc/avahi
- usr
- -usr/lib/**/libavahi-client.a
- -usr/lib/**/libavahi-common.a
- -usr/lib/**/libavahi-client.so*
- -usr/lib/**/libavahi-common.so*
- -usr/lib/**/*.acd
- -usr/lib/**/*.la
- -usr/lib/**/avahi
- -usr/lib/**/libavahi-glib*
- -usr/lib/**/libavahi-libevent*
- -usr/lib/**/libevent-*
# - -usr/lib/**/libnss_mdns*
- -usr/lib/**/pkgconfig
- -usr/include
- -usr/share/doc
- -usr/share/man
- -usr/share/locale
after: [pappl-retrofit, pappl, ghostscript, libcupsfilters, libppd, cups-filters, foomatic-db]

avahi-daemon:
utils:
plugin: nil
overlay-packages:
- avahi-daemon
- avahi-utils
- libnss-mdns
- mdns-scan
- dbus
- python3
- dbus
- libnss-mdns
override-prime: |
set -eux
craftctl default

# Set up Avahi Daemon runtime directory
mkdir -p "$CRAFT_PRIME/var/run/avahi-daemon"
chown 584792:584792 "$CRAFT_PRIME/var/run/avahi-daemon"
chmod 777 "$CRAFT_PRIME/var/run/avahi-daemon"

# Set up D-Bus runtime directory
mkdir -p "$CRAFT_PRIME/var/run/dbus"
chown 584792:584792 "$CRAFT_PRIME/var/run/dbus"
chmod 777 "$CRAFT_PRIME/var/run/dbus"

# Set up the CUPS SSL server root directory
CUPS_SERVERROOT="$CRAFT_PRIME/etc/cups/ssl"
mkdir -p "$CUPS_SERVERROOT"
chown 584792:584792 "$CUPS_SERVERROOT"
chmod 770 "$CUPS_SERVERROOT"

# Set up the state directory and file for the printer app
STATE_DIR="$CRAFT_PRIME/var/lib/ghostscript-printer-app"
mkdir -p "$STATE_DIR"
chown 584792:584792 "$STATE_DIR"
chmod 770 "$STATE_DIR"

# Create a state file inside the state directory
STATE_FILE="$STATE_DIR/ghostscript-printer-app.state"
touch "$STATE_FILE"
chown 584792:584792 "$STATE_FILE"
chmod 644 "$STATE_FILE"

# Ensure the spool directory is owned properly
SPOOL_DIR="$CRAFT_PRIME/var/spool/ghostscript-printer-app"
mkdir -p "$SPOOL_DIR"
chown 584792:584792 "$SPOOL_DIR"
chmod 770 "$SPOOL_DIR"

# Create and set permissions for the application log file
touch $CRAFT_PRIME/ghostscript-printer-app.log
chown 584792:584792 $CRAFT_PRIME/ghostscript-printer-app.log
chmod 644 $CRAFT_PRIME/ghostscript-printer-app.log

# Setting up permissions to USB backend
USB_BACKEND="$CRAFT_PRIME/usr/lib/ghostscript-printer-app/backend/usb"
chmod u+s "$USB_BACKEND"
after: [ghostscript-printer-app, avahi, pappl-retrofit, pappl, ghostscript, libcupsfilters, libppd, cups-filters, foomatic-db]

scripts:
plugin: dump
source: scripts/
organize:
run-dbus.sh: /scripts/run-dbus.sh
start-server.sh: /scripts/start-server.sh
run-avahi.sh: /scripts/run-avahi.sh
override-prime: |
set -eux
craftctl default
# Ensure the run-dbus.sh script has executable permissions
if [ -f "$CRAFT_PRIME/scripts/run-dbus.sh" ]; then
chmod +x "$CRAFT_PRIME/scripts/run-dbus.sh"
fi
# Ensure the start-server.sh script has executable permissions
if [ -f "$CRAFT_PRIME/scripts/start-server.sh" ]; then
chmod +x "$CRAFT_PRIME/scripts/start-server.sh"
fi
chmod +x $CRAFT_PRIME/scripts/*
17 changes: 17 additions & 0 deletions scripts/run-avahi.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
#!/bin/sh
set -eux

# Start dbus-daemon in the background
/usr/bin/dbus-daemon --system --nofork &

# Wait for the D-Bus system bus to be ready
while [ ! -e /var/run/dbus/system_bus_socket ]; do
echo "Waiting for dbus-daemon to initialize..."
sleep 1
done

# Start avahi-daemon after dbus-daemon is ready
/usr/sbin/avahi-daemon -f /etc/avahi/avahi-daemon.conf --no-drop-root --debug

# Keep the container running
exec tail -f /dev/null
32 changes: 0 additions & 32 deletions scripts/run-dbus.sh

This file was deleted.

31 changes: 10 additions & 21 deletions scripts/start-server.sh
Original file line number Diff line number Diff line change
Expand Up @@ -9,27 +9,16 @@ if [ -n "${PORT:-}" ]; then
fi
fi

# Ensure the /etc/cups/ssl directory exists with proper permissions
CUPS_SERVERROOT="/etc/cups/ssl"
if [ ! -d "$CUPS_SERVERROOT" ]; then
mkdir -p "$CUPS_SERVERROOT"
fi
chmod 755 "$CUPS_SERVERROOT"

# Ensure /var/lib/ghostscript-printer-app directory exists
STATE_DIR="/var/lib/ghostscript-printer-app"

if [ ! -d "$STATE_DIR" ]; then
mkdir -p "$STATE_DIR"
fi
chmod 755 "$STATE_DIR"
# Wait for avahi-daemon to initialize
while true; do
if [ -f "/var/run/avahi-daemon/pid" ] || [ -f "/run/avahi-daemon/pid" ]; then
echo "avahi-daemon is active. Starting ps-printer-app..."
break
fi

# Ensure ghostscript-printer-app.state file exists
STATE_FILE="$STATE_DIR/ghostscript-printer-app.state"
if [ ! -f "$STATE_FILE" ]; then
touch "$STATE_FILE"
fi
chmod 755 "$STATE_FILE"
echo "Waiting for avahi-daemon to initialize..."
sleep 1
done

# Start the ghostscript-printer-app server
ghostscript-printer-app -o log-file=/ghostscript-printer-app.log ${PORT:+-o server-port=$PORT} server
ghostscript-printer-app -o log-file="/ghostscript-printer-app.log" ${PORT:+-o server-port="$PORT"} server
Loading