Files
deepseek-harness/packages/experimental/schedule-bundle/tests/patch.spec.ts
T
Chinesezjc fd53e83125 Merge origin/master into feat/preset-scoped-schedule-tools
master now ships the reminder stack as the optional
`@deepseek-ai/dsh-experimental-schedule-bundle`; this branch keeps the
preset-level ownership beside it.

Resolutions:
- The Host rows keep master's `disabled: true`. The optional bundle switches
  `schedule` and `ui-schedule` on and no longer `time-context`: the clock row
  is preset-level, so flipping the Host row as well would mount the plugin in
  two scopes and write two readings per step.
- `standard`, `cordis`, and `ptc` declare `preset-time-context` and
  `tool-schedule`; `minimal` declares neither.
- `tool-schedule` injects `tools` and resolves `schedule` per scope through
  `ctx.inject`, so the row stays valid but produces no tools while the service
  is off, and produces them once the bundle mounts it.
- The assembled-Web Schedule spec keeps master's bundle overlay and restates
  the shipped `preset-standard` row instead of the deleted fixture, because a
  top-level patch cannot reach a plugin a preset declares.
- Documentation and Agent Notes describe both layers; the note master archived
  stays frozen with its manifest hashes.
2026-09-26 01:12:54 +08:00

56 lines
2.0 KiB
TypeScript

/** The experimental Schedule switch must turn on exactly the two Host rows the Web bundle inserts. */
import { readFileSync } from 'node:fs'
import { resolve } from 'node:path'
import { fileURLToPath } from 'node:url'
import { describe, expect, it } from 'vitest'
import * as yaml from 'js-yaml'
import { entryListSchema } from '@deepseek-ai/cordis-plugin-include'
const root = fileURLToPath(new URL('..', import.meta.url))
interface Manifest {
name?: string
icon?: string
private?: boolean
publishConfig?: { access?: string }
exports?: Record<string, unknown>
dependencies?: Record<string, string>
dsh?: { bundle?: { patch?: string } }
}
interface Patch {
id?: string
name?: string
disabled?: boolean
insert?: unknown[]
}
describe('experimental Schedule bundle', () => {
const manifest = JSON.parse(readFileSync(resolve(root, 'package.json'), 'utf8')) as Manifest
it('publishes as an experimental bundle with plugin-manager display metadata', () => {
expect(manifest.name).toBe('@deepseek-ai/dsh-experimental-schedule-bundle')
expect(manifest.private).toBeUndefined()
expect(manifest.publishConfig?.access).toBe('public')
expect(manifest.icon).toBe('./icon.svg')
expect(manifest.dsh?.bundle?.patch).toBe('./cordis.patch.yml')
expect(manifest.exports?.['./locale/*.json']).toBe('./locale/*.json')
expect(manifest.exports?.['./cordis.patch.yml']).toBe('./cordis.patch.yml')
// The patch only overrides rows another layer inserts, so it depends on no plugin package.
expect(manifest.dependencies).toBeUndefined()
})
it('turns the two shipped Host rows on and appends none', () => {
const parsed = yaml.load(readFileSync(resolve(root, './cordis.patch.yml'), 'utf8'), { schema: entryListSchema })
expect(parsed).toEqual([
{ id: 'schedule', disabled: false },
{ id: 'ui-schedule', disabled: false },
])
for (const patch of parsed as Patch[]) {
expect(patch.insert).toBeUndefined()
expect(patch.name).toBeUndefined()
}
})
})