← Back to PRs

#22874: fix(slack): preserve numeric threadId for message read

by HarryMWinters open 2026-02-21 19:34 View on GitHub →
size: XS
## Summary - Problem: Slack `message` read can drop numeric `threadId` values and return channel history instead of thread replies. - Why it matters: models/tools often emit Slack timestamps as numbers; thread reads should still work. - What changed: Slack read adapter now accepts string-or-number `threadId` and forwards numeric values as strings. - What did NOT change (scope boundary): no broad parser behavior changes outside Slack read adapter. ## Change Type (select all) - [x] Bug fix - [ ] Feature - [ ] Refactor - [ ] Docs - [ ] Security hardening - [ ] Chore/infra ## Scope (select all touched areas) - [ ] Gateway / orchestration - [x] Skills / tool execution - [x] Integrations - [ ] API / contracts - [ ] UI / DX - [ ] CI/CD / infra ## Linked Issue/PR - Closes #22852 - Related #15713 - Context #1450, #14948, #1442 ## User-visible / Behavior Changes - Slack `message` tool `read` preserves numeric `threadId` inputs by coercing to string before dispatch. ## Security Impact (required) - New permissions/capabilities? (`Yes/No`) No - Secrets/tokens handling changed? (`Yes/No`) No - New/changed network calls? (`Yes/No`) No - Command/tool execution surface changed? (`Yes/No`) No - Data access scope changed? (`Yes/No`) No - If any `Yes`, explain risk + mitigation: ## Repro + Verification ### Environment - OS: macOS - Runtime/container: Node + pnpm - Integration/channel (if any): Slack ### Steps 1. Invoke Slack read with numeric `threadId`. 2. Observe adapter payload passed to Slack action handler. ### Expected - Numeric `threadId` is forwarded as a non-empty string. ### Actual (before fix) - `threadId` was dropped (`undefined`) and reads fell back to channel history. ## Evidence - [x] Failing test/log before + passing after - [ ] Trace/log snippets - [ ] Screenshot/recording - [ ] Perf numbers (if relevant) ## Human Verification (required) - Verified scenarios: - `pnpm test -- src/channels/plugins/actions/actions.test.ts -t "forwards numeric threadId for read"` (failed before fix, passes after) - `pnpm test -- src/channels/plugins/actions/actions.test.ts -t "slack actions adapter"` - `pnpm test -- src/slack/actions.read.test.ts` - Full suite check performed locally by operator: `pnpm build && pnpm check && pnpm test` - Edge cases checked: - Existing string `threadId` forwarding test remains passing. - What you did **not** verify: - Live Slack workspace E2E in this PR. ## Compatibility / Migration - Backward compatible? (`Yes/No`) Yes - Config/env changes? (`Yes/No`) No - Migration needed? (`Yes/No`) No ## Failure Recovery (if this breaks) - How to disable/revert this change quickly: revert this PR. - Files/config to restore: `src/plugin-sdk/slack-message-actions.ts`, `src/channels/plugins/actions/actions.test.ts`, `CHANGELOG.md`. - Known bad symptoms reviewers should watch for: Slack read thread queries returning channel history despite numeric `threadId` input. ## Risks and Mitigations - Risk: Number coercion could accept unintended numeric values for `threadId`. - Mitigation: change is intentionally scoped to Slack read adapter `threadId` parsing only. ## AI Assistance - AI-assisted implementation and test drafting; validated by local test runs. <!-- greptile_comment --> <h3>Greptile Summary</h3> Fixed Slack `message` read to preserve numeric `threadId` values by using `readStringOrNumberParam` instead of `readStringParam`, preventing thread reads from falling back to channel history when LLM models emit timestamps as numbers. - Scoped change to read action only in `src/plugin-sdk/slack-message-actions.ts:115` - Added test coverage for numeric `threadId` conversion to string - Maintains backward compatibility with existing string `threadId` inputs <h3>Confidence Score: 5/5</h3> - This PR is safe to merge with minimal risk - The change is well-scoped to a single parameter parser in one action handler, includes proper test coverage verifying the numeric-to-string conversion, and maintains backward compatibility with existing string inputs. The implementation leverages an existing utility function (`readStringOrNumberParam`) that handles both types safely. - No files require special attention <sub>Last reviewed commit: a812e32</sub> <!-- greptile_other_comments_section --> <sub>(2/5) Greptile learns from your feedback when you react with thumbs up/down!</sub> <!-- /greptile_comment -->

Most Similar PRs