import { type DatabaseSyncLike } from './db.js'; import type { MemoryEntry } from './memory.js'; import type { RerankStep } from './search.js'; export type GoalStatus = 'active' | 'suspended' | 'completed'; export type PolicyType = 'schema-fit-biased' | 'error-prioritized' | 'recency-first' | 'hybrid'; export interface GoalRow { id: string; session_id: string; tenant_id: string; goal_name: string; level: number; parent_goal_id: string | null; status: GoalStatus; success_condition: string | null; retrieval_policy_id: string | null; created_at: string; completed_at: string | null; outcome_score: number | null; } export interface Goal { id: string; sessionId: string; tenantId: string; goalName: string; level: number; parentGoalId?: string; status: GoalStatus; successCondition?: string; retrievalPolicyId?: string; createdAt: string; completedAt?: string; outcomeScore?: number; } export interface RetrievalPolicy { id: string; goalId: string; policyType: PolicyType; weightSchemaFit: number; weightRecency: number; weightOutcome: number; errorPriority: number; } export declare const MAX_ACTIVE_GOAL_DEPTH = 3; export declare const MAX_FINAL_MULTIPLIER = 3; export declare function rowToGoal(row: GoalRow): Goal; export interface PushGoalOpts { sessionId: string; tenantId: string; goalName: string; level?: number; parentGoalId?: string; successCondition?: string; policy?: { policyType: PolicyType; weightSchemaFit?: number; weightRecency?: number; weightOutcome?: number; errorPriority?: number; }; } export declare function pushGoal(hippoRoot: string, opts: PushGoalOpts): Goal; /** * v1.7.4 — depth-cap enforcer extracted from pushGoalWithDb and resumeGoal. * If the (tenant, session) has >= MAX_ACTIVE_GOAL_DEPTH active goals, * suspend the oldest `overflow` ones. * * **Precondition: caller MUST already be inside a `BEGIN IMMEDIATE` * transaction.** Helper does not open or commit -- name reflects this so it * is impossible to misread the contract at a call site. Both existing call * sites (pushGoalWithDb, resumeGoal) wrap in `BEGIN IMMEDIATE` already. * * @internal v1.7.4 -- internal goal-stack invariant. Subject to change. */ export declare function enforceDepthCapWithinTx(db: DatabaseSyncLike, tenantId: string, sessionId: string): void; export declare function pushGoalWithDb(db: DatabaseSyncLike, opts: PushGoalOpts): Goal; export interface GetActiveGoalsOpts { sessionId: string; tenantId: string; } export declare function getActiveGoals(hippoRoot: string, opts: GetActiveGoalsOpts): Goal[]; export declare function getActiveGoalsWithDb(db: DatabaseSyncLike, opts: GetActiveGoalsOpts): Goal[]; /** * v1.7.4 -- dlPFC goal-stack boost helper. Applies the multi-goal boost to a * list of entry-backed scored rows when (tenant, session) has active goals. * Pre-v1.7.4 this logic lived inline in cmdRecall (src/cli.ts:988-1140); * lifting here lets api.recall (primary band only) AND MCP physics/hybrid * call it. * * Caller responsibilities: * - Do NOT call when an explicit `goalTag` is set (caller's gate) * - Pass entry-backed rows (with `entry.tags`, `entry.id`, optional * `entry.schema_fit`) * - Manage the db handle lifecycle (helper neither opens nor closes) * - Recompute `tokens` after if returned rows are projected to a budgeted * shape * * Side effects: * - INSERT OR IGNORE into `goal_recall_log` for each (boosted, goal) pair * - Local memory id filter applied before INSERT (skips global-only ids * to preserve FK invariant on goal_recall_log.memory_id) * * @internal v1.7.4 -- internal recall ranking helper. Subject to change. */ export declare function applyGoalStackBoost(db: DatabaseSyncLike, results: R[], opts: { sessionId: string; tenantId: string; limit: number; /** * A7 recall-trace (optional side-channel). When supplied, the helper * records one goal-boost `RerankStep` per ACTUALLY-boosted row, keyed by * `entry.id`. This is a SEPARATE accumulator, NOT a field on the result * row — the helper re-spreads rows and strips internal markers * (`_goalMatches` below), so a row field would be dropped. The score-mul * + re-sort math is untouched; the trace is only populated when this map * is passed (default path never allocates → byte-identical). */ trace?: Map; }): R[]; export interface CompleteGoalOpts { outcomeScore?: number; /** * v1.7.4 — when true, skip the strength-multiplier propagation block. * Default false (propagate). The goal's status still transitions to * 'completed' and `outcome_score` is still recorded; only the side-effect * on recalled memories' strength is suppressed. * * Note: the status-check idempotency guard short-circuits a second * `completeGoal` call BEFORE this flag is read, so a noPropagate=true * second call after a propagating first call is a true no-op (propagation * already happened on call 1; call 2 returns early regardless). */ noPropagate?: boolean; } export declare function completeGoal(hippoRoot: string, goalId: string, opts: CompleteGoalOpts): void; export declare function suspendGoal(hippoRoot: string, goalId: string): void; export declare function resumeGoal(hippoRoot: string, goalId: string): void; //# sourceMappingURL=goals.d.ts.map