firasKoubaa
firasKoubaa

Reputation: 6867

Angular Unit testing : Error: Cannot match any routes. URL Segment: 'home/advisor'

Am working on unit testing under my angular 4.0.0 app , some method in my real component is calling manual routing via :

method(){
....
    this.navigateTo('/home/advisor');
....
}

with navigateTo is a custom routing method calling this :

  public navigateTo(url: string) {
    this.oldUrl = this.router.url;
    this.router.navigate([url], { skipLocationChange: true });
  }

i have this routing file :

import ...     // Components and dependencies

const homeRoutes: Routes = [
  {
    path: 'home', component: HomeComponent,
    children: [
      {
        path: 'registration',
        component: RegistrationComponent,
        children: [
          {
            path: 'synthese',
            component: SyntheseComponent
          },
          {
            path: 'queue',
            component: QueueComponent,
            children: [
              {
                path: 'queue-modal',
                component: QueueModalComponent
              },
              {
                path: 'confirm',
                component: ConfirmComponent
              }
            ]
          }
        ]
      },
      {
        path: 'toolbox',
        component: ToolboxComponent
      },
      {
        path: 'appointment',
        component: AppointmentRegistrationComponent
      },
      {
        path: 'appointment-validation',
        component: AppointmentValidationComponent
      },
      {
        path: 'datepicker',
        component: DatePickerComponent
      },
      {
        path: 'validation/:defaultNumber',
        component: ValidationComponent,
        children: [
                   {
                     path: 'synthese',
                     component: SyntheseComponent
                   }
                   ]
      },
      {
        path: 'modalField',
        component: ModalFieldComponent
      },
      {
        path: 'search',
        component: SearchComponent
      },
      {
        path: 'advanced-search',
        component: AdvancedSearchComponent
      },
      {
        path: 'tools',
        component: ToolsComponent
      },
      {
        path: 'advisor',
        component: AdvisorComponent
      },
      {
        path: 'pilote',
        component: PilotComponent
      },
      {
          path: 'blank',
          component: BlankComponent
        },
      {
        path: 'view-360/:id',
        component: View360Component,
        children: [
          {
            path: 'client',
            component: ClientComponent
          },
          {
            path: 'tools',
            component: ToolsAdvisorComponent
          },
          {
            path: 'valid-close',
            component: ValidCloseComponent
          },
          {
            path: 'application',
            component: ApplicationView360Component
          }
        ],
        canActivate: [AuthGuardAdviser]
      },
      {
        path: 'view-360',
        component: View360Component,
        children: [
          {
            path: 'client',
            component: ClientComponent
          }
        ],
        canActivate: [AuthGuardAdviser]
      },
      {
        path: 'contract',
        component: ContractComponent
      },
      {
        path: 'queue-again',
        component: QueueAgainComponent
      },
      {
        path: 'stock',
        component: StockComponent,
        children: [
          {
            path: 'mobile',
            component: MobileComponent
          },
          {
            path: 'stock-level',
            component: StockLevelComponent
          }
        ]
      },
      {
        path: 'usefull-number',
        component: UsefullNumberComponent
      },
      {
        path: 'admin',
        loadChildren: 'app/home/admin/admin.module#AdminModule',
        //           component: AdminComponent,
        canActivate: [AuthGuardAdmin]
      },
      {
        path: 'rb',
        loadChildren: 'app/home/rb/rb.module#RbModule',
        //        component: RbComponent
        //        canActivate: [AuthGuardAdmin]
      },
      {
        path: 'tools-advisor',
        component: ToolsAdvisorComponent
      },
      {
        path: 'catalog/:haveClient',
        component: CatalogComponent
      },
      {
        path: 'application',
        component: ApplicationComponent
      },
    ]
  },

   ];

@NgModule({
  imports: [
    CommonModule,
    RouterModule.forChild(homeRoutes)
  ],
  exports: [
    RouterModule
  ],
  declarations: []
})
export class HomeRoutingModule { }

Strangely , even my application goes fonctionnally well ,but the test throws this error :

Failed: Uncaught (in promise): Error: Cannot match any routes. URL Segment: 'home/advisor' Error: Cannot match any routes. URL Segment: 'home/advisor'

it seems like i have some missing configuration .

Any ideas ??

Upvotes: 40

Views: 55233

Answers (5)

adashrod
adashrod

Reputation: 475

Since RouterTestingModule in the accepted answer has since been deprecated, one accepted substitute is to use provideRouter().

You can do it by creating some mock routes for your test:

import { provideRouter } from "@angular/router";

...
    beforeEach(async () => {
        await TestBed.configureTestingModule({
            imports: [MyComponent],
            providers: [provideRouter([{
                path: "path/to/navigate",
                redirectTo: "/"
            }])]
        }).compileComponents();
...

or import the actual routes:

import { routes } from "app/app.routes";

...
    beforeEach(async () => {
        await TestBed.configureTestingModule({
            imports: [NavigationBarComponent],
            providers: [provideRouter(routes)]
        }).compileComponents();
...

Upvotes: 0

user3391142
user3391142

Reputation: 1

In my console, I am getting this error while running my unit test case because of SubRoute. I am able to fix this issue by implementing the following way in my unit test case.

class RouterStub {
        url = '';
        navigate(commands: any[], extras?: any) { }
      }

beforeEach(async(() => {
    TestBed.configureTestingModule({
                    providers:[{ provide: Router, useClass: RouterStub }]
}).compileComponents();
}));

Upvotes: 0

monkey-0001
monkey-0001

Reputation: 492

I run into same issue. The solution of accepted answer doesn't work for me, because I accidentally added the HttpClientModule instead of HttpClientTestingModule to my Spec files. To avoid the "Can not match any routes" issue be sure you add RouterTestingModule and HttpClientTestingModule everywhere it is needed.

beforeEach(async(() => {
    TestBed.configureTestingModule({
        imports: [
            RouterTestingModule,
            HttpClientTestingModule,
        ],
        declarations: [
            AppComponent
        ],
    }).compileComponents();
}));

Upvotes: 4

danday74
danday74

Reputation: 57195

You need RouterTestingModule.withRoutes like so:

beforeEach(async(() => {
  TestBed.configureTestingModule({
    imports: [
      RouterTestingModule.withRoutes(
        [{path: 'yourpath', component: BlankComponent}]
      )
    ],
    declarations: [
      BlankComponent,
      YourComponentBeingTested
    ]
  })
  .compileComponents()
}))

Upvotes: 78

user4676340
user4676340

Reputation:

Following my comment :

When you want to unit test your router, you have to use the testing module, not the actual one.

Start with

import { RouterTestingModule } from '@angular/router/testing';

Then, in your Testbed

imports: [RouterTestingModule]

Now you should be able to unit test your component

EDIT

To make a spy on your routing, what you have to do is

spyOn(component.router, 'navigate').and.returnValue(true);

And you expect will look like

expect(component.router.navigate).toHaveBeenCalledWith('/home/advisor');

Upvotes: 31

Related Questions