@blocklet/pages-kit-agents 0.5.12

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.
Files changed (70) hide show
  1. package/.env.local.example +8 -0
  2. package/LICENSE +13 -0
  3. package/README.md +10 -0
  4. package/cli.ts +354 -0
  5. package/index.ts +14 -0
  6. package/lib/cjs/agents/multi-agent-page-writer.d.ts +48 -0
  7. package/lib/cjs/agents/multi-agent-page-writer.js +203 -0
  8. package/lib/cjs/agents/page-metadata-generator.d.ts +10 -0
  9. package/lib/cjs/agents/page-metadata-generator.js +43 -0
  10. package/lib/cjs/agents/page-structure-planner.d.ts +55 -0
  11. package/lib/cjs/agents/page-structure-planner.js +106 -0
  12. package/lib/cjs/agents/page-structure-validator.d.ts +30 -0
  13. package/lib/cjs/agents/page-structure-validator.js +124 -0
  14. package/lib/cjs/agents/sample-html-generator.d.ts +6 -0
  15. package/lib/cjs/agents/sample-html-generator.js +35 -0
  16. package/lib/cjs/agents/section-content-generator.d.ts +19 -0
  17. package/lib/cjs/agents/section-content-generator.js +97 -0
  18. package/lib/cjs/index.d.ts +7 -0
  19. package/lib/cjs/index.js +30 -0
  20. package/lib/cjs/tsconfig.tsbuildinfo +1 -0
  21. package/lib/cjs/utils/agent-utils.d.ts +3 -0
  22. package/lib/cjs/utils/agent-utils.js +44 -0
  23. package/lib/cjs/utils/file-utils.d.ts +5 -0
  24. package/lib/cjs/utils/file-utils.js +90 -0
  25. package/lib/cjs/utils/index.d.ts +12 -0
  26. package/lib/cjs/utils/index.js +48 -0
  27. package/lib/cjs/utils/logger.d.ts +1 -0
  28. package/lib/cjs/utils/logger.js +4 -0
  29. package/lib/cjs/utils/template-utils.d.ts +28 -0
  30. package/lib/cjs/utils/template-utils.js +74 -0
  31. package/lib/esm/agents/multi-agent-page-writer.d.ts +48 -0
  32. package/lib/esm/agents/multi-agent-page-writer.js +199 -0
  33. package/lib/esm/agents/page-metadata-generator.d.ts +10 -0
  34. package/lib/esm/agents/page-metadata-generator.js +40 -0
  35. package/lib/esm/agents/page-structure-planner.d.ts +55 -0
  36. package/lib/esm/agents/page-structure-planner.js +103 -0
  37. package/lib/esm/agents/page-structure-validator.d.ts +30 -0
  38. package/lib/esm/agents/page-structure-validator.js +121 -0
  39. package/lib/esm/agents/sample-html-generator.d.ts +6 -0
  40. package/lib/esm/agents/sample-html-generator.js +32 -0
  41. package/lib/esm/agents/section-content-generator.d.ts +19 -0
  42. package/lib/esm/agents/section-content-generator.js +94 -0
  43. package/lib/esm/index.d.ts +7 -0
  44. package/lib/esm/index.js +8 -0
  45. package/lib/esm/tsconfig.tsbuildinfo +1 -0
  46. package/lib/esm/utils/agent-utils.d.ts +3 -0
  47. package/lib/esm/utils/agent-utils.js +38 -0
  48. package/lib/esm/utils/file-utils.d.ts +5 -0
  49. package/lib/esm/utils/file-utils.js +61 -0
  50. package/lib/esm/utils/index.d.ts +12 -0
  51. package/lib/esm/utils/index.js +28 -0
  52. package/lib/esm/utils/logger.d.ts +1 -0
  53. package/lib/esm/utils/logger.js +1 -0
  54. package/lib/esm/utils/template-utils.d.ts +28 -0
  55. package/lib/esm/utils/template-utils.js +67 -0
  56. package/lib/types/agents/multi-agent-page-writer.d.ts +48 -0
  57. package/lib/types/agents/page-metadata-generator.d.ts +10 -0
  58. package/lib/types/agents/page-structure-planner.d.ts +55 -0
  59. package/lib/types/agents/page-structure-validator.d.ts +30 -0
  60. package/lib/types/agents/sample-html-generator.d.ts +6 -0
  61. package/lib/types/agents/section-content-generator.d.ts +19 -0
  62. package/lib/types/index.d.ts +7 -0
  63. package/lib/types/tsconfig.tsbuildinfo +1 -0
  64. package/lib/types/utils/agent-utils.d.ts +3 -0
  65. package/lib/types/utils/file-utils.d.ts +5 -0
  66. package/lib/types/utils/index.d.ts +12 -0
  67. package/lib/types/utils/logger.d.ts +1 -0
  68. package/lib/types/utils/template-utils.d.ts +28 -0
  69. package/package.json +46 -0
  70. package/types.d.ts +4 -0
@@ -0,0 +1,3 @@
1
+ import { ClaudeChatModel } from '@aigne/core/models/claude-chat-model.js';
2
+ import { OpenAIChatModel } from '@aigne/core/models/openai-chat-model.js';
3
+ export declare function getModel(modelName?: string): OpenAIChatModel | ClaudeChatModel | undefined;
@@ -0,0 +1,38 @@
1
+ import { ClaudeChatModel } from '@aigne/core/models/claude-chat-model.js';
2
+ import { GeminiChatModel } from '@aigne/core/models/gemini-chat-model.js';
3
+ import { OpenAIChatModel } from '@aigne/core/models/openai-chat-model.js';
4
+ import assert from 'node:assert';
5
+ const { OPENAI_API_KEY, GEMINI_API_KEY, CLAUDE_API_KEY } = process.env;
6
+ export function getModel(modelName = 'openai') {
7
+ if (modelName?.includes('gpt')) {
8
+ assert(OPENAI_API_KEY, 'Please set the OPENAI_API_KEY environment variable');
9
+ const openai = new OpenAIChatModel({
10
+ apiKey: OPENAI_API_KEY,
11
+ model: modelName,
12
+ modelOptions: {
13
+ temperature: 0.8,
14
+ },
15
+ });
16
+ return openai;
17
+ }
18
+ if (modelName?.includes('gemini')) {
19
+ assert(GEMINI_API_KEY, 'Please set the GEMINI_API_KEY environment variable');
20
+ const gemini = new GeminiChatModel({
21
+ apiKey: GEMINI_API_KEY,
22
+ model: modelName,
23
+ });
24
+ return gemini;
25
+ }
26
+ if (modelName?.includes('claude')) {
27
+ assert(CLAUDE_API_KEY, 'Please set the CLAUDE_API_KEY environment variable');
28
+ const model = new ClaudeChatModel({
29
+ apiKey: CLAUDE_API_KEY,
30
+ model: modelName,
31
+ modelOptions: {
32
+ temperature: 0.7,
33
+ },
34
+ });
35
+ return model;
36
+ }
37
+ return undefined;
38
+ }
@@ -0,0 +1,5 @@
1
+ /**
2
+ * Updates the file list JSON by scanning the sample-output directory
3
+ * and generating a list of all HTML files in each subfolder
4
+ */
5
+ export declare function updateFileList(): Promise<void>;
@@ -0,0 +1,61 @@
1
+ import { existsSync } from 'fs';
2
+ import * as fs from 'fs/promises';
3
+ import path from 'path';
4
+ /**
5
+ * Updates the file list JSON by scanning the sample-output directory
6
+ * and generating a list of all HTML files in each subfolder
7
+ */
8
+ export async function updateFileList() {
9
+ const outputDir = path.join(process.cwd(), 'sample-output');
10
+ const indexPath = path.join(outputDir, 'index.html');
11
+ // 存储所有子文件夹及其HTML文件信息
12
+ const fileList = [];
13
+ try {
14
+ // 读取sample-output目录下的所有子文件夹
15
+ const folders = await fs.readdir(outputDir, { withFileTypes: true });
16
+ // 过滤出目录,并排除特定文件
17
+ const dirNames = folders
18
+ .filter((dirent) => dirent.isDirectory())
19
+ .map((dirent) => dirent.name)
20
+ .filter((name) => name !== '.git' && !name.startsWith('.'));
21
+ // 按照文件夹名称排序(时间戳格式,新的在前)
22
+ dirNames.sort().reverse();
23
+ // 处理每个子文件夹
24
+ for (const folderName of dirNames) {
25
+ const folderPath = path.join(outputDir, folderName);
26
+ // eslint-disable-next-line no-await-in-loop
27
+ const folderFiles = await fs.readdir(folderPath, { withFileTypes: true });
28
+ // 过滤出HTML文件
29
+ const htmlFiles = folderFiles
30
+ .filter((file) => file.isFile() && file.name.endsWith('.html'))
31
+ .map((file) => {
32
+ const fileName = file.name.replace(/\.html$/, '');
33
+ return {
34
+ name: fileName,
35
+ path: `${folderName}/${file.name}`,
36
+ createdAt: new Date().toISOString(),
37
+ };
38
+ });
39
+ // 将文件夹信息添加到列表
40
+ fileList.push({
41
+ folder: folderName,
42
+ files: htmlFiles,
43
+ });
44
+ }
45
+ // 更新index.html,内联JSON数据
46
+ if (existsSync(indexPath)) {
47
+ let indexHtml = await fs.readFile(indexPath, 'utf8');
48
+ // 使用更简洁的替换方式
49
+ const fileListPlaceholder = /const FILE_LIST_DATA = .*?;/s;
50
+ if (fileListPlaceholder.test(indexHtml)) {
51
+ // 替换占位符为实际数据
52
+ const jsonString = JSON.stringify(fileList, null, 2);
53
+ indexHtml = indexHtml.replace(fileListPlaceholder, `const FILE_LIST_DATA = ${jsonString};`);
54
+ await fs.writeFile(indexPath, indexHtml, 'utf8');
55
+ }
56
+ }
57
+ }
58
+ catch (error) {
59
+ console.error('Error updating file list:', error);
60
+ }
61
+ }
@@ -0,0 +1,12 @@
1
+ /**
2
+ * 读取指定路径的文件并返回字符串内容
3
+ * @param filePath 文件路径,可以是相对路径或绝对路径
4
+ * @param encoding 文件编码,默认为 'utf-8'
5
+ * @returns 文件内容字符串
6
+ * @throws 如果文件不存在或读取失败则抛出异常
7
+ */
8
+ export declare function readFile(filePath: string, encoding?: BufferEncoding): Promise<string>;
9
+ export * from './agent-utils';
10
+ export * from './logger';
11
+ export * from './template-utils';
12
+ export * from './file-utils';
@@ -0,0 +1,28 @@
1
+ import { readFile as fsReadFile } from 'node:fs/promises';
2
+ import path from 'node:path';
3
+ /**
4
+ * 读取指定路径的文件并返回字符串内容
5
+ * @param filePath 文件路径,可以是相对路径或绝对路径
6
+ * @param encoding 文件编码,默认为 'utf-8'
7
+ * @returns 文件内容字符串
8
+ * @throws 如果文件不存在或读取失败则抛出异常
9
+ */
10
+ export async function readFile(filePath, encoding = 'utf-8') {
11
+ try {
12
+ // 如果是相对路径,则从当前工作目录解析
13
+ const resolvedPath = path.isAbsolute(filePath) ? filePath : path.resolve(process.cwd(), filePath);
14
+ // 读取文件内容
15
+ const content = await fsReadFile(resolvedPath, { encoding });
16
+ return content;
17
+ }
18
+ catch (error) {
19
+ // 捕获并重新抛出异常,添加更明确的错误信息
20
+ const err = error;
21
+ throw new Error(`Failed to read file at path ${filePath}: ${err.message}`);
22
+ }
23
+ }
24
+ // 导出所有模块功能
25
+ export * from './agent-utils';
26
+ export * from './logger';
27
+ export * from './template-utils';
28
+ export * from './file-utils';
@@ -0,0 +1 @@
1
+ export declare const logger: Console;
@@ -0,0 +1 @@
1
+ export const logger = console;
@@ -0,0 +1,28 @@
1
+ /**
2
+ * 根据JSON数据更新HTML模板并保存到指定目录
3
+ * @param jsonData 需要应用到模板的JSON数据
4
+ * @param templatePath 模板HTML文件路径,默认为assets目录下的sample.html
5
+ * @param outputFolder 输出文件夹名称,将在output目录下创建
6
+ * @param outputFileName 输出HTML文件名称,不包含扩展名
7
+ * @returns 生成的HTML文件的完整路径
8
+ * @throws 如果模板文件不存在或无法创建输出目录则抛出异常
9
+ */
10
+ export declare function generateHtmlFromTemplate({ jsonData, outputFolder, outputFileName, templatePath, }: {
11
+ jsonData: Record<string, any>;
12
+ outputFolder: string;
13
+ outputFileName: string;
14
+ templatePath?: string;
15
+ }): Promise<string>;
16
+ /**
17
+ * 保存HTML内容到指定目录
18
+ * @param htmlContent 要保存的HTML内容
19
+ * @param outputFolder 输出文件夹路径
20
+ * @param outputFileName 输出HTML文件名称,不包含扩展名
21
+ * @returns 生成的HTML文件的完整路径
22
+ * @throws 如果无法创建输出目录或写入文件则抛出异常
23
+ */
24
+ export declare function saveHtmlContent({ htmlContent, outputFolder, outputFileName, }: {
25
+ htmlContent: string;
26
+ outputFolder: string;
27
+ outputFileName: string;
28
+ }): Promise<string>;
@@ -0,0 +1,67 @@
1
+ import fs from 'node:fs';
2
+ import { readFile as fsReadFile } from 'node:fs/promises';
3
+ import path from 'node:path';
4
+ /**
5
+ * 根据JSON数据更新HTML模板并保存到指定目录
6
+ * @param jsonData 需要应用到模板的JSON数据
7
+ * @param templatePath 模板HTML文件路径,默认为assets目录下的sample.html
8
+ * @param outputFolder 输出文件夹名称,将在output目录下创建
9
+ * @param outputFileName 输出HTML文件名称,不包含扩展名
10
+ * @returns 生成的HTML文件的完整路径
11
+ * @throws 如果模板文件不存在或无法创建输出目录则抛出异常
12
+ */
13
+ export async function generateHtmlFromTemplate({ jsonData, outputFolder, outputFileName, templatePath = 'assets/sample2.html', }) {
14
+ try {
15
+ // 读取模板文件
16
+ const resolvedTemplatePath = path.isAbsolute(templatePath)
17
+ ? templatePath
18
+ : path.resolve(process.cwd(), templatePath);
19
+ const templateContent = await fsReadFile(resolvedTemplatePath, { encoding: 'utf-8' });
20
+ // 将JSON数据转换为字符串
21
+ const jsonDataString = JSON.stringify(jsonData);
22
+ // 替换模板中的jsonData变量
23
+ const updatedContent = templateContent.replace(/const jsonData = \{[\s\S]*?\};/, `const jsonData = ${jsonDataString};`);
24
+ // 创建输出目录
25
+ const outputDir = path.resolve(process.cwd(), 'sample-output', outputFolder);
26
+ // 确保输出目录存在
27
+ if (!fs.existsSync(outputDir)) {
28
+ fs.mkdirSync(outputDir, { recursive: true });
29
+ }
30
+ // 构建输出文件的完整路径
31
+ const outputFilePath = path.join(outputDir, `${outputFileName}.html`);
32
+ // 写入更新后的HTML内容
33
+ fs.writeFileSync(outputFilePath, updatedContent, 'utf-8');
34
+ return outputFilePath;
35
+ }
36
+ catch (error) {
37
+ const err = error;
38
+ throw new Error(`Failed to generate HTML from template: ${err.message}`);
39
+ }
40
+ }
41
+ /**
42
+ * 保存HTML内容到指定目录
43
+ * @param htmlContent 要保存的HTML内容
44
+ * @param outputFolder 输出文件夹路径
45
+ * @param outputFileName 输出HTML文件名称,不包含扩展名
46
+ * @returns 生成的HTML文件的完整路径
47
+ * @throws 如果无法创建输出目录或写入文件则抛出异常
48
+ */
49
+ export async function saveHtmlContent({ htmlContent, outputFolder, outputFileName, }) {
50
+ try {
51
+ // 创建输出目录
52
+ const outputDir = path.resolve(process.cwd(), 'sample-output', outputFolder);
53
+ // 确保输出目录存在
54
+ if (!fs.existsSync(outputDir)) {
55
+ fs.mkdirSync(outputDir, { recursive: true });
56
+ }
57
+ // 构建输出文件的完整路径
58
+ const outputFilePath = path.join(outputDir, `${outputFileName}.html`);
59
+ // 写入HTML内容
60
+ fs.writeFileSync(outputFilePath, htmlContent, 'utf-8');
61
+ return outputFilePath;
62
+ }
63
+ catch (error) {
64
+ const err = error;
65
+ throw new Error(`Failed to save HTML content: ${err.message}`);
66
+ }
67
+ }
@@ -0,0 +1,48 @@
1
+ import type { z } from 'zod';
2
+ export interface GeneratePageContentInput {
3
+ context: string;
4
+ question: string;
5
+ sectionsRules?: Record<string, string>;
6
+ locale: string;
7
+ outputSchema: z.ZodObject<any>;
8
+ modelName?: string;
9
+ onProgress?: (params: {
10
+ sectionName?: string;
11
+ sectionIndex?: number;
12
+ totalSections: number;
13
+ sectionData?: Record<string, any>;
14
+ eventType?: 'progress' | 'section' | 'structure_start' | 'structure_complete';
15
+ structureData?: any;
16
+ }) => void;
17
+ checkConnection?: () => boolean;
18
+ }
19
+ /**
20
+ * 多Agent协作生成页面内容
21
+ *
22
+ * 工作流程:
23
+ * 1. 使用页面结构规划Agent分析内容,规划各section内容
24
+ * 2. 使用结构验证Agent检查规划的完整性和有效性
25
+ * 3. 如果验证不通过,将反馈提供给规划Agent进行修正
26
+ * 4. 逐个生成各section内容
27
+ * 5. 基于所有section内容生成页面元数据
28
+ * 6. 整合所有内容返回完整页面数据
29
+ */
30
+ export default function generatePageContentMultiAgent(input: GeneratePageContentInput): Promise<{
31
+ title: string;
32
+ description: string;
33
+ sectionsData: Record<string, any>;
34
+ } | null>;
35
+ /**
36
+ * 单独生成特定section的内容
37
+ * 支持独立调用,为特定section重新生成内容
38
+ */
39
+ export declare function generateSingleSectionContent({ context, question, locale, sectionName, sectionSchema, sectionPlan, existingSections, modelName, }: {
40
+ context: string;
41
+ question: string;
42
+ locale: string;
43
+ sectionName: string;
44
+ sectionSchema: any;
45
+ sectionPlan?: string;
46
+ existingSections?: Record<string, any>;
47
+ modelName?: string;
48
+ }): Promise<import("@aigne/core").Message>;
@@ -0,0 +1,10 @@
1
+ import { AIAgent } from '@aigne/core';
2
+ export declare const generatePageMetadataAgent: AIAgent<{
3
+ context: string;
4
+ question: string;
5
+ locale: string;
6
+ sectionsData: string;
7
+ }, {
8
+ description: string;
9
+ title: string;
10
+ }>;
@@ -0,0 +1,55 @@
1
+ import { AIAgent } from '@aigne/core';
2
+ export interface PlanPageStructureInput {
3
+ context: string;
4
+ question: string;
5
+ initialStructurePlan?: Array<{
6
+ sectionName: string;
7
+ sectionContentPlan: string;
8
+ }>;
9
+ locale: string;
10
+ outputSchema: any;
11
+ validationFeedback?: {
12
+ isValid: boolean;
13
+ missingSections: string[];
14
+ duplicateContent: Array<{
15
+ sections: string[];
16
+ description: string;
17
+ }>;
18
+ feedback: Array<{
19
+ sectionName: string;
20
+ feedback: string;
21
+ }>;
22
+ generalFeedback: string;
23
+ };
24
+ }
25
+ export interface PageStructurePlannerOutput {
26
+ structurePlan: Array<{
27
+ sectionName: string;
28
+ sectionContentPlan: string;
29
+ }>;
30
+ }
31
+ export declare const pageStructurePlannerAgent: AIAgent<{
32
+ outputSchema: string;
33
+ context: string;
34
+ question: string;
35
+ locale: string;
36
+ expectedSections: string;
37
+ initialStructurePlan: {
38
+ sectionName: string;
39
+ sectionContentPlan: string;
40
+ }[];
41
+ validationFeedback?: {
42
+ isValid: boolean;
43
+ missingSections: string[];
44
+ duplicateContent: {
45
+ description: string;
46
+ sections: string[];
47
+ score: number;
48
+ }[];
49
+ } | undefined;
50
+ }, {
51
+ structurePlan: {
52
+ sectionName: string;
53
+ sectionContentPlan: string;
54
+ }[];
55
+ }>;
@@ -0,0 +1,30 @@
1
+ import { AIAgent } from '@aigne/core';
2
+ export interface ValidatePageStructureInput {
3
+ context: string;
4
+ structurePlan: Array<{
5
+ sectionName: string;
6
+ sectionContentPlan: string;
7
+ }>;
8
+ expectedSections: string;
9
+ outputSchema: string;
10
+ }
11
+ export declare const pageStructureValidatorAgent: AIAgent<{
12
+ outputSchema: string;
13
+ context: string;
14
+ question: string;
15
+ expectedSections: string;
16
+ structurePlan: {
17
+ sectionName: string;
18
+ sectionContentPlan: string;
19
+ }[];
20
+ }, {
21
+ validationFeedback: {
22
+ isValid: boolean;
23
+ missingSections: string[];
24
+ duplicateContent: {
25
+ description: string;
26
+ sections: string[];
27
+ score: number;
28
+ }[];
29
+ };
30
+ }>;
@@ -0,0 +1,6 @@
1
+ import { AIAgent } from '@aigne/core';
2
+ export declare const sampleHtmlGeneratorAgent: AIAgent<{
3
+ jsonData: string;
4
+ }, {
5
+ html: string;
6
+ }>;
@@ -0,0 +1,19 @@
1
+ import { AIAgent } from '@aigne/core';
2
+ interface GenerateSectionContentInput {
3
+ context: string;
4
+ question: string;
5
+ locale: string;
6
+ sectionName: string;
7
+ sectionSchema: any;
8
+ sectionPlan: string;
9
+ generatedSections: string;
10
+ }
11
+ export declare function createSectionContentAgent(input: GenerateSectionContentInput): Promise<AIAgent<{
12
+ context: string;
13
+ question: string;
14
+ locale: string;
15
+ sectionName: string;
16
+ sectionPlan: string;
17
+ generatedSections: string;
18
+ }, import("@aigne/core").Message>>;
19
+ export {};
@@ -0,0 +1,7 @@
1
+ export {};
2
+ export { default as generatePageContentMultiAgent, generateSingleSectionContent, } from './agents/multi-agent-page-writer';
3
+ export * from './agents/page-metadata-generator';
4
+ export * from './agents/page-structure-planner';
5
+ export * from './agents/page-structure-validator';
6
+ export * from './agents/section-content-generator';
7
+ export * from './utils/index';