From 183030188a2e5a70f20efc20d8499f8a9a936151 Mon Sep 17 00:00:00 2001 From: Annemieke Verdenhalven Date: Mon, 5 Aug 2024 11:32:01 +0200 Subject: [PATCH 1/5] internationalize the UI and add German and English localizations --- CHANGELOG.md | 2 + package-lock.json | 43 +++ package.json | 2 + src/app/app.module.ts | 32 +- .../asset-detail-dialog-data.service.ts | 11 +- .../asset-detail-dialog.component.html | 29 +- .../asset-detail-dialog.component.ts | 10 +- .../asset-property-grid-group-builder.ts | 112 ++++--- .../markdown-description.component.html | 15 +- .../policy-property-field-builder.ts | 14 +- .../catalog/catalog.module.ts | 8 + .../contract-offer-mini-list.component.html | 24 +- .../transfer-history-mini-list.component.html | 9 +- ...truncated-short-description.component.html | 10 +- .../confirmation-dialog.module.ts | 9 +- .../confirmation-dialog.component.ts | 22 +- ...e-negotiation-confirm-tos-dialog.module.ts | 3 +- ...otiation-confirm-tos-dialog.component.html | 14 +- .../json-dialog/json-dialog.module.ts | 9 +- .../json-dialog/json-dialog.component.html | 13 +- .../ui-elements/ago/ago.pipe.ts | 11 +- .../ui-elements/ago/formatDateAgo.ts | 15 +- .../url-list-dialog/url-list-dialog.module.ts | 9 +- .../url-list-dialog.component.html | 13 +- ...nector-info-property-grid-group-builder.ts | 43 ++- .../services/contract-negotiation.service.ts | 17 +- src/app/core/services/page-title-strategy.ts | 30 ++ .../services/participant-id-localization.ts | 27 +- .../asset-page/asset-page.module.ts | 9 +- .../asset-page/asset-page.component.html | 13 +- ...browser-fetch-detail-dialog.component.html | 23 +- .../catalog-browser-page.module.ts | 9 +- .../catalog-browser-page.component.html | 27 +- .../catalog-browser-page.component.ts | 15 +- .../data-offer-builder.ts | 13 +- .../connector-ui-routing.module.ts | 6 + .../connector-ui/connector-ui.component.html | 10 +- .../connector-ui/connector-ui.component.scss | 18 ++ .../connector-ui/connector-ui.component.ts | 10 + .../connector-ui/connector-ui.module.ts | 20 +- .../contract-agreement-cards.component.html | 15 +- .../contract-agreement-page.module.ts | 9 +- .../contract-agreement-page.component.html | 23 +- ...t-agreement-transfer-dialog.component.html | 140 ++++++--- .../contract-definition-cards.component.html | 17 +- .../contract-definition-cards.component.ts | 9 + ...ct-definition-editor-dialog.component.html | 19 +- .../contract-definition-page.module.ts | 9 +- .../contract-definition-page.component.html | 15 +- .../dashboard-page/dashboard-page.module.ts | 9 +- .../dashboard-page-data.service.ts | 57 +++- .../dashboard-page.component.html | 192 ++++++++---- .../language-selector.component.html | 33 ++ .../language-selector.component.scss | 16 + .../language-selector.component.spec.ts | 26 ++ .../language-selector.component.ts | 36 +++ ...policy-definition-create-page.component.ts | 15 +- .../policy-cards/policy-cards.component.html | 9 +- .../policy-cards/policy-cards.component.ts | 18 +- .../policy-definition-page.module.ts | 8 + .../policy-definition-page.component.html | 17 +- .../transfer-history-page.module.ts | 8 + .../transfer-history-page.component.html | 29 +- .../transfer-history-page.component.ts | 17 +- src/assets/i18n/de.json | 294 ++++++++++++++++++ src/assets/i18n/en.json | 294 ++++++++++++++++++ src/assets/images/flags/de.svg | 9 + src/assets/images/flags/en.svg | 16 + 68 files changed, 1781 insertions(+), 307 deletions(-) create mode 100644 src/app/core/services/page-title-strategy.ts create mode 100644 src/app/routes/connector-ui/language-selector/language-selector.component.html create mode 100644 src/app/routes/connector-ui/language-selector/language-selector.component.scss create mode 100644 src/app/routes/connector-ui/language-selector/language-selector.component.spec.ts create mode 100644 src/app/routes/connector-ui/language-selector/language-selector.component.ts create mode 100644 src/assets/i18n/de.json create mode 100644 src/assets/i18n/en.json create mode 100644 src/assets/images/flags/de.svg create mode 100644 src/assets/images/flags/en.svg diff --git a/CHANGELOG.md b/CHANGELOG.md index 08e734ca7..2e898a84c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -16,6 +16,8 @@ the detailed section referring to by linking pull requests or issues. #### Major +- Internationalize the UI and add a German localization + #### Minor #### Patch diff --git a/package-lock.json b/package-lock.json index 05e1ccd51..9338c4044 100644 --- a/package-lock.json +++ b/package-lock.json @@ -21,6 +21,8 @@ "@angular/platform-browser-dynamic": "^14.3.0", "@angular/router": "^14.3.0", "@ng-apimock/core": "^3.11.0", + "@ngx-translate/core": "^14.0.0", + "@ngx-translate/http-loader": "^7.0.0", "@ngxs/store": "^3.8.1", "@sovity.de/edc-client": "0.20240719.91939-main-f62d9761", "clean-deep": "^3.4.0", @@ -3351,6 +3353,31 @@ "webpack": "^5.54.0" } }, + "node_modules/@ngx-translate/core": { + "version": "14.0.0", + "resolved": "https://registry.npmjs.org/@ngx-translate/core/-/core-14.0.0.tgz", + "integrity": "sha512-UevdwNCXMRCdJv//0kC8h2eSfmi02r29xeE8E9gJ1Al4D4jEJ7eiLPdjslTMc21oJNGguqqWeEVjf64SFtvw2w==", + "dependencies": { + "tslib": "^2.3.0" + }, + "peerDependencies": { + "@angular/core": ">=13.0.0", + "rxjs": "^6.5.3 || ^7.4.0" + } + }, + "node_modules/@ngx-translate/http-loader": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/@ngx-translate/http-loader/-/http-loader-7.0.0.tgz", + "integrity": "sha512-j+NpXXlcGVdyUNyY/qsJrqqeAdJdizCd+GKh3usXExSqy1aE9866jlAIL+xrfDU4w+LiMoma5pgE4emvFebZmA==", + "dependencies": { + "tslib": "^2.3.0" + }, + "peerDependencies": { + "@angular/common": ">=13.0.0", + "@ngx-translate/core": ">=14.0.0", + "rxjs": "^6.5.3 || ^7.4.0" + } + }, "node_modules/@ngxs/store": { "version": "3.8.1", "resolved": "https://registry.npmjs.org/@ngxs/store/-/store-3.8.1.tgz", @@ -16478,6 +16505,22 @@ "dev": true, "requires": {} }, + "@ngx-translate/core": { + "version": "14.0.0", + "resolved": "https://registry.npmjs.org/@ngx-translate/core/-/core-14.0.0.tgz", + "integrity": "sha512-UevdwNCXMRCdJv//0kC8h2eSfmi02r29xeE8E9gJ1Al4D4jEJ7eiLPdjslTMc21oJNGguqqWeEVjf64SFtvw2w==", + "requires": { + "tslib": "^2.3.0" + } + }, + "@ngx-translate/http-loader": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/@ngx-translate/http-loader/-/http-loader-7.0.0.tgz", + "integrity": "sha512-j+NpXXlcGVdyUNyY/qsJrqqeAdJdizCd+GKh3usXExSqy1aE9866jlAIL+xrfDU4w+LiMoma5pgE4emvFebZmA==", + "requires": { + "tslib": "^2.3.0" + } + }, "@ngxs/store": { "version": "3.8.1", "resolved": "https://registry.npmjs.org/@ngxs/store/-/store-3.8.1.tgz", diff --git a/package.json b/package.json index 677dc2a24..72d8cbaa1 100644 --- a/package.json +++ b/package.json @@ -27,6 +27,8 @@ "@angular/platform-browser-dynamic": "^14.3.0", "@angular/router": "^14.3.0", "@ng-apimock/core": "^3.11.0", + "@ngx-translate/core": "^14.0.0", + "@ngx-translate/http-loader": "^7.0.0", "@ngxs/store": "^3.8.1", "@sovity.de/edc-client": "0.20240719.91939-main-f62d9761", "clean-deep": "^3.4.0", diff --git a/src/app/app.module.ts b/src/app/app.module.ts index 945a31482..a84fa5ebc 100644 --- a/src/app/app.module.ts +++ b/src/app/app.module.ts @@ -1,4 +1,14 @@ -import {HTTP_INTERCEPTORS, HttpClientModule} from '@angular/common/http'; +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ +import { + HTTP_INTERCEPTORS, + HttpClient, + HttpClientModule, +} from '@angular/common/http'; import {NgModule} from '@angular/core'; import {MatButtonModule} from '@angular/material/button'; import {MatCardModule} from '@angular/material/card'; @@ -21,6 +31,9 @@ import { } from '@angular/material/tooltip'; import {BrowserModule} from '@angular/platform-browser'; import {BrowserAnimationsModule} from '@angular/platform-browser/animations'; +import {TitleStrategy} from '@angular/router'; +import {TranslateLoader, TranslateModule} from '@ngx-translate/core'; +import {TranslateHttpLoader} from '@ngx-translate/http-loader'; import {NgxsModule} from '@ngxs/store'; import {NgChartsModule} from 'ng2-charts'; import {AppRoutingModule} from './app-routing.module'; @@ -28,7 +41,11 @@ import {AppComponent} from './app.component'; import {PageNotFoundComponent} from './component-library/error-404-component/page-not-found.component'; import {provideAppConfig} from './core/config/app-config-initializer'; import {ApiKeyInterceptor} from './core/services/api/api-key.interceptor'; +import {CustomPageTitleStrategy} from './core/services/page-title-strategy'; +export function HttploaderFactory(http: HttpClient) { + return new TranslateHttpLoader(http); +} @NgModule({ imports: [ // Angular @@ -48,6 +65,15 @@ import {ApiKeyInterceptor} from './core/services/api/api-key.interceptor'; MatSnackBarModule, MatToolbarModule, + //Translation + TranslateModule.forRoot({ + loader: { + provide: TranslateLoader, + useFactory: HttploaderFactory, + deps: [HttpClient], + }, + }), + // NgXs NgxsModule.forRoot([]), @@ -59,10 +85,11 @@ import {ApiKeyInterceptor} from './core/services/api/api-key.interceptor'; ], declarations: [AppComponent, PageNotFoundComponent], providers: [ + HttpClient, provideAppConfig(), {provide: HTTP_INTERCEPTORS, multi: true, useClass: ApiKeyInterceptor}, - + {provide: TitleStrategy, useClass: CustomPageTitleStrategy}, {provide: MAT_DATE_LOCALE, useValue: 'en-GB'}, { provide: MAT_FORM_FIELD_DEFAULT_OPTIONS, @@ -80,5 +107,6 @@ import {ApiKeyInterceptor} from './core/services/api/api-key.interceptor'; }, ], bootstrap: [AppComponent], + exports: [TranslateModule], }) export class AppModule {} diff --git a/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog-data.service.ts b/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog-data.service.ts index 7cef5f1d4..93e956d06 100644 --- a/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog-data.service.ts +++ b/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog-data.service.ts @@ -1,4 +1,12 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ + import {Injectable} from '@angular/core'; +import {TranslateService} from '@ngx-translate/core'; import {DataOffer} from '../../../core/services/models/data-offer'; import {UiAssetMapped} from '../../../core/services/models/ui-asset-mapped'; import {ContractAgreementCardMapped} from '../../../routes/connector-ui/contract-agreement-page/contract-agreement-cards/contract-agreement-card-mapped'; @@ -12,6 +20,7 @@ import {AssetPropertyGridGroupBuilder} from './asset-property-grid-group-builder export class AssetDetailDialogDataService { constructor( private assetPropertyGridGroupBuilder: AssetPropertyGridGroupBuilder, + private translateService: TranslateService, ) {} assetDetailsReadonly(asset: UiAssetMapped): AssetDetailDialogData { @@ -85,7 +94,7 @@ export class AssetDetailDialogDataService { ), this.assetPropertyGridGroupBuilder.buildAssetPropertiesGroup( asset, - 'Asset', + this.translateService.instant('general.asset'), ), ...this.assetPropertyGridGroupBuilder.buildAdditionalPropertiesGroups( asset, diff --git a/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog.component.html b/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog.component.html index 0c2d1f19d..8d178e40d 100644 --- a/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog.component.html +++ b/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog.component.html @@ -1,3 +1,10 @@ + +
edit @@ -122,7 +129,7 @@
- Transfer History + {{ 'component_library.t_history' | translate }}
@@ -171,7 +178,7 @@
- Negotiate + matTooltip="{{ 'tooltip.negotiate' | translate }}"> + {{ 'component_library.negotiate' | translate }} @@ -229,7 +238,7 @@ [matTooltip]="data.contractAgreement?.statusTooltipText ?? ''" [disabled]="!data.contractAgreement?.canTransfer" (click)="onTransferClick()"> - Transfer + {{ 'component_library.transfer' | translate }}
diff --git a/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog.component.ts b/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog.component.ts index 54e0c69ac..f3e45e493 100644 --- a/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog.component.ts +++ b/src/app/component-library/catalog/asset-detail-dialog/asset-detail-dialog.component.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {DOCUMENT} from '@angular/common'; import {Component, Inject, OnDestroy} from '@angular/core'; import { @@ -7,6 +13,7 @@ import { } from '@angular/material/dialog'; import {Observable, Subject, isObservable} from 'rxjs'; import {filter, finalize, takeUntil} from 'rxjs/operators'; +import {TranslateService} from '@ngx-translate/core'; import {UiContractOffer} from '@sovity.de/edc-client'; import {MailtoLinkBuilder} from 'src/app/core/services/mailto-link-builder'; import {EdcApiService} from '../../../core/services/api/edc-api.service'; @@ -85,6 +92,7 @@ export class AssetDetailDialogComponent implements OnDestroy { public contractNegotiationService: ContractNegotiationService, private mailtoLinkBuilder: MailtoLinkBuilder, @Inject(DOCUMENT) private document: Document, + private translateService: TranslateService, ) { if (isObservable(this._data)) { this._data @@ -180,7 +188,7 @@ export class AssetDetailDialogComponent implements OnDestroy { } private confirmDelete(): Observable { - const dialogData = ConfirmDialogModel.forDelete('asset', this.asset.title); + const dialogData = ConfirmDialogModel.forDelete('asset', this.asset.title, this.translateService); const ref = this.matDialog.open(ConfirmationDialogComponent, { maxWidth: '20%', data: dialogData, diff --git a/src/app/component-library/catalog/asset-detail-dialog/asset-property-grid-group-builder.ts b/src/app/component-library/catalog/asset-detail-dialog/asset-property-grid-group-builder.ts index c6e3fbae3..af62fe918 100644 --- a/src/app/component-library/catalog/asset-detail-dialog/asset-property-grid-group-builder.ts +++ b/src/app/component-library/catalog/asset-detail-dialog/asset-property-grid-group-builder.ts @@ -1,4 +1,11 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {Injectable} from '@angular/core'; +import {TranslateService} from '@ngx-translate/core'; import {UiPolicy} from '@sovity.de/edc-client'; import {ActiveFeatureSet} from '../../../core/config/active-feature-set'; import {UiAssetMapped} from '../../../core/services/models/ui-asset-mapped'; @@ -13,11 +20,12 @@ import {PolicyPropertyFieldBuilder} from './policy-property-field-builder'; @Injectable() export class AssetPropertyGridGroupBuilder { constructor( - private participantIdLocalization: ParticipantIdLocalization, private activeFeatureSet: ActiveFeatureSet, private propertyGridUtils: PropertyGridFieldService, private urlListDialogService: UrlListDialogService, private policyPropertyFieldBuilder: PolicyPropertyFieldBuilder, + private translateService: TranslateService, + private participantIdLocalization: ParticipantIdLocalization, ) {} buildAssetPropertiesGroup( @@ -37,32 +45,34 @@ export class AssetPropertyGridGroupBuilder { }, { icon: 'language', - label: 'Language', + label: this.translateService.instant('general.language'), ...this.propertyGridUtils.guessValue(asset.language?.label), }, { icon: 'apartment', - label: 'Publisher', + label: this.translateService.instant('general.publisher'), ...this.propertyGridUtils.guessValue(asset.publisherHomepage), }, { icon: 'bookmarks', - label: 'Endpoint Documentation', + label: this.translateService.instant('general.endpoint_doc'), ...this.propertyGridUtils.guessValue(asset.landingPageUrl), }, { icon: 'gavel', - label: 'Standard License', + label: this.translateService.instant('general.st_license'), ...this.propertyGridUtils.guessValue(asset.licenseUrl), }, { icon: 'category', - label: this.participantIdLocalization.participantId, + label: this.translateService.instant( + 'component_library.participant_id', + ), ...this.propertyGridUtils.guessValue(asset.participantId), }, { icon: 'account_circle', - label: 'Organization', + label: this.translateService.instant('component_library.organization'), ...this.propertyGridUtils.guessValue(asset.creatorOrganizationName), }, this.buildConnectorEndpointField(asset.connectorEndpoint), @@ -83,10 +93,22 @@ export class AssetPropertyGridGroupBuilder { const fields: PropertyGridField[] = []; const hints: {label: string; value: boolean | undefined}[] = [ - {label: 'Method', value: asset.httpDatasourceHintsProxyMethod}, - {label: 'Path', value: asset.httpDatasourceHintsProxyPath}, - {label: 'Query Params', value: asset.httpDatasourceHintsProxyQueryParams}, - {label: 'Body', value: asset.httpDatasourceHintsProxyBody}, + { + label: this.translateService.instant('general.method'), + value: asset.httpDatasourceHintsProxyMethod, + }, + { + label: this.translateService.instant('general.path'), + value: asset.httpDatasourceHintsProxyPath, + }, + { + label: this.translateService.instant('general.params'), + value: asset.httpDatasourceHintsProxyQueryParams, + }, + { + label: this.translateService.instant('general.body'), + value: asset.httpDatasourceHintsProxyBody, + }, ]; if (hints.some((hint) => hint.value != null)) { @@ -99,7 +121,7 @@ export class AssetPropertyGridGroupBuilder { fields.push({ icon: 'api', - label: 'HTTP Data Source Parameterization', + label: this.translateService.instant('component_library.http_param'), text, }); } @@ -107,7 +129,7 @@ export class AssetPropertyGridGroupBuilder { if (asset.mediaType) { fields.push({ icon: 'category', - label: 'Content Type', + label: this.translateService.instant('general.content'), ...this.propertyGridUtils.guessValue(asset.mediaType), }); } @@ -151,7 +173,7 @@ export class AssetPropertyGridGroupBuilder { return [ { - groupLabel: 'Additional Properties', + groupLabel: this.translateService.instant('general.add_properties'), properties: additionalProperties, }, { @@ -170,42 +192,42 @@ export class AssetPropertyGridGroupBuilder { if (asset.transportMode) { fields.push({ icon: 'commute', - label: 'Transport Mode', + label: this.translateService.instant('general.transport'), ...this.propertyGridUtils.guessValue(asset.transportMode?.label), }); } if (asset.dataCategory) { fields.push({ icon: 'commute', - label: 'Data Category', + label: this.translateService.instant('general.category'), ...this.propertyGridUtils.guessValue(asset.dataCategory?.label), }); } if (asset.dataSubcategory) { fields.push({ icon: 'commute', - label: 'Data Subcategory', + label: this.translateService.instant('general.subcategory'), ...this.propertyGridUtils.guessValue(asset.dataSubcategory?.label), }); } if (asset.dataModel) { fields.push({ icon: 'category', - label: 'Data Model', + label: this.translateService.instant('general.model'), ...this.propertyGridUtils.guessValue(asset.dataModel), }); } if (asset.geoReferenceMethod) { fields.push({ icon: 'commute', - label: 'Geo Reference Method', + label: this.translateService.instant('general.geo_method'), ...this.propertyGridUtils.guessValue(asset.geoReferenceMethod), }); } if (asset.geoLocation) { fields.push({ icon: 'location_on', - label: 'Geo Location', + label: this.translateService.instant('general.geo_location'), ...this.propertyGridUtils.guessValue(asset.geoLocation), }); } @@ -215,7 +237,7 @@ export class AssetPropertyGridGroupBuilder { if (asset.sovereignLegalName) { fields.push({ icon: 'account_balance', - label: 'Sovereign', + label: this.translateService.instant('general.sovereign'), ...this.propertyGridUtils.guessValue(asset.sovereignLegalName), }); } @@ -236,21 +258,21 @@ export class AssetPropertyGridGroupBuilder { if (asset.conditionsForUse) { fields.push({ icon: 'description', - label: 'Conditions For Use', + label: this.translateService.instant('general.conditions'), ...this.propertyGridUtils.guessValue(asset.conditionsForUse), }); } if (asset.dataUpdateFrequency) { fields.push({ icon: 'timelapse', - label: 'Data Update Frequency', + label: this.translateService.instant('general.frequency'), ...this.propertyGridUtils.guessValue(asset.dataUpdateFrequency), }); } if (asset.temporalCoverageFrom || asset.temporalCoverageToInclusive) { fields.push({ icon: 'today', - label: 'Temporal Coverage', + label: this.translateService.instant('general.coverage'), ...this.propertyGridUtils.guessValue( this.buildTemporalCoverageString( asset.temporalCoverageFrom, @@ -266,7 +288,7 @@ export class AssetPropertyGridGroupBuilder { const properties: PropertyGridField[] = [ { icon: 'category', - label: 'Signed', + label: this.translateService.instant('general.signed'), ...this.propertyGridUtils.guessValue( this.propertyGridUtils.formatDate( contractAgreement.contractSigningDate, @@ -275,24 +297,32 @@ export class AssetPropertyGridGroupBuilder { }, { icon: 'policy', - label: 'Direction', - ...this.propertyGridUtils.guessValue(contractAgreement.direction), + label: this.translateService.instant('general.direction'), + ...this.propertyGridUtils.guessValue( + contractAgreement.direction === 'CONSUMING' + ? this.translateService.instant('general.consuming') + : this.translateService.instant('general.providing'), + ), }, { icon: 'category', - label: 'Contract Agreement ID', + label: this.translateService.instant('general.contract') + ' ID', ...this.propertyGridUtils.guessValue( contractAgreement.contractAgreementId, ), }, { icon: 'link', - label: `Counter-Party ${this.participantIdLocalization.participantId}`, + label: `${this.translateService.instant('general.oth_connector')} ${ + this.participantIdLocalization.participantId + }`, ...this.propertyGridUtils.guessValue(contractAgreement.counterPartyId), }, { icon: 'link', - label: 'Counter-Party Connector Endpoint', + label: this.translateService.instant( + 'transfer_history_page.counter_endpoint', + ), ...this.propertyGridUtils.guessValue( contractAgreement.counterPartyAddress, ), @@ -311,7 +341,7 @@ export class AssetPropertyGridGroupBuilder { } return { - groupLabel: 'Contract Agreement', + groupLabel: this.translateService.instant('general.contract'), properties, }; } @@ -321,10 +351,10 @@ export class AssetPropertyGridGroupBuilder { subtitle: string, ): PropertyGridGroup { return { - groupLabel: 'Contract Policy', + groupLabel: this.translateService.instant('general.policy'), properties: this.policyPropertyFieldBuilder.buildPolicyPropertyFields( contractPolicy, - 'Contract Policy JSON-LD', + this.translateService.instant('general.policy') + ' JSON-LD', subtitle, ), }; @@ -333,7 +363,7 @@ export class AssetPropertyGridGroupBuilder { buildConnectorEndpointField(endpoint: string): PropertyGridField { return { icon: 'link', - label: 'Connector Endpoint', + label: this.translateService.instant('general.endpoint'), ...this.propertyGridUtils.guessValue(endpoint), }; } @@ -341,7 +371,7 @@ export class AssetPropertyGridGroupBuilder { buildNutsLocationsField(locations: string[]): PropertyGridField { return { icon: 'location_on', - label: 'NUTS Locations', + label: this.translateService.instant('general.nuts'), text: locations.join(', '), }; } @@ -352,11 +382,11 @@ export class AssetPropertyGridGroupBuilder { ): PropertyGridField { return { icon: 'attachment', - label: 'Data Samples', - text: 'Show Data Samples', + label: this.translateService.instant('general.data'), + text: this.translateService.instant('general.show_data'), onclick: () => this.urlListDialogService.showUrlListDialog({ - title: `Data Samples`, + title: this.translateService.instant('general.data'), subtitle: title, icon: 'attachment', urls: dataSampleUrls, @@ -371,11 +401,11 @@ export class AssetPropertyGridGroupBuilder { ): PropertyGridField { return { icon: 'receipt', - label: 'Reference Files', - text: 'Show Reference Files', + label: this.translateService.instant('general.files'), + text: this.translateService.instant('general.show_files'), onclick: () => this.urlListDialogService.showUrlListDialog({ - title: `Reference Files`, + title: this.translateService.instant('general.show_files'), subtitle: title, icon: 'receipt', urls: referenceFileUrls, diff --git a/src/app/component-library/catalog/asset-detail-dialog/markdown-description/markdown-description.component.html b/src/app/component-library/catalog/asset-detail-dialog/markdown-description/markdown-description.component.html index d98236700..7e2035708 100644 --- a/src/app/component-library/catalog/asset-detail-dialog/markdown-description/markdown-description.component.html +++ b/src/app/component-library/catalog/asset-detail-dialog/markdown-description/markdown-description.component.html @@ -1,3 +1,10 @@ + +
@@ -8,7 +15,7 @@ htmlSanitizer.sanitize(markdownConverter.toHtml(description ?? '')) ">
- No description. + ('component_library.no_description' | translate)
keyboard_double_arrow_up - {{ isCollapsed ? 'Show more' : 'Show less' }} + {{ + isCollapsed + ? ('component_library.show_more' | translate) + : ('component_library.show_less' | translate) + }}
diff --git a/src/app/component-library/catalog/asset-detail-dialog/policy-property-field-builder.ts b/src/app/component-library/catalog/asset-detail-dialog/policy-property-field-builder.ts index 87c7f532e..ec7dff5ce 100644 --- a/src/app/component-library/catalog/asset-detail-dialog/policy-property-field-builder.ts +++ b/src/app/component-library/catalog/asset-detail-dialog/policy-property-field-builder.ts @@ -1,4 +1,11 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {Injectable} from '@angular/core'; +import {TranslateService} from '@ngx-translate/core'; import {UiPolicy} from '@sovity.de/edc-client'; import {JsonDialogService} from '../../json-dialog/json-dialog/json-dialog.service'; import {PolicyMapper} from '../../policy-editor/model/policy-mapper'; @@ -9,6 +16,7 @@ export class PolicyPropertyFieldBuilder { constructor( private jsonDialogService: JsonDialogService, private policyMapper: PolicyMapper, + private translateService: TranslateService, ) {} buildPolicyPropertyFields( @@ -19,15 +27,15 @@ export class PolicyPropertyFieldBuilder { return [ { icon: 'policy', - label: 'Policy', + label: this.translateService.instant('general.policy'), policy: this.policyMapper.buildPolicy(policy.expression!), policyErrors: policy.errors || [], additionalContainerClasses: 'col-span-2', }, { icon: 'policy', - label: 'Policy JSON-LD', - text: 'Show JSON-LD', + label: this.translateService.instant('general.policy') + ' JSON-LD', + text: this.translateService.instant('component_library.json_ld'), onclick: () => this.jsonDialogService.showJsonDetailDialog({ title: policyDetailDialogTitle, diff --git a/src/app/component-library/catalog/catalog.module.ts b/src/app/component-library/catalog/catalog.module.ts index 5fc82d064..b246f436c 100644 --- a/src/app/component-library/catalog/catalog.module.ts +++ b/src/app/component-library/catalog/catalog.module.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {CommonModule} from '@angular/common'; import {NgModule} from '@angular/core'; import {MatButtonModule} from '@angular/material/button'; @@ -8,6 +14,7 @@ import {MatIconModule} from '@angular/material/icon'; import {MatProgressBarModule} from '@angular/material/progress-bar'; import {MatProgressSpinnerModule} from '@angular/material/progress-spinner'; import {MatTooltipModule} from '@angular/material/tooltip'; +import {TranslateModule} from '@ngx-translate/core'; import {InitiateNegotiationConfirmTosDialogModule} from '../initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog.module'; import {JsonDialogModule} from '../json-dialog/json-dialog.module'; import {PipesAndDirectivesModule} from '../pipes-and-directives/pipes-and-directives.module'; @@ -50,6 +57,7 @@ import {TruncatedShortDescription} from './truncated-short-description/truncated PropertyGridModule, UiElementsModule, PipesAndDirectivesModule, + TranslateModule, InitiateNegotiationConfirmTosDialogModule, ], diff --git a/src/app/component-library/catalog/contract-offer-mini-list/contract-offer-mini-list.component.html b/src/app/component-library/catalog/contract-offer-mini-list/contract-offer-mini-list.component.html index d1658d1a6..86bc7b418 100644 --- a/src/app/component-library/catalog/contract-offer-mini-list/contract-offer-mini-list.component.html +++ b/src/app/component-library/catalog/contract-offer-mini-list/contract-offer-mini-list.component.html @@ -1,3 +1,10 @@ + +
Contract Offers @@ -9,7 +16,10 @@
- Contract Offer {{ data.contractOffers.length >= 2 ? i + 1 : '' }} + + {{ 'general.offer' | translate }} + {{ data.contractOffers.length >= 2 ? i + 1 : '' }} + - Negotiate + {{ + 'component_library.negotiate' | translate + }} - Negotiating... + {{ 'component_library.negotiating' | translate }} - Successfully Negotiated + {{ 'component_library.succ_negotiating' | translate }}
diff --git a/src/app/component-library/catalog/transfer-history-mini-list/transfer-history-mini-list.component.html b/src/app/component-library/catalog/transfer-history-mini-list/transfer-history-mini-list.component.html index 9b0c57655..cca53c2a8 100644 --- a/src/app/component-library/catalog/transfer-history-mini-list/transfer-history-mini-list.component.html +++ b/src/app/component-library/catalog/transfer-history-mini-list/transfer-history-mini-list.component.html @@ -1,5 +1,12 @@ + + - No transfer processes started yet. + {{ 'component_library.no_transfer' | translate }}
+ + diff --git a/src/app/component-library/confirmation-dialog/confirmation-dialog.module.ts b/src/app/component-library/confirmation-dialog/confirmation-dialog.module.ts index 703ff1a52..9ab95bded 100644 --- a/src/app/component-library/confirmation-dialog/confirmation-dialog.module.ts +++ b/src/app/component-library/confirmation-dialog/confirmation-dialog.module.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {ClipboardModule} from '@angular/cdk/clipboard'; import {CommonModule} from '@angular/common'; import {NgModule} from '@angular/core'; @@ -6,6 +12,7 @@ import {MatCheckboxModule} from '@angular/material/checkbox'; import {MatDialogModule} from '@angular/material/dialog'; import {MatIconModule} from '@angular/material/icon'; import {MatTooltipModule} from '@angular/material/tooltip'; +import {TranslateModule} from '@ngx-translate/core'; import {PipesAndDirectivesModule} from '../pipes-and-directives/pipes-and-directives.module'; import {ConfirmationDialogComponent} from './confirmation-dialog/confirmation-dialog.component'; @@ -13,7 +20,7 @@ import {ConfirmationDialogComponent} from './confirmation-dialog/confirmation-di imports: [ // Angular CommonModule, - + TranslateModule, // Angular CDK ClipboardModule, diff --git a/src/app/component-library/confirmation-dialog/confirmation-dialog/confirmation-dialog.component.ts b/src/app/component-library/confirmation-dialog/confirmation-dialog/confirmation-dialog.component.ts index 27a22a4de..bc9d573b3 100644 --- a/src/app/component-library/confirmation-dialog/confirmation-dialog/confirmation-dialog.component.ts +++ b/src/app/component-library/confirmation-dialog/confirmation-dialog/confirmation-dialog.component.ts @@ -1,5 +1,12 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {Component, Inject, OnInit} from '@angular/core'; import {MAT_DIALOG_DATA, MatDialogRef} from '@angular/material/dialog'; +import {TranslateService} from '@ngx-translate/core'; @Component({ selector: 'app-confirmation-dialog', @@ -66,14 +73,19 @@ export class ConfirmDialogModel { public static forDelete( type: string, identifier: string, + translateService: TranslateService, ): ConfirmDialogModel { const dialogData = new ConfirmDialogModel( - 'Deletion confirmation', - `Please confirm you want to delete ${type} ${identifier}. This action cannot be undone.`, + `${translateService.instant('component_library.delete_title')}`, + `${translateService.instant( + 'component_library.delete_one', + )} ${type} ${identifier} ${translateService.instant( + 'component_library.delete_two', + )}`, ); - dialogData.confirmColor = 'warn'; - dialogData.confirmText = 'Delete'; - dialogData.cancelText = 'Cancel'; + dialogData.confirmColor = translateService.instant('general.warn'); + dialogData.confirmText = translateService.instant('general.delete'); + dialogData.cancelText = translateService.instant('general.close'); return dialogData; } } diff --git a/src/app/component-library/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog.module.ts b/src/app/component-library/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog.module.ts index e1bdce3f8..7134bafc8 100644 --- a/src/app/component-library/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog.module.ts +++ b/src/app/component-library/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog.module.ts @@ -6,6 +6,7 @@ import {MatCheckboxModule} from '@angular/material/checkbox'; import {MatDialogModule} from '@angular/material/dialog'; import {MatIconModule} from '@angular/material/icon'; import {MatTooltipModule} from '@angular/material/tooltip'; +import {TranslateModule} from '@ngx-translate/core'; import {PipesAndDirectivesModule} from '../pipes-and-directives/pipes-and-directives.module'; import {InitiateNegotiationConfirmTosDialogComponent} from './initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog.component'; @@ -13,7 +14,7 @@ import {InitiateNegotiationConfirmTosDialogComponent} from './initiate-negotiati imports: [ // Angular CommonModule, - + TranslateModule, // Angular CDK ClipboardModule, diff --git a/src/app/component-library/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog.component.html b/src/app/component-library/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog.component.html index 07a32ec8e..9e97890d6 100644 --- a/src/app/component-library/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog.component.html +++ b/src/app/component-library/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog/initiate-negotiation-confirm-tos-dialog.component.html @@ -1,26 +1,26 @@ -

Data Offer Terms & Conditions

+

{{ 'component_library.data_offer' | translate }}

- Hereby I agree that by pressing the 'Confirm' button, I accept the license - terms, policies, and additional conditions for use, including any copyright - notices, associated with the provider's offer. + {{ 'component_library.accept_licence' | translate }}

- I agree to the Data Offer Terms & Conditions + {{ 'component_library.agree' | translate }}
- +
diff --git a/src/app/component-library/json-dialog/json-dialog.module.ts b/src/app/component-library/json-dialog/json-dialog.module.ts index d0d7e19f5..add14049a 100644 --- a/src/app/component-library/json-dialog/json-dialog.module.ts +++ b/src/app/component-library/json-dialog/json-dialog.module.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {CommonModule} from '@angular/common'; import {NgModule} from '@angular/core'; import {FormsModule} from '@angular/forms'; @@ -7,6 +13,7 @@ import {MatCheckboxModule} from '@angular/material/checkbox'; import {MatDialogModule} from '@angular/material/dialog'; import {MatIconModule} from '@angular/material/icon'; import {MatTooltipModule} from '@angular/material/tooltip'; +import {TranslateModule} from '@ngx-translate/core'; import {NgxJsonViewerModule} from 'ngx-json-viewer'; import {ConfirmationDialogModule} from '../confirmation-dialog/confirmation-dialog.module'; import {PipesAndDirectivesModule} from '../pipes-and-directives/pipes-and-directives.module'; @@ -18,7 +25,7 @@ import {JsonDialogService} from './json-dialog/json-dialog.service'; // Angular CommonModule, FormsModule, - + TranslateModule, // Angular Material MatButtonModule, MatCardModule, diff --git a/src/app/component-library/json-dialog/json-dialog/json-dialog.component.html b/src/app/component-library/json-dialog/json-dialog/json-dialog.component.html index b7cefb4e6..c9022e88e 100644 --- a/src/app/component-library/json-dialog/json-dialog/json-dialog.component.html +++ b/src/app/component-library/json-dialog/json-dialog/json-dialog.component.html @@ -1,3 +1,10 @@ + +
@@ -42,8 +49,8 @@ Cleaned JSON + (ngModelChange)="updateVisibleJson()"> + {{ 'component_library.json' | translate }}
@@ -52,7 +59,7 @@ color="default" [mat-dialog-close]="null" [disabled]="busy"> - Close + {{ 'general.close' | translate }}
diff --git a/src/app/component-library/ui-elements/ago/ago.pipe.ts b/src/app/component-library/ui-elements/ago/ago.pipe.ts index 947f447b4..2b21b223f 100644 --- a/src/app/component-library/ui-elements/ago/ago.pipe.ts +++ b/src/app/component-library/ui-elements/ago/ago.pipe.ts @@ -1,6 +1,13 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {Pipe, PipeTransform} from '@angular/core'; import {Observable, concat, interval, of} from 'rxjs'; import {distinctUntilChanged, map} from 'rxjs/operators'; +import {TranslateService} from '@ngx-translate/core'; import {formatDateAgo} from './formatDateAgo'; /** @@ -10,9 +17,11 @@ import {formatDateAgo} from './formatDateAgo'; export class AgoPipe implements PipeTransform { interval$ = concat(of({}), interval(3000)); + constructor(private translateService: TranslateService) {} + transform(date?: Date | null): Observable { return this.interval$.pipe( - map(() => formatDateAgo(date)), + map(() => formatDateAgo(date, this.translateService.currentLang)), distinctUntilChanged(), ); } diff --git a/src/app/component-library/ui-elements/ago/formatDateAgo.ts b/src/app/component-library/ui-elements/ago/formatDateAgo.ts index 99209c52c..f46a54321 100644 --- a/src/app/component-library/ui-elements/ago/formatDateAgo.ts +++ b/src/app/component-library/ui-elements/ago/formatDateAgo.ts @@ -1,16 +1,27 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {formatDistanceToNow} from 'date-fns'; +import {de, enUS} from 'date-fns/locale'; import {DateInput} from './date-input'; /** * Formats date as "{n} {timeUnit} ago" or "in {n} {timeUnit}s". * @param date date */ -export function formatDateAgo(date?: DateInput | null): string { +export function formatDateAgo( + date?: DateInput | null, + locale?: string, +): string { if (!date) { return 'never'; } if (typeof date === 'string') { date = new Date(date); } - return formatDistanceToNow(date, {addSuffix: true}); + const localeDateNfs = locale === 'de' ? de : enUS; + return formatDistanceToNow(date, {addSuffix: true, locale: localeDateNfs}); } diff --git a/src/app/component-library/url-list-dialog/url-list-dialog.module.ts b/src/app/component-library/url-list-dialog/url-list-dialog.module.ts index 00f1deb44..957d56f13 100644 --- a/src/app/component-library/url-list-dialog/url-list-dialog.module.ts +++ b/src/app/component-library/url-list-dialog/url-list-dialog.module.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {CommonModule} from '@angular/common'; import {NgModule} from '@angular/core'; import {FormsModule} from '@angular/forms'; @@ -5,6 +11,7 @@ import {MatButtonModule} from '@angular/material/button'; import {MatCardModule} from '@angular/material/card'; import {MatDialogModule} from '@angular/material/dialog'; import {MatIconModule} from '@angular/material/icon'; +import {TranslateModule} from '@ngx-translate/core'; import {NgxJsonViewerModule} from 'ngx-json-viewer'; import {ConfirmationDialogModule} from '../confirmation-dialog/confirmation-dialog.module'; import {PipesAndDirectivesModule} from '../pipes-and-directives/pipes-and-directives.module'; @@ -16,7 +23,7 @@ import {UrlListDialogService} from './url-list-dialog/url-list-dialog.service'; // Angular CommonModule, FormsModule, - + TranslateModule, // Angular Material MatButtonModule, MatCardModule, diff --git a/src/app/component-library/url-list-dialog/url-list-dialog/url-list-dialog.component.html b/src/app/component-library/url-list-dialog/url-list-dialog/url-list-dialog.component.html index 17c076013..4bb741b72 100644 --- a/src/app/component-library/url-list-dialog/url-list-dialog/url-list-dialog.component.html +++ b/src/app/component-library/url-list-dialog/url-list-dialog/url-list-dialog.component.html @@ -1,3 +1,10 @@ + +
@@ -18,7 +25,7 @@ mat-dialog-content style="display: block; min-width: 40rem; max-width: 40rem; max-height: 60vh">
-
Description
+
{{ 'general.description' | translate }}
{{ data.description }}
@@ -34,5 +41,7 @@
- +
diff --git a/src/app/core/services/connector-info-property-grid-group-builder.ts b/src/app/core/services/connector-info-property-grid-group-builder.ts index 462cebcdb..cefbba33d 100644 --- a/src/app/core/services/connector-info-property-grid-group-builder.ts +++ b/src/app/core/services/connector-info-property-grid-group-builder.ts @@ -1,5 +1,12 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {Injectable} from '@angular/core'; import {MatDialog} from '@angular/material/dialog'; +import {TranslateService} from '@ngx-translate/core'; import {DashboardPage} from '@sovity.de/edc-client'; import {JsonDialogComponent} from '../../component-library/json-dialog/json-dialog/json-dialog.component'; import {JsonDialogData} from '../../component-library/json-dialog/json-dialog/json-dialog.data'; @@ -16,12 +23,13 @@ export class ConnectorInfoPropertyGridGroupBuilder { private participantIdLocalization: ParticipantIdLocalization, private propertyGridUtils: PropertyGridFieldService, private matDialog: MatDialog, + private translateService: TranslateService, ) {} private onShowConnectorVersionClick(title: string, versionData: any) { const data: JsonDialogData = { title, - subtitle: 'Show Details', + subtitle: this.translateService.instant('general.details'), icon: 'link', objectForJson: versionData, }; @@ -86,13 +94,14 @@ export class ConnectorInfoPropertyGridGroupBuilder { label: 'UI Version', text: data.trim().toString() ? this.asDate(data.trim().toString()) - : 'Show Details', + : this.translateService.instant('general.details'), onclick: () => this.onShowConnectorVersionClick('Version Information', { 'UI Last Commit Information': uiCommitDetails.match({ ifOk: (uiCommitdata) => uiCommitdata, ifError: (error) => error.failureMessage, - ifLoading: () => 'Still Loading...', + ifLoading: () => + this.translateService.instant('general.loading2'), }), }), }, @@ -101,7 +110,7 @@ export class ConnectorInfoPropertyGridGroupBuilder { { icon: 'link', label: 'UI Version', - text: 'Show Details', + text: this.translateService.instant('general.details'), onclick: () => this.onShowConnectorVersionClick('Version Information', { 'UI Commit Information': error.failureMessage, @@ -112,7 +121,7 @@ export class ConnectorInfoPropertyGridGroupBuilder { { icon: 'link', label: 'UI Version', - text: 'Loading...', + text: this.translateService.instant('general.loading'), }, ], }); @@ -125,12 +134,16 @@ export class ConnectorInfoPropertyGridGroupBuilder { const fields: PropertyGridField[] = dashboardData.match< PropertyGridField[] >({ - ifLoading: () => [{icon: 'info', label: 'Loading', text: 'Loading...'}], + ifLoading: () => [{ + icon: 'info', + label: this.translateService.instant('general.loading1'), + text: this.translateService.instant('general.loading') + }], ifError: () => [ { icon: 'error', - label: 'Error', - text: 'Failed loading connector information', + label: this.translateService.instant('general.error'), + text: this.translateService.instant('services.failed_loading'), }, ], ifOk: (data) => this.buildConnectorMetadata(data), @@ -146,7 +159,7 @@ export class ConnectorInfoPropertyGridGroupBuilder { const fields = [ { icon: 'link', - label: 'Connector Endpoint', + label: this.translateService.instant('general.endpoint'), ...this.propertyGridUtils.guessValue(data.connectorEndpoint), }, { @@ -156,32 +169,32 @@ export class ConnectorInfoPropertyGridGroupBuilder { }, { icon: 'title', - label: 'Title', + label: this.translateService.instant('general.title'), ...this.propertyGridUtils.guessValue(data.connectorTitle), }, { icon: 'apartment', - label: 'Curator Organization Name', + label: this.translateService.instant('services.curator_org'), ...this.propertyGridUtils.guessValue(data.connectorCuratorName), }, { icon: 'apartment', - label: 'Curator URL', + label: this.translateService.instant('services.curator_url'), ...this.propertyGridUtils.guessValue(data.connectorCuratorUrl), }, { icon: 'title', - label: 'Description', + label: this.translateService.instant('general.description'), ...this.propertyGridUtils.guessValue(data.connectorDescription), }, { icon: 'contact_support', - label: 'Maintainer Organization Name', + label: this.translateService.instant('services.maintainer'), ...this.propertyGridUtils.guessValue(data.connectorMaintainerName), }, { icon: 'contact_support', - label: 'Maintainer URL', + label: this.translateService.instant('services.main_url'), ...this.propertyGridUtils.guessValue(data.connectorMaintainerUrl), }, ]; diff --git a/src/app/core/services/contract-negotiation.service.ts b/src/app/core/services/contract-negotiation.service.ts index adf9da50b..b1d6cdbee 100644 --- a/src/app/core/services/contract-negotiation.service.ts +++ b/src/app/core/services/contract-negotiation.service.ts @@ -1,7 +1,14 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {Injectable} from '@angular/core'; import {MatDialog} from '@angular/material/dialog'; import {EMPTY, Observable, interval} from 'rxjs'; import {catchError, filter, first, switchMap, tap} from 'rxjs/operators'; +import {TranslateService} from '@ngx-translate/core'; import { ContractNegotiationRequest, UiContractNegotiation, @@ -22,6 +29,7 @@ export class ContractNegotiationService { private edcApiService: EdcApiService, private notificationService: NotificationService, private confirmationDialog: MatDialog, + private translateService: TranslateService, ) { if (!environment.production) { // Test data on local dev @@ -106,7 +114,8 @@ export class ContractNegotiationService { } private onFailureStarting() { - this.notificationService.showError('Failure starting negotiation.'); + const err = this.translateService.instant('notification.starting_neg'); + this.notificationService.showError(err); } private onStarted(contractOfferId: string) { @@ -115,13 +124,15 @@ export class ContractNegotiationService { private onFailureNegotiating(contractOfferId: string) { this.runningContractOffers.delete(contractOfferId); - this.notificationService.showError('Failed negotiating contract.'); + const err2 = this.translateService.instant('notification.negotiation'); + this.notificationService.showError(err2); } private onSuccess(contractOfferId: string) { this.runningContractOffers.delete(contractOfferId); this.doneContractOffers.add(contractOfferId); - this.notificationService.showInfo('Contract Negotiation complete!'); + const mes = this.translateService.instant('notification.compl_negotiation'); + this.notificationService.showError(mes); } private initiateNegotiation( diff --git a/src/app/core/services/page-title-strategy.ts b/src/app/core/services/page-title-strategy.ts new file mode 100644 index 000000000..7c84fe413 --- /dev/null +++ b/src/app/core/services/page-title-strategy.ts @@ -0,0 +1,30 @@ +/* + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ +import {Injectable} from '@angular/core'; +import {Title} from '@angular/platform-browser'; +import {RouterStateSnapshot, TitleStrategy} from '@angular/router'; +import {TranslateService} from '@ngx-translate/core'; + +@Injectable() +export class CustomPageTitleStrategy extends TitleStrategy { + constructor( + private translateService: TranslateService, + private readonly title: Title, + ) { + super(); + } + + override updateTitle(snapshot: RouterStateSnapshot): void { + const title = this.buildTitle(snapshot); + if (title) { + this.translateService.get(title).subscribe((translatedTitle) => { + this.title.setTitle(translatedTitle); + }); + } else { + this.title.setTitle('DEFAULT_TITLE'); + } + } +} diff --git a/src/app/core/services/participant-id-localization.ts b/src/app/core/services/participant-id-localization.ts index 2c225295c..0914ce4b0 100644 --- a/src/app/core/services/participant-id-localization.ts +++ b/src/app/core/services/participant-id-localization.ts @@ -1,14 +1,35 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {Inject, Injectable} from '@angular/core'; +import {TranslateService} from '@ngx-translate/core'; import {APP_CONFIG, AppConfig} from '../config/app-config'; @Injectable({providedIn: 'root'}) export class ParticipantIdLocalization { + constructor( + @Inject(APP_CONFIG) private config: AppConfig, + private translateService: TranslateService, + ) { + this.translateService + .stream([ + 'component_library.connector_id', + 'component_library.participant_id', + ]) + .subscribe((translations) => { + this.participantId = this.mds + ? translations['component_library.connector_id'] + : translations['component_library.participant_id']; + this.participantIdPlural = this.participantId + 's'; + }); + } private mds = this.config.features.has('mds-connector-id'); - participantId = this.mds ? 'Connector ID' : 'Participant ID'; + participantId = ''; // init, will be updated by translateService participantIdPlural = this.participantId + 's'; participantIdPlaceholder = this.mds ? 'MDSL1234XX.C1234XX' : 'other-connector-participant-id'; - - constructor(@Inject(APP_CONFIG) private config: AppConfig) {} } diff --git a/src/app/routes/connector-ui/asset-page/asset-page.module.ts b/src/app/routes/connector-ui/asset-page/asset-page.module.ts index 33d61a3a7..9ed22af19 100644 --- a/src/app/routes/connector-ui/asset-page/asset-page.module.ts +++ b/src/app/routes/connector-ui/asset-page/asset-page.module.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {CommonModule} from '@angular/common'; import {NgModule} from '@angular/core'; import {FormsModule, ReactiveFormsModule} from '@angular/forms'; @@ -20,6 +26,7 @@ import {MatSlideToggleModule} from '@angular/material/slide-toggle'; import {MatStepperModule} from '@angular/material/stepper'; import {MatTooltipModule} from '@angular/material/tooltip'; import {RouterModule} from '@angular/router'; +import {TranslateModule} from '@ngx-translate/core'; import {CatalogModule} from '../../../component-library/catalog/catalog.module'; import {DataAddressModule} from '../../../component-library/data-address/data-address.module'; import {PipesAndDirectivesModule} from '../../../component-library/pipes-and-directives/pipes-and-directives.module'; @@ -43,7 +50,7 @@ import {TransportModeSelectComponent} from './transport-mode-select/transport-mo FormsModule, ReactiveFormsModule, RouterModule, - + TranslateModule, // Angular Material MatBadgeModule, MatButtonModule, diff --git a/src/app/routes/connector-ui/asset-page/asset-page/asset-page.component.html b/src/app/routes/connector-ui/asset-page/asset-page/asset-page.component.html index e2b90224b..9dfe3037b 100644 --- a/src/app/routes/connector-ui/asset-page/asset-page/asset-page.component.html +++ b/src/app/routes/connector-ui/asset-page/asset-page/asset-page.component.html @@ -1,3 +1,10 @@ + +
@@ -5,7 +12,7 @@ class="search-form-field" appearance="outline" color="primary"> - Search assets + {{ 'asset_page.search_assets' | translate }} search @@ -58,7 +65,7 @@ !assetList.data.filteredAssets.length) " class="min-h-[35rem]" - [emptyMessage]="'No assets found with given filter.'"> + [emptyMessage]="'asset_page.no_assets' | translate">
diff --git a/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-fetch-detail-dialog/catalog-browser-fetch-detail-dialog.component.html b/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-fetch-detail-dialog/catalog-browser-fetch-detail-dialog.component.html index d4298a605..b26962fcb 100644 --- a/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-fetch-detail-dialog/catalog-browser-fetch-detail-dialog.component.html +++ b/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-fetch-detail-dialog/catalog-browser-fetch-detail-dialog.component.html @@ -1,8 +1,19 @@ + +
- view_timeline + view_timeline
-
Fetch Status
-
Other Connector Endpoint Catalogs
+
+ {{ 'catalog_browser_page.fetch' | translate }} +
+
+ {{ 'catalog_browser_page.endpoint_catalogs' | translate }} +
@@ -23,8 +34,10 @@
- +
diff --git a/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page.module.ts b/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page.module.ts index 3b83ae9cb..e1d625c34 100644 --- a/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page.module.ts +++ b/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page.module.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {ClipboardModule} from '@angular/cdk/clipboard'; import {CommonModule} from '@angular/common'; import {HttpClientModule} from '@angular/common/http'; @@ -27,6 +33,7 @@ import {MatTableModule} from '@angular/material/table'; import {MatTabsModule} from '@angular/material/tabs'; import {MatTooltipModule} from '@angular/material/tooltip'; import {RouterModule} from '@angular/router'; +import {TranslateModule} from '@ngx-translate/core'; import {CatalogModule} from '../../../component-library/catalog/catalog.module'; import {JsonDialogModule} from '../../../component-library/json-dialog/json-dialog.module'; import {PipesAndDirectivesModule} from '../../../component-library/pipes-and-directives/pipes-and-directives.module'; @@ -45,7 +52,7 @@ import {DataOfferBuilder} from './catalog-browser-page/data-offer-builder'; FormsModule, ReactiveFormsModule, RouterModule, - + TranslateModule, // Angular CDK ClipboardModule, diff --git a/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page/catalog-browser-page.component.html b/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page/catalog-browser-page.component.html index f6c805bb4..52c15f2ca 100644 --- a/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page/catalog-browser-page.component.html +++ b/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page/catalog-browser-page.component.html @@ -1,8 +1,15 @@ + +
- Search catalog + {{ 'catalog_browser_page.search' | translate }} search @@ -65,7 +74,7 @@ matSuffix color="primary" mat-icon-button - matTooltip="Click for details" + matTooltip="{{ 'tooltip.details' | translate }}" (click)="onShowFetchDetails()"> info @@ -87,7 +96,9 @@ + [emptyMessage]=" + 'catalog_browser_page.enter_endpoints' | translate + "> + [emptyMessage]=" + 'catalog_browser_page.no_contract_offers' | translate + ">
1 ? ` (${urls.length})` : '' - }: ${urls.join(', ')}`; + return `${usage} ${urls.length > 1 ? ` (${urls.length})` : ''}: ${urls.join( + ', ', + )}`; } private searchText$(): Observable { diff --git a/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page/data-offer-builder.ts b/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page/data-offer-builder.ts index 7ea6e5dc0..6dc2fddcd 100644 --- a/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page/data-offer-builder.ts +++ b/src/app/routes/connector-ui/catalog-browser-page/catalog-browser-page/data-offer-builder.ts @@ -1,4 +1,11 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {Injectable} from '@angular/core'; +import {TranslateService} from '@ngx-translate/core'; import {UiContractOffer, UiDataOffer} from '@sovity.de/edc-client'; import {PolicyPropertyFieldBuilder} from '../../../../component-library/catalog/asset-detail-dialog/policy-property-field-builder'; import {AssetBuilder} from '../../../../core/services/asset-builder'; @@ -11,6 +18,7 @@ export class DataOfferBuilder { constructor( private assetBuilder: AssetBuilder, private policyPropertyFieldBuilder: PolicyPropertyFieldBuilder, + private translateService: TranslateService, ) {} buildDataOffer(dataOffer: UiDataOffer): DataOffer { const asset = this.assetBuilder.buildAsset(dataOffer.asset); @@ -51,6 +59,9 @@ export class DataOfferBuilder { } private getGroupLabel(i: number, total: number) { - return `Contract Offer ${total > 1 ? i : ''}`; + const contract = this.translateService.instant( + 'catalog_browser_page.contract', + ); + return `${contract} ${total > 1 ? i : ''}`; } } diff --git a/src/app/routes/connector-ui/connector-ui-routing.module.ts b/src/app/routes/connector-ui/connector-ui-routing.module.ts index a948fa144..4a61aeebb 100644 --- a/src/app/routes/connector-ui/connector-ui-routing.module.ts +++ b/src/app/routes/connector-ui/connector-ui-routing.module.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {NgModule} from '@angular/core'; import {RouterModule, Routes} from '@angular/router'; import {AssetEditPageComponent} from './asset-edit-page/asset-edit-page/asset-edit-page.component'; diff --git a/src/app/routes/connector-ui/connector-ui.component.html b/src/app/routes/connector-ui/connector-ui.component.html index 6642469c5..94ee7c661 100644 --- a/src/app/routes/connector-ui/connector-ui.component.html +++ b/src/app/routes/connector-ui/connector-ui.component.html @@ -1,3 +1,10 @@ + +
+
menu - {{ titleService.getTitle() }} + {{ titleService.getTitle() || '' | translate }}
diff --git a/src/app/routes/connector-ui/connector-ui.component.scss b/src/app/routes/connector-ui/connector-ui.component.scss index 67fc9a63d..13b58fd1f 100644 --- a/src/app/routes/connector-ui/connector-ui.component.scss +++ b/src/app/routes/connector-ui/connector-ui.component.scss @@ -1,7 +1,25 @@ +/*! + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ + .sidenav-container { height: 100%; } +.languageSelector { + width: 10px; + background-color: red; +} + +.language { + margin-top: 10px; + margin-right: auto; + padding: 8px 16px; +} + .sidenav { width: 300px; } diff --git a/src/app/routes/connector-ui/connector-ui.component.ts b/src/app/routes/connector-ui/connector-ui.component.ts index 021973886..dc1d82e5a 100644 --- a/src/app/routes/connector-ui/connector-ui.component.ts +++ b/src/app/routes/connector-ui/connector-ui.component.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {BreakpointObserver, Breakpoints} from '@angular/cdk/layout'; import {Component, Inject, OnInit} from '@angular/core'; import {Title} from '@angular/platform-browser'; @@ -5,6 +11,7 @@ import {Observable} from 'rxjs'; import {map, shareReplay} from 'rxjs/operators'; import {NavItemGroup} from 'src/app/core/services/models/nav-item-group'; import {NavItemsBuilder} from 'src/app/core/services/nav-items-builder'; +import {TranslateService} from '@ngx-translate/core'; import {APP_CONFIG, AppConfig} from '../../core/config/app-config'; import {LoginPollingService} from '../../core/services/login-polling.service'; import {TitleUtilsService} from '../../core/services/title-utils.service'; @@ -32,8 +39,11 @@ export class ConnectorUiComponent implements OnInit { private breakpointObserver: BreakpointObserver, private loginPollingService: LoginPollingService, private navItemsBuilder: NavItemsBuilder, + private translateService: TranslateService, ) { this.navItemGroups = this.navItemsBuilder.buildNavItemGroups(); + this.translateService.setDefaultLang('en'); + this.translateService.use(localStorage.getItem('selectedLanguage') || 'en'); } ngOnInit() { diff --git a/src/app/routes/connector-ui/connector-ui.module.ts b/src/app/routes/connector-ui/connector-ui.module.ts index 6d7211378..4866cc33a 100644 --- a/src/app/routes/connector-ui/connector-ui.module.ts +++ b/src/app/routes/connector-ui/connector-ui.module.ts @@ -1,13 +1,24 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {CommonModule} from '@angular/common'; +import {HttpClient} from '@angular/common/http'; import {NgModule} from '@angular/core'; import {MatButtonModule} from '@angular/material/button'; import {MatNativeDateModule} from '@angular/material/core'; import {MatDatepickerModule} from '@angular/material/datepicker'; +import {MatFormFieldModule} from '@angular/material/form-field'; import {MatIconModule} from '@angular/material/icon'; import {MatListModule} from '@angular/material/list'; +import {MatMenuModule} from '@angular/material/menu'; +import {MatSelectModule} from '@angular/material/select'; import {MatSidenavModule} from '@angular/material/sidenav'; import {MatSnackBarModule} from '@angular/material/snack-bar'; import {MatToolbarModule} from '@angular/material/toolbar'; +import {TranslateModule} from '@ngx-translate/core'; import {PipesAndDirectivesModule} from '../../component-library/pipes-and-directives/pipes-and-directives.module'; import {UiElementsModule} from '../../component-library/ui-elements/ui-elements.module'; import {AssetEditPageModule} from './asset-edit-page/asset-edit-page.module'; @@ -18,6 +29,7 @@ import {ConnectorUiComponent} from './connector-ui.component'; import {ContractAgreementPageModule} from './contract-agreement-page/contract-agreement-page.module'; import {ContractDefinitionPageModule} from './contract-definition-page/contract-definition-page.module'; import {DashboardPageModule} from './dashboard-page/dashboard-page.module'; +import {LanguageSelectorComponent} from './language-selector/language-selector.component'; import {LocationHistoryUtils} from './logout-page/location-history-utils'; import {LogoutPageModule} from './logout-page/logout-page.module'; import {PreviousRouteListener} from './logout-page/previous-route-listener'; @@ -39,10 +51,14 @@ import {TransferHistoryPageModule} from './transfer-history-page/transfer-histor MatSidenavModule, MatSnackBarModule, MatToolbarModule, + MatMenuModule, + MatFormFieldModule, + MatSelectModule, // Features PipesAndDirectivesModule, UiElementsModule, + TranslateModule, // Pages AssetPageModule, @@ -59,8 +75,8 @@ import {TransferHistoryPageModule} from './transfer-history-page/transfer-histor // Routing ConnectorUiRoutingModule, ], - declarations: [ConnectorUiComponent], - providers: [PreviousRouteListener, LocationHistoryUtils], + declarations: [ConnectorUiComponent, LanguageSelectorComponent], + providers: [PreviousRouteListener, LocationHistoryUtils, HttpClient], }) export class ConnectorUiModule { constructor(previousRouteListener: PreviousRouteListener) { diff --git a/src/app/routes/connector-ui/contract-agreement-page/contract-agreement-cards/contract-agreement-cards.component.html b/src/app/routes/connector-ui/contract-agreement-page/contract-agreement-cards/contract-agreement-cards.component.html index 8586452a1..ebf6d20ad 100644 --- a/src/app/routes/connector-ui/contract-agreement-page/contract-agreement-cards/contract-agreement-cards.component.html +++ b/src/app/routes/connector-ui/contract-agreement-page/contract-agreement-cards/contract-agreement-cards.component.html @@ -1,3 +1,10 @@ + +
-
Signed
+
+ {{ 'general.signed' | translate }} +
@@ -56,7 +65,9 @@
-
Other Connector
+
+ {{ 'general.oth_connector' | translate }} +
+
@@ -5,7 +12,9 @@ class="search-form-field" appearance="outline" color="accent"> - Search contract agreements... + {{ + 'contract_agreement_page.search_agree' | translate + }} search
@@ -79,7 +90,8 @@ *ngIf="page.isReady && !!page.data.contractAgreements.length" class="flex flex-col space-y-[20px]"> - + - + Initiate Transfer + + +

+ {{ 'contract_agreement_page.ini_transfer' | translate }} +

-
Datasink
+
+ {{ 'contract_agreement_page.datasink' | translate }} +
- Custom Datasink Config (JSON) + {{ + 'contract_agreement_page.cus_datasink' | translate + }} {{ validationMessages.invalidJsonMessage }} - JSON-LD values for "edc:connectorId", "edc:contractId", - "edc:connectorId" and "edc:connectorAddress" will be overridden. + {{ 'contract_agreement_page.json_hint' | translate }} @@ -57,7 +71,7 @@

Initiate Transfer

- Method + {{ 'general.method' | translate }} Initiate Transfer
-
Authentication
+
{{ 'general.auth' | translate }}
Initiate Transfer (click)=" form.all.controls.httpAuthHeaderType.setValue('Vault-Secret') "> - Add Authentication + {{ 'general.add_auth' | translate }}
@@ -101,9 +115,11 @@

Initiate Transfer

Type - Header with Vault Secret + {{ 'general.header_sec' | translate }} - Header with Value + {{ + 'general.header_val' | translate + }}
Initiate Transfer class="flex flex-row space-x-[10px]"> - Auth Header Name + {{ 'general.auth_header' | translate }} Initiate Transfer - Auth Header Value + {{ 'general.auth_value' | translate }} Initiate Transfer form.all.controls.httpAuthHeaderType.value === 'Vault-Secret' " class="grow"> - Vault Secret Name + {{ 'general.vault_secret' | translate }} Initiate Transfer mat-button color="warn" (click)="form.all.controls.httpAuthHeaderType.setValue('None')"> - Remove Authentication + {{ 'general.rem_auth' | translate }}
-
Additional Headers
+
+ {{ 'general.add_header' | translate }} +
- Header Name + {{ 'general.header_name' | translate }} Initiate Transfer - Header Value + {{ 'general.header_value' | translate }} Initiate Transfer color="warn" style="height: 54px; margin-top: 4px; margin-left: 8px" (click)="form.onHttpHeadersRemoveClick(i)"> - Remove + {{ 'general.remove' | translate }}
@@ -197,29 +215,25 @@

Initiate Transfer

mat-button color="accent" (click)="form.onHttpHeadersAddClick()"> - Add Additional Header + {{ 'general.add_add_header' | translate }}
-
HTTP Datasource Parameterization
+
+ {{ 'contract_agreement_page.http_para' | translate }} +
- When the data offer on the provider side is of the type - HttpData and certain data source fields are set, certain parts - of the request to the data source can be customized from the consumer - side and will be passed to the other connector when initiating the - transfer. This allows an asset to contain more than just one kind of - data, allowing additional filtering or even sharing of entire APIs - with multiple data sets via a single asset and a single contract. + {{ 'contract_agreement_page.http_message' | translate }}
- The resulting URL will look like + {{ 'contract_agreement_page.res_url' | translate }} {{ '{baseUrl}{customSubPath}?{baseQueryParams}&{customQueryParams}' }} @@ -233,8 +247,14 @@

Initiate Transfer

- Custom Method - + {{ + 'contract_agreement_page.cus_meth' | translate + }} + Initiate Transfer >{{ method }} - Requires "proxyMethod" to be "true". + + {{ + 'contract_agreement_page.proxy_method' | translate + }} @@ -251,12 +275,16 @@

Initiate Transfer

- Custom Subpath + {{ + 'contract_agreement_page.cus_sub' | translate + }} - Requires "proxyPath" to be "true". + {{ + 'contract_agreement_page.proxy_path' | translate + }}
@@ -270,19 +298,23 @@

Initiate Transfer

class="flex flex-row space-x-[10px]"> - Custom Query Param Name + {{ + 'contract_agreement_page.cus_query' | translate + }} - Requires "proxyQueryParams" to be "true". + + {{ 'contract_agreement_page.proxy_query' | translate }} + - Value + {{ 'general.value' | translate }} Initiate Transfer color="warn" style="height: 54px; margin-top: 4px; margin-left: 8px" (click)="form.onHttpQueryParamsRemoveClick(i)"> - Remove + {{ 'general.remove' | translate }}
@@ -306,7 +338,7 @@

Initiate Transfer

mat-button color="accent" (click)="form.onHttpQueryParamsAddClick()"> - Add Custom Query Param + {{ 'contract_agreement_page.add_cus_query' | translate }}
@@ -314,24 +346,32 @@

Initiate Transfer

- Custom Request Body Content Type + {{ + 'contract_agreement_page.req_cont' | translate + }} - Requires "proxyBody" to be "true". + + {{ 'contract_agreement_page.proxy_body' | translate }} + - Custom Request Body + {{ + 'contract_agreement_page.req_body' | translate + }} - Requires "proxyBody" to be "true". + + {{ 'contract_agreement_page.proxy_body' | translate }} @@ -347,8 +387,12 @@

Initiate Transfer

mat-button [color]="ctrl.value ? 'warn' : 'accent'" (click)="ctrl.setValue(!ctrl.value)"> - {{ ctrl.value ? 'Hide' : 'Show' }} Http Datasource Parameterization - Fields + {{ + ctrl.value + ? ('general.hide' | translate) + : ('general.show' | translate) + }} + {{ 'contract_agreement_page.http_fields' | translate }}
@@ -362,7 +406,7 @@

Initiate Transfer

color="default" [mat-dialog-close]="null" [disabled]="loading"> - Cancel + {{ 'general.cancel' | translate }} diff --git a/src/app/routes/connector-ui/contract-definition-page/contract-definition-cards/contract-definition-cards.component.html b/src/app/routes/connector-ui/contract-definition-page/contract-definition-cards/contract-definition-cards.component.html index 2b364ddda..fa793d69a 100644 --- a/src/app/routes/connector-ui/contract-definition-page/contract-definition-cards/contract-definition-cards.component.html +++ b/src/app/routes/connector-ui/contract-definition-page/contract-definition-cards/contract-definition-cards.component.html @@ -1,3 +1,10 @@ + +
- Contract Definition + {{ + 'general.con_def' | translate + }}
- Access Policy + {{ 'general.access_pol' | translate }}
- Contract Policy + {{ 'general.policy' | translate }}
this.edcApiService.deleteContractDefinition(card.id).pipe( diff --git a/src/app/routes/connector-ui/contract-definition-page/contract-definition-editor-dialog/contract-definition-editor-dialog.component.html b/src/app/routes/connector-ui/contract-definition-page/contract-definition-editor-dialog/contract-definition-editor-dialog.component.html index a7c43daa4..e56cce859 100644 --- a/src/app/routes/connector-ui/contract-definition-page/contract-definition-editor-dialog/contract-definition-editor-dialog.component.html +++ b/src/app/routes/connector-ui/contract-definition-page/contract-definition-editor-dialog/contract-definition-editor-dialog.component.html @@ -1,4 +1,11 @@ -

Create New Contract Definition

+ + +

{{ 'contract_agreement_page.new_def' | translate }}

@@ -16,20 +23,20 @@

Create New Contract Definition

@@ -37,7 +44,7 @@

Create New Contract Definition

diff --git a/src/app/routes/connector-ui/contract-definition-page/contract-definition-page.module.ts b/src/app/routes/connector-ui/contract-definition-page/contract-definition-page.module.ts index 2791500c1..26db52a58 100644 --- a/src/app/routes/connector-ui/contract-definition-page/contract-definition-page.module.ts +++ b/src/app/routes/connector-ui/contract-definition-page/contract-definition-page.module.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {CommonModule} from '@angular/common'; import {NgModule} from '@angular/core'; import {FormsModule, ReactiveFormsModule} from '@angular/forms'; @@ -18,6 +24,7 @@ import {MatSlideToggleModule} from '@angular/material/slide-toggle'; import {MatStepperModule} from '@angular/material/stepper'; import {MatTooltipModule} from '@angular/material/tooltip'; import {RouterModule} from '@angular/router'; +import {TranslateModule} from '@ngx-translate/core'; import {CatalogModule} from '../../../component-library/catalog/catalog.module'; import {JsonDialogModule} from '../../../component-library/json-dialog/json-dialog.module'; import {PipesAndDirectivesModule} from '../../../component-library/pipes-and-directives/pipes-and-directives.module'; @@ -35,7 +42,7 @@ import {PolicySelectComponent} from './policy-select/policy-select.component'; FormsModule, ReactiveFormsModule, RouterModule, - + TranslateModule, // Angular Material MatBadgeModule, MatButtonModule, diff --git a/src/app/routes/connector-ui/contract-definition-page/contract-definition-page/contract-definition-page.component.html b/src/app/routes/connector-ui/contract-definition-page/contract-definition-page/contract-definition-page.component.html index e8e4f1444..4794074e1 100644 --- a/src/app/routes/connector-ui/contract-definition-page/contract-definition-page/contract-definition-page.component.html +++ b/src/app/routes/connector-ui/contract-definition-page/contract-definition-page/contract-definition-page.component.html @@ -1,3 +1,10 @@ + +
@@ -5,7 +12,9 @@ class="search-form-field" appearance="outline" color="accent"> - Search contract definitions + {{ + 'contract_agreement_page.search_def' | translate + }} search @@ -58,7 +67,7 @@ " class="min-h-[35rem]" [emptyMessage]=" - 'No contract definition found with given filter.' + 'contract_agreement_page.con_def' | translate ">
dataOffers.length), Fetched.wrap({ - failureMessage: 'Failed fetching data offers.', + failureMessage: this.translateService.instant( + 'dashboard_page.failed_offers', + ), }), map((numOffers) => ({numCatalogEntries: numOffers})), ); @@ -77,22 +87,37 @@ export class DashboardPageDataService { direction: 'CONSUMING' | 'PROVIDING', ): DonutChartData { const amounts: {label: string; amount: number; color: string}[] = [ - {label: 'Completed', amount: transfers.numOk, color: '#b2e061'}, - {label: 'In Progress', amount: transfers.numRunning, color: '#7eb0d5'}, - {label: 'Error', amount: transfers.numError, color: '#fd7f6f'}, + { + label: this.translateService.instant('dashboard_page.completed'), + amount: transfers.numOk, + color: '#b2e061', + }, + { + label: this.translateService.instant('dashboard_page.progress'), + amount: transfers.numRunning, + color: '#7eb0d5', + }, + { + label: this.translateService.instant('dashboard_page.error'), + amount: transfers.numError, + color: '#fd7f6f', + }, ].filter((it) => it.amount); const total = transfers.numTotal; - + const emptyMessage = + direction === 'CONSUMING' + ? this.translateService.instant('dashboard_page.no_transfer') + : this.translateService.instant('dashboard_page.no_transfer2'); return { - totalLabel: 'Total', + totalLabel: this.translateService.instant('general.total'), totalValue: total, isEmpty: !total, - emptyMessage: `No ${direction} transfer processes.`, + emptyMessage: emptyMessage, labels: amounts.map((it) => it.label), datasets: [ { - label: 'Number of Transfer Processes', + label: this.translateService.instant('dashboard_page.num_transfer'), data: amounts.map((it) => it.amount), backgroundColor: amounts.map((it) => it.color), }, @@ -105,22 +130,30 @@ export class DashboardPageDataService { return combineLatest([ this.lastCommitInfoService.getLastCommitInfoData().pipe( Fetched.wrap({ - failureMessage: 'Failed fetching Env and Jar Last Commit Data', + failureMessage: this.translateService.instant( + 'dashboard_page.failed_env', + ), }), ), this.lastCommitInfoService.getUiBuildDateDetails().pipe( Fetched.wrap({ - failureMessage: 'Failed fetching UI Last Build Date Data', + failureMessage: this.translateService.instant( + 'dashboard_page.failed_ui_build', + ), }), ), this.lastCommitInfoService.getUiCommitDetails().pipe( Fetched.wrap({ - failureMessage: 'Failed fetching UI Last Commit Data', + failureMessage: this.translateService.instant( + 'dashboard_page.failed_ui', + ), }), ), this.edcApiService.getDashboardPage().pipe( Fetched.wrap({ - failureMessage: 'Failed fetching Dashboard Page Data', + failureMessage: this.translateService.instant( + 'dashboard_page.failed_dashboard', + ), }), ), ]).pipe( diff --git a/src/app/routes/connector-ui/dashboard-page/dashboard-page/dashboard-page.component.html b/src/app/routes/connector-ui/dashboard-page/dashboard-page/dashboard-page.component.html index 0e6c3a83d..22249f70a 100644 --- a/src/app/routes/connector-ui/dashboard-page/dashboard-page/dashboard-page.component.html +++ b/src/app/routes/connector-ui/dashboard-page/dashboard-page/dashboard-page.component.html @@ -1,9 +1,20 @@ + +
- Incoming Data - Transfer Processes + {{ + 'dashboard_page.inc_data' | translate + }} + {{ + 'dashboard_page.trans_pro' | translate + }}
@@ -11,8 +22,12 @@ - Outgoing Data - Transfer Processes + {{ + 'dashboard_page.out_data' | translate + }} + {{ + 'dashboard_page.trans_pro' | translate + }}
@@ -23,33 +38,37 @@
- Connector Properties - Additional Properties + {{ + 'dashboard_page.conn_prop' | translate + }} + {{ + 'dashboard_page.add_prop' | translate + }} @@ -59,7 +78,9 @@
- Get Managed EDC - Connector-as-a-Service + {{ + 'dashboard_page.managed_edc' | translate + }} + {{ + 'dashboard_page.conn_service' | translate + }}

- To join data spaces like Mobility Data Space or - Catena-X within minutes, consider the managed solution by + {{ 'dashboard_page.descrip4' | translate }} sovity - - the Connector-as-a-Service (CaaS) based on open-source - software enriched with key enterprise features. + {{ 'dashboard_page.descrip5' | translate }}

- Contact + {{ 'dashboard_page.contact' | translate }} - About EDC - Eclipse Dataspace Components + {{ 'dashboard_page.about' | translate }} + {{ + 'dashboard_page.eclipse' | translate + }}

- The Eclipse Dataspace Components framework facilitates - sovereign, inter-organizational data exchange. + {{ 'dashboard_page.descrip6' | translate }}

- It implements the International Data Spaces standard (IDS) as - well as relevant protocols associated with GAIA-X. + {{ 'dashboard_page.descrip7' | translate }}

- The framework is designed as extensible as possible to encourage - integrations into various data ecosystems. + {{ 'dashboard_page.descrip8' | translate }}

- About EDC UI - Data Dashboard + {{ + 'dashboard_page.about_ui' | translate + }} + {{ + 'dashboard_page.data_dashboard' | translate + }}

- Example use cases, that you can try out with this application, are: + {{ 'dashboard_page.descrip9' | translate }}

diff --git a/src/app/routes/connector-ui/language-selector/language-selector.component.html b/src/app/routes/connector-ui/language-selector/language-selector.component.html new file mode 100644 index 000000000..cd8f79a5f --- /dev/null +++ b/src/app/routes/connector-ui/language-selector/language-selector.component.html @@ -0,0 +1,33 @@ + + +
+ + {{ 'general.language' | translate }} +
+ Selected Flag + + + Custom Icon + {{ language.name }} + + +
+
+
diff --git a/src/app/routes/connector-ui/language-selector/language-selector.component.scss b/src/app/routes/connector-ui/language-selector/language-selector.component.scss new file mode 100644 index 000000000..15b9b70d0 --- /dev/null +++ b/src/app/routes/connector-ui/language-selector/language-selector.component.scss @@ -0,0 +1,16 @@ +/*! + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ + +.container { + top: 0px; + right: 0px; + max-width: 150px; + text-align: right; +} + +.flag { + height: 1em; +} diff --git a/src/app/routes/connector-ui/language-selector/language-selector.component.spec.ts b/src/app/routes/connector-ui/language-selector/language-selector.component.spec.ts new file mode 100644 index 000000000..ab03cd2dc --- /dev/null +++ b/src/app/routes/connector-ui/language-selector/language-selector.component.spec.ts @@ -0,0 +1,26 @@ +/* + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ +import {ComponentFixture, TestBed} from '@angular/core/testing'; +import {LanguageSelectorComponent} from './language-selector.component'; + +describe('LanguageSelectorComponent', () => { + let component: LanguageSelectorComponent; + let fixture: ComponentFixture; + + beforeEach(async () => { + await TestBed.configureTestingModule({ + declarations: [LanguageSelectorComponent], + }).compileComponents(); + + fixture = TestBed.createComponent(LanguageSelectorComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); +}); diff --git a/src/app/routes/connector-ui/language-selector/language-selector.component.ts b/src/app/routes/connector-ui/language-selector/language-selector.component.ts new file mode 100644 index 000000000..c38e34998 --- /dev/null +++ b/src/app/routes/connector-ui/language-selector/language-selector.component.ts @@ -0,0 +1,36 @@ +/* + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ +// language-selector.component.ts +import {Component} from '@angular/core'; +import {TranslateService} from '@ngx-translate/core'; + +@Component({ + selector: 'app-language-selector', + templateUrl: './language-selector.component.html', + styleUrls: ['./language-selector.component.scss'], +}) +export class LanguageSelectorComponent { + supportedLanguages = [ + {code: 'en', name: 'English'}, + {code: 'de', name: 'Deutsch'}, + // Add more languages as needed + ]; + + selectedLanguage!: string; + constructor(private translateService: TranslateService) {} + ngOnInit(): void { + // Set the initial selected language from localStorage + this.selectedLanguage = localStorage.getItem('selectedLanguage') || 'en'; + this.translateService.use(this.selectedLanguage); + } + + onLanguageChange(): void { + // Update selected language in localStorage + localStorage.setItem('selectedLanguage', this.selectedLanguage); + + this.translateService.use(this.selectedLanguage); + } +} diff --git a/src/app/routes/connector-ui/policy-definition-create-page/policy-definition-create-page/policy-definition-create-page.component.ts b/src/app/routes/connector-ui/policy-definition-create-page/policy-definition-create-page/policy-definition-create-page.component.ts index 354ef8568..c5cf9447a 100644 --- a/src/app/routes/connector-ui/policy-definition-create-page/policy-definition-create-page/policy-definition-create-page.component.ts +++ b/src/app/routes/connector-ui/policy-definition-create-page/policy-definition-create-page/policy-definition-create-page.component.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {Component, OnDestroy} from '@angular/core'; import {Router} from '@angular/router'; import {Subject} from 'rxjs'; @@ -5,6 +11,7 @@ import {finalize, takeUntil} from 'rxjs/operators'; import {PolicyDefinitionCreateDto} from '@sovity.de/edc-client'; import {ExpressionFormControls} from '../../../../component-library/policy-editor/editor/expression-form-controls'; import {ExpressionFormHandler} from '../../../../component-library/policy-editor/editor/expression-form-handler'; +import {TranslateService} from '@ngx-translate/core'; import {EdcApiService} from '../../../../core/services/api/edc-api.service'; import {NotificationService} from '../../../../core/services/notification.service'; import {ValidationMessages} from '../../../../core/validators/validation-messages'; @@ -29,6 +36,7 @@ export class PolicyDefinitionCreatePageComponent implements OnDestroy { public validationMessages: ValidationMessages, private edcApiService: EdcApiService, private notificationService: NotificationService, + private translateService: TranslateService, ) {} onSave() { @@ -46,12 +54,13 @@ export class PolicyDefinitionCreatePageComponent implements OnDestroy { ) .subscribe({ complete: () => { - this.notificationService.showInfo('Successfully created policy.'); + this.notificationService.showInfo(this.translateService.instant('notification.succ_pol')); this.router.navigate(['/policies']); }, error: (error) => { - console.error('Failed creating Policy!', error); - this.notificationService.showError('Failed creating policy!'); + const fai_pol = this.translateService.instant('notification.fai_pol'); + console.error(fai_pol, error); + this.notificationService.showError(fai_pol); }, }); } diff --git a/src/app/routes/connector-ui/policy-definition-page/policy-cards/policy-cards.component.html b/src/app/routes/connector-ui/policy-definition-page/policy-cards/policy-cards.component.html index a0fabfb9b..97b26e654 100644 --- a/src/app/routes/connector-ui/policy-definition-page/policy-cards/policy-cards.component.html +++ b/src/app/routes/connector-ui/policy-definition-page/policy-cards/policy-cards.component.html @@ -1,3 +1,10 @@ + +
- Policy + {{ 'general.pol' | translate }} ; const data: JsonDialogData = { title: policyCard.id, - subtitle: 'Policy', + subtitle: this.translateService.instant('general.pol'), icon: 'policy', objectForJson: policyCard.objectForJson, toolbarButton: { - text: 'Delete', + text: this.translateService.instant('general.delete'), icon: 'delete', - confirmation: ConfirmDialogModel.forDelete('policy', policyCard.id), + confirmation: ConfirmDialogModel.forDelete( + 'policy', + policyCard.id, + this.translateService, + ), action: () => this.edcApiService.deletePolicyDefinition(policyCard.id).pipe( tap(() => { diff --git a/src/app/routes/connector-ui/policy-definition-page/policy-definition-page.module.ts b/src/app/routes/connector-ui/policy-definition-page/policy-definition-page.module.ts index 3d6baaabd..8edb031b3 100644 --- a/src/app/routes/connector-ui/policy-definition-page/policy-definition-page.module.ts +++ b/src/app/routes/connector-ui/policy-definition-page/policy-definition-page.module.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {CommonModule} from '@angular/common'; import {NgModule} from '@angular/core'; import {FormsModule, ReactiveFormsModule} from '@angular/forms'; @@ -16,6 +22,7 @@ import {MatProgressSpinnerModule} from '@angular/material/progress-spinner'; import {MatSelectModule} from '@angular/material/select'; import {MatTooltipModule} from '@angular/material/tooltip'; import {RouterModule} from '@angular/router'; +import {TranslateModule} from '@ngx-translate/core'; import {JsonDialogModule} from '../../../component-library/json-dialog/json-dialog.module'; import {PolicyEditorModule} from '../../../component-library/policy-editor/policy-editor.module'; import {UiElementsModule} from '../../../component-library/ui-elements/ui-elements.module'; @@ -29,6 +36,7 @@ import {PolicyDefinitionPageComponent} from './policy-definition-page/policy-def FormsModule, ReactiveFormsModule, RouterModule, + TranslateModule, // Angular Material MatBadgeModule, diff --git a/src/app/routes/connector-ui/policy-definition-page/policy-definition-page/policy-definition-page.component.html b/src/app/routes/connector-ui/policy-definition-page/policy-definition-page/policy-definition-page.component.html index 1e34bee36..acf31d2c7 100644 --- a/src/app/routes/connector-ui/policy-definition-page/policy-definition-page/policy-definition-page.component.html +++ b/src/app/routes/connector-ui/policy-definition-page/policy-definition-page/policy-definition-page.component.html @@ -1,3 +1,10 @@ + +
@@ -5,7 +12,9 @@ class="search-form-field" appearance="outline" color="accent"> - Search policies + {{ + 'policy_definition_page.search_pol' | translate + }} search @@ -55,7 +64,9 @@ !policyList.data.policyCards.length) " class="min-h-[35rem]" - [emptyMessage]="'No policy found with given filter.'"> + [emptyMessage]=" + 'policy_definition_page.no_pol' | translate + ">
+
@@ -24,7 +31,9 @@ !transferProcessesList.data.transferProcesses.length " class="min-h-[35rem]" - [emptyMessage]="'No transfer history found.'"> + [emptyMessage]=" + 'tranfer_history_page.no_trans' | translate + ">
- Direction + {{ 'general.direction' | translate }} @@ -47,14 +56,16 @@ - Last updated + {{ 'general.updated' | translate }} - Asset + + {{ 'general.asset' | translate }} +
- State + {{ 'general.state' | translate }}
@@ -104,7 +115,7 @@ - Counterparty {{ participantIdLocalization.participantId }} + {{ 'transfer_history_page.counter_id' | translate }} {{ item.counterPartyParticipantId }} @@ -112,7 +123,7 @@ - Counterparty Connector Endpoint + {{ 'transfer_history_page.counter_endpoint' | translate }} {{ item.counterPartyConnectorEndpoint }} @@ -120,14 +131,14 @@ - Details + {{ 'general.detail' | translate }} - {{ 'Show Details' }} + {{ 'general.details' | translate }} diff --git a/src/app/routes/connector-ui/transfer-history-page/transfer-history-page/transfer-history-page.component.ts b/src/app/routes/connector-ui/transfer-history-page/transfer-history-page/transfer-history-page.component.ts index abc70ba92..eae19698a 100644 --- a/src/app/routes/connector-ui/transfer-history-page/transfer-history-page/transfer-history-page.component.ts +++ b/src/app/routes/connector-ui/transfer-history-page/transfer-history-page/transfer-history-page.component.ts @@ -1,3 +1,9 @@ +/* + * Copyright (c) 2021-2024. sovity GmbH + * Copyright (c) 2024. Fraunhofer Institute for Applied Information Technology FIT + * Contributors: + * - Fraunhofer FIT: Internationalization and German Localization + */ import {Component, OnDestroy, OnInit} from '@angular/core'; import { EMPTY, @@ -9,6 +15,7 @@ import { switchMap, } from 'rxjs'; import {catchError, map} from 'rxjs/operators'; +import {TranslateService} from '@ngx-translate/core'; import { TransferHistoryEntry, TransferHistoryPage, @@ -51,13 +58,16 @@ export class TransferHistoryPageComponent implements OnInit, OnDestroy { private notificationService: NotificationService, private jsonDialogService: JsonDialogService, public participantIdLocalization: ParticipantIdLocalization, + private translateService: TranslateService, ) {} onTransferHistoryDetailsClick(item: TransferHistoryEntry) { this.jsonDialogService.showJsonDetailDialog( { title: item.assetName ?? item.assetId, - subtitle: 'Transfer History Details', + subtitle: this.translateService.instant( + 'transfer_history_page.subtitle', + ), icon: 'assignment', objectForJson: item, }, @@ -79,8 +89,9 @@ export class TransferHistoryPageComponent implements OnInit, OnDestroy { this.assetDetailDialogService.open(data, this.ngOnDestroy$); }, error: (error) => { - console.error('Failed to fetch asset details!', error); - this.notificationService.showError('Failed to fetch asset details!'); + const fai_fet = this.translateService.instant('notification.fai_fet'); + console.error(fai_fet, error); + this.notificationService.showError(fai_fet); }, }); } diff --git a/src/assets/i18n/de.json b/src/assets/i18n/de.json new file mode 100644 index 000000000..0b22ffb34 --- /dev/null +++ b/src/assets/i18n/de.json @@ -0,0 +1,294 @@ +{ + "general": { + "close": "Schließen", + "delete": "Löschen", + "error": "Fehler", + "confirm": "Bestätigen", + "edit": "Bearbeiten", + "remove": "Entfernen", + "add": "Hinzufügen", + "cancel": "Abbrechen", + "create": "Erstellen", + "update": "Aktualisieren", + "refresh": "Aktualisieren", + "total": "Total", + "details": "Zeige Details", + "detail": "Details", + "warn": "Warnung", + "title": "Titel", + "disable": "Deaktivieren", + "enable": "Aktivieren", + "show": "Zeige", + "hide": "Verberge", + "description": "Beschreibung", + "loading": "Lädt...", + "loading1": "Lädt", + "loading2": "Lädt noch...", + "language": "Sprache", + "value": "Wert", + "method": "Methode", + "method_para": "Parametrisierung der Methode", + "path": "Pfad", + "params": "Abfrageparameter", + "add_properties": "Weitere Eigenschaften", + "category": "Datenkategorie", + "subcategory": "Datenunterkategorie", + "model": "Datenmodell", + "transport": "Transportmodus", + "geo_method": "Georeferenz-Methode", + "geo_location": "Geo-Standort", + "sovereign": "Souverän", + "frequency": "Häufigkeit der Datenaktualisierung", + "nuts": "NUTS-Standort", + "data": "Datenbeispiel", + "show_data": "Zeige Datenbeispiel", + "files": "Referenzdateien", + "show_files": "Zeige Referenzdateien", + "coverage": "Zeitlicher Geltungsbereich", + "conditions": "Nutzungsbedingungen", + "pol": "Richtlinie", + "policies": "Richtlinien", + "irr_pol": "Irreguläre Richtlinie", + "policy": "Vertragsrichtlinien", + "offer": "Vertragsangebot", + "con_def": "Vertragsdefinition", + "cons": "Einschränkungen", + "body": "Körper", + "type": "Typ", + "state": "Status", + "updated": "Zuletzt aktualisiert", + "direction": "Richtung", + "contract": "Vertragsabschluss", + "access_pol": "Zugriffsrichtlinie", + "assets": "Datenbestände", + "asset": "Datenbestand", + "consuming": "Eingehend", + "providing": "Ausgehend", + "endpoint": "Konnektor Endpunkt", + "endpoint_doc": "Endpunkt Dokumentation", + "content": "Inhaltstyp", + "publisher": "Anbieter", + "st_license": "Standardlizenz", + "ad_info": "Weitere Informationen", + "id": "Vertragsangebot ID", + "oth_connector": "Gegenseite", + "signed": "Abgeschlossen", + "auth": "Authentifizierung", + "add_auth": "Authentifizierung hinzufügen", + "header_sec": "Kopfzeile mit Vault Passwort", + "header_val": "Kopfzeile mit Wert", + "auth_header": "Authentifizierungskopfzeile Name", + "auth_value": "Authentifizierungskopfzeile Wert", + "vault_secret": "Vault-Passwort-Name", + "rem_auth": "Entferne Authentifizierung", + "add_header": "Zusätzliche Kopfzeilen", + "header_name": "Kopfzeilen-Name", + "header_value": "Kopfzeilen-Wert", + "add_add_header": "Füge zusätzliche Kopfzeile hinzu" + }, + "tooltip": { + "negotiate": "Sie können keine Verträge mit Ihrem eigenen Konnektor aushandeln.", + "details": "Klicken Sie hier für Details", + "failed_details": "Klicken Sie hier für fehlgeschlagene Katalogdetails", + "clipboard": "In die Zwischenablage kopieren" + }, + "notification": { + "starting_neg": "Scheitern bei der Aufnahme von Verhandlungen.", + "negotiation": "Gescheiterte Vertragsverhandlungen.", + "compl_negotiation": "Vertragsverhandlungen abgeschlossen!", + "asset": "Datei erfolgreich gespeichert.", + "failed_asset": "Fehlgeschlagene Speichervorgang!", + "failed_refresh": "Aktualisierung der Datenbestände fehlgeschlagen!", + "succ_pol": "Erfolgreich erstellte Richtlinie.", + "fai_pol": "Fehlgeschlagene Richtlinie", + "fai_fet": "Datei-Details konnten nicht abgerufen werden!" + }, + "component_library": { + "delete_title": "Bestätigung der Löschung", + "delete_one": "Bitte bestätigen Sie, dass Sie löschen möchten", + "delete_two": ". Diese Aktion kann nicht rückgängig gemacht werden.", + "t_history": "Übertragungshistorie", + "negotiate": "Verhandeln", + "negotiating": "Verhandeln...", + "succ_negotiating": "Erfolgreich verhandelt", + "transfer": "Übertragung", + "no_description": "Keine Beschreibung", + "show_more": "Zeige mehr", + "show_less": "Zeige weniger", + "organization": "Organisation", + "http_param": "HTTP-Datenquellen-Parametrisierung", + "policy_details": "Zeige Richtlinien Details", + "content": "Inhaltstyp", + "at": "Erstellt am", + "up_at": "Aktualisiert am", + "oth_connector": "Gegenpart", + "participant_id": "Teilnehmer ID", + "connector_id": "Konnector ID", + "json_ld": "Zeige JSON-LD", + "no_transfer": "Kein Übertragungsprozess bisher gestartet.", + "json": "Bereinigtes JSON", + "agree": "Ich stimme den Allgemeinen Geschäftsbedingungen zu.", + "accept_licence": "Hiermit erkläre ich mich damit einverstanden, dass ich durch Drücken der Schaltfläche \"Bestätigen\" die mit dem Angebot des Anbieters verbundenen Lizenzbedingungen, Richtlinien und zusätzlichen Nutzungsbedingungen, einschließlich aller Urheberrechtshinweise, akzeptiere.", + "data_offer": "Allgemeine Geschäftsbedingungen für das Datenangebot" + }, + "services": { + "env_version": "Umgebungs Version", + "failed_loading": "Fehler beim Laden von Verbindungsinformationen", + "curator_url": "Kurator-URL", + "curator_org": "Name der Kurator Organisation", + "maintainer": "Name der betreuenden Organisation", + "main_url": "URL betreuende Organisation" + }, + "asset_page": { + "information": "Generelle Informationen", + "asset_id": "Datenbestand-ID", + "keywords": "Passwort", + "legal_name": "Rechtlicher Name des Dateninhabers", + "add_file": "Referenzdatei hinzufügen", + "file_des": "Beschreibung der Referenzdateien", + "info_file": "Zusätzliche Informationen zu den Referenzdateien", + "instructions": "Zusätzliche, rechtlich nicht relevante Nutzungshinweise (z. B. wie der Datensatz zu zitieren ist)", + "datasource_info": "Datenquellen Information", + "datasource": "Datenquelle", + "datasource_config": "Benutzerdefinierte Datenquellenkonfiguration (JSON)", + "provide": "Die konsumierende Seite muss eine benutzerdefinierte HTTP-Methode mit aktivierter Methodenparametrisierung bereitstellen.", + "http_subpath": "Die konsumierende Seite muss einen benutzerdefinierten HTTP-Unterpfad bereitstellen, bei dem die Methodenparametrisierung aktiviert ist. Der benutzerdefinierte HTTP-Teilpfad wird an den Basispfad angehängt.", + "path_para": "Pfadparametrisierung", + "query_para": "Abfrageparameter", + "query_name": "Abfrage Parametername", + "default_query": "Wenn die Parametrisierung von Abfrageparametern aktiviert ist, werden die Standardabfrageparameter und die vom Verbraucher bereitgestellten Abfrageparameter zusammengeführt.", + "query_parameter": " Parametrisierung von Abfrageparametern", + "info_body": "Der Anfragekörper kann nur von der Verbraucherseite aus festgelegt werden, wenn die Parametrisierung aktiviert ist.", + "request_body": "Anfragekörper", + "request_para": "Parametrisierung des Anfragekörpers", + "search_assets": "Durchsuche Datenbestände", + "create_assets": "Erstelle Datenbestände", + "create_asset": " Erstelle neuen Datenbestand", + "edit_asset": "Bearbeite Datenbestand", + "no_assets": "Keine Datenbestände mit gegebenem Filter gefunden.", + "descrip": "Die Beschreibung nutzt", + "add_loc": "Füge Ort hinzu", + "add_sample": "Füge Beispieldaten hinzu" + }, + "catalog_browser_page": { + "fetch": "Status abrufen", + "endpoint_catalogs": "Andere Kataloge für Verbindungs-Endpunkte", + "search": "Katalogssuche", + "con_endpoints": "Konnektor Endpunkte", + "enter_endpoints": "Bitte geben Sie andere Connector-Endpunkte an, um Kataloge zu holen.", + "no_contract_offers": "Keine Vertragsangebote mit diesem Filter gefunden", + "contract": "Vertragsangebot", + "usage": "Bereits verwendet" + }, + "contract_agreement_page": { + "search_agree": "Suche nach Vertragsvereinbarungen...", + "no_agree": "Noch keine vertraglichen Vereinbarungen.", + "no_agree_found": "Keine Vertragsvereinbarungen mit gegebenem Filter gefunden.", + "con_agree": "Verbrauchen von Vertragsvereinbarungen", + "prov_agree": "Bereitstellung von Vertragsvereinbarungen", + "ini_transfer": "Übertragung einleiten", + "http_fields": "Http-Datenquellenparametrisierung Felder", + "http_para": "Http-Datenquellen-Parametrisierung", + "http_message": "Wenn das Datenangebot auf der Anbieterseite vom Typ HttpData ist und bestimmte Datenquellenfelder gesetzt sind, können bestimmte Teile der Anfrage an die Datenquelle von der Verbraucherseite aus angepasst werden und werden bei der Einleitung der Übertragung an den anderen Konnektor übergeben. Dadurch kann ein Asset mehr als nur eine Art von Daten enthalten, was zusätzliche Filterung oder sogar die gemeinsame Nutzung ganzer APIs mit mehreren Datensätzen über ein einziges Asset und einen einzigen Vertrag ermöglicht.", + "res_url": "Die resultierende URL sieht wie folgt aus", + "proxy_body": "Erfordert, dass Anfragekörper wahr ist.", + "proxy_query": "Erfordert, dass Anfrageparameter wahr sind.", + "proxy_path": "Erfordert, dass Anfragepfad wahr ist.", + "proxy_method": "Erfordert, dass Anfragemethode wahr ist. ", + "datasink": "Datasenke", + "cus_datasink": "Benutzerdefinierte Datasenke-Konfiguration (JSON)", + "cus_transfer": "Benutzerdefinierte Übertragungsprozess-Anforderung (JSON)", + "json_hint": "JSON-LD Werte für edc:connectorId, edc:contractId, edc:connectorId und edc:connectorAddress werden überschrieben.", + "cus_meth": "Benutzerdefinierte Methode", + "cus_query": "Benutzerdefinierte Abfrage Parameter Name", + "add_cus_query": "Benutzerdefinierten Abfrage-Parameter hinzufügen", + "req_cont": "Benutzerdefinierter Inhaltstyp für Anfragen", + "req_body": "Anfragekörper", + "cus_sub": "Benutzerdefinierter Unterpfad", + "new_def": "Erstelle neue Vertragsdefinition", + "search_def": "Suche Vertragsdefinition", + "create_def": "Vertragsdefinition erstellen", + "con_def": "Keine Vertragsdefinition mit gegebenem Filter gefunden." + }, + "dashboard_page": { + "error": "Fehler", + "completed": "Abgeschlossen", + "progress": "In Arbeit", + "no_transfer": "Keine ausgehenden Übertragungen", + "no_transfer2": "Keine eingehenden Übertragungen", + "num_transfer": "Anzahl der Übertragungsvorgänge", + "failed_ui_build": "Abruf der Daten des letzten Baudatums der Benutzeroberfläche fehlgeschlagen", + "failed_ui": "Abruf der letzten UI Commit Daten fehlgeschlagen", + "failed_env": "Abruf von Env und Jar letzten Commit Daten fehlgeschlagen", + "failed_dashboard": "Abruf von Dashboard-Seitendaten fehlgeschlagen", + "failed_offers": "DATENÜBERTRAGUNG FEHLGESCHLAGEN", + "inc_data": "Eingehende Daten", + "trans_pro": "Übertragungsvorgänge", + "out_data": "Ausgehende Daten", + "conn_prop": "Konnektor Eigenschaften", + "add_prop": "Zusätzliche Eigenschaften", + "edc_conn": "EDC Konnektor", + "descrip": "Geben Sie den folgenden Konnektor-Endpunkt frei, um anderen den Zugriff auf den Katalog Ihres EDC Konnektors zu ermöglichen. Dies ist vor allem bei der Verwendung von Datenangeboten mit eingeschränktem Konnektor nützlich, die in Brokern nicht angezeigt werden.", + "conn_end": "Konnektor Endpunkte", + "api_url": "Management API URL", + "edition_edc": "Basisausgabe EDC", + "page": "klicken.", + "descrip2": "Dieser EDC Konnektor auf der Abo-Ebene Basic wird von sovity bereitgestellt, um Ihre ersten Schritte im Mobility Data Space (MDS) zu ermöglichen.", + "descrip3": "Für zusätzliche Funktionen und erweiterte Kapazitäten können Sie uns gerne kontaktieren.", + "descrip4": "Um Datenräume wie Mobility Data Space oder Catena-X innerhalb weniger Minuten zu verbinden, betrachten Sie die verwaltete Lösung von", + "descrip5": "- den Connector-as-a-Service (CaaS), der auf Open-Source-Software basiert und mit wichtigen Unternehmensfunktionen angereichert ist.", + "descrip6": "Das Eclipse Dataspace Components Framework ermöglicht einen souveränen, organisationsübergreifenden Datenaustausch.", + "descrip7": "Es implementiert den internationalen Datenraumstandard (IDS) sowie die mit GAIA-X verbundenen relevanten Protokolle.", + "descrip8": "Der Aufbau ist so erweiterbar wie möglich gestaltet, um die Integration in verschiedene Datenökosysteme zu fördern.", + "descrip9": "Beispielhafte Anwendungsfälle, die Sie mit dieser Anwendung ausprobieren können, sind:", + "descrip10": "Zeigen Sie den Datenbestands-Katalog an, der Ihnen in Ihrem Datenraum zur Verfügung steht, unter", + "descrip11": "Verhandeln Sie einen Vertrag für die gemeinsame Nutzung von Daten in Ihrem Datenraum unter", + "descrip12": "Übertragen Sie ein Element in Ihren Datenraum indem Sie auf ", + "descrip13": "Sehen Sie sich an, welche Datenbestände in Ihrem Datenraum übertragen wurden, indem Sie auf", + "descrip14": "Betrachten und erstellen Sie Datenbstände indem Sie auf", + "descrip15": "Betrachten und erstellen Sie Richtlinien und wenden Sie diese auf Datenbestände in Ihrem Datenraum an, indem Sie auf", + "descrip16": "Veröffentlichen Sie ein neues Element in Ihrem Datenraum unter", + "descrip17": "Betrachten Sie ihre existierenden Verträge, indem Sie auf", + "contact": "Kontaktieren Sie uns", + "managed_edc": "Managed EDC", + "conn_service": "Konnektor als Dienstleistung", + "about": "Über EDC", + "eclipse": "Eclipse-Datenraum-Komponenten", + "about_ui": "Über EDC UI", + "data_dashboard": "Daten Dashboard", + "catalog": "Datenkatalog", + "contracts": "Verträge", + "transfer": "Übertragungshistorie", + "con_def": "Vertragsefinitions", + "your_def": "Deine Vertragsdefinitionen", + "your_assets": "Deine Datenbestände", + "your_pol": "Deine Richtlinien", + "pre_cat": "Vorkonfigurierte Kataloge", + "con_agree": "Vertragliche Vereinbarungen" + }, + "policy_definition_page": { + "create_pol": "Erstelle eine neue Richtlinie", + "time_res": "Zeitlich begrenzter Zeitraum", + "conn_res": "Anschluss mit vom Konnektor eingeschränkter Nutzung", + "date_range": "Datumsbereich", + "search_pol": "Durchsuche Richtlinien", + "create_policy": "Erstelle eine Richtlinie", + "no_pol": "Keine Richtlinie mit gegebenem Filter gefunden." + }, + "transfer_history_page": { + "subtitle": "Übertragungshistorie Details", + "no_trans": "Keine Übertragungshistorie gefunden.", + "counter_endpoint": "Gegenpart Konnektorendpunkt", + "counter_id": "Gegenpart Teilnehmer ID" + }, + "connector_ui": { + "dashboard": "Übersicht", + "catalog": "Katalogssuche", + "contracts": "Verträge", + "transfer": "Übertragungshistorie", + "assets": "Datenbestände", + "policies": "Richtlinien", + "contract": "Vertragsdefinition", + "logout": "Ausloggen" + } +} diff --git a/src/assets/i18n/en.json b/src/assets/i18n/en.json new file mode 100644 index 000000000..d8a8e6d42 --- /dev/null +++ b/src/assets/i18n/en.json @@ -0,0 +1,294 @@ +{ + "general": { + "close": "Close", + "delete": "Delete", + "error": "Error", + "confirm": "Confirm", + "edit": "Edit", + "remove": "Remove", + "add": "Add", + "cancel": "Cancel", + "create": "Create", + "update": "Update", + "refresh": "Refresh", + "total": "Total", + "details": "Show Details", + "detail": "Details", + "warn": "Warn", + "title": "Title", + "disable": "Disable", + "enable": "Enable", + "show": "Show", + "hide": "Hide", + "description": "Description", + "loading": "Loading...", + "loading1": "Loading", + "loading2": " Still Loading...", + "language": "Language", + "value": "Value", + "method": "Method", + "method_para": "Method Parameterization", + "path": "Path", + "params": "Query Params", + "add_properties": "Additional Properties", + "category": "Data Category", + "subcategory": "Data Subcategory", + "model": "Data Model", + "transport": "Transport Mode", + "geo_method": "Geo reference method", + "geo_location": "Geo Location", + "sovereign": "Sovereign", + "frequency": "Data Update Frequency", + "nuts": "NUTS Locations", + "data": "Data Samples", + "show_data": "Show Data Samples", + "files": "Reference Files", + "show_files": "Show Reference Files", + "coverage": "Temporal Coverage", + "conditions": "Conditions For Use", + "pol": "Policy", + "policies": "Policies", + "irr_pol": "Irregular Policy", + "policy": "Contract Policy", + "offer": "Contract Offer", + "con_def": "Contract Definition", + "cons": "Constraints", + "body": "Body", + "type": "Type", + "state": "State", + "updated": "Last updated", + "direction": "Direction", + "contract": "Contract Agreement", + "access_pol": "Access Policy", + "assets": "Assets", + "asset": "Asset", + "consuming": "Consuming", + "providing": "Providing", + "endpoint": "Connector Endpoint", + "endpoint_doc": "Endpoint Documentation", + "content": "Content Type", + "publisher": "Publisher", + "st_license": "Standard License", + "ad_info": "Advanced Information", + "id": "Contract Offer ID", + "oth_connector": "Other Connector", + "signed": "Signed", + "auth": "Authentication", + "add_auth": "Add Authentication", + "header_sec": "Header with Vault Secret", + "header_val": "Header with Value", + "auth_header": "Auth Header Name", + "auth_value": "Auth Header Value", + "vault_secret": "Vault Secret Name", + "rem_auth": "Remove Authentication", + "add_header": "Additional Headers", + "header_name": "Header Name", + "header_value": "Header Value", + "add_add_header": "Add Additional Header" + }, + "tooltip": { + "negotiate": "Cannot negotiate contracts with your own connector.", + "details": "Click for details", + "failed_details": "Click for failed catalog details", + "clipboard": "Copy to clipboard" + }, + "notification": { + "starting_neg": "Failure starting negotiation.", + "negotiation": "Failed negotiating contract.", + "compl_negotiation": "Contract Negotiation complete!", + "asset": "Successfully saved asset.", + "failed_asset": "Failed saving asset!", + "failed_refresh": "Failed refreshing asset list!", + "succ_pol": "Successfully created policy.", + "fai_pol": "Failed creating Policy!", + "fai_fet": "Failed to fetch asset details!" + }, + "component_library": { + "delete_title": "Deletion confirmation", + "delete_one": "Please confirm you want to delete", + "delete_two": ". This action cannot be undone.", + "t_history": "Transfer History", + "negotiate": "Negotiate", + "negotiating": "Negotiating...", + "succ_negotiating": "Successfully Negotiated", + "transfer": "Transfer", + "no_description": "No Description", + "show_more": "Show more", + "show_less": "Show less", + "organization": "Organization", + "http_param": "HTTP Data Source Parameterization", + "policy_details": "Show Policy Details", + "content": "Content Type", + "at": "Created At", + "up_at": "Updated At", + "oth_connector": "Other Connector", + "participant_id": "Participant ID", + "connector_id": "Connector ID", + "json_ld": "Show JSON-LD", + "no_transfer": "No transfer processes started yet.", + "json": "Cleaned JSON", + "agree": "I agree to the Data Offer Terms & Conditions", + "accept_licence": "Hereby I agree that by pressing the 'Confirm' button, I accept the license\n terms, policies, and additional conditions for use, including any copyright\n notices, associated with the provider's offer.", + "data_offer": "Data Offer Terms & Conditions" + }, + "services": { + "env_version": "Environment Version", + "failed_loading": "Failed loading connector information", + "curator_url": "Curator URL", + "curator_org": "Curator Organization Name", + "maintainer": "Maintainer Organization Name", + "main_url": "Maintainer URL" + }, + "asset_page": { + "information": "General Information", + "asset_id": "Asset ID", + "keywords": "Keywords", + "legal_name": "Legal name of the data owner", + "add_file": "Add reference file", + "file_des": "Reference files description", + "info_file": "Additional information regarding the reference files", + "instructions": "Additional not legally relevant usage instructions (e.g. how to cite the dataset)", + "datasource_info": "Datasource Information", + "datasource": "Datasource", + "datasource_config": "Custom Datasource Config (JSON)", + "provide": "The consuming side must provide a Custom HTTP Method with method parameterization enabled.", + "http_subpath": "The consuming side must provide a Custom HTTP Subpath with method parameterization is enabled. The Custom HTTP Subpath will be appended to the base path.", + "path_para": "Path Parameterization", + "query_para": "Query Params", + "query_name": "Query Param Name", + "default_query": "With query param parameterization enabled, the default query params and the query params provided by the consumer will be merged.", + "query_parameter": " Query Param Parameterization", + "info_body": "The request body can only be set from the consumer side, if parameterization is enabled.", + "request_body": "Request Body", + "request_para": "Request Body Parameterization", + "search_assets": "Search assets", + "create_assets": "Create assets", + "create_asset": " Create New Asset", + "edit_asset": "Edit Asset", + "no_assets": "No assets found with given filter.", + "descrip": "The description uses", + "add_loc": "Add location", + "add_sample": "Add data sample" + }, + "catalog_browser_page": { + "fetch": "Fetch Status", + "endpoint_catalogs": "Other Connector Endpoint Catalogs", + "search": "Search catalog", + "con_endpoints": "Connector Endpoints", + "enter_endpoints": "Please enter other connector endpoints to fetch catalogs.", + "no_contract_offers": "No contract offers found with this filter", + "contract": "Contract Offer", + "usage": "Already using" + }, + "contract_agreement_page": { + "search_agree": "Search contract agreements...", + "no_agree": "No contract agreements yet.", + "no_agree_found": "No contract agreements found with given filter.", + "con_agree": "Consuming Contract Agreements", + "prov_agree": "Providing Contract Agreements", + "ini_transfer": "Initiate Transfer", + "http_fields": "Http Datasource Parameterization Fields", + "http_para": "Http Datasource Parameterization", + "http_message": "When the data offer on the provider side is of the type HttpData and certain data source fields are set, certain parts of the request to the data source can be customized from the consumer side and will be passed to the other connector when initiating the transfer. This allows an asset to contain more than just one kind of data, allowing additional filtering or even sharing of entire APIs with multiple data sets via a single asset and a single contract.", + "res_url": "The resulting URL will look like", + "proxy_body": "Requires proxyBody to be true.", + "proxy_query": "Requires proxyQueryParams to be true", + "proxy_path": "Requires proxyPath to be true. ", + "proxy_method": "Requires proxyMethod to be true. ", + "datasink": "Datasink", + "cus_datasink": "Custom Datasink Config (JSON)", + "cus_transfer": "Custom Transfer Process Request (JSON)", + "json_hint": "JSON-LD values for edc:connectorId, edc:contractId, edc:connectorId and edc:connectorAddress will be overridden.", + "cus_meth": "Custom Method", + "cus_query": "Custom Query Param Name", + "add_cus_query": "Add Custom Query Param", + "req_cont": "Custom Request Body Content Type", + "req_body": "Custom Request Body", + "cus_sub": "Custom Subpath", + "new_def": "Create New Contract Definition", + "search_def": "Search contract definitions", + "create_def": "Create Contract Definition", + "con_def": "No contract definition found with given filter." + }, + "dashboard_page": { + "error": "Error", + "completed": "Completed", + "progress": "In Progress", + "no_transfer": "NO PROVIDING TRANSFER PROCESSES", + "no_transfer2": "NO CONSUMING TRANSFER PROCESSES", + "num_transfer": "Number of Transfer Processes", + "failed_ui_build": "Failed fetching UI Last Build Date Data", + "failed_ui": "Failed fetching UI Last Commit Data", + "failed_env": "Failed fetching Env and Jar Last Commit Data", + "failed_dashboard": "Failed fetching Dashboard Page Data", + "failed_offers": "Failed fetching data offers.", + "inc_data": "Incoming Data", + "trans_pro": "Transfer Processes", + "out_data": "Outgoing Data", + "conn_prop": "Connector Properties", + "add_prop": "Additional Properties", + "edc_conn": "EDC Connector", + "descrip": "Share the following Connector Endpoint to let others access your EDC Connector's catalog. This is especially useful when using connector-restricted data offers which won't show up in brokers.", + "conn_end": "Connector Endpoint", + "api_url": "Management API URL", + "edition_edc": "Basic Edition EDC", + "page": "Page", + "descrip2": "This EDC Connector on the subscription level Basic is provided by sovity to enable your first steps in the Mobility Data Space (MDS).", + "descrip3": "For additional features and advanced capacities, please feel free to contact us.", + "descrip4": "To join data spaces like Mobility Data Space or Catena-X within minutes, consider the managed solution by", + "descrip5": "- the Connector-as-a-Service (CaaS) based on open-source software enriched with key enterprise features.", + "descrip6": "The Eclipse Dataspace Components framework facilitates sovereign, inter-organizational data exchange.", + "descrip7": "It implements the International Data Spaces standard (IDS) as well as relevant protocols associated with GAIA-X.", + "descrip8": "The framework is designed as extensible as possible to encourage integrations into various data ecosystems.", + "descrip9": "Example use cases, that you can try out with this application, are:", + "descrip10": "View the asset catalog available to you in your Dataspace using the", + "descrip11": "Negotiate a contract for data sharing in your Dataspace using the", + "descrip12": "Transfer an asset in your Dataspace using the", + "descrip13": "View which assets have been transferred in your Dataspace in the", + "descrip14": "View and create assets using the", + "descrip15": "View and create policies and apply these to assets in your Dataspace using the", + "descrip16": "Publish a new asset into your Dataspace using the", + "descrip17": "View your existing contracts in the", + "contact": "Contact us", + "managed_edc": "Get Managed EDC", + "conn_service": "Connector-as-a-Service", + "about": "About EDC", + "eclipse": "Eclipse Dataspace Components", + "about_ui": "About EDC UI", + "data_dashboard": "Data Dashboard", + "catalog": "Catalog Browser", + "contracts": "Contracts", + "transfer": "Transfer History", + "con_def": "Contract Definitions", + "your_def": "Your Contract Definitions", + "your_assets": "Your Assets", + "your_pol": "Your Policies", + "pre_cat": "Preconfigured Catalogs", + "con_agree": "Contract Agreements" + }, + "policy_definition_page": { + "create_pol": "Create New Policy", + "time_res": "Time-Period-Restricted", + "conn_res": "Connector-Restricted-Usage", + "date_range": "Date Range", + "search_pol": "Search policies", + "create_policy": "Create Policy", + "no_pol": "No policy found with given filter." + }, + "transfer_history_page": { + "subtitle": "Transfer History Details", + "no_trans": "No transfer history found.", + "counter_endpoint": "Counterparty Connector Endpoint", + "counter_id": "Counterparty Participant ID" + }, + "connector_ui": { + "dashboard": "Dashboard", + "catalog": "Catalog Browser", + "contracts": "Contracts", + "transfer": "Transfer History", + "assets": "Assets", + "policies": "Policies", + "contract": "Contract Definitions", + "logout": "Logout" + } +} diff --git a/src/assets/images/flags/de.svg b/src/assets/images/flags/de.svg new file mode 100644 index 000000000..442047028 --- /dev/null +++ b/src/assets/images/flags/de.svg @@ -0,0 +1,9 @@ + + + + Flag of Germany + + + + diff --git a/src/assets/images/flags/en.svg b/src/assets/images/flags/en.svg new file mode 100644 index 000000000..56487b083 --- /dev/null +++ b/src/assets/images/flags/en.svg @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + From 66426e1e56b88670278a2dc16397d6b2ab59e104 Mon Sep 17 00:00:00 2001 From: Andreas Timmermann Date: Thu, 5 Sep 2024 17:05:51 +0200 Subject: [PATCH 2/5] adapt translations after rebase --- .../edit-asset-form/edit-asset-form.module.ts | 3 + .../edit-asset-form.component.html | 127 +++++++++--------- .../keyword-select.component.html | 4 +- .../language-select.component.html | 2 +- .../policy-operator-select.component.ts | 6 +- .../asset-edit-dialog.component.html | 105 +++++++-------- .../keyword-select.component.html | 4 +- .../policy-definition-create-page.module.ts | 2 + ...licy-definition-create-page.component.html | 8 +- src/assets/i18n/de.json | 42 +++++- src/assets/i18n/en.json | 36 ++++- 11 files changed, 199 insertions(+), 140 deletions(-) diff --git a/src/app/component-library/edit-asset-form/edit-asset-form.module.ts b/src/app/component-library/edit-asset-form/edit-asset-form.module.ts index 47d79dac2..636a0f879 100644 --- a/src/app/component-library/edit-asset-form/edit-asset-form.module.ts +++ b/src/app/component-library/edit-asset-form/edit-asset-form.module.ts @@ -37,6 +37,8 @@ import {EditAssetFormComponent} from './edit-asset-form/edit-asset-form.componen import {KeywordSelectComponent} from './keyword-select/keyword-select.component'; import {LanguageSelectComponent} from './language-select/language-select.component'; import {TransportModeSelectComponent} from './transport-mode-select/transport-mode-select.component'; +import {TranslateModule} from '@ngx-translate/core'; + @NgModule({ imports: [ @@ -45,6 +47,7 @@ import {TransportModeSelectComponent} from './transport-mode-select/transport-mo FormsModule, ReactiveFormsModule, RouterModule, + TranslateModule, // Angular Material MatBadgeModule, diff --git a/src/app/component-library/edit-asset-form/edit-asset-form/edit-asset-form.component.html b/src/app/component-library/edit-asset-form/edit-asset-form/edit-asset-form.component.html index da2054554..133b34885 100644 --- a/src/app/component-library/edit-asset-form/edit-asset-form/edit-asset-form.component.html +++ b/src/app/component-library/edit-asset-form/edit-asset-form/edit-asset-form.component.html @@ -2,12 +2,12 @@ + myTitle="{{ 'asset_page.datasource' | translate }}" + description="{{ 'create_data_offer.def_datasrc' | translate }}">
- Keep the datasource unchanged. + {{ 'create_data_offer.keep_datasrc' | translate }} - I do not have a datasource. + {{ 'create_data_offer.no_datasrc' | translate }} - I want to connect to a datasource. + {{ 'create_data_offer.con_datasrc' | translate }}
@@ -34,23 +34,20 @@ This email address will be offered to potential consumers for - contacting you. This is done in place of having an actual data source - connected.{{ 'create_data_offer.contact_email_descr' | translate }} Will be added to the mailto-link and displayed to potential consumers - to use.{{ 'create_data_offer.pref_email_descr' | translate }} @@ -61,7 +58,7 @@
@@ -84,7 +81,7 @@
- The consuming side must provide a Custom HTTP Method with - method parameterization enabled. @@ -113,8 +110,8 @@ mat-button [color]="ctrl.value ? 'warn' : 'accent'" (click)="$event.preventDefault(); ctrl.setValue(!ctrl.value)"> - {{ ctrl.value ? 'Disable' : 'Enable' }} - Method Parameterization + {{ ctrl.value ? ( 'general.disable' | translate ) : ( 'general.enable' | translate ) }} + {{ 'asset_page.method_para' | translate }}
@@ -127,9 +124,8 @@ [hideHint]="!form.proxyPath" [ctrl]="ctrl" [label]="form.proxyPath ? 'Base URL' : 'URL'" - >The consuming side must provide a Custom HTTP Subpath with - method parameterization enabled. The Custom HTTP Subpath will be - appended to the base path.{{ 'asset_page.http_subpath' | translate }} + @@ -140,7 +136,7 @@ mat-button [color]="ctrl.value ? 'warn' : 'accent'" (click)="$event.preventDefault(); ctrl.setValue(!ctrl.value)"> - {{ ctrl.value ? 'Disable' : 'Enable' }} Path Parameterization + {{ ctrl.value ? ( 'general.disable' | translate ) : ( 'general.enable' | translate ) }} {{ 'asset_page.method_para' | translate }}
@@ -148,7 +144,7 @@
- Remove + {{ 'general.remove' | translate }}
@@ -212,7 +208,7 @@ mat-button color="accent" (click)="form.onHttpQueryParamsAddClick($event)"> - Add {{ form.proxyQueryParams ? 'Default' : '' }} Query Param + {{ 'general.add' | translate }} {{ form.proxyQueryParams ? 'Default' : '' }} {{ 'asset_page.query_para_single' | translate }}
- + - The request body can only be set from the consumer side, if - parameterization is enabled. + {{ 'asset_page.info_body' | translate }}
- {{ ctrl.value ? 'Disable' : 'Enable' }} Request Body - Parameterization + {{ ctrl.value ? ( 'general.disable' | translate ) : ( 'general.enable' | translate ) }} {{ 'asset_page.request_para' | translate }}
+ label="{{ 'general.auth' | translate }}">
- Add Authentication + {{ 'general.add' | translate }} {{ 'general.auth' | translate }}
@@ -272,13 +265,13 @@ form.datasource.controls.httpAuthHeaderType.value !== 'None' " class="grow mt-4"> - Type + {{ 'general.type' | translate }} - Header with Vault Secret + {{ 'general.header_sec' | translate }} - Header with Value + {{ 'general.header_val' | translate }}
- Auth Header Name + {{ 'general.auth_header' | translate }} - Auth Header Value + {{ 'general.auth_value' | translate }} - Vault Secret Name + {{ 'general.vault_secret' | translate }} - Remove Authentication + {{ 'general.remove' | translate }} {{ 'general.auth' | translate }}
+ label="{{ 'general.add_header' | translate }}">
- Header Name + {{ 'general.header_name' | translate }} - Header Value + {{ 'general.header_value' | translate }} - Remove + {{ 'general.remove' | translate }}
@@ -385,7 +378,7 @@ mat-button color="accent" (click)="form.onHttpHeadersAddClick($event)"> - Add Additional Header + {{ 'general.add' | translate }} {{ 'general.add_header' | translate }}
@@ -394,13 +387,13 @@ + myTitle="{{ 'asset_page.information' | translate }}" + description="{{ 'asset_page.information_desc' | translate }}"> @@ -408,19 +401,19 @@ *ngIf="form.general.controls.id; let ctrl" fieldId="create-asset-form-id" placeholder="my-asset" - label="ID" + label="{{ 'asset_page.asset_id' | translate}}" [ctrl]="ctrl">
- The description uses + {{ 'asset_page.descrip' | translate }}
Show Advanced Fields{{ 'general.show_adv_fields' | translate }} @@ -499,7 +492,7 @@ + myTitle="{{ 'general.publishing' | translate }}" + description="{{ 'general.pub_desc' | translate }}">
- Publish unrestricted + {{ 'general.pub_unrestr' | translate }} - Publish restricted + {{ 'general.pub_restr' | translate }} - Do not publish + {{ 'general.pub_no' | translate }}
@@ -763,7 +756,7 @@
diff --git a/src/app/component-library/edit-asset-form/keyword-select/keyword-select.component.html b/src/app/component-library/edit-asset-form/keyword-select/keyword-select.component.html index df7acea8e..4261195b9 100644 --- a/src/app/component-library/edit-asset-form/keyword-select/keyword-select.component.html +++ b/src/app/component-library/edit-asset-form/keyword-select/keyword-select.component.html @@ -12,12 +12,12 @@ (removed)="remove(keyword)"> {{ keyword }} diff --git a/src/app/component-library/policy-editor/editor/policy-operator-select/policy-operator-select.component.ts b/src/app/component-library/policy-editor/editor/policy-operator-select/policy-operator-select.component.ts index 4bcfa9595..90bfc6f25 100644 --- a/src/app/component-library/policy-editor/editor/policy-operator-select/policy-operator-select.component.ts +++ b/src/app/component-library/policy-editor/editor/policy-operator-select/policy-operator-select.component.ts @@ -1,6 +1,7 @@ import {Component, HostBinding, Input} from '@angular/core'; import {UntypedFormControl} from '@angular/forms'; import {PolicyOperatorConfig} from '../../model/policy-operators'; +import {TranslateService} from '@ngx-translate/core'; @Component({ selector: 'policy-operator-select', @@ -17,5 +18,8 @@ export class PolicyOperatorSelectComponent { @HostBinding('class.flex-row') cls = true; - label = 'Operator'; + constructor(public translationService: TranslateService) {} + + label = this.translationService.instant('general.operator'); + } diff --git a/src/app/routes/connector-ui/asset-page/asset-edit-dialog/asset-edit-dialog.component.html b/src/app/routes/connector-ui/asset-page/asset-edit-dialog/asset-edit-dialog.component.html index 2eee6e6cb..aaf585c41 100644 --- a/src/app/routes/connector-ui/asset-page/asset-edit-dialog/asset-edit-dialog.component.html +++ b/src/app/routes/connector-ui/asset-page/asset-edit-dialog/asset-edit-dialog.component.html @@ -1,17 +1,17 @@

- {{ form.mode === 'CREATE' ? 'Create New Asset' : 'Edit Asset' }} + {{ form.mode === 'CREATE' ? ('asset_page.create_asset' | translate) : ('asset_page.edit_asset' | translate) }}

- General Information + {{'asset_page.information' | translate}}
- Name + {{'asset_page.name' | translate}} - Version + {{'asset_page.version' | translate}} - Asset ID + {{'asset_page.asset_id' | translate }} - Description + {{'asset_page.file_des' | translate }} - The description uses + {{'asset_page.descrip' | translate }}
- Content Type + {{'general.content' | translate }} - Endpoint Documentation + {{'general.endpoint_doc' | translate }} {{ validationMessages.invalidUrlMessage }} @@ -112,7 +112,7 @@

- Publisher + {{'general.publisher' | translate }} {{ validationMessages.invalidUrlMessage }} @@ -123,7 +123,7 @@

- Standard License + {{'general.st_license' | translate }} {{ validationMessages.invalidUrlMessage }} @@ -136,7 +136,7 @@

- Advanced Information + {{ 'general.ad_inf' | translate}}
@@ -377,12 +377,12 @@

- Datasource Information -
Datasource
+ {{ 'asset_page.datasource_info' | translate }} +
{{ 'asset_page.datasource' | translate }}
- Custom Datasource Config (JSON) + {{ 'asset_page.datasource_config' | translate }} - The description supports + {{ 'asset_list_page.descrip' | translate }}
- Content Type + {{ 'general.content' | translate }} - Endpoint Documentation + {{ 'general.endpoint_doc' | translate }}