All checks were successful
Native Rust workspace compile / compile (push) Successful in 21m44s
241 lines
11 KiB
Markdown
241 lines
11 KiB
Markdown
# Native programs
|
||
|
||
The `libremetaverse-programs` package owns one native Rust binary for every
|
||
program in the pinned LibreMetaverse source snapshot. The source inventory and
|
||
hashes remain in `upstream-programs.json`; implementation status is tracked
|
||
here so a source entry is never mistaken for a completed port.
|
||
|
||
| Binary | Upstream project | Status |
|
||
| --- | --- | --- |
|
||
| `osd-inspector` | OSDInspector | Implemented and tested offline |
|
||
| `simple-bot` | SimpleBot | Implemented with live and deterministic fake-grid modes |
|
||
| `packet-dump` | PacketDump | Implemented with live and deterministic fake-grid capture |
|
||
| `prim-inspector` | PrimInspector | Implemented with live and deterministic fake-grid discovery |
|
||
| `inventory-explorer` | InventoryExplorer | Implemented with live inventory and deterministic AIS fixtures |
|
||
| `irc-gateway` | IRCGateway | Pending milestone 11 issue #90 |
|
||
| `test-client` | TestClient | Pending milestone 11 issues #91–#94 |
|
||
| `vivox-test` | VivoxTest | Pending milestone 11 issue #95 |
|
||
| `webrtc-test` | WebRtcTest | Pending milestone 11 issue #96 |
|
||
|
||
## OSDInspector
|
||
|
||
`osd-inspector` is a bounded, offline command-line client of the public native
|
||
StructuredData and Primitive APIs. It does not initialize a grid client, read
|
||
credentials, load a native codec, or invoke a .NET process.
|
||
|
||
```text
|
||
osd-inspector inspect <file> # alias: i
|
||
osd-inspector convert <input> <format> <out> # alias: c
|
||
osd-inspector validate <file> # alias: v
|
||
osd-inspector prim-to-osd
|
||
osd-inspector osd-to-prim <file>
|
||
```
|
||
|
||
The supported output formats are `json` (`j`), `xml` (`x`), `binary`
|
||
(`bin` or `b`), and `notation` (`llsd` or `n`). Use `-` as an input or output
|
||
path for standard input or standard output. Format detection uses the filename
|
||
extension as a hint and then checks every native parser, so binary and notation
|
||
LLSD work through files and pipes as well as JSON and XML.
|
||
|
||
Input is read through a bounded buffer and is limited to the StructuredData
|
||
binary allocation limit by default. `--max-input-bytes <BYTES>` can lower that
|
||
ceiling for constrained callers. StructuredData also enforces its depth, node,
|
||
and aggregate allocation limits while parsing.
|
||
|
||
Normal results are written to stdout and diagnostics to stderr. Exit status is
|
||
stable for scripts:
|
||
|
||
| Status | Meaning |
|
||
| --- | --- |
|
||
| 0 | Success |
|
||
| 2 | Command-line usage error |
|
||
| 3 | File or standard-stream I/O error |
|
||
| 4 | Invalid or oversized OSD input |
|
||
| 5 | Primitive conversion or output serialization error |
|
||
|
||
Run the issue-focused CLI suite and the related translated StructuredData cases
|
||
with:
|
||
|
||
```sh
|
||
cargo test -p libremetaverse-programs --test osd_inspector_cli --locked
|
||
cargo test --manifest-path tests/compat/Cargo.toml --test structured_data --locked
|
||
```
|
||
|
||
## SimpleBot
|
||
|
||
`simple-bot` is an asynchronous native Rust client with the command surface of
|
||
the upstream example. A live session accepts the original positional
|
||
credentials, or reads them from the environment:
|
||
|
||
```text
|
||
simple-bot FIRSTNAME LASTNAME PASSWORD [--login-uri URL]
|
||
GRID_FIRST_NAME=... GRID_LAST_NAME=... GRID_PASSWORD=... simple-bot
|
||
```
|
||
|
||
`GRID_LOGIN_URL` supplies the endpoint when `--login-uri` is absent, and
|
||
`--login-timeout-seconds` bounds login to 30 seconds by default. Credentials,
|
||
authorization values, capability URLs, and token values are redacted from
|
||
output. After login the bot answers `help`/`?`, `where`/`location`, `sit`,
|
||
`stand`, `dance`, `fly`, `walk`, `jump`, and `hello`/`hi`/`hey` instant
|
||
messages. It also greets other avatars that say hello in local chat. Ctrl-C
|
||
cancels pending greetings and login work, releases an in-progress jump,
|
||
unsubscribes event handlers, logs out, and disposes the client before exit.
|
||
|
||
For offline validation, `--fake-script FILE` runs the same command handlers
|
||
against a deterministic fake grid. Scripts contain no credentials. Blank
|
||
lines and lines beginning with `#` are ignored; remaining lines use one of:
|
||
|
||
```text
|
||
im<TAB>source-uuid<TAB>source-name<TAB>message
|
||
chat<TAB>source-uuid<TAB>source-name<TAB>message
|
||
status<TAB>message
|
||
```
|
||
|
||
The reader accepts at most 1 MiB, 1,024 events, 256-byte names, and 4,096-byte
|
||
messages. The fake transcript records every client call, uses the real DANCE1
|
||
UUID, and finishes with zero active tasks and sockets. Run the issue-focused
|
||
suite and the related runtime compatibility cases with:
|
||
|
||
```sh
|
||
cargo test -p libremetaverse-programs --test simple_bot_cli --locked
|
||
cargo test --manifest-path tests/compat/Cargo.toml --test core_runtime_shims --locked
|
||
```
|
||
|
||
## PacketDump
|
||
|
||
`packet-dump` preserves the upstream live arguments and its 20-second login
|
||
timeout while adding safe, bounded capture controls:
|
||
|
||
```text
|
||
packet-dump FIRSTNAME LASTNAME PASSWORD SECONDS
|
||
[--direction incoming|outgoing|both]
|
||
[--packet-type NAME]... [--raw]
|
||
[--output FILE] [--max-output-bytes BYTES] [--max-packets COUNT]
|
||
```
|
||
|
||
`SECONDS=0` captures until Ctrl-C. Credentials can instead come from
|
||
`GRID_FIRST_NAME`, `GRID_LAST_NAME`, and `GRID_PASSWORD`; `GRID_LOGIN_URL` or
|
||
`--login-uri` selects a login endpoint. The client disables multiple simulator
|
||
connections and sends zero land, wind, and cloud throttles like the source
|
||
program. Incoming decoded callbacks retain their original datagrams, while
|
||
outgoing callbacks are decoded through the public packet factory. Records show
|
||
direction, packet type, simulator, byte count, sequence, frequency, ID, and
|
||
header flags. Exact packet-type filters may be repeated.
|
||
|
||
Raw hexadecimal output is opt-in. Live capture masks the password and native
|
||
session identifiers wherever they occur in a datagram, and suppresses raw
|
||
payloads containing URLs, authorization terms, capability terms, or token
|
||
assignments. Login and disconnect messages use the same text redaction.
|
||
Output defaults to stdout, may be redirected to a newly truncated file, and is
|
||
bounded to 16 MiB and 100,000 matching packets unless lower or higher explicit
|
||
limits are supplied. A complete line is either written or rejected at the byte
|
||
limit.
|
||
|
||
Offline validation uses `--fake-script FILE` with records of this form:
|
||
|
||
```text
|
||
incoming<TAB>simulator<TAB>hex-bytes
|
||
outgoing<TAB>simulator<TAB>hex-bytes
|
||
```
|
||
|
||
Scripts are capped at 8 MiB and individual datagrams at 64 KiB. Each datagram
|
||
is passed through the native wire decoder; malformed and unknown packets are
|
||
reported without aborting the capture. The issue-focused and related translated
|
||
wire tests are:
|
||
|
||
```sh
|
||
cargo test -p libremetaverse-programs --test packet_dump_cli --locked
|
||
cargo test -p libremetaverse --test packet_wire --locked
|
||
cargo test --manifest-path tests/compat/Cargo.toml --test wire_semantics --locked
|
||
```
|
||
|
||
## PrimInspector
|
||
|
||
`prim-inspector` preserves the upstream positional login and search arguments:
|
||
|
||
```text
|
||
prim-inspector FIRSTNAME LASTNAME PASSWORD [SEARCH_TERM]
|
||
GRID_FIRST_NAME=... GRID_LAST_NAME=... GRID_PASSWORD=... prim-inspector
|
||
```
|
||
|
||
The native client disables multiple-simulator connections, allows 30 seconds
|
||
for login, collects object updates for two seconds, and snapshots the current
|
||
simulator's real primitive table. It requests missing properties through
|
||
`ObjectManager::SelectObject`, sharing a three-second deadline across at most
|
||
1,024 outstanding requests. A disconnect, simulator change, or Ctrl-C cancels
|
||
the operation and still removes handlers, logs out, and disposes the client.
|
||
|
||
Names are filtered case-insensitively after available properties are hydrated.
|
||
Matches are ordered by distance from the agent, with local ID and UUID tie
|
||
breakers, and the nearest ten are shown by default. `--limit` accepts one
|
||
through 100 objects. Output covers transforms, construction data, flags,
|
||
parentage, sculpt, light, flexible, ownership, creator, description, sale, and
|
||
hover-text details. Status text, descriptions, and names suppress URLs and
|
||
credential-like assignments, and `--max-output-bytes` bounds the complete
|
||
buffer before anything is written.
|
||
|
||
For offline validation, `--fake-grid FILE [--search SEARCH_TERM]` reads an LLSD
|
||
JSON map containing `region`, `agent_position`, and an `objects` array. Object
|
||
maps use the public `Primitive::from_osd` fields and may add `owner`, `creator`,
|
||
`sale_type`, `sale_price`, `hover_text`, and `property_state`. The latter is
|
||
`ready`, `delayed`, or `missing`; delayed and missing fixtures record the same
|
||
selection/property-timeout decisions as a live session. Input is limited to 8
|
||
MiB, 100,000 objects, LLSD depth/allocation limits, nonzero UUID/local IDs, and
|
||
validated property/sale states. No live grid is contacted by the tests.
|
||
|
||
Run the isolated CLI golden tests and the related translated primitive cases:
|
||
|
||
```sh
|
||
cargo test -p libremetaverse-programs --test prim_inspector_cli --locked
|
||
cargo test --manifest-path tests/compat/Cargo.toml --test world_object_semantics --locked
|
||
```
|
||
|
||
## InventoryExplorer
|
||
|
||
`inventory-explorer` preserves the source program's live login and operation
|
||
options:
|
||
|
||
```text
|
||
inventory-explorer FIRSTNAME LASTNAME PASSWORD [--stats]
|
||
[--search TERM [--type TYPE]] [--export FILE]
|
||
```
|
||
|
||
Credentials may instead come from `GRID_FIRST_NAME`, `GRID_LAST_NAME`, and
|
||
`GRID_PASSWORD`; `GRID_LOGIN_URL` or `--login-uri` selects the endpoint. Login
|
||
and inventory readiness each have a 30-second deadline. The native client waits
|
||
for a populated root in the real `InventoryManager::store`, handles Ctrl-C and
|
||
disconnects, removes event handlers, logs out, and disposes the client on every
|
||
post-construction path.
|
||
|
||
With no operation option, the program prints the sorted top-level folders and
|
||
items. `--stats` traverses the hierarchy and reports item and root-folder counts
|
||
plus the ten most common asset types. `--search` performs a case-insensitive
|
||
name search across folders and items, reports parent folders and UUIDs, and
|
||
shows link targets. `--type` accepts every native `AssetType` name and narrows
|
||
item results. Search output defaults to 50 results and is capped at 1,000.
|
||
|
||
`--export FILE` writes a deterministic `deterministic-v1` hierarchy with
|
||
folders before items, stable case-insensitive name and UUID ordering, asset
|
||
types, link targets, and UUIDs. The destination must be an explicit non-symlink
|
||
path of at most 4,096 characters. The in-memory export is validated before the
|
||
file is written and defaults to a 16 MiB limit. Traversal defaults to 100,000
|
||
entries and 64 folder levels, detects cycles, and exposes configurable bounded
|
||
limits. Standard output is buffered and limited to 4 MiB, and inventory/status
|
||
text redacts URLs and credential-like assignments.
|
||
|
||
Offline validation uses `--fake-ais FILE`. The file is an LLSD JSON AIS response
|
||
with a nonzero `root_id` and ordinary `_embedded.categories`, `.items`, and
|
||
`.links` maps. It is capped at 8 MiB and parsed by the public native
|
||
`InventoryAISClient`; parsed folders, items, and links are then installed
|
||
through the real manager-owned `Inventory` store. This exercises AIS typing,
|
||
derived inventory items, link targets, parent indexes, and folder contents
|
||
without contacting a grid or embedding credentials.
|
||
|
||
Run the isolated CLI/golden suite and its related translated inventory gates:
|
||
|
||
```sh
|
||
cargo test -p libremetaverse-programs --test inventory_explorer_cli --locked
|
||
cargo test --manifest-path tests/compat/Cargo.toml --test inventory_store_semantics --locked
|
||
cargo test --manifest-path tests/compat/Cargo.toml --test inventory_ais_semantics --locked
|
||
```
|