/activity
Run any external, side-effecting operation — send an email, call Stripe, patch a deployment, fulfill a webhook — as a MeshWeaver Activity with a durable log. The uniform contract for side-effects — reactive (no async on hub threads), I/O through IIoPool, progress and outcome persisted under the partition's _Activity satellite, cancellable. Covers when to use it, the RunActivity recipe, the node-native Code-node form, and the anti-patterns (bare HttpClient on a hub thread, a bespoke control-plane node reinventing the log).
- Instructions: You are wiring up an **external, side-effecting operation** — one that reaches outside the mesh and *changes something*: send an email, create a Stripe Checkout session, patch a Kubernetes deployment, fulfill a payment webhook, push to GitHub. In MeshWeaver these do **not** get a bare `async` method or a one-off `HttpClient` on a hub thread. They run as an **Activity with a log**. # Why — one contract for every side-effect An Activity gives you four things a bare async call never will, for free and uniformly: 1. **A durable, queryable log.** The activity is a real node at `{partition}/_Activity/{id}` whose `ActivityLog` keeps every `ctx.Log(...)` line and a terminal `Status` (Succeeded / Failed / Cancelled). *The log is always kept* — after the fact you can see exactly what happened, who ran it, and why it failed. (The memex self-update that patches a live deployment is the poster child: when it silently half-ran, there was no log; as an Activity it would have been self-documenting.) 2. **Reactive, off the hub scheduler.** The command is `Func<ActivityContext, IObservable<Unit>>` — no `async`/`await` on hub- or view-reachable threads. The one sanctioned async boundary is **`IIoPool`** (`Doc/Architecture/ControlledIoPooling.md`); the HTTP/file round-trip runs there, bounded, never on the subscribing thread. 3. **Cancellation** via the Activity Control Plane — `RequestedStatus = Cancelled` trips the command's `CancellationToken`. (`Doc/Architecture/ActivityControlPlane.md`.) 4. **Correct ownership/routing.** The activity node is created under a real, routable `partitionPath` and the command runs as its owner. An **empty/whitespace partition NotFound-storms the router** — the same failure mode that makes ad-hoc hub reads from an ephemeral `cache/…` hub time out. # The recipe — `hub.RunActivity` ```csharp using System.Reactive; // Unit using System.Reactive.Linq; using MeshWeaver.GitSync; // RunActivity, Activity…
- Auto mount: yes
- Launches sub thread: no