ants-move 0.0.1 → 0.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +23 -3
- package/dist/index.d.ts +31 -0
- package/dist/index.js +443 -0
- package/dist/index.js.map +1 -1
- package/package.json +2 -1
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/index.ts","../src/cli.ts","../src/hn/command.ts","../src/output.ts","../src/hn/output.ts","../src/hn/types.ts","../src/hn/service.ts","../src/hn/runtime.ts","../src/36kr/command.ts","../src/36kr/output.ts","../src/36kr/types.ts","../src/36kr/service.ts","../src/36kr/runtime.ts","../src/toutiao/command.ts","../src/toutiao/output.ts","../src/toutiao/types.ts","../src/toutiao/service.ts","../src/toutiao/runtime.ts"],"sourcesContent":["import { realpathSync } from 'node:fs';\nimport { fileURLToPath } from 'node:url';\n\nimport { createCli } from './cli.js';\n\nexport { createCli } from './cli.js';\nexport type { CliIo, CliRunner, CreateCliOptions } from './cli.js';\n\nexport function isMainEntrypoint(moduleUrl: string, argv: string[]): boolean {\n const scriptPath = argv[1];\n\n if (!scriptPath) {\n return false;\n }\n\n return realpathSync(fileURLToPath(moduleUrl)) === realpathSync(scriptPath);\n}\n\n/* v8 ignore start */\nif (isMainEntrypoint(import.meta.url, process.argv)) {\n const cli = createCli();\n void cli.run(process.argv.slice(2)).then((exitCode) => {\n process.exitCode = exitCode;\n });\n}\n/* v8 ignore end */\n","import { Command, CommanderError } from 'commander';\nimport { ZodError } from 'zod';\n\nimport {\n handleHackerNewsCommandError,\n registerHackerNewsCommands\n} from './hn/command.js';\nimport {\n createDefaultHackerNewsRuntime,\n type HackerNewsRuntime\n} from './hn/runtime.js';\nimport {\n handleKr36CommandError,\n registerKr36Commands\n} from './36kr/command.js';\nimport {\n createDefaultKr36Runtime,\n type Kr36Runtime\n} from './36kr/runtime.js';\nimport {\n handleToutiaoCommandError,\n registerToutiaoCommands\n} from './toutiao/command.js';\nimport {\n createDefaultToutiaoRuntime,\n type ToutiaoRuntime\n} from './toutiao/runtime.js';\n\nexport interface CliIo {\n stderr: (value: string) => void;\n stdout: (value: string) => void;\n}\n\nexport interface CliRunner {\n run: (args: string[]) => Promise<number>;\n}\n\nexport interface CreateCliOptions extends Partial<CliIo> {\n hackerNewsRuntime?: HackerNewsRuntime;\n kr36Runtime?: Kr36Runtime;\n toutiaoRuntime?: ToutiaoRuntime;\n}\n\nexport function createCli(options: CreateCliOptions = {}): CliRunner {\n const io: CliIo = {\n stderr: options.stderr ?? ((value) => process.stderr.write(value)),\n stdout: options.stdout ?? ((value) => process.stdout.write(value))\n };\n const program = new Command()\n .name('ants')\n .description('Move data between systems with composable collectors.')\n .showHelpAfterError()\n .exitOverride();\n\n program.configureOutput({\n outputError: () => undefined,\n writeErr: () => undefined,\n writeOut: (value) => io.stdout(value)\n });\n\n registerKr36Commands(program, {\n runtime: options.kr36Runtime ?? createDefaultKr36Runtime(),\n stderr: io.stderr,\n stdout: io.stdout\n });\n registerHackerNewsCommands(program, {\n runtime: options.hackerNewsRuntime ?? createDefaultHackerNewsRuntime(),\n stderr: io.stderr,\n stdout: io.stdout\n });\n registerToutiaoCommands(program, {\n runtime: options.toutiaoRuntime ?? createDefaultToutiaoRuntime(),\n stderr: io.stderr,\n stdout: io.stdout\n });\n\n return {\n run: async (args) => {\n try {\n await program.parseAsync(args, { from: 'user' });\n return 0;\n } catch (error) {\n if (error instanceof CommanderError && error.exitCode === 0) {\n return 0;\n }\n\n const toutiaoExitCode = handleToutiaoCommandError(error, io);\n if (toutiaoExitCode !== undefined) {\n return toutiaoExitCode;\n }\n\n const hackerNewsExitCode = handleHackerNewsCommandError(error, io);\n if (hackerNewsExitCode !== undefined) {\n return hackerNewsExitCode;\n }\n\n const kr36ExitCode = handleKr36CommandError(error, io);\n if (kr36ExitCode !== undefined) {\n return kr36ExitCode;\n }\n\n if (error instanceof ZodError || error instanceof CommanderError) {\n const message = error instanceof ZodError\n ? error.issues[0]?.message ?? 'Invalid command arguments.'\n : error.message;\n writeCliError(io, 'INVALID_ARGUMENT', message);\n return 2;\n }\n\n writeCliError(\n io,\n 'INTERNAL_ERROR',\n 'An unexpected internal error occurred.'\n );\n return 1;\n }\n }\n };\n}\n\nfunction writeCliError(io: CliIo, code: string, message: string): void {\n io.stderr(`${JSON.stringify({\n ok: false,\n error: {\n code,\n message\n }\n }, null, 2)}\\n`);\n}\n","import type { Command } from 'commander';\nimport { z } from 'zod';\n\nimport {\n renderHackerNewsCommandErrorAsJson,\n renderHackerNewsSearchAsJson,\n renderHackerNewsSearchAsTable,\n renderHackerNewsStoriesAsJson,\n renderHackerNewsStoriesAsTable\n} from './output.js';\nimport type { HackerNewsRuntime } from './runtime.js';\nimport { HackerNewsService } from './service.js';\nimport { HackerNewsCommandError, type HackerNewsStorySource } from './types.js';\n\nexport interface HackerNewsCommandDependencies {\n runtime: HackerNewsRuntime;\n stderr: (value: string) => void;\n stdout: (value: string) => void;\n}\n\nconst storiesOptionsSchema = z.object({\n format: z.enum(['json', 'table']).default('json'),\n limit: z.number().int().default(30),\n table: z.boolean().optional()\n});\n\nconst searchOptionsSchema = z.object({\n format: z.enum(['json', 'table']).default('json'),\n limit: z.number().int().default(30),\n sort: z.enum(['relevance', 'date']).default('relevance'),\n table: z.boolean().optional()\n});\n\nexport function registerHackerNewsCommands(\n program: Command,\n dependencies: HackerNewsCommandDependencies\n): void {\n const hn = program\n .command('hn')\n .alias('hackernews')\n .description('Fetch Hacker News stories and search results.');\n const service = new HackerNewsService({ runtime: dependencies.runtime });\n\n for (const source of ['top', 'new', 'best'] as const) {\n hn.command(source)\n .option('--limit <limit>', 'number of stories to fetch', parseLimit, 30)\n .option('--format <format>', 'output format', 'json')\n .option('-t, --table', 'render as a table')\n .action(async (options) => {\n const parsed = storiesOptionsSchema.parse(applyTableShortcut(options));\n const result = await service.stories({\n limit: parsed.limit,\n source\n });\n dependencies.stdout(\n parsed.format === 'table'\n ? `${renderHackerNewsStoriesAsTable(result)}\\n`\n : `${renderHackerNewsStoriesAsJson(result)}\\n`\n );\n });\n }\n\n hn.command('search')\n .argument('<query>', 'search query')\n .option('--limit <limit>', 'number of search results to fetch', parseLimit, 30)\n .option('--sort <sort>', 'search sort: relevance or date', 'relevance')\n .option('--format <format>', 'output format', 'json')\n .option('-t, --table', 'render as a table')\n .action(async (query, options) => {\n const parsed = searchOptionsSchema.parse(applyTableShortcut(options));\n const result = await service.search({\n limit: parsed.limit,\n query,\n sort: parsed.sort\n });\n dependencies.stdout(\n parsed.format === 'table'\n ? `${renderHackerNewsSearchAsTable(result)}\\n`\n : `${renderHackerNewsSearchAsJson(result)}\\n`\n );\n });\n}\n\nexport function handleHackerNewsCommandError(\n error: unknown,\n dependencies: Pick<HackerNewsCommandDependencies, 'stderr'>\n): number | undefined {\n if (error instanceof HackerNewsCommandError) {\n dependencies.stderr(\n `${renderHackerNewsCommandErrorAsJson(error.code, error.message, error.details)}\\n`\n );\n return error.exitCode;\n }\n\n return undefined;\n}\n\nfunction parseLimit(value: string): number {\n const parsed = Number(value);\n\n if (!Number.isInteger(parsed)) {\n throw new HackerNewsCommandError(\n 'HN_INVALID_LIMIT',\n 'Hacker News limit must be an integer between 1 and 100.',\n 2,\n {\n limit: value\n }\n );\n }\n\n return parsed;\n}\n\nfunction applyTableShortcut<T extends { format: string; table?: boolean }>(options: T): T & {\n format: 'json' | 'table';\n} {\n if (options.table) {\n return {\n ...options,\n format: 'table'\n };\n }\n\n return {\n ...options,\n format: options.format as 'json' | 'table'\n };\n}\n","import { stripVTControlCharacters } from 'node:util';\n\nimport { table } from 'table';\n\nfunction sanitizeTableCell(value: unknown): string {\n return stripVTControlCharacters(String(value))\n .replace(/[\\u0000-\\u001f\\u007f-\\u009f]+/g, ' ')\n .replace(/ +/g, ' ')\n .trim();\n}\n\nexport function renderSafeTable(rows: readonly (readonly unknown[])[]): string {\n return table(rows.map((row) => row.map(sanitizeTableCell)));\n}\n","import { renderSafeTable } from '../output.js';\nimport type { HackerNewsSearchResult, HackerNewsStoriesResult } from './types.js';\n\nexport function renderHackerNewsStoriesAsJson(result: HackerNewsStoriesResult): string {\n return JSON.stringify(\n {\n ok: true,\n data: result\n },\n null,\n 2\n );\n}\n\nexport function renderHackerNewsStoriesAsTable(result: HackerNewsStoriesResult): string {\n return renderSafeTable([\n ['id', 'title', 'author', 'score', 'comments', 'time', 'url'],\n ...result.items.map((item) => [\n String(item.id),\n item.title,\n item.author ?? '',\n item.score === undefined ? '' : String(item.score),\n item.commentCount === undefined ? '' : String(item.commentCount),\n item.time?.iso ?? '',\n item.url\n ])\n ]);\n}\n\nexport function renderHackerNewsSearchAsJson(result: HackerNewsSearchResult): string {\n return JSON.stringify(\n {\n ok: true,\n data: result\n },\n null,\n 2\n );\n}\n\nexport function renderHackerNewsSearchAsTable(result: HackerNewsSearchResult): string {\n return renderSafeTable([\n ['id', 'title', 'author', 'score', 'comments', 'time', 'url'],\n ...result.items.map((item) => [\n String(item.id),\n item.title,\n item.author ?? '',\n item.score === undefined ? '' : String(item.score),\n item.commentCount === undefined ? '' : String(item.commentCount),\n item.time?.iso ?? '',\n item.url\n ])\n ]);\n}\n\nexport function renderHackerNewsCommandErrorAsJson(\n code: string,\n message: string,\n details?: unknown\n): string {\n return JSON.stringify(\n {\n ok: false,\n error: {\n code,\n message,\n ...(details === undefined ? {} : { details })\n }\n },\n null,\n 2\n );\n}\n","export type HackerNewsStorySource = 'top' | 'new' | 'best';\nexport type HackerNewsSearchSort = 'relevance' | 'date';\n\nexport interface HackerNewsItem {\n author?: string;\n commentCount?: number;\n id: number;\n score?: number;\n text?: string;\n time?: {\n iso: string;\n seconds: number;\n };\n title: string;\n type: 'story';\n url: string;\n}\n\nexport interface HackerNewsStoriesRuntimeResult {\n items: HackerNewsItem[];\n source: HackerNewsStorySource;\n}\n\nexport interface HackerNewsStoriesResult extends HackerNewsStoriesRuntimeResult {\n meta: {\n limit: number;\n totalItems: number;\n };\n}\n\nexport interface HackerNewsSearchRuntimeResult {\n items: HackerNewsItem[];\n query: string;\n}\n\nexport interface HackerNewsSearchResult extends HackerNewsSearchRuntimeResult {\n meta: {\n limit: number;\n sort: HackerNewsSearchSort;\n totalItems: number;\n };\n}\n\nexport class HackerNewsCommandError extends Error {\n constructor(\n public readonly code: string,\n message: string,\n public readonly exitCode: number,\n public readonly details?: unknown\n ) {\n super(message);\n this.name = 'HackerNewsCommandError';\n }\n}\n","import type { HackerNewsRuntime } from './runtime.js';\nimport {\n HackerNewsCommandError,\n type HackerNewsSearchResult,\n type HackerNewsSearchSort,\n type HackerNewsStoriesResult,\n type HackerNewsStorySource\n} from './types.js';\n\nconst SUPPORTED_SOURCES = new Set<HackerNewsStorySource>(['top', 'new', 'best']);\n\nexport class HackerNewsService {\n constructor(private readonly dependencies: { runtime: HackerNewsRuntime }) {}\n\n async stories(options: {\n limit?: number;\n source: string;\n }): Promise<HackerNewsStoriesResult> {\n const source = parseSource(options.source);\n const limit = normalizeLimit(options.limit);\n const runtimeResult = await this.dependencies.runtime.fetchStories({\n limit,\n source\n });\n\n return {\n ...runtimeResult,\n meta: {\n limit,\n totalItems: runtimeResult.items.length\n }\n };\n }\n\n async search(options: {\n limit?: number;\n query: string;\n sort?: HackerNewsSearchSort;\n }): Promise<HackerNewsSearchResult> {\n const query = normalizeQuery(options.query);\n const limit = normalizeLimit(options.limit);\n const sort = options.sort ?? 'relevance';\n const runtimeResult = await this.dependencies.runtime.fetchSearch({\n limit,\n query,\n sort\n });\n\n return {\n ...runtimeResult,\n meta: {\n limit,\n sort,\n totalItems: runtimeResult.items.length\n }\n };\n }\n}\n\nfunction parseSource(source: string): HackerNewsStorySource {\n if (SUPPORTED_SOURCES.has(source as HackerNewsStorySource)) {\n return source as HackerNewsStorySource;\n }\n\n throw new HackerNewsCommandError(\n 'HN_INVALID_SOURCE',\n 'Hacker News list only supports top, new, and best.',\n 2,\n {\n source,\n supportedSources: [...SUPPORTED_SOURCES]\n }\n );\n}\n\nfunction normalizeLimit(limit: number | undefined): number {\n const value = limit ?? 30;\n\n if (!Number.isInteger(value) || value < 1 || value > 100) {\n throw new HackerNewsCommandError(\n 'HN_INVALID_LIMIT',\n 'Hacker News limit must be an integer between 1 and 100.',\n 2,\n {\n limit: value\n }\n );\n }\n\n return value;\n}\n\nfunction normalizeQuery(query: string): string {\n const value = query.trim();\n\n if (value.length === 0) {\n throw new HackerNewsCommandError(\n 'HN_INVALID_QUERY',\n 'Hacker News search query must not be empty.',\n 2\n );\n }\n\n return value;\n}\n","import {\n HackerNewsCommandError,\n type HackerNewsItem,\n type HackerNewsSearchRuntimeResult,\n type HackerNewsSearchSort,\n type HackerNewsStoriesRuntimeResult,\n type HackerNewsStorySource\n} from './types.js';\n\nexport interface HackerNewsRuntime {\n fetchSearch: (options: {\n limit: number;\n query: string;\n sort: HackerNewsSearchSort;\n }) => Promise<HackerNewsSearchRuntimeResult>;\n fetchStories: (options: {\n limit: number;\n source: HackerNewsStorySource;\n }) => Promise<HackerNewsStoriesRuntimeResult>;\n}\n\nexport interface HackerNewsRuntimeOptions {\n detailConcurrency?: number;\n fetch?: typeof fetch;\n maxResponseBytes?: number;\n requestTimeoutMs?: number;\n}\n\nconst FIREBASE_BASE_URL = 'https://hacker-news.firebaseio.com/v0';\nconst ALGOLIA_BASE_URL = 'https://hn.algolia.com/api/v1';\nconst DEFAULT_DETAIL_CONCURRENCY = 8;\nconst DEFAULT_DETAIL_RESPONSE_BYTES = 256 * 1024;\nconst DEFAULT_MAX_RESPONSE_BYTES = 5 * 1024 * 1024;\nconst DEFAULT_REQUEST_TIMEOUT_MS = 30_000;\nconst SOURCE_TO_ENDPOINT: Record<HackerNewsStorySource, string> = {\n best: 'beststories',\n new: 'newstories',\n top: 'topstories'\n};\n\ninterface RuntimeDependencies {\n detailConcurrency: number;\n fetch: typeof fetch;\n maxResponseBytes: number;\n requestTimeoutMs: number;\n}\n\nexport function createDefaultHackerNewsRuntime(\n options: HackerNewsRuntimeOptions = {}\n): HackerNewsRuntime {\n const dependencies: RuntimeDependencies = {\n detailConcurrency: normalizeDetailConcurrency(options.detailConcurrency),\n fetch: options.fetch ?? fetch,\n maxResponseBytes: options.maxResponseBytes ?? DEFAULT_MAX_RESPONSE_BYTES,\n requestTimeoutMs: options.requestTimeoutMs ?? DEFAULT_REQUEST_TIMEOUT_MS\n };\n\n return {\n fetchSearch: async (request) => fetchSearch(dependencies, request),\n fetchStories: async (request) => fetchStories(dependencies, request)\n };\n}\n\nfunction normalizeDetailConcurrency(value: number | undefined): number {\n if (value === undefined || !Number.isFinite(value)) {\n return DEFAULT_DETAIL_CONCURRENCY;\n }\n return Math.max(1, Math.min(DEFAULT_DETAIL_CONCURRENCY, Math.floor(value)));\n}\n\nasync function fetchStories(\n dependencies: RuntimeDependencies,\n options: {\n limit: number;\n source: HackerNewsStorySource;\n }\n): Promise<HackerNewsStoriesRuntimeResult> {\n const endpoint = SOURCE_TO_ENDPOINT[options.source];\n const ids = await fetchJson<number[]>(\n dependencies,\n `${FIREBASE_BASE_URL}/${endpoint}.json`\n );\n const candidateIds = [...new Set(ids.slice(0, options.limit * 2))];\n const rawItems = await mapOrderedBounded(\n candidateIds,\n dependencies.detailConcurrency,\n async (id) => fetchJson<HackerNewsFirebaseItem | null>(\n dependencies,\n `${FIREBASE_BASE_URL}/item/${id}.json`,\n Math.min(dependencies.maxResponseBytes, DEFAULT_DETAIL_RESPONSE_BYTES)\n )\n );\n\n return {\n items: rawItems.flatMap(mapFirebaseItem).slice(0, options.limit),\n source: options.source\n };\n}\n\nasync function fetchSearch(\n dependencies: RuntimeDependencies,\n options: {\n limit: number;\n query: string;\n sort: HackerNewsSearchSort;\n }\n): Promise<HackerNewsSearchRuntimeResult> {\n const params = new URLSearchParams({\n hitsPerPage: String(options.limit),\n query: options.query,\n tags: 'story'\n });\n const endpoint = options.sort === 'date' ? 'search_by_date' : 'search';\n const response = await fetchJson<HackerNewsAlgoliaResponse>(\n dependencies,\n `${ALGOLIA_BASE_URL}/${endpoint}?${params.toString()}`\n );\n\n return {\n items: response.hits.flatMap(mapAlgoliaHit).slice(0, options.limit),\n query: options.query\n };\n}\n\nasync function fetchJson<T>(\n dependencies: RuntimeDependencies,\n url: string,\n maxResponseBytes = dependencies.maxResponseBytes\n): Promise<T> {\n const controller = new AbortController();\n const timeout = setTimeout(() => controller.abort(), dependencies.requestTimeoutMs);\n\n try {\n let response: Response;\n try {\n response = await dependencies.fetch(url, {\n headers: {\n accept: 'application/json',\n 'user-agent': 'ants-move/0.1 HackerNews collector'\n },\n signal: controller.signal\n });\n } catch (error) {\n throw new HackerNewsCommandError(\n 'HN_FETCH_FAILED',\n 'Failed to fetch Hacker News data.',\n 2,\n {\n cause: error instanceof Error ? error.message : String(error),\n url\n }\n );\n }\n\n if (!response.ok) {\n await cancelResponseBody(response);\n throw new HackerNewsCommandError(\n 'HN_FETCH_FAILED',\n `Failed to fetch Hacker News data. HTTP ${response.status}.`,\n 2,\n { url }\n );\n }\n\n const body = await readBoundedBody(response, maxResponseBytes, url);\n try {\n return JSON.parse(new TextDecoder().decode(body)) as T;\n } catch {\n throw new HackerNewsCommandError(\n 'HN_PARSE_FAILED',\n 'Failed to parse Hacker News JSON.',\n 2,\n { url }\n );\n }\n } finally {\n clearTimeout(timeout);\n }\n}\n\nasync function readBoundedBody(\n response: Response,\n maxBytes: number,\n url: string\n): Promise<Uint8Array> {\n const declaredLength = Number(response.headers.get('content-length'));\n if (Number.isFinite(declaredLength) && declaredLength > maxBytes) {\n await cancelResponseBody(response);\n throw responseTooLarge(url, maxBytes);\n }\n\n const reader = response.body?.getReader();\n if (!reader) {\n return new Uint8Array();\n }\n\n const chunks: Uint8Array[] = [];\n let totalBytes = 0;\n\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n totalBytes += value.byteLength;\n if (totalBytes > maxBytes) {\n await reader.cancel().catch(() => undefined);\n throw responseTooLarge(url, maxBytes);\n }\n chunks.push(value);\n }\n\n const body = new Uint8Array(totalBytes);\n let offset = 0;\n for (const chunk of chunks) {\n body.set(chunk, offset);\n offset += chunk.byteLength;\n }\n return body;\n}\n\nasync function cancelResponseBody(response: Response): Promise<void> {\n await response.body?.cancel().catch(() => undefined);\n}\n\nfunction responseTooLarge(url: string, maxBytes: number): HackerNewsCommandError {\n return new HackerNewsCommandError(\n 'HN_RESPONSE_TOO_LARGE',\n 'Hacker News response exceeded the configured size limit.',\n 2,\n { maxBytes, url }\n );\n}\n\nasync function mapOrderedBounded<T, R>(\n values: readonly T[],\n concurrency: number,\n map: (value: T, index: number) => Promise<R>\n): Promise<R[]> {\n if (values.length === 0) {\n return [];\n }\n\n const results = new Array<R>(values.length);\n let nextIndex = 0;\n let firstError: unknown;\n\n const worker = async () => {\n while (firstError === undefined) {\n const index = nextIndex;\n nextIndex += 1;\n if (index >= values.length) return;\n\n try {\n results[index] = await map(values[index] as T, index);\n } catch (error) {\n firstError ??= error;\n }\n }\n };\n\n const workerCount = Math.max(1, Math.min(\n Math.floor(concurrency),\n values.length\n ));\n await Promise.all(Array.from({ length: workerCount }, worker));\n\n if (firstError !== undefined) {\n throw firstError;\n }\n return results;\n}\n\ninterface HackerNewsFirebaseItem {\n by?: string;\n dead?: boolean;\n deleted?: boolean;\n descendants?: number;\n id?: number;\n score?: number;\n text?: string;\n time?: number;\n title?: string;\n type?: string;\n url?: string;\n}\n\ninterface HackerNewsAlgoliaResponse {\n hits: HackerNewsAlgoliaHit[];\n}\n\ninterface HackerNewsAlgoliaHit {\n author?: string;\n created_at_i?: number;\n num_comments?: number;\n objectID?: string;\n points?: number;\n story_id?: number;\n title?: string;\n url?: string;\n}\n\nfunction mapFirebaseItem(item: HackerNewsFirebaseItem | null): HackerNewsItem[] {\n if (!item || item.deleted || item.dead || item.type !== 'story' || !item.id || !item.title) {\n return [];\n }\n\n return [\n createItem({\n id: item.id,\n title: item.title,\n url: item.url ?? `https://news.ycombinator.com/item?id=${item.id}`,\n ...optional('author', item.by),\n ...optional('commentCount', item.descendants),\n ...optional('score', item.score),\n ...optional('text', item.text),\n ...optional('timeSeconds', item.time)\n })\n ];\n}\n\nfunction mapAlgoliaHit(hit: HackerNewsAlgoliaHit): HackerNewsItem[] {\n const id = hit.story_id ?? parseNumericId(hit.objectID);\n if (!id || !hit.title) {\n return [];\n }\n\n return [\n createItem({\n id,\n title: hit.title,\n url: hit.url ?? `https://news.ycombinator.com/item?id=${id}`,\n ...optional('author', hit.author),\n ...optional('commentCount', hit.num_comments),\n ...optional('score', hit.points),\n ...optional('timeSeconds', hit.created_at_i)\n })\n ];\n}\n\nfunction createItem(input: {\n author?: string;\n commentCount?: number;\n id: number;\n score?: number;\n text?: string;\n timeSeconds?: number;\n title: string;\n url: string;\n}): HackerNewsItem {\n const item: HackerNewsItem = {\n id: input.id,\n title: input.title,\n type: 'story',\n url: input.url\n };\n\n if (input.author !== undefined) item.author = input.author;\n if (input.commentCount !== undefined) item.commentCount = input.commentCount;\n if (input.score !== undefined) item.score = input.score;\n if (input.text !== undefined) item.text = input.text;\n if (input.timeSeconds !== undefined) {\n item.time = {\n iso: new Date(input.timeSeconds * 1000).toISOString(),\n seconds: input.timeSeconds\n };\n }\n\n return item;\n}\n\nfunction optional<K extends string, V>(\n key: K,\n value: V | undefined\n): Partial<Record<K, V>> {\n return value === undefined\n ? {}\n : { [key]: value } as Record<K, V>;\n}\n\nfunction parseNumericId(value: string | undefined): number | undefined {\n if (!value || !/^\\d+$/.test(value)) {\n return undefined;\n }\n return Number(value);\n}\n","import type { Command } from 'commander';\nimport { z } from 'zod';\n\nimport {\n renderKr36ArticleAsJson,\n renderKr36CommandErrorAsJson,\n renderKr36InformationListAsJson,\n renderKr36InformationListAsTable\n} from './output.js';\nimport type { Kr36Runtime } from './runtime.js';\nimport { Kr36ArticleService } from './service.js';\nimport { Kr36CommandError } from './types.js';\n\nexport interface Kr36CommandDependencies {\n runtime: Kr36Runtime;\n stderr: (value: string) => void;\n stdout: (value: string) => void;\n}\n\nconst articleOptionsSchema = z.object({\n format: z.enum(['json']).default('json')\n});\n\nconst informationListOptionsSchema = z.object({\n format: z.enum(['json', 'table']).default('json'),\n pages: z.number().int().min(1).max(20).default(1),\n table: z.boolean().optional()\n});\n\nexport function registerKr36Commands(\n program: Command,\n dependencies: Kr36CommandDependencies\n): void {\n const kr36 = program.command('36kr').description('Fetch and parse 36kr content.');\n const articleService = new Kr36ArticleService(dependencies.runtime);\n\n kr36.command('article')\n .argument('<articleId>', '36kr article id')\n .option('--format <format>', 'output format', 'json')\n .action(async (articleId, options) => {\n articleOptionsSchema.parse(options);\n const article = await articleService.getArticle(articleId);\n dependencies.stdout(`${renderKr36ArticleAsJson(article)}\\n`);\n });\n\n kr36.command('list')\n .argument('<channel>', '36kr information channel: AI or technology')\n .option('--pages <pages>', 'number of pages to fetch', parsePages, 1)\n .option('--format <format>', 'output format', 'json')\n .option('-t, --table', 'render as a table')\n .action(async (channel, options) => {\n const parsed = informationListOptionsSchema.parse(applyTableShortcut(options));\n const list = await articleService.getInformationList({\n channel,\n pages: parsed.pages\n });\n dependencies.stdout(\n parsed.format === 'table'\n ? `${renderKr36InformationListAsTable(list)}\\n`\n : `${renderKr36InformationListAsJson(list)}\\n`\n );\n });\n}\n\nexport function handleKr36CommandError(\n error: unknown,\n dependencies: Pick<Kr36CommandDependencies, 'stderr'>\n): number | undefined {\n if (error instanceof Kr36CommandError) {\n dependencies.stderr(\n `${renderKr36CommandErrorAsJson(error.code, error.message, error.details)}\\n`\n );\n return error.exitCode;\n }\n\n return undefined;\n}\n\nfunction parsePages(value: string): number {\n const parsed = Number(value);\n\n if (!Number.isInteger(parsed)) {\n throw new Kr36CommandError(\n 'KR36_INVALID_PAGES',\n '36kr list pages must be an integer between 1 and 20.',\n 2,\n {\n pages: value\n }\n );\n }\n\n return parsed;\n}\n\nfunction applyTableShortcut<T extends { format: string; table?: boolean }>(options: T): T & {\n format: 'json' | 'table';\n} {\n if (options.table) {\n return {\n ...options,\n format: 'table'\n };\n }\n\n return {\n ...options,\n format: options.format as 'json' | 'table'\n };\n}\n","import { renderSafeTable } from '../output.js';\nimport type { Kr36Article, Kr36InformationList } from './types.js';\n\nexport function renderKr36ArticleAsJson(article: Kr36Article): string {\n return JSON.stringify(\n {\n ok: true,\n data: article\n },\n null,\n 2\n );\n}\n\nexport function renderKr36InformationListAsJson(list: Kr36InformationList): string {\n return JSON.stringify(\n {\n ok: true,\n data: list\n },\n null,\n 2\n );\n}\n\nexport function renderKr36InformationListAsTable(list: Kr36InformationList): string {\n return renderSafeTable([\n ['id', 'title', 'author', 'publishTime', 'url'],\n ...list.items.map((item) => [\n String(item.id),\n item.title,\n item.authorName ?? '',\n item.publishTime?.local ?? '',\n item.url\n ])\n ]);\n}\n\nexport function renderKr36CommandErrorAsJson(\n code: string,\n message: string,\n details?: unknown\n): string {\n return JSON.stringify(\n {\n ok: false,\n error: {\n code,\n message,\n ...(details === undefined ? {} : { details })\n }\n },\n null,\n 2\n );\n}\n","export interface Kr36Request {\n headers: Record<string, string>;\n url: string;\n}\n\nexport interface Kr36JsonRequest {\n body: unknown;\n headers: Record<string, string>;\n url: string;\n}\n\nexport interface Kr36ArticleAuthor {\n face?: string;\n id?: number;\n name: string;\n route?: string;\n summary?: string;\n title?: string;\n}\n\nexport interface Kr36ArticleImage {\n index: number;\n size: string | null;\n url: string;\n}\n\nexport interface Kr36ArticleStats {\n authorArticleCount: number;\n collect: number;\n comment: number;\n favoriteCount: number;\n likeCount: number;\n praise: number;\n}\n\nexport interface Kr36ArticleOrganization {\n briefIntro?: string;\n id: number;\n identityName?: string;\n logo?: string;\n name: string;\n}\n\nexport interface Kr36ArticleListItem {\n author?: string;\n content?: string;\n id: number;\n image?: string;\n publishTime?: number;\n route?: string;\n title: string;\n}\n\nexport interface Kr36Article {\n author: Kr36ArticleAuthor;\n companyCertifyNick?: string;\n content: {\n html: string;\n paragraphs: string[];\n };\n coverImage?: string;\n id: string;\n imageSources: Array<{ name: string; url: string }>;\n images: Kr36ArticleImage[];\n latestArticles: Kr36ArticleListItem[];\n newestArticles: Kr36ArticleListItem[];\n nextArticle?: Kr36ArticleListItem;\n organizations: Kr36ArticleOrganization[];\n publishTime: {\n iso: string;\n local: string;\n ms: number;\n };\n relatedArticles: Kr36ArticleListItem[];\n request: Kr36Request;\n sourceType?: string;\n stats: Kr36ArticleStats;\n summary: string;\n title: string;\n url: string;\n}\n\nexport type Kr36InformationChannel = 'AI' | 'technology';\n\nexport interface Kr36InformationItem {\n authorName?: string;\n authorRoute?: string;\n id: number;\n image?: string;\n publishTime?: {\n iso: string;\n local: string;\n ms: number;\n };\n route?: string;\n summary?: string;\n title: string;\n url: string;\n}\n\nexport interface Kr36InformationList {\n channel: Kr36InformationChannel;\n items: Kr36InformationItem[];\n meta: {\n fetchedPages: number;\n hasNextPage: number;\n nextPageCallback: string;\n pageSize: number;\n totalItems: number;\n };\n request: {\n firstPage: Kr36Request;\n nextPageEndpoint: string;\n };\n}\n\nexport class Kr36CommandError extends Error {\n constructor(\n public readonly code: string,\n message: string,\n public readonly exitCode: number,\n public readonly details?: unknown\n ) {\n super(message);\n this.name = 'Kr36CommandError';\n }\n}\n","import type { Kr36Runtime } from './runtime.js';\nimport {\n Kr36CommandError,\n type Kr36Article,\n type Kr36ArticleAuthor,\n type Kr36ArticleImage,\n type Kr36ArticleListItem,\n type Kr36ArticleOrganization,\n type Kr36ArticleStats,\n type Kr36InformationChannel,\n type Kr36InformationItem,\n type Kr36InformationList,\n type Kr36JsonRequest,\n type Kr36Request\n} from './types.js';\n\nexport const KR36_BROWSER_HEADERS: Record<string, string> = {\n Accept: 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8',\n 'Accept-Language': 'zh-CN,zh;q=0.9,en;q=0.8',\n 'Cache-Control': 'no-cache',\n Pragma: 'no-cache',\n Referer: 'https://36kr.com/',\n 'Sec-Fetch-Dest': 'document',\n 'Sec-Fetch-Mode': 'navigate',\n 'Sec-Fetch-Site': 'same-origin',\n 'Sec-Fetch-User': '?1',\n 'Upgrade-Insecure-Requests': '1',\n 'User-Agent':\n 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36'\n};\n\nconst KR36_INFORMATION_ENDPOINT = 'https://gateway.36kr.com/api/mis/nav/ifm/subNav/flow';\nconst KR36_ARTICLE_MAX_RETAINED_BYTES = 20 * 1024 * 1024;\nconst KR36_INFORMATION_MAX_RETAINED_BYTES = 5 * 1024 * 1024;\nconst KR36_INFORMATION_PAGE_SIZE = 30;\nconst KR36_SUPPORTED_CHANNELS = new Set<Kr36InformationChannel>(['AI', 'technology']);\n\nconst KR36_JSON_HEADERS: Record<string, string> = {\n Accept: 'application/json, text/plain, */*',\n 'Accept-Language': KR36_BROWSER_HEADERS['Accept-Language']!,\n 'Content-Type': 'application/json;charset=UTF-8',\n Origin: 'https://36kr.com',\n 'User-Agent': KR36_BROWSER_HEADERS['User-Agent']!\n};\n\ninterface Kr36InitialState {\n articleDetail?: {\n articleDetailData?: {\n data?: Kr36RawArticle;\n };\n articleRecommendData?: Kr36RawRecommendData;\n favoriteCount?: number;\n likeCount?: number;\n organArticleData?: {\n data?: {\n organizationList?: Kr36ArticleOrganization[];\n };\n };\n latestArticle?: {\n articleLatestList?: Array<{ id: number; title: string }>;\n };\n };\n information?: {\n informationList?: Kr36RawInformationList;\n };\n}\n\ninterface Kr36RawArticle {\n author?: string;\n authorFace?: string;\n authorId?: number;\n authorRoute?: string;\n companyCertifyNick?: string;\n imgSources?: Array<{ name: string; url: string }>;\n itemId?: number;\n popinImage?: string;\n publishTime?: number;\n sourceType?: string;\n summary?: string;\n widgetContent?: string;\n widgetTitle?: string;\n}\n\ninterface Kr36RawRecommendData {\n authorFace?: string;\n authorName?: string;\n authorSummary?: string;\n authorTitle?: string;\n newestItemList?: Array<{\n itemContent?: string;\n itemId: number;\n itemRoute?: string;\n itemTitle: string;\n publishTime?: number;\n }>;\n nextItem?: {\n authorId?: number;\n itemContent?: string;\n itemId: number;\n itemRoute?: string;\n itemTitle: string;\n publishTime?: number;\n };\n relateArticleList?: Array<{\n author?: string;\n authorName?: string;\n itemId: number;\n route?: string;\n widgetImage?: string;\n widgetTitle: string;\n }>;\n statArticle?: number;\n statCollect?: number;\n statComment?: number;\n statPraise?: number;\n}\n\ninterface Kr36RawInformationList {\n hasNextPage?: number;\n itemList?: Kr36RawInformationItem[];\n pageCallback?: string;\n}\n\ninterface Kr36RawInformationItem {\n itemId: number;\n route?: string;\n templateMaterial?: {\n authorName?: string;\n authorRoute?: string;\n publishTime?: number;\n summary?: string;\n widgetImage?: string;\n widgetTitle?: string;\n };\n}\n\ninterface Kr36InformationFlowResponse {\n code?: number;\n data?: Kr36RawInformationList;\n msg?: string;\n}\n\nexport class Kr36ArticleService {\n constructor(private readonly runtime: Pick<Kr36Runtime, 'fetchArticleHtml' | 'fetchJson'>) {}\n\n async getArticle(articleId: string): Promise<Kr36Article> {\n assertArticleId(articleId);\n const request = buildKr36ArticleRequest(articleId);\n const html = await this.runtime.fetchArticleHtml(request);\n const initialState = parseInitialState(html);\n const articleDetail = initialState.articleDetail;\n const rawArticle = articleDetail?.articleDetailData?.data;\n\n if (!rawArticle) {\n throw new Kr36CommandError(\n 'KR36_PARSE_ERROR',\n '36kr article data was not found in window.initialState.',\n 2\n );\n }\n\n const contentHtml = rawArticle.widgetContent ?? '';\n const recommend = articleDetail?.articleRecommendData ?? {};\n const publishTime = rawArticle.publishTime ?? 0;\n const article: Kr36Article = {\n author: buildAuthor(rawArticle, recommend),\n content: {\n html: contentHtml,\n paragraphs: extractParagraphs(contentHtml)\n },\n id: String(rawArticle.itemId ?? articleId),\n imageSources: rawArticle.imgSources ?? [],\n images: extractImages(contentHtml),\n latestArticles: (articleDetail?.latestArticle?.articleLatestList ?? []).map((item) => ({\n id: item.id,\n title: item.title\n })),\n newestArticles: (recommend.newestItemList ?? []).map((item) => {\n const listItem: Kr36ArticleListItem = {\n id: item.itemId,\n title: item.itemTitle\n };\n\n if (item.itemContent !== undefined) {\n listItem.content = item.itemContent;\n }\n if (item.publishTime !== undefined) {\n listItem.publishTime = item.publishTime;\n }\n if (item.itemRoute !== undefined) {\n listItem.route = item.itemRoute;\n }\n\n return listItem;\n }),\n organizations: articleDetail?.organArticleData?.data?.organizationList ?? [],\n publishTime: {\n iso: publishTime ? new Date(publishTime).toISOString() : '',\n local: publishTime ? formatChinaTime(publishTime) : '',\n ms: publishTime\n },\n relatedArticles: (recommend.relateArticleList ?? []).map((item) => {\n const listItem: Kr36ArticleListItem = {\n id: item.itemId,\n title: item.widgetTitle\n };\n const author = item.author ?? item.authorName;\n\n if (author !== undefined) {\n listItem.author = author;\n }\n if (item.widgetImage !== undefined) {\n listItem.image = item.widgetImage;\n }\n if (item.route !== undefined) {\n listItem.route = item.route;\n }\n\n return listItem;\n }),\n request,\n stats: buildStats(articleDetail?.likeCount, articleDetail?.favoriteCount, recommend),\n summary: rawArticle.summary ?? '',\n title: rawArticle.widgetTitle ?? '',\n url: request.url\n };\n\n if (rawArticle.companyCertifyNick !== undefined) {\n article.companyCertifyNick = rawArticle.companyCertifyNick;\n }\n\n if (rawArticle.popinImage !== undefined) {\n article.coverImage = rawArticle.popinImage;\n }\n\n if (recommend.nextItem) {\n article.nextArticle = {\n id: recommend.nextItem.itemId,\n title: recommend.nextItem.itemTitle\n };\n\n if (recommend.nextItem.itemContent !== undefined) {\n article.nextArticle.content = recommend.nextItem.itemContent;\n }\n if (recommend.nextItem.publishTime !== undefined) {\n article.nextArticle.publishTime = recommend.nextItem.publishTime;\n }\n if (recommend.nextItem.itemRoute !== undefined) {\n article.nextArticle.route = recommend.nextItem.itemRoute;\n }\n }\n\n if (rawArticle.sourceType !== undefined) {\n article.sourceType = rawArticle.sourceType;\n }\n\n const retainedBytes = Buffer.byteLength(JSON.stringify(article), 'utf8');\n if (retainedBytes > KR36_ARTICLE_MAX_RETAINED_BYTES) {\n throw new Kr36CommandError(\n 'KR36_RESOURCE_LIMIT',\n '36kr article result exceeded the configured size limit.',\n 2,\n {\n maxRetainedBytes: KR36_ARTICLE_MAX_RETAINED_BYTES,\n retainedBytes\n }\n );\n }\n\n return article;\n }\n\n async getInformationList(options: {\n channel: string;\n pages?: number;\n }): Promise<Kr36InformationList> {\n const channel = parseInformationChannel(options.channel);\n const pageLimit = normalizePages(options.pages);\n const firstPageRequest = buildKr36InformationFirstPageRequest(channel);\n const firstPageHtml = await this.runtime.fetchArticleHtml(firstPageRequest);\n const firstPageState = parseInitialState(firstPageHtml);\n const firstPageList = firstPageState.information?.informationList;\n\n if (!firstPageList) {\n throw new Kr36CommandError(\n 'KR36_PARSE_ERROR',\n '36kr information list data was not found in window.initialState.',\n 2\n );\n }\n\n const firstPageItems = mapInformationPageItems(firstPageList.itemList ?? []);\n let retainedBytes = addInformationRetainedBytes(0, firstPageItems);\n const items = [...firstPageItems];\n let pageCallback = firstPageList.pageCallback ?? '';\n let hasNextPage = firstPageList.hasNextPage ?? 0;\n let fetchedPages = 1;\n\n while (fetchedPages < pageLimit && hasNextPage && pageCallback) {\n const request = buildKr36InformationNextPageRequest(channel, pageCallback);\n const response = parseInformationFlowResponse(await this.runtime.fetchJson(request));\n const nextList = response.data ?? {};\n\n const nextItems = mapInformationPageItems(nextList.itemList ?? []);\n retainedBytes = addInformationRetainedBytes(retainedBytes, nextItems);\n items.push(...nextItems);\n pageCallback = nextList.pageCallback ?? '';\n hasNextPage = nextList.hasNextPage ?? 0;\n fetchedPages += 1;\n }\n\n return {\n channel,\n items,\n meta: {\n fetchedPages,\n hasNextPage,\n nextPageCallback: pageCallback,\n pageSize: KR36_INFORMATION_PAGE_SIZE,\n totalItems: items.length\n },\n request: {\n firstPage: firstPageRequest,\n nextPageEndpoint: KR36_INFORMATION_ENDPOINT\n }\n };\n }\n}\n\nexport function buildKr36ArticleUrl(articleId: string): string {\n assertArticleId(articleId);\n return `https://36kr.com/p/${articleId}?f=rss`;\n}\n\nexport function buildKr36ArticleRequest(articleId: string): Kr36Request {\n return {\n headers: KR36_BROWSER_HEADERS,\n url: buildKr36ArticleUrl(articleId)\n };\n}\n\nexport function buildKr36InformationFirstPageRequest(channel: Kr36InformationChannel): Kr36Request {\n return {\n headers: KR36_BROWSER_HEADERS,\n url: `https://36kr.com/information/${channel}/`\n };\n}\n\nexport function buildKr36InformationNextPageRequest(\n channel: Kr36InformationChannel,\n pageCallback: string,\n timestamp = Date.now()\n): Kr36JsonRequest {\n return {\n body: {\n partner_id: 'web',\n timestamp,\n param: {\n subnavType: 1,\n subnavNick: channel,\n pageSize: KR36_INFORMATION_PAGE_SIZE,\n pageEvent: 1,\n pageCallback,\n siteId: 1,\n platformId: 2\n }\n },\n headers: {\n ...KR36_JSON_HEADERS,\n Referer: `https://36kr.com/information/${channel}/`\n },\n url: KR36_INFORMATION_ENDPOINT\n };\n}\n\nfunction assertArticleId(articleId: string): void {\n if (!/^\\d+$/.test(articleId)) {\n throw new Kr36CommandError(\n 'KR36_INVALID_ARTICLE_ID',\n '36kr article id must contain digits only.',\n 2,\n {\n articleId\n }\n );\n }\n}\n\nfunction parseInformationChannel(channel: string): Kr36InformationChannel {\n if (KR36_SUPPORTED_CHANNELS.has(channel as Kr36InformationChannel)) {\n return channel as Kr36InformationChannel;\n }\n\n throw new Kr36CommandError(\n 'KR36_INVALID_CHANNEL',\n '36kr list only supports AI and technology channels.',\n 2,\n {\n channel,\n supportedChannels: [...KR36_SUPPORTED_CHANNELS]\n }\n );\n}\n\nfunction normalizePages(pages: number | undefined): number {\n const value = pages ?? 1;\n\n if (!Number.isInteger(value) || value < 1 || value > 20) {\n throw new Kr36CommandError(\n 'KR36_INVALID_PAGES',\n '36kr list pages must be an integer between 1 and 20.',\n 2,\n {\n pages: value\n }\n );\n }\n\n return value;\n}\n\nfunction parseInitialState(html: string): Kr36InitialState {\n const match = /window\\.initialState=(\\{[\\s\\S]*?\\})\\s*;?\\s*<\\/script>/.exec(html);\n\n if (!match?.[1]) {\n throw new Kr36CommandError(\n 'KR36_PARSE_ERROR',\n 'window.initialState was not found in the 36kr article page.',\n 2\n );\n }\n\n try {\n return JSON.parse(match[1]) as Kr36InitialState;\n } catch (error) {\n throw new Kr36CommandError(\n 'KR36_PARSE_ERROR',\n 'Failed to parse window.initialState from the 36kr article page.',\n 2,\n {\n cause: error instanceof Error ? error.message : String(error)\n }\n );\n }\n}\n\nfunction extractImages(html: string): Kr36ArticleImage[] {\n return [...html.matchAll(/<img\\b[^>]*>/gi)].map((match, index) => {\n const tag = match[0];\n return {\n index: index + 1,\n size: getAttribute(tag, 'data-img-size-val'),\n url: getAttribute(tag, 'src') ?? ''\n };\n }).filter((image) => image.url);\n}\n\nfunction parseInformationFlowResponse(jsonText: string): Kr36InformationFlowResponse {\n try {\n const response = JSON.parse(jsonText) as Kr36InformationFlowResponse;\n\n if (response.code !== 0) {\n throw new Kr36CommandError(\n 'KR36_REQUEST_FAILED',\n response.msg || '36kr information flow request failed.',\n 1,\n {\n code: response.code\n }\n );\n }\n\n return response;\n } catch (error) {\n if (error instanceof Kr36CommandError) {\n throw error;\n }\n\n throw new Kr36CommandError(\n 'KR36_PARSE_ERROR',\n 'Failed to parse 36kr information flow response.',\n 2,\n {\n cause: error instanceof Error ? error.message : String(error)\n }\n );\n }\n}\n\nfunction mapInformationItems(items: Kr36RawInformationItem[]): Kr36InformationItem[] {\n return items.map((item) => {\n const material = item.templateMaterial ?? {};\n const mapped: Kr36InformationItem = {\n id: item.itemId,\n title: material.widgetTitle ?? '',\n url: `https://36kr.com/p/${item.itemId}`\n };\n\n if (material.authorName !== undefined) {\n mapped.authorName = material.authorName;\n }\n if (material.authorRoute !== undefined) {\n mapped.authorRoute = material.authorRoute;\n }\n if (material.widgetImage !== undefined) {\n mapped.image = material.widgetImage;\n }\n if (material.publishTime !== undefined) {\n mapped.publishTime = {\n iso: new Date(material.publishTime).toISOString(),\n local: formatChinaTime(material.publishTime),\n ms: material.publishTime\n };\n }\n if (item.route !== undefined) {\n mapped.route = item.route;\n }\n if (material.summary !== undefined) {\n mapped.summary = material.summary;\n }\n\n return mapped;\n });\n}\n\nfunction mapInformationPageItems(items: Kr36RawInformationItem[]): Kr36InformationItem[] {\n if (items.length > KR36_INFORMATION_PAGE_SIZE) {\n throw new Kr36CommandError(\n 'KR36_RESOURCE_LIMIT',\n '36kr information response exceeded the configured item limit.',\n 2,\n {\n maxItemsPerPage: KR36_INFORMATION_PAGE_SIZE,\n receivedItems: items.length\n }\n );\n }\n return mapInformationItems(items);\n}\n\nfunction addInformationRetainedBytes(\n retainedBytes: number,\n items: Kr36InformationItem[]\n): number {\n const nextRetainedBytes = retainedBytes\n + Buffer.byteLength(JSON.stringify(items), 'utf8');\n if (nextRetainedBytes > KR36_INFORMATION_MAX_RETAINED_BYTES) {\n throw new Kr36CommandError(\n 'KR36_RESOURCE_LIMIT',\n '36kr information results exceeded the configured size limit.',\n 2,\n {\n maxRetainedBytes: KR36_INFORMATION_MAX_RETAINED_BYTES,\n retainedBytes: nextRetainedBytes\n }\n );\n }\n return nextRetainedBytes;\n}\n\nfunction extractParagraphs(html: string): string[] {\n return html\n .replace(/<script[\\s\\S]*?<\\/script>/gi, '')\n .replace(/<style[\\s\\S]*?<\\/style>/gi, '')\n .replace(/<[^>]+>/g, '\\n')\n .split(/\\n+/)\n .map((value) => decodeHtmlEntities(value).trim())\n .filter(Boolean);\n}\n\nfunction getAttribute(tag: string, name: string): string | null {\n const match = new RegExp(`${name}=[\"']([^\"']+)[\"']`, 'i').exec(tag);\n return match?.[1] ?? null;\n}\n\nfunction decodeHtmlEntities(value: string): string {\n return value\n .replace(/ /g, ' ')\n .replace(/"/g, '\"')\n .replace(/'/g, \"'\")\n .replace(/</g, '<')\n .replace(/>/g, '>')\n .replace(/&/g, '&');\n}\n\nfunction buildStats(\n likeCount: number | undefined,\n favoriteCount: number | undefined,\n recommend: Kr36RawRecommendData\n): Kr36ArticleStats {\n return {\n authorArticleCount: recommend.statArticle ?? 0,\n collect: recommend.statCollect ?? 0,\n comment: recommend.statComment ?? 0,\n favoriteCount: favoriteCount ?? 0,\n likeCount: likeCount ?? 0,\n praise: recommend.statPraise ?? 0\n };\n}\n\nfunction buildAuthor(\n rawArticle: Kr36RawArticle,\n recommend: Kr36RawRecommendData\n): Kr36ArticleAuthor {\n const author: Kr36ArticleAuthor = {\n name: rawArticle.author ?? recommend.authorName ?? ''\n };\n const face = rawArticle.authorFace ?? recommend.authorFace;\n\n if (face !== undefined) {\n author.face = face;\n }\n if (rawArticle.authorId !== undefined) {\n author.id = rawArticle.authorId;\n }\n if (rawArticle.authorRoute !== undefined) {\n author.route = rawArticle.authorRoute;\n }\n if (recommend.authorSummary !== undefined) {\n author.summary = recommend.authorSummary;\n }\n if (recommend.authorTitle !== undefined) {\n author.title = recommend.authorTitle;\n }\n\n return author;\n}\n\nfunction formatChinaTime(timestampMs: number): string {\n const formatter = new Intl.DateTimeFormat('sv-SE', {\n day: '2-digit',\n hour: '2-digit',\n hour12: false,\n minute: '2-digit',\n month: '2-digit',\n second: '2-digit',\n timeZone: 'Asia/Shanghai',\n year: 'numeric'\n });\n\n return formatter.format(new Date(timestampMs));\n}\n","import { execFile as nodeExecFile } from 'node:child_process';\nimport { promisify } from 'node:util';\n\nimport {\n Kr36CommandError,\n type Kr36JsonRequest,\n type Kr36Request\n} from './types.js';\n\nexport interface Kr36Runtime {\n fetchArticleHtml: (request: Kr36Request) => Promise<string>;\n fetchJson: (request: Kr36JsonRequest) => Promise<string>;\n}\n\nexport type Kr36ExecFile = (\n file: string,\n args: string[],\n options: { encoding: 'utf8'; maxBuffer: number }\n) => Promise<{ stderr: string; stdout: string }>;\n\nconst execFileAsync = promisify(nodeExecFile) as unknown as Kr36ExecFile;\n\nexport function createDefaultKr36Runtime(options: {\n execFile?: Kr36ExecFile;\n} = {}): Kr36Runtime {\n const execFile = options.execFile ?? execFileAsync;\n\n return {\n fetchArticleHtml: async (request) => fetchWithCurl(execFile, request),\n fetchJson: async (request) => fetchWithCurl(execFile, request)\n };\n}\n\nasync function fetchWithCurl(\n execFile: Kr36ExecFile,\n request: Kr36JsonRequest | Kr36Request\n): Promise<string> {\n const args = [\n '--silent',\n '--show-error',\n '--location',\n '--compressed',\n '--connect-timeout',\n '10',\n '--max-time',\n '45',\n ...Object.entries(request.headers).flatMap(([name, value]) => [\n '--header',\n `${name}: ${value}`\n ]),\n ...('body' in request ? ['--data-raw', JSON.stringify(request.body)] : []),\n request.url\n ];\n\n try {\n const result = await execFile('curl', args, {\n encoding: 'utf8',\n maxBuffer: 20 * 1024 * 1024\n });\n return result.stdout;\n } catch (error) {\n const execError = error as Error & { code?: number | string; stderr?: string };\n const failureReason = execError.stderr?.trim() || 'curl request failed.';\n throw new Kr36CommandError(\n 'KR36_REQUEST_FAILED',\n `Failed to fetch 36kr page: ${failureReason}`,\n 1,\n {\n curlExitCode: execError.code,\n url: request.url\n }\n );\n }\n}\n","import type { Command } from 'commander';\nimport { z } from 'zod';\n\nimport {\n renderToutiaoArticleAsJson,\n renderToutiaoAuthorAsJson,\n renderToutiaoAuthorAsTable,\n renderToutiaoCommandErrorAsJson,\n renderToutiaoListAsJson,\n renderToutiaoListAsTable\n} from './output.js';\nimport type { ToutiaoRuntime } from './runtime.js';\nimport { ToutiaoService } from './service.js';\nimport { ToutiaoCommandError } from './types.js';\n\nexport interface ToutiaoCommandDependencies {\n runtime: ToutiaoRuntime;\n stderr: (value: string) => void;\n stdout: (value: string) => void;\n}\n\nconst listOptionsSchema = z.object({\n format: z.enum(['json', 'table']).default('json'),\n pages: z.number().int().min(1).max(5).default(1),\n table: z.boolean().optional()\n});\n\nconst articleOptionsSchema = z.object({\n format: z.enum(['json']).default('json')\n});\n\nconst authorOptionsSchema = z.object({\n format: z.enum(['json', 'table']).default('json'),\n pages: z.number().int().min(1).max(5).default(1),\n table: z.boolean().optional(),\n withContent: z.boolean().default(false)\n});\n\nexport function registerToutiaoCommands(\n program: Command,\n dependencies: ToutiaoCommandDependencies\n): void {\n const toutiao = program.command('toutiao')\n .description('Fetch Toutiao channel and search content.');\n const service = new ToutiaoService({ runtime: dependencies.runtime });\n\n toutiao.command('article')\n .argument('<article>', 'Toutiao article id or URL')\n .option('--format <format>', 'output format', 'json')\n .action(async (article, options) => {\n articleOptionsSchema.parse(options);\n const result = await service.article(article);\n dependencies.stdout(`${renderToutiaoArticleAsJson(result)}\\n`);\n });\n\n toutiao.command('list')\n .argument('<source>', 'Toutiao source: tech, AI, 光刻机, 芯片, or 半导体')\n .option('--pages <pages>', 'number of pages to fetch', parsePages, 1)\n .option('--format <format>', 'output format', 'json')\n .option('-t, --table', 'render as a table')\n .action(async (source, options) => {\n const parsed = listOptionsSchema.parse(applyTableShortcut(options));\n const result = await service.list({\n pages: parsed.pages,\n source\n });\n dependencies.stdout(\n parsed.format === 'table'\n ? `${renderToutiaoListAsTable(result)}\\n`\n : `${renderToutiaoListAsJson(result)}\\n`\n );\n });\n\n toutiao.command('author')\n .argument('<author>', 'Toutiao author token or /c/user/token/<token>/ homepage URL')\n .option('--pages <pages>', 'number of pages to fetch', parsePages, 1)\n .option('--with-content', 'also fetch detail content for each author article')\n .option('--format <format>', 'output format', 'json')\n .option('-t, --table', 'render as a table')\n .action(async (author, options) => {\n const parsed = authorOptionsSchema.parse(applyTableShortcut(options));\n const result = await service.author(author, {\n pages: parsed.pages,\n withContent: parsed.withContent\n });\n dependencies.stdout(\n parsed.format === 'table'\n ? `${renderToutiaoAuthorAsTable(result)}\\n`\n : `${renderToutiaoAuthorAsJson(result)}\\n`\n );\n });\n}\n\nexport function handleToutiaoCommandError(\n error: unknown,\n dependencies: Pick<ToutiaoCommandDependencies, 'stderr'>\n): number | undefined {\n if (error instanceof ToutiaoCommandError) {\n dependencies.stderr(\n `${renderToutiaoCommandErrorAsJson(error.code, error.message, error.details)}\\n`\n );\n return error.exitCode;\n }\n\n return undefined;\n}\n\nfunction parsePages(value: string): number {\n const parsed = Number(value);\n\n if (!Number.isInteger(parsed)) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_INVALID_PAGES',\n 'Toutiao list pages must be an integer between 1 and 5.',\n 2,\n {\n pages: value\n }\n );\n }\n\n return parsed;\n}\n\nfunction applyTableShortcut<T extends { format: string; table?: boolean }>(options: T): T & {\n format: 'json' | 'table';\n} {\n if (options.table) {\n return {\n ...options,\n format: 'table'\n };\n }\n\n return {\n ...options,\n format: options.format as 'json' | 'table'\n };\n}\n","import { renderSafeTable } from '../output.js';\nimport type { ToutiaoArticle, ToutiaoAuthorResult, ToutiaoListResult } from './types.js';\n\nexport function renderToutiaoListAsJson(result: ToutiaoListResult): string {\n return JSON.stringify(\n {\n ok: true,\n data: result\n },\n null,\n 2\n );\n}\n\nexport function renderToutiaoListAsTable(result: ToutiaoListResult): string {\n return renderSafeTable([\n ['id', 'title', 'author', 'publishTime', 'comments', 'url'],\n ...result.items.map((item) => [\n item.id,\n item.title,\n item.authorName ?? '',\n item.publishTime?.local ?? '',\n item.commentCount === undefined ? '' : String(item.commentCount),\n item.url\n ])\n ]);\n}\n\nexport function renderToutiaoArticleAsJson(article: ToutiaoArticle): string {\n return JSON.stringify(\n {\n ok: true,\n data: article\n },\n null,\n 2\n );\n}\n\nexport function renderToutiaoAuthorAsJson(result: ToutiaoAuthorResult): string {\n return JSON.stringify(\n {\n ok: true,\n data: result\n },\n null,\n 2\n );\n}\n\nexport function renderToutiaoAuthorAsTable(result: ToutiaoAuthorResult): string {\n return renderSafeTable([\n ['id', 'title', 'author', 'publishTime', 'comments', 'url'],\n ...result.items.map((item) => [\n item.id,\n item.title,\n item.authorName ?? '',\n item.publishTime?.local ?? '',\n item.commentCount === undefined ? '' : String(item.commentCount),\n item.url\n ])\n ]);\n}\n\nexport function renderToutiaoCommandErrorAsJson(\n code: string,\n message: string,\n details?: unknown\n): string {\n return JSON.stringify(\n {\n ok: false,\n error: {\n code,\n message,\n ...(details === undefined ? {} : { details })\n }\n },\n null,\n 2\n );\n}\n","export type ToutiaoSource = 'tech' | 'AI' | '光刻机' | '芯片' | '半导体';\n\nexport interface ToutiaoItem {\n abstract?: string;\n authorName?: string;\n commentCount?: number;\n id: string;\n image?: string;\n publishTime?: {\n iso: string;\n local: string;\n seconds: number;\n };\n sourceUrl?: string;\n title: string;\n url: string;\n}\n\nexport interface ToutiaoListResult {\n hasMore: boolean;\n items: ToutiaoItem[];\n keyword?: string;\n meta: {\n fetchedPages: number;\n totalItems: number;\n };\n next?: {\n maxBehotTime?: number;\n offset?: number;\n };\n source: ToutiaoSource;\n}\n\nexport interface ToutiaoAuthorRuntimeResult {\n authorToken: string;\n hasMore: boolean;\n items: ToutiaoItem[];\n next?: {\n maxBehotTime?: number;\n offset?: number;\n };\n}\n\nexport interface ToutiaoAuthorResult extends ToutiaoAuthorRuntimeResult {\n articles?: ToutiaoArticle[];\n meta: {\n fetchedPages: number;\n totalArticles?: number;\n totalItems: number;\n withContent: boolean;\n };\n request: {\n input: string;\n url: string;\n };\n}\n\nexport interface ToutiaoArticle {\n authorName?: string;\n content: {\n paragraphs: string[];\n text: string;\n };\n id: string;\n publishTimeText?: string;\n request: {\n input: string;\n url: string;\n };\n title: string;\n url: string;\n}\n\nexport interface ToutiaoRuntimeListResult {\n hasMore: boolean;\n items: ToutiaoItem[];\n keyword?: string;\n next?: {\n maxBehotTime?: number;\n offset?: number;\n };\n source: ToutiaoSource;\n}\n\nexport class ToutiaoCommandError extends Error {\n constructor(\n public readonly code: string,\n message: string,\n public readonly exitCode: number,\n public readonly details?: unknown\n ) {\n super(message);\n this.name = 'ToutiaoCommandError';\n }\n}\n","import type { ToutiaoRuntime } from './runtime.js';\nimport {\n ToutiaoCommandError,\n type ToutiaoArticle,\n type ToutiaoAuthorResult,\n type ToutiaoListResult,\n type ToutiaoSource\n} from './types.js';\n\nconst SUPPORTED_SOURCES = new Set<ToutiaoSource>([\n 'tech',\n 'AI',\n '光刻机',\n '芯片',\n '半导体'\n]);\nconst MAX_AUTHOR_CONTENT_ARTICLES = 100;\nconst MAX_AUTHOR_CONTENT_RETAINED_BYTES = 10 * 1024 * 1024;\n\nexport class ToutiaoService {\n constructor(private readonly dependencies: { runtime: ToutiaoRuntime }) {}\n\n async article(input: string): Promise<ToutiaoArticle> {\n const url = buildToutiaoArticleUrl(input);\n return this.dependencies.runtime.withSession(async (session) =>\n session.fetchArticle({ input, url })\n );\n }\n\n async author(input: string, options: {\n pages?: number;\n withContent?: boolean;\n } = {}): Promise<ToutiaoAuthorResult> {\n const authorToken = buildToutiaoAuthorToken(input);\n const pages = normalizePages(options.pages);\n const url = buildToutiaoAuthorUrl(authorToken);\n const withContent = options.withContent ?? false;\n\n return this.dependencies.runtime.withSession(async (session) => {\n const runtimeResult = await session.fetchAuthorArticles({\n authorToken,\n pages,\n url\n });\n const result: ToutiaoAuthorResult = {\n ...runtimeResult,\n meta: {\n fetchedPages: pages,\n totalItems: runtimeResult.items.length,\n withContent\n },\n request: {\n input,\n url\n }\n };\n\n if (!withContent) {\n return result;\n }\n\n if (runtimeResult.items.length > MAX_AUTHOR_CONTENT_ARTICLES) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_RESOURCE_LIMIT',\n 'Toutiao author content collection supports at most 100 articles per invocation.',\n 2,\n {\n totalItems: runtimeResult.items.length\n }\n );\n }\n\n const articles: ToutiaoArticle[] = [];\n let retainedBytes = 0;\n for (const item of runtimeResult.items) {\n const article = await session.fetchArticle({\n input: item.id,\n url: buildToutiaoArticleUrl(item.url || item.id)\n });\n const nextRetainedBytes = retainedBytes\n + Buffer.byteLength(JSON.stringify(article), 'utf8');\n if (nextRetainedBytes > MAX_AUTHOR_CONTENT_RETAINED_BYTES) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_RESOURCE_LIMIT',\n 'Toutiao author content exceeded the configured size limit.',\n 2,\n {\n maxRetainedBytes: MAX_AUTHOR_CONTENT_RETAINED_BYTES,\n retainedBytes: nextRetainedBytes\n }\n );\n }\n retainedBytes = nextRetainedBytes;\n articles.push(article);\n }\n\n result.articles = articles;\n result.meta.totalArticles = articles.length;\n return result;\n });\n }\n\n async list(options: {\n pages?: number;\n source: string;\n }): Promise<ToutiaoListResult> {\n const source = parseSource(options.source);\n const pages = normalizePages(options.pages);\n\n return this.dependencies.runtime.withSession(async (session) => {\n const runtimeResult = source === 'tech'\n ? await session.fetchTechnologyChannel({ pages })\n : await session.fetchKeywordInformation({\n keyword: source,\n pages,\n source\n });\n\n return {\n ...runtimeResult,\n meta: {\n fetchedPages: pages,\n totalItems: runtimeResult.items.length\n }\n };\n });\n }\n}\n\nexport function buildToutiaoAuthorToken(input: string): string {\n const trimmed = input.trim();\n\n if (/^[A-Za-z0-9._-]+$/.test(trimmed) && trimmed.length >= 12) {\n return trimmed;\n }\n\n try {\n const url = new URL(trimmed);\n const token = /\\/c\\/user\\/token\\/([^/?#]+)/.exec(url.pathname)?.[1];\n\n if (token && isToutiaoHost(url.hostname)) {\n return decodeURIComponent(token);\n }\n } catch {\n // Fall through to the explicit command error below.\n }\n\n throw new ToutiaoCommandError(\n 'TOUTIAO_INVALID_AUTHOR',\n 'Toutiao author must be a user token or a /c/user/token/<token>/ homepage URL.',\n 2,\n {\n input\n }\n );\n}\n\nexport function buildToutiaoAuthorUrl(authorToken: string): string {\n return `https://www.toutiao.com/c/user/token/${encodeURIComponent(authorToken)}/`;\n}\n\nexport function buildToutiaoArticleUrl(input: string): string {\n const trimmed = input.trim();\n\n if (/^\\d+$/.test(trimmed)) {\n return `https://www.toutiao.com/article/${trimmed}/`;\n }\n\n try {\n const url = new URL(trimmed);\n const id = /(?:article|group)\\/(\\d+)/.exec(url.pathname)?.[1]\n ?? /^\\/a(\\d+)/.exec(url.pathname)?.[1];\n\n if (id && isToutiaoHost(url.hostname)) {\n return `https://www.toutiao.com/article/${id}/`;\n }\n\n const nextUrl = url.searchParams.get('url');\n if (nextUrl) {\n return buildToutiaoArticleUrl(nextUrl);\n }\n } catch {\n // Fall through to the explicit command error below.\n }\n\n throw new ToutiaoCommandError(\n 'TOUTIAO_INVALID_ARTICLE',\n 'Toutiao article must be a numeric id or a toutiao article/group URL.',\n 2,\n {\n input\n }\n );\n}\n\nfunction isToutiaoHost(hostname: string): boolean {\n return hostname === 'www.toutiao.com' || hostname === 'toutiao.com';\n}\n\nfunction parseSource(source: string): ToutiaoSource {\n if (SUPPORTED_SOURCES.has(source as ToutiaoSource)) {\n return source as ToutiaoSource;\n }\n\n throw new ToutiaoCommandError(\n 'TOUTIAO_INVALID_SOURCE',\n 'Toutiao list only supports tech, AI, 光刻机, 芯片, and 半导体.',\n 2,\n {\n source,\n supportedSources: [...SUPPORTED_SOURCES]\n }\n );\n}\n\nfunction normalizePages(pages: number | undefined): number {\n const value = pages ?? 1;\n\n if (!Number.isInteger(value) || value < 1 || value > 5) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_INVALID_PAGES',\n 'Toutiao list pages must be an integer between 1 and 5.',\n 2,\n {\n pages: value\n }\n );\n }\n\n return value;\n}\n","import type { Browser, BrowserContext, Page, Response } from 'playwright';\n\nimport {\n ToutiaoCommandError,\n type ToutiaoArticle,\n type ToutiaoAuthorRuntimeResult,\n type ToutiaoItem,\n type ToutiaoRuntimeListResult,\n type ToutiaoSource\n} from './types.js';\n\nexport interface ToutiaoSession {\n fetchArticle: (request: { input: string; url: string }) => Promise<ToutiaoArticle>;\n fetchAuthorArticles: (options: {\n authorToken: string;\n pages: number;\n url: string;\n }) => Promise<ToutiaoAuthorRuntimeResult>;\n fetchKeywordInformation: (options: {\n keyword: ToutiaoSource;\n pages: number;\n source: ToutiaoSource;\n }) => Promise<ToutiaoRuntimeListResult>;\n fetchTechnologyChannel: (\n options: { pages: number }\n ) => Promise<ToutiaoRuntimeListResult>;\n}\n\nexport interface ToutiaoRuntime {\n withSession: <T>(\n operation: (session: ToutiaoSession) => Promise<T>\n ) => Promise<T>;\n}\n\nexport interface ToutiaoRuntimeOptions {\n deadlineMs?: number;\n loadPlaywright?: () => Promise<typeof import('playwright')>;\n}\n\nconst TOUTIAO_USER_AGENT =\n 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36';\nconst TECH_CHANNEL_ID = 3189398999;\nconst DEFAULT_DEADLINE_MS = 10 * 60 * 1000;\nconst MAX_ARTICLE_TEXT_BYTES = 1024 * 1024;\nconst MAX_FEED_ITEMS_PER_RESPONSE = 100;\nconst MAX_FEED_RESPONSE_BYTES = 5 * 1024 * 1024;\nconst MAX_SEARCH_TEXT_BYTES = 1024 * 1024;\nconst BLOCKED_RESOURCE_TYPES = new Set(['font', 'image', 'media']);\n\nexport function createDefaultToutiaoRuntime(\n options: ToutiaoRuntimeOptions = {}\n): ToutiaoRuntime {\n const deadlineMs = options.deadlineMs ?? DEFAULT_DEADLINE_MS;\n const playwrightLoader = options.loadPlaywright ?? loadPlaywright;\n\n return {\n withSession: async <T>(operation: (session: ToutiaoSession) => Promise<T>) => {\n let browser: Browser | undefined;\n let browserClosed = false;\n let context: BrowserContext | undefined;\n let deadlineTriggered = false;\n let operationPromise: Promise<T> | undefined;\n let lifecyclePromise: Promise<T>;\n\n const createTimeoutError = () => new ToutiaoCommandError(\n 'TOUTIAO_TIMEOUT',\n 'Toutiao collection exceeded the command deadline.',\n 1,\n { deadlineMs }\n );\n const ensureWithinDeadline = (): void => {\n if (deadlineTriggered) {\n throw createTimeoutError();\n }\n };\n\n lifecyclePromise = (async () => {\n try {\n let playwright: typeof import('playwright');\n try {\n playwright = await playwrightLoader();\n } catch {\n ensureWithinDeadline();\n throw new ToutiaoCommandError(\n 'TOUTIAO_BROWSER_UNAVAILABLE',\n 'Toutiao collection requires Playwright to be installed.',\n 2\n );\n }\n ensureWithinDeadline();\n\n try {\n browser = await playwright.chromium.launch({ headless: true });\n } catch {\n ensureWithinDeadline();\n throw new ToutiaoCommandError(\n 'TOUTIAO_BROWSER_UNAVAILABLE',\n 'Toutiao collection requires Playwright Chromium to be installed.',\n 2\n );\n }\n if (deadlineTriggered) {\n browserClosed = true;\n await browser.close().catch(() => undefined);\n throw createTimeoutError();\n }\n\n context = await browser.newContext({\n locale: 'zh-CN',\n userAgent: TOUTIAO_USER_AGENT\n });\n ensureWithinDeadline();\n const page = await context.newPage();\n ensureWithinDeadline();\n await page.route('**/*', async (route) => {\n if (BLOCKED_RESOURCE_TYPES.has(route.request().resourceType())) {\n await route.abort();\n return;\n }\n await route.continue();\n });\n ensureWithinDeadline();\n\n operationPromise = Promise.resolve().then(() =>\n operation(createToutiaoSession(page))\n );\n return await operationPromise;\n } finally {\n await context?.close().catch(() => undefined);\n if (!browserClosed) {\n await browser?.close().catch(() => undefined);\n }\n }\n })();\n\n return await new Promise<T>((resolve, reject) => {\n const deadlineTimer = setTimeout(() => {\n deadlineTriggered = true;\n void (async () => {\n if (browser !== undefined) {\n browserClosed = true;\n await browser.close().catch(() => undefined);\n }\n if (operationPromise !== undefined) {\n await operationPromise.then(\n () => undefined,\n () => undefined\n );\n await lifecyclePromise.then(\n () => undefined,\n () => undefined\n );\n }\n reject(createTimeoutError());\n })();\n }, deadlineMs);\n\n void lifecyclePromise.then(\n (value) => {\n if (!deadlineTriggered) {\n clearTimeout(deadlineTimer);\n resolve(value);\n }\n },\n (error: unknown) => {\n if (!deadlineTriggered) {\n clearTimeout(deadlineTimer);\n reject(error);\n }\n }\n );\n });\n }\n };\n}\n\nfunction createToutiaoSession(page: Page): ToutiaoSession {\n return {\n fetchArticle: async (request) => fetchArticle(page, request),\n fetchAuthorArticles: async (options) => fetchAuthorArticles(page, options),\n fetchKeywordInformation: async (options) => fetchKeywordInformation(page, options),\n fetchTechnologyChannel: async (options) => fetchTechnologyChannel(page, options)\n };\n}\n\nasync function fetchArticle(\n page: Page,\n request: { input: string; url: string }\n): Promise<ToutiaoArticle> {\n await page.goto(request.url, {\n timeout: 45000,\n waitUntil: 'domcontentloaded'\n });\n await page.waitForTimeout(5000);\n\n const title = await page.locator('h1').first().innerText({ timeout: 5000 }).catch(() => '');\n const paragraphs = await page.locator('article p').evaluateAll((nodes) =>\n nodes.map((node) => (node.textContent ?? '').trim()).filter(Boolean)\n );\n const bodyText = await page.locator('body').innerText({ timeout: 5000 });\n const extractedTextBytes = Math.max(\n Buffer.byteLength(title, 'utf8'),\n Buffer.byteLength(bodyText, 'utf8'),\n paragraphs.reduce(\n (total, paragraph) => total + Buffer.byteLength(paragraph, 'utf8'),\n 0\n )\n );\n if (extractedTextBytes > MAX_ARTICLE_TEXT_BYTES) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_RESOURCE_LIMIT',\n 'Toutiao article text exceeded the configured size limit.',\n 2,\n {\n maxTextBytes: MAX_ARTICLE_TEXT_BYTES,\n textBytes: extractedTextBytes\n }\n );\n }\n const metadata = extractArticleMetadata(bodyText, title);\n const id = extractArticleId(request.url) ?? extractArticleId(request.input) ?? '';\n\n if (!id || !title || paragraphs.length === 0) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_PARSE_ERROR',\n 'Toutiao article page did not expose title and content.',\n 2,\n {\n input: request.input,\n url: request.url\n }\n );\n }\n\n const article: ToutiaoArticle = {\n content: {\n paragraphs,\n text: paragraphs.join('\\n')\n },\n id,\n request,\n title,\n url: page.url()\n };\n\n if (metadata.authorName !== undefined) {\n article.authorName = metadata.authorName;\n }\n if (metadata.publishTimeText !== undefined) {\n article.publishTimeText = metadata.publishTimeText;\n }\n\n return article;\n}\n\nasync function fetchTechnologyChannel(\n page: Page,\n options: { pages: number }\n): Promise<ToutiaoRuntimeListResult> {\n const feedResponses = await collectFeedResponses(\n page,\n options.pages,\n (response) => response.url().includes('/api/pc/list/feed'),\n async () => {\n await page.goto(\n `https://www.toutiao.com/?channel=tech&source=ch&channel_id=${TECH_CHANNEL_ID}`,\n {\n timeout: 45000,\n waitUntil: 'domcontentloaded'\n }\n );\n }\n );\n const selectedResponses = feedResponses.slice(0, options.pages);\n const items = deduplicateItems(\n selectedResponses.flatMap((response) => mapFeedItems(response.data ?? []))\n );\n const lastResponse = selectedResponses.at(-1);\n\n if (items.length === 0) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_PARSE_ERROR',\n 'Toutiao technology channel did not return feed items.',\n 2\n );\n }\n\n const result: ToutiaoRuntimeListResult = {\n hasMore: lastResponse?.has_more ?? false,\n items,\n source: 'tech'\n };\n addNextPage(result, lastResponse);\n return result;\n}\n\nasync function fetchAuthorArticles(\n page: Page,\n options: {\n authorToken: string;\n pages: number;\n url: string;\n }\n): Promise<ToutiaoAuthorRuntimeResult> {\n const feedResponses = await collectFeedResponses(\n page,\n options.pages,\n (response) => isAuthorFeedResponseUrl(response.url(), options.authorToken),\n async () => {\n await page.goto(options.url, {\n timeout: 45000,\n waitUntil: 'domcontentloaded'\n });\n }\n );\n const selectedResponses = feedResponses.slice(0, options.pages);\n const items = deduplicateItems(\n selectedResponses.flatMap((response) => mapFeedItems(response.data ?? []))\n );\n const lastResponse = selectedResponses.at(-1);\n\n if (items.length === 0) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_PARSE_ERROR',\n 'Toutiao author homepage did not return article feed items.',\n 2,\n {\n authorToken: options.authorToken,\n url: options.url\n }\n );\n }\n\n const result: ToutiaoAuthorRuntimeResult = {\n authorToken: options.authorToken,\n hasMore: lastResponse?.has_more ?? false,\n items\n };\n addNextPage(result, lastResponse);\n return result;\n}\n\nasync function collectFeedResponses(\n page: Page,\n pages: number,\n accepts: (response: Response) => boolean,\n navigate: () => Promise<void>\n): Promise<ToutiaoFeedResponse[]> {\n const feedResponses: ToutiaoFeedResponse[] = [];\n const maxResponseParses = pages * 2;\n const pendingResponses = new Set<Promise<void>>();\n const queuedResponses: Response[] = [];\n let firstResourceError: ToutiaoCommandError | undefined;\n let startedResponseParses = 0;\n\n const startQueuedResponses = (): void => {\n while (\n firstResourceError === undefined\n && queuedResponses.length > 0\n && feedResponses.length + pendingResponses.size < pages\n && startedResponseParses < maxResponseParses\n ) {\n startResponseParse(queuedResponses.shift()!);\n }\n };\n const startResponseParse = (response: Response): void => {\n startedResponseParses += 1;\n const pending = parseFeedResponse(response)\n .then((feedResponse) => {\n feedResponses.push(feedResponse);\n })\n .catch((error: unknown) => {\n if (error instanceof ToutiaoCommandError) {\n firstResourceError ??= error;\n }\n })\n .finally(() => {\n pendingResponses.delete(pending);\n startQueuedResponses();\n });\n pendingResponses.add(pending);\n };\n const handler = (response: Response): void => {\n if (\n !accepts(response)\n || firstResourceError !== undefined\n || feedResponses.length >= pages\n || startedResponseParses + queuedResponses.length >= maxResponseParses\n ) {\n return;\n }\n\n if (feedResponses.length + pendingResponses.size < pages) {\n startResponseParse(response);\n return;\n }\n queuedResponses.push(response);\n };\n\n page.on('response', handler);\n try {\n await navigate();\n await waitForFeedResponses(\n page,\n feedResponses,\n pages,\n () => firstResourceError !== undefined\n );\n while (pendingResponses.size > 0) {\n await Promise.allSettled([...pendingResponses]);\n }\n if (firstResourceError !== undefined) {\n throw firstResourceError;\n }\n return feedResponses;\n } finally {\n page.off('response', handler);\n queuedResponses.length = 0;\n while (pendingResponses.size > 0) {\n await Promise.allSettled([...pendingResponses]);\n }\n }\n}\n\nasync function parseFeedResponse(response: Response): Promise<ToutiaoFeedResponse> {\n const declaredLength = Number(await response.headerValue('content-length'));\n if (Number.isFinite(declaredLength) && declaredLength > MAX_FEED_RESPONSE_BYTES) {\n throw feedResponseTooLarge();\n }\n\n const body = await response.body();\n if (body.byteLength > MAX_FEED_RESPONSE_BYTES) {\n throw feedResponseTooLarge();\n }\n const feedResponse = JSON.parse(body.toString('utf8')) as ToutiaoFeedResponse;\n if (\n Array.isArray(feedResponse.data)\n && feedResponse.data.length > MAX_FEED_ITEMS_PER_RESPONSE\n ) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_RESOURCE_LIMIT',\n 'Toutiao feed response exceeded the configured item limit.',\n 2,\n { maxItems: MAX_FEED_ITEMS_PER_RESPONSE }\n );\n }\n return feedResponse;\n}\n\nfunction feedResponseTooLarge(): ToutiaoCommandError {\n return new ToutiaoCommandError(\n 'TOUTIAO_RESPONSE_TOO_LARGE',\n 'Toutiao feed response exceeded the configured size limit.',\n 2,\n { maxBytes: MAX_FEED_RESPONSE_BYTES }\n );\n}\n\nasync function fetchKeywordInformation(\n page: Page,\n options: {\n keyword: ToutiaoSource;\n pages: number;\n source: ToutiaoSource;\n }\n): Promise<ToutiaoRuntimeListResult> {\n const items: ToutiaoItem[] = [];\n const seen = new Set<string>();\n let blocked = false;\n\n for (let pageIndex = 0; pageIndex < options.pages; pageIndex += 1) {\n const url = buildSearchUrl(options.keyword, pageIndex);\n\n await page.goto(url, {\n timeout: 45000,\n waitUntil: 'domcontentloaded'\n });\n await page.waitForTimeout(5000);\n\n blocked = blocked || await page.locator('#pc_captcha').count() > 0;\n\n for (const item of await extractSearchItemsFromPage(page, options.keyword)) {\n if (seen.has(item.id)) {\n continue;\n }\n seen.add(item.id);\n items.push(item);\n }\n }\n\n if (blocked && items.length === 0) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_VERIFICATION_REQUIRED',\n 'Toutiao search requires browser verification before returning usable results.',\n 1,\n {\n keyword: options.keyword\n }\n );\n }\n\n if (items.length === 0) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_PARSE_ERROR',\n 'Toutiao search page did not expose result items.',\n 2,\n {\n keyword: options.keyword\n }\n );\n }\n\n return {\n hasMore: true,\n items,\n keyword: options.keyword,\n source: options.source\n };\n}\n\nfunction buildSearchUrl(keyword: string, pageIndex: number): string {\n const params = new URLSearchParams({\n action_type: pageIndex === 0 ? 'search' : 'pagination',\n cur_tab_title: 'news',\n dvpf: 'pc',\n from: 'news',\n keyword,\n page_num: String(pageIndex),\n pd: 'information',\n source: pageIndex === 0 ? 'input' : 'pagination'\n });\n\n return `https://so.toutiao.com/search?${params.toString()}`;\n}\n\nasync function waitForFeedResponses(\n page: Page,\n responses: ToutiaoFeedResponse[],\n pages: number,\n shouldStop: () => boolean\n): Promise<void> {\n for (\n let attempt = 0;\n attempt < 45 && responses.length < pages && !shouldStop();\n attempt += 1\n ) {\n await page.waitForTimeout(1000);\n if (responses.length < pages && !shouldStop()) {\n await page.mouse.wheel(0, 4000);\n }\n }\n}\n\ninterface ToutiaoFeedResponse {\n data?: ToutiaoRawFeedItem[];\n has_more?: boolean;\n next?: {\n max_behot_time?: number;\n };\n offset?: number;\n}\n\ninterface ToutiaoRawFeedItem {\n Abstract?: string;\n abstract?: string;\n article_url?: string;\n behot_time?: number;\n comment_count?: number;\n display_url?: string;\n group_id?: string;\n id?: string;\n image_url?: string;\n item_id?: string;\n media_name?: string;\n source?: string;\n source_url?: string;\n title?: string;\n Title?: string;\n}\n\nfunction mapFeedItems(items: ToutiaoRawFeedItem[]): ToutiaoItem[] {\n return items.flatMap((item) => {\n const id = String(item.group_id ?? item.item_id ?? item.id ?? '');\n const title = item.title ?? item.Title ?? '';\n\n if (!id || !title) {\n return [];\n }\n\n const mapped: ToutiaoItem = {\n id,\n title,\n url: normalizeArticleUrl(item.article_url ?? item.display_url ?? item.source_url, id)\n };\n\n const abstract = item.Abstract ?? item.abstract;\n if (abstract !== undefined) {\n mapped.abstract = abstract;\n }\n if (item.comment_count !== undefined) {\n mapped.commentCount = item.comment_count;\n }\n if (item.image_url !== undefined) {\n mapped.image = item.image_url;\n }\n const authorName = item.media_name ?? item.source;\n if (authorName !== undefined) {\n mapped.authorName = authorName;\n }\n if (item.source_url !== undefined) {\n mapped.sourceUrl = item.source_url;\n }\n if (item.behot_time !== undefined) {\n mapped.publishTime = {\n iso: new Date(item.behot_time * 1000).toISOString(),\n local: formatChinaTime(item.behot_time),\n seconds: item.behot_time\n };\n }\n\n return [mapped];\n });\n}\n\nfunction deduplicateItems(items: ToutiaoItem[]): ToutiaoItem[] {\n const seen = new Set<string>();\n return items.filter((item) => {\n if (seen.has(item.id)) {\n return false;\n }\n seen.add(item.id);\n return true;\n });\n}\n\nfunction addNextPage(\n result: ToutiaoAuthorRuntimeResult | ToutiaoRuntimeListResult,\n response: ToutiaoFeedResponse | undefined\n): void {\n const next: NonNullable<typeof result.next> = {};\n if (response?.next?.max_behot_time !== undefined) {\n next.maxBehotTime = response.next.max_behot_time;\n }\n if (response?.offset !== undefined) {\n next.offset = response.offset;\n }\n if (Object.keys(next).length > 0) {\n result.next = next;\n }\n}\n\nfunction normalizeArticleUrl(value: string | undefined, id: string): string {\n if (!value) {\n return `https://www.toutiao.com/article/${id}/`;\n }\n\n try {\n const url = new URL(value, 'https://www.toutiao.com');\n return parseToutiaoArticleLink(url.toString())?.url\n ?? `https://www.toutiao.com/article/${id}/`;\n } catch {\n return `https://www.toutiao.com/article/${id}/`;\n }\n}\n\nasync function extractSearchItemsFromPage(\n page: Page,\n keyword: string\n): Promise<ToutiaoItem[]> {\n const anchors = await page.locator('a').evaluateAll((nodes) =>\n nodes.slice(0, 300).map((node) => ({\n href: (node as HTMLAnchorElement).href.slice(0, 2048),\n text: (node.textContent ?? '').trim().replace(/\\s+/g, ' ').slice(0, 1000)\n }))\n );\n const seen = new Set<string>();\n const items: ToutiaoItem[] = [];\n\n for (const anchor of anchors) {\n const articleLink = parseToutiaoArticleLink(anchor.href);\n\n if (!articleLink || !anchor.text || anchor.text.length < 6 || seen.has(articleLink.id)) {\n continue;\n }\n\n seen.add(articleLink.id);\n items.push({\n id: articleLink.id,\n title: anchor.text.slice(0, 180),\n url: articleLink.url\n });\n\n if (items.length >= 30) {\n break;\n }\n }\n\n if (items.length > 0) {\n return items;\n }\n\n const bodyText = await page.locator('body').innerText({ timeout: 5000 });\n const textBytes = Buffer.byteLength(bodyText, 'utf8');\n if (textBytes > MAX_SEARCH_TEXT_BYTES) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_RESOURCE_LIMIT',\n 'Toutiao search text exceeded the configured size limit.',\n 2,\n {\n maxTextBytes: MAX_SEARCH_TEXT_BYTES,\n textBytes\n }\n );\n }\n return extractSearchItemsFromText(bodyText, keyword);\n}\n\nfunction extractSearchItemsFromText(text: string, keyword: string): ToutiaoItem[] {\n const blockedPrefixes = new Set([\n '无障碍 今日头条首页 登录 综合 资讯 视频 图片 用户 小视频 微头条 音乐 去抖音搜'\n ]);\n const lines = text\n .split(/\\n+/)\n .map((line) => line.trim())\n .filter((line) => line.length >= 12 && !blockedPrefixes.has(line));\n\n const seen = new Set<string>();\n const items: ToutiaoItem[] = [];\n\n for (const line of lines) {\n const normalized = line.replace(/\\s+/g, ' ');\n if (seen.has(normalized)) {\n continue;\n }\n seen.add(normalized);\n items.push({\n id: createSearchItemId(keyword, normalized, items.length),\n title: normalized.slice(0, 180),\n url: `https://so.toutiao.com/search?keyword=${encodeURIComponent(keyword)}&pd=information&dvpf=pc&source=input`\n });\n\n if (items.length >= 30) {\n break;\n }\n }\n\n return items;\n}\n\nfunction parseToutiaoArticleLink(\n href: string,\n depth = 0\n): { id: string; url: string } | undefined {\n if (depth > 3) {\n return undefined;\n }\n\n const directId = extractArticleId(href);\n\n if (directId) {\n return {\n id: directId,\n url: `https://www.toutiao.com/article/${directId}/`\n };\n }\n\n try {\n const url = new URL(href);\n const nextUrl = url.searchParams.get('url');\n\n if (nextUrl) {\n return parseToutiaoArticleLink(nextUrl, depth + 1);\n }\n } catch {\n return undefined;\n }\n\n return undefined;\n}\n\nfunction extractArticleMetadata(bodyText: string, title: string): {\n authorName?: string;\n publishTimeText?: string;\n} {\n const lines = bodyText.split(/\\n+/).map((line) => line.trim()).filter(Boolean);\n const titleIndex = lines.findIndex((line) => line === title);\n const metadataLine = titleIndex >= 0 ? lines[titleIndex + 1] : undefined;\n const match = metadataLine?.match(/^(.+?)·(.+)$/);\n\n if (!match?.[1] || !match[2]) {\n return {};\n }\n\n return {\n authorName: match[2],\n publishTimeText: match[1]\n };\n}\n\nfunction extractArticleId(value: string): string | undefined {\n return /(?:article|group)\\/(\\d+)/.exec(value)?.[1]\n ?? /\\/a(\\d+)/.exec(value)?.[1]\n ?? (/^\\d+$/.test(value) ? value : undefined);\n}\n\nfunction isAuthorFeedResponseUrl(value: string, authorToken: string): boolean {\n try {\n const url = new URL(value);\n const isProfileArticleFeed = url.pathname.includes('/api/pc/list/feed')\n && (\n url.searchParams.get('category') === 'pc_profile_article'\n || url.searchParams.get('author_token') === authorToken\n );\n const isProfileAllFeed = url.pathname.includes('/api/pc/list/user/feed')\n && url.searchParams.get('category') === 'profile_all'\n && url.searchParams.get('token') === authorToken;\n\n return isProfileArticleFeed || isProfileAllFeed;\n } catch {\n return (\n value.includes('/api/pc/list/feed')\n && (value.includes('pc_profile_article') || value.includes(authorToken))\n ) || (\n value.includes('/api/pc/list/user/feed')\n && value.includes('profile_all')\n && value.includes(authorToken)\n );\n }\n}\n\nfunction createSearchItemId(keyword: string, value: string, index: number): string {\n let hash = 2166136261;\n const input = `${keyword}:${index}:${value}`;\n\n for (const char of input) {\n hash ^= char.charCodeAt(0);\n hash = Math.imul(hash, 16777619);\n }\n\n return `search-${(hash >>> 0).toString(16)}`;\n}\n\nfunction formatChinaTime(timestampSeconds: number): string {\n return new Intl.DateTimeFormat('sv-SE', {\n day: '2-digit',\n hour: '2-digit',\n hour12: false,\n minute: '2-digit',\n month: '2-digit',\n second: '2-digit',\n timeZone: 'Asia/Shanghai',\n year: 'numeric'\n }).format(new Date(timestampSeconds * 1000));\n}\n\nasync function loadPlaywright(): Promise<typeof import('playwright')> {\n return await import('playwright');\n}\n"],"mappings":"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","names":["z","z","applyTableShortcut","z","SUPPORTED_SOURCES","normalizePages","parseSource","z","articleOptionsSchema","parsePages","applyTableShortcut","formatChinaTime"]}
|
|
1
|
+
{"version":3,"sources":["../src/index.ts","../src/cli.ts","../src/hn/command.ts","../src/output.ts","../src/hn/output.ts","../src/hn/types.ts","../src/hn/service.ts","../src/hn/runtime.ts","../src/36kr/command.ts","../src/36kr/output.ts","../src/36kr/types.ts","../src/36kr/service.ts","../src/36kr/runtime.ts","../src/toutiao/command.ts","../src/toutiao/output.ts","../src/toutiao/types.ts","../src/toutiao/service.ts","../src/toutiao/runtime.ts","../src/github/command.ts","../src/github/output.ts","../src/github/types.ts","../src/github/service.ts","../src/github/parser.ts","../src/github/runtime.ts"],"sourcesContent":["import { realpathSync } from 'node:fs';\nimport { fileURLToPath } from 'node:url';\n\nimport { createCli } from './cli.js';\n\nexport { createCli } from './cli.js';\nexport type { CliIo, CliRunner, CreateCliOptions } from './cli.js';\n\nexport function isMainEntrypoint(moduleUrl: string, argv: string[]): boolean {\n const scriptPath = argv[1];\n\n if (!scriptPath) {\n return false;\n }\n\n return realpathSync(fileURLToPath(moduleUrl)) === realpathSync(scriptPath);\n}\n\n/* v8 ignore start */\nif (isMainEntrypoint(import.meta.url, process.argv)) {\n const cli = createCli();\n void cli.run(process.argv.slice(2)).then((exitCode) => {\n process.exitCode = exitCode;\n });\n}\n/* v8 ignore end */\n","import { Command, CommanderError } from 'commander';\nimport { ZodError } from 'zod';\n\nimport {\n handleHackerNewsCommandError,\n registerHackerNewsCommands\n} from './hn/command.js';\nimport {\n createDefaultHackerNewsRuntime,\n type HackerNewsRuntime\n} from './hn/runtime.js';\nimport {\n handleKr36CommandError,\n registerKr36Commands\n} from './36kr/command.js';\nimport {\n createDefaultKr36Runtime,\n type Kr36Runtime\n} from './36kr/runtime.js';\nimport {\n handleToutiaoCommandError,\n registerToutiaoCommands\n} from './toutiao/command.js';\nimport {\n createDefaultToutiaoRuntime,\n type ToutiaoRuntime\n} from './toutiao/runtime.js';\nimport {\n handleGitHubCommandError,\n registerGitHubCommands\n} from './github/command.js';\nimport { createDefaultGitHubRuntime } from './github/runtime.js';\nimport type { GitHubRuntime } from './github/types.js';\n\nexport interface CliIo {\n stderr: (value: string) => void;\n stdout: (value: string) => void;\n}\n\nexport interface CliRunner {\n run: (args: string[]) => Promise<number>;\n}\n\nexport interface CreateCliOptions extends Partial<CliIo> {\n githubRuntime?: GitHubRuntime;\n hackerNewsRuntime?: HackerNewsRuntime;\n kr36Runtime?: Kr36Runtime;\n toutiaoRuntime?: ToutiaoRuntime;\n}\n\nexport function createCli(options: CreateCliOptions = {}): CliRunner {\n const io: CliIo = {\n stderr: options.stderr ?? ((value) => process.stderr.write(value)),\n stdout: options.stdout ?? ((value) => process.stdout.write(value))\n };\n const program = new Command()\n .name('ants')\n .description('Move data between systems with composable collectors.')\n .showHelpAfterError()\n .exitOverride();\n\n program.configureOutput({\n outputError: () => undefined,\n writeErr: () => undefined,\n writeOut: (value) => io.stdout(value)\n });\n\n registerKr36Commands(program, {\n runtime: options.kr36Runtime ?? createDefaultKr36Runtime(),\n stderr: io.stderr,\n stdout: io.stdout\n });\n registerHackerNewsCommands(program, {\n runtime: options.hackerNewsRuntime ?? createDefaultHackerNewsRuntime(),\n stderr: io.stderr,\n stdout: io.stdout\n });\n registerGitHubCommands(program, {\n runtime: options.githubRuntime ?? createDefaultGitHubRuntime(),\n stderr: io.stderr,\n stdout: io.stdout\n });\n registerToutiaoCommands(program, {\n runtime: options.toutiaoRuntime ?? createDefaultToutiaoRuntime(),\n stderr: io.stderr,\n stdout: io.stdout\n });\n\n return {\n run: async (args) => {\n try {\n await program.parseAsync(args, { from: 'user' });\n return 0;\n } catch (error) {\n if (error instanceof CommanderError && error.exitCode === 0) {\n return 0;\n }\n\n const githubExitCode = handleGitHubCommandError(error, io);\n if (githubExitCode !== undefined) {\n return githubExitCode;\n }\n\n const toutiaoExitCode = handleToutiaoCommandError(error, io);\n if (toutiaoExitCode !== undefined) {\n return toutiaoExitCode;\n }\n\n const hackerNewsExitCode = handleHackerNewsCommandError(error, io);\n if (hackerNewsExitCode !== undefined) {\n return hackerNewsExitCode;\n }\n\n const kr36ExitCode = handleKr36CommandError(error, io);\n if (kr36ExitCode !== undefined) {\n return kr36ExitCode;\n }\n\n if (error instanceof ZodError || error instanceof CommanderError) {\n const message = error instanceof ZodError\n ? error.issues[0]?.message ?? 'Invalid command arguments.'\n : error.message;\n writeCliError(io, 'INVALID_ARGUMENT', message);\n return 2;\n }\n\n writeCliError(\n io,\n 'INTERNAL_ERROR',\n 'An unexpected internal error occurred.'\n );\n return 1;\n }\n }\n };\n}\n\nfunction writeCliError(io: CliIo, code: string, message: string): void {\n io.stderr(`${JSON.stringify({\n ok: false,\n error: {\n code,\n message\n }\n }, null, 2)}\\n`);\n}\n","import type { Command } from 'commander';\nimport { z } from 'zod';\n\nimport {\n renderHackerNewsCommandErrorAsJson,\n renderHackerNewsSearchAsJson,\n renderHackerNewsSearchAsTable,\n renderHackerNewsStoriesAsJson,\n renderHackerNewsStoriesAsTable\n} from './output.js';\nimport type { HackerNewsRuntime } from './runtime.js';\nimport { HackerNewsService } from './service.js';\nimport { HackerNewsCommandError, type HackerNewsStorySource } from './types.js';\n\nexport interface HackerNewsCommandDependencies {\n runtime: HackerNewsRuntime;\n stderr: (value: string) => void;\n stdout: (value: string) => void;\n}\n\nconst storiesOptionsSchema = z.object({\n format: z.enum(['json', 'table']).default('json'),\n limit: z.number().int().default(30),\n table: z.boolean().optional()\n});\n\nconst searchOptionsSchema = z.object({\n format: z.enum(['json', 'table']).default('json'),\n limit: z.number().int().default(30),\n sort: z.enum(['relevance', 'date']).default('relevance'),\n table: z.boolean().optional()\n});\n\nexport function registerHackerNewsCommands(\n program: Command,\n dependencies: HackerNewsCommandDependencies\n): void {\n const hn = program\n .command('hn')\n .alias('hackernews')\n .description('Fetch Hacker News stories and search results.');\n const service = new HackerNewsService({ runtime: dependencies.runtime });\n\n for (const source of ['top', 'new', 'best'] as const) {\n hn.command(source)\n .option('--limit <limit>', 'number of stories to fetch', parseLimit, 30)\n .option('--format <format>', 'output format', 'json')\n .option('-t, --table', 'render as a table')\n .action(async (options) => {\n const parsed = storiesOptionsSchema.parse(applyTableShortcut(options));\n const result = await service.stories({\n limit: parsed.limit,\n source\n });\n dependencies.stdout(\n parsed.format === 'table'\n ? `${renderHackerNewsStoriesAsTable(result)}\\n`\n : `${renderHackerNewsStoriesAsJson(result)}\\n`\n );\n });\n }\n\n hn.command('search')\n .argument('<query>', 'search query')\n .option('--limit <limit>', 'number of search results to fetch', parseLimit, 30)\n .option('--sort <sort>', 'search sort: relevance or date', 'relevance')\n .option('--format <format>', 'output format', 'json')\n .option('-t, --table', 'render as a table')\n .action(async (query, options) => {\n const parsed = searchOptionsSchema.parse(applyTableShortcut(options));\n const result = await service.search({\n limit: parsed.limit,\n query,\n sort: parsed.sort\n });\n dependencies.stdout(\n parsed.format === 'table'\n ? `${renderHackerNewsSearchAsTable(result)}\\n`\n : `${renderHackerNewsSearchAsJson(result)}\\n`\n );\n });\n}\n\nexport function handleHackerNewsCommandError(\n error: unknown,\n dependencies: Pick<HackerNewsCommandDependencies, 'stderr'>\n): number | undefined {\n if (error instanceof HackerNewsCommandError) {\n dependencies.stderr(\n `${renderHackerNewsCommandErrorAsJson(error.code, error.message, error.details)}\\n`\n );\n return error.exitCode;\n }\n\n return undefined;\n}\n\nfunction parseLimit(value: string): number {\n const parsed = Number(value);\n\n if (!Number.isInteger(parsed)) {\n throw new HackerNewsCommandError(\n 'HN_INVALID_LIMIT',\n 'Hacker News limit must be an integer between 1 and 100.',\n 2,\n {\n limit: value\n }\n );\n }\n\n return parsed;\n}\n\nfunction applyTableShortcut<T extends { format: string; table?: boolean }>(options: T): T & {\n format: 'json' | 'table';\n} {\n if (options.table) {\n return {\n ...options,\n format: 'table'\n };\n }\n\n return {\n ...options,\n format: options.format as 'json' | 'table'\n };\n}\n","import { stripVTControlCharacters } from 'node:util';\n\nimport { table } from 'table';\n\nfunction sanitizeTableCell(value: unknown): string {\n return stripVTControlCharacters(String(value))\n .replace(/[\\u0000-\\u001f\\u007f-\\u009f]+/g, ' ')\n .replace(/ +/g, ' ')\n .trim();\n}\n\nexport function renderSafeTable(rows: readonly (readonly unknown[])[]): string {\n return table(rows.map((row) => row.map(sanitizeTableCell)));\n}\n","import { renderSafeTable } from '../output.js';\nimport type { HackerNewsSearchResult, HackerNewsStoriesResult } from './types.js';\n\nexport function renderHackerNewsStoriesAsJson(result: HackerNewsStoriesResult): string {\n return JSON.stringify(\n {\n ok: true,\n data: result\n },\n null,\n 2\n );\n}\n\nexport function renderHackerNewsStoriesAsTable(result: HackerNewsStoriesResult): string {\n return renderSafeTable([\n ['id', 'title', 'author', 'score', 'comments', 'time', 'url'],\n ...result.items.map((item) => [\n String(item.id),\n item.title,\n item.author ?? '',\n item.score === undefined ? '' : String(item.score),\n item.commentCount === undefined ? '' : String(item.commentCount),\n item.time?.iso ?? '',\n item.url\n ])\n ]);\n}\n\nexport function renderHackerNewsSearchAsJson(result: HackerNewsSearchResult): string {\n return JSON.stringify(\n {\n ok: true,\n data: result\n },\n null,\n 2\n );\n}\n\nexport function renderHackerNewsSearchAsTable(result: HackerNewsSearchResult): string {\n return renderSafeTable([\n ['id', 'title', 'author', 'score', 'comments', 'time', 'url'],\n ...result.items.map((item) => [\n String(item.id),\n item.title,\n item.author ?? '',\n item.score === undefined ? '' : String(item.score),\n item.commentCount === undefined ? '' : String(item.commentCount),\n item.time?.iso ?? '',\n item.url\n ])\n ]);\n}\n\nexport function renderHackerNewsCommandErrorAsJson(\n code: string,\n message: string,\n details?: unknown\n): string {\n return JSON.stringify(\n {\n ok: false,\n error: {\n code,\n message,\n ...(details === undefined ? {} : { details })\n }\n },\n null,\n 2\n );\n}\n","export type HackerNewsStorySource = 'top' | 'new' | 'best';\nexport type HackerNewsSearchSort = 'relevance' | 'date';\n\nexport interface HackerNewsItem {\n author?: string;\n commentCount?: number;\n id: number;\n score?: number;\n text?: string;\n time?: {\n iso: string;\n seconds: number;\n };\n title: string;\n type: 'story';\n url: string;\n}\n\nexport interface HackerNewsStoriesRuntimeResult {\n items: HackerNewsItem[];\n source: HackerNewsStorySource;\n}\n\nexport interface HackerNewsStoriesResult extends HackerNewsStoriesRuntimeResult {\n meta: {\n limit: number;\n totalItems: number;\n };\n}\n\nexport interface HackerNewsSearchRuntimeResult {\n items: HackerNewsItem[];\n query: string;\n}\n\nexport interface HackerNewsSearchResult extends HackerNewsSearchRuntimeResult {\n meta: {\n limit: number;\n sort: HackerNewsSearchSort;\n totalItems: number;\n };\n}\n\nexport class HackerNewsCommandError extends Error {\n constructor(\n public readonly code: string,\n message: string,\n public readonly exitCode: number,\n public readonly details?: unknown\n ) {\n super(message);\n this.name = 'HackerNewsCommandError';\n }\n}\n","import type { HackerNewsRuntime } from './runtime.js';\nimport {\n HackerNewsCommandError,\n type HackerNewsSearchResult,\n type HackerNewsSearchSort,\n type HackerNewsStoriesResult,\n type HackerNewsStorySource\n} from './types.js';\n\nconst SUPPORTED_SOURCES = new Set<HackerNewsStorySource>(['top', 'new', 'best']);\n\nexport class HackerNewsService {\n constructor(private readonly dependencies: { runtime: HackerNewsRuntime }) {}\n\n async stories(options: {\n limit?: number;\n source: string;\n }): Promise<HackerNewsStoriesResult> {\n const source = parseSource(options.source);\n const limit = normalizeLimit(options.limit);\n const runtimeResult = await this.dependencies.runtime.fetchStories({\n limit,\n source\n });\n\n return {\n ...runtimeResult,\n meta: {\n limit,\n totalItems: runtimeResult.items.length\n }\n };\n }\n\n async search(options: {\n limit?: number;\n query: string;\n sort?: HackerNewsSearchSort;\n }): Promise<HackerNewsSearchResult> {\n const query = normalizeQuery(options.query);\n const limit = normalizeLimit(options.limit);\n const sort = options.sort ?? 'relevance';\n const runtimeResult = await this.dependencies.runtime.fetchSearch({\n limit,\n query,\n sort\n });\n\n return {\n ...runtimeResult,\n meta: {\n limit,\n sort,\n totalItems: runtimeResult.items.length\n }\n };\n }\n}\n\nfunction parseSource(source: string): HackerNewsStorySource {\n if (SUPPORTED_SOURCES.has(source as HackerNewsStorySource)) {\n return source as HackerNewsStorySource;\n }\n\n throw new HackerNewsCommandError(\n 'HN_INVALID_SOURCE',\n 'Hacker News list only supports top, new, and best.',\n 2,\n {\n source,\n supportedSources: [...SUPPORTED_SOURCES]\n }\n );\n}\n\nfunction normalizeLimit(limit: number | undefined): number {\n const value = limit ?? 30;\n\n if (!Number.isInteger(value) || value < 1 || value > 100) {\n throw new HackerNewsCommandError(\n 'HN_INVALID_LIMIT',\n 'Hacker News limit must be an integer between 1 and 100.',\n 2,\n {\n limit: value\n }\n );\n }\n\n return value;\n}\n\nfunction normalizeQuery(query: string): string {\n const value = query.trim();\n\n if (value.length === 0) {\n throw new HackerNewsCommandError(\n 'HN_INVALID_QUERY',\n 'Hacker News search query must not be empty.',\n 2\n );\n }\n\n return value;\n}\n","import {\n HackerNewsCommandError,\n type HackerNewsItem,\n type HackerNewsSearchRuntimeResult,\n type HackerNewsSearchSort,\n type HackerNewsStoriesRuntimeResult,\n type HackerNewsStorySource\n} from './types.js';\n\nexport interface HackerNewsRuntime {\n fetchSearch: (options: {\n limit: number;\n query: string;\n sort: HackerNewsSearchSort;\n }) => Promise<HackerNewsSearchRuntimeResult>;\n fetchStories: (options: {\n limit: number;\n source: HackerNewsStorySource;\n }) => Promise<HackerNewsStoriesRuntimeResult>;\n}\n\nexport interface HackerNewsRuntimeOptions {\n detailConcurrency?: number;\n fetch?: typeof fetch;\n maxResponseBytes?: number;\n requestTimeoutMs?: number;\n}\n\nconst FIREBASE_BASE_URL = 'https://hacker-news.firebaseio.com/v0';\nconst ALGOLIA_BASE_URL = 'https://hn.algolia.com/api/v1';\nconst DEFAULT_DETAIL_CONCURRENCY = 8;\nconst DEFAULT_DETAIL_RESPONSE_BYTES = 256 * 1024;\nconst DEFAULT_MAX_RESPONSE_BYTES = 5 * 1024 * 1024;\nconst DEFAULT_REQUEST_TIMEOUT_MS = 30_000;\nconst SOURCE_TO_ENDPOINT: Record<HackerNewsStorySource, string> = {\n best: 'beststories',\n new: 'newstories',\n top: 'topstories'\n};\n\ninterface RuntimeDependencies {\n detailConcurrency: number;\n fetch: typeof fetch;\n maxResponseBytes: number;\n requestTimeoutMs: number;\n}\n\nexport function createDefaultHackerNewsRuntime(\n options: HackerNewsRuntimeOptions = {}\n): HackerNewsRuntime {\n const dependencies: RuntimeDependencies = {\n detailConcurrency: normalizeDetailConcurrency(options.detailConcurrency),\n fetch: options.fetch ?? fetch,\n maxResponseBytes: options.maxResponseBytes ?? DEFAULT_MAX_RESPONSE_BYTES,\n requestTimeoutMs: options.requestTimeoutMs ?? DEFAULT_REQUEST_TIMEOUT_MS\n };\n\n return {\n fetchSearch: async (request) => fetchSearch(dependencies, request),\n fetchStories: async (request) => fetchStories(dependencies, request)\n };\n}\n\nfunction normalizeDetailConcurrency(value: number | undefined): number {\n if (value === undefined || !Number.isFinite(value)) {\n return DEFAULT_DETAIL_CONCURRENCY;\n }\n return Math.max(1, Math.min(DEFAULT_DETAIL_CONCURRENCY, Math.floor(value)));\n}\n\nasync function fetchStories(\n dependencies: RuntimeDependencies,\n options: {\n limit: number;\n source: HackerNewsStorySource;\n }\n): Promise<HackerNewsStoriesRuntimeResult> {\n const endpoint = SOURCE_TO_ENDPOINT[options.source];\n const ids = await fetchJson<number[]>(\n dependencies,\n `${FIREBASE_BASE_URL}/${endpoint}.json`\n );\n const candidateIds = [...new Set(ids.slice(0, options.limit * 2))];\n const rawItems = await mapOrderedBounded(\n candidateIds,\n dependencies.detailConcurrency,\n async (id) => fetchJson<HackerNewsFirebaseItem | null>(\n dependencies,\n `${FIREBASE_BASE_URL}/item/${id}.json`,\n Math.min(dependencies.maxResponseBytes, DEFAULT_DETAIL_RESPONSE_BYTES)\n )\n );\n\n return {\n items: rawItems.flatMap(mapFirebaseItem).slice(0, options.limit),\n source: options.source\n };\n}\n\nasync function fetchSearch(\n dependencies: RuntimeDependencies,\n options: {\n limit: number;\n query: string;\n sort: HackerNewsSearchSort;\n }\n): Promise<HackerNewsSearchRuntimeResult> {\n const params = new URLSearchParams({\n hitsPerPage: String(options.limit),\n query: options.query,\n tags: 'story'\n });\n const endpoint = options.sort === 'date' ? 'search_by_date' : 'search';\n const response = await fetchJson<HackerNewsAlgoliaResponse>(\n dependencies,\n `${ALGOLIA_BASE_URL}/${endpoint}?${params.toString()}`\n );\n\n return {\n items: response.hits.flatMap(mapAlgoliaHit).slice(0, options.limit),\n query: options.query\n };\n}\n\nasync function fetchJson<T>(\n dependencies: RuntimeDependencies,\n url: string,\n maxResponseBytes = dependencies.maxResponseBytes\n): Promise<T> {\n const controller = new AbortController();\n const timeout = setTimeout(() => controller.abort(), dependencies.requestTimeoutMs);\n\n try {\n let response: Response;\n try {\n response = await dependencies.fetch(url, {\n headers: {\n accept: 'application/json',\n 'user-agent': 'ants-move/0.1 HackerNews collector'\n },\n signal: controller.signal\n });\n } catch (error) {\n throw new HackerNewsCommandError(\n 'HN_FETCH_FAILED',\n 'Failed to fetch Hacker News data.',\n 2,\n {\n cause: error instanceof Error ? error.message : String(error),\n url\n }\n );\n }\n\n if (!response.ok) {\n await cancelResponseBody(response);\n throw new HackerNewsCommandError(\n 'HN_FETCH_FAILED',\n `Failed to fetch Hacker News data. HTTP ${response.status}.`,\n 2,\n { url }\n );\n }\n\n const body = await readBoundedBody(response, maxResponseBytes, url);\n try {\n return JSON.parse(new TextDecoder().decode(body)) as T;\n } catch {\n throw new HackerNewsCommandError(\n 'HN_PARSE_FAILED',\n 'Failed to parse Hacker News JSON.',\n 2,\n { url }\n );\n }\n } finally {\n clearTimeout(timeout);\n }\n}\n\nasync function readBoundedBody(\n response: Response,\n maxBytes: number,\n url: string\n): Promise<Uint8Array> {\n const declaredLength = Number(response.headers.get('content-length'));\n if (Number.isFinite(declaredLength) && declaredLength > maxBytes) {\n await cancelResponseBody(response);\n throw responseTooLarge(url, maxBytes);\n }\n\n const reader = response.body?.getReader();\n if (!reader) {\n return new Uint8Array();\n }\n\n const chunks: Uint8Array[] = [];\n let totalBytes = 0;\n\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n totalBytes += value.byteLength;\n if (totalBytes > maxBytes) {\n await reader.cancel().catch(() => undefined);\n throw responseTooLarge(url, maxBytes);\n }\n chunks.push(value);\n }\n\n const body = new Uint8Array(totalBytes);\n let offset = 0;\n for (const chunk of chunks) {\n body.set(chunk, offset);\n offset += chunk.byteLength;\n }\n return body;\n}\n\nasync function cancelResponseBody(response: Response): Promise<void> {\n await response.body?.cancel().catch(() => undefined);\n}\n\nfunction responseTooLarge(url: string, maxBytes: number): HackerNewsCommandError {\n return new HackerNewsCommandError(\n 'HN_RESPONSE_TOO_LARGE',\n 'Hacker News response exceeded the configured size limit.',\n 2,\n { maxBytes, url }\n );\n}\n\nasync function mapOrderedBounded<T, R>(\n values: readonly T[],\n concurrency: number,\n map: (value: T, index: number) => Promise<R>\n): Promise<R[]> {\n if (values.length === 0) {\n return [];\n }\n\n const results = new Array<R>(values.length);\n let nextIndex = 0;\n let firstError: unknown;\n\n const worker = async () => {\n while (firstError === undefined) {\n const index = nextIndex;\n nextIndex += 1;\n if (index >= values.length) return;\n\n try {\n results[index] = await map(values[index] as T, index);\n } catch (error) {\n firstError ??= error;\n }\n }\n };\n\n const workerCount = Math.max(1, Math.min(\n Math.floor(concurrency),\n values.length\n ));\n await Promise.all(Array.from({ length: workerCount }, worker));\n\n if (firstError !== undefined) {\n throw firstError;\n }\n return results;\n}\n\ninterface HackerNewsFirebaseItem {\n by?: string;\n dead?: boolean;\n deleted?: boolean;\n descendants?: number;\n id?: number;\n score?: number;\n text?: string;\n time?: number;\n title?: string;\n type?: string;\n url?: string;\n}\n\ninterface HackerNewsAlgoliaResponse {\n hits: HackerNewsAlgoliaHit[];\n}\n\ninterface HackerNewsAlgoliaHit {\n author?: string;\n created_at_i?: number;\n num_comments?: number;\n objectID?: string;\n points?: number;\n story_id?: number;\n title?: string;\n url?: string;\n}\n\nfunction mapFirebaseItem(item: HackerNewsFirebaseItem | null): HackerNewsItem[] {\n if (!item || item.deleted || item.dead || item.type !== 'story' || !item.id || !item.title) {\n return [];\n }\n\n return [\n createItem({\n id: item.id,\n title: item.title,\n url: item.url ?? `https://news.ycombinator.com/item?id=${item.id}`,\n ...optional('author', item.by),\n ...optional('commentCount', item.descendants),\n ...optional('score', item.score),\n ...optional('text', item.text),\n ...optional('timeSeconds', item.time)\n })\n ];\n}\n\nfunction mapAlgoliaHit(hit: HackerNewsAlgoliaHit): HackerNewsItem[] {\n const id = hit.story_id ?? parseNumericId(hit.objectID);\n if (!id || !hit.title) {\n return [];\n }\n\n return [\n createItem({\n id,\n title: hit.title,\n url: hit.url ?? `https://news.ycombinator.com/item?id=${id}`,\n ...optional('author', hit.author),\n ...optional('commentCount', hit.num_comments),\n ...optional('score', hit.points),\n ...optional('timeSeconds', hit.created_at_i)\n })\n ];\n}\n\nfunction createItem(input: {\n author?: string;\n commentCount?: number;\n id: number;\n score?: number;\n text?: string;\n timeSeconds?: number;\n title: string;\n url: string;\n}): HackerNewsItem {\n const item: HackerNewsItem = {\n id: input.id,\n title: input.title,\n type: 'story',\n url: input.url\n };\n\n if (input.author !== undefined) item.author = input.author;\n if (input.commentCount !== undefined) item.commentCount = input.commentCount;\n if (input.score !== undefined) item.score = input.score;\n if (input.text !== undefined) item.text = input.text;\n if (input.timeSeconds !== undefined) {\n item.time = {\n iso: new Date(input.timeSeconds * 1000).toISOString(),\n seconds: input.timeSeconds\n };\n }\n\n return item;\n}\n\nfunction optional<K extends string, V>(\n key: K,\n value: V | undefined\n): Partial<Record<K, V>> {\n return value === undefined\n ? {}\n : { [key]: value } as Record<K, V>;\n}\n\nfunction parseNumericId(value: string | undefined): number | undefined {\n if (!value || !/^\\d+$/.test(value)) {\n return undefined;\n }\n return Number(value);\n}\n","import type { Command } from 'commander';\nimport { z } from 'zod';\n\nimport {\n renderKr36ArticleAsJson,\n renderKr36CommandErrorAsJson,\n renderKr36InformationListAsJson,\n renderKr36InformationListAsTable\n} from './output.js';\nimport type { Kr36Runtime } from './runtime.js';\nimport { Kr36ArticleService } from './service.js';\nimport { Kr36CommandError } from './types.js';\n\nexport interface Kr36CommandDependencies {\n runtime: Kr36Runtime;\n stderr: (value: string) => void;\n stdout: (value: string) => void;\n}\n\nconst articleOptionsSchema = z.object({\n format: z.enum(['json']).default('json')\n});\n\nconst informationListOptionsSchema = z.object({\n format: z.enum(['json', 'table']).default('json'),\n pages: z.number().int().min(1).max(20).default(1),\n table: z.boolean().optional()\n});\n\nexport function registerKr36Commands(\n program: Command,\n dependencies: Kr36CommandDependencies\n): void {\n const kr36 = program.command('36kr').description('Fetch and parse 36kr content.');\n const articleService = new Kr36ArticleService(dependencies.runtime);\n\n kr36.command('article')\n .argument('<articleId>', '36kr article id')\n .option('--format <format>', 'output format', 'json')\n .action(async (articleId, options) => {\n articleOptionsSchema.parse(options);\n const article = await articleService.getArticle(articleId);\n dependencies.stdout(`${renderKr36ArticleAsJson(article)}\\n`);\n });\n\n kr36.command('list')\n .argument('<channel>', '36kr information channel: AI or technology')\n .option('--pages <pages>', 'number of pages to fetch', parsePages, 1)\n .option('--format <format>', 'output format', 'json')\n .option('-t, --table', 'render as a table')\n .action(async (channel, options) => {\n const parsed = informationListOptionsSchema.parse(applyTableShortcut(options));\n const list = await articleService.getInformationList({\n channel,\n pages: parsed.pages\n });\n dependencies.stdout(\n parsed.format === 'table'\n ? `${renderKr36InformationListAsTable(list)}\\n`\n : `${renderKr36InformationListAsJson(list)}\\n`\n );\n });\n}\n\nexport function handleKr36CommandError(\n error: unknown,\n dependencies: Pick<Kr36CommandDependencies, 'stderr'>\n): number | undefined {\n if (error instanceof Kr36CommandError) {\n dependencies.stderr(\n `${renderKr36CommandErrorAsJson(error.code, error.message, error.details)}\\n`\n );\n return error.exitCode;\n }\n\n return undefined;\n}\n\nfunction parsePages(value: string): number {\n const parsed = Number(value);\n\n if (!Number.isInteger(parsed)) {\n throw new Kr36CommandError(\n 'KR36_INVALID_PAGES',\n '36kr list pages must be an integer between 1 and 20.',\n 2,\n {\n pages: value\n }\n );\n }\n\n return parsed;\n}\n\nfunction applyTableShortcut<T extends { format: string; table?: boolean }>(options: T): T & {\n format: 'json' | 'table';\n} {\n if (options.table) {\n return {\n ...options,\n format: 'table'\n };\n }\n\n return {\n ...options,\n format: options.format as 'json' | 'table'\n };\n}\n","import { renderSafeTable } from '../output.js';\nimport type { Kr36Article, Kr36InformationList } from './types.js';\n\nexport function renderKr36ArticleAsJson(article: Kr36Article): string {\n return JSON.stringify(\n {\n ok: true,\n data: article\n },\n null,\n 2\n );\n}\n\nexport function renderKr36InformationListAsJson(list: Kr36InformationList): string {\n return JSON.stringify(\n {\n ok: true,\n data: list\n },\n null,\n 2\n );\n}\n\nexport function renderKr36InformationListAsTable(list: Kr36InformationList): string {\n return renderSafeTable([\n ['id', 'title', 'author', 'publishTime', 'url'],\n ...list.items.map((item) => [\n String(item.id),\n item.title,\n item.authorName ?? '',\n item.publishTime?.local ?? '',\n item.url\n ])\n ]);\n}\n\nexport function renderKr36CommandErrorAsJson(\n code: string,\n message: string,\n details?: unknown\n): string {\n return JSON.stringify(\n {\n ok: false,\n error: {\n code,\n message,\n ...(details === undefined ? {} : { details })\n }\n },\n null,\n 2\n );\n}\n","export interface Kr36Request {\n headers: Record<string, string>;\n url: string;\n}\n\nexport interface Kr36JsonRequest {\n body: unknown;\n headers: Record<string, string>;\n url: string;\n}\n\nexport interface Kr36ArticleAuthor {\n face?: string;\n id?: number;\n name: string;\n route?: string;\n summary?: string;\n title?: string;\n}\n\nexport interface Kr36ArticleImage {\n index: number;\n size: string | null;\n url: string;\n}\n\nexport interface Kr36ArticleStats {\n authorArticleCount: number;\n collect: number;\n comment: number;\n favoriteCount: number;\n likeCount: number;\n praise: number;\n}\n\nexport interface Kr36ArticleOrganization {\n briefIntro?: string;\n id: number;\n identityName?: string;\n logo?: string;\n name: string;\n}\n\nexport interface Kr36ArticleListItem {\n author?: string;\n content?: string;\n id: number;\n image?: string;\n publishTime?: number;\n route?: string;\n title: string;\n}\n\nexport interface Kr36Article {\n author: Kr36ArticleAuthor;\n companyCertifyNick?: string;\n content: {\n html: string;\n paragraphs: string[];\n };\n coverImage?: string;\n id: string;\n imageSources: Array<{ name: string; url: string }>;\n images: Kr36ArticleImage[];\n latestArticles: Kr36ArticleListItem[];\n newestArticles: Kr36ArticleListItem[];\n nextArticle?: Kr36ArticleListItem;\n organizations: Kr36ArticleOrganization[];\n publishTime: {\n iso: string;\n local: string;\n ms: number;\n };\n relatedArticles: Kr36ArticleListItem[];\n request: Kr36Request;\n sourceType?: string;\n stats: Kr36ArticleStats;\n summary: string;\n title: string;\n url: string;\n}\n\nexport type Kr36InformationChannel = 'AI' | 'technology';\n\nexport interface Kr36InformationItem {\n authorName?: string;\n authorRoute?: string;\n id: number;\n image?: string;\n publishTime?: {\n iso: string;\n local: string;\n ms: number;\n };\n route?: string;\n summary?: string;\n title: string;\n url: string;\n}\n\nexport interface Kr36InformationList {\n channel: Kr36InformationChannel;\n items: Kr36InformationItem[];\n meta: {\n fetchedPages: number;\n hasNextPage: number;\n nextPageCallback: string;\n pageSize: number;\n totalItems: number;\n };\n request: {\n firstPage: Kr36Request;\n nextPageEndpoint: string;\n };\n}\n\nexport class Kr36CommandError extends Error {\n constructor(\n public readonly code: string,\n message: string,\n public readonly exitCode: number,\n public readonly details?: unknown\n ) {\n super(message);\n this.name = 'Kr36CommandError';\n }\n}\n","import type { Kr36Runtime } from './runtime.js';\nimport {\n Kr36CommandError,\n type Kr36Article,\n type Kr36ArticleAuthor,\n type Kr36ArticleImage,\n type Kr36ArticleListItem,\n type Kr36ArticleOrganization,\n type Kr36ArticleStats,\n type Kr36InformationChannel,\n type Kr36InformationItem,\n type Kr36InformationList,\n type Kr36JsonRequest,\n type Kr36Request\n} from './types.js';\n\nexport const KR36_BROWSER_HEADERS: Record<string, string> = {\n Accept: 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8',\n 'Accept-Language': 'zh-CN,zh;q=0.9,en;q=0.8',\n 'Cache-Control': 'no-cache',\n Pragma: 'no-cache',\n Referer: 'https://36kr.com/',\n 'Sec-Fetch-Dest': 'document',\n 'Sec-Fetch-Mode': 'navigate',\n 'Sec-Fetch-Site': 'same-origin',\n 'Sec-Fetch-User': '?1',\n 'Upgrade-Insecure-Requests': '1',\n 'User-Agent':\n 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36'\n};\n\nconst KR36_INFORMATION_ENDPOINT = 'https://gateway.36kr.com/api/mis/nav/ifm/subNav/flow';\nconst KR36_ARTICLE_MAX_RETAINED_BYTES = 20 * 1024 * 1024;\nconst KR36_INFORMATION_MAX_RETAINED_BYTES = 5 * 1024 * 1024;\nconst KR36_INFORMATION_PAGE_SIZE = 30;\nconst KR36_SUPPORTED_CHANNELS = new Set<Kr36InformationChannel>(['AI', 'technology']);\n\nconst KR36_JSON_HEADERS: Record<string, string> = {\n Accept: 'application/json, text/plain, */*',\n 'Accept-Language': KR36_BROWSER_HEADERS['Accept-Language']!,\n 'Content-Type': 'application/json;charset=UTF-8',\n Origin: 'https://36kr.com',\n 'User-Agent': KR36_BROWSER_HEADERS['User-Agent']!\n};\n\ninterface Kr36InitialState {\n articleDetail?: {\n articleDetailData?: {\n data?: Kr36RawArticle;\n };\n articleRecommendData?: Kr36RawRecommendData;\n favoriteCount?: number;\n likeCount?: number;\n organArticleData?: {\n data?: {\n organizationList?: Kr36ArticleOrganization[];\n };\n };\n latestArticle?: {\n articleLatestList?: Array<{ id: number; title: string }>;\n };\n };\n information?: {\n informationList?: Kr36RawInformationList;\n };\n}\n\ninterface Kr36RawArticle {\n author?: string;\n authorFace?: string;\n authorId?: number;\n authorRoute?: string;\n companyCertifyNick?: string;\n imgSources?: Array<{ name: string; url: string }>;\n itemId?: number;\n popinImage?: string;\n publishTime?: number;\n sourceType?: string;\n summary?: string;\n widgetContent?: string;\n widgetTitle?: string;\n}\n\ninterface Kr36RawRecommendData {\n authorFace?: string;\n authorName?: string;\n authorSummary?: string;\n authorTitle?: string;\n newestItemList?: Array<{\n itemContent?: string;\n itemId: number;\n itemRoute?: string;\n itemTitle: string;\n publishTime?: number;\n }>;\n nextItem?: {\n authorId?: number;\n itemContent?: string;\n itemId: number;\n itemRoute?: string;\n itemTitle: string;\n publishTime?: number;\n };\n relateArticleList?: Array<{\n author?: string;\n authorName?: string;\n itemId: number;\n route?: string;\n widgetImage?: string;\n widgetTitle: string;\n }>;\n statArticle?: number;\n statCollect?: number;\n statComment?: number;\n statPraise?: number;\n}\n\ninterface Kr36RawInformationList {\n hasNextPage?: number;\n itemList?: Kr36RawInformationItem[];\n pageCallback?: string;\n}\n\ninterface Kr36RawInformationItem {\n itemId: number;\n route?: string;\n templateMaterial?: {\n authorName?: string;\n authorRoute?: string;\n publishTime?: number;\n summary?: string;\n widgetImage?: string;\n widgetTitle?: string;\n };\n}\n\ninterface Kr36InformationFlowResponse {\n code?: number;\n data?: Kr36RawInformationList;\n msg?: string;\n}\n\nexport class Kr36ArticleService {\n constructor(private readonly runtime: Pick<Kr36Runtime, 'fetchArticleHtml' | 'fetchJson'>) {}\n\n async getArticle(articleId: string): Promise<Kr36Article> {\n assertArticleId(articleId);\n const request = buildKr36ArticleRequest(articleId);\n const html = await this.runtime.fetchArticleHtml(request);\n const initialState = parseInitialState(html);\n const articleDetail = initialState.articleDetail;\n const rawArticle = articleDetail?.articleDetailData?.data;\n\n if (!rawArticle) {\n throw new Kr36CommandError(\n 'KR36_PARSE_ERROR',\n '36kr article data was not found in window.initialState.',\n 2\n );\n }\n\n const contentHtml = rawArticle.widgetContent ?? '';\n const recommend = articleDetail?.articleRecommendData ?? {};\n const publishTime = rawArticle.publishTime ?? 0;\n const article: Kr36Article = {\n author: buildAuthor(rawArticle, recommend),\n content: {\n html: contentHtml,\n paragraphs: extractParagraphs(contentHtml)\n },\n id: String(rawArticle.itemId ?? articleId),\n imageSources: rawArticle.imgSources ?? [],\n images: extractImages(contentHtml),\n latestArticles: (articleDetail?.latestArticle?.articleLatestList ?? []).map((item) => ({\n id: item.id,\n title: item.title\n })),\n newestArticles: (recommend.newestItemList ?? []).map((item) => {\n const listItem: Kr36ArticleListItem = {\n id: item.itemId,\n title: item.itemTitle\n };\n\n if (item.itemContent !== undefined) {\n listItem.content = item.itemContent;\n }\n if (item.publishTime !== undefined) {\n listItem.publishTime = item.publishTime;\n }\n if (item.itemRoute !== undefined) {\n listItem.route = item.itemRoute;\n }\n\n return listItem;\n }),\n organizations: articleDetail?.organArticleData?.data?.organizationList ?? [],\n publishTime: {\n iso: publishTime ? new Date(publishTime).toISOString() : '',\n local: publishTime ? formatChinaTime(publishTime) : '',\n ms: publishTime\n },\n relatedArticles: (recommend.relateArticleList ?? []).map((item) => {\n const listItem: Kr36ArticleListItem = {\n id: item.itemId,\n title: item.widgetTitle\n };\n const author = item.author ?? item.authorName;\n\n if (author !== undefined) {\n listItem.author = author;\n }\n if (item.widgetImage !== undefined) {\n listItem.image = item.widgetImage;\n }\n if (item.route !== undefined) {\n listItem.route = item.route;\n }\n\n return listItem;\n }),\n request,\n stats: buildStats(articleDetail?.likeCount, articleDetail?.favoriteCount, recommend),\n summary: rawArticle.summary ?? '',\n title: rawArticle.widgetTitle ?? '',\n url: request.url\n };\n\n if (rawArticle.companyCertifyNick !== undefined) {\n article.companyCertifyNick = rawArticle.companyCertifyNick;\n }\n\n if (rawArticle.popinImage !== undefined) {\n article.coverImage = rawArticle.popinImage;\n }\n\n if (recommend.nextItem) {\n article.nextArticle = {\n id: recommend.nextItem.itemId,\n title: recommend.nextItem.itemTitle\n };\n\n if (recommend.nextItem.itemContent !== undefined) {\n article.nextArticle.content = recommend.nextItem.itemContent;\n }\n if (recommend.nextItem.publishTime !== undefined) {\n article.nextArticle.publishTime = recommend.nextItem.publishTime;\n }\n if (recommend.nextItem.itemRoute !== undefined) {\n article.nextArticle.route = recommend.nextItem.itemRoute;\n }\n }\n\n if (rawArticle.sourceType !== undefined) {\n article.sourceType = rawArticle.sourceType;\n }\n\n const retainedBytes = Buffer.byteLength(JSON.stringify(article), 'utf8');\n if (retainedBytes > KR36_ARTICLE_MAX_RETAINED_BYTES) {\n throw new Kr36CommandError(\n 'KR36_RESOURCE_LIMIT',\n '36kr article result exceeded the configured size limit.',\n 2,\n {\n maxRetainedBytes: KR36_ARTICLE_MAX_RETAINED_BYTES,\n retainedBytes\n }\n );\n }\n\n return article;\n }\n\n async getInformationList(options: {\n channel: string;\n pages?: number;\n }): Promise<Kr36InformationList> {\n const channel = parseInformationChannel(options.channel);\n const pageLimit = normalizePages(options.pages);\n const firstPageRequest = buildKr36InformationFirstPageRequest(channel);\n const firstPageHtml = await this.runtime.fetchArticleHtml(firstPageRequest);\n const firstPageState = parseInitialState(firstPageHtml);\n const firstPageList = firstPageState.information?.informationList;\n\n if (!firstPageList) {\n throw new Kr36CommandError(\n 'KR36_PARSE_ERROR',\n '36kr information list data was not found in window.initialState.',\n 2\n );\n }\n\n const firstPageItems = mapInformationPageItems(firstPageList.itemList ?? []);\n let retainedBytes = addInformationRetainedBytes(0, firstPageItems);\n const items = [...firstPageItems];\n let pageCallback = firstPageList.pageCallback ?? '';\n let hasNextPage = firstPageList.hasNextPage ?? 0;\n let fetchedPages = 1;\n\n while (fetchedPages < pageLimit && hasNextPage && pageCallback) {\n const request = buildKr36InformationNextPageRequest(channel, pageCallback);\n const response = parseInformationFlowResponse(await this.runtime.fetchJson(request));\n const nextList = response.data ?? {};\n\n const nextItems = mapInformationPageItems(nextList.itemList ?? []);\n retainedBytes = addInformationRetainedBytes(retainedBytes, nextItems);\n items.push(...nextItems);\n pageCallback = nextList.pageCallback ?? '';\n hasNextPage = nextList.hasNextPage ?? 0;\n fetchedPages += 1;\n }\n\n return {\n channel,\n items,\n meta: {\n fetchedPages,\n hasNextPage,\n nextPageCallback: pageCallback,\n pageSize: KR36_INFORMATION_PAGE_SIZE,\n totalItems: items.length\n },\n request: {\n firstPage: firstPageRequest,\n nextPageEndpoint: KR36_INFORMATION_ENDPOINT\n }\n };\n }\n}\n\nexport function buildKr36ArticleUrl(articleId: string): string {\n assertArticleId(articleId);\n return `https://36kr.com/p/${articleId}?f=rss`;\n}\n\nexport function buildKr36ArticleRequest(articleId: string): Kr36Request {\n return {\n headers: KR36_BROWSER_HEADERS,\n url: buildKr36ArticleUrl(articleId)\n };\n}\n\nexport function buildKr36InformationFirstPageRequest(channel: Kr36InformationChannel): Kr36Request {\n return {\n headers: KR36_BROWSER_HEADERS,\n url: `https://36kr.com/information/${channel}/`\n };\n}\n\nexport function buildKr36InformationNextPageRequest(\n channel: Kr36InformationChannel,\n pageCallback: string,\n timestamp = Date.now()\n): Kr36JsonRequest {\n return {\n body: {\n partner_id: 'web',\n timestamp,\n param: {\n subnavType: 1,\n subnavNick: channel,\n pageSize: KR36_INFORMATION_PAGE_SIZE,\n pageEvent: 1,\n pageCallback,\n siteId: 1,\n platformId: 2\n }\n },\n headers: {\n ...KR36_JSON_HEADERS,\n Referer: `https://36kr.com/information/${channel}/`\n },\n url: KR36_INFORMATION_ENDPOINT\n };\n}\n\nfunction assertArticleId(articleId: string): void {\n if (!/^\\d+$/.test(articleId)) {\n throw new Kr36CommandError(\n 'KR36_INVALID_ARTICLE_ID',\n '36kr article id must contain digits only.',\n 2,\n {\n articleId\n }\n );\n }\n}\n\nfunction parseInformationChannel(channel: string): Kr36InformationChannel {\n if (KR36_SUPPORTED_CHANNELS.has(channel as Kr36InformationChannel)) {\n return channel as Kr36InformationChannel;\n }\n\n throw new Kr36CommandError(\n 'KR36_INVALID_CHANNEL',\n '36kr list only supports AI and technology channels.',\n 2,\n {\n channel,\n supportedChannels: [...KR36_SUPPORTED_CHANNELS]\n }\n );\n}\n\nfunction normalizePages(pages: number | undefined): number {\n const value = pages ?? 1;\n\n if (!Number.isInteger(value) || value < 1 || value > 20) {\n throw new Kr36CommandError(\n 'KR36_INVALID_PAGES',\n '36kr list pages must be an integer between 1 and 20.',\n 2,\n {\n pages: value\n }\n );\n }\n\n return value;\n}\n\nfunction parseInitialState(html: string): Kr36InitialState {\n const match = /window\\.initialState=(\\{[\\s\\S]*?\\})\\s*;?\\s*<\\/script>/.exec(html);\n\n if (!match?.[1]) {\n throw new Kr36CommandError(\n 'KR36_PARSE_ERROR',\n 'window.initialState was not found in the 36kr article page.',\n 2\n );\n }\n\n try {\n return JSON.parse(match[1]) as Kr36InitialState;\n } catch (error) {\n throw new Kr36CommandError(\n 'KR36_PARSE_ERROR',\n 'Failed to parse window.initialState from the 36kr article page.',\n 2,\n {\n cause: error instanceof Error ? error.message : String(error)\n }\n );\n }\n}\n\nfunction extractImages(html: string): Kr36ArticleImage[] {\n return [...html.matchAll(/<img\\b[^>]*>/gi)].map((match, index) => {\n const tag = match[0];\n return {\n index: index + 1,\n size: getAttribute(tag, 'data-img-size-val'),\n url: getAttribute(tag, 'src') ?? ''\n };\n }).filter((image) => image.url);\n}\n\nfunction parseInformationFlowResponse(jsonText: string): Kr36InformationFlowResponse {\n try {\n const response = JSON.parse(jsonText) as Kr36InformationFlowResponse;\n\n if (response.code !== 0) {\n throw new Kr36CommandError(\n 'KR36_REQUEST_FAILED',\n response.msg || '36kr information flow request failed.',\n 1,\n {\n code: response.code\n }\n );\n }\n\n return response;\n } catch (error) {\n if (error instanceof Kr36CommandError) {\n throw error;\n }\n\n throw new Kr36CommandError(\n 'KR36_PARSE_ERROR',\n 'Failed to parse 36kr information flow response.',\n 2,\n {\n cause: error instanceof Error ? error.message : String(error)\n }\n );\n }\n}\n\nfunction mapInformationItems(items: Kr36RawInformationItem[]): Kr36InformationItem[] {\n return items.map((item) => {\n const material = item.templateMaterial ?? {};\n const mapped: Kr36InformationItem = {\n id: item.itemId,\n title: material.widgetTitle ?? '',\n url: `https://36kr.com/p/${item.itemId}`\n };\n\n if (material.authorName !== undefined) {\n mapped.authorName = material.authorName;\n }\n if (material.authorRoute !== undefined) {\n mapped.authorRoute = material.authorRoute;\n }\n if (material.widgetImage !== undefined) {\n mapped.image = material.widgetImage;\n }\n if (material.publishTime !== undefined) {\n mapped.publishTime = {\n iso: new Date(material.publishTime).toISOString(),\n local: formatChinaTime(material.publishTime),\n ms: material.publishTime\n };\n }\n if (item.route !== undefined) {\n mapped.route = item.route;\n }\n if (material.summary !== undefined) {\n mapped.summary = material.summary;\n }\n\n return mapped;\n });\n}\n\nfunction mapInformationPageItems(items: Kr36RawInformationItem[]): Kr36InformationItem[] {\n if (items.length > KR36_INFORMATION_PAGE_SIZE) {\n throw new Kr36CommandError(\n 'KR36_RESOURCE_LIMIT',\n '36kr information response exceeded the configured item limit.',\n 2,\n {\n maxItemsPerPage: KR36_INFORMATION_PAGE_SIZE,\n receivedItems: items.length\n }\n );\n }\n return mapInformationItems(items);\n}\n\nfunction addInformationRetainedBytes(\n retainedBytes: number,\n items: Kr36InformationItem[]\n): number {\n const nextRetainedBytes = retainedBytes\n + Buffer.byteLength(JSON.stringify(items), 'utf8');\n if (nextRetainedBytes > KR36_INFORMATION_MAX_RETAINED_BYTES) {\n throw new Kr36CommandError(\n 'KR36_RESOURCE_LIMIT',\n '36kr information results exceeded the configured size limit.',\n 2,\n {\n maxRetainedBytes: KR36_INFORMATION_MAX_RETAINED_BYTES,\n retainedBytes: nextRetainedBytes\n }\n );\n }\n return nextRetainedBytes;\n}\n\nfunction extractParagraphs(html: string): string[] {\n return html\n .replace(/<script[\\s\\S]*?<\\/script>/gi, '')\n .replace(/<style[\\s\\S]*?<\\/style>/gi, '')\n .replace(/<[^>]+>/g, '\\n')\n .split(/\\n+/)\n .map((value) => decodeHtmlEntities(value).trim())\n .filter(Boolean);\n}\n\nfunction getAttribute(tag: string, name: string): string | null {\n const match = new RegExp(`${name}=[\"']([^\"']+)[\"']`, 'i').exec(tag);\n return match?.[1] ?? null;\n}\n\nfunction decodeHtmlEntities(value: string): string {\n return value\n .replace(/ /g, ' ')\n .replace(/"/g, '\"')\n .replace(/'/g, \"'\")\n .replace(/</g, '<')\n .replace(/>/g, '>')\n .replace(/&/g, '&');\n}\n\nfunction buildStats(\n likeCount: number | undefined,\n favoriteCount: number | undefined,\n recommend: Kr36RawRecommendData\n): Kr36ArticleStats {\n return {\n authorArticleCount: recommend.statArticle ?? 0,\n collect: recommend.statCollect ?? 0,\n comment: recommend.statComment ?? 0,\n favoriteCount: favoriteCount ?? 0,\n likeCount: likeCount ?? 0,\n praise: recommend.statPraise ?? 0\n };\n}\n\nfunction buildAuthor(\n rawArticle: Kr36RawArticle,\n recommend: Kr36RawRecommendData\n): Kr36ArticleAuthor {\n const author: Kr36ArticleAuthor = {\n name: rawArticle.author ?? recommend.authorName ?? ''\n };\n const face = rawArticle.authorFace ?? recommend.authorFace;\n\n if (face !== undefined) {\n author.face = face;\n }\n if (rawArticle.authorId !== undefined) {\n author.id = rawArticle.authorId;\n }\n if (rawArticle.authorRoute !== undefined) {\n author.route = rawArticle.authorRoute;\n }\n if (recommend.authorSummary !== undefined) {\n author.summary = recommend.authorSummary;\n }\n if (recommend.authorTitle !== undefined) {\n author.title = recommend.authorTitle;\n }\n\n return author;\n}\n\nfunction formatChinaTime(timestampMs: number): string {\n const formatter = new Intl.DateTimeFormat('sv-SE', {\n day: '2-digit',\n hour: '2-digit',\n hour12: false,\n minute: '2-digit',\n month: '2-digit',\n second: '2-digit',\n timeZone: 'Asia/Shanghai',\n year: 'numeric'\n });\n\n return formatter.format(new Date(timestampMs));\n}\n","import { execFile as nodeExecFile } from 'node:child_process';\nimport { promisify } from 'node:util';\n\nimport {\n Kr36CommandError,\n type Kr36JsonRequest,\n type Kr36Request\n} from './types.js';\n\nexport interface Kr36Runtime {\n fetchArticleHtml: (request: Kr36Request) => Promise<string>;\n fetchJson: (request: Kr36JsonRequest) => Promise<string>;\n}\n\nexport type Kr36ExecFile = (\n file: string,\n args: string[],\n options: { encoding: 'utf8'; maxBuffer: number }\n) => Promise<{ stderr: string; stdout: string }>;\n\nconst execFileAsync = promisify(nodeExecFile) as unknown as Kr36ExecFile;\n\nexport function createDefaultKr36Runtime(options: {\n execFile?: Kr36ExecFile;\n} = {}): Kr36Runtime {\n const execFile = options.execFile ?? execFileAsync;\n\n return {\n fetchArticleHtml: async (request) => fetchWithCurl(execFile, request),\n fetchJson: async (request) => fetchWithCurl(execFile, request)\n };\n}\n\nasync function fetchWithCurl(\n execFile: Kr36ExecFile,\n request: Kr36JsonRequest | Kr36Request\n): Promise<string> {\n const args = [\n '--silent',\n '--show-error',\n '--location',\n '--compressed',\n '--connect-timeout',\n '10',\n '--max-time',\n '45',\n ...Object.entries(request.headers).flatMap(([name, value]) => [\n '--header',\n `${name}: ${value}`\n ]),\n ...('body' in request ? ['--data-raw', JSON.stringify(request.body)] : []),\n request.url\n ];\n\n try {\n const result = await execFile('curl', args, {\n encoding: 'utf8',\n maxBuffer: 20 * 1024 * 1024\n });\n return result.stdout;\n } catch (error) {\n const execError = error as Error & { code?: number | string; stderr?: string };\n const failureReason = execError.stderr?.trim() || 'curl request failed.';\n throw new Kr36CommandError(\n 'KR36_REQUEST_FAILED',\n `Failed to fetch 36kr page: ${failureReason}`,\n 1,\n {\n curlExitCode: execError.code,\n url: request.url\n }\n );\n }\n}\n","import type { Command } from 'commander';\nimport { z } from 'zod';\n\nimport {\n renderToutiaoArticleAsJson,\n renderToutiaoAuthorAsJson,\n renderToutiaoAuthorAsTable,\n renderToutiaoCommandErrorAsJson,\n renderToutiaoListAsJson,\n renderToutiaoListAsTable\n} from './output.js';\nimport type { ToutiaoRuntime } from './runtime.js';\nimport { ToutiaoService } from './service.js';\nimport { ToutiaoCommandError } from './types.js';\n\nexport interface ToutiaoCommandDependencies {\n runtime: ToutiaoRuntime;\n stderr: (value: string) => void;\n stdout: (value: string) => void;\n}\n\nconst listOptionsSchema = z.object({\n format: z.enum(['json', 'table']).default('json'),\n pages: z.number().int().min(1).max(5).default(1),\n table: z.boolean().optional()\n});\n\nconst articleOptionsSchema = z.object({\n format: z.enum(['json']).default('json')\n});\n\nconst authorOptionsSchema = z.object({\n format: z.enum(['json', 'table']).default('json'),\n pages: z.number().int().min(1).max(5).default(1),\n table: z.boolean().optional(),\n withContent: z.boolean().default(false)\n});\n\nexport function registerToutiaoCommands(\n program: Command,\n dependencies: ToutiaoCommandDependencies\n): void {\n const toutiao = program.command('toutiao')\n .description('Fetch Toutiao channel and search content.');\n const service = new ToutiaoService({ runtime: dependencies.runtime });\n\n toutiao.command('article')\n .argument('<article>', 'Toutiao article id or URL')\n .option('--format <format>', 'output format', 'json')\n .action(async (article, options) => {\n articleOptionsSchema.parse(options);\n const result = await service.article(article);\n dependencies.stdout(`${renderToutiaoArticleAsJson(result)}\\n`);\n });\n\n toutiao.command('list')\n .argument('<source>', 'Toutiao source: tech, AI, 光刻机, 芯片, or 半导体')\n .option('--pages <pages>', 'number of pages to fetch', parsePages, 1)\n .option('--format <format>', 'output format', 'json')\n .option('-t, --table', 'render as a table')\n .action(async (source, options) => {\n const parsed = listOptionsSchema.parse(applyTableShortcut(options));\n const result = await service.list({\n pages: parsed.pages,\n source\n });\n dependencies.stdout(\n parsed.format === 'table'\n ? `${renderToutiaoListAsTable(result)}\\n`\n : `${renderToutiaoListAsJson(result)}\\n`\n );\n });\n\n toutiao.command('author')\n .argument('<author>', 'Toutiao author token or /c/user/token/<token>/ homepage URL')\n .option('--pages <pages>', 'number of pages to fetch', parsePages, 1)\n .option('--with-content', 'also fetch detail content for each author article')\n .option('--format <format>', 'output format', 'json')\n .option('-t, --table', 'render as a table')\n .action(async (author, options) => {\n const parsed = authorOptionsSchema.parse(applyTableShortcut(options));\n const result = await service.author(author, {\n pages: parsed.pages,\n withContent: parsed.withContent\n });\n dependencies.stdout(\n parsed.format === 'table'\n ? `${renderToutiaoAuthorAsTable(result)}\\n`\n : `${renderToutiaoAuthorAsJson(result)}\\n`\n );\n });\n}\n\nexport function handleToutiaoCommandError(\n error: unknown,\n dependencies: Pick<ToutiaoCommandDependencies, 'stderr'>\n): number | undefined {\n if (error instanceof ToutiaoCommandError) {\n dependencies.stderr(\n `${renderToutiaoCommandErrorAsJson(error.code, error.message, error.details)}\\n`\n );\n return error.exitCode;\n }\n\n return undefined;\n}\n\nfunction parsePages(value: string): number {\n const parsed = Number(value);\n\n if (!Number.isInteger(parsed)) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_INVALID_PAGES',\n 'Toutiao list pages must be an integer between 1 and 5.',\n 2,\n {\n pages: value\n }\n );\n }\n\n return parsed;\n}\n\nfunction applyTableShortcut<T extends { format: string; table?: boolean }>(options: T): T & {\n format: 'json' | 'table';\n} {\n if (options.table) {\n return {\n ...options,\n format: 'table'\n };\n }\n\n return {\n ...options,\n format: options.format as 'json' | 'table'\n };\n}\n","import { renderSafeTable } from '../output.js';\nimport type { ToutiaoArticle, ToutiaoAuthorResult, ToutiaoListResult } from './types.js';\n\nexport function renderToutiaoListAsJson(result: ToutiaoListResult): string {\n return JSON.stringify(\n {\n ok: true,\n data: result\n },\n null,\n 2\n );\n}\n\nexport function renderToutiaoListAsTable(result: ToutiaoListResult): string {\n return renderSafeTable([\n ['id', 'title', 'author', 'publishTime', 'comments', 'url'],\n ...result.items.map((item) => [\n item.id,\n item.title,\n item.authorName ?? '',\n item.publishTime?.local ?? '',\n item.commentCount === undefined ? '' : String(item.commentCount),\n item.url\n ])\n ]);\n}\n\nexport function renderToutiaoArticleAsJson(article: ToutiaoArticle): string {\n return JSON.stringify(\n {\n ok: true,\n data: article\n },\n null,\n 2\n );\n}\n\nexport function renderToutiaoAuthorAsJson(result: ToutiaoAuthorResult): string {\n return JSON.stringify(\n {\n ok: true,\n data: result\n },\n null,\n 2\n );\n}\n\nexport function renderToutiaoAuthorAsTable(result: ToutiaoAuthorResult): string {\n return renderSafeTable([\n ['id', 'title', 'author', 'publishTime', 'comments', 'url'],\n ...result.items.map((item) => [\n item.id,\n item.title,\n item.authorName ?? '',\n item.publishTime?.local ?? '',\n item.commentCount === undefined ? '' : String(item.commentCount),\n item.url\n ])\n ]);\n}\n\nexport function renderToutiaoCommandErrorAsJson(\n code: string,\n message: string,\n details?: unknown\n): string {\n return JSON.stringify(\n {\n ok: false,\n error: {\n code,\n message,\n ...(details === undefined ? {} : { details })\n }\n },\n null,\n 2\n );\n}\n","export type ToutiaoSource = 'tech' | 'AI' | '光刻机' | '芯片' | '半导体';\n\nexport interface ToutiaoItem {\n abstract?: string;\n authorName?: string;\n commentCount?: number;\n id: string;\n image?: string;\n publishTime?: {\n iso: string;\n local: string;\n seconds: number;\n };\n sourceUrl?: string;\n title: string;\n url: string;\n}\n\nexport interface ToutiaoListResult {\n hasMore: boolean;\n items: ToutiaoItem[];\n keyword?: string;\n meta: {\n fetchedPages: number;\n totalItems: number;\n };\n next?: {\n maxBehotTime?: number;\n offset?: number;\n };\n source: ToutiaoSource;\n}\n\nexport interface ToutiaoAuthorRuntimeResult {\n authorToken: string;\n hasMore: boolean;\n items: ToutiaoItem[];\n next?: {\n maxBehotTime?: number;\n offset?: number;\n };\n}\n\nexport interface ToutiaoAuthorResult extends ToutiaoAuthorRuntimeResult {\n articles?: ToutiaoArticle[];\n meta: {\n fetchedPages: number;\n totalArticles?: number;\n totalItems: number;\n withContent: boolean;\n };\n request: {\n input: string;\n url: string;\n };\n}\n\nexport interface ToutiaoArticle {\n authorName?: string;\n content: {\n paragraphs: string[];\n text: string;\n };\n id: string;\n publishTimeText?: string;\n request: {\n input: string;\n url: string;\n };\n title: string;\n url: string;\n}\n\nexport interface ToutiaoRuntimeListResult {\n hasMore: boolean;\n items: ToutiaoItem[];\n keyword?: string;\n next?: {\n maxBehotTime?: number;\n offset?: number;\n };\n source: ToutiaoSource;\n}\n\nexport class ToutiaoCommandError extends Error {\n constructor(\n public readonly code: string,\n message: string,\n public readonly exitCode: number,\n public readonly details?: unknown\n ) {\n super(message);\n this.name = 'ToutiaoCommandError';\n }\n}\n","import type { ToutiaoRuntime } from './runtime.js';\nimport {\n ToutiaoCommandError,\n type ToutiaoArticle,\n type ToutiaoAuthorResult,\n type ToutiaoListResult,\n type ToutiaoSource\n} from './types.js';\n\nconst SUPPORTED_SOURCES = new Set<ToutiaoSource>([\n 'tech',\n 'AI',\n '光刻机',\n '芯片',\n '半导体'\n]);\nconst MAX_AUTHOR_CONTENT_ARTICLES = 100;\nconst MAX_AUTHOR_CONTENT_RETAINED_BYTES = 10 * 1024 * 1024;\n\nexport class ToutiaoService {\n constructor(private readonly dependencies: { runtime: ToutiaoRuntime }) {}\n\n async article(input: string): Promise<ToutiaoArticle> {\n const url = buildToutiaoArticleUrl(input);\n return this.dependencies.runtime.withSession(async (session) =>\n session.fetchArticle({ input, url })\n );\n }\n\n async author(input: string, options: {\n pages?: number;\n withContent?: boolean;\n } = {}): Promise<ToutiaoAuthorResult> {\n const authorToken = buildToutiaoAuthorToken(input);\n const pages = normalizePages(options.pages);\n const url = buildToutiaoAuthorUrl(authorToken);\n const withContent = options.withContent ?? false;\n\n return this.dependencies.runtime.withSession(async (session) => {\n const runtimeResult = await session.fetchAuthorArticles({\n authorToken,\n pages,\n url\n });\n const result: ToutiaoAuthorResult = {\n ...runtimeResult,\n meta: {\n fetchedPages: pages,\n totalItems: runtimeResult.items.length,\n withContent\n },\n request: {\n input,\n url\n }\n };\n\n if (!withContent) {\n return result;\n }\n\n if (runtimeResult.items.length > MAX_AUTHOR_CONTENT_ARTICLES) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_RESOURCE_LIMIT',\n 'Toutiao author content collection supports at most 100 articles per invocation.',\n 2,\n {\n totalItems: runtimeResult.items.length\n }\n );\n }\n\n const articles: ToutiaoArticle[] = [];\n let retainedBytes = 0;\n for (const item of runtimeResult.items) {\n const article = await session.fetchArticle({\n input: item.id,\n url: buildToutiaoArticleUrl(item.url || item.id)\n });\n const nextRetainedBytes = retainedBytes\n + Buffer.byteLength(JSON.stringify(article), 'utf8');\n if (nextRetainedBytes > MAX_AUTHOR_CONTENT_RETAINED_BYTES) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_RESOURCE_LIMIT',\n 'Toutiao author content exceeded the configured size limit.',\n 2,\n {\n maxRetainedBytes: MAX_AUTHOR_CONTENT_RETAINED_BYTES,\n retainedBytes: nextRetainedBytes\n }\n );\n }\n retainedBytes = nextRetainedBytes;\n articles.push(article);\n }\n\n result.articles = articles;\n result.meta.totalArticles = articles.length;\n return result;\n });\n }\n\n async list(options: {\n pages?: number;\n source: string;\n }): Promise<ToutiaoListResult> {\n const source = parseSource(options.source);\n const pages = normalizePages(options.pages);\n\n return this.dependencies.runtime.withSession(async (session) => {\n const runtimeResult = source === 'tech'\n ? await session.fetchTechnologyChannel({ pages })\n : await session.fetchKeywordInformation({\n keyword: source,\n pages,\n source\n });\n\n return {\n ...runtimeResult,\n meta: {\n fetchedPages: pages,\n totalItems: runtimeResult.items.length\n }\n };\n });\n }\n}\n\nexport function buildToutiaoAuthorToken(input: string): string {\n const trimmed = input.trim();\n\n if (/^[A-Za-z0-9._-]+$/.test(trimmed) && trimmed.length >= 12) {\n return trimmed;\n }\n\n try {\n const url = new URL(trimmed);\n const token = /\\/c\\/user\\/token\\/([^/?#]+)/.exec(url.pathname)?.[1];\n\n if (token && isToutiaoHost(url.hostname)) {\n return decodeURIComponent(token);\n }\n } catch {\n // Fall through to the explicit command error below.\n }\n\n throw new ToutiaoCommandError(\n 'TOUTIAO_INVALID_AUTHOR',\n 'Toutiao author must be a user token or a /c/user/token/<token>/ homepage URL.',\n 2,\n {\n input\n }\n );\n}\n\nexport function buildToutiaoAuthorUrl(authorToken: string): string {\n return `https://www.toutiao.com/c/user/token/${encodeURIComponent(authorToken)}/`;\n}\n\nexport function buildToutiaoArticleUrl(input: string): string {\n const trimmed = input.trim();\n\n if (/^\\d+$/.test(trimmed)) {\n return `https://www.toutiao.com/article/${trimmed}/`;\n }\n\n try {\n const url = new URL(trimmed);\n const id = /(?:article|group)\\/(\\d+)/.exec(url.pathname)?.[1]\n ?? /^\\/a(\\d+)/.exec(url.pathname)?.[1];\n\n if (id && isToutiaoHost(url.hostname)) {\n return `https://www.toutiao.com/article/${id}/`;\n }\n\n const nextUrl = url.searchParams.get('url');\n if (nextUrl) {\n return buildToutiaoArticleUrl(nextUrl);\n }\n } catch {\n // Fall through to the explicit command error below.\n }\n\n throw new ToutiaoCommandError(\n 'TOUTIAO_INVALID_ARTICLE',\n 'Toutiao article must be a numeric id or a toutiao article/group URL.',\n 2,\n {\n input\n }\n );\n}\n\nfunction isToutiaoHost(hostname: string): boolean {\n return hostname === 'www.toutiao.com' || hostname === 'toutiao.com';\n}\n\nfunction parseSource(source: string): ToutiaoSource {\n if (SUPPORTED_SOURCES.has(source as ToutiaoSource)) {\n return source as ToutiaoSource;\n }\n\n throw new ToutiaoCommandError(\n 'TOUTIAO_INVALID_SOURCE',\n 'Toutiao list only supports tech, AI, 光刻机, 芯片, and 半导体.',\n 2,\n {\n source,\n supportedSources: [...SUPPORTED_SOURCES]\n }\n );\n}\n\nfunction normalizePages(pages: number | undefined): number {\n const value = pages ?? 1;\n\n if (!Number.isInteger(value) || value < 1 || value > 5) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_INVALID_PAGES',\n 'Toutiao list pages must be an integer between 1 and 5.',\n 2,\n {\n pages: value\n }\n );\n }\n\n return value;\n}\n","import type { Browser, BrowserContext, Page, Response } from 'playwright';\n\nimport {\n ToutiaoCommandError,\n type ToutiaoArticle,\n type ToutiaoAuthorRuntimeResult,\n type ToutiaoItem,\n type ToutiaoRuntimeListResult,\n type ToutiaoSource\n} from './types.js';\n\nexport interface ToutiaoSession {\n fetchArticle: (request: { input: string; url: string }) => Promise<ToutiaoArticle>;\n fetchAuthorArticles: (options: {\n authorToken: string;\n pages: number;\n url: string;\n }) => Promise<ToutiaoAuthorRuntimeResult>;\n fetchKeywordInformation: (options: {\n keyword: ToutiaoSource;\n pages: number;\n source: ToutiaoSource;\n }) => Promise<ToutiaoRuntimeListResult>;\n fetchTechnologyChannel: (\n options: { pages: number }\n ) => Promise<ToutiaoRuntimeListResult>;\n}\n\nexport interface ToutiaoRuntime {\n withSession: <T>(\n operation: (session: ToutiaoSession) => Promise<T>\n ) => Promise<T>;\n}\n\nexport interface ToutiaoRuntimeOptions {\n deadlineMs?: number;\n loadPlaywright?: () => Promise<typeof import('playwright')>;\n}\n\nconst TOUTIAO_USER_AGENT =\n 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36';\nconst TECH_CHANNEL_ID = 3189398999;\nconst DEFAULT_DEADLINE_MS = 10 * 60 * 1000;\nconst MAX_ARTICLE_TEXT_BYTES = 1024 * 1024;\nconst MAX_FEED_ITEMS_PER_RESPONSE = 100;\nconst MAX_FEED_RESPONSE_BYTES = 5 * 1024 * 1024;\nconst MAX_SEARCH_TEXT_BYTES = 1024 * 1024;\nconst BLOCKED_RESOURCE_TYPES = new Set(['font', 'image', 'media']);\n\nexport function createDefaultToutiaoRuntime(\n options: ToutiaoRuntimeOptions = {}\n): ToutiaoRuntime {\n const deadlineMs = options.deadlineMs ?? DEFAULT_DEADLINE_MS;\n const playwrightLoader = options.loadPlaywright ?? loadPlaywright;\n\n return {\n withSession: async <T>(operation: (session: ToutiaoSession) => Promise<T>) => {\n let browser: Browser | undefined;\n let browserClosed = false;\n let context: BrowserContext | undefined;\n let deadlineTriggered = false;\n let operationPromise: Promise<T> | undefined;\n let lifecyclePromise: Promise<T>;\n\n const createTimeoutError = () => new ToutiaoCommandError(\n 'TOUTIAO_TIMEOUT',\n 'Toutiao collection exceeded the command deadline.',\n 1,\n { deadlineMs }\n );\n const ensureWithinDeadline = (): void => {\n if (deadlineTriggered) {\n throw createTimeoutError();\n }\n };\n\n lifecyclePromise = (async () => {\n try {\n let playwright: typeof import('playwright');\n try {\n playwright = await playwrightLoader();\n } catch {\n ensureWithinDeadline();\n throw new ToutiaoCommandError(\n 'TOUTIAO_BROWSER_UNAVAILABLE',\n 'Toutiao collection requires Playwright to be installed.',\n 2\n );\n }\n ensureWithinDeadline();\n\n try {\n browser = await playwright.chromium.launch({ headless: true });\n } catch {\n ensureWithinDeadline();\n throw new ToutiaoCommandError(\n 'TOUTIAO_BROWSER_UNAVAILABLE',\n 'Toutiao collection requires Playwright Chromium to be installed.',\n 2\n );\n }\n if (deadlineTriggered) {\n browserClosed = true;\n await browser.close().catch(() => undefined);\n throw createTimeoutError();\n }\n\n context = await browser.newContext({\n locale: 'zh-CN',\n userAgent: TOUTIAO_USER_AGENT\n });\n ensureWithinDeadline();\n const page = await context.newPage();\n ensureWithinDeadline();\n await page.route('**/*', async (route) => {\n if (BLOCKED_RESOURCE_TYPES.has(route.request().resourceType())) {\n await route.abort();\n return;\n }\n await route.continue();\n });\n ensureWithinDeadline();\n\n operationPromise = Promise.resolve().then(() =>\n operation(createToutiaoSession(page))\n );\n return await operationPromise;\n } finally {\n await context?.close().catch(() => undefined);\n if (!browserClosed) {\n await browser?.close().catch(() => undefined);\n }\n }\n })();\n\n return await new Promise<T>((resolve, reject) => {\n const deadlineTimer = setTimeout(() => {\n deadlineTriggered = true;\n void (async () => {\n if (browser !== undefined) {\n browserClosed = true;\n await browser.close().catch(() => undefined);\n }\n if (operationPromise !== undefined) {\n await operationPromise.then(\n () => undefined,\n () => undefined\n );\n await lifecyclePromise.then(\n () => undefined,\n () => undefined\n );\n }\n reject(createTimeoutError());\n })();\n }, deadlineMs);\n\n void lifecyclePromise.then(\n (value) => {\n if (!deadlineTriggered) {\n clearTimeout(deadlineTimer);\n resolve(value);\n }\n },\n (error: unknown) => {\n if (!deadlineTriggered) {\n clearTimeout(deadlineTimer);\n reject(error);\n }\n }\n );\n });\n }\n };\n}\n\nfunction createToutiaoSession(page: Page): ToutiaoSession {\n return {\n fetchArticle: async (request) => fetchArticle(page, request),\n fetchAuthorArticles: async (options) => fetchAuthorArticles(page, options),\n fetchKeywordInformation: async (options) => fetchKeywordInformation(page, options),\n fetchTechnologyChannel: async (options) => fetchTechnologyChannel(page, options)\n };\n}\n\nasync function fetchArticle(\n page: Page,\n request: { input: string; url: string }\n): Promise<ToutiaoArticle> {\n await page.goto(request.url, {\n timeout: 45000,\n waitUntil: 'domcontentloaded'\n });\n await page.waitForTimeout(5000);\n\n const title = await page.locator('h1').first().innerText({ timeout: 5000 }).catch(() => '');\n const paragraphs = await page.locator('article p').evaluateAll((nodes) =>\n nodes.map((node) => (node.textContent ?? '').trim()).filter(Boolean)\n );\n const bodyText = await page.locator('body').innerText({ timeout: 5000 });\n const extractedTextBytes = Math.max(\n Buffer.byteLength(title, 'utf8'),\n Buffer.byteLength(bodyText, 'utf8'),\n paragraphs.reduce(\n (total, paragraph) => total + Buffer.byteLength(paragraph, 'utf8'),\n 0\n )\n );\n if (extractedTextBytes > MAX_ARTICLE_TEXT_BYTES) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_RESOURCE_LIMIT',\n 'Toutiao article text exceeded the configured size limit.',\n 2,\n {\n maxTextBytes: MAX_ARTICLE_TEXT_BYTES,\n textBytes: extractedTextBytes\n }\n );\n }\n const metadata = extractArticleMetadata(bodyText, title);\n const id = extractArticleId(request.url) ?? extractArticleId(request.input) ?? '';\n\n if (!id || !title || paragraphs.length === 0) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_PARSE_ERROR',\n 'Toutiao article page did not expose title and content.',\n 2,\n {\n input: request.input,\n url: request.url\n }\n );\n }\n\n const article: ToutiaoArticle = {\n content: {\n paragraphs,\n text: paragraphs.join('\\n')\n },\n id,\n request,\n title,\n url: page.url()\n };\n\n if (metadata.authorName !== undefined) {\n article.authorName = metadata.authorName;\n }\n if (metadata.publishTimeText !== undefined) {\n article.publishTimeText = metadata.publishTimeText;\n }\n\n return article;\n}\n\nasync function fetchTechnologyChannel(\n page: Page,\n options: { pages: number }\n): Promise<ToutiaoRuntimeListResult> {\n const feedResponses = await collectFeedResponses(\n page,\n options.pages,\n (response) => response.url().includes('/api/pc/list/feed'),\n async () => {\n await page.goto(\n `https://www.toutiao.com/?channel=tech&source=ch&channel_id=${TECH_CHANNEL_ID}`,\n {\n timeout: 45000,\n waitUntil: 'domcontentloaded'\n }\n );\n }\n );\n const selectedResponses = feedResponses.slice(0, options.pages);\n const items = deduplicateItems(\n selectedResponses.flatMap((response) => mapFeedItems(response.data ?? []))\n );\n const lastResponse = selectedResponses.at(-1);\n\n if (items.length === 0) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_PARSE_ERROR',\n 'Toutiao technology channel did not return feed items.',\n 2\n );\n }\n\n const result: ToutiaoRuntimeListResult = {\n hasMore: lastResponse?.has_more ?? false,\n items,\n source: 'tech'\n };\n addNextPage(result, lastResponse);\n return result;\n}\n\nasync function fetchAuthorArticles(\n page: Page,\n options: {\n authorToken: string;\n pages: number;\n url: string;\n }\n): Promise<ToutiaoAuthorRuntimeResult> {\n const feedResponses = await collectFeedResponses(\n page,\n options.pages,\n (response) => isAuthorFeedResponseUrl(response.url(), options.authorToken),\n async () => {\n await page.goto(options.url, {\n timeout: 45000,\n waitUntil: 'domcontentloaded'\n });\n }\n );\n const selectedResponses = feedResponses.slice(0, options.pages);\n const items = deduplicateItems(\n selectedResponses.flatMap((response) => mapFeedItems(response.data ?? []))\n );\n const lastResponse = selectedResponses.at(-1);\n\n if (items.length === 0) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_PARSE_ERROR',\n 'Toutiao author homepage did not return article feed items.',\n 2,\n {\n authorToken: options.authorToken,\n url: options.url\n }\n );\n }\n\n const result: ToutiaoAuthorRuntimeResult = {\n authorToken: options.authorToken,\n hasMore: lastResponse?.has_more ?? false,\n items\n };\n addNextPage(result, lastResponse);\n return result;\n}\n\nasync function collectFeedResponses(\n page: Page,\n pages: number,\n accepts: (response: Response) => boolean,\n navigate: () => Promise<void>\n): Promise<ToutiaoFeedResponse[]> {\n const feedResponses: ToutiaoFeedResponse[] = [];\n const maxResponseParses = pages * 2;\n const pendingResponses = new Set<Promise<void>>();\n const queuedResponses: Response[] = [];\n let firstResourceError: ToutiaoCommandError | undefined;\n let startedResponseParses = 0;\n\n const startQueuedResponses = (): void => {\n while (\n firstResourceError === undefined\n && queuedResponses.length > 0\n && feedResponses.length + pendingResponses.size < pages\n && startedResponseParses < maxResponseParses\n ) {\n startResponseParse(queuedResponses.shift()!);\n }\n };\n const startResponseParse = (response: Response): void => {\n startedResponseParses += 1;\n const pending = parseFeedResponse(response)\n .then((feedResponse) => {\n feedResponses.push(feedResponse);\n })\n .catch((error: unknown) => {\n if (error instanceof ToutiaoCommandError) {\n firstResourceError ??= error;\n }\n })\n .finally(() => {\n pendingResponses.delete(pending);\n startQueuedResponses();\n });\n pendingResponses.add(pending);\n };\n const handler = (response: Response): void => {\n if (\n !accepts(response)\n || firstResourceError !== undefined\n || feedResponses.length >= pages\n || startedResponseParses + queuedResponses.length >= maxResponseParses\n ) {\n return;\n }\n\n if (feedResponses.length + pendingResponses.size < pages) {\n startResponseParse(response);\n return;\n }\n queuedResponses.push(response);\n };\n\n page.on('response', handler);\n try {\n await navigate();\n await waitForFeedResponses(\n page,\n feedResponses,\n pages,\n () => firstResourceError !== undefined\n );\n while (pendingResponses.size > 0) {\n await Promise.allSettled([...pendingResponses]);\n }\n if (firstResourceError !== undefined) {\n throw firstResourceError;\n }\n return feedResponses;\n } finally {\n page.off('response', handler);\n queuedResponses.length = 0;\n while (pendingResponses.size > 0) {\n await Promise.allSettled([...pendingResponses]);\n }\n }\n}\n\nasync function parseFeedResponse(response: Response): Promise<ToutiaoFeedResponse> {\n const declaredLength = Number(await response.headerValue('content-length'));\n if (Number.isFinite(declaredLength) && declaredLength > MAX_FEED_RESPONSE_BYTES) {\n throw feedResponseTooLarge();\n }\n\n const body = await response.body();\n if (body.byteLength > MAX_FEED_RESPONSE_BYTES) {\n throw feedResponseTooLarge();\n }\n const feedResponse = JSON.parse(body.toString('utf8')) as ToutiaoFeedResponse;\n if (\n Array.isArray(feedResponse.data)\n && feedResponse.data.length > MAX_FEED_ITEMS_PER_RESPONSE\n ) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_RESOURCE_LIMIT',\n 'Toutiao feed response exceeded the configured item limit.',\n 2,\n { maxItems: MAX_FEED_ITEMS_PER_RESPONSE }\n );\n }\n return feedResponse;\n}\n\nfunction feedResponseTooLarge(): ToutiaoCommandError {\n return new ToutiaoCommandError(\n 'TOUTIAO_RESPONSE_TOO_LARGE',\n 'Toutiao feed response exceeded the configured size limit.',\n 2,\n { maxBytes: MAX_FEED_RESPONSE_BYTES }\n );\n}\n\nasync function fetchKeywordInformation(\n page: Page,\n options: {\n keyword: ToutiaoSource;\n pages: number;\n source: ToutiaoSource;\n }\n): Promise<ToutiaoRuntimeListResult> {\n const items: ToutiaoItem[] = [];\n const seen = new Set<string>();\n let blocked = false;\n\n for (let pageIndex = 0; pageIndex < options.pages; pageIndex += 1) {\n const url = buildSearchUrl(options.keyword, pageIndex);\n\n await page.goto(url, {\n timeout: 45000,\n waitUntil: 'domcontentloaded'\n });\n await page.waitForTimeout(5000);\n\n blocked = blocked || await page.locator('#pc_captcha').count() > 0;\n\n for (const item of await extractSearchItemsFromPage(page, options.keyword)) {\n if (seen.has(item.id)) {\n continue;\n }\n seen.add(item.id);\n items.push(item);\n }\n }\n\n if (blocked && items.length === 0) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_VERIFICATION_REQUIRED',\n 'Toutiao search requires browser verification before returning usable results.',\n 1,\n {\n keyword: options.keyword\n }\n );\n }\n\n if (items.length === 0) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_PARSE_ERROR',\n 'Toutiao search page did not expose result items.',\n 2,\n {\n keyword: options.keyword\n }\n );\n }\n\n return {\n hasMore: true,\n items,\n keyword: options.keyword,\n source: options.source\n };\n}\n\nfunction buildSearchUrl(keyword: string, pageIndex: number): string {\n const params = new URLSearchParams({\n action_type: pageIndex === 0 ? 'search' : 'pagination',\n cur_tab_title: 'news',\n dvpf: 'pc',\n from: 'news',\n keyword,\n page_num: String(pageIndex),\n pd: 'information',\n source: pageIndex === 0 ? 'input' : 'pagination'\n });\n\n return `https://so.toutiao.com/search?${params.toString()}`;\n}\n\nasync function waitForFeedResponses(\n page: Page,\n responses: ToutiaoFeedResponse[],\n pages: number,\n shouldStop: () => boolean\n): Promise<void> {\n for (\n let attempt = 0;\n attempt < 45 && responses.length < pages && !shouldStop();\n attempt += 1\n ) {\n await page.waitForTimeout(1000);\n if (responses.length < pages && !shouldStop()) {\n await page.mouse.wheel(0, 4000);\n }\n }\n}\n\ninterface ToutiaoFeedResponse {\n data?: ToutiaoRawFeedItem[];\n has_more?: boolean;\n next?: {\n max_behot_time?: number;\n };\n offset?: number;\n}\n\ninterface ToutiaoRawFeedItem {\n Abstract?: string;\n abstract?: string;\n article_url?: string;\n behot_time?: number;\n comment_count?: number;\n display_url?: string;\n group_id?: string;\n id?: string;\n image_url?: string;\n item_id?: string;\n media_name?: string;\n source?: string;\n source_url?: string;\n title?: string;\n Title?: string;\n}\n\nfunction mapFeedItems(items: ToutiaoRawFeedItem[]): ToutiaoItem[] {\n return items.flatMap((item) => {\n const id = String(item.group_id ?? item.item_id ?? item.id ?? '');\n const title = item.title ?? item.Title ?? '';\n\n if (!id || !title) {\n return [];\n }\n\n const mapped: ToutiaoItem = {\n id,\n title,\n url: normalizeArticleUrl(item.article_url ?? item.display_url ?? item.source_url, id)\n };\n\n const abstract = item.Abstract ?? item.abstract;\n if (abstract !== undefined) {\n mapped.abstract = abstract;\n }\n if (item.comment_count !== undefined) {\n mapped.commentCount = item.comment_count;\n }\n if (item.image_url !== undefined) {\n mapped.image = item.image_url;\n }\n const authorName = item.media_name ?? item.source;\n if (authorName !== undefined) {\n mapped.authorName = authorName;\n }\n if (item.source_url !== undefined) {\n mapped.sourceUrl = item.source_url;\n }\n if (item.behot_time !== undefined) {\n mapped.publishTime = {\n iso: new Date(item.behot_time * 1000).toISOString(),\n local: formatChinaTime(item.behot_time),\n seconds: item.behot_time\n };\n }\n\n return [mapped];\n });\n}\n\nfunction deduplicateItems(items: ToutiaoItem[]): ToutiaoItem[] {\n const seen = new Set<string>();\n return items.filter((item) => {\n if (seen.has(item.id)) {\n return false;\n }\n seen.add(item.id);\n return true;\n });\n}\n\nfunction addNextPage(\n result: ToutiaoAuthorRuntimeResult | ToutiaoRuntimeListResult,\n response: ToutiaoFeedResponse | undefined\n): void {\n const next: NonNullable<typeof result.next> = {};\n if (response?.next?.max_behot_time !== undefined) {\n next.maxBehotTime = response.next.max_behot_time;\n }\n if (response?.offset !== undefined) {\n next.offset = response.offset;\n }\n if (Object.keys(next).length > 0) {\n result.next = next;\n }\n}\n\nfunction normalizeArticleUrl(value: string | undefined, id: string): string {\n if (!value) {\n return `https://www.toutiao.com/article/${id}/`;\n }\n\n try {\n const url = new URL(value, 'https://www.toutiao.com');\n return parseToutiaoArticleLink(url.toString())?.url\n ?? `https://www.toutiao.com/article/${id}/`;\n } catch {\n return `https://www.toutiao.com/article/${id}/`;\n }\n}\n\nasync function extractSearchItemsFromPage(\n page: Page,\n keyword: string\n): Promise<ToutiaoItem[]> {\n const anchors = await page.locator('a').evaluateAll((nodes) =>\n nodes.slice(0, 300).map((node) => ({\n href: (node as HTMLAnchorElement).href.slice(0, 2048),\n text: (node.textContent ?? '').trim().replace(/\\s+/g, ' ').slice(0, 1000)\n }))\n );\n const seen = new Set<string>();\n const items: ToutiaoItem[] = [];\n\n for (const anchor of anchors) {\n const articleLink = parseToutiaoArticleLink(anchor.href);\n\n if (!articleLink || !anchor.text || anchor.text.length < 6 || seen.has(articleLink.id)) {\n continue;\n }\n\n seen.add(articleLink.id);\n items.push({\n id: articleLink.id,\n title: anchor.text.slice(0, 180),\n url: articleLink.url\n });\n\n if (items.length >= 30) {\n break;\n }\n }\n\n if (items.length > 0) {\n return items;\n }\n\n const bodyText = await page.locator('body').innerText({ timeout: 5000 });\n const textBytes = Buffer.byteLength(bodyText, 'utf8');\n if (textBytes > MAX_SEARCH_TEXT_BYTES) {\n throw new ToutiaoCommandError(\n 'TOUTIAO_RESOURCE_LIMIT',\n 'Toutiao search text exceeded the configured size limit.',\n 2,\n {\n maxTextBytes: MAX_SEARCH_TEXT_BYTES,\n textBytes\n }\n );\n }\n return extractSearchItemsFromText(bodyText, keyword);\n}\n\nfunction extractSearchItemsFromText(text: string, keyword: string): ToutiaoItem[] {\n const blockedPrefixes = new Set([\n '无障碍 今日头条首页 登录 综合 资讯 视频 图片 用户 小视频 微头条 音乐 去抖音搜'\n ]);\n const lines = text\n .split(/\\n+/)\n .map((line) => line.trim())\n .filter((line) => line.length >= 12 && !blockedPrefixes.has(line));\n\n const seen = new Set<string>();\n const items: ToutiaoItem[] = [];\n\n for (const line of lines) {\n const normalized = line.replace(/\\s+/g, ' ');\n if (seen.has(normalized)) {\n continue;\n }\n seen.add(normalized);\n items.push({\n id: createSearchItemId(keyword, normalized, items.length),\n title: normalized.slice(0, 180),\n url: `https://so.toutiao.com/search?keyword=${encodeURIComponent(keyword)}&pd=information&dvpf=pc&source=input`\n });\n\n if (items.length >= 30) {\n break;\n }\n }\n\n return items;\n}\n\nfunction parseToutiaoArticleLink(\n href: string,\n depth = 0\n): { id: string; url: string } | undefined {\n if (depth > 3) {\n return undefined;\n }\n\n const directId = extractArticleId(href);\n\n if (directId) {\n return {\n id: directId,\n url: `https://www.toutiao.com/article/${directId}/`\n };\n }\n\n try {\n const url = new URL(href);\n const nextUrl = url.searchParams.get('url');\n\n if (nextUrl) {\n return parseToutiaoArticleLink(nextUrl, depth + 1);\n }\n } catch {\n return undefined;\n }\n\n return undefined;\n}\n\nfunction extractArticleMetadata(bodyText: string, title: string): {\n authorName?: string;\n publishTimeText?: string;\n} {\n const lines = bodyText.split(/\\n+/).map((line) => line.trim()).filter(Boolean);\n const titleIndex = lines.findIndex((line) => line === title);\n const metadataLine = titleIndex >= 0 ? lines[titleIndex + 1] : undefined;\n const match = metadataLine?.match(/^(.+?)·(.+)$/);\n\n if (!match?.[1] || !match[2]) {\n return {};\n }\n\n return {\n authorName: match[2],\n publishTimeText: match[1]\n };\n}\n\nfunction extractArticleId(value: string): string | undefined {\n return /(?:article|group)\\/(\\d+)/.exec(value)?.[1]\n ?? /\\/a(\\d+)/.exec(value)?.[1]\n ?? (/^\\d+$/.test(value) ? value : undefined);\n}\n\nfunction isAuthorFeedResponseUrl(value: string, authorToken: string): boolean {\n try {\n const url = new URL(value);\n const isProfileArticleFeed = url.pathname.includes('/api/pc/list/feed')\n && (\n url.searchParams.get('category') === 'pc_profile_article'\n || url.searchParams.get('author_token') === authorToken\n );\n const isProfileAllFeed = url.pathname.includes('/api/pc/list/user/feed')\n && url.searchParams.get('category') === 'profile_all'\n && url.searchParams.get('token') === authorToken;\n\n return isProfileArticleFeed || isProfileAllFeed;\n } catch {\n return (\n value.includes('/api/pc/list/feed')\n && (value.includes('pc_profile_article') || value.includes(authorToken))\n ) || (\n value.includes('/api/pc/list/user/feed')\n && value.includes('profile_all')\n && value.includes(authorToken)\n );\n }\n}\n\nfunction createSearchItemId(keyword: string, value: string, index: number): string {\n let hash = 2166136261;\n const input = `${keyword}:${index}:${value}`;\n\n for (const char of input) {\n hash ^= char.charCodeAt(0);\n hash = Math.imul(hash, 16777619);\n }\n\n return `search-${(hash >>> 0).toString(16)}`;\n}\n\nfunction formatChinaTime(timestampSeconds: number): string {\n return new Intl.DateTimeFormat('sv-SE', {\n day: '2-digit',\n hour: '2-digit',\n hour12: false,\n minute: '2-digit',\n month: '2-digit',\n second: '2-digit',\n timeZone: 'Asia/Shanghai',\n year: 'numeric'\n }).format(new Date(timestampSeconds * 1000));\n}\n\nasync function loadPlaywright(): Promise<typeof import('playwright')> {\n return await import('playwright');\n}\n","import type { Command } from 'commander';\nimport { z } from 'zod';\n\nimport {\n renderGitHubCommandErrorAsJson,\n renderGitHubTrendingAsJson,\n renderGitHubTrendingAsTable\n} from './output.js';\nimport { GitHubService } from './service.js';\nimport {\n GitHubCommandError,\n type GitHubRuntime\n} from './types.js';\n\nexport interface GitHubCommandDependencies {\n runtime: GitHubRuntime;\n stderr: (value: string) => void;\n stdout: (value: string) => void;\n}\n\nconst trendingOptionsSchema = z.object({\n format: z.enum(['json', 'table']).default('json'),\n since: z.string().default('daily'),\n table: z.boolean().optional()\n});\n\nexport function registerGitHubCommands(\n program: Command,\n dependencies: GitHubCommandDependencies\n): void {\n const github = program\n .command('github')\n .description('Fetch GitHub Trending repositories.');\n const service = new GitHubService({ runtime: dependencies.runtime });\n\n github.command('trending')\n .description('Fetch the all-language GitHub Trending page.')\n .option(\n '--since <period>',\n 'trending period: daily, weekly, or monthly',\n 'daily'\n )\n .option('--format <format>', 'output format', 'json')\n .option('-t, --table', 'render as a table')\n .action(async (options) => {\n const parsed = trendingOptionsSchema.parse(applyTableShortcut(options));\n const result = await service.trending({ period: parsed.since });\n dependencies.stdout(\n parsed.format === 'table'\n ? `${renderGitHubTrendingAsTable(result)}\\n`\n : `${renderGitHubTrendingAsJson(result)}\\n`\n );\n });\n}\n\nexport function handleGitHubCommandError(\n error: unknown,\n dependencies: Pick<GitHubCommandDependencies, 'stderr'>\n): number | undefined {\n if (error instanceof GitHubCommandError) {\n dependencies.stderr(\n `${renderGitHubCommandErrorAsJson(error.code, error.message, error.details)}\\n`\n );\n return error.exitCode;\n }\n\n return undefined;\n}\n\nfunction applyTableShortcut<T extends { format: string; table?: boolean }>(options: T): T & {\n format: 'json' | 'table';\n} {\n if (options.table) {\n return {\n ...options,\n format: 'table'\n };\n }\n\n return {\n ...options,\n format: options.format as 'json' | 'table'\n };\n}\n","import { renderSafeTable } from '../output.js';\nimport type { GitHubTrendingResult } from './types.js';\n\nexport function renderGitHubTrendingAsJson(result: GitHubTrendingResult): string {\n return JSON.stringify(\n {\n ok: true,\n data: result\n },\n null,\n 2\n );\n}\n\nexport function renderGitHubTrendingAsTable(result: GitHubTrendingResult): string {\n return renderSafeTable([\n [\n 'rank',\n 'repository',\n 'language',\n 'stars',\n 'forks',\n 'period stars',\n 'description',\n 'url'\n ],\n ...result.items.map((item) => [\n String(item.rank),\n item.fullName,\n item.language ?? '',\n String(item.stars),\n String(item.forks),\n String(item.starsInPeriod),\n item.description ?? '',\n item.url\n ])\n ]);\n}\n\nexport function renderGitHubCommandErrorAsJson(\n code: string,\n message: string,\n details?: unknown\n): string {\n return JSON.stringify(\n {\n ok: false,\n error: {\n code,\n message,\n ...(details === undefined ? {} : { details })\n }\n },\n null,\n 2\n );\n}\n","export type GitHubTrendingPeriod = 'daily' | 'weekly' | 'monthly';\n\nexport interface GitHubTrendingContributor {\n avatarUrl: string;\n url: string;\n username: string;\n}\n\nexport interface GitHubTrendingRepository {\n builtBy?: GitHubTrendingContributor[];\n description?: string;\n forks: number;\n fullName: string;\n language?: string;\n name: string;\n owner: string;\n rank: number;\n stars: number;\n starsInPeriod: number;\n url: string;\n}\n\nexport interface GitHubTrendingRuntimeResult {\n items: GitHubTrendingRepository[];\n period: GitHubTrendingPeriod;\n sourceUrl: string;\n}\n\nexport interface GitHubRuntime {\n fetchTrending: (options: {\n period: GitHubTrendingPeriod;\n }) => Promise<GitHubTrendingRuntimeResult>;\n}\n\nexport interface GitHubTrendingResult extends GitHubTrendingRuntimeResult {\n meta: {\n totalItems: number;\n };\n}\n\nexport class GitHubCommandError extends Error {\n constructor(\n public readonly code: string,\n message: string,\n public readonly exitCode: number,\n public readonly details?: unknown\n ) {\n super(message);\n this.name = 'GitHubCommandError';\n }\n}\n","import {\n GitHubCommandError,\n type GitHubRuntime,\n type GitHubTrendingPeriod,\n type GitHubTrendingResult\n} from './types.js';\n\nconst SUPPORTED_PERIODS = ['daily', 'weekly', 'monthly'] as const;\nconst SUPPORTED_PERIOD_SET = new Set<string>(SUPPORTED_PERIODS);\n\nexport class GitHubService {\n constructor(private readonly dependencies: { runtime: GitHubRuntime }) {}\n\n async trending(options: { period?: string }): Promise<GitHubTrendingResult> {\n const period = parsePeriod(options.period);\n const result = await this.dependencies.runtime.fetchTrending({ period });\n\n return {\n ...result,\n meta: {\n totalItems: result.items.length\n }\n };\n }\n}\n\nfunction parsePeriod(period: string | undefined): GitHubTrendingPeriod {\n const value = period ?? 'daily';\n\n if (SUPPORTED_PERIOD_SET.has(value)) {\n return value as GitHubTrendingPeriod;\n }\n\n throw new GitHubCommandError(\n 'GITHUB_INVALID_PERIOD',\n 'GitHub Trending period must be daily, weekly, or monthly.',\n 2,\n {\n period: value,\n supportedPeriods: [...SUPPORTED_PERIODS]\n }\n );\n}\n","import { load } from 'cheerio';\n\nimport {\n GitHubCommandError,\n type GitHubTrendingContributor,\n type GitHubTrendingPeriod,\n type GitHubTrendingRepository,\n type GitHubTrendingRuntimeResult\n} from './types.js';\n\nexport interface ParseGitHubTrendingHtmlOptions {\n maxBuiltBy: number;\n maxItems: number;\n period: GitHubTrendingPeriod;\n sourceUrl: string;\n}\n\nconst GITHUB_ORIGIN = 'https://github.com';\nconst PERIOD_LABEL: Record<GitHubTrendingPeriod, string> = {\n daily: 'today',\n monthly: 'this month',\n weekly: 'this week'\n};\n\nexport function parseGitHubTrendingHtml(\n html: string,\n options: ParseGitHubTrendingHtmlOptions\n): GitHubTrendingRuntimeResult {\n const $ = load(html);\n const items: GitHubTrendingRepository[] = [];\n\n $('article.Box-row').each((_, element) => {\n const row = $(element);\n const repository = parseRepositoryLink(\n row.find('h2 a[href]').first().attr('href')\n );\n\n if (!repository) {\n return;\n }\n\n if (items.length >= options.maxItems) {\n throw new GitHubCommandError(\n 'GITHUB_PARSE_FAILED',\n 'GitHub Trending returned more repositories than the configured limit.',\n 2,\n {\n maxItems: options.maxItems,\n sourceUrl: options.sourceUrl\n }\n );\n }\n\n const description = normalizeText(row.find('p.col-9').first().text());\n const language = normalizeText(\n row.find('[itemprop=\"programmingLanguage\"]').first().text()\n );\n const builtBy = parseContributors(\n $,\n row.find('a[data-hovercard-type=\"user\"][href]'),\n options.maxBuiltBy\n );\n\n items.push({\n forks: parseCount(findRepositoryLinkText(\n $,\n row.find('a[href]'),\n `${repository.path}/forks`\n )),\n fullName: `${repository.owner}/${repository.name}`,\n name: repository.name,\n owner: repository.owner,\n rank: items.length + 1,\n stars: parseCount(findRepositoryLinkText(\n $,\n row.find('a[href]'),\n `${repository.path}/stargazers`\n )),\n starsInPeriod: parsePeriodStars(\n row.find('span.float-sm-right').first().text(),\n options.period\n ),\n url: repository.url,\n ...(builtBy.length === 0 ? {} : { builtBy }),\n ...(description.length === 0 ? {} : { description }),\n ...(language.length === 0 ? {} : { language })\n });\n });\n\n if (items.length === 0) {\n throw new GitHubCommandError(\n 'GITHUB_PARSE_FAILED',\n 'Failed to parse GitHub Trending repositories.',\n 2,\n {\n sourceUrl: options.sourceUrl\n }\n );\n }\n\n return {\n items,\n period: options.period,\n sourceUrl: options.sourceUrl\n };\n}\n\nfunction parseRepositoryLink(href: string | undefined): {\n name: string;\n owner: string;\n path: string;\n url: string;\n} | undefined {\n const url = parseGitHubUrl(href);\n if (!url) return undefined;\n\n const segments = url.pathname.split('/').filter(Boolean);\n if (segments.length !== 2) return undefined;\n\n const [owner, name] = segments as [string, string];\n\n const path = `/${owner}/${name}`;\n return {\n name,\n owner,\n path,\n url: `${GITHUB_ORIGIN}${path}`\n };\n}\n\nfunction parseContributors(\n $: ReturnType<typeof load>,\n links: ReturnType<ReturnType<typeof load>>,\n maxBuiltBy: number\n): GitHubTrendingContributor[] {\n const contributors: GitHubTrendingContributor[] = [];\n\n links.each((_, element) => {\n if (contributors.length >= maxBuiltBy) return false;\n\n const link = $(element);\n const user = parseGitHubUser(link.attr('href'));\n const avatarUrl = parseHttpUrl(link.find('img').first().attr('src'));\n if (!user || !avatarUrl) return;\n\n contributors.push({\n avatarUrl,\n url: `${GITHUB_ORIGIN}/${user}`,\n username: user\n });\n });\n\n return contributors;\n}\n\nfunction parseGitHubUser(href: string | undefined): string | undefined {\n const url = parseGitHubUrl(href);\n if (!url) return undefined;\n\n const segments = url.pathname.split('/').filter(Boolean);\n return segments.length === 1 ? segments[0] : undefined;\n}\n\nfunction parseGitHubUrl(value: string | undefined): URL | undefined {\n if (!value) return undefined;\n\n try {\n const url = new URL(value, GITHUB_ORIGIN);\n return url.origin === GITHUB_ORIGIN ? url : undefined;\n } catch {\n return undefined;\n }\n}\n\nfunction parseHttpUrl(value: string | undefined): string | undefined {\n if (!value) return undefined;\n\n try {\n const url = new URL(value, GITHUB_ORIGIN);\n return url.protocol === 'http:' || url.protocol === 'https:'\n ? url.toString()\n : undefined;\n } catch {\n return undefined;\n }\n}\n\nfunction findRepositoryLinkText(\n $: ReturnType<typeof load>,\n links: ReturnType<ReturnType<typeof load>>,\n expectedPath: string\n): string {\n let text = '';\n\n links.each((_, element) => {\n const link = $(element);\n const url = parseGitHubUrl(link.attr('href'));\n if (url?.pathname === expectedPath) {\n text = link.text();\n return false;\n }\n });\n\n return text;\n}\n\nfunction parsePeriodStars(value: string, period: GitHubTrendingPeriod): number {\n const suffix = new RegExp(`\\\\s+stars?\\\\s+${PERIOD_LABEL[period]}\\\\s*$`, 'i');\n if (!suffix.test(value)) return 0;\n return parseCount(value.replace(suffix, ''));\n}\n\nfunction parseCount(value: string): number {\n const digits = value.replace(/[,\\s]/g, '');\n if (!/^\\d+$/.test(digits)) return 0;\n\n const count = Number(digits);\n return Number.isSafeInteger(count) ? count : 0;\n}\n\nfunction normalizeText(value: string): string {\n return value.replace(/\\s+/g, ' ').trim();\n}\n","import { parseGitHubTrendingHtml } from './parser.js';\nimport {\n GitHubCommandError,\n type GitHubRuntime,\n type GitHubTrendingPeriod,\n type GitHubTrendingRuntimeResult\n} from './types.js';\n\nexport interface GitHubRuntimeOptions {\n fetch?: typeof fetch;\n maxResponseBytes?: number;\n requestTimeoutMs?: number;\n}\n\nconst DEFAULT_MAX_RESPONSE_BYTES = 5 * 1024 * 1024;\nconst DEFAULT_REQUEST_TIMEOUT_MS = 30_000;\nconst MAX_BUILT_BY = 10;\nconst MAX_ITEMS = 100;\n\ninterface RuntimeDependencies {\n fetch: typeof fetch;\n maxResponseBytes: number;\n requestTimeoutMs: number;\n}\n\nexport function createDefaultGitHubRuntime(\n options: GitHubRuntimeOptions = {}\n): GitHubRuntime {\n const dependencies: RuntimeDependencies = {\n fetch: options.fetch ?? fetch,\n maxResponseBytes: options.maxResponseBytes ?? DEFAULT_MAX_RESPONSE_BYTES,\n requestTimeoutMs: options.requestTimeoutMs ?? DEFAULT_REQUEST_TIMEOUT_MS\n };\n\n return {\n fetchTrending: async ({ period }) => fetchTrending(dependencies, period)\n };\n}\n\nasync function fetchTrending(\n dependencies: RuntimeDependencies,\n period: GitHubTrendingPeriod\n): Promise<GitHubTrendingRuntimeResult> {\n const sourceUrl = createSourceUrl(period);\n const controller = new AbortController();\n const timeout = setTimeout(\n () => controller.abort(),\n dependencies.requestTimeoutMs\n );\n\n try {\n let response: Response;\n try {\n response = await dependencies.fetch(sourceUrl, {\n headers: {\n accept: 'text/html,application/xhtml+xml',\n 'user-agent': 'ants-move GitHub collector'\n },\n redirect: 'error',\n signal: controller.signal\n });\n } catch {\n throw fetchFailed(sourceUrl);\n }\n\n if (!response.ok) {\n await cancelResponseBody(response);\n throw new GitHubCommandError(\n 'GITHUB_FETCH_FAILED',\n `Failed to fetch GitHub Trending data. HTTP ${response.status}.`,\n 2,\n {\n status: response.status,\n url: sourceUrl\n }\n );\n }\n\n let body: Uint8Array;\n try {\n body = await readBoundedBody(\n response,\n dependencies.maxResponseBytes,\n sourceUrl\n );\n } catch (error) {\n if (error instanceof GitHubCommandError) throw error;\n throw fetchFailed(sourceUrl);\n }\n\n return parseGitHubTrendingHtml(new TextDecoder().decode(body), {\n maxBuiltBy: MAX_BUILT_BY,\n maxItems: MAX_ITEMS,\n period,\n sourceUrl\n });\n } finally {\n clearTimeout(timeout);\n }\n}\n\nfunction createSourceUrl(period: GitHubTrendingPeriod): string {\n const url = new URL('/trending', 'https://github.com');\n url.searchParams.set('since', period);\n return url.toString();\n}\n\nasync function readBoundedBody(\n response: Response,\n maxBytes: number,\n url: string\n): Promise<Uint8Array> {\n const declaredLength = Number(response.headers.get('content-length'));\n if (Number.isFinite(declaredLength) && declaredLength > maxBytes) {\n await cancelResponseBody(response);\n throw responseTooLarge(url, maxBytes);\n }\n\n const reader = response.body?.getReader();\n if (!reader) {\n return new Uint8Array();\n }\n\n const chunks: Uint8Array[] = [];\n let totalBytes = 0;\n\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n\n totalBytes += value.byteLength;\n if (totalBytes > maxBytes) {\n await reader.cancel().catch(() => undefined);\n throw responseTooLarge(url, maxBytes);\n }\n chunks.push(value);\n }\n\n const body = new Uint8Array(totalBytes);\n let offset = 0;\n for (const chunk of chunks) {\n body.set(chunk, offset);\n offset += chunk.byteLength;\n }\n return body;\n}\n\nasync function cancelResponseBody(response: Response): Promise<void> {\n await response.body?.cancel().catch(() => undefined);\n}\n\nfunction fetchFailed(url: string): GitHubCommandError {\n return new GitHubCommandError(\n 'GITHUB_FETCH_FAILED',\n 'Failed to fetch GitHub Trending data.',\n 2,\n {\n url\n }\n );\n}\n\nfunction responseTooLarge(url: string, maxBytes: number): GitHubCommandError {\n return new GitHubCommandError(\n 'GITHUB_RESPONSE_TOO_LARGE',\n 'GitHub Trending response exceeded the configured size limit.',\n 2,\n {\n maxBytes,\n url\n }\n );\n}\n"],"mappings":"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","names":["z","z","applyTableShortcut","z","SUPPORTED_SOURCES","normalizePages","parseSource","z","articleOptionsSchema","parsePages","applyTableShortcut","formatChinaTime","z","z","applyTableShortcut","DEFAULT_MAX_RESPONSE_BYTES","DEFAULT_REQUEST_TIMEOUT_MS","cancelResponseBody","readBoundedBody","responseTooLarge"]}
|