docs: update advanced docs; rm best-practice
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
import { APIDivider, APIReference } from '@/components/APIReference'
|
||||
import CodeEditor from '@/components/CodeEditor'
|
||||
import { Heading } from '@/components/Heading'
|
||||
import { APIDivider, APIReference } from '@/components/ui/api-reference'
|
||||
import { useLanguage } from '@/i18n/context'
|
||||
|
||||
export default function CustomUIDocs() {
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
import { Link } from 'wouter'
|
||||
|
||||
import { APIDivider, APIReference, TypeRef } from '@/components/APIReference'
|
||||
import CodeEditor from '@/components/CodeEditor'
|
||||
import { Heading } from '@/components/Heading'
|
||||
import { APIDivider, APIReference, TypeRef } from '@/components/ui/api-reference'
|
||||
import { useLanguage } from '@/i18n/context'
|
||||
|
||||
export default function PageAgentCoreDocs() {
|
||||
@@ -50,19 +52,13 @@ const agent = new PageAgentCore({
|
||||
baseURL: 'https://api.openai.com/v1',
|
||||
apiKey: 'your-api-key',
|
||||
model: 'gpt-5.2',
|
||||
language: 'en-US',
|
||||
})
|
||||
|
||||
// Listen to events for UI display
|
||||
|
||||
agent.addEventListener('statuschange', () => {
|
||||
console.log('Status:', agent.status)
|
||||
})
|
||||
|
||||
agent.addEventListener('historychange', () => {
|
||||
console.log('History:', agent.history)
|
||||
})
|
||||
|
||||
agent.addEventListener('activity', (e) => {
|
||||
const activity = (e as CustomEvent).detail
|
||||
console.log('Activity:', activity.type)
|
||||
@@ -75,14 +71,54 @@ const result = await agent.execute('Fill in the form with test data')`}
|
||||
|
||||
<APIDivider title={isZh ? '配置' : 'Configuration'} />
|
||||
|
||||
{/* LLM Configuration */}
|
||||
{/* Configuration */}
|
||||
<section className="mb-10">
|
||||
<Heading id="llmconfig">LLMConfig</Heading>
|
||||
<Heading id="configuration">PageAgentCoreConfig</Heading>
|
||||
<p className="text-gray-600 dark:text-gray-400 mb-4">
|
||||
{isZh
|
||||
? '配置与大语言模型的连接参数。支持 OpenAI 兼容的 API。'
|
||||
: 'Configure connection parameters for the language model. Supports OpenAI-compatible APIs.'}
|
||||
? 'PageAgentCoreConfig = AgentConfig & { pageController: PageController }。AgentConfig 包含以下配置项:'
|
||||
: 'PageAgentCoreConfig = AgentConfig & { pageController: PageController }. AgentConfig contains the following options:'}
|
||||
</p>
|
||||
|
||||
{/* PageController */}
|
||||
<h3 className="text-lg font-semibold mt-6 mb-3 text-gray-800 dark:text-gray-200">
|
||||
PageController
|
||||
</h3>
|
||||
<APIReference
|
||||
properties={[
|
||||
{
|
||||
name: 'pageController',
|
||||
type: 'PageController',
|
||||
required: true,
|
||||
description: isZh ? (
|
||||
<>
|
||||
<Link
|
||||
href="/advanced/page-controller"
|
||||
className="text-blue-600 dark:text-blue-400 hover:underline"
|
||||
>
|
||||
PageController
|
||||
</Link>{' '}
|
||||
实例,用于 DOM 操作和元素交互。
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
<Link
|
||||
href="/advanced/page-controller"
|
||||
className="text-blue-600 dark:text-blue-400 hover:underline"
|
||||
>
|
||||
PageController
|
||||
</Link>{' '}
|
||||
instance for DOM operations and element interaction.
|
||||
</>
|
||||
),
|
||||
},
|
||||
]}
|
||||
/>
|
||||
|
||||
{/* LLM Config */}
|
||||
<h3 className="text-lg font-semibold mt-6 mb-3 text-gray-800 dark:text-gray-200">
|
||||
{isZh ? 'LLM 配置' : 'LLM Config'}
|
||||
</h3>
|
||||
<APIReference
|
||||
properties={[
|
||||
{
|
||||
@@ -110,7 +146,6 @@ const result = await agent.execute('Fill in the form with test data')`}
|
||||
{
|
||||
name: 'temperature',
|
||||
type: 'number',
|
||||
defaultValue: '0',
|
||||
description: isZh
|
||||
? '模型温度参数,控制输出随机性'
|
||||
: 'Model temperature, controls output randomness',
|
||||
@@ -130,16 +165,11 @@ const result = await agent.execute('Fill in the form with test data')`}
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</section>
|
||||
|
||||
{/* Agent Configuration */}
|
||||
<section className="mb-10">
|
||||
<Heading id="agentconfig">AgentConfig</Heading>
|
||||
<p className="text-gray-600 dark:text-gray-400 mb-4">
|
||||
{isZh
|
||||
? '配置 Agent 的行为、生命周期钩子和扩展能力。'
|
||||
: 'Configure agent behavior, lifecycle hooks, and extension capabilities.'}
|
||||
</p>
|
||||
{/* Agent Config */}
|
||||
<h3 className="text-lg font-semibold mt-6 mb-3 text-gray-800 dark:text-gray-200">
|
||||
{isZh ? 'Agent 配置' : 'Agent Config'}
|
||||
</h3>
|
||||
<APIReference
|
||||
properties={[
|
||||
{
|
||||
@@ -166,8 +196,8 @@ const result = await agent.execute('Fill in the form with test data')`}
|
||||
name: 'instructions',
|
||||
type: 'InstructionsConfig',
|
||||
description: isZh
|
||||
? '指导 Agent 行为的指令配置'
|
||||
: 'Instructions to guide agent behavior',
|
||||
? '指导 Agent 行为的指令配置,见下方类型定义'
|
||||
: 'Instructions to guide agent behavior, see type definition below',
|
||||
},
|
||||
{
|
||||
name: 'transformPageContent',
|
||||
@@ -177,7 +207,15 @@ const result = await agent.execute('Fill in the form with test data')`}
|
||||
: 'Transform page content before sending to LLM, useful for data masking',
|
||||
},
|
||||
{
|
||||
name: 'experimentalScriptExecutionTool',
|
||||
name: 'customSystemPrompt',
|
||||
type: 'string',
|
||||
status: 'experimental',
|
||||
description: isZh
|
||||
? '完全覆盖默认系统提示词。谨慎使用。'
|
||||
: 'Completely override the default system prompt. Use with caution.',
|
||||
},
|
||||
{
|
||||
name: 'experimentalScript\nExecutionTool',
|
||||
type: 'boolean',
|
||||
defaultValue: 'false',
|
||||
status: 'experimental',
|
||||
@@ -191,137 +229,52 @@ const result = await agent.execute('Fill in the form with test data')`}
|
||||
defaultValue: 'false',
|
||||
status: 'experimental',
|
||||
description: isZh
|
||||
? '从当前站点根目录获取 /llms.txt 并作为上下文提供给 LLM,每个 origin 仅请求一次'
|
||||
: 'Fetch /llms.txt from site origin and include as LLM context, fetched once per origin',
|
||||
? '从当前站点根目录获取 /llms.txt 并作为上下文提供给 LLM'
|
||||
: 'Fetch /llms.txt from site origin and include as LLM context',
|
||||
},
|
||||
]}
|
||||
/>
|
||||
|
||||
<h3 className="text-lg font-semibold mt-6 mb-3">InstructionsConfig</h3>
|
||||
<APIReference
|
||||
properties={[
|
||||
{
|
||||
name: 'system',
|
||||
type: 'string',
|
||||
description: isZh
|
||||
? '全局系统级指令,应用于所有任务'
|
||||
: 'Global system-level instructions, applied to all tasks',
|
||||
},
|
||||
{
|
||||
name: 'getPageInstructions',
|
||||
type: '(url: string) => string | undefined | null',
|
||||
description: isZh
|
||||
? '动态页面级指令回调,在每个步骤前调用'
|
||||
: 'Dynamic page-level instructions callback, called before each step',
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</section>
|
||||
|
||||
{/* Lifecycle Hooks */}
|
||||
<section className="mb-10">
|
||||
<Heading id="lifecycle-hooks">{isZh ? '生命周期钩子' : 'Lifecycle Hooks'}</Heading>
|
||||
{/* Lifecycle Hooks */}
|
||||
<h3 className="text-lg font-semibold mt-6 mb-3 text-gray-800 dark:text-gray-200">
|
||||
{isZh ? '生命周期钩子' : 'Lifecycle Hooks'}
|
||||
<span className="ml-2 text-xs font-normal text-amber-600 dark:text-amber-400">
|
||||
experimental
|
||||
</span>
|
||||
</h3>
|
||||
<div className="bg-amber-50 dark:bg-amber-900/20 border border-amber-200 dark:border-amber-800 rounded-lg p-4 mb-4">
|
||||
<p className="text-amber-800 dark:text-amber-200 text-sm">
|
||||
<strong>⚠️ {isZh ? '警告' : 'Warning'}:</strong>{' '}
|
||||
{isZh
|
||||
? '这些接口高度实验性,可能在未来版本中发生变化。建议优先使用事件系统(Events)来监听 Agent 状态。'
|
||||
: 'These APIs are highly experimental and may change in future versions. Prefer using the Events system for monitoring agent state.'}
|
||||
? '这些接口高度实验性,可能在未来版本中发生变化。'
|
||||
: 'These APIs are highly experimental and may change in future versions. '}
|
||||
</p>
|
||||
</div>
|
||||
<p className="text-gray-600 dark:text-gray-400 mb-4">
|
||||
{isZh
|
||||
? '所有生命周期钩子都接收 agent 实例作为第一个参数,便于在回调中访问 Agent 状态和方法。'
|
||||
: 'All lifecycle hooks receive the agent instance as first parameter, making it easy to access agent state and methods in callbacks.'}
|
||||
</p>
|
||||
<APIReference
|
||||
properties={[
|
||||
{
|
||||
name: 'onBeforeStep',
|
||||
type: '(agent: PageAgentCore, stepCount: number) => void | Promise<void>',
|
||||
type: '(agent, stepCount) => void | Promise<void>',
|
||||
description: isZh ? '每个步骤执行前调用' : 'Called before each step execution',
|
||||
status: 'experimental',
|
||||
},
|
||||
{
|
||||
name: 'onAfterStep',
|
||||
type: '(agent: PageAgentCore, history: HistoricalEvent[]) => void | Promise<void>',
|
||||
type: '(agent, history) => void | Promise<void>',
|
||||
description: isZh ? '每个步骤执行后调用' : 'Called after each step execution',
|
||||
status: 'experimental',
|
||||
},
|
||||
{
|
||||
name: 'onBeforeTask',
|
||||
type: '(agent: PageAgentCore) => void | Promise<void>',
|
||||
type: '(agent) => void | Promise<void>',
|
||||
description: isZh ? '任务开始前调用' : 'Called before task starts',
|
||||
status: 'experimental',
|
||||
},
|
||||
{
|
||||
name: 'onAfterTask',
|
||||
type: '(agent: PageAgentCore, result: ExecutionResult) => void | Promise<void>',
|
||||
type: '(agent, result) => void | Promise<void>',
|
||||
description: isZh ? '任务结束后调用' : 'Called after task ends',
|
||||
status: 'experimental',
|
||||
},
|
||||
{
|
||||
name: 'onDispose',
|
||||
type: '(agent: PageAgentCore, reason?: string) => void',
|
||||
type: '(agent, reason?) => void',
|
||||
description: isZh ? 'Agent 销毁时调用' : 'Called when agent is disposed',
|
||||
status: 'experimental',
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</section>
|
||||
|
||||
{/* PageController Configuration */}
|
||||
<section className="mb-10">
|
||||
<Heading id="pagecontrollerconfig">PageControllerConfig</Heading>
|
||||
<p className="text-gray-600 dark:text-gray-400 mb-4">
|
||||
{isZh
|
||||
? '配置 DOM 提取、元素交互和视觉反馈。'
|
||||
: 'Configure DOM extraction, element interaction, and visual feedback.'}
|
||||
</p>
|
||||
<APIReference
|
||||
properties={[
|
||||
{
|
||||
name: 'pageController',
|
||||
type: 'PageController',
|
||||
status: 'experimental',
|
||||
description: isZh
|
||||
? '自定义 PageController 实例。如不提供,将创建默认实例。'
|
||||
: 'Custom PageController instance. If not provided, a default one will be created.',
|
||||
},
|
||||
{
|
||||
name: 'enableMask',
|
||||
type: 'boolean',
|
||||
defaultValue: 'true',
|
||||
description: isZh
|
||||
? '启用视觉遮罩覆盖层,阻止用户在自动化期间操作'
|
||||
: 'Enable visual mask overlay that blocks user interaction during automation',
|
||||
},
|
||||
{
|
||||
name: 'viewportExpansion',
|
||||
type: 'number',
|
||||
defaultValue: '0',
|
||||
description: isZh
|
||||
? '视口扩展像素数,-1 表示提取整个页面'
|
||||
: 'Viewport expansion in pixels, -1 means extract entire page',
|
||||
},
|
||||
{
|
||||
name: 'interactiveBlacklist',
|
||||
type: '(Element | (() => Element))[]',
|
||||
description: isZh ? '要排除的交互元素列表' : 'Elements to exclude from interaction',
|
||||
},
|
||||
{
|
||||
name: 'interactiveWhitelist',
|
||||
type: '(Element | (() => Element))[]',
|
||||
description: isZh
|
||||
? '要强制包含的交互元素列表'
|
||||
: 'Elements to force include for interaction',
|
||||
},
|
||||
{
|
||||
name: 'includeAttributes',
|
||||
type: 'string[]',
|
||||
description: isZh
|
||||
? '在 DOM 提取中包含的额外属性'
|
||||
: 'Additional attributes to include in DOM extraction',
|
||||
},
|
||||
]}
|
||||
/>
|
||||
@@ -378,16 +331,24 @@ const result = await agent.execute('Fill in the form with test data')`}
|
||||
<section className="mb-10">
|
||||
<Heading id="methods">{isZh ? '方法' : 'Methods'}</Heading>
|
||||
<APIReference
|
||||
variant="methods"
|
||||
properties={[
|
||||
{
|
||||
name: 'execute(task: string)',
|
||||
name: 'execute(task)',
|
||||
type: 'Promise<ExecutionResult>',
|
||||
description: isZh
|
||||
? '执行任务并返回结果。包含 success、data 和 history 字段。'
|
||||
: 'Execute a task and return result. Contains success, data, and history fields.',
|
||||
},
|
||||
{
|
||||
name: 'dispose(reason?: string)',
|
||||
name: 'stop()',
|
||||
type: 'void',
|
||||
description: isZh
|
||||
? '停止当前任务。Agent 仍可复用。'
|
||||
: 'Stop the current task. Agent remains reusable.',
|
||||
},
|
||||
{
|
||||
name: 'dispose()',
|
||||
type: 'void',
|
||||
description: isZh
|
||||
? '销毁 Agent 并清理资源'
|
||||
@@ -452,11 +413,8 @@ const result = await agent.execute('Fill in the form with test data')`}
|
||||
<CodeEditor
|
||||
language="typescript"
|
||||
code={`interface ExecutionResult {
|
||||
/** Whether the task completed successfully */
|
||||
success: boolean
|
||||
/** Result description from the agent */
|
||||
data: string
|
||||
/** Full execution history */
|
||||
history: HistoricalEvent[]
|
||||
}`}
|
||||
/>
|
||||
@@ -476,50 +434,21 @@ const result = await agent.execute('Fill in the form with test data')`}
|
||||
/>
|
||||
</section>
|
||||
|
||||
<APIDivider title={isZh ? '无头模式' : 'Headless Mode'} />
|
||||
|
||||
{/* Headless Usage */}
|
||||
{/* InstructionsConfig */}
|
||||
<section className="mb-10">
|
||||
<Heading id="headless-mode">{isZh ? '无头模式' : 'Headless Mode'}</Heading>
|
||||
<p className="text-gray-600 dark:text-gray-400 mb-4">
|
||||
{isZh
|
||||
? '在非 DOM 环境中,你必须实现自定义的 PageController(例如远程操作页面或 Puppeteer)。'
|
||||
: 'In non-DOM environments, you must implement a custom PageController (e.g., remote page control or Puppeteer).'}
|
||||
</p>
|
||||
<Heading id="instructionsconfig">InstructionsConfig</Heading>
|
||||
<CodeEditor
|
||||
language="typescript"
|
||||
code={`import { PageAgentCore } from '@page-agent/core'
|
||||
import type { PageController } from '@page-agent/page-controller'
|
||||
code={`interface InstructionsConfig {
|
||||
/** Global system-level instructions, applied to all tasks */
|
||||
system?: string
|
||||
|
||||
class MyRemotePageController implements PageController {
|
||||
// Implement required methods for DOM extraction and interaction
|
||||
}
|
||||
|
||||
const agent = new PageAgentCore({
|
||||
pageController: new MyRemotePageController(),
|
||||
baseURL: 'https://api.openai.com/v1',
|
||||
apiKey: 'your-api-key',
|
||||
model: 'gpt-5.2',
|
||||
language: 'en-US',
|
||||
})
|
||||
|
||||
// Listen to events for UI display
|
||||
|
||||
agent.addEventListener('statuschange', () => {
|
||||
console.log('Status:', agent.status)
|
||||
})
|
||||
|
||||
agent.addEventListener('historychange', () => {
|
||||
console.log('History:', agent.history)
|
||||
})
|
||||
|
||||
agent.addEventListener('activity', (e) => {
|
||||
const activity = (e as CustomEvent).detail
|
||||
console.log('Activity:', activity.type)
|
||||
})
|
||||
|
||||
// Execute task
|
||||
const result = await agent.execute('Fill in the form with test data')`}
|
||||
/**
|
||||
* Dynamic page-level instructions callback.
|
||||
* Called before each step to get instructions for the current page.
|
||||
*/
|
||||
getPageInstructions?: (url: string) => string | undefined
|
||||
}`}
|
||||
/>
|
||||
</section>
|
||||
</div>
|
||||
|
||||
@@ -2,7 +2,6 @@ import { Link } from 'wouter'
|
||||
|
||||
import CodeEditor from '@/components/CodeEditor'
|
||||
import { Heading } from '@/components/Heading'
|
||||
import { APIReference, TypeRef } from '@/components/ui/api-reference'
|
||||
import { useLanguage } from '@/i18n/context'
|
||||
|
||||
export default function PageAgentDocs() {
|
||||
@@ -14,8 +13,8 @@ export default function PageAgentDocs() {
|
||||
|
||||
<p className="text-xl text-gray-600 dark:text-gray-300 mb-8 leading-relaxed">
|
||||
{isZh
|
||||
? 'PageAgent 是带有内置 UI 面板的完整 Agent 类。它继承自 PageAgentCore,并自动创建交互面板。'
|
||||
: 'PageAgent is the complete Agent class with built-in UI panel. It extends PageAgentCore and automatically creates an interactive panel.'}
|
||||
? 'PageAgent 是带有内置 UI 面板的完整 Agent 类。它继承自 PageAgentCore,并自动创建交互面板和 PageController。'
|
||||
: 'PageAgent is the complete Agent class with built-in UI panel. It extends PageAgentCore and automatically creates an interactive panel and PageController.'}
|
||||
</p>
|
||||
|
||||
{/* When to use */}
|
||||
@@ -29,6 +28,11 @@ export default function PageAgentDocs() {
|
||||
: 'In most cases, you should use PageAgent. It provides a complete out-of-the-box experience:'}
|
||||
</p>
|
||||
<ul className="list-disc list-inside text-gray-600 dark:text-gray-400 space-y-2 mb-6">
|
||||
<li>
|
||||
{isZh
|
||||
? '自动创建 PageController,处理 DOM 提取和元素操作'
|
||||
: 'Automatically creates PageController for DOM extraction and element actions'}
|
||||
</li>
|
||||
<li>
|
||||
{isZh
|
||||
? '内置 UI 面板,显示任务进度、Agent 思考过程和操作结果'
|
||||
@@ -74,9 +78,8 @@ console.log(result.history) // Full execution history`}
|
||||
<CodeEditor
|
||||
language="typescript"
|
||||
code={`class PageAgent extends PageAgentCore {
|
||||
/** The UI panel instance */
|
||||
panel: Panel
|
||||
|
||||
pageController: PageController
|
||||
constructor(config: PageAgentConfig)
|
||||
}`}
|
||||
/>
|
||||
@@ -90,7 +93,21 @@ console.log(result.history) // Full execution history`}
|
||||
>
|
||||
PageAgentCore
|
||||
</Link>
|
||||
,所有核心方法和事件都可用。详细的 API 参考请查看 PageAgentCore 文档。
|
||||
,所有核心方法和事件都可用。配置项合并了{' '}
|
||||
<Link
|
||||
href="/advanced/page-agent-core#configuration"
|
||||
className="text-blue-600 dark:text-blue-400 hover:underline"
|
||||
>
|
||||
AgentConfig
|
||||
</Link>{' '}
|
||||
和{' '}
|
||||
<Link
|
||||
href="/advanced/page-controller#configuration"
|
||||
className="text-blue-600 dark:text-blue-400 hover:underline"
|
||||
>
|
||||
PageControllerConfig
|
||||
</Link>
|
||||
。
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
@@ -101,71 +118,34 @@ console.log(result.history) // Full execution history`}
|
||||
>
|
||||
PageAgentCore
|
||||
</Link>
|
||||
. All core methods and events are available. See PageAgentCore docs for detailed API
|
||||
reference.
|
||||
</>
|
||||
)}
|
||||
</p>
|
||||
</section>
|
||||
|
||||
{/* Configuration */}
|
||||
<section className="mb-10">
|
||||
<Heading id="configuration">{isZh ? '配置' : 'Configuration'}</Heading>
|
||||
<p className="text-gray-600 dark:text-gray-400 mb-4">
|
||||
{isZh
|
||||
? 'PageAgent 使用与 PageAgentCore 相同的配置接口。'
|
||||
: 'PageAgent uses the same configuration interface as PageAgentCore.'}
|
||||
</p>
|
||||
<p className="text-gray-600 dark:text-gray-400 mb-4">
|
||||
{isZh ? (
|
||||
<>
|
||||
完整配置请参考{' '}
|
||||
. All core methods and events are available. Config merges{' '}
|
||||
<Link
|
||||
href="/advanced/page-agent-core"
|
||||
href="/advanced/page-agent-core#configuration"
|
||||
className="text-blue-600 dark:text-blue-400 hover:underline"
|
||||
>
|
||||
PageAgentCore 配置文档
|
||||
</Link>
|
||||
。
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
See{' '}
|
||||
<Link
|
||||
href="/advanced/page-agent-core"
|
||||
className="text-blue-600 dark:text-blue-400 hover:underline"
|
||||
>
|
||||
PageAgentCore configuration docs
|
||||
AgentConfig
|
||||
</Link>{' '}
|
||||
for complete reference.
|
||||
and{' '}
|
||||
<Link
|
||||
href="/advanced/page-controller#configuration"
|
||||
className="text-blue-600 dark:text-blue-400 hover:underline"
|
||||
>
|
||||
PageControllerConfig
|
||||
</Link>
|
||||
.
|
||||
</>
|
||||
)}
|
||||
</p>
|
||||
</section>
|
||||
|
||||
{/* Panel Property */}
|
||||
{/* Panel */}
|
||||
<section className="mb-10">
|
||||
<Heading id="panel-property">{isZh ? 'Panel 属性' : 'Panel Property'}</Heading>
|
||||
<Heading id="panel">{isZh ? 'UI 面板' : 'UI Panel'}</Heading>
|
||||
<p className="text-gray-600 dark:text-gray-400 mb-4">
|
||||
{isZh
|
||||
? 'PageAgent 自动创建一个 Panel 实例。你可以通过 panel 属性访问它来控制 UI:'
|
||||
: 'PageAgent automatically creates a Panel instance. You can access it via the panel property to control the UI:'}
|
||||
? 'PageAgent 自动创建一个 Panel 实例。你可以通过 panel 属性控制 UI:'
|
||||
: 'PageAgent automatically creates a Panel instance. You can control the UI via the panel property:'}
|
||||
</p>
|
||||
|
||||
<APIReference
|
||||
properties={[
|
||||
{
|
||||
name: 'panel',
|
||||
type: 'Panel',
|
||||
required: true,
|
||||
description: isZh
|
||||
? '内置的 UI 面板实例,用于显示任务进度和接收用户输入。'
|
||||
: 'The built-in UI panel instance for displaying task progress and receiving user input.',
|
||||
},
|
||||
]}
|
||||
/>
|
||||
|
||||
<h3 className="text-lg font-semibold mt-6 mb-3">{isZh ? 'Panel 方法' : 'Panel Methods'}</h3>
|
||||
<CodeEditor
|
||||
language="typescript"
|
||||
code={`// Show/hide the panel
|
||||
@@ -212,16 +192,16 @@ agent.panel.dispose()`}
|
||||
</tr>
|
||||
<tr className="bg-white dark:bg-gray-900">
|
||||
<td className="px-4 py-3 text-gray-600 dark:text-gray-400">
|
||||
{isZh ? 'Headless 模式' : 'Headless Mode'}
|
||||
{isZh ? '自动创建 PageController' : 'Auto-creates PageController'}
|
||||
</td>
|
||||
<td className="px-4 py-3 text-center text-gray-400 dark:text-gray-600">-</td>
|
||||
<td className="px-4 py-3 text-center text-green-600 dark:text-green-400">✓</td>
|
||||
<td className="px-4 py-3 text-center text-gray-400 dark:text-gray-600">-</td>
|
||||
</tr>
|
||||
<tr className="bg-white dark:bg-gray-900">
|
||||
<td className="px-4 py-3 text-gray-600 dark:text-gray-400">
|
||||
{isZh ? '自定义 PageController' : 'Custom PageController'}
|
||||
{isZh ? 'Headless 模式' : 'Headless Mode'}
|
||||
</td>
|
||||
<td className="px-4 py-3 text-center text-green-600 dark:text-green-400">✓</td>
|
||||
<td className="px-4 py-3 text-center text-gray-400 dark:text-gray-600">-</td>
|
||||
<td className="px-4 py-3 text-center text-green-600 dark:text-green-400">✓</td>
|
||||
</tr>
|
||||
<tr className="bg-white dark:bg-gray-900">
|
||||
|
||||
@@ -0,0 +1,286 @@
|
||||
import { Link } from 'wouter'
|
||||
|
||||
import { APIDivider, APIReference } from '@/components/APIReference'
|
||||
import CodeEditor from '@/components/CodeEditor'
|
||||
import { Heading } from '@/components/Heading'
|
||||
import { useLanguage } from '@/i18n/context'
|
||||
|
||||
export default function PageControllerDocs() {
|
||||
const { isZh } = useLanguage()
|
||||
|
||||
return (
|
||||
<div>
|
||||
<h1 className="text-4xl font-bold mb-6">PageController</h1>
|
||||
|
||||
<p className="text-xl text-gray-600 dark:text-gray-300 mb-8 leading-relaxed">
|
||||
{isZh
|
||||
? 'PageController 负责 DOM 提取和元素交互,独立于 LLM。它将页面状态结构化为 LLM 可消费的格式,并执行元素级操作。'
|
||||
: 'PageController handles DOM extraction and element interaction, independent of LLM. It structures page state into LLM-consumable format and executes element-level actions.'}
|
||||
</p>
|
||||
|
||||
{/* Basic Usage */}
|
||||
<section className="mb-10">
|
||||
<Heading id="basic-usage">{isZh ? '基本用法' : 'Basic Usage'}</Heading>
|
||||
<p className="text-gray-600 dark:text-gray-400 mb-4">
|
||||
{isZh
|
||||
? 'PageAgent 接受 PageController 配置项:'
|
||||
: 'PageAgent accepts PageController options:'}
|
||||
</p>
|
||||
<CodeEditor
|
||||
language="typescript"
|
||||
code={`import { PageAgent } from 'page-agent'
|
||||
|
||||
const agent = new PageAgent({
|
||||
baseURL: 'https://api.openai.com/v1',
|
||||
apiKey: 'your-api-key',
|
||||
model: 'gpt-5.2',
|
||||
|
||||
// PageController options
|
||||
enableMask: true,
|
||||
viewportExpansion: 0,
|
||||
})`}
|
||||
/>
|
||||
<p className="text-gray-600 dark:text-gray-400 mt-4">
|
||||
{isZh
|
||||
? 'PageAgentCore 接受 PageController 实例:'
|
||||
: 'PageAgentCore accepts a PageController instance:'}
|
||||
</p>
|
||||
<CodeEditor
|
||||
language="typescript"
|
||||
code={`import { PageAgentCore } from '@page-agent/core'
|
||||
import { PageController } from '@page-agent/page-controller'
|
||||
|
||||
const pageController = new PageController({
|
||||
enableMask: true,
|
||||
viewportExpansion: -1, // extract full page
|
||||
})
|
||||
|
||||
const agent = new PageAgentCore({
|
||||
pageController,
|
||||
baseURL: 'https://api.openai.com/v1',
|
||||
apiKey: 'your-api-key',
|
||||
model: 'gpt-5.2',
|
||||
})`}
|
||||
/>
|
||||
</section>
|
||||
|
||||
<APIDivider title={isZh ? '配置' : 'Configuration'} />
|
||||
|
||||
{/* Configuration */}
|
||||
<section className="mb-10">
|
||||
<Heading id="configuration">PageControllerConfig</Heading>
|
||||
<APIReference
|
||||
properties={[
|
||||
{
|
||||
name: 'enableMask',
|
||||
type: 'boolean',
|
||||
defaultValue: 'false',
|
||||
description: isZh
|
||||
? '启用视觉遮罩覆盖层,在自动化期间阻止用户操作页面。通过 PageAgent 创建时默认为 true。'
|
||||
: 'Enable visual mask overlay that blocks user interaction during automation. Defaults to true when created via PageAgent.',
|
||||
},
|
||||
{
|
||||
name: 'viewportExpansion',
|
||||
type: 'number',
|
||||
defaultValue: '0',
|
||||
description: isZh
|
||||
? '向视口外扩展提取的像素数。设为 -1 表示提取整个页面。'
|
||||
: 'Pixels to expand extraction beyond viewport. Set to -1 to extract the entire page.',
|
||||
},
|
||||
{
|
||||
name: 'interactiveBlacklist',
|
||||
type: '(Element | (() => Element))[]',
|
||||
description: isZh
|
||||
? '要排除的交互元素列表。支持元素引用或返回元素的函数(延迟求值)。'
|
||||
: 'Elements to exclude from interaction. Supports element references or functions returning elements (lazy evaluation).',
|
||||
},
|
||||
{
|
||||
name: 'interactiveWhitelist',
|
||||
type: '(Element | (() => Element))[]',
|
||||
description: isZh
|
||||
? '要强制包含的交互元素列表。支持元素引用或返回元素的函数。'
|
||||
: 'Elements to force include for interaction. Supports element references or functions returning elements.',
|
||||
},
|
||||
{
|
||||
name: 'includeAttributes',
|
||||
type: 'string[]',
|
||||
description: isZh
|
||||
? '在 DOM 提取中包含的额外 HTML 属性(如 data-testid)。默认已包含常见属性如 role, aria-label 等。'
|
||||
: 'Additional HTML attributes to include in DOM extraction (e.g. data-testid). Common attributes like role, aria-label are included by default.',
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</section>
|
||||
|
||||
<APIDivider title={isZh ? '方法' : 'Methods'} />
|
||||
|
||||
{/* Methods */}
|
||||
<section className="mb-10">
|
||||
<Heading id="methods">{isZh ? '方法' : 'Methods'}</Heading>
|
||||
|
||||
<h3 className="text-lg font-semibold mt-6 mb-3">{isZh ? '状态查询' : 'State Queries'}</h3>
|
||||
<APIReference
|
||||
variant="methods"
|
||||
properties={[
|
||||
{
|
||||
name: 'getBrowserState()',
|
||||
type: 'Promise<BrowserState>',
|
||||
description: isZh
|
||||
? '获取结构化的浏览器状态(URL、标题、简化 HTML 等),自动调用 updateTree() 刷新 DOM。这是 Agent 在每步使用的主要方法。'
|
||||
: 'Get structured browser state (URL, title, simplified HTML, etc.), automatically calls updateTree() to refresh DOM. This is the primary method the agent uses each step.',
|
||||
},
|
||||
{
|
||||
name: 'updateTree()',
|
||||
type: 'Promise<string>',
|
||||
description: isZh
|
||||
? '刷新 DOM 树并返回简化 HTML。通常不需要手动调用 —— getBrowserState() 会自动调用。'
|
||||
: 'Refresh DOM tree and return simplified HTML. Usually not needed manually — getBrowserState() calls it automatically.',
|
||||
},
|
||||
{
|
||||
name: 'getCurrentUrl()',
|
||||
type: 'Promise<string>',
|
||||
description: isZh ? '获取当前页面 URL。' : 'Get current page URL.',
|
||||
},
|
||||
]}
|
||||
/>
|
||||
|
||||
<h3 className="text-lg font-semibold mt-6 mb-3">{isZh ? '元素操作' : 'Element Actions'}</h3>
|
||||
<APIReference
|
||||
variant="methods"
|
||||
properties={[
|
||||
{
|
||||
name: 'clickElement(index)',
|
||||
type: 'Promise<ActionResult>',
|
||||
description: isZh
|
||||
? '按索引点击元素。索引来自简化 HTML 中的 [N] 标记。'
|
||||
: 'Click element by index. Index comes from [N] markers in simplified HTML.',
|
||||
},
|
||||
{
|
||||
name: 'inputText(index, text)',
|
||||
type: 'Promise<ActionResult>',
|
||||
description: isZh ? '向输入框元素填入文本。' : 'Input text into a form element.',
|
||||
},
|
||||
{
|
||||
name: 'selectOption(index, optionText)',
|
||||
type: 'Promise<ActionResult>',
|
||||
description: isZh ? '在下拉框中选择选项。' : 'Select option in a dropdown element.',
|
||||
},
|
||||
{
|
||||
name: 'scroll(options)',
|
||||
type: 'Promise<ActionResult>',
|
||||
description: isZh
|
||||
? '垂直滚动页面或指定元素。'
|
||||
: 'Scroll page or specific element vertically.',
|
||||
},
|
||||
{
|
||||
name: 'scrollHorizontally(options)',
|
||||
type: 'Promise<ActionResult>',
|
||||
description: isZh
|
||||
? '水平滚动页面或指定元素。'
|
||||
: 'Scroll page or specific element horizontally.',
|
||||
},
|
||||
]}
|
||||
/>
|
||||
|
||||
<h3 className="text-lg font-semibold mt-6 mb-3">{isZh ? '遮罩控制' : 'Mask Control'}</h3>
|
||||
<APIReference
|
||||
variant="methods"
|
||||
properties={[
|
||||
{
|
||||
name: 'showMask()',
|
||||
type: 'Promise<void>',
|
||||
description: isZh
|
||||
? '显示视觉遮罩。需要 enableMask: true。'
|
||||
: 'Show visual mask overlay. Requires enableMask: true.',
|
||||
},
|
||||
{
|
||||
name: 'hideMask()',
|
||||
type: 'Promise<void>',
|
||||
description: isZh ? '隐藏视觉遮罩。' : 'Hide visual mask overlay.',
|
||||
},
|
||||
]}
|
||||
/>
|
||||
|
||||
<h3 className="text-lg font-semibold mt-6 mb-3">{isZh ? '生命周期' : 'Lifecycle'}</h3>
|
||||
<APIReference
|
||||
variant="methods"
|
||||
properties={[
|
||||
{
|
||||
name: 'dispose()',
|
||||
type: 'void',
|
||||
description: isZh
|
||||
? '清理所有资源(DOM 高亮、遮罩等)。Agent 销毁时自动调用。'
|
||||
: 'Clean up all resources (DOM highlights, mask, etc.). Called automatically when agent disposes.',
|
||||
},
|
||||
]}
|
||||
/>
|
||||
</section>
|
||||
|
||||
<APIDivider title={isZh ? '类型定义' : 'Type Definitions'} />
|
||||
|
||||
{/* BrowserState */}
|
||||
<section className="mb-10">
|
||||
<Heading id="browser-state">BrowserState</Heading>
|
||||
<p className="text-gray-600 dark:text-gray-400 mb-4">
|
||||
{isZh
|
||||
? 'getBrowserState() 返回的结构化浏览器状态,直接用于构建 LLM prompt。'
|
||||
: 'Structured browser state returned by getBrowserState(), used directly to build LLM prompts.'}
|
||||
</p>
|
||||
<CodeEditor
|
||||
language="typescript"
|
||||
code={`interface BrowserState {
|
||||
url: string
|
||||
title: string
|
||||
header: string // page info + scroll position
|
||||
content: string // simplified HTML of interactive elements
|
||||
footer: string // scroll hint
|
||||
}`}
|
||||
/>
|
||||
</section>
|
||||
|
||||
{/* ActionResult */}
|
||||
<section className="mb-10">
|
||||
<Heading id="action-result">ActionResult</Heading>
|
||||
<CodeEditor
|
||||
language="typescript"
|
||||
code={`interface ActionResult {
|
||||
success: boolean
|
||||
message: string
|
||||
}`}
|
||||
/>
|
||||
</section>
|
||||
|
||||
{/* Custom PageController */}
|
||||
<section className="mb-10">
|
||||
<Heading id="custom-implementation">
|
||||
{isZh ? '自定义实现' : 'Custom Implementation'}
|
||||
</Heading>
|
||||
<p className="text-gray-600 dark:text-gray-400 mb-4">
|
||||
{isZh
|
||||
? '在非浏览器环境(如 Puppeteer、Playwright),你可以实现自定义 PageController。需要实现 Agent 使用的核心方法:'
|
||||
: 'In non-browser environments (e.g. Puppeteer, Playwright), you can implement a custom PageController. Implement the core methods used by the agent:'}
|
||||
</p>
|
||||
<CodeEditor
|
||||
language="typescript"
|
||||
code={`import { PageAgentCore } from '@page-agent/core'
|
||||
import type { PageController } from '@page-agent/page-controller'
|
||||
|
||||
class PuppeteerPageController implements PageController {
|
||||
async getBrowserState() { /* ... */ }
|
||||
async clickElement(index: number) { /* ... */ }
|
||||
async inputText(index: number, text: string) { /* ... */ }
|
||||
async scroll(options: { down: boolean; numPages: number }) { /* ... */ }
|
||||
// ... other methods
|
||||
}
|
||||
|
||||
const agent = new PageAgentCore({
|
||||
pageController: new PuppeteerPageController(),
|
||||
baseURL: 'https://api.openai.com/v1',
|
||||
apiKey: 'your-api-key',
|
||||
model: 'gpt-5.2',
|
||||
})`}
|
||||
/>
|
||||
</section>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
@@ -0,0 +1,89 @@
|
||||
import BetaNotice from '@/components/BetaNotice'
|
||||
import { Heading } from '@/components/Heading'
|
||||
import { useLanguage } from '@/i18n/context'
|
||||
|
||||
export default function SecurityPermissions() {
|
||||
const { isZh } = useLanguage()
|
||||
|
||||
return (
|
||||
<div>
|
||||
<BetaNotice />
|
||||
|
||||
<h1 className="text-4xl font-bold mb-6">{isZh ? '安全与权限' : 'Security & Permissions'}</h1>
|
||||
|
||||
<p className="text-xl text-gray-600 dark:text-gray-300 mb-8 leading-relaxed">
|
||||
{isZh
|
||||
? 'page-agent 提供多种安全机制,确保 AI 操作在可控范围内进行。'
|
||||
: 'page-agent provides multiple security mechanisms to ensure AI operations stay within controlled boundaries.'}
|
||||
</p>
|
||||
|
||||
<div className="space-y-6">
|
||||
<section>
|
||||
<Heading id="element-interaction-allowlist-blocklist" className="text-2xl font-bold mb-3">
|
||||
{isZh ? '元素操作黑白名单' : 'Element Interaction Allowlist/Blocklist'}
|
||||
</Heading>
|
||||
<div className="space-y-3">
|
||||
<div className="p-4 bg-red-50 dark:bg-red-900/20 rounded-lg">
|
||||
<h3 className="text-lg font-semibold text-red-900 dark:text-red-300">
|
||||
🚫 {isZh ? '操作黑名单' : 'Blocklist'}
|
||||
</h3>
|
||||
<p className="text-gray-600 dark:text-gray-300">
|
||||
{isZh
|
||||
? '禁止 AI 操作敏感元素,如删除按钮、支付按钮等。'
|
||||
: 'Prevent AI from interacting with sensitive elements like delete buttons, payment buttons, etc.'}
|
||||
</p>
|
||||
</div>
|
||||
<div className="p-4 bg-green-50 dark:bg-green-900/20 rounded-lg">
|
||||
<h3 className="text-lg font-semibold text-green-900 dark:text-green-300">
|
||||
✅ {isZh ? '操作白名单' : 'Allowlist'}
|
||||
</h3>
|
||||
<p className="text-gray-600 dark:text-gray-300">
|
||||
{isZh
|
||||
? '明确定义 AI 可以操作的元素范围。'
|
||||
: 'Explicitly define which elements AI can interact with.'}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<section>
|
||||
<Heading id="instruction-safety-constraints" className="text-2xl font-bold mb-3">
|
||||
{isZh ? 'Instruction 安全约束' : 'Instruction Safety Constraints'}
|
||||
</Heading>
|
||||
<div className="p-4 bg-yellow-50 dark:bg-yellow-900/20 rounded-lg">
|
||||
<h3 className="text-lg font-semibold mb-2 text-yellow-900 dark:text-yellow-300">
|
||||
⚠️ {isZh ? '高危操作控制' : 'High-Risk Operation Control'}
|
||||
</h3>
|
||||
<p className="text-gray-600 dark:text-gray-300 mb-3">
|
||||
{isZh
|
||||
? '在 AI 指令中明确列举高危操作,通过两种策略进行控制:'
|
||||
: 'Define high-risk operations in AI instructions and control them through two strategies:'}
|
||||
</p>
|
||||
<div className="space-y-2">
|
||||
<div className="pl-3 border-l-2 border-red-400">
|
||||
<p className="font-medium text-red-700 dark:text-red-300">
|
||||
{isZh ? '完全禁止操作' : 'Completely Forbidden'}
|
||||
</p>
|
||||
<p className="text-sm text-gray-500 dark:text-gray-400">
|
||||
{isZh
|
||||
? '对极高风险操作明确禁止执行'
|
||||
: 'Explicitly prohibit execution of extremely high-risk operations'}
|
||||
</p>
|
||||
</div>
|
||||
<div className="pl-3 border-l-2 border-orange-400">
|
||||
<p className="font-medium text-orange-700 dark:text-orange-300">
|
||||
{isZh ? '需用户确认操作' : 'Requires User Confirmation'}
|
||||
</p>
|
||||
<p className="text-sm text-gray-500 dark:text-gray-400">
|
||||
{isZh
|
||||
? '对中等风险操作要求用户明确同意'
|
||||
: 'Require explicit user consent for medium-risk operations'}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
Reference in New Issue
Block a user