@newton-cloud/react
v0.2.3
Published
React integration layer for Newton Cloud Agent.
Readme
@newton-cloud/react
Newton Cloud 的 React 集成包。它把 @newton-cloud/sdk 的 NewtonAgent controller 接入 React,
并组合 @newton-cloud/ui 的消息流、输入器、业务表格和默认样式。
如何选择
| 需求 | 安装包 |
| --- | --- |
| 在 React 应用中开箱即用地接入完整 Agent | @newton-cloud/react |
| 自行组合框架或界面,只使用任务状态与控制能力 | @newton-cloud/sdk |
| 只使用受控 React 组件和默认样式 | @newton-cloud/ui |
| 在自己的服务器上部署浏览器安全网关 | @newton-cloud/server |
包之间的关系
- npm 运行时依赖:
@newton-cloud/react精确依赖@newton-cloud/sdk和@newton-cloud/ui,安装 React 集成时会自动安装这两个包。 - HTTPS 部署关系:
@newton-cloud/sdk通过 HTTPS 调用@newton-cloud/server或兼容的企业网关,再由网关访问 Newton Cloud Open API。 - 独立使用:
@newton-cloud/ui不依赖 SDK,可由应用直接传入 props 和处理交互意图。 - 独立部署:
@newton-cloud/server不会进入浏览器 bundle,也不会随 React 集成自动安装或部署。
安装
npm install --save-exact \
@newton-cloud/[email protected] \
react@19 react-dom@19本包以 React/React DOM 为 peer dependencies。SDK 和 UI 是普通运行时依赖,由本包 精确版本解析;Server 需要单独部署或由兼容的企业网关替代。
默认组件
import { NewtonAgent } from '@newton-cloud/react';
export function AgentPage() {
return (
<NewtonAgent
serverBase="https://newton-gateway.example.test"
placeholder="请输入任务"
submitLabel="发送"
stopLabel="停止"
/>
);
}默认组件和 useNewtonAgent() 已内置 1688 产品能力:商品详情、订单详情、收银台、售后
HTTPS 外链、旺旺、采购/补货 POST 下单,以及带隐藏业务上下文的 Composer 提交都不要求
宿主适配。UI 组件与 SDK controller 只产生和校验语义 intent,URL、DOM 与消息序列化由本 React 集成执行。
businessProductAdapter 是可选的逐方法覆盖点,不是运行前提。例如桌面壳只接管导航时,
未覆盖的旺旺、下单和 Composer 能力仍使用本包的默认实现:
<NewtonAgent
serverBase="/newton-gateway"
businessProductAdapter={{
openExternal(input) {
desktopShell.openProductIntent(input);
},
}}
/>默认组件在存在受支持的 live business resource 时打开桌面 workspace:Conversation、资源入口
和 Composer 保持在左侧,当前 ComplexTable panel 位于右侧;关闭 panel 后左侧扩展,资源入口
仍可重新打开它。React 集成管理 live/replay、open/active、session/reset 和 intent policy,实际分栏
DOM/CSS 由 UI 包的 ConversationWorkspace 提供。当前契约不持久化 workspace 状态、不同时展示多个
panel,也不承诺移动端 workspace 形态。
serverBase 必须指向 @newton-cloud/server 或兼容的企业浏览器安全网关,不能直接指向
Newton Cloud Open API。浏览器 bundle、配置和日志中不得出现 app secret、上游 access token
或签名材料。目标服务需要允许消费应用的 origin;HTTPS 页面必须使用 HTTPS 服务地址。
注入 request
已有统一浏览器 HTTP 封装时可以注入 request executor。路径选择、请求体、轮询和 resume
仍由 SDK 负责。企业自建网关的路径不同但遵循相同任务 API 契约时,同时配置 taskPaths:
import {
NewtonAgent,
type NewtonAgentProps,
} from '@newton-cloud/react';
import type { NewtonRequestExecutor } from '@newton-cloud/sdk';
const request: NewtonRequestExecutor = async req => {
const response = await fetch(req.url, {
method: req.method,
headers: {
...req.headers,
Authorization: getEnterpriseToken(),
'x-tenant-id': currentTenantId(),
},
body: JSON.stringify(req.body),
signal: req.signal,
credentials: 'include',
});
return { status: response.status, data: await response.json() };
};
const props: NewtonAgentProps = {
serverBase: 'https://agent.isv.example.com/gateway',
taskPaths: {
createTask: '/internal/newton/create',
getTask: '/internal/newton/query',
resumeTask: '/internal/newton/resume',
killTask: '/internal/newton/stop',
fetchTask: '/internal/newton/fetch',
},
request,
};
export function AgentPage() {
return <NewtonAgent {...props} />;
}request executor 可以添加浏览器会话上下文,但不能注入 app secret、上游 access token 或签名材料。企业网关
或兼容服务必须真实校验身份及 taskId / sessionId 的租户归属。
如果企业网络层只在标准网关响应外增加统一 HTTP envelope,可通过
transformResponse 解包回 { success, data, eagleTraceId? }。它不用于改写业务字段、
模拟 fromIndex/nextIndex 或补齐缺失的任务接口。
Hook 与已有 controller
import { NewtonAgent as NewtonAgentController } from '@newton-cloud/sdk';
import { useNewtonAgent } from '@newton-cloud/react';
const controller = new NewtonAgentController({
serverBase: '/newton-gateway',
});
export function CustomAgent() {
const runtime = useNewtonAgent({ agent: controller });
const active = runtime.businessWorkspace.activeResourceRef;
return (
<div>
{runtime.businessWorkspace.entries.map(entry => (
<button
key={`${entry.resourceRef.taskId}:${entry.resourceRef.resourceId}`}
onClick={() => runtime.openBusinessResource(entry.resourceRef)}
>
{entry.label}
</button>
))}
<button onClick={runtime.closeBusinessWorkspace}>关闭 workspace</button>
<button onClick={() => void runtime.sendMessage('继续')}>{runtime.state.status}</button>
{active ? <span>当前资源:{active.resourceId}</span> : null}
</div>
);
}注入 controller 时,React 集成只订阅,不会在卸载时隐式 kill/reset。内部创建 controller 的
配置是挂载级配置;替换配置应使用新的 React key 或显式创建新 controller。
useNewtonAgent() 返回的 businessWorkspace 是从同一份 state.businessData 派生的只读
presentation snapshot,包括 entries、isOpen、activeResourceRef 和
activeViewModel。openBusinessResource(resourceRef) 负责选择或重新打开当前 occurrence,
closeBusinessWorkspace() 只隐藏 panel,不会删除资源或取消 SDK operation。
表格产生 intent 时,通过同一个 hook 路由:
const result = await runtime.handleBusinessIntent({
resourceRef: entry.resourceRef,
intent,
});
// result 为 'handled' 或 'ignored'runtime intent 会调用当前 controller 的 executeBusinessAction;
follow-order.open-product 会映射为语义化
{ target: 'product-detail', itemId, resourceRef, sessionId, source } 输入,并由本 React 集成默认打开
1688 商品详情。未知 action 或过期 resourceRef 返回 ignored;非 DOM 环境中的浏览器动作也返回
ignored。自定义 adapter rejection 不会重试或修改 SDK 状态。
补货产品能力
补货下单使用独立的 PlaceReplenishmentOrderIntent,不会改变 purchase 固定数量 1 的
PlaceOrderIntent。本 React 集成默认执行对应的 1688 下单表单、旺旺和 Composer 行为;宿主只在
需要替换某个能力时注入该方法:
import {
NewtonAgent,
type BusinessProductAdapter,
type PlaceReplenishmentOrderIntent,
} from '@newton-cloud/react';
const adapter: BusinessProductAdapter = {
submitPrompt(input) {
composer.submit(input.prompt, input.rows);
},
openChat(input) {
if (input.itemId !== undefined) sellerChat.openProduct(input.sellerLoginId, input.itemId);
else sellerChat.openSeller(input.sellerLoginId);
},
async placeReplenishmentOrder(input: PlaceReplenishmentOrderIntent) {
await orderService.place(input.items);
},
};
export function ReplenishmentAgent() {
return <NewtonAgent serverBase="/newton-gateway" businessProductAdapter={adapter} />;
}PlaceReplenishmentOrderIntent.items 保持当前响应顺序,每项包含字符串 offerId、允许为空的
specId 和 0..99999 的 canonical quantity;DTO 不包含 URL、form、凭证或上游 API 私有字段。
订单场景产品能力
myOrders 的「查看订单 / 立即支付」映射为 openExternal 的 order-detail / order-cashier
语义 target,并由本 React 集成默认打开 1688 订单详情/收银台;RiskOrder 的「催促商家处理」映射为
urgeSeller,携带按当前响应顺序去重的 orderNos(选择为空时为 [])。默认实现负责源兼容
的隐藏分隔符、{ query, orderNos } 序列化和 Composer 提交。
迁移说明:OpenExternalIntent 已从单一接口改为按 target 判别的联合类型。
既有实现直接访问 input.itemId 会编译失败,必须先 narrowing;运行时行为不变。
既有宿主 adapter 仍兼容,并会逐方法覆盖默认实现:
const adapter: BusinessProductAdapter = {
openExternal(input) {
if (input.target === 'product-detail') productRouter.openItem(input.itemId);
else if (input.target === 'order-detail') tradeRouter.openOrder(input.orderId);
else if (input.target === 'order-cashier') tradeRouter.openCashier(input.orderId);
else if (input.target === 'url') browserRouter.openHttps(input.url);
// 前向兼容策略:忽略未知 target,不影响既有 target。
},
urgeSeller(input) {
composer.submit(input.prompt, { orderNos: input.orderNos });
},
};远程分页由 SDK runtime 承载:表格分页交互经 handleBusinessIntent 路由为 changePage
action,React 不持有页码状态;intent 携带的 pageSize 被忽略,pageSize 事实源恒为 chunk
descriptor。
售后场景产品能力
afterSale registration 将级联筛选、清除、分页和重试 intent 路由到同一个 SDK controller。
行内「处理售后」使用 openExternal({ target: 'url', url, ...context });「联系商家」优先使用
openChat,缺少 loginId 时回退商家主页 target: 'url'。行 id 包含
JSON.stringify([taskId, resourceId, dataRevision ?? 0]) interaction scope,旧 revision 或已替换
resourceRef 的 intent 会返回 ignored。
迁移说明:OpenChatIntent.itemId 从必填放宽为可选。afterSale 只保证稳定的
sellerLoginId,宿主读取 itemId 前必须检查 undefined,不得用 refundId 或非契约字段伪造
商品 id。OpenExternalIntent 同时 additive 增加 target: 'url';宿主必须继续按 target
narrowing,并对未知 target fail closed。本 React 集成仅会把可解析的绝对 https: URL 交给 adapter,
相对地址和 javascript:、data: 等 scheme 返回 ignored。
followUps chip 表示“回填但不发送”。公共 DTO 与 adapter 为:
interface InsertPromptIntent {
readonly text: string;
readonly resourceRef: { readonly taskId: string; readonly resourceId: string };
readonly sessionId?: string;
readonly source: ComplexTableActionSource;
}
interface BusinessProductAdapter {
insertPrompt?(input: InsertPromptIntent): void | Promise<void>;
}useNewtonAgent().handleBusinessIntent() 在 capability 缺失时返回 ignored,不会回退
submitPrompt;adapter throw/reject 原样传播。默认 <NewtonAgent /> 自身实现回填其 Composer,
并在提供宿主 insertPrompt 时继续委托该回调。
兼容性与排查
- 建议固定本包精确版本,并保留消费项目 lockfile。
- 类型或构建失败时先检查 React peer 版本以及 bundler 的 ESM/CSS 支持。
- 请求失败时检查
serverBase、HTTPS、CORS、反向代理和目标浏览器安全网关状态。 - 浏览器配置、bundle 和日志不得包含 app secret、上游 access token 或签名材料。
License
Apache-2.0。Copyright 2026 Newton Cloud Open Contributors.
