@@ -896,16 +896,64 @@ describe('InstanceWrapper', () => {
896896 } ) ;
897897 } ) ;
898898 describe ( 'when instance is transient' , ( ) => {
899- it ( 'should return all static instances ' , ( ) => {
899+ it ( 'should return instances where constructor was called ' , ( ) => {
900900 const wrapper = new InstanceWrapper ( {
901901 scope : Scope . TRANSIENT ,
902902 } ) ;
903903 const instanceHost = {
904904 instance : { } ,
905+ isConstructorCalled : true ,
905906 } ;
906907 wrapper . setInstanceByInquirerId ( STATIC_CONTEXT , 'test' , instanceHost ) ;
907908 expect ( wrapper . getStaticTransientInstances ( ) ) . to . be . eql ( [ instanceHost ] ) ;
908909 } ) ;
910+
911+ describe ( 'lifecycle hooks on transient services' , ( ) => {
912+ // Tests for issue #15553: prevent lifecycle hooks on non-instantiated transient services
913+ it ( 'should filter out instances created with Object.create (prototype only)' , ( ) => {
914+ const wrapper = new InstanceWrapper ( {
915+ scope : Scope . TRANSIENT ,
916+ } ) ;
917+ // Simulates what happens in cloneTransientInstance
918+ const prototypeOnlyInstance = {
919+ instance : Object . create ( { } ) ,
920+ isResolved : true , // This is set to true incorrectly in injector.ts
921+ isConstructorCalled : false , // But constructor was never called
922+ } ;
923+ wrapper . setInstanceByInquirerId (
924+ STATIC_CONTEXT ,
925+ 'inquirer' ,
926+ prototypeOnlyInstance ,
927+ ) ;
928+
929+ // Should not include this instance for lifecycle hooks
930+ expect ( wrapper . getStaticTransientInstances ( ) ) . to . be . eql ( [ ] ) ;
931+ } ) ;
932+
933+ it ( 'should include instances where constructor was actually invoked' , ( ) => {
934+ class TestService { }
935+ const wrapper = new InstanceWrapper ( {
936+ scope : Scope . TRANSIENT ,
937+ metatype : TestService ,
938+ } ) ;
939+ // Simulates what happens after instantiateClass
940+ const properInstance = {
941+ instance : new TestService ( ) ,
942+ isResolved : true ,
943+ isConstructorCalled : true ,
944+ } ;
945+ wrapper . setInstanceByInquirerId (
946+ STATIC_CONTEXT ,
947+ 'inquirer' ,
948+ properInstance ,
949+ ) ;
950+
951+ // Should include this instance for lifecycle hooks
952+ expect ( wrapper . getStaticTransientInstances ( ) ) . to . be . eql ( [
953+ properInstance ,
954+ ] ) ;
955+ } ) ;
956+ } ) ;
909957 } ) ;
910958 } ) ;
911959
0 commit comments