Merge pull request #1260 from ohmont/feat/optimize-slack-get-channels

Modify getChannels method in server-slack to support fetching channels by IDs from env
This commit is contained in:
Tadas Antanavicius 2025-04-14 09:13:43 -07:00 • committed by GitHub
commit 1ba26786c4
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
2 changed files with 56 additions and 18 deletions

View file

@ -5,7 +5,7 @@ MCP Server for the Slack API, enabling Claude to interact with Slack workspaces.
## Tools ## Tools
1. `slack_list_channels` 1. `slack_list_channels`
- List public channels in the workspace - List public or pre-defined channels in the workspace
- Optional inputs: - Optional inputs:
- `limit` (number, default: 100, max: 200): Maximum number of channels to return - `limit` (number, default: 100, max: 200): Maximum number of channels to return
- `cursor` (string): Pagination cursor for next page - `cursor` (string): Pagination cursor for next page
@ -102,7 +102,8 @@ Add the following to your `claude_desktop_config.json`:
], ],
"env": { "env": {
"SLACK_BOT_TOKEN": "xoxb-your-bot-token", "SLACK_BOT_TOKEN": "xoxb-your-bot-token",
"SLACK_TEAM_ID": "T01234567" "SLACK_TEAM_ID": "T01234567",
"SLACK_CHANNEL_IDS": "C01234567, C76543210"
} }
} }
} }
@ -124,17 +125,26 @@ Add the following to your `claude_desktop_config.json`:
"SLACK_BOT_TOKEN", "SLACK_BOT_TOKEN",
"-e", "-e",
"SLACK_TEAM_ID", "SLACK_TEAM_ID",
"-e",
"SLACK_CHANNEL_IDS",
"mcp/slack" "mcp/slack"
], ],
"env": { "env": {
"SLACK_BOT_TOKEN": "xoxb-your-bot-token", "SLACK_BOT_TOKEN": "xoxb-your-bot-token",
"SLACK_TEAM_ID": "T01234567" "SLACK_TEAM_ID": "T01234567",
"SLACK_CHANNEL_IDS": "C01234567, C76543210"
} }
} }
} }
} }
``` ```
### Environment Variables
1. `SLACK_BOT_TOKEN`: Required. The Bot User OAuth Token starting with `xoxb-`.
2. `SLACK_TEAM_ID`: Required. Your Slack workspace ID starting with `T`.
3. `SLACK_CHANNEL_IDS`: Optional. Comma-separated list of channel IDs to limit channel access (e.g., "C01234567, C76543210"). If not set, all public channels will be listed.
### Troubleshooting ### Troubleshooting
If you encounter permission errors, verify that: If you encounter permission errors, verify that:

View file

@ -53,7 +53,7 @@ interface GetUserProfileArgs {
// Tool definitions // Tool definitions
const listChannelsTool: Tool = { const listChannelsTool: Tool = {
name: "slack_list_channels", name: "slack_list_channels",
description: "List public channels in the workspace with pagination", description: "List public or pre-defined channels in the workspace with pagination",
inputSchema: { inputSchema: {
type: "object", type: "object",
properties: { properties: {
@ -221,23 +221,51 @@ class SlackClient {
} }
async getChannels(limit: number = 100, cursor?: string): Promise<any> { async getChannels(limit: number = 100, cursor?: string): Promise<any> {
const params = new URLSearchParams({ const predefinedChannelIds = process.env.SLACK_CHANNEL_IDS;
types: "public_channel", if (!predefinedChannelIds) {
exclude_archived: "true", const params = new URLSearchParams({
limit: Math.min(limit, 200).toString(), types: "public_channel",
team_id: process.env.SLACK_TEAM_ID!, exclude_archived: "true",
}); limit: Math.min(limit, 200).toString(),
team_id: process.env.SLACK_TEAM_ID!,
});
if (cursor) { if (cursor) {
params.append("cursor", cursor); params.append("cursor", cursor);
}
const response = await fetch(
`https://slack.com/api/conversations.list?${params}`,
{ headers: this.botHeaders },
);
return response.json();
} }
const response = await fetch( const predefinedChannelIdsArray = predefinedChannelIds.split(",").map((id: string) => id.trim());
`https://slack.com/api/conversations.list?${params}`, const channels = [];
{ headers: this.botHeaders },
);
return response.json(); for (const channelId of predefinedChannelIdsArray) {
const params = new URLSearchParams({
channel: channelId,
});
const response = await fetch(
`https://slack.com/api/conversations.info?${params}`,
{ headers: this.botHeaders }
);
const data = await response.json();
if (data.ok && data.channel && !data.channel.is_archived) {
channels.push(data.channel);
}
}
return {
ok: true,
channels: channels,
response_metadata: { next_cursor: "" },
};
} }
async postMessage(channel_id: string, text: string): Promise<any> { async postMessage(channel_id: string, text: string): Promise<any> {