| name | slack-rs |
| description | Slack Web API automation via the slack-rs CLI (Rust). Use when you need to authenticate to Slack via OAuth (PKCE), manage multiple workspace profiles, call arbitrary Slack Web API methods (e.g. chat.postMessage, conversations.list, users.info), and run safe scripted Slack operations from the terminal. Includes tunnel-assisted remote login (see auth login --help), encrypted profile export/import, and a write-safety guard via SLACKCLI_ALLOW_WRITE. Credentials are stored in file-based storage under ~/.config/slack-rs/.
|
slack-rs - Slack Web API CLI (Rust)
Use slack-rs to interact with Slack workspaces using your own OAuth credentials. It supports multiple profiles (workspaces/apps), stores credentials in file-based storage under ~/.config/slack-rs/, and can call any Slack Web API method.
Setup
For install, OAuth app creation, and first-time authentication, see slack-rs/references/setup.md.
Make API Calls
Use generic API calls for anything supported by Slack Web API:
slack-rs api call users.info user=U123456
slack-rs api call conversations.list limit=200
slack-rs api call conversations.history channel=C123456 limit=50
slack-rs api call chat.postMessage channel=C123456 text="Hello from slack-rs"
Unified Output Envelope
By default, commands output a unified structure:
{
"meta": {
"profile_name": "default",
"method": "conversations.list",
"command": "api call",
"token_type": "user"
},
"response": {
"ok": true,
"channels": []
}
}
To get the raw Slack Web API response (without the envelope), use --raw:
slack-rs api call conversations.list --raw
Choose Bot vs User Token
If your Slack app has both a bot token and a user token, set the default token type per profile:
slack-rs config set my-workspace --token-type user
slack-rs config set my-workspace --token-type bot
Confirm with:
slack-rs auth status my-workspace
For more copy/pasteable recipes, see slack-rs/references/recipes.md.
Fixed Rules for Slack Posting
When posting or updating Slack messages (chat.postMessage, chat.update), follow these rules to avoid broken newlines such as literal \\n appearing in the final message.
- Do not write long message bodies directly in the shell
- Avoid relying on shell quoting or escaped
\n
- Generate the body with
python3 - <<'PY' using triple-quoted strings, then assign it to a variable
- Always verify the rendered message after posting
- Do not treat the
chat.postMessage / chat.update response alone as success
- Re-fetch the message with
conversations.history or conversations.replies and inspect the actual rendered text
- Do not report success until verification is complete
- This is an operational rule
Recommended flow:
TEXT="$({ python3 - <<'PY'
text = """line 1
line 2
line 3"""
print(text, end="")
PY
} )"
slack-rs api call chat.postMessage channel=C123456 text="$TEXT"
slack-rs api call conversations.history channel=C123456 limit=1
slack-rs api call conversations.replies channel=C123456 ts=<thread_ts>
During verification, inspect the fetched text as-is and confirm that no unintended literal \\n or \\n\\n sequences appear before treating the operation as successful.
Introspection (Commands / Help / Schemas)
Use these commands to discover what the CLI can do and how to call it (machine-readable):
slack-rs commands --json
slack-rs conv list --help --json
slack-rs msg post --help --json
slack-rs schema --command msg.post --output json-schema
slack-rs schema --command conv.list --output json-schema
slack-rs schema --command api.call --output json-schema
Conversation Helpers
Use the convenience commands instead of api call for common tasks:
slack-rs conv list
slack-rs conv search <pattern>
slack-rs conv history <channel_id>
slack-rs thread get <channel_id> <thread_ts>
Notes:
- Command names accept both dot and space formats (e.g.
conv.list == conv list, msg.post == msg post).
schema describes the default enveloped JSON output; it does not describe --raw output.
meta is a baseline envelope and not exhaustive; additional fields may be added over time.
conv list supports --filter, --format, and --sort (see slack-rs conv list --help).
conv select and conv history --interactive require an interactive terminal (TTY).
Example output (slack-rs schema --command msg.post --output json-schema):
{
"schemaVersion": 1,
"type": "schema",
"ok": true,
"command": "msg.post",
"schema": {
"$schema": "http://json-schema.org/draft-07/schema#",
"type": "object",
"properties": {
"schemaVersion": {
"type": "integer",
"description": "Schema version number"
},
"type": {
"type": "string",
"description": "Response type identifier"
},
"ok": {
"type": "boolean",
"description": "Indicates if the operation was successful"
},
"response": {
"type": "object",
"description": "Slack API response data"
},
"meta": {
"type": "object",
"description": "Metadata about the request and profile",
"properties": {
"profile": {"type": "string"},
"team_id": {"type": "string"},
"user_id": {"type": "string"},
"method": {"type": "string"},
"command": {"type": "string"}
}
}
},
"required": ["schemaVersion", "type", "ok"]
}
}
Safe Defaults for Write Operations
Many Slack methods are write operations (posting, updating, deleting, reactions). Use the guard in environments where writes are risky:
export SLACKCLI_ALLOW_WRITE=false
Re-enable explicitly when you intend to write:
export SLACKCLI_ALLOW_WRITE=true
Profile Backup / Migration
Export/import profiles using encrypted files (treat as secrets):
slack-rs auth export --all --out all-profiles.enc --passphrase-prompt --yes
slack-rs auth import --all --in all-profiles.enc --passphrase-prompt
For non-interactive automation options, refer to slack-rs auth export --help and slack-rs auth import --help.
Configuration
Common environment variables:
SLACKCLI_ALLOW_WRITE: allow/deny write operations (default: allowed)
SLACK_OAUTH_BASE_URL: custom OAuth base URL (testing/enterprise Slack)
For export/import passphrase options, use --passphrase-prompt or see slack-rs auth export --help.
Troubleshooting
- Remote environments: use a tunnel (ngrok/cloudflared) and set your profile redirect URI accordingly.
Private channels are missing
Private channels typically require a user token. Ensure:
slack-rs config set <profile> --token-type user
- Your Slack app has user scopes (
groups:read, groups:history / conversations:read, etc.)
Useful Commands
Profile management:
slack-rs auth list
slack-rs auth status <profile>
slack-rs auth rename <old> <new>
slack-rs auth logout <profile>
OAuth config management:
slack-rs config oauth show <profile>
slack-rs config oauth delete <profile>