KeiSeiKit-1.0/_ts_packages/packages/youtube-adapter/src/tools.ts
Parfii-bot 0be354a920 KeiSeiKit-public — clean state
Single-commit clean baseline after security scrub of niche-tells,
project codenames, internal jargon, and contributor-email leaks.

Contents:
- 100 Rust crates (_primitives/_rust/)
- 37 agent manifests (_manifests/) + generated specs (_generated/)
- 67 user-invocable skills (skills/)
- 33 hooks (hooks/)
- Composition blocks (_blocks/)
- Documentation (docs/, README.md)
- TS adapter packages (_ts_packages/)
- Assembler (_assembler/)
- Roles (_roles/)
- Templates (_templates/)
- Forgejo CI (.forgejo/)

Author: Denis Parfionovich <info@greendragon.info>

License: see LICENSE.
2026-05-01 12:09:03 +08:00

87 lines
2.6 KiB
TypeScript

import { z } from "zod";
import { YouTubeClient } from "./client.js";
import {
NewVideosArgs,
SearchArgs,
SubscriptionsArgs,
VideoIdArgs,
type TranscriptLine,
type VideoStats,
type VideoSummary,
} from "./types.js";
export interface YouTubeTool {
name: string;
description: string;
inputSchema: z.ZodObject<Record<string, z.ZodTypeAny>>;
handler: (args: Record<string, unknown>) => Promise<string>;
}
export function buildYouTubeTools(client: YouTubeClient): YouTubeTool[] {
return [
{
name: "youtube_subscriptions",
description: "List the authenticated user's channel subscriptions.",
inputSchema: SubscriptionsArgs,
handler: async (raw) => {
const args = SubscriptionsArgs.parse(raw);
return formatList(await client.subscriptions(args.max));
},
},
{
name: "youtube_new_videos",
description: "Latest videos from a given channel (optional --since ISO8601).",
inputSchema: NewVideosArgs,
handler: async (raw) => {
const args = NewVideosArgs.parse(raw);
return formatList(await client.newVideos(args.channel_id, args.since, args.max));
},
},
{
name: "youtube_search",
description: "Search YouTube for a query string.",
inputSchema: SearchArgs,
handler: async (raw) => {
const args = SearchArgs.parse(raw);
return formatList(await client.search(args.query, args.max));
},
},
{
name: "youtube_transcript",
description: "Fetch the transcript (captions) of a video as plain text.",
inputSchema: VideoIdArgs,
handler: async (raw) => {
const args = VideoIdArgs.parse(raw);
return formatTranscript(await client.transcript(args.video_id));
},
},
{
name: "youtube_video_stats",
description: "View/like/comment counts for a given video.",
inputSchema: VideoIdArgs,
handler: async (raw) => {
const args = VideoIdArgs.parse(raw);
return formatStats(await client.stats(args.video_id));
},
},
];
}
function formatList(items: VideoSummary[]): string {
if (items.length === 0) return "No results.";
return items.map((v) => `${v.videoId} | ${v.channel ?? "?"} | ${v.title ?? "?"}`).join("\n");
}
function formatTranscript(lines: TranscriptLine[]): string {
if (lines.length === 0) return "No transcript available.";
return lines.map((l) => l.text).join(" ");
}
function formatStats(s: VideoStats): string {
return [
`video: ${s.videoId}`,
`views: ${s.viewCount ?? "?"}`,
`likes: ${s.likeCount ?? "?"}`,
`comments: ${s.commentCount ?? "?"}`,
].join("\n");
}