@@ -72,6 +72,7 @@ describe('state', function () {
7272 $rootScope . $on ( '$stateChangeStart' , eventLogger ) ;
7373 $rootScope . $on ( '$stateChangeSuccess' , eventLogger ) ;
7474 $rootScope . $on ( '$stateChangeError' , eventLogger ) ;
75+ $rootScope . $on ( '$stateNotFound' , eventLogger ) ;
7576 } ) ) ;
7677
7778
@@ -139,6 +140,109 @@ describe('state', function () {
139140 expect ( resolvedError ( promise ) ) . toBeTruthy ( ) ;
140141 } ) ) ;
141142
143+ it ( 'triggers $stateNotFound' , inject ( function ( $state , $q , $rootScope ) {
144+ initStateTo ( E , { i : 'iii' } ) ;
145+ var called ;
146+ $rootScope . $on ( '$stateNotFound' , function ( ev , redirect , from , fromParams ) {
147+ expect ( from ) . toBe ( E ) ;
148+ expect ( fromParams ) . toEqual ( { i : 'iii' } ) ;
149+ expect ( redirect . to ) . toEqual ( 'never_defined' ) ;
150+ expect ( redirect . toParams ) . toEqual ( { x : '1' , y : '2' } ) ;
151+
152+ expect ( $state . current ) . toBe ( from ) ; // $state not updated yet
153+ expect ( $state . params ) . toEqual ( fromParams ) ;
154+ called = true ;
155+ } ) ;
156+ var message ;
157+ try {
158+ $state . transitionTo ( 'never_defined' , { x : '1' , y : '2' } ) ;
159+ } catch ( err ) {
160+ message = err . message ;
161+ }
162+ $q . flush ( ) ;
163+ expect ( message ) . toEqual ( 'No such state \'never_defined\'' ) ;
164+ expect ( called ) . toBeTruthy ( ) ;
165+ expect ( $state . current ) . toBe ( E ) ;
166+ } ) ) ;
167+
168+ it ( 'can be cancelled by preventDefault() in $stateNotFound' , inject ( function ( $state , $q , $rootScope ) {
169+ initStateTo ( A ) ;
170+ var called ;
171+ $rootScope . $on ( '$stateNotFound' , function ( ev ) {
172+ ev . preventDefault ( ) ;
173+ called = true ;
174+ } ) ;
175+ var promise = $state . transitionTo ( 'never_defined' , { } ) ;
176+ $q . flush ( ) ;
177+ expect ( called ) . toBeTruthy ( ) ;
178+ expect ( $state . current ) . toBe ( A ) ;
179+ expect ( resolvedError ( promise ) ) . toBeTruthy ( ) ;
180+ } ) ) ;
181+
182+ it ( 'can be redirected in $stateNotFound' , inject ( function ( $state , $q , $rootScope ) {
183+ initStateTo ( A ) ;
184+ var called ;
185+ $rootScope . $on ( '$stateNotFound' , function ( ev , redirect ) {
186+ redirect . to = D ;
187+ redirect . toParams = { x : '1' , y : '2' } ;
188+ called = true ;
189+ } ) ;
190+ var promise = $state . transitionTo ( 'never_defined' , { z : 3 } ) ;
191+ $q . flush ( ) ;
192+ expect ( called ) . toBeTruthy ( ) ;
193+ expect ( $state . current ) . toBe ( D ) ;
194+ expect ( $state . params ) . toEqual ( { x : '1' , y : '2' } ) ;
195+ } ) ) ;
196+
197+ it ( 'can lazy-define a state in $stateNotFound' , inject ( function ( $state , $q , $rootScope ) {
198+ initStateTo ( DD , { x : 1 , y : 2 , z : 3 } ) ;
199+ var called ;
200+ $rootScope . $on ( '$stateNotFound' , function ( ev , redirect ) {
201+ stateProvider . state ( redirect . to , { parent : DD , params : [ 'x' , 'y' , 'z' , 'w' ] } ) ;
202+ called = true ;
203+ } ) ;
204+ var promise = $state . go ( 'DDD' , { w : 4 } ) ;
205+ $q . flush ( ) ;
206+ expect ( called ) . toBeTruthy ( ) ;
207+ expect ( $state . current . name ) . toEqual ( 'DDD' ) ;
208+ expect ( $state . params ) . toEqual ( { x : '1' , y : '2' , z : '3' , w : '4' } ) ;
209+ } ) ) ;
210+
211+ it ( 'can defer a state transition in $stateNotFound' , inject ( function ( $state , $q , $rootScope ) {
212+ initStateTo ( A ) ;
213+ var called ;
214+ var deferred = $q . defer ( ) ;
215+ $rootScope . $on ( '$stateNotFound' , function ( ev , redirect ) {
216+ ev . retry = deferred . promise ;
217+ called = true ;
218+ } ) ;
219+ var promise = $state . go ( 'AA' , { a : 1 } ) ;
220+ stateProvider . state ( 'AA' , { parent : A , params : [ 'a' ] } ) ;
221+ deferred . resolve ( ) ;
222+ $q . flush ( ) ;
223+ expect ( called ) . toBeTruthy ( ) ;
224+ expect ( $state . current . name ) . toEqual ( 'AA' ) ;
225+ expect ( $state . params ) . toEqual ( { a : '1' } ) ;
226+ } ) ) ;
227+
228+ it ( 'can defer and supersede a state transition in $stateNotFound' , inject ( function ( $state , $q , $rootScope ) {
229+ initStateTo ( A ) ;
230+ var called ;
231+ var deferred = $q . defer ( ) ;
232+ $rootScope . $on ( '$stateNotFound' , function ( ev , redirect ) {
233+ ev . retry = deferred . promise ;
234+ called = true ;
235+ } ) ;
236+ var promise = $state . go ( 'AA' , { a : 1 } ) ;
237+ $state . go ( B ) ;
238+ stateProvider . state ( 'AA' , { parent : A , params : [ 'a' ] } ) ;
239+ deferred . resolve ( ) ;
240+ $q . flush ( ) ;
241+ expect ( called ) . toBeTruthy ( ) ;
242+ expect ( $state . current ) . toEqual ( B ) ;
243+ expect ( $state . params ) . toEqual ( { } ) ;
244+ } ) ) ;
245+
142246 it ( 'triggers $stateChangeSuccess' , inject ( function ( $state , $q , $rootScope ) {
143247 initStateTo ( E , { i : 'iii' } ) ;
144248 var called ;
0 commit comments