fix: suppress runtime context in minimal profiles
This commit is contained in:
@@ -2,5 +2,5 @@
|
||||
# side as of the last confirmed-consistent state. Both languages carry equal authority;
|
||||
# after editing either side, bring the other along and re-record with:
|
||||
# pnpm run verify-translation-pairing --write packages/preset/persona/README.md
|
||||
README.md: 742141e65fa8d50b89e6b74e6d21aa8c5bfe98cd
|
||||
README.zh.md: 61112d1091e428d8c92aa056b7aaa272d3bbbc1d
|
||||
README.md: 978d01ddbd52095bc2486d27d08fde2d4a8fa79b
|
||||
README.zh.md: d36af6c028f1258d044608535c6da4eaf2fb92e8
|
||||
|
||||
@@ -16,8 +16,9 @@ Mounting this row outside an agent scope collides with the registry's own `deplo
|
||||
|---|---|---|
|
||||
| `text` | required | Persona prose rendered as the `deployment:persona` section |
|
||||
| `complete` | `false` | Restore this persona after assembly as the only system-prompt section |
|
||||
| `includeRuntimeContext` | `true` | Include dynamic runtime-context snapshots for this agent scope; false suppresses every context contribution without disabling its owning services |
|
||||
|
||||
`text` is a template, like any prompt section: complete `{{…}}` groups resolve strictly against registered prompt variables when the prompt renders, not when it assembles. Empty text still occupies the slot, so it shadows the deployment persona away entirely and then disappears at render. With `complete: true`, assembly still resolves contexts, tools, variables, and cooperative listeners, then the prompt registry restores this exact persona as the sole section; no identity, tool guidance, or listener can append prompt text.
|
||||
`text` is a template, like any prompt section: complete `{{…}}` groups resolve strictly against registered prompt variables when the prompt renders, not when it assembles. Empty text still occupies the slot, so it shadows the deployment persona away entirely and then disappears at render. With `complete: true`, assembly still resolves contexts, tools, variables, and cooperative listeners, then the prompt registry restores this exact persona as the sole section; no identity, tool guidance, or listener can append prompt text. With `includeRuntimeContext: false`, context providers are not evaluated for this scope and contexts added by assembly listeners are discarded.
|
||||
|
||||
## Model Experience
|
||||
|
||||
@@ -25,7 +26,7 @@ Mounting this row outside an agent scope collides with the registry's own `deplo
|
||||
|
||||
#### What the model sees
|
||||
|
||||
The `deployment:persona` section at order 0, immediately after the harness identity opener, carrying exactly this row's configured `text` with prompt variables resolved. For an agent whose preset mounts this row, it replaces whatever persona the deployment configured. In complete mode, the model sees only this rendered section as its system prompt.
|
||||
The `deployment:persona` section at order 0, immediately after the harness identity opener, carrying exactly this row's configured `text` with prompt variables resolved. For an agent whose preset mounts this row, it replaces whatever persona the deployment configured. In complete mode, the model sees only this rendered section as its system prompt. Runtime context remains enabled by default. When disabled, a fresh agent receives no runtime-context snapshot from sandbox policy, approval policy, delegation, or another system-prompt context provider.
|
||||
|
||||
#### Token effect
|
||||
|
||||
|
||||
@@ -16,8 +16,9 @@
|
||||
|---|---|---|
|
||||
| `text` | 必填 | 作为 `deployment:persona` 段落渲染的人设文本 |
|
||||
| `complete` | `false` | 组装后将此人设恢复为唯一的系统提示词段落 |
|
||||
| `includeRuntimeContext` | `true` | 是否为此 agent 作用域包含动态 runtime-context 快照;false 会抑制所有上下文贡献,但不禁用拥有它们的服务 |
|
||||
|
||||
`text` 与任何提示词段落一样是模板:完整的 `{{…}}` 组在提示词**渲染**时(而非组装时)严格解析为已注册的提示词变量。空文本同样占据该槽位,因此会把部署级人设整个遮蔽掉,然后在渲染时消失。启用 `complete: true` 时,组装仍会解析上下文、工具、变量和协作式监听器,之后提示词注册表将这份确切人设恢复为唯一段落;身份、工具引导或监听器都无法追加提示词文本。
|
||||
`text` 与任何提示词段落一样是模板:完整的 `{{…}}` 组在提示词**渲染**时(而非组装时)严格解析为已注册的提示词变量。空文本同样占据该槽位,因此会把部署级人设整个遮蔽掉,然后在渲染时消失。启用 `complete: true` 时,组装仍会解析上下文、工具、变量和协作式监听器,之后提示词注册表将这份确切人设恢复为唯一段落;身份、工具引导或监听器都无法追加提示词文本。启用 `includeRuntimeContext: false` 时,此作用域的上下文提供方不会被求值,组装监听器添加的上下文也会被丢弃。
|
||||
|
||||
## 模型体验
|
||||
|
||||
@@ -25,7 +26,7 @@
|
||||
|
||||
#### What the model sees
|
||||
|
||||
位于 order 0 的 `deployment:persona` 段落,紧随 harness 身份开场白之后,携带本行配置的 `text`,其中的提示词变量已解析。对于其 preset 挂载了本行的 agent,它会替换部署所配置的任何人设。在完整模式下,模型只会看到这个渲染后的段落作为系统提示词。
|
||||
位于 order 0 的 `deployment:persona` 段落,紧随 harness 身份开场白之后,携带本行配置的 `text`,其中的提示词变量已解析。对于其 preset 挂载了本行的 agent,它会替换部署所配置的任何人设。在完整模式下,模型只会看到这个渲染后的段落作为系统提示词。Runtime context 默认保持启用。禁用后,新建 agent 不会收到来自沙箱策略、批准策略、委派或其他 system-prompt 上下文提供方的 runtime-context 快照。
|
||||
|
||||
#### Token effect
|
||||
|
||||
|
||||
@@ -40,12 +40,15 @@ export interface Config {
|
||||
text: string
|
||||
/** Make this persona the complete system prompt, suppressing every other section. */
|
||||
complete?: boolean
|
||||
/** Suppress dynamic runtime-context snapshots for this persona's agent scope. */
|
||||
includeRuntimeContext?: boolean
|
||||
}
|
||||
|
||||
/** Runtime schema for the persona row. */
|
||||
export const Config: z<Config> = z.object({
|
||||
text: z.string().required(),
|
||||
complete: z.boolean().default(false),
|
||||
includeRuntimeContext: z.boolean().default(true),
|
||||
})
|
||||
|
||||
/**
|
||||
@@ -61,4 +64,5 @@ export function apply(ctx: Context, config: Config): void {
|
||||
text: config.text,
|
||||
...(config.complete ? { complete: true } : {}),
|
||||
}), 'persona.section()')
|
||||
if (!(config.includeRuntimeContext ?? true)) ctx.systemPrompt.suppressRuntimeContext()
|
||||
}
|
||||
|
||||
@@ -102,4 +102,41 @@ describe('the persona row', () => {
|
||||
expect(assembly.sections).toEqual([{ name: PERSONA_SECTION, text: 'Only this.' }])
|
||||
expect(renderPrompt(assembly)).toBe('Only this.')
|
||||
})
|
||||
|
||||
it('can suppress runtime context for its scope without changing the global assembly', async () => {
|
||||
const ctx = await harness('deployment identity')
|
||||
const key: ScopeKey = { agent: 'a1' }
|
||||
const scope = createScope(ctx, key)
|
||||
ctx.systemPrompt.context({ name: 'policy', order: 1, text: 'global policy' })
|
||||
|
||||
const fiber = await scope.ctx.plugin(Persona, {
|
||||
text: 'Only this.',
|
||||
includeRuntimeContext: false,
|
||||
})
|
||||
const suppressed = await ctx.systemPrompt.assemble({ scope: key })
|
||||
expect(suppressed.contexts).toEqual([])
|
||||
const global = await ctx.systemPrompt.assemble()
|
||||
expect(global.contexts).toEqual([
|
||||
{ name: 'policy', text: 'global policy' },
|
||||
])
|
||||
|
||||
await fiber.dispose()
|
||||
expect((await ctx.systemPrompt.assemble({ scope: key })).contexts).toEqual([
|
||||
{ name: 'policy', text: 'global policy' },
|
||||
])
|
||||
})
|
||||
|
||||
it('keeps runtime context by default when apply bypasses schema defaults', async () => {
|
||||
const ctx = await harness('deployment identity')
|
||||
const key: ScopeKey = { agent: 'a1' }
|
||||
ctx.systemPrompt.context({ name: 'policy', order: 1, text: 'global policy' })
|
||||
|
||||
await ctx.plugin(Object.assign((inner: Context) => {
|
||||
Persona.apply(createScope(inner, key).ctx, { text: 'Scoped identity.' })
|
||||
}, { inject: ['systemPrompt'] }))
|
||||
|
||||
expect((await ctx.systemPrompt.assemble({ scope: key })).contexts).toEqual([
|
||||
{ name: 'policy', text: 'global policy' },
|
||||
])
|
||||
})
|
||||
})
|
||||
|
||||
Reference in New Issue
Block a user