diff --git a/apps/datahub/src/app/app.module.ts b/apps/datahub/src/app/app.module.ts index 03555b3475..663e0b0be7 100644 --- a/apps/datahub/src/app/app.module.ts +++ b/apps/datahub/src/app/app.module.ts @@ -4,6 +4,7 @@ import { BrowserModule } from '@angular/platform-browser' import { Router, RouterModule } from '@angular/router' import { FeatureCatalogModule, + OrganisationsComponent, ORGANIZATION_PAGE_URL_TOKEN, ORGANIZATION_URL_TOKEN, } from '@geonetwork-ui/feature/catalog' @@ -29,19 +30,11 @@ import { RECORD_URL_TOKEN, } from '@geonetwork-ui/feature/search' import { - LinkCardComponent, THUMBNAIL_PLACEHOLDER, UiElementsModule, } from '@geonetwork-ui/ui/elements' -import { - PreviousNextButtonsComponent, - UiInputsModule, -} from '@geonetwork-ui/ui/inputs' -import { - BlockListComponent, - CarouselComponent, - UiLayoutModule, -} from '@geonetwork-ui/ui/layout' +import { UiInputsModule } from '@geonetwork-ui/ui/inputs' +import { UiLayoutModule } from '@geonetwork-ui/ui/layout' import { UiSearchModule } from '@geonetwork-ui/ui/search' import { getGlobalConfig, @@ -74,14 +67,13 @@ import { NewsPageComponent } from './home/news-page/news-page.component' import { OrganisationsPageComponent } from './home/organisations-page/organisations-page.component' import { SearchPageComponent } from './home/search/search-page/search-page.component' import { SearchFiltersComponent } from './home/search/search-filters/search-filters.component' -import { HeaderRecordComponent } from './record/header-record/header-record.component' import { NavigationBarComponent } from './record/navigation-bar/navigation-bar.component' import { RecordPageComponent } from './record/record-page/record-page.component' import { DatahubRouterService } from './router/datahub-router.service' import { NavigationMenuComponent } from './home/navigation-menu/navigation-menu.component' import { FormsModule } from '@angular/forms' import { UiDatavizModule } from '@geonetwork-ui/ui/dataviz' -import { LANGUAGES_LIST, UiCatalogModule } from '@geonetwork-ui/ui/catalog' +import { LANGUAGES_LIST } from '@geonetwork-ui/ui/catalog' import { LOGIN_URL, METADATA_LANGUAGE, @@ -89,14 +81,8 @@ import { provideRepositoryUrl, } from '@geonetwork-ui/api/repository' import { BrowserAnimationsModule } from '@angular/platform-browser/animations' -import { RecordRelatedRecordsComponent } from './record/record-related-records/record-related-records.component' -import { RecordMetadataComponent } from './record/record-metadata/record-metadata.component' -import { RecordOtherlinksComponent } from './record/record-otherlinks/record-otherlinks.component' -import { RecordDownloadsComponent } from './record/record-downloads/record-downloads.component' -import { RecordApisComponent } from './record/record-apis/record-apis.component' import { MatTabsModule } from '@angular/material/tabs' import { UiWidgetsModule } from '@geonetwork-ui/ui/widgets' -import { RecordUserFeedbacksComponent } from './record/record-user-feedbacks/record-user-feedbacks.component' import { LetDirective } from '@ngrx/component' import { OrganizationPageComponent } from './organization/organization-page/organization-page.component' import { @@ -105,16 +91,11 @@ import { MAP_VIEW_CONSTRAINTS, } from '@geonetwork-ui/ui/map' import { - matAccountBoxOutline, matAddOutline, - matCloseOutline, - matEditOutline, matExpandMoreOutline, - matLocationSearchingOutline, matMenuOutline, matMoreHorizOutline, matRemoveOutline, - matSendOutline, matStarOutline, } from '@ng-icons/material-icons/outline' import { NgIconsModule, provideNgIconsConfig } from '@ng-icons/core' @@ -128,8 +109,6 @@ export const metaReducers: MetaReducer[] = !environment.production ? [] : [] HomePageComponent, HomeHeaderComponent, HeaderBadgeButtonComponent, - HeaderRecordComponent, - RecordPageComponent, SearchFiltersComponent, NavigationBarComponent, NewsPageComponent, @@ -138,12 +117,6 @@ export const metaReducers: MetaReducer[] = !environment.production ? [] : [] LastCreatedComponent, KeyFiguresComponent, NavigationMenuComponent, - RecordRelatedRecordsComponent, - RecordUserFeedbacksComponent, - RecordMetadataComponent, - RecordOtherlinksComponent, - RecordDownloadsComponent, - RecordApisComponent, ], imports: [ BrowserModule, @@ -182,29 +155,20 @@ export const metaReducers: MetaReducer[] = !environment.production ? [] : [] UiDatavizModule, FormsModule, UiInputsModule, - UiCatalogModule, MatTabsModule, UiWidgetsModule, - LinkCardComponent, - CarouselComponent, - BlockListComponent, - PreviousNextButtonsComponent, RecordMetaComponent, LetDirective, // FIXME: these imports are required by non-standalone components and should be removed once all components have been made standalone NgIconsModule.withIcons({ matMenuOutline, matRemoveOutline, - matCloseOutline, matMoreHorizOutline, matAddOutline, matExpandMoreOutline, - matEditOutline, - matAccountBoxOutline, matStarOutline, - matLocationSearchingOutline, - matSendOutline, }), + OrganisationsComponent, ], providers: [ provideNgIconsConfig({ diff --git a/apps/datahub/src/app/organization/organization-details/organization-details.component.ts b/apps/datahub/src/app/organization/organization-details/organization-details.component.ts index 620324cf4f..a089aca958 100644 --- a/apps/datahub/src/app/organization/organization-details/organization-details.component.ts +++ b/apps/datahub/src/app/organization/organization-details/organization-details.component.ts @@ -6,7 +6,7 @@ import { OnInit, ViewChild, } from '@angular/core' -import { AsyncPipe, NgClass, NgForOf, NgIf } from '@angular/common' +import { CommonModule } from '@angular/common' import { CatalogRecord, Organization, @@ -23,8 +23,10 @@ import { } from '@geonetwork-ui/ui/layout' import { LetDirective } from '@ngrx/component' import { + ErrorComponent, ErrorType, LinkCardComponent, + RelatedRecordCardComponent, UiElementsModule, } from '@geonetwork-ui/ui/elements' import { UiSearchModule } from '@geonetwork-ui/ui/search' @@ -41,7 +43,10 @@ import { UiDatavizModule } from '@geonetwork-ui/ui/dataviz' import { RouterLink } from '@angular/router' import { ROUTER_ROUTE_SEARCH } from '@geonetwork-ui/feature/router' import { OrganizationsServiceInterface } from '@geonetwork-ui/common/domain/organizations.service.interface' -import { UiWidgetsModule } from '@geonetwork-ui/ui/widgets' +import { + SpinningLoaderComponent, + UiWidgetsModule, +} from '@geonetwork-ui/ui/widgets' import { startWith } from 'rxjs/operators' @Component({ @@ -51,15 +56,13 @@ import { startWith } from 'rxjs/operators' changeDetection: ChangeDetectionStrategy.OnPush, standalone: true, imports: [ - AsyncPipe, - NgIf, + CommonModule, ButtonComponent, TranslateModule, CarouselComponent, BlockListComponent, LetDirective, LinkCardComponent, - NgForOf, PreviousNextButtonsComponent, UiElementsModule, UiSearchModule, @@ -67,7 +70,9 @@ import { startWith } from 'rxjs/operators' UiDatavizModule, RouterLink, UiWidgetsModule, - NgClass, + ErrorComponent, + SpinningLoaderComponent, + RelatedRecordCardComponent, ], }) export class OrganizationDetailsComponent implements OnInit, OnDestroy { diff --git a/apps/datahub/src/app/organization/organization-header/organization-header.component.spec.ts b/apps/datahub/src/app/organization/organization-header/organization-header.component.spec.ts index 7028299361..a43c64c1b1 100644 --- a/apps/datahub/src/app/organization/organization-header/organization-header.component.spec.ts +++ b/apps/datahub/src/app/organization/organization-header/organization-header.component.spec.ts @@ -3,7 +3,6 @@ import { ComponentFixture, TestBed } from '@angular/core/testing' import { OrganizationHeaderComponent } from './organization-header.component' import { UiInputsModule } from '@geonetwork-ui/ui/inputs' import { TranslateModule } from '@ngx-translate/core' -import { UiCatalogModule } from '@geonetwork-ui/ui/catalog' import { AsyncPipe, Location, NgIf } from '@angular/common' import { someOrganizationsFixture } from '@geonetwork-ui/common/fixtures' @@ -33,7 +32,6 @@ describe('OrganizationHeaderComponent', () => { OrganizationHeaderComponent, UiInputsModule, TranslateModule, - UiCatalogModule, NgIf, AsyncPipe, TranslateModule.forRoot(), diff --git a/apps/datahub/src/app/organization/organization-header/organization-header.component.ts b/apps/datahub/src/app/organization/organization-header/organization-header.component.ts index a59e7de46b..37b3216a59 100644 --- a/apps/datahub/src/app/organization/organization-header/organization-header.component.ts +++ b/apps/datahub/src/app/organization/organization-header/organization-header.component.ts @@ -1,8 +1,10 @@ import { ChangeDetectionStrategy, Component, Input } from '@angular/core' import { getGlobalConfig, getThemeConfig } from '@geonetwork-ui/util/app-config' import { TranslateModule } from '@ngx-translate/core' -import { UiInputsModule } from '@geonetwork-ui/ui/inputs' -import { UiCatalogModule } from '@geonetwork-ui/ui/catalog' +import { + NavigationButtonComponent, + UiInputsModule, +} from '@geonetwork-ui/ui/inputs' import { Organization } from '@geonetwork-ui/common/domain/model/record' import { AsyncPipe, Location, NgIf } from '@angular/common' import { ErrorType, UiElementsModule } from '@geonetwork-ui/ui/elements' @@ -16,6 +18,8 @@ import { matFolderOutline, matOpenInNewOutline, } from '@ng-icons/material-icons/outline' +import { LanguageSwitcherComponent } from '@geonetwork-ui/ui/catalog' +import { matArrowBack } from '@ng-icons/material-icons/baseline' @Component({ selector: 'datahub-organization-header', @@ -26,14 +30,15 @@ import { imports: [ UiInputsModule, TranslateModule, - UiCatalogModule, NgIf, AsyncPipe, UiElementsModule, NgIconComponent, + LanguageSwitcherComponent, + NavigationButtonComponent, ], providers: [ - provideIcons({ matFolderOutline, matOpenInNewOutline }), + provideIcons({ matFolderOutline, matOpenInNewOutline, matArrowBack }), provideNgIconsConfig({ size: '1.5em', }), diff --git a/apps/datahub/src/app/record/header-record/header-record.component.spec.ts b/apps/datahub/src/app/record/header-record/header-record.component.spec.ts index 8381d548d5..5d30a6cfcf 100644 --- a/apps/datahub/src/app/record/header-record/header-record.component.spec.ts +++ b/apps/datahub/src/app/record/header-record/header-record.component.spec.ts @@ -1,12 +1,12 @@ -import { NO_ERRORS_SCHEMA } from '@angular/core' import { ComponentFixture, TestBed } from '@angular/core/testing' import { datasetRecordsFixture } from '@geonetwork-ui/common/fixtures' -import { MdViewFacade } from '@geonetwork-ui/feature/record' import { SearchService } from '@geonetwork-ui/feature/search' import { TranslateModule } from '@ngx-translate/core' -import { BehaviorSubject } from 'rxjs' import { HeaderRecordComponent } from './header-record.component' +import { MockBuilder, MockProvider } from 'ng-mocks' +import { DatasetRecord } from '@geonetwork-ui/common/domain/model/record' +import { MdViewFacade } from '@geonetwork-ui/feature/record' jest.mock('@geonetwork-ui/util/app-config', () => ({ getThemeConfig: () => ({ @@ -20,30 +20,20 @@ jest.mock('@geonetwork-ui/util/app-config', () => ({ }, })) -const searchServiceMock = { - updateFilters: jest.fn(), -} - -class MdViewFacadeMock { - mapApiLinks$ = new BehaviorSubject([]) - geoDataLinks$ = new BehaviorSubject([]) -} - describe('HeaderRecordComponent', () => { let component: HeaderRecordComponent let fixture: ComponentFixture + beforeEach(() => MockBuilder(HeaderRecordComponent)) + beforeEach(async () => { await TestBed.configureTestingModule({ - declarations: [HeaderRecordComponent], imports: [TranslateModule.forRoot()], - schemas: [NO_ERRORS_SCHEMA], providers: [ - { provide: SearchService, useValue: searchServiceMock }, - { - provide: MdViewFacade, - useClass: MdViewFacadeMock, - }, + MockProvider(MdViewFacade), + MockProvider(SearchService, { + updateFilters: jest.fn(), + }), ], }).compileComponents() }) @@ -53,7 +43,7 @@ describe('HeaderRecordComponent', () => { component = fixture.componentInstance component.metadata = { ...datasetRecordsFixture()[0], - } + } as DatasetRecord fixture.detectChanges() }) @@ -63,8 +53,9 @@ describe('HeaderRecordComponent', () => { describe('#back', () => { it('searchFilter updateSearch', () => { + const searchService = TestBed.inject(SearchService) component.back() - expect(searchServiceMock.updateFilters).toHaveBeenCalledWith({}) + expect(searchService.updateFilters).toHaveBeenCalledWith({}) }) }) }) diff --git a/apps/datahub/src/app/record/header-record/header-record.component.ts b/apps/datahub/src/app/record/header-record/header-record.component.ts index 9d92672674..dc0c3a481a 100644 --- a/apps/datahub/src/app/record/header-record/header-record.component.ts +++ b/apps/datahub/src/app/record/header-record/header-record.component.ts @@ -1,16 +1,39 @@ import { ChangeDetectionStrategy, Component, Input } from '@angular/core' -import { SearchService } from '@geonetwork-ui/feature/search' +import { + FavoriteStarComponent, + SearchService, +} from '@geonetwork-ui/feature/search' import { getGlobalConfig, getThemeConfig } from '@geonetwork-ui/util/app-config' import { DatasetRecord } from '@geonetwork-ui/common/domain/model/record' import { MdViewFacade } from '@geonetwork-ui/feature/record' import { combineLatest, map } from 'rxjs' -import { TranslateService } from '@ngx-translate/core' +import { TranslateModule, TranslateService } from '@ngx-translate/core' +import { + BadgeComponent, + NavigationButtonComponent, +} from '@geonetwork-ui/ui/inputs' +import { LanguageSwitcherComponent } from '@geonetwork-ui/ui/catalog' +import { CommonModule } from '@angular/common' +import { NgIcon, provideIcons } from '@ng-icons/core' +import { matLocationSearchingOutline } from '@ng-icons/material-icons/outline' +import { matArrowBack } from '@ng-icons/material-icons/baseline' @Component({ selector: 'datahub-header-record', templateUrl: './header-record.component.html', styleUrls: ['./header-record.component.css'], changeDetection: ChangeDetectionStrategy.OnPush, + standalone: true, + imports: [ + CommonModule, + NavigationButtonComponent, + LanguageSwitcherComponent, + TranslateModule, + FavoriteStarComponent, + BadgeComponent, + NgIcon, + ], + viewProviders: [provideIcons({ matLocationSearchingOutline, matArrowBack })], }) export class HeaderRecordComponent { @Input() metadata: DatasetRecord diff --git a/apps/datahub/src/app/record/record-apis/record-apis.component.spec.ts b/apps/datahub/src/app/record/record-apis/record-apis.component.spec.ts index 699b7e7b08..4581894788 100644 --- a/apps/datahub/src/app/record/record-apis/record-apis.component.spec.ts +++ b/apps/datahub/src/app/record/record-apis/record-apis.component.spec.ts @@ -4,7 +4,7 @@ import { TranslateModule } from '@ngx-translate/core' import { DatasetServiceDistribution } from '@geonetwork-ui/common/domain/model/record' import { MdViewFacade } from '@geonetwork-ui/feature/record' import { BehaviorSubject } from 'rxjs' -import { NO_ERRORS_SCHEMA } from '@angular/core' +import { MockBuilder } from 'ng-mocks' class MdViewFacadeMock { selectedApiLink$ = new BehaviorSubject([]) @@ -20,11 +20,11 @@ describe('RecordApisComponent', () => { let component: RecordApisComponent let fixture: ComponentFixture + beforeEach(() => MockBuilder(RecordApisComponent)) + beforeEach(async () => { await TestBed.configureTestingModule({ - declarations: [RecordApisComponent], imports: [TranslateModule.forRoot()], - schemas: [NO_ERRORS_SCHEMA], providers: [ { provide: MdViewFacade, diff --git a/apps/datahub/src/app/record/record-apis/record-apis.component.ts b/apps/datahub/src/app/record/record-apis/record-apis.component.ts index c89732aff9..d08c6717ba 100644 --- a/apps/datahub/src/app/record/record-apis/record-apis.component.ts +++ b/apps/datahub/src/app/record/record-apis/record-apis.component.ts @@ -8,12 +8,36 @@ import { import { DatasetServiceDistribution } from '@geonetwork-ui/common/domain/model/record' import { MdViewFacade } from '@geonetwork-ui/feature/record' import { CarouselComponent } from '@geonetwork-ui/ui/layout' +import { PreviousNextButtonsComponent } from '@geonetwork-ui/ui/inputs' +import { + ApiCardComponent, + RecordApiFormComponent, +} from '@geonetwork-ui/ui/elements' +import { CommonModule } from '@angular/common' +import { NgIcon, provideIcons } from '@ng-icons/core' +import { matCloseOutline } from '@ng-icons/material-icons/outline' +import { TranslateModule } from '@ngx-translate/core' @Component({ selector: 'datahub-record-apis', templateUrl: './record-apis.component.html', styleUrls: ['./record-apis.component.css'], changeDetection: ChangeDetectionStrategy.OnPush, + standalone: true, + imports: [ + CommonModule, + CarouselComponent, + PreviousNextButtonsComponent, + ApiCardComponent, + RecordApiFormComponent, + NgIcon, + TranslateModule, + ], + viewProviders: [ + provideIcons({ + matCloseOutline, + }), + ], }) export class RecordApisComponent implements OnInit { @ViewChild(CarouselComponent) carousel: CarouselComponent diff --git a/apps/datahub/src/app/record/record-downloads/record-downloads.component.spec.ts b/apps/datahub/src/app/record/record-downloads/record-downloads.component.spec.ts index faf9206080..4ac4a1fecd 100644 --- a/apps/datahub/src/app/record/record-downloads/record-downloads.component.spec.ts +++ b/apps/datahub/src/app/record/record-downloads/record-downloads.component.spec.ts @@ -6,11 +6,12 @@ import { } from '@angular/core/testing' import { BehaviorSubject, of, throwError } from 'rxjs' import { RecordDownloadsComponent } from './record-downloads.component' -import { Component, Input, NO_ERRORS_SCHEMA } from '@angular/core' import { By } from '@angular/platform-browser' import { DataService } from '@geonetwork-ui/feature/dataviz' import { DatasetOnlineResource } from '@geonetwork-ui/common/domain/model/record' import { MdViewFacade } from '@geonetwork-ui/feature/record' +import { MockBuilder } from 'ng-mocks' +import { PopupAlertComponent } from '@geonetwork-ui/ui/widgets' // This is used to work around a very weird bug when comparing URL objects would fail // if the `searchParams` of the object wasn't accessed beforehand in some cases... @@ -71,34 +72,15 @@ class DataServiceMock { ) } -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-download-item', - template: '
', -}) -export class MockDownloadsListItemComponent { - @Input() link: DatasetOnlineResource -} - -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-popup-alert', - template: '
', -}) -export class MockPopupAlertComponent {} - -describe('DataDownloadsComponent', () => { +describe('RecordDownloadsComponent', () => { let component: RecordDownloadsComponent let fixture: ComponentFixture let facade + beforeEach(() => MockBuilder(RecordDownloadsComponent)) + beforeEach(async () => { await TestBed.configureTestingModule({ - declarations: [ - RecordDownloadsComponent, - MockDownloadsListItemComponent, - MockPopupAlertComponent, - ], providers: [ { provide: MdViewFacade, @@ -109,7 +91,6 @@ describe('DataDownloadsComponent', () => { useClass: DataServiceMock, }, ], - schemas: [NO_ERRORS_SCHEMA], }).compileComponents() facade = TestBed.inject(MdViewFacade) }) @@ -162,7 +143,7 @@ describe('DataDownloadsComponent', () => { // disable error handling in UI it.skip('shows an error', () => { const popup = fixture.debugElement.query( - By.directive(MockPopupAlertComponent) + By.directive(PopupAlertComponent) ) expect(popup).toBeTruthy() }) diff --git a/apps/datahub/src/app/record/record-downloads/record-downloads.component.ts b/apps/datahub/src/app/record/record-downloads/record-downloads.component.ts index d21343e025..e9293d7584 100644 --- a/apps/datahub/src/app/record/record-downloads/record-downloads.component.ts +++ b/apps/datahub/src/app/record/record-downloads/record-downloads.component.ts @@ -8,12 +8,16 @@ import { DatasetServiceDistribution, } from '@geonetwork-ui/common/domain/model/record' import { MdViewFacade } from '@geonetwork-ui/feature/record' +import { CommonModule } from '@angular/common' +import { DownloadsListComponent } from '@geonetwork-ui/ui/elements' @Component({ selector: 'datahub-record-downloads', templateUrl: './record-downloads.component.html', styleUrls: ['./record-downloads.component.css'], changeDetection: ChangeDetectionStrategy.OnPush, + standalone: true, + imports: [CommonModule, DownloadsListComponent], }) export class RecordDownloadsComponent { constructor(public facade: MdViewFacade, private dataService: DataService) {} diff --git a/apps/datahub/src/app/record/record-metadata/record-metadata.component.spec.ts b/apps/datahub/src/app/record/record-metadata/record-metadata.component.spec.ts index d6363c9659..ddb562bcf2 100644 --- a/apps/datahub/src/app/record/record-metadata/record-metadata.component.spec.ts +++ b/apps/datahub/src/app/record/record-metadata/record-metadata.component.spec.ts @@ -1,30 +1,32 @@ -import { - Component, - EventEmitter, - Input, - NO_ERRORS_SCHEMA, - Output, -} from '@angular/core' import { ComponentFixture, TestBed } from '@angular/core/testing' import { By } from '@angular/platform-browser' import { SourcesService } from '@geonetwork-ui/feature/catalog' -import { MapManagerService } from '@geonetwork-ui/feature/map' import { SearchService } from '@geonetwork-ui/feature/search' -import { ErrorComponent, ErrorType } from '@geonetwork-ui/ui/elements' +import { + ErrorComponent, + ErrorType, + ImageOverlayPreviewComponent, + MetadataCatalogComponent, + MetadataContactComponent, + MetadataInfoComponent, +} from '@geonetwork-ui/ui/elements' import { TranslateModule } from '@ngx-translate/core' import { BehaviorSubject, of } from 'rxjs' import { RecordMetadataComponent } from './record-metadata.component' import { OrganizationsServiceInterface } from '@geonetwork-ui/common/domain/organizations.service.interface' import { datasetRecordsFixture } from '@geonetwork-ui/common/fixtures' -import { MdViewFacade } from '@geonetwork-ui/feature/record' import { - CatalogRecord, - DatasetRecord, - DatasetServiceDistribution, - Individual, - Keyword, - Organization, -} from '@geonetwork-ui/common/domain/model/record' + DataViewComponent, + DataViewShareComponent, + MapViewComponent, + MdViewFacade, +} from '@geonetwork-ui/feature/record' +import { MockBuilder } from 'ng-mocks' +import { RecordDownloadsComponent } from '../record-downloads/record-downloads.component' +import { RecordOtherlinksComponent } from '../record-otherlinks/record-otherlinks.component' +import { RecordApisComponent } from '../record-apis/record-apis.component' +import { RecordRelatedRecordsComponent } from '../record-related-records/record-related-records.component' +import { MatTab, MatTabGroup } from '@angular/material/tabs' const SAMPLE_RECORD = { ...datasetRecordsFixture()[0], @@ -64,100 +66,6 @@ class OrganisationsServiceMock { ) } -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-map-view', - template: '
', -}) -export class MockDataMapComponent {} - -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-data-view', - template: '
', -}) -export class MockDataViewComponent {} - -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-data-view-share', - template: '
', -}) -export class MockDataViewShareComponent {} - -@Component({ - selector: 'datahub-record-downloads', - template: '
', -}) -export class MockDataDownloadsComponent {} - -@Component({ - selector: 'datahub-record-otherlinks', - template: '
', -}) -export class MockDataOtherlinksComponent {} - -@Component({ - selector: 'datahub-record-apis', - template: '
', -}) -export class MockDataApisComponent {} - -@Component({ - selector: 'datahub-record-related-records', - template: '
', -}) -export class MockRelatedComponent {} - -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-metadata-info', - template: '
', -}) -export class MockMetadataInfoComponent { - @Input() metadata: Partial - @Input() incomplete: boolean - @Output() keyword = new EventEmitter() -} - -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-metadata-contact', - template: '
', -}) -export class MockMetadataContactComponent { - @Input() metadata: Partial - @Output() organizationClick = new EventEmitter() - @Output() contactClick = new EventEmitter() -} - -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-metadata-catalog', - template: '
', -}) -export class MockMetadataCatalogComponent { - @Input() sourceLabel: string -} - -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-record-api-form', - template: '
', -}) -export class MockRecordApiFormComponent { - @Input() apiLink: DatasetServiceDistribution -} -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-image-overlay-preview', - template: '
', -}) -export class MockImgOverlayPreviewComponent { - @Input() imageUrl: string - @Output() isPlaceholderShown = new EventEmitter() -} - describe('RecordMetadataComponent', () => { let component: RecordMetadataComponent let fixture: ComponentFixture @@ -165,35 +73,16 @@ describe('RecordMetadataComponent', () => { let searchService: SearchService let sourcesService: SourcesService + beforeEach(() => MockBuilder(RecordMetadataComponent)) + beforeEach(async () => { await TestBed.configureTestingModule({ - declarations: [ - RecordMetadataComponent, - MockDataMapComponent, - MockDataViewComponent, - MockDataViewShareComponent, - MockDataDownloadsComponent, - MockDataOtherlinksComponent, - MockDataApisComponent, - MockRelatedComponent, - ErrorComponent, - MockMetadataInfoComponent, - MockMetadataCatalogComponent, - MockMetadataContactComponent, - MockRecordApiFormComponent, - MockImgOverlayPreviewComponent, - ], - schemas: [NO_ERRORS_SCHEMA], imports: [TranslateModule.forRoot()], providers: [ { provide: MdViewFacade, useClass: MdViewFacadeMock, }, - { - provide: MapManagerService, - useValue: {}, - }, { provide: SearchService, useClass: SearchServiceMock, @@ -224,21 +113,21 @@ describe('RecordMetadataComponent', () => { }) describe('about', () => { - let metadataInfo: MockMetadataInfoComponent - let metadataContact: MockMetadataContactComponent - let catalogComponent: MockMetadataCatalogComponent + let metadataInfo: MetadataInfoComponent + let metadataContact: MetadataContactComponent + let catalogComponent: MetadataCatalogComponent beforeEach(() => { facade.isPresent$.next(true) fixture.detectChanges() metadataInfo = fixture.debugElement.query( - By.directive(MockMetadataInfoComponent) + By.directive(MetadataInfoComponent) ).componentInstance metadataContact = fixture.debugElement.query( - By.directive(MockMetadataContactComponent) + By.directive(MetadataContactComponent) ).componentInstance catalogComponent = fixture.debugElement.query( - By.directive(MockMetadataCatalogComponent) + By.directive(MetadataCatalogComponent) ).componentInstance }) describe('if metadata present', () => { @@ -260,7 +149,7 @@ describe('RecordMetadataComponent', () => { facade.isPresent$.next(false) fixture.detectChanges() metadataInfo = fixture.debugElement.query( - By.directive(MockMetadataInfoComponent) + By.directive(MetadataInfoComponent) ).componentInstance }) it('shows a placeholder', () => { @@ -269,31 +158,29 @@ describe('RecordMetadataComponent', () => { }) it('does not display the metadata contact component', () => { expect( - fixture.debugElement.query(By.directive(MockMetadataContactComponent)) + fixture.debugElement.query(By.directive(MetadataContactComponent)) ).toBeFalsy() }) it('does not display the metadata catalog component', () => { expect( - fixture.debugElement.query(By.directive(MockMetadataCatalogComponent)) + fixture.debugElement.query(By.directive(MetadataCatalogComponent)) ).toBeFalsy() }) it('does not display the image overlay preview', () => { expect( - fixture.debugElement.query( - By.directive(MockImgOverlayPreviewComponent) - ) + fixture.debugElement.query(By.directive(ImageOverlayPreviewComponent)) ).toBeFalsy() }) }) describe('Image Overlay Preview', () => { describe('if metadata without overview', () => { - let imgOverlayPreview: MockImgOverlayPreviewComponent + let imgOverlayPreview: ImageOverlayPreviewComponent beforeEach(() => { facade.isPresent$.next(true) facade.metadata$.next({}) fixture.detectChanges() imgOverlayPreview = fixture.debugElement.query( - By.directive(MockImgOverlayPreviewComponent) + By.directive(ImageOverlayPreviewComponent) ).componentInstance }) it('should send undefined as imageUrl to imgOverlayPreview component', () => { @@ -302,12 +189,12 @@ describe('RecordMetadataComponent', () => { }) }) describe('if metadata with overview', () => { - let imgOverlayPreview: MockImgOverlayPreviewComponent + let imgOverlayPreview: ImageOverlayPreviewComponent beforeEach(() => { facade.isPresent$.next(true) fixture.detectChanges() imgOverlayPreview = fixture.debugElement.query( - By.directive(MockImgOverlayPreviewComponent) + By.directive(ImageOverlayPreviewComponent) ).componentInstance }) describe('and url defined', () => { @@ -347,18 +234,18 @@ describe('RecordMetadataComponent', () => { beforeEach(() => { facade.dataLinks$.next(['link']) fixture.detectChanges() - mapTab = fixture.debugElement.queryAll(By.css('mat-tab'))[0] - tabGroup = fixture.debugElement.queryAll(By.css('mat-tab-group'))[0] + mapTab = fixture.debugElement.queryAll(By.directive(MatTab))[0] + tabGroup = fixture.debugElement.queryAll(By.directive(MatTabGroup))[0] }) it('renders preview, map tab is disabled', () => { - expect(mapTab.nativeNode.disabled).toBe(true) + expect(mapTab.componentInstance.disabled).toBe(true) }) it('renders preview, table tab is selected', () => { - expect(tabGroup.nativeNode.selectedIndex).toBe(1) + expect(tabGroup.componentInstance.selectedIndex).toBe(1) }) it('does not render map component', () => { expect( - fixture.debugElement.query(By.directive(MockDataMapComponent)) + fixture.debugElement.query(By.directive(MapViewComponent)) ).toBeFalsy() }) }) @@ -366,14 +253,14 @@ describe('RecordMetadataComponent', () => { beforeEach(() => { facade.mapApiLinks$.next(['link']) fixture.detectChanges() - mapTab = fixture.debugElement.queryAll(By.css('mat-tab'))[0] + mapTab = fixture.debugElement.queryAll(By.directive(MatTab))[0] }) it('renders preview, map tab is enabled', () => { - expect(mapTab.nativeNode.disabled).toBe(false) + expect(mapTab.componentInstance.disabled).toBe(false) }) it('renders map component', () => { expect( - fixture.debugElement.query(By.directive(MockDataMapComponent)) + fixture.debugElement.query(By.directive(MapViewComponent)) ).toBeTruthy() }) }) @@ -382,14 +269,14 @@ describe('RecordMetadataComponent', () => { facade.geoDataLinksWithGeometry$.next(['link']) facade.geoDataLinks$.next(['link']) fixture.detectChanges() - mapTab = fixture.debugElement.queryAll(By.css('mat-tab'))[0] + mapTab = fixture.debugElement.queryAll(By.directive(MatTab))[0] }) it('renders preview, map tab is enabled', () => { - expect(mapTab.nativeNode.disabled).toBe(false) + expect(mapTab.componentInstance.disabled).toBe(false) }) it('renders map component', () => { expect( - fixture.debugElement.query(By.directive(MockDataMapComponent)) + fixture.debugElement.query(By.directive(MapViewComponent)) ).toBeTruthy() }) }) @@ -404,27 +291,27 @@ describe('RecordMetadataComponent', () => { facade.dataLinks$.next(null) facade.geoDataLinksWithGeometry$.next(null) fixture.detectChanges() - tableTab = fixture.debugElement.queryAll(By.css('mat-tab'))[1] - chartTab = fixture.debugElement.queryAll(By.css('mat-tab'))[2] - tabGroup = fixture.debugElement.queryAll(By.css('mat-tab-group'))[0] + tableTab = fixture.debugElement.queryAll(By.directive(MatTab))[1] + chartTab = fixture.debugElement.queryAll(By.directive(MatTab))[2] + tabGroup = fixture.debugElement.queryAll(By.directive(MatTabGroup))[0] }) it('renders preview, table tab is disabled', () => { - expect(tableTab.nativeNode.disabled).toBe(true) + expect(tableTab.componentInstance.disabled).toBe(true) }) it('renders preview, chart tab is disabled', () => { - expect(chartTab.nativeNode.disabled).toBe(true) + expect(chartTab.componentInstance.disabled).toBe(true) }) it('renders preview, map tab is selected', () => { - expect(tabGroup.nativeNode.selectedIndex).toBe(0) + expect(tabGroup.componentInstance.selectedIndex).toBe(0) }) it('does not render any data view component', () => { expect( - fixture.debugElement.query(By.directive(MockDataViewComponent)) + fixture.debugElement.query(By.directive(DataViewComponent)) ).toBeFalsy() }) it('does render the permalink component', () => { expect( - fixture.debugElement.query(By.directive(MockDataViewShareComponent)) + fixture.debugElement.query(By.directive(DataViewShareComponent)) ).toBeTruthy() }) }) @@ -432,24 +319,23 @@ describe('RecordMetadataComponent', () => { beforeEach(() => { facade.dataLinks$.next(['link']) fixture.detectChanges() - tableTab = fixture.debugElement.queryAll(By.css('mat-tab'))[1] - chartTab = fixture.debugElement.queryAll(By.css('mat-tab'))[2] + tableTab = fixture.debugElement.queryAll(By.directive(MatTab))[1] + chartTab = fixture.debugElement.queryAll(By.directive(MatTab))[2] }) it('renders preview, table tab is enabled', () => { - expect(tableTab.nativeNode.disabled).toBe(false) + expect(tableTab.componentInstance.disabled).toBe(false) }) it('renders preview, chart tab is enabled', () => { - expect(chartTab.nativeNode.disabled).toBe(false) + expect(chartTab.componentInstance.disabled).toBe(false) }) it('renders two data view components (for table and chart tabs)', () => { expect( - fixture.debugElement.queryAll(By.directive(MockDataViewComponent)) - .length + fixture.debugElement.queryAll(By.directive(DataViewComponent)).length ).toEqual(2) }) it('does render the permalink component', () => { expect( - fixture.debugElement.query(By.directive(MockDataViewShareComponent)) + fixture.debugElement.query(By.directive(DataViewShareComponent)) ).toBeTruthy() }) describe('when selectedView$ is chart', () => { @@ -459,7 +345,7 @@ describe('RecordMetadataComponent', () => { }) it('renders the permalink component', () => { expect( - fixture.debugElement.query(By.directive(MockDataViewShareComponent)) + fixture.debugElement.query(By.directive(DataViewShareComponent)) ).toBeTruthy() }) }) @@ -468,19 +354,18 @@ describe('RecordMetadataComponent', () => { beforeEach(() => { facade.geoDataLinks$.next(['link']) fixture.detectChanges() - tableTab = fixture.debugElement.queryAll(By.css('mat-tab'))[1] - chartTab = fixture.debugElement.queryAll(By.css('mat-tab'))[2] + tableTab = fixture.debugElement.queryAll(By.directive(MatTab))[1] + chartTab = fixture.debugElement.queryAll(By.directive(MatTab))[2] }) it('renders preview, table tab is enabled', () => { - expect(tableTab.nativeNode.disabled).toBe(false) + expect(tableTab.componentInstance.disabled).toBe(false) }) it('renders preview, chart tab is enabled', () => { - expect(chartTab.nativeNode.disabled).toBe(false) + expect(chartTab.componentInstance.disabled).toBe(false) }) it('renders two data view components (for table and chart tabs)', () => { expect( - fixture.debugElement.queryAll(By.directive(MockDataViewComponent)) - .length + fixture.debugElement.queryAll(By.directive(DataViewComponent)).length ).toEqual(2) }) }) @@ -491,7 +376,7 @@ describe('RecordMetadataComponent', () => { beforeEach(() => { fixture.detectChanges() downloadsComponent = fixture.debugElement.query( - By.directive(MockDataDownloadsComponent) + By.directive(RecordDownloadsComponent) ) }) it('download component does not render', () => { @@ -503,7 +388,7 @@ describe('RecordMetadataComponent', () => { facade.downloadLinks$.next(['link']) fixture.detectChanges() downloadsComponent = fixture.debugElement.query( - By.directive(MockDataDownloadsComponent) + By.directive(RecordDownloadsComponent) ) }) it('download component renders', () => { @@ -517,7 +402,7 @@ describe('RecordMetadataComponent', () => { beforeEach(() => { fixture.detectChanges() otherLinksComponent = fixture.debugElement.query( - By.directive(MockDataOtherlinksComponent) + By.directive(RecordOtherlinksComponent) ) }) it('otherlink component does not render', () => { @@ -529,7 +414,7 @@ describe('RecordMetadataComponent', () => { facade.otherLinks$.next(['link']) fixture.detectChanges() otherLinksComponent = fixture.debugElement.query( - By.directive(MockDataOtherlinksComponent) + By.directive(RecordOtherlinksComponent) ) }) it('otherlink component renders', () => { @@ -543,7 +428,7 @@ describe('RecordMetadataComponent', () => { beforeEach(() => { fixture.detectChanges() apiComponent = fixture.debugElement.query( - By.directive(MockDataApisComponent) + By.directive(RecordApisComponent) ) }) it('API component does not render', () => { @@ -555,7 +440,7 @@ describe('RecordMetadataComponent', () => { facade.apiLinks$.next(['link']) fixture.detectChanges() apiComponent = fixture.debugElement.query( - By.directive(MockDataApisComponent) + By.directive(RecordApisComponent) ) }) it('API component renders', () => { @@ -571,7 +456,7 @@ describe('RecordMetadataComponent', () => { facade.related$.next([]) fixture.detectChanges() relatedComponent = fixture.debugElement.query( - By.directive(MockRelatedComponent) + By.directive(RecordRelatedRecordsComponent) ) }) it('Related component does not render', () => { @@ -583,7 +468,7 @@ describe('RecordMetadataComponent', () => { facade.related$.next([{ title: 'title' }]) fixture.detectChanges() relatedComponent = fixture.debugElement.query( - By.directive(MockRelatedComponent) + By.directive(RecordRelatedRecordsComponent) ) }) it('Related component renders', () => { diff --git a/apps/datahub/src/app/record/record-metadata/record-metadata.component.ts b/apps/datahub/src/app/record/record-metadata/record-metadata.component.ts index 3d485c2c0f..90c0227e92 100644 --- a/apps/datahub/src/app/record/record-metadata/record-metadata.component.ts +++ b/apps/datahub/src/app/record/record-metadata/record-metadata.component.ts @@ -1,7 +1,15 @@ import { ChangeDetectionStrategy, Component, Input } from '@angular/core' import { SourcesService } from '@geonetwork-ui/feature/catalog' import { SearchService } from '@geonetwork-ui/feature/search' -import { ErrorType } from '@geonetwork-ui/ui/elements' +import { + ErrorComponent, + ErrorType, + ImageOverlayPreviewComponent, + MetadataCatalogComponent, + MetadataContactComponent, + MetadataInfoComponent, + MetadataQualityComponent, +} from '@geonetwork-ui/ui/elements' import { BehaviorSubject, combineLatest } from 'rxjs' import { filter, map, mergeMap, startWith } from 'rxjs/operators' import { OrganizationsServiceInterface } from '@geonetwork-ui/common/domain/organizations.service.interface' @@ -9,13 +17,46 @@ import { Keyword, Organization, } from '@geonetwork-ui/common/domain/model/record' -import { MdViewFacade } from '@geonetwork-ui/feature/record' +import { + DataViewComponent, + DataViewShareComponent, + MapViewComponent, + MdViewFacade, +} from '@geonetwork-ui/feature/record' +import { CommonModule } from '@angular/common' +import { MatTabsModule } from '@angular/material/tabs' +import { RecordUserFeedbacksComponent } from '../record-user-feedbacks/record-user-feedbacks.component' +import { RecordDownloadsComponent } from '../record-downloads/record-downloads.component' +import { RecordApisComponent } from '../record-apis/record-apis.component' +import { RecordOtherlinksComponent } from '../record-otherlinks/record-otherlinks.component' +import { RecordRelatedRecordsComponent } from '../record-related-records/record-related-records.component' +import { TranslateModule } from '@ngx-translate/core' @Component({ selector: 'datahub-record-metadata', templateUrl: './record-metadata.component.html', styleUrls: ['./record-metadata.component.css'], changeDetection: ChangeDetectionStrategy.OnPush, + standalone: true, + imports: [ + CommonModule, + ImageOverlayPreviewComponent, + MatTabsModule, + ErrorComponent, + RecordUserFeedbacksComponent, + RecordDownloadsComponent, + RecordApisComponent, + RecordOtherlinksComponent, + DataViewShareComponent, + MetadataInfoComponent, + MetadataContactComponent, + MetadataQualityComponent, + MetadataCatalogComponent, + RecordRelatedRecordsComponent, + DataViewComponent, + MapViewComponent, + TranslateModule, + ], }) export class RecordMetadataComponent { @Input() metadataQualityDisplay: boolean diff --git a/apps/datahub/src/app/record/record-otherlinks/record-otherlinks.component.spec.ts b/apps/datahub/src/app/record/record-otherlinks/record-otherlinks.component.spec.ts index bc4d48e632..34d39fa230 100644 --- a/apps/datahub/src/app/record/record-otherlinks/record-otherlinks.component.spec.ts +++ b/apps/datahub/src/app/record/record-otherlinks/record-otherlinks.component.spec.ts @@ -2,6 +2,7 @@ import { ComponentFixture, TestBed } from '@angular/core/testing' import { BehaviorSubject } from 'rxjs' import { RecordOtherlinksComponent } from './record-otherlinks.component' import { MdViewFacade } from '@geonetwork-ui/feature/record' +import { MockBuilder, MockProvider } from 'ng-mocks' class MdViewFacadeMock { otherLinks$ = new BehaviorSubject([]) @@ -10,10 +11,15 @@ describe('RecordOtherlinksComponent', () => { let component: RecordOtherlinksComponent let fixture: ComponentFixture + beforeEach(() => MockBuilder(RecordOtherlinksComponent)) + beforeEach(async () => { await TestBed.configureTestingModule({ - declarations: [RecordOtherlinksComponent], - providers: [{ provide: MdViewFacade, useClass: MdViewFacadeMock }], + providers: [ + MockProvider(MdViewFacade, { + otherLinks$: new BehaviorSubject([]), + }), + ], }).compileComponents() }) diff --git a/apps/datahub/src/app/record/record-otherlinks/record-otherlinks.component.ts b/apps/datahub/src/app/record/record-otherlinks/record-otherlinks.component.ts index 97a39cf5a8..cef2c555c7 100644 --- a/apps/datahub/src/app/record/record-otherlinks/record-otherlinks.component.ts +++ b/apps/datahub/src/app/record/record-otherlinks/record-otherlinks.component.ts @@ -7,12 +7,27 @@ import { } from '@angular/core' import { MdViewFacade } from '@geonetwork-ui/feature/record' import { BlockListComponent, CarouselComponent } from '@geonetwork-ui/ui/layout' +import { PreviousNextButtonsComponent } from '@geonetwork-ui/ui/inputs' +import { CommonModule } from '@angular/common' +import { LinkCardComponent } from '@geonetwork-ui/ui/elements' +import { LetDirective } from '@ngrx/component' +import { TranslateModule } from '@ngx-translate/core' @Component({ selector: 'datahub-record-otherlinks', templateUrl: './record-otherlinks.component.html', styleUrls: ['./record-otherlinks.component.css'], changeDetection: ChangeDetectionStrategy.OnPush, + standalone: true, + imports: [ + CommonModule, + PreviousNextButtonsComponent, + BlockListComponent, + LinkCardComponent, + CarouselComponent, + LetDirective, + TranslateModule, + ], }) export class RecordOtherlinksComponent implements AfterViewInit { otherLinks$ = this.facade.otherLinks$ diff --git a/apps/datahub/src/app/record/record-page/record-page.component.spec.ts b/apps/datahub/src/app/record/record-page/record-page.component.spec.ts index a13f001ce8..723866b8fa 100644 --- a/apps/datahub/src/app/record/record-page/record-page.component.spec.ts +++ b/apps/datahub/src/app/record/record-page/record-page.component.spec.ts @@ -1,28 +1,18 @@ -import { NO_ERRORS_SCHEMA } from '@angular/core' import { ComponentFixture, TestBed } from '@angular/core/testing' import { MdViewFacade } from '@geonetwork-ui/feature/record' -import { of } from 'rxjs' import { RecordPageComponent } from './record-page.component' - -class MdViewFacadeMock { - metadata$ = of() -} +import { MockBuilder, MockProvider } from 'ng-mocks' describe('RecordPageComponent', () => { let component: RecordPageComponent let fixture: ComponentFixture + beforeEach(() => MockBuilder(RecordPageComponent)) + beforeEach(async () => { await TestBed.configureTestingModule({ - declarations: [RecordPageComponent], - schemas: [NO_ERRORS_SCHEMA], - providers: [ - { - provide: MdViewFacade, - useClass: MdViewFacadeMock, - }, - ], + providers: [MockProvider(MdViewFacade)], }).compileComponents() }) diff --git a/apps/datahub/src/app/record/record-page/record-page.component.ts b/apps/datahub/src/app/record/record-page/record-page.component.ts index dbe43824ce..074eea1d9e 100644 --- a/apps/datahub/src/app/record/record-page/record-page.component.ts +++ b/apps/datahub/src/app/record/record-page/record-page.component.ts @@ -1,15 +1,20 @@ import { ChangeDetectionStrategy, Component, OnDestroy } from '@angular/core' import { MdViewFacade } from '@geonetwork-ui/feature/record' import { - MetadataQualityConfig, getMetadataQualityConfig, + MetadataQualityConfig, } from '@geonetwork-ui/util/app-config' +import { RecordMetadataComponent } from '../record-metadata/record-metadata.component' +import { HeaderRecordComponent } from '../header-record/header-record.component' +import { CommonModule } from '@angular/common' @Component({ selector: 'datahub-record-page', templateUrl: './record-page.component.html', styleUrls: ['./record-page.component.css'], changeDetection: ChangeDetectionStrategy.OnPush, + standalone: true, + imports: [CommonModule, RecordMetadataComponent, HeaderRecordComponent], }) export class RecordPageComponent implements OnDestroy { metadataQualityDisplay: boolean diff --git a/apps/datahub/src/app/record/record-related-records/record-related-records.component.spec.ts b/apps/datahub/src/app/record/record-related-records/record-related-records.component.spec.ts index b5e95e7938..b51cfff4c3 100644 --- a/apps/datahub/src/app/record/record-related-records/record-related-records.component.spec.ts +++ b/apps/datahub/src/app/record/record-related-records/record-related-records.component.spec.ts @@ -1,16 +1,13 @@ import { ComponentFixture, TestBed } from '@angular/core/testing' import { RecordRelatedRecordsComponent } from './record-related-records.component' +import { MockBuilder } from 'ng-mocks' describe('RelatedRecordsComponent', () => { let component: RecordRelatedRecordsComponent let fixture: ComponentFixture - beforeEach(async () => { - await TestBed.configureTestingModule({ - declarations: [RecordRelatedRecordsComponent], - }).compileComponents() - }) + beforeEach(() => MockBuilder(RecordRelatedRecordsComponent)) beforeEach(() => { fixture = TestBed.createComponent(RecordRelatedRecordsComponent) diff --git a/apps/datahub/src/app/record/record-related-records/record-related-records.component.ts b/apps/datahub/src/app/record/record-related-records/record-related-records.component.ts index d82b51ff1f..d2802b425b 100644 --- a/apps/datahub/src/app/record/record-related-records/record-related-records.component.ts +++ b/apps/datahub/src/app/record/record-related-records/record-related-records.component.ts @@ -1,11 +1,16 @@ import { ChangeDetectionStrategy, Component, Input } from '@angular/core' import { CatalogRecord } from '@geonetwork-ui/common/domain/model/record' +import { RelatedRecordCardComponent } from '@geonetwork-ui/ui/elements' +import { CommonModule } from '@angular/common' +import { TranslateModule } from '@ngx-translate/core' @Component({ selector: 'datahub-record-related-records', templateUrl: './record-related-records.component.html', styleUrls: ['./record-related-records.component.css'], changeDetection: ChangeDetectionStrategy.OnPush, + standalone: true, + imports: [CommonModule, RelatedRecordCardComponent, TranslateModule], }) export class RecordRelatedRecordsComponent { @Input() records: CatalogRecord[] diff --git a/apps/datahub/src/app/record/record-user-feedbacks/record-user-feedbacks.component.spec.ts b/apps/datahub/src/app/record/record-user-feedbacks/record-user-feedbacks.component.spec.ts index 048b1322fb..0fc6088674 100644 --- a/apps/datahub/src/app/record/record-user-feedbacks/record-user-feedbacks.component.spec.ts +++ b/apps/datahub/src/app/record/record-user-feedbacks/record-user-feedbacks.component.spec.ts @@ -8,11 +8,7 @@ import { RecordUserFeedbacksComponent } from './record-user-feedbacks.component' import { TranslateModule } from '@ngx-translate/core' import { MdViewFacade } from '@geonetwork-ui/feature/record' import { BehaviorSubject, of, Subject } from 'rxjs' -import { - ChangeDetectionStrategy, - ChangeDetectorRef, - NO_ERRORS_SCHEMA, -} from '@angular/core' +import { ChangeDetectionStrategy } from '@angular/core' import { PlatformServiceInterface } from '@geonetwork-ui/common/domain/platform.service.interface' import { barbieUserFixture, @@ -24,8 +20,9 @@ import { UserFeedbackViewModel, } from '@geonetwork-ui/common/domain/model/record' import { Gn4PlatformMapper } from '@geonetwork-ui/api/repository' +import { MockBuilder, MockProvider } from 'ng-mocks' -describe('RelatedRecordsComponent', () => { +describe('RecordUserFeedbacksComponent', () => { const allUserFeedbacks = someUserFeedbacksFixture() let mockDestroy$: Subject @@ -48,10 +45,6 @@ describe('RelatedRecordsComponent', () => { }, } - const changeDetectorRefMock: Partial = { - markForCheck: jest.fn(), - } - const platformServiceInterfaceMock: Partial = { getUserFeedbacks: jest.fn(), getMe: jest.fn(() => new BehaviorSubject(activeUser)), @@ -60,30 +53,17 @@ describe('RelatedRecordsComponent', () => { let component: RecordUserFeedbacksComponent let fixture: ComponentFixture + beforeEach(() => MockBuilder(RecordUserFeedbacksComponent)) + beforeEach(async () => { mockDestroy$ = new Subject() await TestBed.configureTestingModule({ - declarations: [RecordUserFeedbacksComponent], imports: [TranslateModule.forRoot()], - schemas: [NO_ERRORS_SCHEMA], providers: [ - { - provide: MdViewFacade, - useValue: mdViewFacadeMock, - }, - { - provide: ChangeDetectorRef, - useValue: changeDetectorRefMock, - }, - { - provide: PlatformServiceInterface, - useValue: platformServiceInterfaceMock, - }, - { - provide: Gn4PlatformMapper, - useValue: gn4PlatformMapperMock, - }, + MockProvider(MdViewFacade, mdViewFacadeMock), + MockProvider(PlatformServiceInterface, platformServiceInterfaceMock), + MockProvider(Gn4PlatformMapper, gn4PlatformMapperMock), ], }) .overrideComponent(RecordUserFeedbacksComponent, { diff --git a/apps/datahub/src/app/record/record-user-feedbacks/record-user-feedbacks.component.ts b/apps/datahub/src/app/record/record-user-feedbacks/record-user-feedbacks.component.ts index 9e7d92356f..033233ca64 100644 --- a/apps/datahub/src/app/record/record-user-feedbacks/record-user-feedbacks.component.ts +++ b/apps/datahub/src/app/record/record-user-feedbacks/record-user-feedbacks.component.ts @@ -14,11 +14,24 @@ import { } from '@geonetwork-ui/common/domain/model/record' import { PlatformServiceInterface } from '@geonetwork-ui/common/domain/platform.service.interface' import { UserModel } from '@geonetwork-ui/common/domain/model/user' -import { DropdownChoice } from '@geonetwork-ui/ui/inputs' +import { + ButtonComponent, + DropdownChoice, + DropdownSelectorComponent, + TextAreaComponent, +} from '@geonetwork-ui/ui/inputs' import { MdViewFacade } from '@geonetwork-ui/feature/record' -import { TranslateService } from '@ngx-translate/core' +import { TranslateModule, TranslateService } from '@ngx-translate/core' import { AuthService, Gn4PlatformMapper } from '@geonetwork-ui/api/repository' -import { UserApiModel } from '@geonetwork-ui/data-access/gn4' +import { SpinningLoaderComponent } from '@geonetwork-ui/ui/widgets' +import { NgIcon, provideIcons } from '@ng-icons/core' +import { + matAccountBoxOutline, + matEditOutline, + matSendOutline, +} from '@ng-icons/material-icons/outline' +import { CommonModule } from '@angular/common' +import { UserFeedbackItemComponent } from '@geonetwork-ui/ui/elements' type UserFeedbackSortingFunction = ( userFeedbackA: UserFeedback, @@ -30,6 +43,24 @@ type UserFeedbackSortingFunction = ( templateUrl: './record-user-feedbacks.component.html', styleUrls: ['./record-user-feedbacks.component.css'], changeDetection: ChangeDetectionStrategy.OnPush, + standalone: true, + imports: [ + CommonModule, + DropdownSelectorComponent, + SpinningLoaderComponent, + NgIcon, + ButtonComponent, + TextAreaComponent, + TranslateModule, + UserFeedbackItemComponent, + ], + viewProviders: [ + provideIcons({ + matEditOutline, + matSendOutline, + matAccountBoxOutline, + }), + ], }) export class RecordUserFeedbacksComponent implements OnInit, OnDestroy { @Input() organisationName$: Observable diff --git a/apps/metadata-editor/src/app/records/records-list.component.spec.ts b/apps/metadata-editor/src/app/records/records-list.component.spec.ts index 2b1621ed6f..2a277e8594 100644 --- a/apps/metadata-editor/src/app/records/records-list.component.spec.ts +++ b/apps/metadata-editor/src/app/records/records-list.component.spec.ts @@ -1,49 +1,21 @@ import { ComponentFixture, TestBed } from '@angular/core/testing' -import { SearchFacade, SearchService } from '@geonetwork-ui/feature/search' +import { + ResultsTableContainerComponent, + SearchFacade, + SearchService, +} from '@geonetwork-ui/feature/search' import { allSearchFields, RecordsListComponent } from './records-list.component' -import { Component, EventEmitter, Input, Output } from '@angular/core' -import { CatalogRecord } from '@geonetwork-ui/common/domain/model/record' import { By } from '@angular/platform-browser' import { Router } from '@angular/router' import { BehaviorSubject } from 'rxjs' -import { CommonModule } from '@angular/common' import { datasetRecordsFixture } from '@geonetwork-ui/common/fixtures' +import { MockBuilder } from 'ng-mocks' +import { PaginationButtonsComponent } from '@geonetwork-ui/ui/elements' const results = [{ md: true }] const currentPage = 5 const totalPages = 25 -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-results-table-container', - template: '', - standalone: true, -}) -export class ResultsTableContainerComponent { - @Output() recordClick = new EventEmitter() - @Output() duplicateRecord = new EventEmitter() -} - -@Component({ - // eslint-disable-next-line @angular-eslint/component-selector - selector: 'gn-ui-pagination-buttons', - template: '', - standalone: true, -}) -export class PaginationButtonsComponent { - @Input() currentPage = 1 - @Input() totalPages = 1 - @Input() hideButton = false - @Output() newCurrentPageEvent = new EventEmitter() -} - -@Component({ - selector: 'md-editor-records-count', - template: '', - standalone: true, -}) -export class RecordsCountComponent {} - class SearchFacadeMock { results$ = new BehaviorSubject(results) currentPage$ = new BehaviorSubject(currentPage) @@ -68,6 +40,8 @@ describe('RecordsListComponent', () => { let searchService: SearchService let searchFacade: SearchFacade + beforeEach(() => MockBuilder(RecordsListComponent)) + beforeEach(() => { TestBed.configureTestingModule({ providers: [ @@ -84,15 +58,6 @@ describe('RecordsListComponent', () => { useClass: SearchServiceMock, }, ], - }).overrideComponent(RecordsListComponent, { - set: { - imports: [ - CommonModule, - ResultsTableContainerComponent, - PaginationButtonsComponent, - RecordsCountComponent, - ], - }, }) router = TestBed.inject(Router) searchService = TestBed.inject(SearchService) diff --git a/apps/metadata-editor/src/app/records/records-list.component.ts b/apps/metadata-editor/src/app/records/records-list.component.ts index 83b3b75ab7..8f53f6d992 100644 --- a/apps/metadata-editor/src/app/records/records-list.component.ts +++ b/apps/metadata-editor/src/app/records/records-list.component.ts @@ -8,10 +8,12 @@ import { SearchService, } from '@geonetwork-ui/feature/search' import { UiSearchModule } from '@geonetwork-ui/ui/search' -import { UiElementsModule } from '@geonetwork-ui/ui/elements' +import { + PaginationButtonsComponent, + UiElementsModule, +} from '@geonetwork-ui/ui/elements' import { TranslateModule } from '@ngx-translate/core' import { UiInputsModule } from '@geonetwork-ui/ui/inputs' -import { RecordsCountComponent } from './records-count/records-count.component' export const allSearchFields = [ 'uuid', @@ -36,7 +38,7 @@ export const allSearchFields = [ TranslateModule, ResultsTableContainerComponent, UiInputsModule, - RecordsCountComponent, + PaginationButtonsComponent, ], }) export class RecordsListComponent implements OnInit { diff --git a/libs/feature/catalog/src/lib/organisations/organisations.component.spec.ts b/libs/feature/catalog/src/lib/organisations/organisations.component.spec.ts index be631b6959..8844d1ccb0 100644 --- a/libs/feature/catalog/src/lib/organisations/organisations.component.spec.ts +++ b/libs/feature/catalog/src/lib/organisations/organisations.component.spec.ts @@ -1,55 +1,21 @@ import { ChangeDetectionStrategy, - Component, DebugElement, - EventEmitter, - Input, NO_ERRORS_SCHEMA, - Output, } from '@angular/core' import { ComponentFixture, TestBed } from '@angular/core/testing' import { By } from '@angular/platform-browser' -import { ContentGhostComponent } from '@geonetwork-ui/ui/elements' -import { Organization } from '@geonetwork-ui/common/domain/model/record' import { firstValueFrom, of } from 'rxjs' import { someOrganizationsFixture } from '@geonetwork-ui/common/fixtures' import { OrganisationsComponent } from './organisations.component' import { OrganizationsServiceInterface } from '@geonetwork-ui/common/domain/organizations.service.interface' - -@Component({ - selector: 'gn-ui-organisations-filter', - template: '
', -}) -class OrganisationsFilterMockComponent { - @Output() sortBy = new EventEmitter() -} -@Component({ - selector: 'gn-ui-organisation-preview', - template: '
', -}) -class OrganisationPreviewMockComponent { - @Input() organization: Organization - @Output() clickedOrganization = new EventEmitter() -} - -@Component({ - selector: 'gn-ui-organisations-result', - template: '
', -}) -class OrganisationsResultMockComponent { - @Input() hits: number - @Input() total: number -} - -@Component({ - selector: 'gn-ui-pagination', - template: '
', -}) -class PaginationMockComponent { - @Input() currentPage: number - @Input() nPages: number - @Output() newCurrentPageEvent = new EventEmitter() -} +import { MockBuilder } from 'ng-mocks' +import { + OrganisationPreviewComponent, + OrganisationsFilterComponent, + OrganisationsResultComponent, +} from '@geonetwork-ui/ui/catalog' +import { PaginationComponent } from '@geonetwork-ui/ui/elements' class OrganisationsServiceMock { organisations$ = of(someOrganizationsFixture()) @@ -70,16 +36,10 @@ describe('OrganisationsComponent', () => { let fixture: ComponentFixture let de: DebugElement + beforeEach(() => MockBuilder(OrganisationsComponent)) + beforeEach(async () => { await TestBed.configureTestingModule({ - declarations: [ - OrganisationsComponent, - OrganisationsFilterMockComponent, - OrganisationPreviewMockComponent, - PaginationMockComponent, - OrganisationsResultMockComponent, - ContentGhostComponent, - ], providers: [ { provide: OrganizationsServiceInterface, @@ -105,18 +65,18 @@ describe('OrganisationsComponent', () => { }) describe('on component init', () => { - let orgPreviewComponents: OrganisationPreviewMockComponent[] - let orgResultComponent: OrganisationsResultMockComponent + let orgPreviewComponents: OrganisationPreviewComponent[] + let orgResultComponent: OrganisationsResultComponent let paginationComponentDE: DebugElement let setCurrentPageSpy let setSortBySpy beforeEach(() => { - paginationComponentDE = de.query(By.directive(PaginationMockComponent)) + paginationComponentDE = de.query(By.directive(PaginationComponent)) }) describe('pass organisations to ui preview components', () => { beforeEach(() => { orgPreviewComponents = de - .queryAll(By.directive(OrganisationPreviewMockComponent)) + .queryAll(By.directive(OrganisationPreviewComponent)) .map((debugElement) => debugElement.componentInstance) }) it('should pass first organisation (sorted by name-asc) to first ui preview component', () => { @@ -141,7 +101,7 @@ describe('OrganisationsComponent', () => { paginationComponentDE.triggerEventHandler('newCurrentPageEvent', 2) fixture.detectChanges() orgPreviewComponents = de - .queryAll(By.directive(OrganisationPreviewMockComponent)) + .queryAll(By.directive(OrganisationPreviewComponent)) .map((debugElement) => debugElement.componentInstance) }) afterEach(() => { @@ -180,11 +140,11 @@ describe('OrganisationsComponent', () => { beforeEach(() => { setSortBySpy = jest.spyOn(component, 'setSortBy') de.query( - By.directive(OrganisationsFilterMockComponent) + By.directive(OrganisationsFilterComponent) ).triggerEventHandler('sortBy', ['desc', 'recordCount']) fixture.detectChanges() orgPreviewComponents = de - .queryAll(By.directive(OrganisationPreviewMockComponent)) + .queryAll(By.directive(OrganisationPreviewComponent)) .map((debugElement) => debugElement.componentInstance) }) it('should call setSortBy', () => { @@ -209,7 +169,7 @@ describe('OrganisationsComponent', () => { describe('initial state', () => { beforeEach(() => { orgResultComponent = de.query( - By.directive(OrganisationsResultMockComponent) + By.directive(OrganisationsResultComponent) ).componentInstance }) it('should display number of organisations found to equal all', () => { @@ -226,7 +186,7 @@ describe('OrganisationsComponent', () => { describe('entering search terms', () => { beforeEach(() => { orgResultComponent = de.query( - By.directive(OrganisationsResultMockComponent) + By.directive(OrganisationsResultComponent) ).componentInstance }) it('should ignore case and display 11 matches for "Data", "DATA" or "data"', () => { @@ -247,7 +207,7 @@ describe('OrganisationsComponent', () => { orgSelected = [] component.orgSelect.subscribe((org) => orgSelected.push(org)) de.query( - By.directive(OrganisationPreviewMockComponent) + By.directive(OrganisationPreviewComponent) ).triggerEventHandler('clickedOrganisation', organisationMock) fixture.detectChanges() })