From 1e1520644ba8afcf501da9e05fcea20044655a39 Mon Sep 17 00:00:00 2001 From: Mark Goho Date: Wed, 12 Jul 2023 14:57:38 +0000 Subject: [PATCH 1/4] use standalone for components --- apps/example-app/src/app/app.module.ts | 6 +- .../src/app/examples/00-single-component.ts | 1 + .../app/examples/01-nested-component.spec.ts | 6 +- .../src/app/examples/01-nested-component.ts | 10 ++- .../src/app/examples/02-input-output.spec.ts | 4 +- .../src/app/examples/02-input-output.ts | 1 + apps/example-app/src/app/examples/03-forms.ts | 5 +- .../examples/04-forms-with-material.spec.ts | 9 +-- .../app/examples/04-forms-with-material.ts | 6 +- .../src/app/examples/05-component-provider.ts | 1 + .../src/app/examples/06-with-ngrx-store.ts | 3 + .../app/examples/07-with-ngrx-mock-store.ts | 3 + .../src/app/examples/08-directive.spec.ts | 6 +- .../src/app/examples/08-directive.ts | 1 + .../src/app/examples/09-router.spec.ts | 3 - .../example-app/src/app/examples/09-router.ts | 16 ++-- .../examples/10-inject-token-dependency.ts | 1 + .../src/app/examples/11-ng-content.spec.ts | 4 +- .../src/app/examples/11-ng-content.ts | 1 + .../src/app/examples/12-service-component.ts | 3 + .../examples/13-scrolling.component.spec.ts | 5 +- .../app/examples/13-scrolling.component.ts | 3 + .../src/app/examples/14-async-component.ts | 3 + .../app/examples/15-dialog.component.spec.ts | 13 +--- .../src/app/examples/15-dialog.component.ts | 13 ++-- .../app/examples/16-input-getter-setter.ts | 1 + ...-component-with-attribute-selector.spec.ts | 11 ++- .../17-component-with-attribute-selector.ts | 5 +- .../src/app/examples/18-html-as-input.spec.ts | 7 +- .../app/examples/19-standalone-component.ts | 2 +- .../src/app/examples/20-test-harness.spec.ts | 8 +- apps/example-app/src/app/issues/.gitkeep | 0 .../src/app/issues/issue-106.spec.ts | 46 ----------- .../src/app/issues/issue-254.spec.ts | 78 ------------------- .../src/app/issues/issue-304.spec.ts | 71 ----------------- .../src/app/issues/issue-316.spec.ts | 78 ------------------- .../src/app/issues/issue-358.spec.ts | 40 ---------- 37 files changed, 91 insertions(+), 383 deletions(-) create mode 100644 apps/example-app/src/app/issues/.gitkeep delete mode 100644 apps/example-app/src/app/issues/issue-106.spec.ts delete mode 100644 apps/example-app/src/app/issues/issue-254.spec.ts delete mode 100644 apps/example-app/src/app/issues/issue-304.spec.ts delete mode 100644 apps/example-app/src/app/issues/issue-316.spec.ts delete mode 100644 apps/example-app/src/app/issues/issue-358.spec.ts diff --git a/apps/example-app/src/app/app.module.ts b/apps/example-app/src/app/app.module.ts index cb95434f..3ac3c4ca 100644 --- a/apps/example-app/src/app/app.module.ts +++ b/apps/example-app/src/app/app.module.ts @@ -28,8 +28,8 @@ function reducerItems() { } @NgModule({ - declarations: [ - AppComponent, + declarations: [AppComponent], + imports: [ SingleComponent, NestedButtonComponent, NestedValueComponent, @@ -43,8 +43,6 @@ function reducerItems() { RootComponent, DetailComponent, HiddenDetailComponent, - ], - imports: [ BrowserModule, ReactiveFormsModule, BrowserAnimationsModule, diff --git a/apps/example-app/src/app/examples/00-single-component.ts b/apps/example-app/src/app/examples/00-single-component.ts index 25001036..7c132c2f 100644 --- a/apps/example-app/src/app/examples/00-single-component.ts +++ b/apps/example-app/src/app/examples/00-single-component.ts @@ -2,6 +2,7 @@ import { Component } from '@angular/core'; @Component({ selector: 'app-fixture', + standalone: true, template: ` {{ value }} diff --git a/apps/example-app/src/app/examples/01-nested-component.spec.ts b/apps/example-app/src/app/examples/01-nested-component.spec.ts index 751d1c47..dfa3fe3f 100644 --- a/apps/example-app/src/app/examples/01-nested-component.spec.ts +++ b/apps/example-app/src/app/examples/01-nested-component.spec.ts @@ -1,13 +1,11 @@ import { render, screen } from '@testing-library/angular'; import userEvent from '@testing-library/user-event'; -import { NestedButtonComponent, NestedValueComponent, NestedContainerComponent } from './01-nested-component'; +import { NestedContainerComponent } from './01-nested-component'; test('renders the current value and can increment and decrement', async () => { const user = userEvent.setup(); - await render(NestedContainerComponent, { - declarations: [NestedButtonComponent, NestedValueComponent], - }); + await render(NestedContainerComponent); const incrementControl = screen.getByRole('button', { name: /increment/i }); const decrementControl = screen.getByRole('button', { name: /decrement/i }); diff --git a/apps/example-app/src/app/examples/01-nested-component.ts b/apps/example-app/src/app/examples/01-nested-component.ts index 51087b44..645ce966 100644 --- a/apps/example-app/src/app/examples/01-nested-component.ts +++ b/apps/example-app/src/app/examples/01-nested-component.ts @@ -1,6 +1,7 @@ import { Component, Input, Output, EventEmitter } from '@angular/core'; @Component({ + standalone: true, selector: 'app-button', template: ' ', }) @@ -10,6 +11,7 @@ export class NestedButtonComponent { } @Component({ + standalone: true, selector: 'app-value', template: ' {{ value }} ', }) @@ -18,12 +20,14 @@ export class NestedValueComponent { } @Component({ + standalone: true, selector: 'app-fixture', template: ` - - - + + + `, + imports: [NestedButtonComponent, NestedValueComponent], }) export class NestedContainerComponent { value = 0; diff --git a/apps/example-app/src/app/examples/02-input-output.spec.ts b/apps/example-app/src/app/examples/02-input-output.spec.ts index 93edee4d..c193d3e5 100644 --- a/apps/example-app/src/app/examples/02-input-output.spec.ts +++ b/apps/example-app/src/app/examples/02-input-output.spec.ts @@ -38,8 +38,8 @@ test('is possible to set input and listen for output with the template syntax', const user = userEvent.setup(); const sendSpy = jest.fn(); - await render('', { - declarations: [InputOutputComponent], + await render('', { + imports: [InputOutputComponent], componentProperties: { sendValue: sendSpy, }, diff --git a/apps/example-app/src/app/examples/02-input-output.ts b/apps/example-app/src/app/examples/02-input-output.ts index a7ef9ce4..5bf70abb 100644 --- a/apps/example-app/src/app/examples/02-input-output.ts +++ b/apps/example-app/src/app/examples/02-input-output.ts @@ -1,6 +1,7 @@ import { Component, EventEmitter, Input, Output } from '@angular/core'; @Component({ + standalone: true, selector: 'app-fixture', template: ` diff --git a/apps/example-app/src/app/examples/03-forms.ts b/apps/example-app/src/app/examples/03-forms.ts index cbf0a316..49756dca 100644 --- a/apps/example-app/src/app/examples/03-forms.ts +++ b/apps/example-app/src/app/examples/03-forms.ts @@ -1,8 +1,11 @@ +import { NgForOf, NgIf } from '@angular/common'; import { Component } from '@angular/core'; -import { FormBuilder, Validators } from '@angular/forms'; +import { FormBuilder, ReactiveFormsModule, Validators } from '@angular/forms'; @Component({ + standalone: true, selector: 'app-fixture', + imports: [ReactiveFormsModule, NgForOf, NgIf], template: `
diff --git a/apps/example-app/src/app/examples/04-forms-with-material.spec.ts b/apps/example-app/src/app/examples/04-forms-with-material.spec.ts index 24b9cdc9..638d76ff 100644 --- a/apps/example-app/src/app/examples/04-forms-with-material.spec.ts +++ b/apps/example-app/src/app/examples/04-forms-with-material.spec.ts @@ -1,15 +1,12 @@ import { render, screen } from '@testing-library/angular'; import userEvent from '@testing-library/user-event'; -import { MaterialModule } from '../material.module'; import { MaterialFormsComponent } from './04-forms-with-material'; test('is possible to fill in a form and verify error messages (with the help of jest-dom https://testing-library.com/docs/ecosystem-jest-dom)', async () => { const user = userEvent.setup(); - const { fixture } = await render(MaterialFormsComponent, { - imports: [MaterialModule], - }); + const { fixture } = await render(MaterialFormsComponent); const nameControl = screen.getByLabelText(/name/i); const scoreControl = screen.getByRole('spinbutton', { name: /score/i }); @@ -69,9 +66,7 @@ test('is possible to fill in a form and verify error messages (with the help of test('set and show pre-set form values', async () => { const user = userEvent.setup(); - const { fixture, detectChanges } = await render(MaterialFormsComponent, { - imports: [MaterialModule], - }); + const { fixture, detectChanges } = await render(MaterialFormsComponent); fixture.componentInstance.form.setValue({ name: 'Max', diff --git a/apps/example-app/src/app/examples/04-forms-with-material.ts b/apps/example-app/src/app/examples/04-forms-with-material.ts index 852a345b..5e6ed8e9 100644 --- a/apps/example-app/src/app/examples/04-forms-with-material.ts +++ b/apps/example-app/src/app/examples/04-forms-with-material.ts @@ -1,7 +1,11 @@ import { Component } from '@angular/core'; -import { FormBuilder, Validators } from '@angular/forms'; +import { FormBuilder, ReactiveFormsModule, Validators } from '@angular/forms'; +import { MaterialModule } from '../material.module'; +import { NgForOf, NgIf } from '@angular/common'; @Component({ + standalone: true, + imports: [MaterialModule, ReactiveFormsModule, NgForOf, NgIf], selector: 'app-fixture', template: ` diff --git a/apps/example-app/src/app/examples/05-component-provider.ts b/apps/example-app/src/app/examples/05-component-provider.ts index 4d933dbb..1f345b94 100644 --- a/apps/example-app/src/app/examples/05-component-provider.ts +++ b/apps/example-app/src/app/examples/05-component-provider.ts @@ -20,6 +20,7 @@ export class CounterService { } @Component({ + standalone: true, selector: 'app-fixture', template: ` diff --git a/apps/example-app/src/app/examples/06-with-ngrx-store.ts b/apps/example-app/src/app/examples/06-with-ngrx-store.ts index 470f52d9..b1db1d46 100644 --- a/apps/example-app/src/app/examples/06-with-ngrx-store.ts +++ b/apps/example-app/src/app/examples/06-with-ngrx-store.ts @@ -1,3 +1,4 @@ +import { AsyncPipe } from '@angular/common'; import { Component } from '@angular/core'; import { createSelector, Store, createAction, createReducer, on, select } from '@ngrx/store'; @@ -15,6 +16,8 @@ const selectValue = createSelector( ); @Component({ + standalone: true, + imports: [AsyncPipe], selector: 'app-fixture', template: ` diff --git a/apps/example-app/src/app/examples/07-with-ngrx-mock-store.ts b/apps/example-app/src/app/examples/07-with-ngrx-mock-store.ts index 249caf21..7754bf1c 100644 --- a/apps/example-app/src/app/examples/07-with-ngrx-mock-store.ts +++ b/apps/example-app/src/app/examples/07-with-ngrx-mock-store.ts @@ -1,3 +1,4 @@ +import { AsyncPipe, NgForOf } from '@angular/common'; import { Component } from '@angular/core'; import { createSelector, Store, select } from '@ngrx/store'; @@ -7,6 +8,8 @@ export const selectItems = createSelector( ); @Component({ + standalone: true, + imports: [AsyncPipe, NgForOf], selector: 'app-fixture', template: `
    diff --git a/apps/example-app/src/app/examples/08-directive.spec.ts b/apps/example-app/src/app/examples/08-directive.spec.ts index b81dcff0..5ba450bd 100644 --- a/apps/example-app/src/app/examples/08-directive.spec.ts +++ b/apps/example-app/src/app/examples/08-directive.spec.ts @@ -7,7 +7,7 @@ test('it is possible to test directives', async () => { const user = userEvent.setup(); await render('
    ', { - declarations: [SpoilerDirective], + imports: [SpoilerDirective], }); const directive = screen.getByTestId('dir'); @@ -30,7 +30,7 @@ test('it is possible to test directives with props', async () => { const visible = 'There is nothing to see here ...'; await render('
    ', { - declarations: [SpoilerDirective], + imports: [SpoilerDirective], componentProperties: { hidden, visible, @@ -55,7 +55,7 @@ test('it is possible to test directives with props in template', async () => { const visible = 'There is nothing to see here ...'; await render(``, { - declarations: [SpoilerDirective], + imports: [SpoilerDirective], }); expect(screen.queryByText(visible)).not.toBeInTheDocument(); diff --git a/apps/example-app/src/app/examples/08-directive.ts b/apps/example-app/src/app/examples/08-directive.ts index 12a029cf..40548b1e 100644 --- a/apps/example-app/src/app/examples/08-directive.ts +++ b/apps/example-app/src/app/examples/08-directive.ts @@ -1,6 +1,7 @@ import { Directive, HostListener, ElementRef, Input, OnInit } from '@angular/core'; @Directive({ + standalone: true, selector: '[appSpoiler]', }) export class SpoilerDirective implements OnInit { diff --git a/apps/example-app/src/app/examples/09-router.spec.ts b/apps/example-app/src/app/examples/09-router.spec.ts index 9483695d..f1da85d2 100644 --- a/apps/example-app/src/app/examples/09-router.spec.ts +++ b/apps/example-app/src/app/examples/09-router.spec.ts @@ -6,7 +6,6 @@ import { DetailComponent, RootComponent, HiddenDetailComponent } from './09-rout test('it can navigate to routes', async () => { const user = userEvent.setup(); await render(RootComponent, { - declarations: [DetailComponent, HiddenDetailComponent], routes: [ { path: '', @@ -45,7 +44,6 @@ test('it can navigate to routes', async () => { test('it can navigate to routes - workaround', async () => { const { navigate } = await render(RootComponent, { - declarations: [DetailComponent, HiddenDetailComponent], routes: [ { path: '', @@ -84,7 +82,6 @@ test('it can navigate to routes - workaround', async () => { test('it can navigate to routes with a base path', async () => { const basePath = 'base'; const { navigate } = await render(RootComponent, { - declarations: [DetailComponent, HiddenDetailComponent], routes: [ { path: basePath, diff --git a/apps/example-app/src/app/examples/09-router.ts b/apps/example-app/src/app/examples/09-router.ts index 6ea0df73..888d7fdf 100644 --- a/apps/example-app/src/app/examples/09-router.ts +++ b/apps/example-app/src/app/examples/09-router.ts @@ -1,28 +1,33 @@ +import { AsyncPipe } from '@angular/common'; import { Component } from '@angular/core'; -import { ActivatedRoute } from '@angular/router'; +import { ActivatedRoute, RouterLink, RouterOutlet } from '@angular/router'; import { map } from 'rxjs/operators'; @Component({ + standalone: true, + imports: [RouterLink, RouterOutlet], selector: 'app-main', template: ` - Load one | Load two | - Load three | + Load one | Load two | + Load three |
    - + `, }) export class RootComponent {} @Component({ + standalone: true, + imports: [RouterLink, AsyncPipe], selector: 'app-detail', template: `

    Detail {{ id | async }}

    {{ text | async }} {{ subtext | async }}

    - Back to parent + Back to parent hidden x `, }) @@ -34,6 +39,7 @@ export class DetailComponent { } @Component({ + standalone: true, selector: 'app-detail-hidden', template: ' You found the treasure! ', }) diff --git a/apps/example-app/src/app/examples/10-inject-token-dependency.ts b/apps/example-app/src/app/examples/10-inject-token-dependency.ts index 8cc843e5..6a17d538 100644 --- a/apps/example-app/src/app/examples/10-inject-token-dependency.ts +++ b/apps/example-app/src/app/examples/10-inject-token-dependency.ts @@ -3,6 +3,7 @@ import { Component, InjectionToken, Inject } from '@angular/core'; export const DATA = new InjectionToken<{ text: string }>('Components Data'); @Component({ + standalone: true, selector: 'app-fixture', template: ' {{ data.text }} ', }) diff --git a/apps/example-app/src/app/examples/11-ng-content.spec.ts b/apps/example-app/src/app/examples/11-ng-content.spec.ts index f061e862..2f910252 100644 --- a/apps/example-app/src/app/examples/11-ng-content.spec.ts +++ b/apps/example-app/src/app/examples/11-ng-content.spec.ts @@ -4,9 +4,9 @@ import { CellComponent } from './11-ng-content'; test('it is possible to test ng-content without selector', async () => { const projection = 'it should be showed into a p element!'; - + await render(`${projection}`, { - declarations: [CellComponent] + imports: [CellComponent], }); expect(screen.getByText(projection)).toBeInTheDocument(); diff --git a/apps/example-app/src/app/examples/11-ng-content.ts b/apps/example-app/src/app/examples/11-ng-content.ts index 47845919..d4446839 100644 --- a/apps/example-app/src/app/examples/11-ng-content.ts +++ b/apps/example-app/src/app/examples/11-ng-content.ts @@ -1,6 +1,7 @@ import { Component, ChangeDetectionStrategy } from '@angular/core'; @Component({ + standalone: true, selector: 'app-fixture', template: `

    diff --git a/apps/example-app/src/app/examples/12-service-component.ts b/apps/example-app/src/app/examples/12-service-component.ts index d272e270..2aed1657 100644 --- a/apps/example-app/src/app/examples/12-service-component.ts +++ b/apps/example-app/src/app/examples/12-service-component.ts @@ -1,3 +1,4 @@ +import { AsyncPipe, NgForOf } from '@angular/common'; import { Component, Injectable } from '@angular/core'; import { Observable, of } from 'rxjs'; @@ -16,6 +17,8 @@ export class CustomersService { } @Component({ + standalone: true, + imports: [AsyncPipe, NgForOf], selector: 'app-fixture', template: `

      diff --git a/apps/example-app/src/app/examples/13-scrolling.component.spec.ts b/apps/example-app/src/app/examples/13-scrolling.component.spec.ts index 4abaed08..cb1ad11b 100644 --- a/apps/example-app/src/app/examples/13-scrolling.component.spec.ts +++ b/apps/example-app/src/app/examples/13-scrolling.component.spec.ts @@ -1,12 +1,9 @@ import { render, screen, waitForElementToBeRemoved } from '@testing-library/angular'; import { CdkVirtualScrollOverviewExampleComponent } from './13-scrolling.component'; -import { ScrollingModule } from '@angular/cdk/scrolling'; test('should scroll to load more items', async () => { - await render(CdkVirtualScrollOverviewExampleComponent, { - imports: [ScrollingModule], - }); + await render(CdkVirtualScrollOverviewExampleComponent); const item0 = await screen.findByText(/Item #0/i); expect(item0).toBeVisible(); diff --git a/apps/example-app/src/app/examples/13-scrolling.component.ts b/apps/example-app/src/app/examples/13-scrolling.component.ts index 0080c4e8..7d7b2e7c 100644 --- a/apps/example-app/src/app/examples/13-scrolling.component.ts +++ b/apps/example-app/src/app/examples/13-scrolling.component.ts @@ -1,6 +1,9 @@ import { ChangeDetectionStrategy, Component } from '@angular/core'; +import { ScrollingModule } from '@angular/cdk/scrolling'; @Component({ + standalone: true, + imports: [ScrollingModule], selector: 'app-cdk-virtual-scroll-overview-example', template: ` diff --git a/apps/example-app/src/app/examples/14-async-component.ts b/apps/example-app/src/app/examples/14-async-component.ts index f8521539..f87732ad 100644 --- a/apps/example-app/src/app/examples/14-async-component.ts +++ b/apps/example-app/src/app/examples/14-async-component.ts @@ -1,8 +1,11 @@ +import { AsyncPipe, NgIf } from '@angular/common'; import { Component, OnDestroy } from '@angular/core'; import { Subject } from 'rxjs'; import { delay, filter, mapTo } from 'rxjs/operators'; @Component({ + standalone: true, + imports: [AsyncPipe, NgIf], selector: 'app-fixture', template: ` diff --git a/apps/example-app/src/app/examples/15-dialog.component.spec.ts b/apps/example-app/src/app/examples/15-dialog.component.spec.ts index 1177f293..97ad829a 100644 --- a/apps/example-app/src/app/examples/15-dialog.component.spec.ts +++ b/apps/example-app/src/app/examples/15-dialog.component.spec.ts @@ -1,15 +1,14 @@ -import { MatDialogModule, MatDialogRef } from '@angular/material/dialog'; +import { MatDialogRef } from '@angular/material/dialog'; import { render, screen } from '@testing-library/angular'; import userEvent from '@testing-library/user-event'; -import { DialogComponent, DialogContentComponent, DialogContentComponentModule } from './15-dialog.component'; +import { DialogComponent, DialogContentComponent } from './15-dialog.component'; test('dialog closes', async () => { const user = userEvent.setup(); const closeFn = jest.fn(); await render(DialogContentComponent, { - imports: [MatDialogModule], providers: [ { provide: MatDialogRef, @@ -29,9 +28,7 @@ test('dialog closes', async () => { test('closes the dialog via the backdrop', async () => { const user = userEvent.setup(); - await render(DialogComponent, { - imports: [MatDialogModule, DialogContentComponentModule], - }); + await render(DialogComponent); const openDialogButton = await screen.findByRole('button', { name: /open dialog/i }); await user.click(openDialogButton); @@ -53,9 +50,7 @@ test('closes the dialog via the backdrop', async () => { test('opens and closes the dialog with buttons', async () => { const user = userEvent.setup(); - await render(DialogComponent, { - imports: [MatDialogModule, DialogContentComponentModule], - }); + await render(DialogComponent); const openDialogButton = await screen.findByRole('button', { name: /open dialog/i }); await user.click(openDialogButton); diff --git a/apps/example-app/src/app/examples/15-dialog.component.ts b/apps/example-app/src/app/examples/15-dialog.component.ts index af5d8d89..f6c89703 100644 --- a/apps/example-app/src/app/examples/15-dialog.component.ts +++ b/apps/example-app/src/app/examples/15-dialog.component.ts @@ -1,7 +1,9 @@ -import { Component, NgModule } from '@angular/core'; -import { MatDialog, MatDialogRef } from '@angular/material/dialog'; +import { Component } from '@angular/core'; +import { MatDialog, MatDialogModule, MatDialogRef } from '@angular/material/dialog'; @Component({ + standalone: true, + imports: [MatDialogModule], selector: 'app-dialog-overview-example', template: '', }) @@ -14,6 +16,8 @@ export class DialogComponent { } @Component({ + standalone: true, + imports: [MatDialogModule], selector: 'app-dialog-overview-example-dialog', template: `

      Dialog Title

      @@ -31,8 +35,3 @@ export class DialogContentComponent { this.dialogRef.close(); } } - -@NgModule({ - declarations: [DialogContentComponent], -}) -export class DialogContentComponentModule {} diff --git a/apps/example-app/src/app/examples/16-input-getter-setter.ts b/apps/example-app/src/app/examples/16-input-getter-setter.ts index 22d9641a..a9097a48 100644 --- a/apps/example-app/src/app/examples/16-input-getter-setter.ts +++ b/apps/example-app/src/app/examples/16-input-getter-setter.ts @@ -1,6 +1,7 @@ import { Component, Input } from '@angular/core'; @Component({ + standalone: true, selector: 'app-fixture', template: ` {{ derivedValue }} diff --git a/apps/example-app/src/app/examples/17-component-with-attribute-selector.spec.ts b/apps/example-app/src/app/examples/17-component-with-attribute-selector.spec.ts index cd6334d1..ba69f70a 100644 --- a/apps/example-app/src/app/examples/17-component-with-attribute-selector.spec.ts +++ b/apps/example-app/src/app/examples/17-component-with-attribute-selector.spec.ts @@ -1,12 +1,15 @@ import { render, screen } from '@testing-library/angular'; -import {ComponentWithAttributeSelectorComponent} from './17-component-with-attribute-selector'; +import { ComponentWithAttributeSelectorComponent } from './17-component-with-attribute-selector'; // Note: At this stage it is not possible to use the render(ComponentWithAttributeSelectorComponent, {...}) syntax // for components with attribute selectors! test('is possible to set input of component with attribute selector through template', async () => { - await render(``, { - declarations: [ComponentWithAttributeSelectorComponent] - }); + await render( + ``, + { + imports: [ComponentWithAttributeSelectorComponent], + }, + ); const valueControl = screen.getByTestId('value'); diff --git a/apps/example-app/src/app/examples/17-component-with-attribute-selector.ts b/apps/example-app/src/app/examples/17-component-with-attribute-selector.ts index 2d0b904b..ac2a25d3 100644 --- a/apps/example-app/src/app/examples/17-component-with-attribute-selector.ts +++ b/apps/example-app/src/app/examples/17-component-with-attribute-selector.ts @@ -1,10 +1,9 @@ import { Component, Input } from '@angular/core'; @Component({ + standalone: true, selector: 'app-fixture-component-with-attribute-selector[value]', - template: ` - {{ value }} - `, + template: ` {{ value }} `, }) export class ComponentWithAttributeSelectorComponent { @Input() value!: number; diff --git a/apps/example-app/src/app/examples/18-html-as-input.spec.ts b/apps/example-app/src/app/examples/18-html-as-input.spec.ts index 5a56b412..068a8c09 100644 --- a/apps/example-app/src/app/examples/18-html-as-input.spec.ts +++ b/apps/example-app/src/app/examples/18-html-as-input.spec.ts @@ -2,6 +2,7 @@ import { render, screen } from '@testing-library/angular'; import { Pipe, PipeTransform } from '@angular/core'; @Pipe({ + standalone: true, name: 'stripHTML', }) class StripHTMLPipe implements PipeTransform { @@ -19,18 +20,16 @@ test('passes HTML as component properties', async () => { componentProperties: { stringWithHtml: STRING_WITH_HTML, }, - declarations: [StripHTMLPipe], + imports: [StripHTMLPipe], }); expect(screen.getByText('Some database field with stripped HTML')).toBeInTheDocument(); }); - test('throws when passed HTML is passed in directly', async () => { await expect(() => render(`

      {{ '${STRING_WITH_HTML}' | stripHTML }}

      `, { - declarations: [StripHTMLPipe], + imports: [StripHTMLPipe], }), ).rejects.toThrow(); }); - diff --git a/apps/example-app/src/app/examples/19-standalone-component.ts b/apps/example-app/src/app/examples/19-standalone-component.ts index 481f0562..efcf0884 100644 --- a/apps/example-app/src/app/examples/19-standalone-component.ts +++ b/apps/example-app/src/app/examples/19-standalone-component.ts @@ -11,7 +11,7 @@ export class StandaloneComponent {} selector: 'app-standalone-with-child', template: `

      Hi {{ name }}

      This has a child

      - `, + `, standalone: true, imports: [StandaloneComponent], }) diff --git a/apps/example-app/src/app/examples/20-test-harness.spec.ts b/apps/example-app/src/app/examples/20-test-harness.spec.ts index 5023f662..50e99bcd 100644 --- a/apps/example-app/src/app/examples/20-test-harness.spec.ts +++ b/apps/example-app/src/app/examples/20-test-harness.spec.ts @@ -2,13 +2,13 @@ import { TestbedHarnessEnvironment } from '@angular/cdk/testing/testbed'; import { MatButtonHarness } from '@angular/material/button/testing'; import { MatSnackBarHarness } from '@angular/material/snack-bar/testing'; import { render, screen } from '@testing-library/angular'; -import user from '@testing-library/user-event'; +import userEvent from '@testing-library/user-event'; import { SnackBarComponent } from './20-test-harness'; // eslint-disable-next-line jest/no-disabled-tests test.skip('can be used with TestHarness', async () => { - const view = await render(``, { + const view = await render(``, { imports: [SnackBarComponent], }); const loader = TestbedHarnessEnvironment.documentRootLoader(view.fixture); @@ -23,10 +23,12 @@ test.skip('can be used with TestHarness', async () => { // eslint-disable-next-line jest/no-disabled-tests test.skip('can be used in combination with TestHarness', async () => { + const user = userEvent.setup(); + const view = await render(SnackBarComponent); const loader = TestbedHarnessEnvironment.documentRootLoader(view.fixture); - user.click(screen.getByRole('button')); + await user.click(screen.getByRole('button')); const snackbarHarness = await loader.getHarness(MatSnackBarHarness); expect(await snackbarHarness.getMessage()).toMatch(/Pizza Party!!!/i); diff --git a/apps/example-app/src/app/issues/.gitkeep b/apps/example-app/src/app/issues/.gitkeep new file mode 100644 index 00000000..e69de29b diff --git a/apps/example-app/src/app/issues/issue-106.spec.ts b/apps/example-app/src/app/issues/issue-106.spec.ts deleted file mode 100644 index 56097a83..00000000 --- a/apps/example-app/src/app/issues/issue-106.spec.ts +++ /dev/null @@ -1,46 +0,0 @@ -import { Component } from '@angular/core'; -import { BehaviorSubject } from 'rxjs'; -import { render, screen, fireEvent } from '@testing-library/angular'; -import { waitFor } from '@testing-library/dom'; - -@Component({ - template: ` -
      Here I am
      `, -}) -class TestSelectComponent { - showSubj = new BehaviorSubject(false); - show$ = this.showSubj.asObservable(); - - toggleShow() { - this.showSubj.next(true); - } -} - -test('https://github.com/testing-library/angular-testing-library/issues/106', async () => { - await render(TestSelectComponent); - const toggle = screen.getByTestId('toggle'); - const hiddenText = screen.queryByTestId('getme'); - - expect(hiddenText).not.toBeInTheDocument(); - fireEvent.click(toggle); - - // fails - // await waitFor(() => expect(hiddenText).not.toBeNull()); - - // succeeds - /// Next line is disabled, because we wish to test the behavior of the library and test the bug/issue #106 - /// @see https://github.com/testing-library/angular-testing-library/pull/277/files#r779743116 - // eslint-disable-next-line testing-library/prefer-presence-queries, testing-library/prefer-find-by - await waitFor(() => expect(screen.queryByTestId('getme')).toBeInTheDocument()); -}); - -test('better https://github.com/testing-library/angular-testing-library/issues/106', async () => { - await render(TestSelectComponent); - const toggle = screen.getByTestId('toggle'); - const hiddenText = screen.queryByTestId('getme'); - - expect(hiddenText).not.toBeInTheDocument(); - fireEvent.click(toggle); - - expect(screen.getByTestId('getme')).toBeInTheDocument(); -}); diff --git a/apps/example-app/src/app/issues/issue-254.spec.ts b/apps/example-app/src/app/issues/issue-254.spec.ts deleted file mode 100644 index 917f35de..00000000 --- a/apps/example-app/src/app/issues/issue-254.spec.ts +++ /dev/null @@ -1,78 +0,0 @@ -import { Component, Inject, OnInit } from '@angular/core'; -import { render, screen } from '@testing-library/angular'; -import { createMock } from '@testing-library/angular/jest-utils'; - -interface Division { - jobType?: string; - jobBullets?: string[]; - description?: string; -} - -@Inject({ - providedIn: 'root', -}) -class JobsService { - divisions(): Promise { - throw new Error('Method not implemented.'); - } -} - -@Component({ - selector: 'app-home-career-oportunities', - template: `
        -
      • - {{ bullet }} -
      • -
      `, -}) -class CareerOportunitiesComponent implements OnInit { - dedicated: Division | undefined; - intermodal: Division | undefined; - noCdl: Division | undefined; - otr: Division | undefined; - - constructor(private jobsService: JobsService) {} - - ngOnInit(): void { - this.jobsService.divisions().then((apiDivisions) => { - this.dedicated = apiDivisions.find((c) => c.jobType === 'DEDICATED'); - this.intermodal = apiDivisions.find((c) => c.jobType === 'INTERMODAL'); - this.noCdl = apiDivisions.find((c) => c.jobType === 'NO_CDL'); - this.otr = apiDivisions.find((c) => c.jobType === 'OVER_THE_ROAD'); - }); - } -} - -test('Render Component', async () => { - const divisions2: Division[] = [ - { - jobType: 'INTERMODAL', - jobBullets: ['Local Routes', 'Flexible Schedules', 'Competitive Pay'], - description: '', - }, - { jobType: 'NO_CDL', jobBullets: ['We Train', 'We Hire', 'We Pay'], description: '' }, - { - jobType: 'OVER_THE_ROAD', - jobBullets: ['Great Miles', 'Competitive Pay', 'Explore the Country'], - description: '', - }, - { - jobType: 'DEDICATED', - jobBullets: ['Regular Routes', 'Consistent Miles', 'Great Pay'], - description: '', - }, - ]; - const jobService = createMock(JobsService); - jobService.divisions = jest.fn(() => Promise.resolve(divisions2)); - - await render(CareerOportunitiesComponent, { - componentProviders: [ - { - provide: JobsService, - useValue: jobService, - }, - ], - }); - const listItemControl = await screen.findAllByRole('listitem'); - expect(listItemControl).toHaveLength(3); -}); diff --git a/apps/example-app/src/app/issues/issue-304.spec.ts b/apps/example-app/src/app/issues/issue-304.spec.ts deleted file mode 100644 index 25d3b6f3..00000000 --- a/apps/example-app/src/app/issues/issue-304.spec.ts +++ /dev/null @@ -1,71 +0,0 @@ -import { Component, EventEmitter, Input, Output } from '@angular/core'; -import { Location } from '@angular/common'; -import { render, screen } from '@testing-library/angular'; -import userEvent from '@testing-library/user-event'; -import { TestBed } from '@angular/core/testing'; - -// with goBackSpy, the implementation of goBack won't be invoked (because it's using the spy) -test('should call a goBack when user click in the button', async () => { - const user = userEvent.setup(); - - const goBackSpy = jest.fn(); - await render(HeaderBackButtonComponent, { - declarations: [IconButtonComponent], - componentProperties: { - goBack: goBackSpy, - }, - }); - - const button = screen.getByLabelText(/icon button/i); - await user.click(button); - expect(goBackSpy).toHaveBeenCalled(); -}); - -// don't spy on goBack, this way the implementation of goBack is invoked, and you can test if location.back() is called -test('should call a Location.back when user click in the button', async () => { - const user = userEvent.setup(); - - await render(HeaderBackButtonComponent, { - declarations: [IconButtonComponent], - }); - - const location = TestBed.inject(Location); - jest.spyOn(location, 'back'); - - const button = screen.getByLabelText(/icon button/i); - await user.click(button); - expect(location.back).toHaveBeenCalled(); -}); - -@Component({ - selector: 'app-cebs-header-back-button', - template: ` -
      - -
      - `, -}) -class HeaderBackButtonComponent { - constructor(private location: Location) {} - - goBack(): void { - this.location.back(); - } -} - -@Component({ - selector: 'app-cebs-icon-button', - template: ` - - `, -}) -class IconButtonComponent { - @Output() clickEvent = new EventEmitter(); - @Input() icon!: string; - - onClick(): void { - this.clickEvent.emit(); - } -} diff --git a/apps/example-app/src/app/issues/issue-316.spec.ts b/apps/example-app/src/app/issues/issue-316.spec.ts deleted file mode 100644 index 4dd38815..00000000 --- a/apps/example-app/src/app/issues/issue-316.spec.ts +++ /dev/null @@ -1,78 +0,0 @@ -import { Component, Input } from '@angular/core' -import { render, screen } from '@testing-library/angular' - -describe('TagComponent', () => { - it('create a tag default primary', async () => { - await render(`primary`, { - declarations: [TagComponent], - }) - - expect(screen.getByText(/primary/i)).toBeInTheDocument() - expect(screen.getByRole('tag')).toHaveClass('hc-tag-primary') - }) -}) - - -@Component({ - selector: 'hc-tag', - template: ` - - - - `, - styles: [ - ` - .hc-tag { - display: inline-flex; - align-items: center; - justify-content: center; - color: var(--neutral-white); - padding: 4px 10px; - border-radius: 6px; - } - - .hc-tag-primary { - background-color: var(--primary-default); - } - - .hc-tag-success { - background-color: var(--green-default); - } - - .hc-tag-info { - background-color: var(--primary-default); - } - - .hc-tag-warning { - background-color: var(--yellow-default); - } - - .hc-tag-danger { - background-color: var(--red-default); - } - - .hc-tag-rounded { - border-radius: 10rem; - } - `, - ], -}) -export class TagComponent { - @Input() severity: 'success' | 'info' | 'warning' | 'danger' | 'primary' = 'primary' - @Input() rounded = false - @Input() ariaLabel?: string - - get classes() { - return { - ['hc-tag']: true, - [`hc-tag-${this.severity}`]: true, - ['hc-tag-rounded']: this.rounded, - } - } -} - diff --git a/apps/example-app/src/app/issues/issue-358.spec.ts b/apps/example-app/src/app/issues/issue-358.spec.ts deleted file mode 100644 index 6d936c09..00000000 --- a/apps/example-app/src/app/issues/issue-358.spec.ts +++ /dev/null @@ -1,40 +0,0 @@ -import { Component, Input } from '@angular/core'; -import { render, screen, fireEvent } from '@testing-library/angular'; - -@Component({ - selector: 'app-root', - template: ` - Current Count: {{ counter }} - `, -}) -class AppComponent { - @Input() counter = 0; - - increment() { - this.counter += 1; - } - - decrement() { - this.counter -= 1; - } -} - -describe('Counter', () => { - it('should render counter', async () => { - await render(AppComponent, { - componentProperties: { counter: 5 }, - }); - - expect(screen.getByText('Current Count: 5')).toBeInTheDocument(); - }); - - it('should increment the counter on click', async () => { - await render(AppComponent, { - componentProperties: { counter: 5 }, - }); - - fireEvent.click(screen.getByText('+')); - - expect(screen.getByText('Current Count: 6')).toBeInTheDocument(); - }); -}); From 22009374b05d0a0408a2fef5974124fc302cf50d Mon Sep 17 00:00:00 2001 From: Tim Deschryver <28659384+timdeschryver@users.noreply.github.com> Date: Wed, 26 Jul 2023 09:08:46 +0200 Subject: [PATCH 2/4] cleanup --- apps/example-app-karma/karma.conf.js | 38 ------- apps/example-app-karma/project.json | 5 +- apps/example-app-karma/src/app/app.module.ts | 9 -- .../src/app/examples/login-form.spec.ts | 79 ++++++++++++++ .../src/app/issues/issue-373.spec.ts | 69 ------------ .../{issue-222.spec.ts => rerender.spec.ts} | 2 +- apps/example-app-karma/src/assets/.gitkeep | 0 .../src/environments/environment.prod.ts | 3 - .../src/environments/environment.ts | 15 --- apps/example-app-karma/src/favicon.ico | Bin 5430 -> 0 bytes apps/example-app-karma/src/index.html | 14 --- apps/example-app-karma/src/main.ts | 13 --- apps/example-app-karma/src/polyfills.ts | 65 ----------- apps/example-app-karma/src/test.ts | 2 +- apps/example-app-karma/tsconfig.app.json | 2 +- apps/example-app-karma/tsconfig.spec.json | 2 +- .../example-app/src/app/app-routing.module.ts | 101 ------------------ apps/example-app/src/app/app.component.css | 17 --- apps/example-app/src/app/app.component.html | 17 --- apps/example-app/src/app/app.component.ts | 11 -- apps/example-app/src/app/app.module.ts | 63 ----------- .../app/examples/04-forms-with-material.ts | 18 +++- apps/example-app/src/app/issues/.gitkeep | 0 apps/example-app/src/app/material.module.ts | 12 --- apps/example-app/src/assets/.gitkeep | 0 .../src/environments/environment.prod.ts | 3 - .../src/environments/environment.ts | 15 --- apps/example-app/src/favicon.ico | Bin 5430 -> 0 bytes apps/example-app/src/index.html | 14 --- apps/example-app/src/main.ts | 13 --- apps/example-app/src/polyfills.ts | 65 ----------- apps/example-app/src/styles.css | 1 - apps/example-app/tsconfig.app.json | 2 +- package.json | 1 + 34 files changed, 101 insertions(+), 570 deletions(-) delete mode 100644 apps/example-app-karma/karma.conf.js delete mode 100644 apps/example-app-karma/src/app/app.module.ts create mode 100644 apps/example-app-karma/src/app/examples/login-form.spec.ts delete mode 100644 apps/example-app-karma/src/app/issues/issue-373.spec.ts rename apps/example-app-karma/src/app/issues/{issue-222.spec.ts => rerender.spec.ts} (77%) delete mode 100644 apps/example-app-karma/src/assets/.gitkeep delete mode 100644 apps/example-app-karma/src/environments/environment.prod.ts delete mode 100644 apps/example-app-karma/src/environments/environment.ts delete mode 100644 apps/example-app-karma/src/favicon.ico delete mode 100644 apps/example-app-karma/src/index.html delete mode 100644 apps/example-app-karma/src/main.ts delete mode 100644 apps/example-app-karma/src/polyfills.ts delete mode 100644 apps/example-app/src/app/app-routing.module.ts delete mode 100644 apps/example-app/src/app/app.component.css delete mode 100644 apps/example-app/src/app/app.component.html delete mode 100644 apps/example-app/src/app/app.component.ts delete mode 100644 apps/example-app/src/app/app.module.ts delete mode 100644 apps/example-app/src/app/issues/.gitkeep delete mode 100644 apps/example-app/src/app/material.module.ts delete mode 100644 apps/example-app/src/assets/.gitkeep delete mode 100644 apps/example-app/src/environments/environment.prod.ts delete mode 100644 apps/example-app/src/environments/environment.ts delete mode 100644 apps/example-app/src/favicon.ico delete mode 100644 apps/example-app/src/index.html delete mode 100644 apps/example-app/src/main.ts delete mode 100644 apps/example-app/src/polyfills.ts delete mode 100644 apps/example-app/src/styles.css diff --git a/apps/example-app-karma/karma.conf.js b/apps/example-app-karma/karma.conf.js deleted file mode 100644 index 304517cd..00000000 --- a/apps/example-app-karma/karma.conf.js +++ /dev/null @@ -1,38 +0,0 @@ -// Karma configuration file, see link for more information -// https://karma-runner.github.io/1.0/config/configuration-file.html -module.exports = function (config) { - try { - config.set({ - basePath: '', - frameworks: ['jasmine', '@angular-devkit/build-angular'], - plugins: [ - require('karma-jasmine'), - require('karma-chrome-launcher'), - require('@angular-devkit/build-angular/plugins/karma'), - ], - client: { - jasmine: { - // you can add configuration options for Jasmine here - // the possible options are listed at https://jasmine.github.io/api/edge/Configuration.html - // for example, you can disable the random execution with `random: false` - // or set a specific seed with `seed: 4321` - }, - clearContext: false, // leave Jasmine Spec Runner output visible in browser - }, - jasmineHtmlReporter: { - suppressAll: true, // removes the duplicated traces - }, - reporters: ['progress'], - port: 9876, - colors: true, - logLevel: config.LOG_INFO, - autoWatch: true, - browsers: ['ChromeHeadless'], - singleRun: true, - restartOnFileChange: true, - }); - } catch (err) { - console.log(err); - throw err; - } -}; diff --git a/apps/example-app-karma/project.json b/apps/example-app-karma/project.json index 673471e5..1141a14f 100644 --- a/apps/example-app-karma/project.json +++ b/apps/example-app-karma/project.json @@ -13,7 +13,6 @@ "outputPath": "dist/apps/example-app-karma", "index": "apps/example-app-karma/src/index.html", "main": "apps/example-app-karma/src/main.ts", - "polyfills": "apps/example-app-karma/src/polyfills.ts", "tsConfig": "apps/example-app-karma/tsconfig.app.json", "assets": ["apps/example-app-karma/src/favicon.ico", "apps/example-app-karma/src/assets"], "styles": [], @@ -73,9 +72,7 @@ "executor": "@angular-devkit/build-angular:karma", "options": { "main": "apps/example-app-karma/src/test.ts", - "tsConfig": "apps/example-app-karma/tsconfig.spec.json", - "polyfills": "apps/example-app-karma/src/polyfills.ts", - "karmaConfig": "apps/example-app-karma/karma.conf.js" + "tsConfig": "apps/example-app-karma/tsconfig.spec.json" } } }, diff --git a/apps/example-app-karma/src/app/app.module.ts b/apps/example-app-karma/src/app/app.module.ts deleted file mode 100644 index e636d9eb..00000000 --- a/apps/example-app-karma/src/app/app.module.ts +++ /dev/null @@ -1,9 +0,0 @@ -import { BrowserModule } from '@angular/platform-browser'; -import { BrowserAnimationsModule } from '@angular/platform-browser/animations'; -import { NgModule } from '@angular/core'; - -@NgModule({ - declarations: [], - imports: [BrowserModule, BrowserAnimationsModule], -}) -export class AppModule {} diff --git a/apps/example-app-karma/src/app/examples/login-form.spec.ts b/apps/example-app-karma/src/app/examples/login-form.spec.ts new file mode 100644 index 00000000..0be20b73 --- /dev/null +++ b/apps/example-app-karma/src/app/examples/login-form.spec.ts @@ -0,0 +1,79 @@ +import { Component } from '@angular/core'; +import { FormBuilder, FormControl, FormGroup, Validators, ReactiveFormsModule } from '@angular/forms'; +import userEvent from '@testing-library/user-event'; +import { render, screen } from '@testing-library/angular'; +import { NgIf } from '@angular/common'; + +const setup = async () => { + return render(LoginComponent); +}; + +it('should create a component with inputs and a button to submit', async () => { + await setup(); + + expect(screen.getByRole('textbox', { name: 'email' })).toBeInTheDocument(); + expect(screen.getByLabelText('password')).toBeInTheDocument(); + expect(screen.getByRole('button', { name: 'submit' })).toBeInTheDocument(); +}); + +it('should display invalid message and submit button must be disabled', async () => { + const utils = userEvent.setup(); + + await setup(); + + const email = screen.getByRole('textbox', { name: 'email' }); + const password = screen.getByLabelText('password'); + + await utils.type(email, 'foo'); + await utils.type(password, 's'); + + expect(screen.getAllByText(/is invalid/i).length).toBe(2); + expect(screen.getAllByRole('alert').length).toBe(2); + expect(screen.getByRole('button', { name: 'submit' })).toBeDisabled(); +}); + +@Component({ + selector: 'app-login', + standalone: true, + imports: [ReactiveFormsModule, NgIf], + template: ` +

      Login

      + + + +
      Email is invalid
      + +
      Password is invalid
      + + + `, +}) +class LoginComponent { + form: FormGroup = this.fb.group({ + email: ['', [Validators.required, Validators.email]], + password: ['', [Validators.required, Validators.minLength(8)]], + }); + + constructor(private fb: FormBuilder) {} + + blurred() { + console.log('aaaaaaaaac'); + console.log('aaaaaaaaac'); + console.log('aaaaaaaaac'); + console.log('aaaaaaaaac'); + console.log('aaaaaaaaac'); + console.log('aaaaaaaaac'); + console.log('aaaaaaaaac'); + } + get email(): FormControl { + return this.form.get('email') as FormControl; + } + + get password(): FormControl { + return this.form.get('password') as FormControl; + } + + onSubmit(_fg: FormGroup): void { + // do nothing + } +} diff --git a/apps/example-app-karma/src/app/issues/issue-373.spec.ts b/apps/example-app-karma/src/app/issues/issue-373.spec.ts deleted file mode 100644 index cdbd0ccb..00000000 --- a/apps/example-app-karma/src/app/issues/issue-373.spec.ts +++ /dev/null @@ -1,69 +0,0 @@ -import { Component } from '@angular/core'; -import { FormBuilder, FormControl, FormGroup, Validators, ReactiveFormsModule } from '@angular/forms'; -import userEvent from '@testing-library/user-event'; -import { render, screen } from '@testing-library/angular'; - -@Component({ - selector: 'app-login', - template: `

      Login

      - -
      - -
      -
      Email is required
      -
      - -
      -
      Password is required
      -
      - -
      `, -}) -class LoginComponent { - form: FormGroup = this.fb.group({ - email: ['', [Validators.required]], - password: ['', [Validators.required]], - }); - - constructor(private fb: FormBuilder) {} - - get email(): FormControl { - return this.form.get('email') as FormControl; - } - - get password(): FormControl { - return this.form.get('password') as FormControl; - } - - onSubmit(_fg: FormGroup): void { - // do nothing - } -} - -describe('LoginComponent', () => { - const setup = async () => { - return render(LoginComponent, { - imports: [ReactiveFormsModule], - }); - }; - - it('should create a component with inputs and a button to submit', async () => { - await setup(); - - expect(screen.getByRole('textbox', { name: 'email' })).toBeInTheDocument(); - expect(screen.getByLabelText('password')).toBeInTheDocument(); - expect(screen.getByRole('button', { name: 'submit' })).toBeInTheDocument(); - }); - - it('should show a message required to password and login and a button must be disabled', async () => { - await setup(); - - await userEvent.click(screen.getByRole('textbox', { name: 'email' })); - await userEvent.click(screen.getByLabelText('password')); - await userEvent.tab(); - await userEvent.click(screen.getByRole('button', { name: 'submit' })); - - expect(screen.getAllByText(/required/i).length).toBe(2); - expect(screen.getByRole('button', { name: 'submit' })).toBeDisabled(); - }); -}); diff --git a/apps/example-app-karma/src/app/issues/issue-222.spec.ts b/apps/example-app-karma/src/app/issues/rerender.spec.ts similarity index 77% rename from apps/example-app-karma/src/app/issues/issue-222.spec.ts rename to apps/example-app-karma/src/app/issues/rerender.spec.ts index 5da35d44..9b044d1f 100644 --- a/apps/example-app-karma/src/app/issues/issue-222.spec.ts +++ b/apps/example-app-karma/src/app/issues/rerender.spec.ts @@ -1,6 +1,6 @@ import { render, screen } from '@testing-library/angular'; -it('https://github.com/testing-library/angular-testing-library/issues/222 with rerender', async () => { +it('can rerender component', async () => { const { rerender } = await render(`
      Hello {{ name}}
      `, { componentProperties: { name: 'Sarah', diff --git a/apps/example-app-karma/src/assets/.gitkeep b/apps/example-app-karma/src/assets/.gitkeep deleted file mode 100644 index e69de29b..00000000 diff --git a/apps/example-app-karma/src/environments/environment.prod.ts b/apps/example-app-karma/src/environments/environment.prod.ts deleted file mode 100644 index c9669790..00000000 --- a/apps/example-app-karma/src/environments/environment.prod.ts +++ /dev/null @@ -1,3 +0,0 @@ -export const environment = { - production: true, -}; diff --git a/apps/example-app-karma/src/environments/environment.ts b/apps/example-app-karma/src/environments/environment.ts deleted file mode 100644 index 64c3e6c7..00000000 --- a/apps/example-app-karma/src/environments/environment.ts +++ /dev/null @@ -1,15 +0,0 @@ -// This file can be replaced during build by using the `fileReplacements` array. -// `ng build ---prod` replaces `environment.ts` with `environment.prod.ts`. -// The list of file replacements can be found in `workspace.json`. - -export const environment = { - production: false, -}; - -/* - * In development mode, to ignore zone related error stack frames such as - * `zone.run`, `zoneDelegate.invokeTask` for easier debugging, you can - * import the following file, but please comment it out in production mode - * because it will have performance impact when throw error - */ -// import 'zone.js/plugins/zone-error'; // Included with Angular CLI. diff --git a/apps/example-app-karma/src/favicon.ico b/apps/example-app-karma/src/favicon.ico deleted file mode 100644 index 8081c7ceaf2be08bf59010158c586170d9d2d517..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 5430 zcmc(je{54#6vvCoAI3i*G5%$U7!sA3wtMZ$fH6V9C`=eXGJb@R1%(I_{vnZtpD{6n z5Pl{DmxzBDbrB>}`90e12m8T*36WoeDLA&SD_hw{H^wM!cl_RWcVA!I+x87ee975; z@4kD^=bYPn&pmG@(+JZ`rqQEKxW<}RzhW}I!|ulN=fmjVi@x{p$cC`)5$a!)X&U+blKNvN5tg=uLvuLnuqRM;Yc*swiexsoh#XPNu{9F#c`G zQLe{yWA(Y6(;>y|-efAy11k<09(@Oo1B2@0`PtZSkqK&${ zgEY}`W@t{%?9u5rF?}Y7OL{338l*JY#P!%MVQY@oqnItpZ}?s z!r?*kwuR{A@jg2Chlf0^{q*>8n5Ir~YWf*wmsh7B5&EpHfd5@xVaj&gqsdui^spyL zB|kUoblGoO7G(MuKTfa9?pGH0@QP^b#!lM1yHWLh*2iq#`C1TdrnO-d#?Oh@XV2HK zKA{`eo{--^K&MW66Lgsktfvn#cCAc*(}qsfhrvOjMGLE?`dHVipu1J3Kgr%g?cNa8 z)pkmC8DGH~fG+dlrp(5^-QBeEvkOvv#q7MBVLtm2oD^$lJZx--_=K&Ttd=-krx(Bb zcEoKJda@S!%%@`P-##$>*u%T*mh+QjV@)Qa=Mk1?#zLk+M4tIt%}wagT{5J%!tXAE;r{@=bb%nNVxvI+C+$t?!VJ@0d@HIyMJTI{vEw0Ul ze(ha!e&qANbTL1ZneNl45t=#Ot??C0MHjjgY8%*mGisN|S6%g3;Hlx#fMNcL<87MW zZ>6moo1YD?P!fJ#Jb(4)_cc50X5n0KoDYfdPoL^iV`k&o{LPyaoqMqk92wVM#_O0l z09$(A-D+gVIlq4TA&{1T@BsUH`Bm=r#l$Z51J-U&F32+hfUP-iLo=jg7Xmy+WLq6_tWv&`wDlz#`&)Jp~iQf zZP)tu>}pIIJKuw+$&t}GQuqMd%Z>0?t%&BM&Wo^4P^Y z)c6h^f2R>X8*}q|bblAF?@;%?2>$y+cMQbN{X$)^R>vtNq_5AB|0N5U*d^T?X9{xQnJYeU{ zoZL#obI;~Pp95f1`%X3D$Mh*4^?O?IT~7HqlWguezmg?Ybq|7>qQ(@pPHbE9V?f|( z+0xo!#m@Np9PljsyxBY-UA*{U*la#8Wz2sO|48_-5t8%_!n?S$zlGe+NA%?vmxjS- zHE5O3ZarU=X}$7>;Okp(UWXJxI%G_J-@IH;%5#Rt$(WUX?6*Ux!IRd$dLP6+SmPn= z8zjm4jGjN772R{FGkXwcNv8GBcZI#@Y2m{RNF_w8(Z%^A*!bS*!}s6sh*NnURytky humW;*g7R+&|Ledvc- - - - - AngularTestingLibraryApp - - - - - - - - - diff --git a/apps/example-app-karma/src/main.ts b/apps/example-app-karma/src/main.ts deleted file mode 100644 index 741c9eb8..00000000 --- a/apps/example-app-karma/src/main.ts +++ /dev/null @@ -1,13 +0,0 @@ -import { enableProdMode } from '@angular/core'; -import { platformBrowserDynamic } from '@angular/platform-browser-dynamic'; - -import { AppModule } from './app/app.module'; -import { environment } from './environments/environment'; - -if (environment.production) { - enableProdMode(); -} - -platformBrowserDynamic() - .bootstrapModule(AppModule) - .catch((err) => console.log(err)); diff --git a/apps/example-app-karma/src/polyfills.ts b/apps/example-app-karma/src/polyfills.ts deleted file mode 100644 index f84fd8a6..00000000 --- a/apps/example-app-karma/src/polyfills.ts +++ /dev/null @@ -1,65 +0,0 @@ -/** - * This file includes polyfills needed by Angular and is loaded before the app. - * You can add your own extra polyfills to this file. - * - * This file is divided into 2 sections: - * 1. Browser polyfills. These are applied before loading ZoneJS and are sorted by browsers. - * 2. Application imports. Files imported after ZoneJS that should be loaded before your main - * file. - * - * The current setup is for so-called "evergreen" browsers; the last versions of browsers that - * automatically update themselves. This includes Safari >= 10, Chrome >= 55 (including Opera), - * Edge >= 13 on the desktop, and iOS 10 and Chrome on mobile. - * - * Learn more in https://angular.io/docs/ts/latest/guide/browser-support.html - */ - -/** ************************************************************************************************* - * BROWSER POLYFILLS - */ - -/** IE9, IE10 and IE11 requires all of the following polyfills. **/ -// import 'core-js/es6/symbol'; -// import 'core-js/es6/object'; -// import 'core-js/es6/function'; -// import 'core-js/es6/parse-int'; -// import 'core-js/es6/parse-float'; -// import 'core-js/es6/number'; -// import 'core-js/es6/math'; -// import 'core-js/es6/string'; -// import 'core-js/es6/date'; -// import 'core-js/es6/array'; -// import 'core-js/es6/regexp'; -// import 'core-js/es6/map'; -// import 'core-js/es6/weak-map'; -// import 'core-js/es6/set'; - -/** IE10 and IE11 requires the following for the Reflect API. */ -// import 'core-js/es6/reflect'; - -/** Evergreen browsers require these. **/ -// Used for reflect-metadata in JIT. If you use AOT (and only Angular decorators), you can remove. - -/** - * By default, zone.js will patch all possible macroTask and DomEvents - * user can disable parts of macroTask/DomEvents patch by setting following flags - */ - -// (window as any).__Zone_disable_requestAnimationFrame = true; // disable patch requestAnimationFrame -// (window as any).__Zone_disable_on_property = true; // disable patch onProperty such as onclick -// (window as any).__zone_symbol__BLACK_LISTED_EVENTS = ['scroll', 'mousemove']; // disable patch specified eventNames - -/* - * in IE/Edge developer tools, the addEventListener will also be wrapped by zone.js - * with the following flag, it will bypass `zone.js` patch for IE/Edge - */ -// (window as any).__Zone_enable_cross_context_check = true; - -/** ************************************************************************************************* - * Zone JS is required by default for Angular itself. - */ -import 'zone.js'; // Included with Angular CLI. - -/** ************************************************************************************************* - * APPLICATION IMPORTS - */ diff --git a/apps/example-app-karma/src/test.ts b/apps/example-app-karma/src/test.ts index 60544d54..ad4ed9e4 100644 --- a/apps/example-app-karma/src/test.ts +++ b/apps/example-app-karma/src/test.ts @@ -1,4 +1,4 @@ -// This file is required by karma.conf.js and loads recursively all the .spec and framework files +import 'zone.js'; import 'zone.js/dist/zone-testing'; import { getTestBed } from '@angular/core/testing'; import { BrowserDynamicTestingModule, platformBrowserDynamicTesting } from '@angular/platform-browser-dynamic/testing'; diff --git a/apps/example-app-karma/tsconfig.app.json b/apps/example-app-karma/tsconfig.app.json index 79a77d1b..46150c25 100644 --- a/apps/example-app-karma/tsconfig.app.json +++ b/apps/example-app-karma/tsconfig.app.json @@ -7,7 +7,7 @@ "target": "ES2022", "useDefineForClassFields": false }, - "files": ["src/main.ts", "src/polyfills.ts"], + "files": ["src/main.ts"], "include": ["src/**/*.d.ts"], "exclude": ["**/*.test.ts", "**/*.spec.ts"] } diff --git a/apps/example-app-karma/tsconfig.spec.json b/apps/example-app-karma/tsconfig.spec.json index ff71a7ee..0f4baec3 100644 --- a/apps/example-app-karma/tsconfig.spec.json +++ b/apps/example-app-karma/tsconfig.spec.json @@ -6,6 +6,6 @@ "target": "ES2022", "useDefineForClassFields": false }, - "files": ["src/test.ts", "src/polyfills.ts"], + "files": ["src/test.ts"], "include": ["**/*.spec.ts", "**/*.d.ts"] } diff --git a/apps/example-app/src/app/app-routing.module.ts b/apps/example-app/src/app/app-routing.module.ts deleted file mode 100644 index 6a9f0b9e..00000000 --- a/apps/example-app/src/app/app-routing.module.ts +++ /dev/null @@ -1,101 +0,0 @@ -import { NgModule } from '@angular/core'; -import { Routes, RouterModule } from '@angular/router'; - -import { SingleComponent } from './examples/00-single-component'; -import { NestedContainerComponent } from './examples/01-nested-component'; -import { InputOutputComponent } from './examples/02-input-output'; -import { FormsComponent } from './examples/03-forms'; -import { MaterialFormsComponent } from './examples/04-forms-with-material'; -import { ComponentWithProviderComponent } from './examples/05-component-provider'; -import { WithNgRxStoreComponent } from './examples/06-with-ngrx-store'; -import { WithNgRxMockStoreComponent } from './examples/07-with-ngrx-mock-store'; -import { RootComponent, DetailComponent, HiddenDetailComponent } from './examples/09-router'; - -export const examples = [ - { - path: 'single-component', - component: SingleComponent, - data: { - name: 'Single component', - }, - }, - { - path: 'nested-component', - component: NestedContainerComponent, - data: { - name: 'Nested components', - }, - }, - { - path: 'input-output', - component: InputOutputComponent, - data: { - name: 'Input and Output', - }, - }, - { - path: 'forms', - component: FormsComponent, - data: { - name: 'Form', - }, - }, - { - path: 'forms-material', - component: MaterialFormsComponent, - data: { - name: 'Material form', - }, - }, - { - path: 'component-with-provider', - component: ComponentWithProviderComponent, - data: { - name: 'With provider', - }, - }, - { - path: 'with-ngrx-store', - component: WithNgRxStoreComponent, - data: { - name: 'With NgRx Store', - }, - }, - { - path: 'with-ngrx-mock-store', - component: WithNgRxMockStoreComponent, - data: { - name: 'With NgRx MockStore', - }, - }, - { - path: 'with-router', - component: RootComponent, - data: { - name: 'Router', - }, - children: [ - { - path: 'detail/:id', - component: DetailComponent, - }, - { - path: 'hidden-detail', - component: HiddenDetailComponent, - }, - ], - }, -]; - -export const routes: Routes = [ - { - path: '', - children: examples, - }, -]; - -@NgModule({ - imports: [RouterModule.forRoot(routes, {})], - exports: [RouterModule], -}) -export class AppRoutingModule {} diff --git a/apps/example-app/src/app/app.component.css b/apps/example-app/src/app/app.component.css deleted file mode 100644 index 6d3bc67b..00000000 --- a/apps/example-app/src/app/app.component.css +++ /dev/null @@ -1,17 +0,0 @@ -.container { - display: flex; - flex-direction: column; - position: absolute; - top: 0; - bottom: 0; - left: 0; - right: 0; -} - -.sidenav { - flex: 1; -} - -.sidenav-container { - padding: 10px; -} diff --git a/apps/example-app/src/app/app.component.html b/apps/example-app/src/app/app.component.html deleted file mode 100644 index 04b5f476..00000000 --- a/apps/example-app/src/app/app.component.html +++ /dev/null @@ -1,17 +0,0 @@ -
      - -

      @testing-library/angular

      -
      - - - - - {{ example.data.name }} - - - - - - - -
      diff --git a/apps/example-app/src/app/app.component.ts b/apps/example-app/src/app/app.component.ts deleted file mode 100644 index 5b20ef63..00000000 --- a/apps/example-app/src/app/app.component.ts +++ /dev/null @@ -1,11 +0,0 @@ -import { Component } from '@angular/core'; -import { examples as routes } from './app-routing.module'; - -@Component({ - selector: 'app-root', - templateUrl: './app.component.html', - styleUrls: ['app.component.css'], -}) -export class AppComponent { - examples = routes; -} diff --git a/apps/example-app/src/app/app.module.ts b/apps/example-app/src/app/app.module.ts deleted file mode 100644 index 3ac3c4ca..00000000 --- a/apps/example-app/src/app/app.module.ts +++ /dev/null @@ -1,63 +0,0 @@ -import { BrowserModule } from '@angular/platform-browser'; -import { BrowserAnimationsModule } from '@angular/platform-browser/animations'; -import { NgModule } from '@angular/core'; -import { ReactiveFormsModule } from '@angular/forms'; -import { StoreModule } from '@ngrx/store'; - -import { AppRoutingModule } from './app-routing.module'; -import { MaterialModule } from './material.module'; -import { MatIconModule } from '@angular/material/icon'; -import { MatListModule } from '@angular/material/list'; -import { MatSidenavModule } from '@angular/material/sidenav'; -import { MatToolbarModule } from '@angular/material/toolbar'; - -import { AppComponent } from './app.component'; -import { SingleComponent } from './examples/00-single-component'; -import { NestedButtonComponent, NestedValueComponent, NestedContainerComponent } from './examples/01-nested-component'; -import { InputOutputComponent } from './examples/02-input-output'; -import { FormsComponent } from './examples/03-forms'; -import { MaterialFormsComponent } from './examples/04-forms-with-material'; -import { ComponentWithProviderComponent } from './examples/05-component-provider'; -import { WithNgRxStoreComponent, reducer } from './examples/06-with-ngrx-store'; -import { WithNgRxMockStoreComponent } from './examples/07-with-ngrx-mock-store'; -import { RootComponent, DetailComponent, HiddenDetailComponent } from './examples/09-router'; -import { ScrollingModule } from '@angular/cdk/scrolling'; - -function reducerItems() { - return ['One', 'Two', 'Three']; -} - -@NgModule({ - declarations: [AppComponent], - imports: [ - SingleComponent, - NestedButtonComponent, - NestedValueComponent, - NestedContainerComponent, - InputOutputComponent, - FormsComponent, - MaterialFormsComponent, - ComponentWithProviderComponent, - WithNgRxStoreComponent, - WithNgRxMockStoreComponent, - RootComponent, - DetailComponent, - HiddenDetailComponent, - BrowserModule, - ReactiveFormsModule, - BrowserAnimationsModule, - MaterialModule, - MatIconModule, - MatListModule, - MatSidenavModule, - MatToolbarModule, - AppRoutingModule, - ScrollingModule, - StoreModule.forRoot({ - value: reducer, - items: reducerItems, - }), - ], - bootstrap: [AppComponent], -}) -export class AppModule {} diff --git a/apps/example-app/src/app/examples/04-forms-with-material.ts b/apps/example-app/src/app/examples/04-forms-with-material.ts index 5e6ed8e9..ef80493e 100644 --- a/apps/example-app/src/app/examples/04-forms-with-material.ts +++ b/apps/example-app/src/app/examples/04-forms-with-material.ts @@ -1,11 +1,23 @@ import { Component } from '@angular/core'; import { FormBuilder, ReactiveFormsModule, Validators } from '@angular/forms'; -import { MaterialModule } from '../material.module'; import { NgForOf, NgIf } from '@angular/common'; - +import { MatCheckboxModule } from '@angular/material/checkbox'; +import { MatInputModule } from '@angular/material/input'; +import { MatSelectModule } from '@angular/material/select'; +import { MatDatepickerModule } from '@angular/material/datepicker'; +import { MatNativeDateModule } from '@angular/material/core'; @Component({ standalone: true, - imports: [MaterialModule, ReactiveFormsModule, NgForOf, NgIf], + imports: [ + MatInputModule, + MatSelectModule, + MatDatepickerModule, + MatNativeDateModule, + MatCheckboxModule, + ReactiveFormsModule, + NgForOf, + NgIf, + ], selector: 'app-fixture', template: `
      diff --git a/apps/example-app/src/app/issues/.gitkeep b/apps/example-app/src/app/issues/.gitkeep deleted file mode 100644 index e69de29b..00000000 diff --git a/apps/example-app/src/app/material.module.ts b/apps/example-app/src/app/material.module.ts deleted file mode 100644 index 51a91899..00000000 --- a/apps/example-app/src/app/material.module.ts +++ /dev/null @@ -1,12 +0,0 @@ -import { NgModule } from '@angular/core'; - -import { MatCheckboxModule } from '@angular/material/checkbox'; -import { MatInputModule } from '@angular/material/input'; -import { MatSelectModule } from '@angular/material/select'; -import { MatDatepickerModule } from '@angular/material/datepicker'; -import { MatNativeDateModule } from '@angular/material/core'; - -@NgModule({ - exports: [MatInputModule, MatSelectModule, MatDatepickerModule, MatNativeDateModule, MatCheckboxModule], -}) -export class MaterialModule {} diff --git a/apps/example-app/src/assets/.gitkeep b/apps/example-app/src/assets/.gitkeep deleted file mode 100644 index e69de29b..00000000 diff --git a/apps/example-app/src/environments/environment.prod.ts b/apps/example-app/src/environments/environment.prod.ts deleted file mode 100644 index c9669790..00000000 --- a/apps/example-app/src/environments/environment.prod.ts +++ /dev/null @@ -1,3 +0,0 @@ -export const environment = { - production: true, -}; diff --git a/apps/example-app/src/environments/environment.ts b/apps/example-app/src/environments/environment.ts deleted file mode 100644 index 85db3caf..00000000 --- a/apps/example-app/src/environments/environment.ts +++ /dev/null @@ -1,15 +0,0 @@ -// This file can be replaced during build by using the `fileReplacements` array. -// `ng build ---prod` replaces `environment.ts` with `environment.prod.ts`. -// The list of file replacements can be found in `angular.json`. - -export const environment = { - production: false, -}; - -/* - * In development mode, to ignore zone related error stack frames such as - * `zone.run`, `zoneDelegate.invokeTask` for easier debugging, you can - * import the following file, but please comment it out in production mode - * because it will have performance impact when throw error - */ -// import 'zone.js/plugins/zone-error'; // Included with Angular CLI. diff --git a/apps/example-app/src/favicon.ico b/apps/example-app/src/favicon.ico deleted file mode 100644 index 8081c7ceaf2be08bf59010158c586170d9d2d517..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 5430 zcmc(je{54#6vvCoAI3i*G5%$U7!sA3wtMZ$fH6V9C`=eXGJb@R1%(I_{vnZtpD{6n z5Pl{DmxzBDbrB>}`90e12m8T*36WoeDLA&SD_hw{H^wM!cl_RWcVA!I+x87ee975; z@4kD^=bYPn&pmG@(+JZ`rqQEKxW<}RzhW}I!|ulN=fmjVi@x{p$cC`)5$a!)X&U+blKNvN5tg=uLvuLnuqRM;Yc*swiexsoh#XPNu{9F#c`G zQLe{yWA(Y6(;>y|-efAy11k<09(@Oo1B2@0`PtZSkqK&${ zgEY}`W@t{%?9u5rF?}Y7OL{338l*JY#P!%MVQY@oqnItpZ}?s z!r?*kwuR{A@jg2Chlf0^{q*>8n5Ir~YWf*wmsh7B5&EpHfd5@xVaj&gqsdui^spyL zB|kUoblGoO7G(MuKTfa9?pGH0@QP^b#!lM1yHWLh*2iq#`C1TdrnO-d#?Oh@XV2HK zKA{`eo{--^K&MW66Lgsktfvn#cCAc*(}qsfhrvOjMGLE?`dHVipu1J3Kgr%g?cNa8 z)pkmC8DGH~fG+dlrp(5^-QBeEvkOvv#q7MBVLtm2oD^$lJZx--_=K&Ttd=-krx(Bb zcEoKJda@S!%%@`P-##$>*u%T*mh+QjV@)Qa=Mk1?#zLk+M4tIt%}wagT{5J%!tXAE;r{@=bb%nNVxvI+C+$t?!VJ@0d@HIyMJTI{vEw0Ul ze(ha!e&qANbTL1ZneNl45t=#Ot??C0MHjjgY8%*mGisN|S6%g3;Hlx#fMNcL<87MW zZ>6moo1YD?P!fJ#Jb(4)_cc50X5n0KoDYfdPoL^iV`k&o{LPyaoqMqk92wVM#_O0l z09$(A-D+gVIlq4TA&{1T@BsUH`Bm=r#l$Z51J-U&F32+hfUP-iLo=jg7Xmy+WLq6_tWv&`wDlz#`&)Jp~iQf zZP)tu>}pIIJKuw+$&t}GQuqMd%Z>0?t%&BM&Wo^4P^Y z)c6h^f2R>X8*}q|bblAF?@;%?2>$y+cMQbN{X$)^R>vtNq_5AB|0N5U*d^T?X9{xQnJYeU{ zoZL#obI;~Pp95f1`%X3D$Mh*4^?O?IT~7HqlWguezmg?Ybq|7>qQ(@pPHbE9V?f|( z+0xo!#m@Np9PljsyxBY-UA*{U*la#8Wz2sO|48_-5t8%_!n?S$zlGe+NA%?vmxjS- zHE5O3ZarU=X}$7>;Okp(UWXJxI%G_J-@IH;%5#Rt$(WUX?6*Ux!IRd$dLP6+SmPn= z8zjm4jGjN772R{FGkXwcNv8GBcZI#@Y2m{RNF_w8(Z%^A*!bS*!}s6sh*NnURytky humW;*g7R+&|Ledvc- - - - - AngularTestingLibraryApp - - - - - - - - - diff --git a/apps/example-app/src/main.ts b/apps/example-app/src/main.ts deleted file mode 100644 index 741c9eb8..00000000 --- a/apps/example-app/src/main.ts +++ /dev/null @@ -1,13 +0,0 @@ -import { enableProdMode } from '@angular/core'; -import { platformBrowserDynamic } from '@angular/platform-browser-dynamic'; - -import { AppModule } from './app/app.module'; -import { environment } from './environments/environment'; - -if (environment.production) { - enableProdMode(); -} - -platformBrowserDynamic() - .bootstrapModule(AppModule) - .catch((err) => console.log(err)); diff --git a/apps/example-app/src/polyfills.ts b/apps/example-app/src/polyfills.ts deleted file mode 100644 index f84fd8a6..00000000 --- a/apps/example-app/src/polyfills.ts +++ /dev/null @@ -1,65 +0,0 @@ -/** - * This file includes polyfills needed by Angular and is loaded before the app. - * You can add your own extra polyfills to this file. - * - * This file is divided into 2 sections: - * 1. Browser polyfills. These are applied before loading ZoneJS and are sorted by browsers. - * 2. Application imports. Files imported after ZoneJS that should be loaded before your main - * file. - * - * The current setup is for so-called "evergreen" browsers; the last versions of browsers that - * automatically update themselves. This includes Safari >= 10, Chrome >= 55 (including Opera), - * Edge >= 13 on the desktop, and iOS 10 and Chrome on mobile. - * - * Learn more in https://angular.io/docs/ts/latest/guide/browser-support.html - */ - -/** ************************************************************************************************* - * BROWSER POLYFILLS - */ - -/** IE9, IE10 and IE11 requires all of the following polyfills. **/ -// import 'core-js/es6/symbol'; -// import 'core-js/es6/object'; -// import 'core-js/es6/function'; -// import 'core-js/es6/parse-int'; -// import 'core-js/es6/parse-float'; -// import 'core-js/es6/number'; -// import 'core-js/es6/math'; -// import 'core-js/es6/string'; -// import 'core-js/es6/date'; -// import 'core-js/es6/array'; -// import 'core-js/es6/regexp'; -// import 'core-js/es6/map'; -// import 'core-js/es6/weak-map'; -// import 'core-js/es6/set'; - -/** IE10 and IE11 requires the following for the Reflect API. */ -// import 'core-js/es6/reflect'; - -/** Evergreen browsers require these. **/ -// Used for reflect-metadata in JIT. If you use AOT (and only Angular decorators), you can remove. - -/** - * By default, zone.js will patch all possible macroTask and DomEvents - * user can disable parts of macroTask/DomEvents patch by setting following flags - */ - -// (window as any).__Zone_disable_requestAnimationFrame = true; // disable patch requestAnimationFrame -// (window as any).__Zone_disable_on_property = true; // disable patch onProperty such as onclick -// (window as any).__zone_symbol__BLACK_LISTED_EVENTS = ['scroll', 'mousemove']; // disable patch specified eventNames - -/* - * in IE/Edge developer tools, the addEventListener will also be wrapped by zone.js - * with the following flag, it will bypass `zone.js` patch for IE/Edge - */ -// (window as any).__Zone_enable_cross_context_check = true; - -/** ************************************************************************************************* - * Zone JS is required by default for Angular itself. - */ -import 'zone.js'; // Included with Angular CLI. - -/** ************************************************************************************************* - * APPLICATION IMPORTS - */ diff --git a/apps/example-app/src/styles.css b/apps/example-app/src/styles.css deleted file mode 100644 index dd3d5ed2..00000000 --- a/apps/example-app/src/styles.css +++ /dev/null @@ -1 +0,0 @@ -@import '@angular/material/prebuilt-themes/deeppurple-amber.css'; diff --git a/apps/example-app/tsconfig.app.json b/apps/example-app/tsconfig.app.json index 6feb8d6e..b0e22e14 100644 --- a/apps/example-app/tsconfig.app.json +++ b/apps/example-app/tsconfig.app.json @@ -7,7 +7,7 @@ "target": "ES2022", "useDefineForClassFields": false }, - "files": ["src/main.ts", "src/polyfills.ts"], + "files": ["src/main.ts"], "include": ["src/**/*.d.ts"], "exclude": ["**/*.test.ts", "**/*.spec.ts", "jest.config.ts"] } diff --git a/package.json b/package.json index f9264f29..858b01ac 100644 --- a/package.json +++ b/package.json @@ -89,6 +89,7 @@ "jest-preset-angular": "13.1.0", "karma": "6.4.0", "karma-chrome-launcher": "^3.1.0", + "karma-coverage": "^2.2.1", "karma-jasmine": "5.1.0", "karma-jasmine-html-reporter": "2.0.0", "lint-staged": "^12.1.6", From 26fb189ee355a7bf4307b20cfaa3b214248f2c62 Mon Sep 17 00:00:00 2001 From: Tim Deschryver <28659384+timdeschryver@users.noreply.github.com> Date: Wed, 26 Jul 2023 09:19:35 +0200 Subject: [PATCH 3/4] cleanup v2 --- .../src/app/examples/login-form.spec.ts | 14 +++++--------- .../src/app/examples/20-test-harness.spec.ts | 6 +++--- .../src/app/examples/20-test-harness.ts | 2 +- apps/example-app/src/test-setup.ts | 6 ------ 4 files changed, 9 insertions(+), 19 deletions(-) diff --git a/apps/example-app-karma/src/app/examples/login-form.spec.ts b/apps/example-app-karma/src/app/examples/login-form.spec.ts index 0be20b73..07a1e1d1 100644 --- a/apps/example-app-karma/src/app/examples/login-form.spec.ts +++ b/apps/example-app-karma/src/app/examples/login-form.spec.ts @@ -4,12 +4,8 @@ import userEvent from '@testing-library/user-event'; import { render, screen } from '@testing-library/angular'; import { NgIf } from '@angular/common'; -const setup = async () => { - return render(LoginComponent); -}; - it('should create a component with inputs and a button to submit', async () => { - await setup(); + await render(LoginComponent); expect(screen.getByRole('textbox', { name: 'email' })).toBeInTheDocument(); expect(screen.getByLabelText('password')).toBeInTheDocument(); @@ -17,15 +13,15 @@ it('should create a component with inputs and a button to submit', async () => { }); it('should display invalid message and submit button must be disabled', async () => { - const utils = userEvent.setup(); + const user = userEvent.setup(); - await setup(); + await render(LoginComponent); const email = screen.getByRole('textbox', { name: 'email' }); const password = screen.getByLabelText('password'); - await utils.type(email, 'foo'); - await utils.type(password, 's'); + await user.type(email, 'foo'); + await user.type(password, 's'); expect(screen.getAllByText(/is invalid/i).length).toBe(2); expect(screen.getAllByRole('alert').length).toBe(2); diff --git a/apps/example-app/src/app/examples/20-test-harness.spec.ts b/apps/example-app/src/app/examples/20-test-harness.spec.ts index 50e99bcd..6e4d9e3a 100644 --- a/apps/example-app/src/app/examples/20-test-harness.spec.ts +++ b/apps/example-app/src/app/examples/20-test-harness.spec.ts @@ -4,12 +4,12 @@ import { MatSnackBarHarness } from '@angular/material/snack-bar/testing'; import { render, screen } from '@testing-library/angular'; import userEvent from '@testing-library/user-event'; -import { SnackBarComponent } from './20-test-harness'; +import { HarnessComponent } from './20-test-harness'; // eslint-disable-next-line jest/no-disabled-tests test.skip('can be used with TestHarness', async () => { const view = await render(``, { - imports: [SnackBarComponent], + imports: [HarnessComponent], }); const loader = TestbedHarnessEnvironment.documentRootLoader(view.fixture); @@ -25,7 +25,7 @@ test.skip('can be used with TestHarness', async () => { test.skip('can be used in combination with TestHarness', async () => { const user = userEvent.setup(); - const view = await render(SnackBarComponent); + const view = await render(HarnessComponent); const loader = TestbedHarnessEnvironment.documentRootLoader(view.fixture); await user.click(screen.getByRole('button')); diff --git a/apps/example-app/src/app/examples/20-test-harness.ts b/apps/example-app/src/app/examples/20-test-harness.ts index 53069075..08d6afd7 100644 --- a/apps/example-app/src/app/examples/20-test-harness.ts +++ b/apps/example-app/src/app/examples/20-test-harness.ts @@ -10,7 +10,7 @@ import { MatSnackBar, MatSnackBarModule } from '@angular/material/snack-bar'; `, }) -export class SnackBarComponent { +export class HarnessComponent { constructor(private snackBar: MatSnackBar) {} openSnackBar() { diff --git a/apps/example-app/src/test-setup.ts b/apps/example-app/src/test-setup.ts index 8301387c..0da94a0a 100644 --- a/apps/example-app/src/test-setup.ts +++ b/apps/example-app/src/test-setup.ts @@ -1,8 +1,2 @@ import 'jest-preset-angular/setup-jest'; import '@testing-library/jest-dom'; -import { configure } from '@testing-library/angular'; -import { ReactiveFormsModule } from '@angular/forms'; - -configure({ - defaultImports: [ReactiveFormsModule], -}); From 3a473aeaf780b4cec24c5a905bacac46e3e89d4d Mon Sep 17 00:00:00 2001 From: Tim Deschryver <28659384+timdeschryver@users.noreply.github.com> Date: Wed, 26 Jul 2023 10:06:43 +0200 Subject: [PATCH 4/4] ci: re-add karma config to run once in headless mode --- apps/example-app-karma/karma.conf.js | 38 ++++++++++++++++++++++++++++ apps/example-app-karma/project.json | 9 ++----- apps/example-app/project.json | 6 ----- 3 files changed, 40 insertions(+), 13 deletions(-) create mode 100644 apps/example-app-karma/karma.conf.js diff --git a/apps/example-app-karma/karma.conf.js b/apps/example-app-karma/karma.conf.js new file mode 100644 index 00000000..304517cd --- /dev/null +++ b/apps/example-app-karma/karma.conf.js @@ -0,0 +1,38 @@ +// Karma configuration file, see link for more information +// https://karma-runner.github.io/1.0/config/configuration-file.html +module.exports = function (config) { + try { + config.set({ + basePath: '', + frameworks: ['jasmine', '@angular-devkit/build-angular'], + plugins: [ + require('karma-jasmine'), + require('karma-chrome-launcher'), + require('@angular-devkit/build-angular/plugins/karma'), + ], + client: { + jasmine: { + // you can add configuration options for Jasmine here + // the possible options are listed at https://jasmine.github.io/api/edge/Configuration.html + // for example, you can disable the random execution with `random: false` + // or set a specific seed with `seed: 4321` + }, + clearContext: false, // leave Jasmine Spec Runner output visible in browser + }, + jasmineHtmlReporter: { + suppressAll: true, // removes the duplicated traces + }, + reporters: ['progress'], + port: 9876, + colors: true, + logLevel: config.LOG_INFO, + autoWatch: true, + browsers: ['ChromeHeadless'], + singleRun: true, + restartOnFileChange: true, + }); + } catch (err) { + console.log(err); + throw err; + } +}; diff --git a/apps/example-app-karma/project.json b/apps/example-app-karma/project.json index 1141a14f..02434953 100644 --- a/apps/example-app-karma/project.json +++ b/apps/example-app-karma/project.json @@ -26,12 +26,6 @@ "maximumWarning": "6kb" } ], - "fileReplacements": [ - { - "replace": "apps/example-app-karma/src/environments/environment.ts", - "with": "apps/example-app-karma/src/environments/environment.prod.ts" - } - ], "outputHashing": "all" }, "development": { @@ -72,7 +66,8 @@ "executor": "@angular-devkit/build-angular:karma", "options": { "main": "apps/example-app-karma/src/test.ts", - "tsConfig": "apps/example-app-karma/tsconfig.spec.json" + "tsConfig": "apps/example-app-karma/tsconfig.spec.json", + "karmaConfig": "apps/example-app-karma/karma.conf.js" } } }, diff --git a/apps/example-app/project.json b/apps/example-app/project.json index b3b1667d..1c1e4ede 100644 --- a/apps/example-app/project.json +++ b/apps/example-app/project.json @@ -27,12 +27,6 @@ "maximumWarning": "6kb" } ], - "fileReplacements": [ - { - "replace": "apps/example-app/src/environments/environment.ts", - "with": "apps/example-app/src/environments/environment.prod.ts" - } - ], "outputHashing": "all" }, "development": {