Specification: msghandler
Version: 1.2.0
Date: 2026-05-13
Status: Active
Ground Truth: src/msghandler.jl
Specification Format: JSON Schema + AsyncAPI
1. Technical Contract Overview
This document defines the technical contract for msghandler - the cross-platform bi-directional data bridge that enables seamless communication between Julia, JavaScript, Python, Dart, Rust, and MicroPython applications using a message broker as the transport layer.
This specification serves as the single source of truth for:
- Inputs: What data structures are accepted by
smartsend()
- Outputs: What data structures are returned by
smartreceive()
- Data Shapes: Exact field names, types, and constraints
- Error Codes: Standardized error responses for failure scenarios
1.1 Requirements Traceability
| Specification Section |
Requirement ID(s) |
Description |
| Section 2 (Message Envelope) |
FR-012, FR-013, NFR-101, NFR-102 |
Message envelope structure and validation |
| Section 3 (Payload Schema) |
FR-001, FR-002, FR-003, FR-004, NFR-101, NFR-102 |
Payload structure and field definitions |
| Section 4 (Payload Format) |
FR-006, FR-007 |
Tuple format for smartsend() |
| Section 5 (Enumerations) |
FR-003, FR-004, FR-006, NFR-101 |
Enumerations for transport and encoding |
| Section 6 (Transport Protocols) |
FR-003, FR-004, NFR-104, NFR-105 |
Direct and link transport protocols |
| Section 7 (Size Thresholds) |
FR-004, FR-005, NFR-104, NFR-105 |
Size thresholds for transport selection |
| Section 8 (Topic Convention) |
FR-013, FR-014 |
Topic/subject naming patterns |
| Section 9 (Error Handling) |
FR-010, FR-011, NFR-201, NFR-202, NFR-203 |
Error codes and exception handling |
| Section 10 (Serialization Rules) |
FR-001, FR-002, FR-003, FR-012, NFR-101, NFR-102 |
Serialization and encoding rules |
| Section 11 (API Contract) |
FR-001, FR-002, FR-003, FR-004, FR-005, FR-006, FR-007, FR-008, FR-009, FR-010, FR-011, FR-012, FR-013, FR-014 |
Function signatures for all platforms |
| Section 12 (File Server Interface) |
FR-008, FR-009, FR-010 |
Upload and download handler contracts |
| Section 13 (Platform-Specific Constraints) |
FR-005, FR-006, NFR-106, NFR-107 |
Platform-specific feature support |
| Section 14 (Implementation Files) |
FR-001, FR-002, FR-003, FR-004, FR-005, FR-006, FR-007 |
Implementation file mapping |
| Section 15 (Message Flow) |
FR-001, FR-002, FR-003, FR-004, FR-005, FR-006, FR-007, FR-008, FR-009, FR-010, FR-011, FR-012, FR-013, FR-014 |
Mermaid diagrams for send/receive flows |
| Section 16 (Validation Rules) |
FR-001, FR-002, FR-003, FR-004, FR-005, FR-006, FR-007, FR-008, FR-009, FR-010, FR-011, FR-012, FR-013, FR-014 |
Envelope and payload validation rules |
| Section 17 (Test Contracts) |
FR-001, FR-002, FR-003, FR-004, FR-005, FR-006, FR-007, FR-008, FR-009, FR-010, FR-011, FR-012, FR-013, FR-014 |
Unit and integration test scenarios |
| Section 18 (Dependencies) |
FR-001, FR-002, FR-003, FR-004, FR-005, FR-006, FR-007, FR-008, FR-009, FR-010, FR-011, FR-012, FR-013, FR-014 |
Platform-specific dependencies |
| Section 19 (Change Log) |
N/A |
Version history and changes |
2. Message Envelope Schema
Specification Versioning
| Component |
Version |
Notes |
| Specification |
1.0.0 |
Initial release |
| Protocol |
v1 |
Message envelope protocol version |
Message Envelope Schema
Envelope Structure (JSON)
Field Definitions
| Field |
Type |
Required |
Validation |
Description |
Requirement ID |
correlation_id |
string |
Yes |
UUID v4 format |
Track message flow across distributed systems |
FR-011, NFR-401 |
msg_id |
string |
Yes |
UUID v4 format |
Unique identifier for this specific message |
FR-012, NFR-401 |
timestamp |
string |
Yes |
ISO 8601 UTC |
Message publication timestamp |
FR-012, NFR-401 |
send_to |
string |
Yes |
Non-empty string |
Topic/subject to publish the message to |
FR-013 |
msg_purpose |
string |
Yes |
Enum |
Purpose of the message |
FR-013 |
sender_name |
string |
Yes |
Non-empty string |
Name of the sender application |
FR-013 |
sender_id |
string |
Yes |
UUID v4 format |
Unique identifier for the sender |
FR-013 |
receiver_name |
string |
Yes |
Any string |
Name of the receiver (empty = broadcast) |
FR-013 |
receiver_id |
string |
Yes |
Any string |
UUID of the receiver (empty = broadcast) |
FR-013 |
reply_to |
string |
Yes |
Any string |
Topic where receiver should reply |
FR-013 |
reply_to_msg_id |
string |
Yes |
Any string |
Message ID this message is replying to |
FR-013 |
broker_url |
string |
Yes |
Valid URL |
Broker URL for the transport layer |
FR-013 |
metadata |
object |
No |
Any JSON object |
Message-level metadata |
NFR-401 |
payloads |
array |
Yes |
Non-empty array |
List of payload objects |
FR-012, FR-013 |
Payload Schema
Payload Structure (JSON)
Payload Field Definitions
| Field |
Type |
Required |
Validation |
Description |
Requirement ID |
id |
string |
Yes |
UUID v4 format |
Unique identifier for this payload |
FR-012 |
dataname |
string |
Yes |
Non-empty string |
Name of the payload (e.g., login_image, user_data) |
FR-001, FR-002, FR-003 |
payload_type |
string |
Yes |
Enum |
Type of payload (see payload_type enum) |
FR-001, FR-002, FR-003, FR-006 |
transport |
string |
Yes |
Enum |
Transport method: direct or link |
FR-003, FR-004, NFR-104, NFR-105 |
encoding |
string |
Yes |
Enum |
Encoding method (see encoding enum) |
FR-001, FR-002, FR-003, FR-012 |
size |
integer |
Yes |
Positive integer |
Size of the payload in bytes |
FR-003, FR-004, NFR-104, NFR-105 |
data |
string or URL |
Yes |
Base64 string or URL |
Payload data (base64 for direct, URL for link) |
FR-003, FR-004, FR-008, FR-009, FR-010 |
metadata |
object |
No |
Any JSON object |
Payload-level metadata |
NFR-401 |
Payload Format
Tuple Format for smartsend()
The smartsend() function accepts data as an array of tuples with the format:
| Position |
Type |
Description |
Example |
| 1 |
string |
Data name - identifier for the payload |
"msg", "login_image", "user_data" |
| 2 |
any |
Actual data - content to be serialized |
"Hello", {"key": "value"}, DataFrame(...) |
| 3 |
string |
Data type - must be in payload_type enum |
"text", "dictionary", "arrowtable" |
Single Payload Example
Multiple Payloads Example
Data Type Mapping
| Platform |
Input Type |
Data Type String |
| All |
String |
"text" |
| All |
Dict/Object |
"dictionary" |
| Desktop |
DataFrame |
"arrowtable" or "jsontable" |
| Browser |
Array of objects |
"jsontable" (only table type) |
| All |
Array of objects |
"jsontable" |
| All |
Uint8Array/Buffer/bytes |
"binary" |
| Desktop |
Arrow.Table |
"arrowtable" |
| All |
Image/Audio/Video binary |
"image", "audio", "video" |
Enumerations
msg_purpose Enum
| Value |
Description |
ACK |
Acknowledgment of successful message processing |
NACK |
Negative acknowledgment of message processing failure |
updateStatus |
Status update message |
shutdown |
Graceful shutdown request |
chat |
Chat/message payload |
command |
Command payload |
event |
Event payload |
payload_type Enum
| Value |
Description |
Supported Platforms |
Encoding Options |
text |
Plain text string |
All |
base64 |
dictionary |
JSON object/dictionary |
All |
base64, json |
arrowtable |
Apache Arrow IPC table |
Desktop (Julia/Python/Node.js/Dart) |
base64, arrow-ipc |
jsontable |
JSON array of objects |
All (including Browser/Dart Web) |
base64, json |
image |
Binary image data |
All |
base64 |
audio |
Binary audio data |
All |
base64 |
video |
Binary video data |
All |
base64 |
binary |
Generic binary data |
All |
base64 |
transport Enum
| Value |
Description |
Data Format |
Use Case |
direct |
Payload sent directly via the transport layer |
Base64-encoded string |
Payloads < size_threshold |
link |
Payload uploaded to file server |
HTTP URL |
Payloads ≥ size_threshold |
encoding Enum
| Value |
Description |
Payload Types |
none |
No additional encoding |
Link transport URLs |
base64 |
Base64 encoding |
Text, binary, image, audio, video |
json |
JSON encoding |
Dictionary, jsontable |
arrow-ipc |
Apache Arrow IPC format |
Arrowtable |
Transport Protocols
Direct Transport Protocol
When transport = "direct", the data field contains a Base64-encoded string of the serialized payload.
Flow:
- Serialize payload according to
payload_type
- Encode serialized bytes as Base64
- Include Base64 string in
data field
Example:
Link Transport Protocol
When transport = "link", the data field contains a URL pointing to the uploaded payload.
Flow:
- Serialize payload according to
payload_type
- Upload to HTTP file server (e.g., Plik)
- Include returned URL in
data field
Example:
Size Thresholds
Desktop Platforms (Julia/JS/Python)
| Platform |
Size Threshold |
Notes |
| Desktop |
500,000 bytes (0.5MB) |
Default threshold |
MicroPython Platform
| Platform |
Size Threshold |
Maximum Payload |
Notes |
| MicroPython |
100,000 bytes (100KB) |
50,000 bytes |
Hard limit due to memory constraints |
Topic Convention
Subject Naming Pattern
Examples:
/agent/wine/api/v1/prompt - AI agent prompt endpoint
/chat/user/v1/message - User chat message
/system/worker/v1/status - Worker status update
Subject Wildcards
| Wildcard |
Description |
Example |
* |
Single-level wildcard |
/chat/user/v1/* matches /chat/user/v1/message |
> |
Multi-level wildcard |
/chat/user/v1/> matches all /chat/user/v1/* subjects |
Error Handling
Error Response Format
Error Codes
| Code |
HTTP Status |
Description |
Recovery |
Requirement ID |
INVALID_ENVELOPE |
400 |
Message envelope validation failed |
Fix envelope structure |
FR-012, FR-013, FR-014 |
INVALID_PAYLOAD_TYPE |
400 |
Unsupported payload type |
Use supported payload_type |
FR-001, FR-002, FR-003, FR-006 |
INVALID_TRANSPORT |
400 |
Unsupported transport type |
Use direct or link |
FR-003, FR-004, FR-006 |
UPLOAD_FAILED |
500 |
File server upload failed |
Retry or use direct transport |
FR-008, FR-009 |
DOWNLOAD_FAILED |
503 |
File server download failed |
Retry with exponential backoff |
FR-010, FR-011, NFR-201, NFR-202 |
TRANSPORT_CONNECTION_FAILED |
503 |
Transport connection failed |
Check broker/server availability |
FR-013, FR-014, NFR-201, NFR-203 |
DESERIALIZATION_ERROR |
500 |
Payload deserialization failed |
Check payload_type matches data |
FR-001, FR-002, FR-003, FR-012 |
SIZE_EXCEEDED |
413 |
Payload exceeds maximum size |
Split payload or use link transport |
FR-003, FR-004, FR-005, NFR-104, NFR-105 |
Exception Handling
| Scenario |
Handler |
Retry Policy |
Requirement ID |
| File server unavailable |
Retry up to 5 times |
Exponential backoff (100ms → 5000ms) |
FR-010, NFR-202 |
| Transport publish failure |
Handled by caller |
Caller's retry logic |
FR-013, FR-014, NFR-201, NFR-203 |
| Deserialization error |
Log correlation ID and throw |
No retry (data corruption) |
FR-001, FR-002, FR-003, FR-012, NFR-401 |
| Memory overflow (MicroPython) |
Reject payloads >50KB |
No retry (client-side check) |
FR-005, NFR-106 |
Serialization Rules
Text Serialization
| Platform |
Input Type |
Serialization |
Encoding |
| All |
String |
UTF-8 bytes |
Base64 |
Dictionary Serialization
| Platform |
Input Type |
Serialization |
Encoding |
| All |
Object/Dict |
JSON string |
Base64 or direct JSON |
Arrow Table Serialization
| Platform |
Input Type |
Serialization |
Encoding |
| Desktop |
DataFrame |
Arrow IPC stream |
Base64 or arrow-ipc |
| Desktop |
Arrow.Table |
Arrow IPC stream |
Base64 or arrow-ipc |
| MicroPython |
❌ |
Not supported |
N/A |
JSON Table Serialization
| Platform |
Input Type |
Serialization |
Encoding |
| All |
Vector{Dict}/Array<Object> |
JSON array |
Base64 or direct JSON |
| Desktop |
pandas.DataFrame |
JSON array |
Base64 or direct JSON |
Binary Serialization
| Platform |
Input Type |
Serialization |
Encoding |
| All |
Uint8Array/Buffer/bytes |
Raw bytes |
Base64 |
API Contract
smartsend Function Signature
Julia
Note: Publishing via the transport layer is the caller's responsibility. Returns (env::msg_envelope_v1, env_json_str::String).
Python
Note: Publishing via the transport layer is the caller's responsibility.
JavaScript (Node.js)
Note: Publishing via the transport layer is the caller's responsibility.
JavaScript (Browser)
Note: Publishing via the transport layer is the caller's responsibility.
MicroPython
Note: Publishing via the transport layer is the caller's responsibility.
Dart (Desktop/Flutter)
Rust
pub async fn smartsend(
subject: &str,
data: &[(String, Payload, String)],
options: &SmartsendOptions,
) -> Result<(MsgEnvelopeV1, String), msghandlerError>
// SmartsendOptions struct
pub struct SmartsendOptions {
pub broker_url: String,
pub fileserver_url: String,
pub fileserver_upload_handler: Option<UploadHandler>,
pub size_threshold: usize,
pub correlation_id: String,
pub msg_purpose: String,
pub sender_name: String,
pub receiver_name: String,
pub receiver_id: String,
pub reply_to: String,
pub reply_to_msg_id: String,
pub msg_id: String,
pub sender_id: String,
}
// Payload enum for type-safe data handling
#[derive(Serialize, Deserialize, Clone)]
pub enum Payload {
Text(String),
Dictionary(serde_json::Value),
ArrowTable(Vec<u8>),
JsonTable(serde_json::Value),
Image(Vec<u8>),
Audio(Vec<u8>),
Video(Vec<u8>),
Binary(Vec<u8>),
}
// MsgEnvelopeV1 struct (serde-serializable)
#[derive(Serialize, Deserialize, Clone)]
pub struct MsgEnvelopeV1 {
pub correlation_id: String,
pub msg_id: String,
pub timestamp: String,
pub send_to: String,
pub msg_purpose: String,
pub sender_name: String,
pub sender_id: String,
pub receiver_name: String,
pub receiver_id: String,
pub reply_to: String,
pub reply_to_msg_id: String,
pub broker_url: String,
pub metadata: serde_json::Value,
pub payloads: Vec<MsgPayloadV1>,
}
Note: Publishing via the transport layer is the caller's responsibility. Returns Result<(MsgEnvelopeV1, String), msghandlerError>. Uses serde for JSON serialization.
smartreceive Function Signature
Julia
Note: Input is the JSON string payload from the transport subscription, not the transport message object directly.
Python
Note: Input is the JSON string payload from the transport message.
JavaScript (Node.js)
JavaScript (Browser)
Note: Input is the JSON string payload from the transport message.
MicroPython
Note: Input is the JSON string payload from the transport message.
Dart (Desktop/Flutter)
Dart Web
Rust
Note: Input is the JSON string payload from the transport message. Returns Result<MsgEnvelopeV1, msghandlerError>.
File Server Interface
Upload Handler Contract
Function Signature:
Return Format:
Required Keys:
| Key |
Type |
Description |
status |
integer |
HTTP response status code |
uploadid |
string |
Upload session identifier |
fileid |
string |
File identifier within session |
url |
string |
Full download URL |
Download Handler Contract
Function Signature:
Retry Policy:
- Initial delay:
base_delay milliseconds
- Maximum delay:
max_delay milliseconds
- Multiplier: 2x per retry
- Maximum retries:
max_retries
Platform-Specific Constraints
Desktop (Julia/Python/Node.js/Dart)
| Feature |
Status |
Notes |
| Arrow IPC |
✅ Supported |
Requires Arrow.jl/pyarrow/dart-arrow |
| JSON table |
✅ Supported |
Human-readable format |
| File server upload |
✅ Supported |
HTTP/HTTPS |
| File server download |
✅ Supported |
HTTP/HTTPS |
| Size threshold |
500KB |
Configurable |
Browser (JavaScript)
| Feature |
Status |
Notes |
| Arrow IPC |
❌ Not supported |
Apache Arrow not browser-compatible |
| JSON table |
✅ Supported |
Only table type available in browser |
| File server upload |
✅ Supported |
HTTP/HTTPS |
| File server download |
✅ Supported |
HTTP/HTTPS |
| Size threshold |
500KB |
Configurable |
Dart Desktop (Dart SDK)
| Feature |
Status |
Notes |
| Arrow IPC |
✅ Supported |
Requires dart-arrow package |
| JSON table |
✅ Supported |
Human-readable format |
| File server upload |
✅ Supported |
HTTP/HTTPS |
| File server download |
✅ Supported |
HTTP/HTTPS |
| Size threshold |
500KB |
Configurable |
Dart Flutter (Dart SDK)
| Feature |
Status |
Notes |
| Arrow IPC |
✅ Supported |
Requires dart-arrow package |
| JSON table |
✅ Supported |
Human-readable format |
| File server upload |
✅ Supported |
HTTP/HTTPS |
| File server download |
✅ Supported |
HTTP/HTTPS |
| Size threshold |
500KB |
Configurable |
Dart Web (Dart SDK)
| Feature |
Status |
Notes |
| Arrow IPC |
❌ Not supported |
Apache Arrow not browser-compatible |
| JSON table |
✅ Supported |
Only table type available in browser |
| File server upload |
✅ Supported |
HTTP/HTTPS |
| File server download |
✅ Supported |
HTTP/HTTPS |
| Size threshold |
500KB |
Configurable |
Rust
| Feature |
Status |
Notes |
| Arrow IPC |
✅ Supported |
Requires arrow2 crate |
| JSON table |
✅ Supported |
Uses serde_json |
| File server upload |
✅ Supported |
HTTP/HTTPS via reqwest |
| File server download |
✅ Supported |
HTTP/HTTPS via reqwest with retry |
| Size threshold |
500KB |
Configurable |
| Async runtime |
✅ Supported |
Uses tokio for async I/O |
| Type safety |
✅ Supported |
Compile-time type checking via Rust enums |
MicroPython
| Feature |
Status |
Notes |
| Arrow IPC |
❌ Not supported |
Memory constraints |
| JSON table |
⚠️ Limited |
Only direct transport |
| File server upload |
❌ Not implemented |
Placeholder only |
| File server download |
❌ Not implemented |
Placeholder only |
| Size threshold |
100KB |
Hard limit enforced |
| Max payload |
50KB |
Hard limit enforced |
Implementation Files
Browser Implementation Notes
The browser implementation (src/msghandler_csr.js) has the following constraints:
| Constraint |
Reason |
Workaround |
| No Apache Arrow IPC |
Browser-incompatible dependency |
Use jsontable for tabular data |
| WebSocket only |
Browser cannot use TCP directly |
Use ws:// or wss:// broker URLs |
| Fetch API for HTTP |
Browser fetch() API only |
Compatible with Plik and other HTTP servers |
Payload Type Availability by Platform
| Payload Type |
Julia |
Node.js |
Browser |
Python |
Dart |
Rust |
MicroPython |
text |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
dictionary |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
arrowtable |
✅ |
✅ |
❌ |
✅ |
✅ |
✅ |
❌ |
jsontable |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
⚠️ |
image |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
audio |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
video |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
binary |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
✅ |
Message Flow
Sending Flow
Receiving Flow
Validation Rules
Envelope Validation
| Rule |
Condition |
Error Code |
Requirement ID |
| Required fields present |
correlation_id, msg_id, timestamp, send_to, payloads |
INVALID_ENVELOPE |
FR-012, FR-013 |
| Valid UUID format |
correlation_id, msg_id, sender_id, receiver_id |
INVALID_ENVELOPE |
FR-011, FR-012, NFR-401 |
| Valid timestamp format |
ISO 8601 UTC |
INVALID_ENVELOPE |
FR-012, NFR-401 |
| Non-empty payloads array |
length(payloads) > 0 |
INVALID_ENVELOPE |
FR-012, FR-013 |
Payload Validation
| Rule |
Condition |
Error Code |
Requirement ID |
| Valid payload_type |
Must be in payload_type enum |
INVALID_PAYLOAD_TYPE |
FR-001, FR-002, FR-003, FR-006 |
| Valid transport |
Must be direct or link |
INVALID_TRANSPORT |
FR-003, FR-004, FR-006 |
| Valid encoding |
Must match payload_type and transport |
INVALID_TRANSPORT |
FR-001, FR-002, FR-003, FR-012 |
| Positive size |
size > 0 |
INVALID_PAYLOAD |
FR-003, FR-004, NFR-104, NFR-105 |
| Valid Base64 for direct |
data matches Base64 pattern |
DESERIALIZATION_ERROR |
FR-001, FR-002, FR-003, FR-012 |
| Valid URL for link |
data matches HTTP(S) URL pattern |
DOWNLOAD_FAILED |
FR-008, FR-009, FR-010 |
Test Contracts
Unit Test Validation
| Test |
Input |
Expected Output |
Notes |
Requirement ID |
| Text round-trip |
("msg", "Hello", "text") |
("msg", "Hello", "text") |
String serialization |
FR-001, FR-012, NFR-101, NFR-102 |
| Dictionary round-trip |
("data", {"key": "value"}, "dictionary") |
("data", {"key": "value"}, "dictionary") |
JSON object round-trip |
FR-002, FR-012, NFR-101, NFR-102 |
| Arrow table round-trip |
("table", arrow_table_data, "arrowtable") |
("table", arrow_table_data, "arrowtable") |
Arrow IPC round-trip |
FR-002, FR-012, NFR-101, NFR-102 |
| JSON table round-trip |
("table", [{"a":1},{"b":2}], "jsontable") |
("table", [{"a":1},{"b":2}], "jsontable") |
JSON array of objects |
FR-001, FR-002, FR-006, FR-012 |
| Mixed payloads |
[("msg", "Hello", "text"), ("imgname", bytes, "binary")] |
[("msg", "Hello", "text"), ("imgname", bytes, "binary")] |
Multiple payload types |
FR-006, FR-007 |
| Large payload |
("data", rand(10_000_000), "arrowtable") |
("data", URL, "arrowtable") with link transport |
File server upload |
FR-003, FR-004, FR-008, FR-009, NFR-104, NFR-105 |
Platform-Specific Notes:
- Julia: Use
Dict, Vector{Dict}, or convert DataFrame to dictionary for testing
- Python: Use
dict, list[dict], or convert pandas.DataFrame to dictionary for testing
- JavaScript: Use plain objects
{} and arrays []
- MicroPython: Use plain
dict and list (limited to JSON table and text types)
Integration Test Scenarios
| Scenario |
Platforms |
Payloads |
Size Mix |
Transport |
Expected Result |
Requirement ID |
| Single text (small) |
All |
text |
Small |
direct |
Round-trip successful |
FR-001, FR-012, NFR-101, NFR-102 |
| Single dictionary (small) |
All |
dictionary |
Small |
direct |
Round-trip successful |
FR-002, FR-012, NFR-101, NFR-102 |
| Single arrow table (small) |
Julia/JS/Python |
arrowtable |
Small |
direct |
Arrow IPC round-trip |
FR-002, FR-012, NFR-101, NFR-102 |
| Single JSON table (small) |
All |
jsontable |
Small |
direct |
Dictionary array round-trip |
FR-001, FR-002, FR-006, FR-012 |
| Single image (small) |
All |
image |
Small |
direct |
Binary round-trip |
FR-001, FR-006, FR-012 |
| Single audio (small) |
All |
audio |
Small |
direct |
Binary round-trip |
FR-001, FR-006, FR-012 |
| Single video (small) |
All |
video |
Small |
direct |
Binary round-trip |
FR-001, FR-006, FR-012 |
| Single binary (small) |
All |
binary |
Small |
direct |
Binary round-trip |
FR-001, FR-006, FR-012 |
| Single text (large) |
All |
text |
Large |
link |
File server upload/download |
FR-003, FR-004, FR-008, FR-009, NFR-104, NFR-105 |
| Single JSON table (large) |
All |
jsontable |
Large |
link |
File server upload/download |
FR-003, FR-004, FR-008, FR-009, NFR-104, NFR-105 |
| Single image (large) |
All |
image |
Large |
link |
File server upload/download |
FR-003, FR-004, FR-008, FR-009, NFR-104, NFR-105 |
| Ultimate Test |
Julia/JS/Python |
text (small) + dictionary (small) + arrowtable (small) + jsontable (small) + image (small) + audio (small) + video (small) + binary (small) + text (large) + dictionary (large) + arrowtable (large) + jsontable (large) + image (large) |
Mixed |
direct/link |
All payloads preserved with correct transport |
FR-001, FR-002, FR-003, FR-004, FR-005, FR-006, FR-007, FR-008, FR-009, FR-010, FR-011, FR-012, FR-013, FR-014 |
| Ultimate Test |
MicroPython |
text (small) + dictionary (small) + text (large) + dictionary (large) |
Mixed |
direct |
Limited to text/dictionary with direct transport only |
FR-005, FR-006, FR-012 |
| Cross-platform JSON table |
All |
jsontable |
Small |
direct |
Dictionary array round-trip |
FR-001, FR-002, FR-006, FR-012 |
| MicroPython ↔ Desktop |
MicroPython ↔ Desktop |
text/dictionary |
Small |
direct |
Limited payload types |
FR-005, FR-006, FR-012 |
| Desktop ↔ Desktop (all combos) |
Julia↔JS↔Python |
All types |
Small/Large |
direct/link |
Full compatibility |
FR-001, FR-002, FR-003, FR-004, FR-005, FR-006, FR-007, FR-012, FR-013, FR-014 |
Dependencies
Required Dependencies by Platform
| Platform |
Package |
Version |
Purpose |
| Julia |
JSON.jl |
Latest |
JSON serialization |
| Julia |
Arrow.jl |
Latest |
Arrow IPC support |
| Julia |
HTTP.jl |
Latest |
HTTP file server |
| Julia |
UUIDs.jl |
Latest |
UUID generation |
| Node.js |
node-fetch |
Latest |
HTTP file server |
| Browser |
- |
- |
Transport-agnostic (caller provides) |
| Python |
aiohttp |
Latest |
HTTP file server |
| Python |
pyarrow |
Latest |
Arrow IPC support |
| Dart |
http |
Latest |
HTTP file server |
| Dart |
uuid |
Latest |
UUID generation |
| Dart |
dart-arrow |
Latest |
Arrow IPC support (Desktop/Flutter) |
| Rust |
serde |
Latest |
JSON serialization |
| Rust |
serde_json |
Latest |
JSON handling |
| Rust |
tokio |
Latest |
Async runtime |
| Rust |
reqwest |
Latest |
HTTP file server |
| Rust |
uuid |
Latest |
UUID generation |
| Rust |
arrow2 |
Latest |
Arrow IPC support |
| MicroPython |
builtin |
N/A |
Limited implementation |
Optional Dependencies
| Platform |
Package |
Purpose |
| Julia |
DataFrames.jl |
DataFrame support |
| Python |
pandas |
DataFrame support |
Change Log
| Date |
Version |
Changes |
| 2026-05-15 |
1.3.0 |
Made transport layer agnostic |
| - |
- |
Removed all NATS-specific dependencies (NATS.jl, nats, nats-py, nats.ws) |
| - |
- |
Updated docs to reference generic message broker/transport |
| - |
- |
broker_url is now metadata only, not used for active connections |
| 2026-03-15 |
1.1.0 |
Browser connection management |
| - |
- |
Added NATSClient class with keepAlive support |
| - |
- |
Added NATSConnectionPool for connection reuse |
| - |
- |
Added publishMessage function with closeConnection option |
| - |
- |
Added nats.ws to browser dependencies |
| 2026-03-13 |
1.0.0 |
Initial specification |
| - |
- |
Message envelope schema defined |
| - |
- |
Payload schema with transport modes |
| - |
- |
Enumerations for payload_type, transport, encoding |
| - |
- |
Size thresholds for desktop/MicroPython |
| - |
- |
Error codes and validation rules |
| - |
- |
API contracts for all platforms |
References
20.1 Documentation Artifacts
20.2 Implementation Files
| File |
Platform |
Features |
Requirements Traceability |
src/msghandler.jl |
Julia |
Full feature set, Arrow IPC, multiple dispatch |
FR-001 through FR-014, NFR-101 through NFR-405 |
src/msghandler_ssr.js |
Node.js |
Arrow IPC, async/await |
FR-001 through FR-014, NFR-101 through NFR-405 |
src/msghandler_csr.js |
Browser |
JSON table only |
FR-001 through FR-014, NFR-101 through NFR-405 |
src/msghandler.py |
Python |
Arrow IPC, async/await |
FR-001 through FR-014, NFR-101 through NFR-405 |
src/msghandler.dart |
Dart |
Full feature set, Arrow IPC, async/await |
FR-001 through FR-014, NFR-101 through NFR-405 |
src/msghandler.rs |
Rust |
Full feature set, Arrow IPC, async/await, type-safe |
FR-001 through FR-014, NFR-101 through NFR-405 |
src/msghandler_mpy.py |
MicroPython |
Limited to direct transport |
FR-005, FR-006, FR-012 |
20.3 External Dependencies
| Platform |
Package |
Version |
Purpose |
Requirements Traceability |
| Julia |
JSON.jl |
Latest |
JSON serialization |
FR-012, NFR-101, NFR-102 |
| Julia |
Arrow.jl |
Latest |
Arrow IPC support |
FR-002, FR-012 |
| Julia |
HTTP.jl |
Latest |
HTTP file server |
FR-008, FR-009 |
| Julia |
UUIDs.jl |
Latest |
UUID generation |
FR-011, NFR-401 |
| Node.js |
node-fetch |
Latest |
HTTP file server |
FR-008, FR-009 |
| Browser |
- |
- |
Transport-agnostic (caller provides) |
FR-013, FR-014 |
| Python |
aiohttp |
Latest |
HTTP file server |
FR-008, FR-009 |
| Python |
pyarrow |
Latest |
Arrow IPC support |
FR-002, FR-012 |
| Dart |
http |
Latest |
HTTP file server |
FR-008, FR-009 |
| Dart |
uuid |
Latest |
UUID generation |
FR-011, NFR-401 |
| Dart |
dart-arrow |
Latest |
Arrow IPC support |
FR-002, FR-012 |
| Rust |
serde |
Latest |
JSON serialization |
FR-012, NFR-101, NFR-102 |
| Rust |
serde_json |
Latest |
JSON handling |
FR-012, NFR-101, NFR-102 |
| Rust |
tokio |
Latest |
Async runtime |
FR-013, FR-014 |
| Rust |
reqwest |
Latest |
HTTP file server |
FR-008, FR-009 |
| Rust |
uuid |
Latest |
UUID generation |
FR-011, NFR-401 |
| Rust |
arrow2 |
Latest |
Arrow IPC support |
FR-002, FR-012 |
| MicroPython |
builtin |
N/A |
Limited implementation |
FR-005, FR-006 |
21. Change Log
| Date |
Version |
Changes |
Requirement ID(s) |
| 2026-05-15 |
1.3.0 |
Made transport layer agnostic |
All |
| - |
- |
Removed NATS-specific dependencies and references from all docs |
All |
| - |
- |
Updated all NATS references to generic "transport layer"/"message broker" |
All |
| - |
- |
Removed NATS client packages from dependencies tables |
All |
| 2026-05-13 |
1.2.0 |
Aligned with ground truth implementation (src/msghandler.jl) |
All |
| - |
- |
Updated smartsend signatures: removed is_publish, nats_connection; added sender_name |
FR-001 through FR-014 |
| - |
- |
Updated smartreceive signatures: takes msg_json_str::String instead of msg |
FR-001 through FR-014 |
| - |
- |
Removed publishMessage function and NATSClient/NATSConnectionPool classes from browser section |
FR-013, FR-014 |
| - |
- |
Added plik_oneshot_upload(filepath) overload to file server interface |
FR-008, FR-009 |
| - |
- |
Fixed SIZE_THRESHOLD default to 500,000 bytes |
FR-003, FR-004 |
| 2026-03-23 |
1.1.0 |
Updated to ASG Framework specification guidelines |
All |
| 2026-03-15 |
1.1.0 |
Browser connection management |
FR-001 through FR-014 |
| 2026-03-13 |
1.0.0 |
Initial specification |
FR-001 through FR-014, NFR-101 through NFR-405 |
Appendix
A. Complete JSON Schema
{
"$schema": "http://json-schema.org/draft-07/schema#",
"title": "msghandler Envelope",
"type": "object",
"properties": {
"correlation_id": {
"type": "string",
"pattern": "^[0-9A-F]{8}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{12}$",
"description": "UUID v4 format for tracking message flow"
},
"msg_id": {
"type": "string",
"pattern": "^[0-9A-F]{8}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{12}$",
"description": "Unique message identifier"
},
"timestamp": {
"type": "string",
"pattern": "^\\d{4}-\\d{2}-\\d{2}T\\d{2}:\\d{2}:\\d{2}\\.\\d{3}Z$",
"description": "ISO 8601 UTC timestamp"
},
"send_to": {
"type": "string",
"minLength": 1,
"description": "Topic/subject to publish to"
},
"msg_purpose": {
"type": "string",
"enum": ["ACK", "NACK", "updateStatus", "shutdown", "chat", "command", "event"],
"description": "Purpose of the message"
},
"sender_name": {
"type": "string",
"minLength": 1,
"description": "Sender application name"
},
"sender_id": {
"type": "string",
"pattern": "^[0-9A-F]{8}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{12}$",
"description": "Sender UUID"
},
"receiver_name": {
"type": "string",
"description": "Receiver name (empty = broadcast)"
},
"receiver_id": {
"type": "string",
"pattern": "^[0-9A-F]{8}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{12}$|^$",
"description": "Receiver UUID (empty = broadcast)"
},
"reply_to": {
"type": "string",
"description": "Topic for reply messages"
},
"reply_to_msg_id": {
"type": "string",
"description": "Message ID being replied to"
},
"broker_url": {
"type": "string",
"description": "Broker URL for the transport layer"
},
"metadata": {
"type": "object",
"description": "Message-level metadata"
},
"payloads": {
"type": "array",
"minItems": 1,
"items": {
"$ref": "#/definitions/Payload"
}
}
},
"required": ["correlation_id", "msg_id", "timestamp", "send_to", "msg_purpose", "sender_name", "sender_id", "receiver_name", "receiver_id", "reply_to", "reply_to_msg_id", "broker_url", "payloads"],
"definitions": {
"Payload": {
"type": "object",
"properties": {
"id": {
"type": "string",
"pattern": "^[0-9A-F]{8}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{4}-[0-9A-F]{12}$"
},
"dataname": {
"type": "string",
"minLength": 1
},
"payload_type": {
"type": "string",
"enum": ["text", "dictionary", "arrowtable", "jsontable", "image", "audio", "video", "binary"]
},
"transport": {
"type": "string",
"enum": ["direct", "link"]
},
"encoding": {
"type": "string",
"enum": ["none", "base64", "json", "arrow-ipc"]
},
"size": {
"type": "integer",
"minimum": 1
},
"data": {
"anyOf": [
{
"type": "string",
"pattern": "^(https?://[^\\s]+)$"
},
{
"type": "string",
"pattern": "^[A-Za-z0-9+/]+=*$"
}
]
},
"metadata": {
"type": "object"
}
},
"required": ["id", "dataname", "payload_type", "transport", "encoding", "size", "data"]
}
}
}
B. AsyncAPI Specification
This specification is versioned and maintained in git alongside the codebase. All implementations must adhere to this specification.