Install#
pamoja is the whole framework in one package, in every language:
cargo add pamoja # Rust
npm install pamoja # TypeScript and Node
pip install pamoja # Python
dotnet add package Pamoja # C# and .NETThat is the right default. Every capability is also its own package, and the sections below list them, but what you gain by picking them differs between Rust and the bindings. It is worth knowing which before you choose.
Every crate, package, and binding shares one version and is released together,
so 0.1.15 of any package wraps 0.1.15 of every other. The
changelog covers
all of them in one entry.
What picking packages changes#
In Rust, it changes what gets compiled. A crate you do not name is never built, and its dependencies are never fetched, so a narrow build is genuinely smaller and carries less third-party code.
In the bindings it changes what you import, not what you download. Node, Python, and .NET each load one compiled engine that carries every capability, and every package depends on it. Choosing packages narrows the API you see, the manifest you ship, and the code your dependency scanners have to account for. It does not shrink the engine.
Neither is a workaround. Compiling only what you use is a property of a compiled language, and the deployments that need it (a microcontroller with kilobytes of flash) run Rust and could not host a Python or .NET runtime at all.
The two things called core#
A binding has one package you never name and one you sometimes do, and they are easy to confuse.
The compiled engine is @pamoja/native, pamoja-native, and
Pamoja.Native. It is the built Rust library, the generated contract over it,
and the plumbing every facade needs to call it: the handle type, the error every
failed call raises, and string marshalling. Every package declares it, so it
arrives on its own and you never install it by hand. Rust has no equivalent,
because there you compile the crates.
The engine surface is @pamoja/core, pamoja-core, and Pamoja.Core, the
counterpart of the pamoja-core crate. It is the runtime version and
Transport, the abstraction MQTT, CoAP, and the loopback all implement. It is a
capability like any other, listed first in the tables below, and most packages do
not depend on it: only the transports do, because they are the ones that return a
Transport. Install it when you want to hold a link behind that interface.
Rust#
cargo add pamoja # every capability, behind a feature each
cargo add pamoja-modbus # or one crate on its ownFrom examples/tests/guides/imports.rs:
use pamoja::modbus::Adu; // the same type as pamoja_modbus::Adu
use pamoja_codec::CborCodec;Each module of pamoja is the crate of the same name, so the two ways in share
one API and one set of documentation, and code moves between them unchanged.
Naming features is what makes a build small. Measured from the resolved
dependency graph, for a x86_64-unknown-linux-gnu build:
| Build | What you write | Crates compiled | From this workspace | External |
|---|---|---|---|---|
| Every capability | cargo add pamoja | 107 | 31 | 76 |
| Codecs and identity | cargo add pamoja --no-default-features --features codec,security | 36 | 4 | 32 |
| Field I/O | cargo add pamoja --no-default-features --features field-io | 6 | 6 | 0 |
| One capability | cargo add pamoja --no-default-features --features modbus | 3 | 3 | 0 |
Bare metal, no std | cargo add pamoja --no-default-features --features modbus,sensors,lora | 5 | 5 | 0 |
field-io there is a group feature. Six domains have one, so a build names a
domain rather than listing its parts:
Serial framing, Modbus RTU, CAN and J1939, I2C, SPI, and GPIO
cargo add pamoja --features field-iocargo add pamoja --features sensingcargo add pamoja --features radioAudit log, Secured session, Signed updates, Power, Telemetry
cargo add pamoja --features trustMQTT, CoAP, Loopback, Store and forward, Transport ladder, Event bus, Engine surface, Simulators
cargo add pamoja --features transportscargo add pamoja --features profilesThe narrow builds carry no third-party code at all: pamoja, pamoja-core, and
the capability crates, and nothing else. Most capability crates are no_std, so
the same code runs on a gateway and on a microcontroller. The
Rust reference lists every crate.
TypeScript and Node#
npm install pamoja # every capability
npm install @pamoja/modbus @pamoja/codec # or only the packages you useimport { readHoldingRegisters } from '@pamoja/modbus'
import { toCbor, fromCbor } from '@pamoja/codec'Every package depends on @pamoja/native, the compiled engine, prebuilt for
Linux (x64, arm64), macOS (x64, arm64), and Windows (x64); npm picks the right
one, and installs on anything else without a binary to load. Alpine and Windows
on ARM are the two that catch people out. It is one binary carrying every capability whichever packages you install,
so the choice is about the API surface and your dependency manifest, not the
download. Node 16 or later.
The same six domains, one package each. A domain package brings in its capabilities and re-exports each under its own name, so a name two of them share stays unambiguous:
npm install @pamoja/field-ionpm install @pamoja/sensingnpm install @pamoja/radionpm install @pamoja/trust@pamoja/transportsMQTT, CoAP, Loopback, Store and forward, Transport ladder, Event bus, Engine surface, Simulators
npm install @pamoja/transportsnpm install @pamoja/profilesEngine#
@pamoja/coreThe transport every link shares (send, receive, subscribe, and a faulty wrapper for tests) and the runtime version
npm install @pamoja/coreIdentity#
@pamoja/securityed25519 device identity: sign a reading and verify it, so a gateway can prove it is authentic
npm install @pamoja/securityCodecs#
@pamoja/codecCBOR, JSON, and raw codecs behind one trait, delta and varint batch packing, and an f32 quantizer for metered links
npm install @pamoja/codecHelpers#
@pamoja/kitPlain-language helper math: smoothing, calibration, PID and thermostat control, trend and surge prediction, rolling windows, kinematics, and geo
npm install @pamoja/kitField I/O#
@pamoja/serialSLIP and COBS byte stuffing with streaming decoders, so a UART byte stream carries discrete packets
npm install @pamoja/serialnpm install @pamoja/modbus@pamoja/canCAN 2.0 and CAN-FD frames with 11- and 29-bit identifiers, plus J1939 decode and compose
npm install @pamoja/can@pamoja/gpioI2C address frames with reserved-range checks, the four SPI clock modes, and active-high or active-low pins
npm install @pamoja/gpioSensing and actuation#
@pamoja/sensorsDatasheet-anchored decoders for eleven parts: the BME280, BMP280, DS18B20, HDC1080, INA219, INA226, ADS1115, OPT3001, SCD4x, SHT3x, and TMP117
npm install @pamoja/sensorsnpm install @pamoja/actuatorsRadio and reach#
@pamoja/loraTime-on-air, duty-cycle off-time, and the regional channel plans a LoRa node must keep to
npm install @pamoja/lora@pamoja/lorawanLoRaWAN 1.0.x MAC framing, AES-CMAC and AES encryption, and both halves of the OTAA join
npm install @pamoja/lorawan@pamoja/meshAddressed, hop-limited, CRC-checked frames and duplicate suppression that floods a packet exactly once
npm install @pamoja/meshnpm install @pamoja/routingMAVLink#
@pamoja/mavlinkMAVLink v1 and v2 framing, signing, named message fields, and the mission, command, and offboard protocols
npm install @pamoja/mavlinkTrust and operation#
@pamoja/auditA tamper-evident, hash-chained log; altering, reordering, or dropping a record breaks verification
npm install @pamoja/audit@pamoja/sessionX25519 key agreement, HKDF, and ChaCha20-Poly1305 with an anti-replay window, with no TLS stack
npm install @pamoja/session@pamoja/updateSigned firmware manifests, streaming image verification, and A/B slots that fall back on their own
npm install @pamoja/update@pamoja/powerDuty cycling and an energy-aware governor that stretches work as the battery drains
npm install @pamoja/power@pamoja/telemetryObservability that ships only what is worth the bytes as link cost rises, while counting everything
npm install @pamoja/telemetryTransports and testing#
npm install @pamoja/mqttnpm install @pamoja/coap@pamoja/loopbackAn in-process transport with topic matching and a fault injector, for testing with no broker
npm install @pamoja/loopback@pamoja/syncOffline-first queues: in memory, and a crash-safe on-disk queue that survives power loss
npm install @pamoja/sync@pamoja/ladderCheapest reachable link first, buffering to a store when every link is down
npm install @pamoja/laddernpm install @pamoja/bus@pamoja/simNoisy and replay sensors, a recording actuator, and a simulated robot that dead-reckons its pose
npm install @pamoja/simProfiles and robotics#
@pamoja/profileNamed, ready-to-run device profiles from plain data or a JSON manifest
npm install @pamoja/profile@pamoja/ros2ROS 2 names, RIHS01 type hashes, CDR encoding, and rmw_zenoh key assembly, with no ROS 2 installed
npm install @pamoja/ros2npm install @pamoja/zenohPython#
pip install pamoja # every capability
pip install pamoja-modbus pamoja-codec # or only the distributions you usefrom pamoja.modbus import read_holding_registers
from pamoja.codec import to_cbor, from_cborpamoja is a namespace package: each distribution ships one pamoja.<name>
module and they merge on import. Every distribution depends on pamoja-native,
the compiled engine, with wheels for the same platforms as the Node engine and
for Python 3.10 and later; elsewhere pip builds it from the sdist, which needs
a Rust toolchain.
The same six domains, one package each. A domain package brings in its capabilities and re-exports each under its own name, so a name two of them share stays unambiguous:
pip install pamoja-field-iopip install pamoja-sensingpip install pamoja-radiopip install pamoja-trustpamoja.transportsMQTT, CoAP, Loopback, Store and forward, Transport ladder, Event bus, Engine surface, Simulators
pip install pamoja-transportspip install pamoja-profilesEngine#
pamoja.coreThe transport every link shares (send, receive, subscribe, and a faulty wrapper for tests) and the runtime version
pip install pamoja-coreIdentity#
pamoja.securityed25519 device identity: sign a reading and verify it, so a gateway can prove it is authentic
pip install pamoja-securityCodecs#
pamoja.codecCBOR, JSON, and raw codecs behind one trait, delta and varint batch packing, and an f32 quantizer for metered links
pip install pamoja-codecHelpers#
pamoja.kitPlain-language helper math: smoothing, calibration, PID and thermostat control, trend and surge prediction, rolling windows, kinematics, and geo
pip install pamoja-kitField I/O#
pamoja.serialSLIP and COBS byte stuffing with streaming decoders, so a UART byte stream carries discrete packets
pip install pamoja-serialpip install pamoja-modbuspamoja.canCAN 2.0 and CAN-FD frames with 11- and 29-bit identifiers, plus J1939 decode and compose
pip install pamoja-canpamoja.gpioI2C address frames with reserved-range checks, the four SPI clock modes, and active-high or active-low pins
pip install pamoja-gpioSensing and actuation#
pamoja.sensorsDatasheet-anchored decoders for eleven parts: the BME280, BMP280, DS18B20, HDC1080, INA219, INA226, ADS1115, OPT3001, SCD4x, SHT3x, and TMP117
pip install pamoja-sensorspip install pamoja-actuatorsRadio and reach#
pamoja.loraTime-on-air, duty-cycle off-time, and the regional channel plans a LoRa node must keep to
pip install pamoja-lorapamoja.lorawanLoRaWAN 1.0.x MAC framing, AES-CMAC and AES encryption, and both halves of the OTAA join
pip install pamoja-lorawanpamoja.meshAddressed, hop-limited, CRC-checked frames and duplicate suppression that floods a packet exactly once
pip install pamoja-meshpip install pamoja-routingMAVLink#
pamoja.mavlinkMAVLink v1 and v2 framing, signing, named message fields, and the mission, command, and offboard protocols
pip install pamoja-mavlinkTrust and operation#
pamoja.auditA tamper-evident, hash-chained log; altering, reordering, or dropping a record breaks verification
pip install pamoja-auditpamoja.sessionX25519 key agreement, HKDF, and ChaCha20-Poly1305 with an anti-replay window, with no TLS stack
pip install pamoja-sessionpamoja.updateSigned firmware manifests, streaming image verification, and A/B slots that fall back on their own
pip install pamoja-updatepamoja.powerDuty cycling and an energy-aware governor that stretches work as the battery drains
pip install pamoja-powerpamoja.telemetryObservability that ships only what is worth the bytes as link cost rises, while counting everything
pip install pamoja-telemetryTransports and testing#
pip install pamoja-mqttpip install pamoja-coappamoja.loopbackAn in-process transport with topic matching and a fault injector, for testing with no broker
pip install pamoja-loopbackpamoja.syncOffline-first queues: in memory, and a crash-safe on-disk queue that survives power loss
pip install pamoja-syncpamoja.ladderCheapest reachable link first, buffering to a store when every link is down
pip install pamoja-ladderpip install pamoja-buspamoja.simNoisy and replay sensors, a recording actuator, and a simulated robot that dead-reckons its pose
pip install pamoja-simProfiles and robotics#
pip install pamoja-profilepamoja.ros2ROS 2 names, RIHS01 type hashes, CDR encoding, and rmw_zenoh key assembly, with no ROS 2 installed
pip install pamoja-ros2pip install pamoja-zenohC# and .NET#
dotnet add package Pamoja # every capability
dotnet add package Pamoja.Modbus Pamoja.Codec # or only the packages you useusing Pamoja.Modbus;
using Pamoja.Codec;A domain package there brings in its capabilities and ships no assembly of its own, since C# has no way to re-export a namespace, so a type is named the way it is when its package is referenced directly.
Each package is one namespace of the same name. Every package depends on
Pamoja.Native, which carries the native library for win-x64, linux-x64,
linux-arm64, osx-x64, and osx-arm64, and targets .NET 8. Those five are the
whole list: on any other runtime identifier, win-arm64 and the musl-based
distributions among them, the packages restore and compile and then throw
DllNotFoundException on the first call, because there is no native library to
load and, unlike Python, no source build to fall back on.
The same six domains, one package each. A domain package brings in its capabilities and re-exports each under its own name, so a name two of them share stays unambiguous:
Serial framing, Modbus RTU, CAN and J1939, I2C, SPI, and GPIO
dotnet add package Pamoja.FieldIodotnet add package Pamoja.Sensingdotnet add package Pamoja.RadioAudit log, Secured session, Signed updates, Power, Telemetry
dotnet add package Pamoja.TrustMQTT, CoAP, Loopback, Store and forward, Transport ladder, Event bus, Engine surface, Simulators
dotnet add package Pamoja.Transportsdotnet add package Pamoja.ProfilesEngine#
Pamoja.CoreThe transport every link shares (send, receive, subscribe, and a faulty wrapper for tests) and the runtime version
dotnet add package Pamoja.CoreIdentity#
Pamoja.Securityed25519 device identity: sign a reading and verify it, so a gateway can prove it is authentic
dotnet add package Pamoja.SecurityCodecs#
Pamoja.CodecCBOR, JSON, and raw codecs behind one trait, delta and varint batch packing, and an f32 quantizer for metered links
dotnet add package Pamoja.CodecHelpers#
Pamoja.KitPlain-language helper math: smoothing, calibration, PID and thermostat control, trend and surge prediction, rolling windows, kinematics, and geo
dotnet add package Pamoja.KitField I/O#
Pamoja.SerialSLIP and COBS byte stuffing with streaming decoders, so a UART byte stream carries discrete packets
dotnet add package Pamoja.Serialdotnet add package Pamoja.ModbusPamoja.CanCAN 2.0 and CAN-FD frames with 11- and 29-bit identifiers, plus J1939 decode and compose
dotnet add package Pamoja.CanPamoja.GpioI2C address frames with reserved-range checks, the four SPI clock modes, and active-high or active-low pins
dotnet add package Pamoja.GpioSensing and actuation#
Pamoja.SensorsDatasheet-anchored decoders for eleven parts: the BME280, BMP280, DS18B20, HDC1080, INA219, INA226, ADS1115, OPT3001, SCD4x, SHT3x, and TMP117
dotnet add package Pamoja.Sensorsdotnet add package Pamoja.ActuatorsRadio and reach#
Pamoja.LoraTime-on-air, duty-cycle off-time, and the regional channel plans a LoRa node must keep to
dotnet add package Pamoja.LoraPamoja.LorawanLoRaWAN 1.0.x MAC framing, AES-CMAC and AES encryption, and both halves of the OTAA join
dotnet add package Pamoja.LorawanPamoja.MeshAddressed, hop-limited, CRC-checked frames and duplicate suppression that floods a packet exactly once
dotnet add package Pamoja.Meshdotnet add package Pamoja.RoutingMAVLink#
Pamoja.MavlinkMAVLink v1 and v2 framing, signing, named message fields, and the mission, command, and offboard protocols
dotnet add package Pamoja.MavlinkTrust and operation#
Pamoja.AuditA tamper-evident, hash-chained log; altering, reordering, or dropping a record breaks verification
dotnet add package Pamoja.AuditPamoja.SessionX25519 key agreement, HKDF, and ChaCha20-Poly1305 with an anti-replay window, with no TLS stack
dotnet add package Pamoja.SessionPamoja.UpdateSigned firmware manifests, streaming image verification, and A/B slots that fall back on their own
dotnet add package Pamoja.UpdatePamoja.PowerDuty cycling and an energy-aware governor that stretches work as the battery drains
dotnet add package Pamoja.PowerPamoja.TelemetryObservability that ships only what is worth the bytes as link cost rises, while counting everything
dotnet add package Pamoja.TelemetryTransports and testing#
dotnet add package Pamoja.Mqttdotnet add package Pamoja.CoapPamoja.LoopbackAn in-process transport with topic matching and a fault injector, for testing with no broker
dotnet add package Pamoja.LoopbackPamoja.SyncOffline-first queues: in memory, and a crash-safe on-disk queue that survives power loss
dotnet add package Pamoja.SyncPamoja.LadderCheapest reachable link first, buffering to a store when every link is down
dotnet add package Pamoja.Ladderdotnet add package Pamoja.BusPamoja.SimNoisy and replay sensors, a recording actuator, and a simulated robot that dead-reckons its pose
dotnet add package Pamoja.SimProfiles and robotics#
dotnet add package Pamoja.ProfilePamoja.Ros2ROS 2 names, RIHS01 type hashes, CDR encoding, and rmw_zenoh key assembly, with no ROS 2 installed
dotnet add package Pamoja.Ros2dotnet add package Pamoja.Zenoh