p4n4-docs

Getting Started

Prerequisites

Installation

pip install p4n4
p4n4 --version

Create a project

p4n4 init my-project                 # IoT stack only (default)
p4n4 init my-project --layer iot,ai  # multiple stacks
p4n4 init my-project --layer all     # iot + ai + edge

The interactive wizard prompts for configuration (InfluxDB organisation, timezone, service passwords, including the Node-RED editor login — leave blank to auto-generate). It then:

Project layout

A single-layer project keeps the stack files at the project root:

my-project/
├── .p4n4.json
├── .env
├── docker-compose.yml
├── config/
└── scripts/

A multi-layer project gives each stack its own subdirectory, so the stacks run as separate Compose projects (the AI and edge stacks attach to the p4n4-net network that the IoT stack creates):

my-project/
├── .p4n4.json                  ← manifest at the root, lists all layers
├── iot/
│   ├── docker-compose.yml
│   ├── .env
│   ├── config/
│   └── scripts/
├── ai/
│   ├── docker-compose.yml
│   ├── .env
│   ├── config/
│   └── scripts/
└── edge/
    ├── docker-compose.yml
    ├── .env
    ├── runner/
    ├── edge-impulse/models/    ← .eim models (never committed)
    └── onnx/models/            ← .onnx models (never committed)

Shared values such as INFLUXDB_TOKEN are written identically to every layer’s .env, and p4n4 secret rotate keeps them in sync.

Start the stacks

cd my-project
p4n4 up          # all enabled stacks
p4n4 up iot      # one stack only

With no argument, stacks start in dependency order:

  1. iot — creates the p4n4-net Docker bridge network, starts Mosquitto and InfluxDB first.
  2. ai — attaches to p4n4-net.
  3. edge — attaches to p4n4-net.

p4n4 down stops them in reverse order.

Service URLs (default ports)

Service URL
Node-RED http://localhost:1880 (log in with NODE_RED_USER / NODE_RED_PASSWORD from the IoT .env)
Grafana http://localhost:3000
InfluxDB http://localhost:8086
n8n http://localhost:5678
Letta http://localhost:8283
Ollama http://localhost:11434
Inference runner http://localhost:8080/health

MQTT is on localhost:1883 (TCP) and :9001 (WebSocket). Credentials are in each layer’s .env; p4n4 secret show prints them masked.

Stop everything

p4n4 down

Send a test reading

Devices publish JSON to sensors/<device-id>/<measurement>:

mosquitto_pub -h localhost -t sensors/test-01/temperature -m '{"value": 23.5, "unit": "C"}'

Node-RED writes it to InfluxDB, and it shows up on Grafana’s Sensor Data panel. With the edge stack running, publish a feature vector to sensors/<device-id>/raw to get a result on inference/<device-id>/result (mock mode until you deploy a model).

Next steps