Script Connector
Overview
Section titled “Overview”The Script connector executes a Lua script against every incoming payload, returning a new payload as a Lua table. The script runs in a hardened sandbox that blocks file I/O, process control, dynamic code loading, and debug introspection.
Connector Type: MeddleScript
Configuration
Section titled “Configuration”{ "type": "MeddleScript", "config": { "runtime": "lua", "timeout": 100, "script": "payload.temperature_f = payload.temperature_c * 9 / 5 + 32\nreturn payload" }}The payload is bound to the global payload table. The script must return either a table (becomes the new payload) or nil (the input payload is forwarded unchanged).
Configuration Parameters
Section titled “Configuration Parameters”- runtime (required): Only
luais supported - script (required): Lua source code, compiled once at startup
- timeout: Per-payload execution timeout in milliseconds (
0or omitted disables the timeout)
Sandbox
Section titled “Sandbox”The Lua sandbox permits a curated set of standard libraries and explicitly denies the rest.
Allowed libraries:
base(subset — see denied functions below)tablestringmathcoroutine
Denied top-level functions (calling them raises a forbidden-access error):
dofile,loadfile,load,loadstringrequire,modulegetfenv,setfenvcollectgarbage,newproxy,_printregsprint
Denied libraries (any access — read or write — raises a forbidden-access error):
osiodebugpackagechannel
The sandbox metatable is locked, so user scripts cannot introspect or replace it.
Type Mapping
Section titled “Type Mapping”Go-to-Lua and Lua-to-Go conversions are applied automatically:
| Go type | Lua type |
|---|---|
string | string |
float64 / float32 / int* | number |
bool | boolean |
map[string]any | table |
nil | nil |
| (other) | string (fallback via fmt.Sprintf) |
The returned Lua table is converted back into a DataPayload (map[string]any). Numbers come back as float64, regardless of how they were used in Lua.
Use Cases
Section titled “Use Cases”- Custom field derivation that goes beyond Transform’s expression types
- Conditional payload rewriting with arbitrary control flow
- Unit conversion, string formatting, or simple math chains
- Lightweight enrichment without spinning up a separate service
Example: Derived Fields
Section titled “Example: Derived Fields”{ "type": "MeddleScript", "config": { "runtime": "lua", "timeout": 200, "script": "payload.temperature_f = payload.temperature_c * 9 / 5 + 32\npayload.is_hot = payload.temperature_c > 30\nreturn payload" }}Adds a Fahrenheit reading and a boolean flag to every payload.
Example: Conditional Drop
Section titled “Example: Conditional Drop”{ "type": "MeddleScript", "config": { "runtime": "lua", "timeout": 100, "script": "if payload.status == \"test\" then\n return nil\nend\nreturn payload" }}Returning nil causes the input payload to be forwarded unchanged. To actually drop a payload, return an empty table or use a Filter downstream.
Example: String Manipulation
Section titled “Example: String Manipulation”{ "type": "MeddleScript", "config": { "runtime": "lua", "script": "payload.normalized_id = string.upper(string.gsub(payload.raw_id, \"-\", \"_\"))\nreturn payload" }}Best Practices
Section titled “Best Practices”- Set a non-zero
timeoutto bound CPU use per payload (100–500ms is typical) - Prefer Transform for simple field extraction; reach for Script only when you need real logic
- Keep scripts short and pure — they run on every payload
- Avoid building large intermediate tables; the sandbox uses a finite registry size
- Test forbidden symbols upfront — a Lua error from the sandbox surfaces as a script execution error and the payload is not emitted