@@ -15,7 +15,7 @@ import { WithInstance } from "../../src/project/with-instance"
1515import * as Log from "@opencode-ai/core/util/log"
1616import { Permission } from "../../src/permission"
1717import { Plugin } from "../../src/plugin"
18- import { provideTmpdirInstance , tmpdir } from "../fixture/fixture"
18+ import { provideTmpdirInstance , TestInstance , tmpdir } from "../fixture/fixture"
1919import { Session as SessionNs } from "@/session/session"
2020import { MessageV2 } from "../../src/session/message-v2"
2121import { MessageID , PartID , SessionID } from "../../src/session/schema"
@@ -147,6 +147,53 @@ async function assistant(sessionID: SessionID, parentID: MessageID, root: string
147147 return msg
148148}
149149
150+ function createUserMessage ( sessionID : SessionID , text : string ) {
151+ return Effect . gen ( function * ( ) {
152+ const ssn = yield * SessionNs . Service
153+ const msg = yield * ssn . updateMessage ( {
154+ id : MessageID . ascending ( ) ,
155+ role : "user" ,
156+ sessionID,
157+ agent : "build" ,
158+ model : ref ,
159+ time : { created : Date . now ( ) } ,
160+ } )
161+ yield * ssn . updatePart ( {
162+ id : PartID . ascending ( ) ,
163+ messageID : msg . id ,
164+ sessionID,
165+ type : "text" ,
166+ text,
167+ } )
168+ return msg
169+ } )
170+ }
171+
172+ function createAssistantMessage ( sessionID : SessionID , parentID : MessageID , root : string ) {
173+ return SessionNs . Service . use ( ( ssn ) =>
174+ ssn . updateMessage ( {
175+ id : MessageID . ascending ( ) ,
176+ role : "assistant" ,
177+ sessionID,
178+ mode : "build" ,
179+ agent : "build" ,
180+ path : { cwd : root , root } ,
181+ cost : 0 ,
182+ tokens : {
183+ output : 0 ,
184+ input : 0 ,
185+ reasoning : 0 ,
186+ cache : { read : 0 , write : 0 } ,
187+ } ,
188+ modelID : ref . modelID ,
189+ providerID : ref . providerID ,
190+ parentID,
191+ time : { created : Date . now ( ) } ,
192+ finish : "end_turn" ,
193+ } ) ,
194+ )
195+ }
196+
150197async function summaryAssistant ( sessionID : SessionID , parentID : MessageID , root : string , text : string ) {
151198 const msg : MessageV2 . Assistant = {
152199 id : MessageID . ascending ( ) ,
@@ -805,35 +852,35 @@ describe("session.compaction.prune", () => {
805852} )
806853
807854describe ( "session.compaction.process" , ( ) => {
808- test ( "throws when parent is not a user message" , async ( ) => {
809- await using tmp = await tmpdir ( )
810- await WithInstance . provide ( {
811- directory : tmp . path ,
812- fn : async ( ) => {
813- const session = await svc . create ( { } )
814- const msg = await user ( session . id , "hello" )
815- const reply = await assistant ( session . id , msg . id , tmp . path )
816- const rt = runtime ( "continue" )
817- try {
818- const msgs = await svc . messages ( { sessionID : session . id } )
819- await expect (
820- rt . runPromise (
821- SessionCompaction . Service . use ( ( svc ) =>
822- svc . process ( {
823- parentID : reply . id ,
824- messages : msgs ,
825- sessionID : session . id ,
826- auto : false ,
827- } ) ,
828- ) ,
829- ) ,
830- ) . rejects . toThrow ( `Compaction parent must be a user message: ${ reply . id } ` )
831- } finally {
832- await rt . dispose ( )
855+ it . instance (
856+ "throws when parent is not a user message" ,
857+ Effect . gen ( function * ( ) {
858+ const test = yield * TestInstance
859+ const ssn = yield * SessionNs . Service
860+ const session = yield * ssn . create ( { } )
861+ const msg = yield * createUserMessage ( session . id , "hello" )
862+ const reply = yield * createAssistantMessage ( session . id , msg . id , test . directory )
863+ const msgs = yield * ssn . messages ( { sessionID : session . id } )
864+
865+ const exit = yield * Effect . exit (
866+ SessionCompaction . use . process ( {
867+ parentID : reply . id ,
868+ messages : msgs ,
869+ sessionID : session . id ,
870+ auto : false ,
871+ } ) ,
872+ )
873+
874+ expect ( Exit . isFailure ( exit ) ) . toBe ( true )
875+ if ( Exit . isFailure ( exit ) ) {
876+ const error = Cause . squash ( exit . cause )
877+ expect ( error ) . toBeInstanceOf ( Error )
878+ if ( error instanceof Error ) {
879+ expect ( error . message ) . toContain ( `Compaction parent must be a user message: ${ reply . id } ` )
833880 }
834- } ,
835- } )
836- } )
881+ }
882+ } ) ,
883+ )
837884
838885 test ( "publishes compacted event on continue" , async ( ) => {
839886 await using tmp = await tmpdir ( )
0 commit comments