@@ -7,7 +7,7 @@ import initOnyxDerivedValues from '@libs/actions/OnyxDerived';
77import { WRITE_COMMANDS } from '@libs/API/types' ;
88import { getOriginalMessage } from '@libs/ReportActionsUtils' ;
99import { buildOptimisticIOUReport , buildOptimisticIOUReportAction } from '@libs/ReportUtils' ;
10- import { buildOptimisticTransaction } from '@libs/TransactionUtils' ;
10+ import { buildOptimisticTransaction , isTimeRequest } from '@libs/TransactionUtils' ;
1111import CONST from '@src/CONST' ;
1212import IntlStore from '@src/languages/IntlStore' ;
1313import OnyxUpdateManager from '@src/libs/actions/OnyxUpdateManager' ;
@@ -690,6 +690,8 @@ describe('actions/Duplicate', () => {
690690 } ,
691691 } ;
692692
693+ await Onyx . clear ( ) ;
694+
693695 duplicateExpenseTransaction ( {
694696 transaction : mockCashExpenseTransaction ,
695697 optimisticChatReportID : mockOptimisticChatReportID ,
@@ -722,6 +724,64 @@ describe('actions/Duplicate', () => {
722724 // The duplicated transaction should have a different transactionID than the original
723725 expect ( duplicatedTransaction ?. transactionID ) . not . toBe ( mockCashExpenseTransaction . transactionID ) ;
724726 } ) ;
727+
728+ it ( 'should create a duplicate time expense successfully' , async ( ) => {
729+ const transactionID = 'time-1' ;
730+ const HOURLY_RATE = 9.99 ;
731+ const HOURS_WORKED = 15 ;
732+ const AMOUNT_CENTS = Math . round ( HOURS_WORKED * HOURLY_RATE * 100 ) ;
733+
734+ const mockTimeExpenseTransaction = {
735+ ...mockTransaction ,
736+ transactionID,
737+ amount : AMOUNT_CENTS ,
738+ comment : {
739+ type : 'time' as const ,
740+ units : {
741+ unit : 'h' as const ,
742+ count : HOURS_WORKED ,
743+ rate : HOURLY_RATE ,
744+ } ,
745+ } ,
746+ } ;
747+
748+ await Onyx . clear ( ) ;
749+
750+ duplicateExpenseTransaction ( {
751+ transaction : mockTimeExpenseTransaction ,
752+ optimisticChatReportID : mockOptimisticChatReportID ,
753+ optimisticIOUReportID : mockOptimisticIOUReportID ,
754+ isASAPSubmitBetaEnabled : mockIsASAPSubmitBetaEnabled ,
755+ introSelected : undefined ,
756+ activePolicyID : undefined ,
757+ quickAction : undefined ,
758+ policyRecentlyUsedCurrencies : [ ] ,
759+ targetPolicy : mockPolicy ,
760+ targetPolicyCategories : fakePolicyCategories ,
761+ targetReport : policyExpenseChat ,
762+ } ) ;
763+
764+ await waitForBatchedUpdates ( ) ;
765+
766+ let duplicatedTransaction : OnyxEntry < Transaction > ;
767+
768+ await getOnyxData ( {
769+ key : ONYXKEYS . COLLECTION . TRANSACTION ,
770+ waitForCollectionCallback : true ,
771+ callback : ( allTransactions ) => {
772+ const transactions = Object . values ( allTransactions ?? { } ) . filter ( ( t ) => ! ! t ) ;
773+ expect ( transactions ) . toHaveLength ( 1 ) ;
774+ duplicatedTransaction = transactions . at ( 0 ) ;
775+ } ,
776+ } ) ;
777+
778+ expect ( duplicatedTransaction ?. transactionID ) . not . toBe ( transactionID ) ;
779+ expect ( duplicatedTransaction ?. comment ?. units ?. count ) . toEqual ( HOURS_WORKED ) ;
780+ expect ( duplicatedTransaction ?. comment ?. units ?. rate ) . toEqual ( HOURLY_RATE ) ;
781+ expect ( duplicatedTransaction ?. comment ?. units ?. unit ) . toBe ( 'h' ) ;
782+ expect ( duplicatedTransaction ?. comment ?. type ) . toBe ( 'time' ) ;
783+ expect ( isTimeRequest ( duplicatedTransaction ) ) . toBeTruthy ( ) ;
784+ } ) ;
725785 } ) ;
726786
727787 describe ( 'resolveDuplicate' , ( ) => {
0 commit comments