Lane Lite · Phone Node Contributor spec Live on devnet

Solinkify DePIN · Android contribution

Build the Lane Lite phone node.

A phone becomes a relay node: connect, forward signed transactions, earn USDC. Here is the exact protocol and a path from MVP to a live devnet test.

01

What a phone node does

A Lite node is a pure transport relay. It opens an outbound WebSocket to the coordinator, receives a Solana transaction that is already signed, submits it to an RPC, and reports back the signature. The node never builds or changes a transaction (ADR-006), so it holds no funds and carries almost no trust: the worst a coordinator can do is withhold a job.

Outbound-only is deliberate. Phones sit behind carrier NAT and have no public IP, so the node dials out to the coordinator rather than the other way around.

How the node earns

02

Prerequisites

Before a node can go online, its wallet must be a registered, active Lite node.

Devnet parameters

Coordinator WSwss://api.solinkify.com/coordinator/ws
Status (GET)https://api.solinkify.com/coordinator/status
Solana RPChttps://api.devnet.solana.com
Program IDA8qSJCS2uxxnEMdCcpjX2L8hUUMydoeCi5xq5qvzS22B
$SINKY mintEAMRKocV7wTrj2S7CwYQVAbBqB4xa51TV1Akdp9FKa8R
Auth domainsolinkify-lite-v1:
Lite stake25 SINKY · on-chain tier byte = 3
03

The WebSocket protocol

This is the contract, one JSON object per text frame. It is identical to the reference Node.js runner already relaying on devnet, so the Android app can port it 1:1.

  1. server → sends a one-time challenge with a random nonce.
  2. client → ed25519-signs "solinkify-lite-v1:" + nonce and returns auth with the wallet pubkey and base58 signature.
  3. server → checks the signature and the on-chain node, then sends ready (or denied with a reason).
  4. server → pushes a job: a job_id and a base64 already-signed transaction.
  5. client → submits the tx to the RPC, then replies result with the signature (or error with a message).
// 1. server → client
{"type":"challenge", "nonce":"<uuid>"}

// 2. client → server   (sig = base58 of ed25519 over the UTF-8 bytes below)
{"type":"auth", "wallet":"<base58 pubkey>",
 "signature":"<base58 ed25519( 'solinkify-lite-v1:' + nonce )>"}

// 3. server → client
{"type":"ready"}
{"type":"denied", "reason":"wallet is not an active Lite node (register 25 SINKY first)"}

// 4. server → client
{"type":"job", "job_id":"<id>", "tx":"<base64 signed tx>"}

// 5. client → server
{"type":"result", "job_id":"<id>", "signature":"<sig>"}
{"type":"error",  "job_id":"<id>", "message":"<err>"}
Submitting a job is cheap. The tx is already signed, so the node just calls Solana RPC sendTransaction with encoding base64 and returns the signature. That is a plain JSON-RPC POST, no full Solana SDK is needed for the runner core. Also reply to WebSocket ping with pong.
04

Timeouts & session rules

These match the coordinator, keep them exact.

05

What the app must implement

06

Android-specific notes

Most of the runner is light. The two real challenges are Android platform behavior, not the protocol:

Suggested stack: Kotlin + OkHttp (WebSocket) + an ed25519 library, with a foreground service. The Solana Mobile SDK / a Kotlin Solana RPC client helps if you later add in-app registration.
07

Milestones: MVP to devnet test

A build path in four phases. Phase 3 is the proof: a real payment relayed by the phone, verifiable on-chain. (Ticks are a reading aid and do not save.)

P0

Setup & access

Prep
P1

Core runner

MVP
P2

Android runtime

Hardening
P3

Devnet validation

Proof
P4

Next, post-MVP

Optional