@@ -67,6 +67,55 @@ test("listPiSessions parses headers, filters by cwd, sorts by mtime desc", () =>
6767 }
6868} ) ;
6969
70+ test ( "listPiSessions prefers the session_info name (last wins), else preview" , ( ) => {
71+ const agentDir = mkdtempSync ( join ( tmpdir ( ) , "pino-agent-" ) ) ;
72+ try {
73+ const cwd = "/work/named" ;
74+ const dir = piSessionsDir ( cwd , agentDir ) ;
75+ mkdirSync ( dir , { recursive : true } ) ;
76+
77+ // Named session: two session_info entries → the LAST one wins for the label,
78+ // while `preview` still reflects the first user message.
79+ const named = join ( dir , "2026-01-01T00-00-00-000Z_named.jsonl" ) ;
80+ writeFileSync (
81+ named ,
82+ [
83+ JSON . stringify ( { type : "session" , version : 3 , id : "named" , timestamp : "2026-01-01T00:00:00.000Z" , cwd } ) ,
84+ JSON . stringify ( { type : "message" , message : { role : "user" , content : [ { type : "text" , text : "add rate limiting to my express api" } ] } } ) ,
85+ JSON . stringify ( { type : "session_info" , id : "si1" , timestamp : "2026-01-01T00:01:00.000Z" , name : "Rough First Name" } ) ,
86+ JSON . stringify ( { type : "message" , message : { role : "assistant" , content : [ { type : "text" , text : "sure" } ] } } ) ,
87+ JSON . stringify ( { type : "session_info" , id : "si2" , timestamp : "2026-01-01T00:02:00.000Z" , name : "Add Rate Limiting to Express API" } ) ,
88+ ] . join ( "\n" ) + "\n" ,
89+ ) ;
90+
91+ // Unnamed session: no session_info → falls back to the first user message.
92+ const unnamed = join ( dir , "2026-01-01T00-00-00-000Z_unnamed.jsonl" ) ;
93+ writeFileSync (
94+ unnamed ,
95+ [
96+ JSON . stringify ( { type : "session" , version : 3 , id : "unnamed" , timestamp : "2026-01-01T00:00:00.000Z" , cwd } ) ,
97+ JSON . stringify ( { type : "message" , message : { role : "user" , content : [ { type : "text" , text : "just the first message" } ] } } ) ,
98+ ] . join ( "\n" ) + "\n" ,
99+ ) ;
100+
101+ utimesSync ( named , new Date ( 2000 ) , new Date ( 2000 ) ) ;
102+ utimesSync ( unnamed , new Date ( 1000 ) , new Date ( 1000 ) ) ;
103+
104+ const list = listPiSessions ( cwd , agentDir ) ;
105+ const byId = Object . fromEntries ( list . map ( ( m ) => [ m . piSessionId , m ] ) ) ;
106+
107+ // Named: label is the latest session_info name; preview keeps the 1st message.
108+ assert . equal ( byId . named . name , "Add Rate Limiting to Express API" ) ;
109+ assert . equal ( byId . named . preview , "add rate limiting to my express api" ) ;
110+
111+ // Unnamed: label falls back to the first user message.
112+ assert . equal ( byId . unnamed . name , "just the first message" ) ;
113+ assert . equal ( byId . unnamed . preview , "just the first message" ) ;
114+ } finally {
115+ rmSync ( agentDir , { recursive : true , force : true } ) ;
116+ }
117+ } ) ;
118+
70119test ( "listPiSessions returns [] when the slug dir is absent" , ( ) => {
71120 const agentDir = mkdtempSync ( join ( tmpdir ( ) , "pino-agent-" ) ) ;
72121 try {
0 commit comments