# quicprochat Playbooks YAML-based scripted command sequences for the qpc client. ## Running a playbook ```bash # Build with playbook support cargo build -p quicprochat-client --features playbook # Run a playbook cargo run -p quicprochat-client --features playbook -- \ run playbooks/smoke-test.yaml \ --server 127.0.0.1:7000 \ --username alice --password hunter2 \ --danger-accept-invalid-certs # Override variables cargo run -p quicprochat-client --features playbook -- \ run playbooks/smoke-test.yaml \ -V recipient=charlie -V server=remote.example.com:7000 ``` ## YAML format ```yaml name: "My playbook" description: "Optional description" variables: key: "value" # available as $key in args steps: - command: dm # any slash command name (without /) args: username: "$key" # variable substitution - command: send args: text: "Hello!" - command: assert condition: message_count # connected, logged_in, in_conversation, message_count, member_count op: gte # eq, ne, gt, lt, gte, lte (or ==, !=, >, <, >=, <=) value: 1 ``` ## Variable substitution - `$varname` — replaced with the variable value - `${VAR:-default}` — replaced with VAR, falling back to env var, then default - Variables from `--var KEY=VALUE` override playbook defaults - `_server` and `_username` are auto-injected ## Step options | Field | Type | Description | |-------|------|-------------| | `command` | string | Command name (required) | | `args` | map | Command arguments | | `condition` | string | For `assert` steps | | `op` | string | Comparison operator for asserts | | `value` | any | Expected value for asserts | | `capture` | string | Store output in this variable | | `on_error` | string | `fail` (default), `skip`, `continue` | | `loop` | object | Repeat with `{var, from, to}` | ## Loop syntax ```yaml - command: send args: text: "Message $i" loop: var: i from: 1 to: 10 ``` ## Available commands All REPL slash commands (without the `/`): `help`, `quit`, `whoami`, `list`, `switch`, `dm`, `create-group`, `invite`, `remove`, `leave`, `join`, `members`, `group-info`, `rename`, `history`, `verify`, `update-key`, `typing`, `react`, `edit`, `delete`, `send-file`, `download`, `delete-account`, `disappear`, `privacy`, `verify-fs`, `rotate-all-keys`, `devices`, `register-device`, `revoke-device`, `mesh-peers`, `mesh-send`, `mesh-broadcast`, `mesh-subscribe`, `mesh-route`, `mesh-identity`, `mesh-store`. Plus lifecycle commands: `send` (send a chat message), `wait` (pause), `assert` (check condition), `set-var` (set variable). ## Programmatic Rust API ```rust use quicprochat_client::{PlaybookRunner, Command, CommandRegistry, CommandResult}; // From YAML file let mut runner = PlaybookRunner::from_file(Path::new("playbook.yaml"))?; runner.set_var("recipient", "bob"); let report = runner.run(&mut session, &client).await; println!("{report}"); // Single command execution let cmd = Command::Dm { username: "alice".into() }; let result = CommandRegistry::execute(&cmd, &mut session, &client).await; assert!(result.success); ``` ## Example playbooks | File | Description | |------|-------------| | `health-check.yaml` | Verify server connectivity | | `smoke-test.yaml` | Quick E2E: DM + send + history | | `register-and-dm.yaml` | DM exchange between two users | | `group-lifecycle.yaml` | Create/invite/send/leave group | | `stress-send.yaml` | Send 100 messages in a loop |