Reticulum MeshChatX
Русский | Deutsch | Italiano | 中文 | 日本語
A extensively modified and feature-rich fork of Reticulum MeshChat by Liam Cottle.
This project is independent from the original Reticulum MeshChat project and is not affiliated with it.
- Website: meshchatx.com
- Source: git.quad4.io/RNS-Things/MeshChatX
- Official Mirror: github.com/Sudo-Ivan/MeshChatX - Used for GitHub Actions.
- Releases: git.quad4.io/RNS-Things/MeshChatX/releases
- Changelog:
CHANGELOG.md - TODO: Boards
Important Changes from Reticulum MeshChat
- Uses LXST
- Replaced Peewee ORM with raw SQL.
- Replaced Axios with native fetch.
- Uses Electron 41.x (bundled Node 24 runtime).
- .whls ships with webserver and built-in frontend assets for more deployment options.
- i18n
- PNPM and Poetry for dependency management.
Warning
MeshChatX is not guaranteed to be wire/data compatible with older Reticulum MeshChat releases. Back up data before migration/testing.
Warning
Legacy systems are not fully supported yet. Current baseline is Python
>=3.11and Node>=24(Electron 41 aligns with Node 24;package.jsonenginesand CI use the same line).
Requirements
- Python
>=3.11(frompyproject.toml) - Node.js
>=24(frompackage.jsonengines) - pnpm
10.33.0(frompackage.jsonpackageManager) - Poetry (used by
Taskfile.ymland CI workflows)
task install
task lint:all
task test:all
task build:all
Install Methods
Use the method that matches your environment and packaging preference.
| Method | Includes frontend assets | Architectures | Best for |
|---|---|---|---|
| Docker image | Yes | linux/amd64, linux/arm64 |
Fastest setup on Linux servers/hosts |
Python wheel (.whl) |
Yes | Any Python-supported architecture | Headless/web-server install without Node build |
| Linux AppImage | Yes | x64, arm64 |
Portable desktop use |
Debian package (.deb) |
Yes | x64, arm64 |
Debian/Ubuntu installs |
RPM package (.rpm) |
Yes | CI-runner dependent for published artifact | Fedora/RHEL/openSUSE style systems |
| From source | Built locally | Host architecture | Development and custom builds |
Notes:
- GitHub Actions builds tagged releases: Windows and macOS via
.github/workflows/build-release.yml, Linux wheel/AppImage/deb/rpm via.github/workflows/build-linux-release.yml, and the container image via.github/workflows/docker.yml. - Linux
x64andarm64AppImage + DEB are built on GitHub; RPM is attempted and uploaded when produced.
Quick Start: Docker
docker compose up -d
Default compose file maps:
127.0.0.1:8000on host -> container port8000./meshchat-config->/configfor persistence
If your local meshchat-config permissions block writes, fix ownership:
sudo chown -R 1000:1000 ./meshchat-config
Install from Release Artifacts
1) Linux AppImage (x64/arm64)
- Download
ReticulumMeshChatX-v<version>-linux-<arch>.AppImagefrom releases. - Make it executable and run:
chmod +x ./ReticulumMeshChatX-v*-linux-*.AppImage
./ReticulumMeshChatX-v*-linux-*.AppImage
2) Debian/Ubuntu .deb (x64/arm64)
- Download
ReticulumMeshChatX-v<version>-linux-<arch>.deb. - Install:
sudo apt install ./ReticulumMeshChatX-v*-linux-*.deb
3) RPM-based systems
- Download
ReticulumMeshChatX-v<version>-linux-<arch>.rpmif present in the release. - Install with your distro tool:
sudo rpm -Uvh ./ReticulumMeshChatX-v*-linux-*.rpm
4) Python wheel (.whl)
Release wheels include the built web assets.
pip install ./reticulum_meshchatx-*-py3-none-any.whl
meshchatx --headless
pipx is also supported:
pipx install ./reticulum_meshchatx-*-py3-none-any.whl
Run from Source (Web Server Mode)
Use this when developing or when you need a local custom build.
git clone https://git.quad4.io/RNS-Things/MeshChatX.git
cd MeshChatX
corepack enable
pnpm config set verify-store-integrity true
pnpm install --frozen-lockfile
pip install "poetry==2.3.4"
poetry check --lock
poetry install
pnpm run build-frontend
poetry run python -m meshchatx.meshchat --headless --host 127.0.0.1
Notes on the install commands above:
pnpm install --frozen-lockfilerefuses to updatepnpm-lock.yamland fails if the lockfile does not matchpackage.json. This is what blocks an unexpected upstream version from being silently pulled in.verify-store-integrity=trueis also set in the project.npmrc; the explicitpnpm config setline above just hardens the user-level config too.- Lifecycle scripts (
preinstall/postinstall) are blocked by default in pnpm v10+. Only the packages listed underpnpm.onlyBuiltDependenciesinpackage.jsonare allowed to run install scripts (currentlyelectron,electron-winstaller,esbuild). poetry check --lockfails fast ifpoetry.lockis out of sync withpyproject.toml;poetry installthen resolves only from the lockfile.- For a strict lockfile-only Poetry install (no implicit lockfile refresh), pin Poetry with
pip install "poetry==2.3.4"to match what CI uses.
If you intentionally want to update dependencies, run pnpm update / poetry update in a dedicated commit and review the resulting lockfile diff before pushing.
Run sandboxed (Linux)
To run the native meshchatx binary (alias: meshchat) with extra filesystem isolation, you can use Firejail or Bubblewrap (bwrap) while keeping normal network access for Reticulum and the web UI. Full examples (pip/pipx, Poetry, USB serial notes) are in:
The same page appears in the in-app Documentation list (MeshChatX docs) when served from the bundled or synced meshchatx-docs files.
Linux desktop: emoji fonts
The emoji picker renders standard Unicode emoji using your system fonts (Electron/Chromium). If emoji show as empty squares (“tofu”), install a color emoji package and restart the app.
| Family (examples) | Package |
|---|---|
| Arch Linux, Artix, Manjaro | noto-fonts-emoji (sudo pacman -S noto-fonts-emoji) |
| Debian, Ubuntu | fonts-noto-color-emoji (sudo apt install fonts-noto-color-emoji) |
| Fedora | google-noto-emoji-color-fonts |
After installing, run fc-cache -fv if glyphs still fail until the next login. Optional: noto-fonts for broader symbol coverage on minimal installs.
Build Desktop Packages from Source
These scripts are defined in package.json and Taskfile.yml.
Linux x64 AppImage + DEB
pnpm run dist:linux-x64
Linux arm64 AppImage + DEB
pnpm run dist:linux-arm64
RPM
pnpm run dist:rpm
Or through Task:
task dist:fe:rpm
Container build (wheel, AppImage, deb, rpm)
Dockerfile.build runs the same shell-driven steps CI uses (Poetry, pnpm, task, packaging APT deps). It is oriented toward linux/amd64 (NodeSource amd64 tarball, Task amd64 binary). Default target is everything; override with a build arg.
Targets for MESHCHATX_BUILD_TARGETS: all (default), wheel, or electron (AppImage + deb for x64 and arm64, best-effort RPM, no wheel).
Build:
docker build -f Dockerfile.build -t meshchatx-build:local .
Build only a wheel:
docker build -f Dockerfile.build --build-arg MESHCHATX_BUILD_TARGETS=wheel -t meshchatx-build:wheel .
Copy /artifacts from the finished image to the host:
cid=$(docker create meshchatx-build:local)
docker cp "${cid}:/artifacts" ./meshchatx-artifacts
docker rm "${cid}"
Architecture Support Summary
- Docker image:
amd64,arm64 - Linux AppImage:
x64,arm64 - Linux DEB:
x64,arm64 - Windows:
x64,arm64(build scripts available) - macOS: build scripts available (
arm64,universal) for local build environments - Android: native APKs — ABIs
arm64-v8a,x86_64,armeabi-v7a(32-bit ARM), plus universal
Android
MeshChatX supports native Android APK builds (not only Termux).
Build APKs from source
From repo root:
# 1) Build Chaquopy wheels used by android/app/build.gradle
bash scripts/build-android-wheels-local.sh
# 2) Build default slim APKs (universal packaging: one APK per flavor+type)
cd android
./gradlew --no-daemon :app:assembleSlimDebug :app:assembleSlimRelease
APK layout uses product flavors slim and full (Python tree size) plus ABI packaging universal (default) or split (see android/app/build.gradle).
With -PmeshchatxAbiPackaging=universal (default), each variant is a single APK containing every selected ABI:
Debug (android/app/build/outputs/apk/slim/debug/):
app-slim-debug.apk
Release (android/app/build/outputs/apk/slim/release/):
app-slim-release-unsigned.apk
Use :app:assembleFullDebug / :app:assembleFullRelease for the larger full Python bundle (offline repository wheels, bundled docs, Vue sources, etc.).
With -PmeshchatxAbiPackaging=split and more than one ABI in -PmeshchatxAbis, Gradle also emits per-ABI APKs under the same flavor folders, plus a universal split APK when enabled.
Notes:
- Release outputs are unsigned by default unless you configure signing.
- If you only need one build, run for example
:app:assembleSlimDebugor:app:assembleSlimRelease. - Android targets the ABIs listed in
android/app/build.gradle(includingarmeabi-v7awhen enabled). Building wheels forarmeabi-v7aneeds an Android SDK onANDROID_HOME(seeandroid/README.md). - Override ABI selection with
-PmeshchatxAbis=<comma-separated list>orMESHCHATX_ABIS. Override packaging with-PmeshchatxAbiPackaging=universal|splitorMESHCHATX_ABI_PACKAGING. - Chaquopy bundle size:
slimflavor (default) syncs a smallermeshchatx/tree intosrc/slim/python/;fullflavor syncs the complete tree intosrc/full/python/(including offline repository wheels after fetch when needed). Seeandroid/README.md.
Additional docs:
Configuration
MeshChatX supports both CLI args and env vars.
| Argument | Environment Variable | Default | Description |
|---|---|---|---|
--host |
MESHCHAT_HOST |
127.0.0.1 |
Web server bind address |
--port |
MESHCHAT_PORT |
8000 |
Web server port |
--no-https |
MESHCHAT_NO_HTTPS |
false |
Disable HTTPS |
--ssl-cert / --ssl-key |
MESHCHAT_SSL_CERT / MESHCHAT_SSL_KEY |
(none) | PEM certificate and private key paths; both must be set together. Overrides auto-generated certs under the identity ssl/ directory. |
--rns-log-level |
MESHCHAT_RNS_LOG_LEVEL |
(none) | Reticulum (RNS) stack log level: none, critical, error, warning, notice, verbose, debug, extreme, or a numeric level. CLI overrides env when both are set. |
--headless |
MESHCHAT_HEADLESS |
false |
Do not auto-launch browser |
--auth |
MESHCHAT_AUTH |
false |
Enable basic auth |
--storage-dir |
MESHCHAT_STORAGE_DIR |
./storage |
Data directory |
--public-dir |
MESHCHAT_PUBLIC_DIR |
auto/bundled | Frontend files directory (needed for source installs without bundled assets) |
Branches
| Branch | Purpose |
|---|---|
master |
Stable releases. Production-ready code only. |
dev |
Active development. May contain breaking or incomplete changes. |
Development
Common tasks from Taskfile.yml:
task install
task lint:all
task test:all
task build:all
Makefile shortcuts are also available:
| Command | Description |
|---|---|
make install |
Install pnpm and poetry dependencies |
make run |
Run MeshChatX via poetry |
make build |
Build frontend |
make lint |
Run eslint and ruff |
make test |
Run frontend and backend tests |
make clean |
Remove build artifacts and node_modules |
Versioning
Current version in this repo is 4.5.1.
package.jsonis the JavaScript/Electron version source.meshchatx/src/version.pyis synced frompackage.jsonusing:
pnpm run version:sync
For release consistency, keep version fields aligned where required (package.json, pyproject.toml, meshchatx/__init__.py).
Security
Security and integrity details:
SECURITY.mdLEGAL.md- Built-in integrity checks and HTTPS/WSS defaults in app runtime
- CI and release builds on GitHub Actions (
.github/workflows/). Version tags also get SLSA Build Level 3 provenance (*.intoto.jsonlvia slsa-github-generator) and a draft GitHub release with binaries plus provenance for review before publishing. Verify with slsa-verifier (seeSECURITY.md). On Gitea, only.gitea/workflows/github-release-sync.ymlis kept: for tags matchingrelease_*it waits for successful GitHub workflow runs and publishes assets to a GitHub release using theGH_PATandGH_REPOSITORYrepository secrets (seeSECURITY.md).
Adding a Language
Locale discovery is automatic. Add a new file under meshchatx/src/frontend/locales/ (for example xx.json) with the same keys as en.json and a top-level _languageName string for the label shown in the language selector. You can copy en.json and translate every value by hand; machine-assisted generation is optional and never required.
Optional: Argos Translate bootstrap -- If you want a machine-generated first draft from en.json, you can use scripts/argos_translate.py. It handles formatting, color output, and helps protect interpolation variables (like {count}) from accidental edits.
# Install argostranslate if you haven't already
pipx install argostranslate
# Run the translation script
python scripts/argos_translate.py --from en --to xx --input meshchatx/src/frontend/locales/en.json --output meshchatx/src/frontend/locales/xx.json --name "Your Language Name"
After any machine-assisted pass, have an LLM or a human reviewer verify grammar, context, and tone (for example formal vs informal).
Run pnpm test -- tests/frontend/i18n.test.js --run to verify key parity with en.json.
No other code changes are required. The app, language selector, and tests all discover locales from the meshchatx/src/frontend/locales/ directory at build time.
Credits
- Liam Cottle - Original Reticulum MeshChat
- RFnexus - micron parser JavaScript work
- markqvist - Reticulum, LXMF, LXST
License
Project-owned portions are licensed under 0BSD.
Original upstream portions from Reticulum MeshChat remain under MIT.
See LICENSE for full text and notices.