speedtest/doc_docker.md
sstidl 3a7dc31ff2
Implement the new design from #649 (#694)
* Implement fromScratch design

* Add some documentation

* enable new design in docker (no alpine yet)

* merge fixed docker images

* alpine docker added new design

* fix #685

* Implement fromScratch design

* Add some documentation

* enable new design in docker (no alpine yet)

* alpine docker added new design

* fix #685

* fix database permissions alpine, remove baby

* hide serverselector on only one server

* Update frontend/styling/server-selector.css

Co-authored-by: qodo-merge-pro-for-open-source[bot] <189517486+qodo-merge-pro-for-open-source[bot]@users.noreply.github.com>

* fix alpine image again

* adjust settings.json in entrypoint

so env vars are honored

* Update frontend/javascript/index.js

Co-authored-by: qodo-merge-for-open-source[bot] <189517486+qodo-merge-for-open-source[bot]@users.noreply.github.com>

* Add feature switch for new design via config file, URL parameters, and Docker (#742)

* Initial plan

* Add feature switch for new design with config and URL parameter support

Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>

* Improve error handling and prevent infinite redirect loops

Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>

* Update Dockerfiles and entrypoint to support design feature switch

Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>

* Update design-switch.js

Co-authored-by: qodo-free-for-open-source-projects[bot] <189517486+qodo-free-for-open-source-projects[bot]@users.noreply.github.com>

* fix: copy actions in entrypoint

* Restructure design switch to place both designs at root level

Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>

* Flatten frontend assets in Docker to eliminate frontend directory

Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>

* fix: entrypoint settings & server-list

disable entrypoint bash debug

* add link to modern design

---------

Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com>
Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>
Co-authored-by: sstidl <sstidl@users.noreply.github.com>
Co-authored-by: qodo-free-for-open-source-projects[bot] <189517486+qodo-free-for-open-source-projects[bot]@users.noreply.github.com>

* add armv7

* reformat

* Add GDPR_EMAIL environment variable for Docker deployments (#743)

* Initial plan

* Add GDPR_EMAIL environment variable for Docker deployments

Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>

* Improve GDPR_EMAIL handling with proper escaping and loop

Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>

* Refine GDPR_EMAIL processing - skip index.html and improve escaping

Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>

* Optimize GDPR_EMAIL sed commands and improve escaping

Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>

* Clarify sed escaping comment for GDPR_EMAIL

Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>

---------

Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com>
Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>

* cleanup old EMAIL ENV Var

* fix: line break in html prevented sed replacement

* version 6.0.0pre1

* test: add mssql docker compose tests

* Update Speedtest screen recording link in README

* Filter unreachable servers from selector (newdesign UI) (#769)

* Filter unreachable servers from selector (newdesign UI)

* Apply suggestions from code review

Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>

* Potential fix for pull request finding

Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>

* keep // servers in list

Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>

* fix misleading comment

---------

Co-authored-by: Lumi <lumi@openclaw.local>
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Stefan Stidl <sti-github@stidl.com>

* fix: server.json handling

* Use server-list.json in classic frontend by default

* Add configurable server list URLs to frontend and Docker

---------

Co-authored-by: Timendus <mail@timendus.com>
Co-authored-by: Stefan Stidl <stefan.stidl@ffg.at>
Co-authored-by: qodo-merge-pro-for-open-source[bot] <189517486+qodo-merge-pro-for-open-source[bot]@users.noreply.github.com>
Co-authored-by: qodo-merge-for-open-source[bot] <189517486+qodo-merge-for-open-source[bot]@users.noreply.github.com>
Co-authored-by: Copilot <198982749+Copilot@users.noreply.github.com>
Co-authored-by: sstidl <12804296+sstidl@users.noreply.github.com>
Co-authored-by: qodo-free-for-open-source-projects[bot] <189517486+qodo-free-for-open-source-projects[bot]@users.noreply.github.com>
Co-authored-by: Stefan Stidl <sti-github@stidl.com>
Co-authored-by: Lumi <lumi@openclaw.local>
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
2026-04-11 23:07:05 +02:00

9.1 KiB
Executable file

Using the docker image

A docker version of LibreSpeed is available here: GitHub Packages

Alpine Linux variant

An Alpine Linux based docker version of LibreSpeed is also available here: GitHub Packages under all the tags that have the -alpine suffix. This variant is significantly smaller but can have slightly different behaviour due to its toolchain being based in musl libc as mentioned in here.

Quickstart

If you just want to try it, the fastest way is:

docker run -p 80:8080 -d --name speedtest --rm ghcr.io/librespeed/speedtest

Then go with your browser to port 80 of your server and try it out. If port 80 is already in use, adjust the first number in 80:8080 above. Default is to run in standalone mode.

Docker Compose

In production environments we would recommend using docker-compose.

To start the container using docker compose the following docker-compose.yml configuration can be used:

version: '3.7'
services:
  speedtest:
    container_name: speedtest
    image: ghcr.io/librespeed/speedtest:latest
    restart: always
    environment:
      MODE: standalone
      #TITLE: "LibreSpeed"
      #TELEMETRY: "false"
      #ENABLE_ID_OBFUSCATION: "false"
      #REDACT_IP_ADDRESSES: "false"
      #PASSWORD:
      #GDPR_EMAIL: "privacy@example.com"
      #DISABLE_IPINFO: "false"
      #IPINFO_APIKEY: "your api key"
      #DISTANCE: "km"
      #WEBPORT: 8080
    ports:
      - "80:8080" # webport mapping (host:container)

Please adjust the environment variables according to the intended operating mode.

Standalone mode

If you want to install LibreSpeed on a single server, you need to configure it in standalone mode. To do this, set the MODE environment variable to standalone.

The test can be accessed on port 80.

Here's a list of additional environment variables available in this mode:

  • TITLE: Title of your speed test. Default value: LibreSpeed
  • USE_NEW_DESIGN: When set to true, enables the new modern frontend design. When set to false (default), uses the classic design. The design can also be switched using URL parameters (?design=new or ?design=old). Default value: false
  • SERVER_LIST_URL: When set, both frontend designs load their server list from this URL instead of the generated or mounted server-list.json. This is useful if you want the containerized frontend to consume a remote shared server list.
  • TELEMETRY: Whether to enable telemetry or not. If enabled, you maybe want your data to be persisted. See below. Default value: false
  • ENABLE_ID_OBFUSCATION: When set to true with telemetry enabled, test IDs are obfuscated, to avoid exposing the database internal sequential IDs. Default value: false
  • OBFUSCATION_SALT: The salt string that is used to obfuscate the test IDs. The format shoud be a 2 byte hex string (e.g. 0x1234abcd). If not specified, a random one will be generated.
  • REDACT_IP_ADDRESSES: When set to true with telemetry enabled, IP addresses and hostnames are redacted from the collected telemetry, for better privacy. Default value: false
  • DB_TYPE: When set to one of the supported DB-Backends it will use this instead of the default sqlite database backend. TELEMETRY has to be set to true. Also you have to create the database as described in doc.md. Supported backend types are:
    • sqlite - no additional settings required
    • mysql, postgresql - set additional env-variables:
      • DB_HOSTNAME - Name or IP of the DB server
      • DB_PORT (mysql only) - Port where DB is running
      • DB_NAME - Name of the telemetry db
      • DB_USERNAME, DB_PASSWORD - credentials of the user with read and update permissions to the db
    • mssql - not supported in docker image yet (feel free to open a PR with that, has to be done in entrypoint.sh)
  • PASSWORD: Password to access the stats page. If not set, stats page will not allow accesses.
  • GDPR_EMAIL: Email address displayed in the privacy policy for data deletion requests. If not set, the default placeholder text will be shown. This should be set to comply with GDPR requirements when running in production. Must be specified when telemetry is enabled.
  • DISABLE_IPINFO: If set to true, ISP info and distance will not be fetched from either ipinfo.io or the offline database. Default: value: false
  • IPINFO_APIKEY: API key for ipinfo.io. Optional, but required if you want to use the full ipinfo.io APIs (required for distance measurement)
  • DISTANCE: When DISABLE_IPINFO is set to false, this specifies how the distance from the server is measured. Can be either km for kilometers, mi for miles, or an empty string to disable distance measurement. Requires an ipinfo.io API key. Default value: km
  • WEBPORT: Allows choosing a custom port for the included web server. Default value: 8080. Note that you will have to expose it through docker with the -p argument. This is not the port where the service is exposed outside docker!

If telemetry is enabled, a stats page will be available at http://your.server/results/stats.php, but a password must be specified.

Persist sqlite database

Default DB driver is sqlite. The DB file is written to /database/db.sql.

So if you want your data to be persisted over image updates, you have to mount a volume with -v $PWD/db-dir:/database.

Example Standalone Mode with telemetry

This command starts LibreSpeed in standalone mode, with persisted telemetry, ID obfuscation and a stats password, on port 86:

docker run -e MODE=standalone -e TELEMETRY=true -e ENABLE_ID_OBFUSCATION=true -e PASSWORD="yourPasswordHere" -e WEBPORT=86 -p 86:86 -v $PWD/db-dir/:/database -it ghcr.io/librespeed/speedtest

Multiple Points of Test

For multiple servers, you need to set up 1+ LibreSpeed backends, and 1 LibreSpeed frontend.

Backend mode

In backend mode, LibreSpeed provides only a test point with no UI. To do this, set the MODE environment variable to backend.

The following backend files can be accessed on port 80: garbage.php, empty.php, getIP.php

Here's a list of additional environment variables available in this mode:

  • IPINFO_APIKEY: API key for ipinfo.io. Optional, but required if you want to use the full ipinfo.io APIs (required for distance measurement). If no API key is provided, the offline database will be used instead.

Example Backend mode

This command starts LibreSpeed in backend mode, with the default settings, on port 80:

docker run -e MODE=backend -p 80:8080 -it ghcr.io/librespeed/speedtest

Frontend mode

In frontend mode, LibreSpeed serves clients the Web UI and a list of servers. To do this:

  • Set the MODE environment variable to frontend

  • Create a servers.json file with your test points. The syntax is the following:

    [
        {
            "name": "Friendly name for Server 1",
            "server" :"//server1.mydomain.com/",
            "dlURL" :"garbage.php",
            "ulURL" :"empty.php",
            "pingURL" :"empty.php",
            "getIpURL" :"getIP.php"
        },
        {
            "name": "Friendly name for Server 2",
            "server" :"https://server2.mydomain.com/",
            "dlURL" :"garbage.php",
            "ulURL" :"empty.php",
            "pingURL" :"empty.php",
            "getIpURL" :"getIP.php"
        },
        //...more servers...
    ]
    

    Note: if a server only supports HTTP or HTTPS, specify the protocol in the server field. If it supports both, just use //.

  • Mount this file to /servers.json in the container (example at the end of this file)

The test can be accessed on port 80.

The list of environment variables available in this mode is the same as above in standalone mode.

If you want the Docker frontend to load its server list from another URL instead of /servers.json, set SERVER_LIST_URL:

docker run -e MODE=frontend -e SERVER_LIST_URL="https://example.com/custom-server-list.json" -p 80:8080 -it ghcr.io/librespeed/speedtest

Example Frontend mode

This command starts LibreSpeed in frontend mode, with a given servers.json file, and with telemetry, ID obfuscation, and a stats password and a persistant sqlite database for results:

docker run -e MODE=frontend -e TELEMETRY=true -e ENABLE_ID_OBFUSCATION=true -e PASSWORD="yourPasswordHere" -v $PWD/servers.json:/servers.json -v $PWD/db-dir/:/database -p 80:80 -it ghcr.io/librespeed/speedtest

Dual mode

In dual mode, LibreSpeed operates as a standalone server that can also connect to other test points. To do this:

  • Set the MODE environment variable to dual
  • Follow the servers.json instructions for the frontend mode
  • The first server entry should be the local server, using the server endpoint address that a client can access.