@sadwx/line-exec-approval-plugin
v1.1.0
Published
OpenClaw plugin: LINE Flex Message cards for exec approval requests
Maintainers
Readme
line-exec-approval-plugin
OpenClaw plugin — deliver exec approval requests to LINE as interactive Flex Message cards
When OpenClaw asks for permission to run a shell command, this plugin pushes a rich card to LINE with three tap-to-approve buttons. No need to switch to a browser or another app.
How It Works
- Subscribes to
exec.approval.requestedevents from the local OpenClaw gateway via WebSocket - Pushes a LINE Flex Message card to the configured approver with three buttons:
- ✅ Allow Once — approve this command, this time only
- ⭐ Allow Always — add to allowlist and approve permanently
- ❌ Deny — block the command
- Tapping a button sends
/approve <id> <decision>through LINE, which OpenClaw resolves
Works alongside other approval channels (e.g. Discord buttons). The first channel to resolve wins.
Screenshots
Approval card
When an exec command requires approval, a Flex Message card is pushed to LINE:
The card appears the same across all button action modes. The difference is what happens after a button is tapped.
Button action modes
silent — nothing appears in chat after tapping (default)
friendly — shows the button label (e.g. ✅ Allow Once)
command — shows the raw /approve command text
Prerequisites
OpenClaw
- OpenClaw gateway installed and running (tested on v2026.3.8+)
execapprovals enabled in your OpenClaw config:
{
"agents": {
"defaults": {
"sandbox": {
"mode": "all"
}
}
}
}LINE
- A LINE Developers account
- A Messaging API channel with:
- A valid channel access token (long-lived token recommended)
- Webhook enabled and pointing to your OpenClaw gateway, e.g.
https://your-domain/line/webhook
- The approver must add the LINE bot as a friend before push messages can be received
Push quota: The free plan allows 200 push messages/month per channel. Consider using a dedicated channel for this plugin to keep its quota separate from other bots.
Installation
Option A: Local path
Clone or download this repo, then add to ~/.openclaw/openclaw.json:
{
"plugins": {
"allow": ["line-exec-approval-plugin"],
"load": {
"paths": ["/path/to/line-exec-approval-plugin"]
},
"entries": {
"line-exec-approval-plugin": {
"enabled": true,
"config": {
"lineUserId": "U1234567890abcdef1234567890abcdef",
"channelAccessTokenFile": "/path/to/line-channel-access-token.txt"
}
}
}
}
}Restart the gateway to load the plugin.
Option B: npm (once published)
openclaw plugins install openclaw-line-exec-approval-pluginThen add the plugins.entries config block above (without plugins.load.paths).
Configuration
| Field | Type | Required | Description |
|---|---|---|---|
| lineUserId | string | ✅ | LINE user ID of the approver (starts with U, 33 chars total) |
| channelAccessToken | string | — | Inline plaintext channel access token |
| channelAccessTokenFile | string | — | Path to a file containing the channel access token |
| channelAccessTokenEnv | string | — | Name of an environment variable containing the channel access token |
| buttonAction | string | — | How buttons behave when tapped: "command", "friendly", or "silent" (default: "silent") |
| enabled | boolean | — | Set to false to disable without removing config (default: true) |
Exactly one of channelAccessToken, channelAccessTokenFile, or channelAccessTokenEnv should be set. If none are set, the plugin falls back to the LINE channel config in OpenClaw.
Token resolution order
config.channelAccessToken— inline plaintext valueconfig.channelAccessTokenFile— content of the specified fileconfig.channelAccessTokenEnv— value of the named environment variablechannels.line.channelAccessToken/channels.line.tokenFile— inherited from the default LINE channel in OpenClaw configLINE_CHANNEL_ACCESS_TOKENenvironment variable
Full config example
{
"plugins": {
"allow": ["line-exec-approval-plugin"],
"load": {
"paths": ["/home/user/.openclaw/plugins/line-exec-approval-plugin"]
},
"entries": {
"line-exec-approval-plugin": {
"enabled": true,
"config": {
"lineUserId": "U1234567890abcdef1234567890abcdef",
"channelAccessTokenFile": "/home/user/.openclaw/secrets/line-token.txt"
}
}
}
}
}Button action modes
Controls what appears in the LINE chat when an approval button is tapped.
| Value | Chat behaviour | Notes |
|---|---|---|
| "silent" | Nothing appears in chat (default) | Cleanest UX; approval resolves silently |
| "friendly" | Shows the button label (e.g. ✅ Allow Once) | Visible confirmation without raw commands |
| "command" | Shows the raw /approve <id> allow-once text | Original behaviour; useful for debugging |
{
"config": {
"lineUserId": "U1234567890abcdef1234567890abcdef",
"channelAccessTokenFile": "/path/to/token.txt",
"buttonAction": "silent"
}
}Finding Your LINE User ID
Add your bot as a LINE friend, send it any message, then check the gateway logs:
openclaw channels logs --channel lineYour user ID appears in the inbound session key:
agent:main:line:direct:<userId>The <userId> part (starting with U) is what you need.
Using Multiple LINE Channels
If you have multiple Messaging API channels configured in OpenClaw (e.g. default and dev), point this plugin to a specific channel's token to control which channel's push quota is used:
{
"config": {
"lineUserId": "U1234567890abcdef1234567890abcdef",
"channelAccessTokenFile": "/home/user/.openclaw/secrets/line-dev-token.txt"
}
}LINE user IDs are scoped per provider (not per channel), so your user ID is the same across all channels under the same provider.
LINE Push Message Quota
| Plan | Monthly push limit | |---|---| | Free | 200 messages | | Light | 1,000 messages | | Standard | Unlimited |
Tip: Create a dedicated LINE Messaging API channel for approval notifications so its quota stays separate from channels used for regular messaging.
Troubleshooting
No Flex Message received after a command runs
- Confirm the approver has added the bot as a LINE friend
- Check gateway logs for
LINE push failed— HTTP 429 means quota is exhausted - Verify
lineUserIdis correct (runopenclaw channels logs --channel lineand look for the session key)
gateway auth OK not appearing in logs
- The gateway may not be running — check
openclaw gateway status - The gateway auth token may be wrong — verify
channels.gateway.auth.tokenin your config
Buttons do nothing when tapped
- The LINE channel's webhook must be active and pointing to your gateway
- The webhook URL must be reachable from LINE's servers (Cloudflare Tunnel or similar)
Command shows as (unknown) on the card
- Normal for sandbox initialization execs where the
commandfield is empty - Real user-triggered exec commands will display correctly
Development
npm run typecheck # TypeScript type check
npm run lint # ESLint
npm run lint:fix # ESLint with auto-fix
npm run format # Prettier
npm run build # Compile to dist/Project structure
src/
types.ts — Plugin config and OpenClaw API type stubs
flex-builder.ts — LINE Flex Message card builder
gateway-client.ts — Gateway WebSocket subscriber
line-sender.ts — LINE push message API + token resolution
index.ts — Plugin entry pointLicense
MIT
