slack-term 1.37.1 → 1.39.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +54 -1
- package/SKILL.md +18 -1
- package/dist/cli.js +179 -151
- package/package.json +1 -1
- package/ts/cli.ts +974 -18
- package/ts/escapes.ts +11 -0
- package/ts/lists.ts +122 -0
- package/ts/pinlog.ts +215 -0
- package/ts/slack.ts +75 -0
package/README.md
CHANGED
|
@@ -91,7 +91,7 @@ slack search "deploy" --count 50
|
|
|
91
91
|
slack send "#general" "Hello team"
|
|
92
92
|
# Prints who you're acting as (From: @handle (Uxxxx) — Workspace) + a destination
|
|
93
93
|
# preview + confirm code; rerun with --code=<code> to actually send. Every gated write
|
|
94
|
-
# (send/edit/delete/upload/schedule/channel create/drafts) shows that From: line and
|
|
94
|
+
# (send/edit/delete/upload/schedule/channel create/lists/drafts) shows that From: line and
|
|
95
95
|
# binds it into the code, so a profile switch mid-flow invalidates it instead of acting
|
|
96
96
|
# as the wrong account.
|
|
97
97
|
slack send "#general" "Hello team" --code=<code>
|
|
@@ -277,6 +277,59 @@ Notes:
|
|
|
277
277
|
are **never** cached — they are exactly the values that change, and Slack's search index
|
|
278
278
|
already lags. A corrupt or unwritable cache is ignored and the command runs uncached.
|
|
279
279
|
|
|
280
|
+
### pinlog — a pinned status board that keeps a log
|
|
281
|
+
|
|
282
|
+
A **pinlog** is one pinned top-level message that always holds the *current* state
|
|
283
|
+
(HEAD), plus a thread under it with one short reply per change (the log). The HEAD is
|
|
284
|
+
**edited in place, which is silent**; each log reply **notifies**. People who want the
|
|
285
|
+
state read the pin; people who want to know what changed follow the thread. Good for
|
|
286
|
+
anything people come back to: blocker boards, release readiness, incidents — one board
|
|
287
|
+
per topic.
|
|
288
|
+
|
|
289
|
+
```bash
|
|
290
|
+
slack pinlog ls "#gtm" # boards in a channel (found by their footer)
|
|
291
|
+
slack pinlog get <board> # state + log (--json for one object)
|
|
292
|
+
slack pinlog new "#gtm" "販売ブロッカー\n1. 見積テンプレ — 未" ["why this board exists"]
|
|
293
|
+
slack pinlog set <board> "<the WHOLE new state>" "見積テンプレ: 未 → 済"
|
|
294
|
+
slack pinlog set <board> --file board.md "見積テンプレ: 未 → 済" # state from a file (- = stdin)
|
|
295
|
+
slack pinlog note <board> "まだ法務待ち — 再送済" # reason only, state unchanged
|
|
296
|
+
```
|
|
297
|
+
|
|
298
|
+
`<board>` is the board's permalink, `#chan:ts`, or the `C…:ts` id `new` prints. There
|
|
299
|
+
are no names and nothing is stored locally: a board *is* its Slack message, so the same
|
|
300
|
+
command works from any machine. Each verb takes only its own kind of target — `new` and
|
|
301
|
+
`ls` a channel, the rest a board — so a pasted channel can never turn an intended update
|
|
302
|
+
into a second board.
|
|
303
|
+
|
|
304
|
+
- Every HEAD ends with a footer, `_Pinlog · 最終更新 2026-10-08 15:10 JST · 更新はスレッドに_`,
|
|
305
|
+
refreshed on each update. `ls` finds boards by it, and `set` **refuses** a message
|
|
306
|
+
without it, so a wrong link cannot overwrite an ordinary message.
|
|
307
|
+
To turn an existing hand-run board into a pinlog on purpose, pass `set --adopt` once.
|
|
308
|
+
- `new`, `set` and `note` use the same two-step `--code` gate as `send`/`edit`, and the
|
|
309
|
+
preview shows the situation, not just your text: `new` lists boards already in the
|
|
310
|
+
channel (usually a sign you meant `set`), and `set` shows the current state next to
|
|
311
|
+
the new one. The `set` code covers the current state, so if someone else changed the
|
|
312
|
+
board after your preview, your code stops matching and you re-read first.
|
|
313
|
+
- **`set` order:** the state edit first, then the reason reply. If the edit fails, **no**
|
|
314
|
+
reason is posted. If the reply fails, the command exits 1, says the state *is* updated,
|
|
315
|
+
and prints the exact retry (`slack pinlog note <board> '…' --code=…`).
|
|
316
|
+
A failure that *may* have landed (network error, Slack `internal_error`/`fatal_error`)
|
|
317
|
+
is reported as `UNKNOWN`, not `NOT posted`, with the `get`/`ls` command to check
|
|
318
|
+
first, because a blind retry would post a second board or a second notifying reply.
|
|
319
|
+
A HEAD over Slack's 40,000-character limit is refused before posting, because Slack
|
|
320
|
+
would truncate the footer.
|
|
321
|
+
- `new` without the pin scope still creates the board: it says `NOT pinned`, prints
|
|
322
|
+
the `slack pinlog pin <board>` command, and exits 0, because retrying `new` would make a
|
|
323
|
+
second board. Pinning needs `pins:write` on the token you act with.
|
|
324
|
+
- `--as-bot` acts as the bot for reads and writes. Slack lets a token edit only its own
|
|
325
|
+
messages, so a board the bot created must be updated `--as-bot`.
|
|
326
|
+
- During quiet hours (JST 23:00–08:00) the preview shows the quiet-hours line, and the
|
|
327
|
+
confirmed run warns that the reply notified. It warns but does not block.
|
|
328
|
+
- Text is posted as-is (plain mrkdwn, no blocks) so the footer reads back verbatim;
|
|
329
|
+
`@handle`s are **not** converted — write `<@U…>` if you need a real mention.
|
|
330
|
+
- Stateless: the only local files are short-lived per-board locks, held while a `set` runs,
|
|
331
|
+
so two writers on one machine cannot interleave.
|
|
332
|
+
|
|
280
333
|
### tail — real-time message stream
|
|
281
334
|
|
|
282
335
|
`slack tail` polls a channel every 3 seconds (configurable via `--interval`) and
|
package/SKILL.md
CHANGED
|
@@ -120,7 +120,7 @@ plus `[as bot]` under `--as-bot`) and the resolved destination (`→ ... — THR
|
|
|
120
120
|
`→ ... — NEW top-level message`); verify both before re-running with `--code`.
|
|
121
121
|
|
|
122
122
|
**Every** gated write opens its preview with that same `From:` line — `send`, `edit`,
|
|
123
|
-
`delete`, `upload`, `schedule send`, `schedule rm`, `channel create`, `drafts edit`,
|
|
123
|
+
`delete`, `upload`, `schedule send`, `schedule rm`, `channel create`, `lists create/add/set/share`, `drafts edit`,
|
|
124
124
|
`drafts delete` — and the identity is part of the confirm hash: switching
|
|
125
125
|
profile/token between preview and confirm invalidates the code instead of acting as
|
|
126
126
|
someone else. It matters most on `schedule send`, where the message goes out later,
|
|
@@ -202,6 +202,22 @@ slack sent --cwd . --json # everything posted from this repo,
|
|
|
202
202
|
Read-only and token-free. `SLACK_TERM_ATTRIBUTION=off` disables both the log and the
|
|
203
203
|
metadata; `SLACK_TERM_AGENT_SESSION` / `_CLI` / `_PID` override what is detected.
|
|
204
204
|
|
|
205
|
+
### pinlog — a pinned board: HEAD = current state, thread = log
|
|
206
|
+
|
|
207
|
+
```bash
|
|
208
|
+
slack pinlog ls "#chan" # boards in a channel
|
|
209
|
+
slack pinlog get <board> # state + log
|
|
210
|
+
slack pinlog new "#chan" --file board.md "<why>" --as-bot # → board id C…:ts; pins it
|
|
211
|
+
slack pinlog set <board> --file board.md "<what changed>" --as-bot
|
|
212
|
+
slack pinlog note <board> "<progress, state unchanged>" --as-bot
|
|
213
|
+
```
|
|
214
|
+
|
|
215
|
+
`<board>` = permalink, `#chan:ts` or `C…:ts` — no names, nothing local. The state is edited
|
|
216
|
+
in place (silent); `set` and `note` each post ONE thread reply (notifies). Always pass the
|
|
217
|
+
WHOLE new state, keep it true, and post only for real changes. Writes need `--code` (preview
|
|
218
|
+
first). If the edit fails, no reply is posted; if the reply fails, the command prints the
|
|
219
|
+
`note` retry. A board the bot created must be changed `--as-bot`.
|
|
220
|
+
|
|
205
221
|
### todo — tasks as reactions
|
|
206
222
|
|
|
207
223
|
A task is any message carrying the marker reaction 📌 `:pushpin:`. Progress lives in a
|
|
@@ -280,6 +296,7 @@ Under **User Token Scopes**:
|
|
|
280
296
|
- `users:read` — resolve display names
|
|
281
297
|
- `chat:write` — send messages
|
|
282
298
|
- `reactions:write` — add/remove reactions (`react`)
|
|
299
|
+
- `pins:write` — pin a board (`pinlog new` / `pinlog pin`)
|
|
283
300
|
|
|
284
301
|
> **Token-type gotcha:** the CLI uses the **user token** (`xoxp-`) by default, so scopes
|
|
285
302
|
> must be under **User Token Scopes**. Adding `reactions:write` only to *Bot* Token Scopes
|