Prompt API for bots & scripts

Send a prompt, get a cited answer. Use your MCP token (askchannelai_...) as a Bearer token and POST to one REST endpoint. You always get the Markdown answer + structured citations; add a platform (telegram, whatsapp, slack) to also get a ready-to-send renderedfield in that app's own format — Telegram HTML or Slack/WhatsApp mrkdwn. The server does the formatting. Create a token on the Tokens page; the examples below are prefilled with your latest token.

Try it

platform

Public API and MCP access is available on Free and Premium. Personal tokens require Premium. Sign in and create a token on the Tokens page.

Code examples

TypeScript SDK — @askchannelai/sdk (recommended)

// npm i @askchannelai/sdk
import { createAskChannelClient } from '@askchannelai/sdk';

const ac = createAskChannelClient({ token: 'askchannelai_your_full_secret_here' }); // your askchannelai_… token

// Ask a cited question. Pass a platform to get a ready-to-send "rendered" field.
const res = await ac.ask({
  channel: '@apple',                 // @handle (with/without @) or a UC… id
  question: 'What is the latest MacBook Pro model?',
  platform: 'telegram',              // telegram | whatsapp | slack
});
console.log(res.answer);             // clean prose (always)
console.log(res.citations);          // [{ videoTitle, startTime, url, ... }] (always)
console.log(res.rendered);           // ready to send — HTML for telegram, etc.

// Search the channels you can ask — e.g. to build a picker / dropdown:
const channels = await ac.searchChannels('apple'); // [{ id, title, handle, ... }]

The official, dependency-free SDK wraps this endpoint and channel search. For Telegram, @askchannelai/telegram layers on the inline channel-picker, stateless reply-recovery, and ready-to-send HTML — see the inline-picker snippet below. npm · source · full Telegram bot example. Prefer raw HTTP? The same calls below work in any language.

cURL (prompt a channel)

curl -X POST 'https://askchannel.ai/api/v1/channel/qa/@apple' \
  -H 'Authorization: Bearer askchannelai_your_full_secret_here' \
  -H 'Content-Type: application/json' \
  -d '{
    "question": "What is the latest Macbook Pro model and what upgrades does it have?",
    "platform": "telegram"
  }' | jq

Node / fetch (minimal)

// One call. Add "platform" to get a ready-to-send "rendered" field.
const res = await fetch('https://askchannel.ai/api/v1/channel/qa/@apple', {
  method: 'POST',
  headers: { Authorization: 'Bearer askchannelai_your_full_secret_here', 'Content-Type': 'application/json' },
  body: JSON.stringify({ question: 'What is the latest Macbook Pro model?', platform: 'telegram' }),
});
const data = await res.json();
console.log(data.answer);     // raw Markdown (always returned)
console.log(data.citations);  // structured [{ videoTitle, startTime, url, ... }] (always)
console.log(data.rendered);   // formatted for "platform" — HTML here

Pass platform in the body and the server returns a ready-to-send renderedfield — no formatting code needed. You still set the platform's own send flag: Telegram parse_mode:'HTML', Slack mrkdwn:true (default); WhatsApp reads the markup directly.

Telegram bot

// npm i node-telegram-bot-api
import TelegramBot from 'node-telegram-bot-api';

const bot = new TelegramBot(process.env.TELEGRAM_TOKEN, { polling: true });
const PROMPT_URL = 'https://askchannel.ai/api/v1/channel/qa/@apple';

bot.on('message', async (msg) => {
  const question = (msg.text || '').trim();
  if (!question) return;
  const res = await fetch(PROMPT_URL, {
    method: 'POST',
    headers: { Authorization: 'Bearer askchannelai_your_full_secret_here', 'Content-Type': 'application/json' },
    body: JSON.stringify({ question, platform: 'telegram' }),
  });
  const data = await res.json();
  if (data.error) return bot.sendMessage(msg.chat.id, 'Prompt failed: ' + data.error);
  // data.rendered is ready-to-send HTML — just set parse_mode.
  await bot.sendMessage(msg.chat.id, data.rendered, { parse_mode: 'HTML', disable_web_page_preview: true });
});

Telegram bot — inline channel-picker (@askchannelai/telegram)

// npm i @askchannelai/sdk @askchannelai/telegram grammy
import { Bot } from 'grammy';
import { createAskChannelClient } from '@askchannelai/sdk';
import { buildInlineResults, channelRefFromPickReply, qaErrorMessage } from '@askchannelai/telegram';

const ac = createAskChannelClient({ token: 'askchannelai_your_full_secret_here' });
const bot = new Bot(process.env.TELEGRAM_TOKEN);

// @yourbot <name> → searchable dropdown of indexed channels
bot.on('inline_query', async (ctx) => {
  const channels = await ac.searchChannels(ctx.inlineQuery.query);
  await ctx.answerInlineQuery(buildInlineResults(channels));
});

// A reply to a picked channel = the question for it (stateless — the ref rides in the prompt)
bot.on('message:text', async (ctx) => {
  const r = ctx.message.reply_to_message;
  const ref = r && channelRefFromPickReply({ via_bot: r.via_bot, entities: r.entities }, ctx.me.username);
  if (!ref) return;
  try {
    const res = await ac.ask({ channel: ref, question: ctx.message.text, platform: 'telegram' });
    await ctx.reply(res.rendered, { parse_mode: 'HTML' });
  } catch (e) {
    await ctx.reply(qaErrorMessage(ref, e), { parse_mode: 'HTML' });
  }
});

bot.start();

A searchable channel dropdown in a few lines: buildInlineResults renders the picker, channelRefFromPickReply recovers the picked channel from the user's reply, and qaErrorMessage formats failures. Full runnable bot in the example.

WhatsApp (Twilio)

// Twilio WhatsApp webhook (Express)
import express from 'express';
import twilio from 'twilio';

const app = express();
app.use(express.urlencoded({ extended: false }));
const PROMPT_URL = 'https://askchannel.ai/api/v1/channel/qa/@apple';

app.post('/whatsapp', async (req, res) => {
  const question = (req.body.Body || '').trim();
  const r = await fetch(PROMPT_URL, {
    method: 'POST',
    headers: { Authorization: 'Bearer askchannelai_your_full_secret_here', 'Content-Type': 'application/json' },
    body: JSON.stringify({ question, platform: 'whatsapp' }),
  });
  const data = await r.json();
  const twiml = new twilio.twiml.MessagingResponse();
  twiml.message(data.rendered); // WhatsApp reads the markup directly
  res.type('text/xml').send(twiml.toString());
});

app.listen(3000);

Slack (Bolt)

// npm i @slack/bolt
import pkg from '@slack/bolt';
const { App } = pkg;

const app = new App({ token: process.env.SLACK_BOT_TOKEN, signingSecret: process.env.SLACK_SIGNING_SECRET });
const PROMPT_URL = 'https://askchannel.ai/api/v1/channel/qa/@apple';

app.event('app_mention', async ({ event, say }) => {
  const question = event.text.replace(/<@[^>]+>/g, '').trim();
  const r = await fetch(PROMPT_URL, {
    method: 'POST',
    headers: { Authorization: 'Bearer askchannelai_your_full_secret_here', 'Content-Type': 'application/json' },
    body: JSON.stringify({ question, platform: 'slack' }),
  });
  const data = await r.json();
  await say({ text: data.rendered, mrkdwn: true }); // mrkdwn is Slack's default
});

(async () => { await app.start(); })();

Endpoint

POST /api/v1/channel/qa/:channelId

Body: { question: string, platform?: 'telegram' | 'whatsapp' | 'slack' }
Response: { answer, citations: [{ videoId, videoTitle, startTime, url, ... }], rendered? }
Citations include YouTube deep links with timestamps. The rendered field is present only when platform is set (HTML for telegram, mrkdwn for slack/whatsapp).

Rate limits and daily question quotas apply (tied to the token owner's account). Each request answers a new question. This API returns text and citations; the web app's Ask video playlists are not exposed through this endpoint or the current MCP tools.