@@ -12,6 +12,7 @@ import {
1212 type Storage ,
1313 type ConversationRecord ,
1414 type MessageRecord ,
15+ loadConversationRecord ,
1516} from '@google/gemini-cli-core' ;
1617import * as fs from 'node:fs/promises' ;
1718import path from 'node:path' ;
@@ -250,23 +251,27 @@ export const getAllSessionFiles = async (
250251 try {
251252 const files = await fs . readdir ( chatsDir ) ;
252253 const sessionFiles = files
253- . filter ( ( f ) => f . startsWith ( SESSION_FILE_PREFIX ) && f . endsWith ( '.json' ) )
254+ . filter (
255+ ( f ) =>
256+ f . startsWith ( SESSION_FILE_PREFIX ) &&
257+ ( f . endsWith ( '.json' ) || f . endsWith ( '.jsonl' ) ) ,
258+ )
254259 . sort ( ) ; // Sort by filename, which includes timestamp
255260
256261 const sessionPromises = sessionFiles . map (
257262 async ( file ) : Promise < SessionFileEntry > => {
258263 const filePath = path . join ( chatsDir , file ) ;
259264 try {
260- // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment
261- const content : ConversationRecord = JSON . parse (
262- await fs . readFile ( filePath , 'utf8' ) ,
263- ) ;
265+ const content = await loadConversationRecord ( filePath , {
266+ metadataOnly : ! options . includeFullContent ,
267+ } ) ;
268+ if ( ! content ) {
269+ return { fileName : file , sessionInfo : null } ;
270+ }
264271
265272 // Validate required fields
266273 if (
267274 ! content . sessionId ||
268- ! content . messages ||
269- ! Array . isArray ( content . messages ) ||
270275 ! content . startTime ||
271276 ! content . lastUpdated
272277 ) {
@@ -275,7 +280,7 @@ export const getAllSessionFiles = async (
275280 }
276281
277282 // Skip sessions that only contain system messages (info, error, warning)
278- if ( ! hasUserOrAssistantMessage ( content . messages ) ) {
283+ if ( ! content . hasUserOrAssistantMessage ) {
279284 return { fileName : file , sessionInfo : null } ;
280285 }
281286
@@ -285,7 +290,9 @@ export const getAllSessionFiles = async (
285290 return { fileName : file , sessionInfo : null } ;
286291 }
287292
288- const firstUserMessage = extractFirstUserMessage ( content . messages ) ;
293+ const firstUserMessage = content . firstUserMessage
294+ ? cleanMessage ( content . firstUserMessage )
295+ : extractFirstUserMessage ( content . messages ) ;
289296 const isCurrentSession = currentSessionId
290297 ? file . includes ( currentSessionId . slice ( 0 , 8 ) )
291298 : false ;
@@ -310,11 +317,11 @@ export const getAllSessionFiles = async (
310317
311318 const sessionInfo : SessionInfo = {
312319 id : content . sessionId ,
313- file : file . replace ( '.json' , '' ) ,
320+ file : file . replace ( / \. j s o n l ? $ / , '' ) ,
314321 fileName : file ,
315322 startTime : content . startTime ,
316323 lastUpdated : content . lastUpdated ,
317- messageCount : content . messages . length ,
324+ messageCount : content . messageCount ?? content . messages . length ,
318325 displayName : content . summary
319326 ? stripUnsafeCharacters ( content . summary )
320327 : firstUserMessage ,
@@ -505,10 +512,10 @@ export class SessionSelector {
505512 const sessionPath = path . join ( chatsDir , sessionInfo . fileName ) ;
506513
507514 try {
508- // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment
509- const sessionData : ConversationRecord = JSON . parse (
510- await fs . readFile ( sessionPath , 'utf8' ) ,
511- ) ;
515+ const sessionData = await loadConversationRecord ( sessionPath ) ;
516+ if ( ! sessionData ) {
517+ throw new Error ( 'Failed to load session data' ) ;
518+ }
512519
513520 const displayInfo = `Session ${ sessionInfo . index } : ${ sessionInfo . firstUserMessage } (${ sessionInfo . messageCount } messages, ${ formatRelativeTime ( sessionInfo . lastUpdated ) } )` ;
514521
0 commit comments