DEV Community

Abdul Talha
Abdul Talha

Posted on

Instrument BookStack with OpenTelemetry and SigNoz Using Docker

Deploying BookStack was the easy part. Understanding what was happening inside the application wasn't. Without visibility into incoming requests, database queries, or Laravel operations, troubleshooting performance issues felt like guesswork. In this tutorial, you'll instrument BookStack with OpenTelemetry, connect it to SigNoz, and build an end-to-end observability pipeline, all without modifying the application's source code.

BookStack is an open-source platform for creating and managing documentation, but it doesn't provide built-in distributed tracing or deep application observability. In this tutorial, you'll instrument BookStack with OpenTelemetry and export traces to SigNoz, enabling you to monitor requests, analyse Laravel application behaviour, and troubleshoot issues more effectively.

Prerequisites

Before you begin, make sure you have the following:

  • A Linux server (Ubuntu 22.04 or later) with at least 4 vCPUs and 8 GB RAM

  • Docker Engine and Docker Compose installed

Solution Overview

BookStack is instrumented with OpenTelemetry, which exports traces to the OpenTelemetry Collector. The collector forwards the telemetry to SigNoz, where you can visualise requests and analyse distributed traces.

                HTTP Requests
                      │
                      ▼
               ┌─────────────┐
               │  BookStack  │
               │  (Laravel)  │
               └──────┬──────┘
                      │
          OpenTelemetry SDK
                      │
             OTLP (HTTP:4318)
                      │
                      ▼
        ┌────────────────────────┐
        │ OpenTelemetry Collector│
        │    (SigNoz Collector)  │
        └───────────┬────────────┘
                    │
                    ▼
              ┌───────────┐
              │  SigNoz   │
              │ Dashboard │
              └───────────┘
Enter fullscreen mode Exit fullscreen mode

Step 1: Install SigNoz

Before instrumenting BookStack, you need a backend to collect, store, and visualise telemetry data. In this step, you'll install SigNoz using the foundryctl CLI and verify that it's ready to receive traces from BookStack.

  1. Install the Foundry CLI, which simplifies the deployment of SigNoz by generating and managing the required Docker Compose configuration.

    curl -fsSL https://signoz.io/foundry.sh | bash
    export PATH="/root/.local/bin:$PATH"
    

    Verify that the installation completed successfully:

    foundryctl version
    
  2. Create a file named casting.yaml with the following configuration. This file instructs foundryctl to deploy SigNoz using Docker Compose.

    apiVersion: v1alpha1
    kind: Installation
    metadata:
      name: signoz
    
    spec:
      deployment:
        flavor: compose
        mode: docker
    
  3. Deploy SigNoz using the installation configuration.

    foundryctl cast -f casting.yaml
    

    The installer validates your Docker environment, generates the required Docker Compose resources, and starts the SigNoz services.

  4. Verify that the deployment completed successfully.

    docker ps
    

    You should see containers such as signoz-frontend, signoz-query-service, signoz-otel-collector, and clickhouse.

  5. Then open http://<SERVER-IP>:8080 in your browser. If the installation completed successfully, the SigNoz dashboard should load. Replace <SERVER_IP> with your Server IP.

Enter the email and password to create the initial admin account for SigNoz.
Enter fullscreen mode Exit fullscreen mode

Step 2: Build a Custom BookStack Image

The official LinuxServer BookStack image doesn't include the OpenTelemetry components required to export traces. In this step, you'll build a custom image that installs the OpenTelemetry PHP extension and Laravel auto-instrumentation packages during the image build, making the deployment reproducible and eliminating the need to modify a running container.

  1. Create a project directory for the deployment and navigate into it.

    mkdir bookstack-otel
    cd bookstack-otel
    
  2. Generate a Laravel application key. BookStack uses this key to encrypt sensitive application data, and you'll reference it later when creating the Docker Compose configuration.

    echo "base64:$(openssl rand -base64 32)"
    

    Save the generated value—you'll use it when configuring the BookStack container.

  3. Create a file named Dockerfile with the following configuration.

    FROM lscr.io/linuxserver/bookstack:version-v26.03.3
    
    COPY scripts/install-opentelemetry.sh /tmp/install-opentelemetry.sh
    
    RUN chmod +x /tmp/install-opentelemetry.sh \
    && /tmp/install-opentelemetry.sh \
    && rm /tmp/install-opentelemetry.sh \
    && rm -rf /root/.composer/cache
    
    WORKDIR /app/www
    
    

    This Dockerfile extends the official BookStack image, runs the installation script during the image build.

  4. Create a file named install-opentelemetry.sh with the following installation script.

    #!/bin/sh
    set -e
    
    echo "=========================================="
    echo "Installing OpenTelemetry PHP Extension"
    echo "=========================================="
    
    # Add Alpine edge testing repository if missing
    if ! grep -q "edge/testing" /etc/apk/repositories; then
        echo "https://dl-cdn.alpinelinux.org/alpine/edge/testing" >> /etc/apk/repositories
    fi
    
    apk update
    
    apk add --no-cache php85-pecl-opentelemetry
    
    echo "=========================================="
    echo "Installing OpenTelemetry Laravel Packages"
    echo "=========================================="
    
    cd /app/www
    
    composer config --no-interaction allow-plugins.php-http/discovery false
    composer config --no-interaction allow-plugins.tbachert/spi true
    
    composer require \
        open-telemetry/sdk \
        open-telemetry/exporter-otlp \
        open-telemetry/opentelemetry-auto-laravel \
        php-http/guzzle7-adapter \
        --no-interaction \
        --prefer-dist \
        --optimize-autoloader \
        --no-scripts
    
    echo "=========================================="
    echo "Verifying installation..."
    echo "=========================================="
    
    php -m | grep opentelemetry
    
    composer show open-telemetry/sdk
    composer show open-telemetry/opentelemetry-auto-laravel
    
    echo "=========================================="
    echo "OpenTelemetry installation completed!"
    echo "=========================================="
    

    This script installs the OpenTelemetry PHP extension together with the Composer packages required for Laravel auto-instrumentation. It also performs basic validation during the image build to confirm that the required components were installed successfully.

Step 3: Deploy BookStack with OpenTelemetry

With the custom image prepared, you're ready to deploy BookStack and its MariaDB database. In this step, you'll create a single Docker Compose configuration that builds the custom image, configures OpenTelemetry, and connects BookStack to the SigNoz OpenTelemetry Collector.

  1. Create a docker-compose.yml file with the following configuration.

    services:
      bookstack:
        build:
          context: .
          dockerfile: Dockerfile
        image: bookstack-otel:latest
        container_name: bookstack
    
        environment:
          - PUID=1000
          - PGID=1000
          - TZ=Asia/Kolkata
    
          - APP_URL=http://<SERVER-IP>:6875
          - APP_KEY=<APP_KEY>
    
          - DB_HOST=bookstack_db
          - DB_PORT=3306
          - DB_DATABASE=bookstackapp
          - DB_USERNAME=bookstack
          - DB_PASSWORD=bookstack
    
          # OpenTelemetry
          - OTEL_SERVICE_NAME=bookstack
          - OTEL_TRACES_EXPORTER=otlp
          - OTEL_METRICS_EXPORTER=none
          - OTEL_LOGS_EXPORTER=none
          - OTEL_EXPORTER_OTLP_PROTOCOL=http/protobuf
          - OTEL_EXPORTER_OTLP_ENDPOINT=http://signoz-ingester-1:4318
          - OTEL_PHP_AUTOLOAD_ENABLED=true
    
        volumes:
          - ./bookstack_data:/config
    
        ports:
          - "6875:80"
    
        depends_on:
          - bookstack_db
    
        restart: unless-stopped
    
      bookstack_db:
        image: lscr.io/linuxserver/mariadb:latest
        container_name: bookstack_db
    
        environment:
          - PUID=1000
          - PGID=1000
          - TZ=Asia/Kolkata
          - MYSQL_ROOT_PASSWORD=<ROOT_PASSWORD>
          - MYSQL_DATABASE=bookstackapp
          - MYSQL_USER=bookstack
          - MYSQL_PASSWORD=bookstack
    
        volumes:
          - ./bookstack_db_data:/config
    
        restart: unless-stopped
    
    networks:
      default:
        external: true
        name: signoz-network
    

    Before starting the deployment, replace the following placeholders:

  *   `<SERVER-IP>` with your server's IP address or domain.

  *   `<APP_KEY>` with the Laravel application key generated in the previous step.

*   `<ROOT_PASSWORD>` with a secure MariaDB root password.

*   `signoz-network` with the Docker network created by your SigNoz installation if it uses a different name.
Enter fullscreen mode Exit fullscreen mode
  1. Build the custom image and start the BookStack and MariaDB containers.

    docker compose up -d --build
    

    Docker builds the custom BookStack image, installs the OpenTelemetry components, and starts both containers.

  2. Verify that the deployment completed successfully.

    docker ps
    

    The bookstack and bookstack_db containers should both be in the Up state.

  3. Open BookStack in your browser.

    http://<SERVER-IP>:6875
    

    Replace <SERVER-IP> with your Server IP.
    The BookStack login page should load successfully, confirming that the application is running with the custom OpenTelemetry-enabled image.
    Enter email as admin@admin.com and password as password.

Step 4: Verify the OpenTelemetry Installation

Before generating application traffic, verify that the OpenTelemetry components were installed correctly and that BookStack is configured to export traces. In this step, you'll confirm that the PHP extension, Composer packages, Laravel package discovery, and OpenTelemetry environment variables are all working as expected.

  1. Verify that the OpenTelemetry PHP extension is loaded inside the BookStack container.

    docker exec bookstack php -m | grep opentelemetry
    

    If the installation was successful, the command should return:

    opentelemetry
    
  2. Confirm that the required OpenTelemetry Composer packages were installed.

    docker exec bookstack composer show | grep opentelemetry
    

    You should see packages similar to:

    open-telemetry/api
    open-telemetry/sdk
    open-telemetry/exporter-otlp
    open-telemetry/opentelemetry-auto-laravel
    
  3. Verify that the OpenTelemetry environment variables are available inside the running container.

    docker exec bookstack printenv | grep OTEL
    

    You should see output similar to:

    OTEL_SERVICE_NAME=bookstack
    OTEL_TRACES_EXPORTER=otlp
    OTEL_EXPORTER_OTLP_ENDPOINT=http://signoz-ingester-1:4318
    OTEL_EXPORTER_OTLP_PROTOCOL=http/protobuf
    OTEL_PHP_AUTOLOAD_ENABLED=true
    
  4. Verify that Laravel can discover the installed packages without errors.

    docker exec bookstack php artisan package:discover
    

    The command should complete successfully without reporting missing dependencies or package discovery errors.

  5. Open BookStack in your browser to confirm that the application is still running.

    http://<SERVER-IP>:6875
    

    Replace <SERVER-IP> with your Server IP.
    The login page should load normally, confirming that the custom image is running correctly and is ready to export traces.

Step 5: Generate Application Traffic

With BookStack configured and the OpenTelemetry installation verified, the next step is to generate application traffic. As users interact with BookStack, OpenTelemetry automatically captures each request and exports the resulting traces to the SigNoz OpenTelemetry Collector.

  1. Open BookStack in your browser.

    http://<SERVER-IP>:6875
    

    Replace <SERVER-IP> with your Server IP.

  2. Log in using the default BookStack administrator credentials or an existing user account.

  3. Perform a few common actions to generate application traffic, such as:

*   Browse books and shelves.

*   Open and view existing pages.

*   Create a new page.

*   Edit and save content.

*   Navigate between different sections of the application.


Each of these actions generates HTTP requests that are automatically instrumented by OpenTelemetry and exported to SigNoz.
Enter fullscreen mode Exit fullscreen mode
  1. Repeat a few of these actions over the next minute to generate multiple traces. This provides enough telemetry data to inspect different requests in the SigNoz dashboard.

Step 6: View Traces in SigNoz

After generating application traffic, verify that BookStack is exporting traces to SigNoz. In this step, you'll inspect the collected traces and explore the request details captured by OpenTelemetry.

  1. Open the SigNoz dashboard in your browser.

    http://<SERVER-IP>:8080
    

    Replace <SERVER-IP> with your Server IP.

  2. From the left navigation menu, select Traces.

    After a few seconds, you should see traces from the bookstack service.

    If no traces appear immediately, wait a few seconds, refresh the page, perform another action in BookStack, and check again.

  3. Click any trace from the bookstack service to inspect its details.

    The trace view displays the sequence of operations performed while processing a request. Depending on the action you performed, you'll typically see spans representing the incoming HTTP request, Laravel middleware, route handling, controller execution, and database operations.

  1. Verify that the trace was recorded successfully.

    Confirm that:

*   The **Service Name** is `bookstack`.

*   The trace completed successfully.

*   Multiple spans are displayed for the request.

*   The request duration and execution timeline are visible.
Enter fullscreen mode Exit fullscreen mode

Congratulations! You've successfully instrumented BookStack with OpenTelemetry and configured it to export traces to SigNoz. You now have end-to-end visibility into your application's requests, making it easier to understand application behaviour and troubleshoot performance issues.

What I Learned

Building this setup highlighted a few practical lessons:

  • Use a custom Docker image. Installing the OpenTelemetry components during the image build makes the deployment reproducible and prevents changes from being lost when containers are recreated.

  • Verify each step as you go. Checking the PHP extension, Composer packages, and environment variables helped identify configuration issues early.

  • Ensure the containers share the same network. BookStack can only export traces if it can reach the SigNoz OpenTelemetry Collector.

  • Generate application traffic before checking SigNoz. Traces are created only when BookStack processes requests.

Conclusion

You've successfully instrumented BookStack with OpenTelemetry and configured it to export traces to SigNoz, giving you end-to-end visibility into application requests with a reproducible Docker-based deployment.

To continue exploring application observability, check out the following resources:

Top comments (0)