Skip to content

Metro-Olografix/ex_meshtastic_client

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

5 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Meshtastic Client (WIP)

Hex.pm Version Hex.pm Docs

Elixir client for Meshtastic devices. Connects over TCP to send and receive mesh network messages using Protobuf.

Installation

Add to your mix.exs:

def deps do
  [
    {:meshtastic_client, "~> 0.1.0"}
  ]
end

Then run mix deps.get to install.

Quick Start

# Connect to your device
{:ok, conn} = MeshtasticClient.connect(type: :tcp, host: "192.168.1.100")

# Subscribe to incoming messages
MeshtasticClient.subscribe(conn)

# Send a message to the mesh
MeshtasticClient.send_text(conn, "Hello from Elixir!")

# Collect messages
messages = MeshtasticClient.collect_messages(timeout: 5000)
IO.inspect(messages)

See the examples/ directory for more usage patterns.

Note

Protobuf client is generated automatically but not all features are available on the Elixir client

Setup

This library uses Meshtastic's protobuf definitions. You'll need protoc installed to generate the Elixir modules:

# Fedora/RHEL
sudo dnf install protobuf-compiler protobuf-devel

# Ubuntu/Debian
sudo apt-get install protobuf-compiler protobuf-devel

# macOS
brew install protobuf

Install the Elixir protobuf plugin:

mix escript.install hex protobuf 0.14.0

The protobuf files are in priv/protos/. Generate modules using the Mix task:

mix protobuf.gen

To regenerate all modules from scratch:

mix protobuf.gen --clean

Connections

TCP

Most Meshtastic devices expose TCP on port 4403:

{:ok, conn} = MeshtasticClient.connect(
  type: :tcp,
  host: "192.168.1.100",
  port: 4403  # default
)

Serial & BLE

Not implemented yet.

Sending Messages

Text Messages

# Broadcast to all nodes
MeshtasticClient.send_text(conn, "Hello mesh!")

# Send to specific node
MeshtasticClient.send_text(conn, "Direct message", to: 0x12345678, want_ack: true)

# Send on channel 1
MeshtasticClient.send_text(conn, "Channel message", channel: 1)

Position Updates

MeshtasticClient.send_position(conn,
  latitude: 37.7749,
  longitude: -122.4194,
  altitude: 15
)

Receiving Messages

Two approaches: collect or stream.

Collect Messages

Gather messages for a set time:

MeshtasticClient.subscribe(conn)

messages = MeshtasticClient.collect_messages(timeout: 5000, count: 10)
Enum.each(messages, &IO.inspect/1)

Stream Messages

Handle messages as they arrive:

MeshtasticClient.subscribe(conn)

receive do
  {:meshtastic_message, %{payload_variant: {:packet, packet}}} ->
    IO.puts("Got packet: #{inspect(packet)}")
end

Device Info

Request configuration and node details:

# Triggers config response messages
MeshtasticClient.get_config(conn)

# Same as get_config
MeshtasticClient.get_node_info(conn)

These functions send requests; responses arrive as messages you receive via subscription.

Client architecture

  • MeshtasticClient - Public API
  • MeshtasticClient.Connection - TCP connection manager (GenServer)
  • MeshtasticClient.Message - Message encoding/framing
  • Meshtastic.* - Generated protobuf structs (mesh.proto, config.proto, etc.)

Message Types

When you receive messages, check the payload_variant field:

case message.payload_variant do
  {:my_info, info} -> # Device node info
  {:node_info, node} -> # Other node discovered
  {:packet, packet} -> # Mesh packet (text, telemetry, etc.)
  {:config, config} -> # Device config
  {:channel, channel} -> # Channel settings
  _ -> # Other message types
end

References

About

An Elixir package to interact with Meshtastic devices

Topics

Resources

Stars

Watchers

Forks

Languages