discourse_list_chat_channels
List public chat channels with details like title, description, and member counts. Filter by name, status, or use pagination to browse available channels.
Instructions
List all public chat channels visible to the current user. Returns channel information including title, description, and member counts.
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| filter | No | Filter channels by name/slug | |
| limit | No | Number of channels to return (default: 25, max: 100) | |
| offset | No | Pagination offset (default: 0) | |
| status | No | Filter by channel status (e.g., 'open', 'closed', 'archived') |
Implementation Reference
- The handler function that implements the core logic of the 'discourse_list_chat_channels' tool. It fetches chat channels from the Discourse chat API using the provided filters, formats them into a structured markdown response including channel details, pagination info, and handles errors.async ({ filter, limit = 25, offset = 0, status }, _extra: any) => { try { const { base, client } = ctx.siteState.ensureSelectedSite(); // Build query parameters const params = new URLSearchParams(); if (filter) params.append("filter", filter); params.append("limit", String(limit)); params.append("offset", String(offset)); if (status) params.append("status", status); const url = `/chat/api/channels?${params.toString()}`; const data = (await client.get(url)) as any; const channels: any[] = data?.channels || []; if (channels.length === 0) { return { content: [{ type: "text", text: "No chat channels found." }] }; } const lines: string[] = []; lines.push(`# Chat Channels (${channels.length} shown)`); lines.push(""); for (const channel of channels) { const title = channel.title || `Channel ${channel.id}`; const slug = channel.slug || String(channel.id); const description = channel.description || ""; const membersCount = channel.memberships_count || 0; const statusText = channel.status || "open"; lines.push(`## ${title}`); lines.push(`- **ID**: ${channel.id}`); lines.push(`- **Slug**: ${slug}`); lines.push(`- **Status**: ${statusText}`); lines.push(`- **Members**: ${membersCount}`); if (description) { lines.push(`- **Description**: ${description}`); } lines.push(`- **URL**: ${base}/chat/c/${slug}/${channel.id}`); lines.push(""); } // Add pagination info if (data?.meta?.load_more_url) { lines.push(`_More channels available. Use offset=${offset + limit} to load next page._`); } return { content: [{ type: "text", text: lines.join("\n") }] }; } catch (e: any) { return { content: [{ type: "text", text: `Failed to list chat channels: ${e?.message || String(e)}` }], isError: true }; }
- Zod schema defining the input parameters for the discourse_list_chat_channels tool, including optional filter, limit, offset, and status.const schema = z.object({ filter: z.string().optional().describe("Filter channels by name/slug"), limit: z.number().int().min(1).max(100).optional().describe("Number of channels to return (default: 25, max: 100)"), offset: z.number().int().min(0).optional().describe("Pagination offset (default: 0)"), status: z.string().optional().describe("Filter by channel status (e.g., 'open', 'closed', 'archived')"), }).strict();
- src/tools/builtin/list_chat_channels.ts:12-75 (registration)Registers the 'discourse_list_chat_channels' tool with the MCP server, specifying name, title, description, input schema, and handler function.server.registerTool( "discourse_list_chat_channels", { title: "List Chat Channels", description: "List all public chat channels visible to the current user. Returns channel information including title, description, and member counts.", inputSchema: schema.shape, }, async ({ filter, limit = 25, offset = 0, status }, _extra: any) => { try { const { base, client } = ctx.siteState.ensureSelectedSite(); // Build query parameters const params = new URLSearchParams(); if (filter) params.append("filter", filter); params.append("limit", String(limit)); params.append("offset", String(offset)); if (status) params.append("status", status); const url = `/chat/api/channels?${params.toString()}`; const data = (await client.get(url)) as any; const channels: any[] = data?.channels || []; if (channels.length === 0) { return { content: [{ type: "text", text: "No chat channels found." }] }; } const lines: string[] = []; lines.push(`# Chat Channels (${channels.length} shown)`); lines.push(""); for (const channel of channels) { const title = channel.title || `Channel ${channel.id}`; const slug = channel.slug || String(channel.id); const description = channel.description || ""; const membersCount = channel.memberships_count || 0; const statusText = channel.status || "open"; lines.push(`## ${title}`); lines.push(`- **ID**: ${channel.id}`); lines.push(`- **Slug**: ${slug}`); lines.push(`- **Status**: ${statusText}`); lines.push(`- **Members**: ${membersCount}`); if (description) { lines.push(`- **Description**: ${description}`); } lines.push(`- **URL**: ${base}/chat/c/${slug}/${channel.id}`); lines.push(""); } // Add pagination info if (data?.meta?.load_more_url) { lines.push(`_More channels available. Use offset=${offset + limit} to load next page._`); } return { content: [{ type: "text", text: lines.join("\n") }] }; } catch (e: any) { return { content: [{ type: "text", text: `Failed to list chat channels: ${e?.message || String(e)}` }], isError: true }; } } );
- src/tools/registry.ts:58-58 (registration)Calls the registerListChatChannels function as part of registering all builtin tools in the MCP server registry.registerListChatChannels(server, ctx, { allowWrites: false });