Skip to content
Stand with Ukraine flag

Installing ThingsBoard PE using Docker (Windows)

This guide covers a single-node ThingsBoard Professional Edition (PE) installation using Docker Compose on Windows. By the end, you will have a fully functional ThingsBoard instance running on your machine. For cluster setup, see Cluster Setup with Docker Compose.

Ensure your server meets the minimum requirements:

Use caseCPURAMRecommended services
Development / PoC1 core4 GBThingsBoard, PostgreSQL
Production (small)2 cores8 GBThingsBoard, PostgreSQL, Kafka
Production (recommended)4+ cores16+ GBThingsBoard, PostgreSQL, Kafka, Cassandra

Install Docker: Docker Desktop for Windows

We assume you have already chosen your subscription plan or decided to purchase a perpetual license. If not, navigate to the pricing page to select the best license option for your case. See How to get a pay-as-you-go subscription or How to get a perpetual license for details.

Create a dedicated directory for your ThingsBoard installation and navigate to it. All subsequent commands in this guide should be run from this directory.

Terminal window
mkdir C:\thingsboard
cd C:\thingsboard

ThingsBoard uses a message queue to route messages between its internal services. Select the option that matches your infrastructure:

  • In Memory (default) — built-in queue, no extra setup required. Suitable for development and PoC. Not recommended for production or multi-node deployments.
  • Kafka — high-throughput, durable queue. Run it yourself or use a managed service such as AWS MSK.
  • Confluent Cloud — fully managed Kafka service. Use this if you want Kafka without managing the infrastructure yourself.

Create the docker-compose.yml file. Replace PUT_YOUR_LICENSE_SECRET_HERE with your license secret from Step 1:

Terminal window
notepad docker-compose.yml

Paste one of the configurations below, save, and exit. Or use the download button to save the file directly.

services:
postgres:
restart: always
image: "postgres:18"
ports:
- "5432"
environment:
POSTGRES_DB: thingsboard
POSTGRES_PASSWORD: postgres
volumes:
- postgres-data:/var/lib/postgresql
healthcheck:
test: ["CMD-SHELL", "pg_isready -U postgres -d thingsboard"]
interval: 10s
timeout: 5s
retries: 5
start_period: 10s
thingsboard-pe:
restart: always
image: "thingsboard/tb-pe-node:4.3.1.1PE"
ports:
- "8080:8080"
- "1883:1883"
- "8883:8883"
- "9090:9090"
- "7070:7070"
- "5683-5688:5683-5688/udp"
logging:
driver: "json-file"
options:
max-size: "100m"
max-file: "10"
environment:
TB_SERVICE_ID: tb-pe-node
TB_LICENSE_SECRET: PUT_YOUR_LICENSE_SECRET_HERE
TB_LICENSE_INSTANCE_DATA_FILE: /data/license.data
REPORTS_SERVER_ENDPOINT_URL: http://tb-web-report:8383
SPRING_DATASOURCE_URL: jdbc:postgresql://postgres:5432/thingsboard
SPRING_DATASOURCE_PASSWORD: postgres
# Pre-configured for optional Trendz Analytics integration
DEFAULT_TRENDZ_URL: http://trendz:8888
DEFAULT_TB_URL: http://thingsboard-pe:8080
volumes:
- license-data:/data
depends_on:
postgres:
condition: service_healthy
tb-web-report:
restart: always
image: "thingsboard/tb-pe-web-report:4.3.1.1PE"
ports:
- "8383"
depends_on:
- thingsboard-pe
environment:
HTTP_BIND_ADDRESS: 0.0.0.0
HTTP_BIND_PORT: 8383
LOGGER_LEVEL: info
LOG_FOLDER: logs
LOGGER_FILENAME: tb-web-report-%DATE%.log
DOCKER_MODE: true
DEFAULT_PAGE_NAVIGATION_TIMEOUT: 120000
DASHBOARD_IDLE_WAIT_TIME: 3000
USE_NEW_PAGE_FOR_REPORT: true
volumes:
postgres-data:
name: tb-postgres-data
driver: local
license-data:
name: tb-pe-license-data
driver: local

Services started:

  • postgres — PostgreSQL database
  • thingsboard-pe — ThingsBoard application node
  • tb-web-report — reporting component for PDF/PNG dashboard exports
Ports (host:container)
Port mappingDescription
8080:8080Web UI and REST API. The left value is the host port — change it if 8080 is already in use.
1883:1883MQTT — plaintext IoT device connections
8883:8883MQTT over TLS — encrypted IoT device connections
5683:5683/udpCoAP — plaintext IoT protocol
5684:5684/udpCoAP over DTLS — encrypted CoAP
5685:5685/udpLwM2M CoAP — plaintext Lightweight M2M
5686:5686/udpLwM2M CoAP over DTLS — encrypted LwM2M
5687:5687/udpLwM2M — plaintext Lightweight M2M (Bootstrap)
5688:5688/udpLwM2M over DTLS — encrypted Lightweight M2M (Bootstrap)
7070:7070Edge RPC (gRPC) — connections from ThingsBoard Edge nodes
9090:9090Remote Integration Executor (gRPC) — used by external integration services
Environment variables
VariableDescription
POSTGRES_PASSWORDPassword for the PostgreSQL postgres user. Must match SPRING_DATASOURCE_PASSWORD. Change the default value in production.
SPRING_DATASOURCE_URLPostgreSQL JDBC connection URL. Specifies the host and database name. Default: jdbc:postgresql://postgres:5432/thingsboard.
SPRING_DATASOURCE_USERNAMEPostgreSQL username ThingsBoard connects as. Default: postgres.
SPRING_DATASOURCE_PASSWORDPostgreSQL password ThingsBoard uses to connect. Must match POSTGRES_PASSWORD.
TB_QUEUE_TYPEMessage queue type. Options: in-memory (default, single-node only), kafka, rabbitmq.
TB_KAFKA_SERVERSKafka bootstrap servers. Required when TB_QUEUE_TYPE=kafka. Default: localhost:9092.
TB_LICENSE_SECRETThingsBoard PE license secret key.
DEFAULT_TRENDZ_URLTrendz Analytics endpoint — pre-configured for optional Trendz integration.
Volumes
VolumeDescription
tb-postgres-dataPersists PostgreSQL data across container restarts and upgrades.
tb-pe-kafka-dataPersists Kafka data. Only present when TB_QUEUE_TYPE=kafka.
tb-pe-license-dataPersists license instance data — prevents license re-activation on each restart.

For the full list of configuration parameters, see the Configuration Reference.

Step 3. Initialize database schema and system assets

Section titled “Step 3. Initialize database schema and system assets”

Before starting ThingsBoard, initialize the database schema and load built-in assets. Choose the option that matches your goal:

  • With demo data — also loads a sample tenant account, pre-built dashboards, and demo devices. Useful for exploring the platform before deploying to production.
  • Clean install — initializes the database with system data only (rule chains, widget bundles, system dashboards).
Terminal window
docker compose run --rm -e INSTALL_TB=true -e LOAD_DEMO=true thingsboard-pe

The container exits automatically once initialization is complete.

Start all containers:

Terminal window
docker compose up -d

Monitor the startup. The line confirming the platform is ready will be highlighted:

Terminal window
docker compose logs -f thingsboard-pe

Press Ctrl+C to detach from the log stream — containers will continue running in the background.

Open http://localhost:8080 in your browser. You should see the ThingsBoard login page. Use the following default credentials:

RoleEmailPasswordWith demo dataClean install
System Administrator[email protected]sysadmin
Tenant Administrator[email protected]tenant
Customer User[email protected]customer

See Getting Started for your next steps after login.

Stream the ThingsBoard container logs:

Terminal window
docker compose logs -f thingsboard-pe

Stop all containers:

Terminal window
docker compose down

Start all containers:

Terminal window
docker compose up -d

You may optionally install Trendz Analytics at any time. The Trendz compose file extends the main docker-compose.yml — always run them together.

  1. Create the Trendz database in PostgreSQL:

    Terminal window
    docker compose -f docker-compose.yml exec -it postgres psql -U postgres -c "CREATE DATABASE trendz;"
  2. Create the docker-compose-trendz.yml file with the following content:

    docker-compose-trendz.yml
    services:
    trendz:
    restart: always
    image: "thingsboard/trendz:1.15.1"
    ports:
    - "8888:8888"
    environment:
    TB_API_URL: http://thingsboard-pe:8080
    SPRING_DATASOURCE_URL: jdbc:postgresql://postgres:5432/trendz
    SPRING_DATASOURCE_USERNAME: postgres
    SPRING_DATASOURCE_PASSWORD: postgres
    SCRIPT_ENGINE_DOCKER_PROVIDER_URL: trendz-python-executor:8181
    SCRIPT_ENGINE_TIMEOUT: 30000
    volumes:
    - trendz-conf:/trendz-config-files
    - trendz-data:/data
    depends_on:
    postgres:
    condition: service_healthy
    trendz-python-executor:
    restart: always
    image: "thingsboard/trendz-python-executor:1.15.1"
    ports:
    - "8181:8181"
    environment:
    EXECUTOR_MANAGER: 1
    EXECUTOR_SCRIPT_ENGINE: 6
    THROTTLING_QUEUE_CAPACITY: 10
    THROTTLING_THREAD_POOL_SIZE: 6
    NETWORK_BUFFER_SIZE: 5242880
    volumes:
    - trendz-python-executor-conf:/python-executor-config-files
    - trendz-python-executor-data:/data
    volumes:
    trendz-conf:
    name: trendz-conf
    driver: local
    trendz-data:
    name: trendz-data
    driver: local
    trendz-python-executor-conf:
    name: trendz-python-executor-conf
    driver: local
    trendz-python-executor-data:
    name: trendz-python-executor-data
    driver: local
ParameterDescription
8888:8888Trendz HTTP port
trendz-confDocker volume for Trendz configuration
trendz-dataDocker volume for Trendz data
trendz-python-executor-confDocker volume for Trendz Python executor configuration
trendz-python-executor-dataDocker volume for Trendz Python executor data

Bring up all containers (including Trendz) as a single Compose project:

Terminal window
docker compose -f docker-compose.yml -f docker-compose-trendz.yml up -d
docker compose -f docker-compose.yml -f docker-compose-trendz.yml logs -f thingsboard-pe

Stream ThingsBoard logs:

Terminal window
docker compose -f docker-compose.yml -f docker-compose-trendz.yml logs -f thingsboard-pe

Stream Trendz logs:

Terminal window
docker compose -f docker-compose.yml -f docker-compose-trendz.yml logs -f trendz

Stop all containers:

Terminal window
docker compose -f docker-compose.yml -f docker-compose-trendz.yml down

Start all containers:

Terminal window
docker compose -f docker-compose.yml -f docker-compose-trendz.yml up -d

Trendz Analytics has a different version system and should be updated separately from the ThingsBoard platform. See Trendz Docker Upgrade.

When a new ThingsBoard release becomes available, update your installation to benefit from the latest features and security patches.

See the Upgrade Instructions for detailed steps.

If you observe errors related to DNS issues, for example:

Terminal window
127.0.1.1:53: cannot unmarshal DNS message

Configure your system to use Google public DNS servers.