@@ -470,6 +470,16 @@ export async function importSplitProData(
470470 `Starting import: ${ data . users . length } users, ${ data . groups . length } groups, ${ data . expenses . length } expenses` ,
471471 ) ;
472472
473+ // Build lookup maps for human-readable log messages
474+ const exportUserNames = new Map < number , string > ( ) ;
475+ for ( const u of data . users ) {
476+ exportUserNames . set ( u . id , u . name ?? u . email ?? `User #${ u . id } ` ) ;
477+ }
478+ const exportGroupNames = new Map < number , string > ( ) ;
479+ for ( const g of data . groups ) {
480+ exportGroupNames . set ( g . id , g . name ) ;
481+ }
482+
473483 // Build mapping from exported userId → existing or new local userId
474484 const userIdMap = new Map < number , number > ( ) ;
475485
@@ -484,7 +494,10 @@ export async function importSplitProData(
484494 const existing = await db . user . findUnique ( { where : { email : exportedUser . email } } ) ;
485495 if ( existing ) {
486496 userIdMap . set ( exportedUser . id , existing . id ) ;
487- log ( 'info' , `User mapped: ${ exportedUser . name ?? exportedUser . email } → existing account` ) ;
497+ log (
498+ 'info' ,
499+ `User mapped: "${ exportedUser . name ?? 'unknown' } " (${ exportedUser . email } ) → existing account (DB #${ existing . id } )` ,
500+ ) ;
488501 continue ;
489502 }
490503 }
@@ -496,7 +509,10 @@ export async function importSplitProData(
496509 } ) ;
497510 if ( existingLocal ) {
498511 userIdMap . set ( exportedUser . id , existingLocal . id ) ;
499- log ( 'info' , `User mapped: ${ localName } → existing local user` ) ;
512+ log (
513+ 'info' ,
514+ `User mapped: "${ localName } " (no email, local user) → existing DB #${ existingLocal . id } ` ,
515+ ) ;
500516 continue ;
501517 }
502518
@@ -509,7 +525,7 @@ export async function importSplitProData(
509525 } ,
510526 } ) ;
511527 userIdMap . set ( exportedUser . id , newUser . id ) ;
512- log ( 'info' , `User created: ${ localName } ` ) ;
528+ log ( 'info' , `User created: " ${ localName } " (no email) → new DB # ${ newUser . id } ` ) ;
513529 }
514530
515531 // Warn about multiple export IDs mapping to the same DB user
@@ -519,11 +535,12 @@ export async function importSplitProData(
519535 list . push ( exportId ) ;
520536 reverseMap . set ( dbId , list ) ;
521537 }
522- for ( const [ , exportIds ] of reverseMap ) {
538+ for ( const [ dbId , exportIds ] of reverseMap ) {
523539 if ( exportIds . length > 1 ) {
540+ const names = exportIds . map ( ( id ) => `"${ exportUserNames . get ( id ) ?? id } "` ) . join ( ', ' ) ;
524541 log (
525542 'warn' ,
526- `${ exportIds . length } exported user IDs (${ exportIds . join ( ', ' ) } ) map to same DB user — participants will be deduplicated ` ,
543+ `${ exportIds . length } exported users (${ names } ) all map to same DB user # ${ dbId } — their expenses will be merged. This usually means duplicate local users existed during export. ` ,
527544 ) ;
528545 }
529546 }
@@ -551,9 +568,22 @@ export async function importSplitProData(
551568 data : missingMembers . map ( ( userId ) => ( { userId, groupId : existing . id } ) ) ,
552569 skipDuplicates : true ,
553570 } ) ;
554- log ( 'info' , `Group "${ exportedGroup . name } ": restored ${ missingMembers . length } member(s)` ) ;
571+ const memberNames = exportedGroup . members
572+ . filter ( ( m ) => {
573+ const uid = userIdMap . get ( m . userId ) ;
574+ return uid !== undefined && ! existingMemberIds . has ( uid ) ;
575+ } )
576+ . map ( ( m ) => exportUserNames . get ( m . userId ) ?? `#${ m . userId } ` )
577+ . map ( ( n ) => `"${ n } "` ) ;
578+ log (
579+ 'info' ,
580+ `Group "${ exportedGroup . name } ": restored ${ missingMembers . length } member(s): ${ memberNames . join ( ', ' ) } ` ,
581+ ) ;
555582 } else {
556- log ( 'info' , `Group "${ exportedGroup . name } ": already exists` ) ;
583+ log (
584+ 'info' ,
585+ `Group "${ exportedGroup . name } ": already exists (${ existing . groupUsers . length } members)` ,
586+ ) ;
557587 }
558588 continue ;
559589 }
@@ -608,9 +638,13 @@ export async function importSplitProData(
608638 skipDuplicates : true ,
609639 } ) ;
610640 }
641+ const groupName = exportedExpense . groupId
642+ ? ( exportGroupNames . get ( exportedExpense . groupId ) ?? 'unknown group' )
643+ : 'no group' ;
644+ const expDate = new Date ( exportedExpense . expenseDate ) . toLocaleDateString ( 'de-DE' ) ;
611645 log (
612646 'warn' ,
613- `Expense "${ exportedExpense . name } " ( ${ exportedExpense . id } ): skipped (already exists) ` ,
647+ `Expense skipped (already exists): "${ exportedExpense . name } " — ${ exportedExpense . amount } ${ exportedExpense . currency } , ${ expDate } , ${ groupName } ` ,
614648 ) ;
615649 expensesSkipped ++ ;
616650 continue ;
@@ -619,9 +653,22 @@ export async function importSplitProData(
619653 const paidByUserId = userIdMap . get ( exportedExpense . paidByUserId ) ;
620654 const addedByUserId = userIdMap . get ( exportedExpense . addedByUserId ) ;
621655 if ( ! paidByUserId || ! addedByUserId ) {
656+ const paidByName = exportUserNames . get ( exportedExpense . paidByUserId ) ?? 'unknown' ;
657+ const addedByName = exportUserNames . get ( exportedExpense . addedByUserId ) ?? 'unknown' ;
658+ const groupName = exportedExpense . groupId
659+ ? ( exportGroupNames . get ( exportedExpense . groupId ) ?? 'unknown group' )
660+ : 'no group' ;
661+ const expDate = new Date ( exportedExpense . expenseDate ) . toLocaleDateString ( 'de-DE' ) ;
662+ const missing = [ ] ;
663+ if ( ! paidByUserId ) {
664+ missing . push ( `payer "${ paidByName } " not found` ) ;
665+ }
666+ if ( ! addedByUserId ) {
667+ missing . push ( `creator "${ addedByName } " not found` ) ;
668+ }
622669 log (
623- 'warn ' ,
624- `Expense "${ exportedExpense . name } " ( ${ exportedExpense . id } ): skipped (paidBy= ${ exportedExpense . paidByUserId } addedBy= ${ exportedExpense . addedByUserId } not found in user map) ` ,
670+ 'error ' ,
671+ `Expense skipped ( ${ missing . join ( ', ' ) } ): "${ exportedExpense . name } " — ${ exportedExpense . amount } ${ exportedExpense . currency } , ${ expDate } , ${ groupName } ` ,
625672 ) ;
626673 expensesSkipped ++ ;
627674 continue ;
@@ -661,7 +708,16 @@ export async function importSplitProData(
661708 } ) ;
662709 expensesImported ++ ;
663710 } catch ( err ) {
664- log ( 'error' , `Expense "${ exportedExpense . name } ": ${ String ( err ) } ` ) ;
711+ const groupName = exportedExpense . groupId
712+ ? ( exportGroupNames . get ( exportedExpense . groupId ) ?? 'unknown group' )
713+ : 'no group' ;
714+ const expDate = new Date ( exportedExpense . expenseDate ) . toLocaleDateString ( 'de-DE' ) ;
715+ const paidByName = exportUserNames . get ( exportedExpense . paidByUserId ) ?? 'unknown' ;
716+ const errMsg = err instanceof Error ? err . message : String ( err ) ;
717+ log (
718+ 'error' ,
719+ `Expense failed: "${ exportedExpense . name } " — ${ exportedExpense . amount } ${ exportedExpense . currency } , ${ expDate } , ${ groupName } , paid by "${ paidByName } ". Error: ${ errMsg } ` ,
720+ ) ;
665721 expensesSkipped ++ ;
666722 }
667723 }
@@ -849,6 +905,14 @@ export async function importFromSplitwisePro(
849905 const expenseId = splitwiseIdToUuid ( swExp . id ) ;
850906 const existing = await db . expense . findUnique ( { where : { id : expenseId } } ) ;
851907 if ( existing ) {
908+ const groupName = swExp . group_id
909+ ? ( data . groups . find ( ( g ) => g . id === swExp . group_id ) ?. name ?? 'unknown group' )
910+ : 'no group' ;
911+ const expDate = new Date ( swExp . date ) . toLocaleDateString ( 'de-DE' ) ;
912+ log (
913+ 'warn' ,
914+ `Expense skipped (already exists): "${ swExp . description } " — ${ swExp . cost } ${ swExp . currency_code } , ${ expDate } , ${ groupName } ` ,
915+ ) ;
852916 expensesSkipped ++ ;
853917 continue ;
854918 }
@@ -862,7 +926,15 @@ export async function importFromSplitwisePro(
862926
863927 const paidByUserId = userIdMap . get ( payerSwId ) ;
864928 if ( ! paidByUserId ) {
865- log ( 'warn' , `Expense "${ swExp . description } ": skipped (unknown payer)` ) ;
929+ const payerName = data . friends . find ( ( f ) => f . id === payerSwId ) ;
930+ const groupName = swExp . group_id
931+ ? ( data . groups . find ( ( g ) => g . id === swExp . group_id ) ?. name ?? 'unknown group' )
932+ : 'no group' ;
933+ const expDate = new Date ( swExp . date ) . toLocaleDateString ( 'de-DE' ) ;
934+ log (
935+ 'error' ,
936+ `Expense skipped (payer "${ payerName ? [ payerName . first_name , payerName . last_name ] . filter ( Boolean ) . join ( ' ' ) : `Splitwise #${ payerSwId } ` } " not found): "${ swExp . description } " — ${ swExp . cost } ${ swExp . currency_code } , ${ expDate } , ${ groupName } ` ,
937+ ) ;
866938 expensesSkipped ++ ;
867939 continue ;
868940 }
@@ -931,7 +1003,15 @@ export async function importFromSplitwisePro(
9311003 } ) ;
9321004 expensesImported ++ ;
9331005 } catch ( err ) {
934- log ( 'error' , `Expense "${ swExp . description } ": ${ String ( err ) } ` ) ;
1006+ const groupName = swExp . group_id
1007+ ? ( data . groups . find ( ( g ) => g . id === swExp . group_id ) ?. name ?? 'unknown group' )
1008+ : 'no group' ;
1009+ const expDate = new Date ( swExp . date ) . toLocaleDateString ( 'de-DE' ) ;
1010+ const errMsg = err instanceof Error ? err . message : String ( err ) ;
1011+ log (
1012+ 'error' ,
1013+ `Expense failed: "${ swExp . description } " — ${ swExp . cost } ${ swExp . currency_code } , ${ expDate } , ${ groupName } . Error: ${ errMsg } ` ,
1014+ ) ;
9351015 expensesSkipped ++ ;
9361016 }
9371017 }
0 commit comments