fix(slack): stop leaking bot token into /api/auth.test request body (#94574)

* fix(slack): stop leaking bot token into /api/auth.test request body

The bot token is already passed as an `Authorization` header,
so we don't need to send it in the request body when calling `/api/auth.test`.

See [Slack API documentation](https://api.slack.com/methods/auth.test).

Also, showing with `curl` that the bot token is not needed in the request body when passed as an `Authorization` header when calling `/api/auth.test`:
```
curl -X POST https://slack.com:443/api/auth.test -H "Authorization: Bearer xoxb-..."
{"ok":true,"url":"https://xcoulonworkspace.slack.com/","team":"xcoulon",...}
```

Signed-off-by: Xavier Coulon <xcoulon@redhat.com>

* add test for slack auth.test token handling

verify that the bot token is not passed in the request body when calling `/api/auth.test`.

Signed-off-by: Xavier Coulon <xcoulon@redhat.com>

---------

Signed-off-by: Xavier Coulon <xcoulon@redhat.com>
This commit is contained in:
Xavier Coulon
2026-06-19 00:09:37 +02:00
committed by GitHub
parent 73cdb78a1e
commit fbc12e0879
2 changed files with 32 additions and 1 deletions

View File

@@ -0,0 +1,31 @@
// Slack tests cover auth.test token handling during provider boot.
import { beforeEach, describe, expect, it } from "vitest";
import {
getSlackClient,
resetSlackTestState,
startSlackMonitor,
stopSlackMonitor,
} from "../monitor.test-helpers.js";
const { monitorSlackProvider } = await import("./provider.js");
beforeEach(() => {
resetSlackTestState();
});
describe("auth.test boot call", () => {
it("does not pass the bot token in the call arguments", async () => {
const monitor = startSlackMonitor(monitorSlackProvider);
await stopSlackMonitor(monitor);
const client = getSlackClient();
expect(client.auth.test).toHaveBeenCalledTimes(1);
// The SDK serializes every property from the call argument into the POST
// body. Passing { token } would leak the bot token into the request
// payload alongside the Authorization header.
const firstArg = client.auth.test.mock.calls[0]?.[0] as Record<string, unknown> | undefined;
if (firstArg != null) {
expect(firstArg).not.toHaveProperty("token");
}
});
});

View File

@@ -296,7 +296,7 @@ export async function monitorSlackProvider(opts: MonitorSlackOpts = {}) {
let authTestFailed = false;
let authTestError: string | undefined;
try {
const auth = await app.client.auth.test({ token: botToken });
const auth = await app.client.auth.test();
botUserId = auth.user_id ?? "";
botId = (auth as { bot_id?: string }).bot_id ?? "";
teamId = auth.team_id ?? "";