85 lines
3.1 KiB
TypeScript
85 lines
3.1 KiB
TypeScript
import type { ThreadsAccountData } from '../../types/api'
|
||
import type { OnboardingSnapshot } from '../onboarding'
|
||
import { detectActiveWorkflow } from '../placementFlow'
|
||
import { formatSiteNavGuide } from './siteGuide'
|
||
import { resolveIslanderPageMeta } from './pageRegistry'
|
||
import { threadsAccountLabel } from '../threadsAccount'
|
||
import { formatPlacementHandoffContext, getPlacementHandoff } from './handoffStore'
|
||
import type { IslanderPageMeta } from './types'
|
||
|
||
type BuildContextInput = {
|
||
pathname: string
|
||
activeAccount: ThreadsAccountData | null
|
||
onboarding: OnboardingSnapshot
|
||
pageSnapshot?: string
|
||
pageMeta?: IslanderPageMeta | null
|
||
/** 僅在使用者主動問頁面/操作,或 agent 執行 action 後為 true */
|
||
includePageDetail?: boolean
|
||
}
|
||
|
||
const onboardingStepLabel = {
|
||
account: '建立經營帳號',
|
||
connection: '完成 Threads 連線',
|
||
persona: '建立至少一個人設',
|
||
} as const
|
||
|
||
export function buildIslanderContext(input: BuildContextInput): string {
|
||
const includePage = input.includePageDetail === true
|
||
const page = resolveIslanderPageMeta(input.pathname, input.pageMeta)
|
||
const accountLabel = input.activeAccount ? threadsAccountLabel(input.activeAccount) : '(尚未選擇)'
|
||
const publishPath = input.activeAccount
|
||
? `/threads/${input.activeAccount.id}/publish`
|
||
: '/settings'
|
||
const connectionsPath = input.activeAccount
|
||
? `/threads/${input.activeAccount.id}/connections`
|
||
: '/settings'
|
||
|
||
const handoff = getPlacementHandoff()
|
||
const handoffBlock = formatPlacementHandoffContext(handoff)
|
||
const workflow = detectActiveWorkflow(input.pathname)
|
||
const workflowLabel =
|
||
workflow === 'copy'
|
||
? '流程 A · 拷貝忍者(仿寫爆款,用人設 8D)'
|
||
: workflow === 'placement'
|
||
? '流程 B · 找 TA(品牌痛點獲客)'
|
||
: '(非核心工作流頁)'
|
||
|
||
const sections = [
|
||
'【目前位置】',
|
||
`- 路徑:${input.pathname}`,
|
||
`- 工作流:${workflowLabel}`,
|
||
includePage
|
||
? `- 頁面:${page.title}`
|
||
: '- 頁面細節:使用者尚未詢問,請勿主動介紹這頁功能或元素',
|
||
'',
|
||
'【目前帳號】',
|
||
`- 經營帳號:${accountLabel}`,
|
||
`- 入門進度:${input.onboarding.isComplete ? '已完成' : input.onboarding.nextStep ? `進行中(${onboardingStepLabel[input.onboarding.nextStep]})` : '載入中'}`,
|
||
'',
|
||
'【常用捷徑】',
|
||
`- 設定與 AI key → /settings`,
|
||
`- 任務列表 → /jobs`,
|
||
`- 人設庫 → /personas`,
|
||
`- 發文 → ${publishPath}`,
|
||
`- 連線細節 → ${connectionsPath}`,
|
||
'',
|
||
'【站內導覽】',
|
||
formatSiteNavGuide(),
|
||
handoffBlock,
|
||
]
|
||
|
||
if (includePage) {
|
||
sections.push(
|
||
'',
|
||
'【目前頁面】',
|
||
page.purpose ? `- 用途:${page.purpose}` : '',
|
||
page.hints?.length ? `- 提示:${page.hints.join(';')}` : '',
|
||
'',
|
||
'【目前頁面可互動元素】',
|
||
'格式:ref | kind | label | meta(offscreen 表示需先 scroll)',
|
||
input.pageSnapshot?.trim() || '(尚未擷取)',
|
||
)
|
||
}
|
||
|
||
return sections.filter((line) => line !== '').join('\n')
|
||
} |