diff --git a/.sonarcloud.properties b/.sonarcloud.properties index f86e4774c9a9..9c94dc959947 100644 --- a/.sonarcloud.properties +++ b/.sonarcloud.properties @@ -7,7 +7,7 @@ sonar.projectName=manager sonar.sources=. sonar.sourceEncoding=UTF-8 sonar.ws.timeout=60 -sonar.projectVersion=tellurium-gnu-2 +sonar.projectVersion=mercury-cheetah-2 sonar.exclusions=node_modules/**, **/node_modules/**, **/dist/**, **/semantic/**, **/coverage/**, **/static/** sonar.coverage.exclusions=**/*.spec.js diff --git a/jest.config.js b/jest.config.js index 554bde40f197..0b4be0832b2b 100644 --- a/jest.config.js +++ b/jest.config.js @@ -22,6 +22,7 @@ module.exports = { '^.+\\.module\\.(css|sass|scss)$', '/node_modules/(?!lodash-es|@stencil)', ], + testPathIgnorePatterns: ['/node_modules/', '/apps/pci-vouchers/'], moduleNameMapper: { '^.+\\.module\\.(css|sass|scss)$': 'identity-obj-proxy', '.+\\.(css|styl|less|sass|scss|png|jpg|ttf|woff|woff2)$': diff --git a/package.json b/package.json index e671237fd4b3..2cb72f388bcf 100644 --- a/package.json +++ b/package.json @@ -41,6 +41,7 @@ "start": "node -r esm scripts/start-application.js", "test:jest": "jest --runInBand", "test": "yarn lint", + "test:turbo": "turbo run test", "test:scripts": "make test", "test:playwright:run": "lerna run test:e2e:script --concurrency 1" }, diff --git a/packages/components/ng-at-internet/CHANGELOG.md b/packages/components/ng-at-internet/CHANGELOG.md index 6b53f9c4bd45..36eacaf3a12f 100644 --- a/packages/components/ng-at-internet/CHANGELOG.md +++ b/packages/components/ng-at-internet/CHANGELOG.md @@ -3,6 +3,38 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [5.11.7](https://github.com/ovh/manager/compare/@ovh-ux/ng-at-internet@5.11.6...@ovh-ux/ng-at-internet@5.11.7) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/ng-at-internet + + + + + +## [5.11.6](https://github.com/ovh/manager/compare/@ovh-ux/ng-at-internet@5.11.5...@ovh-ux/ng-at-internet@5.11.6) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/ng-at-internet + + + + + +## [5.11.5](https://github.com/ovh/manager/compare/@ovh-ux/ng-at-internet@5.11.4...@ovh-ux/ng-at-internet@5.11.5) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/ng-at-internet + + + + + +## [5.11.4](https://github.com/ovh/manager/compare/@ovh-ux/ng-at-internet@5.11.3...@ovh-ux/ng-at-internet@5.11.4) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/ng-at-internet + + + + + ## [5.11.3](https://github.com/ovh/manager/compare/@ovh-ux/ng-at-internet@5.11.2...@ovh-ux/ng-at-internet@5.11.3) (2024-02-21) **Note:** Version bump only for package @ovh-ux/ng-at-internet diff --git a/packages/components/ng-at-internet/package.json b/packages/components/ng-at-internet/package.json index 337e2e1fc93d..913acc873aa3 100644 --- a/packages/components/ng-at-internet/package.json +++ b/packages/components/ng-at-internet/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/ng-at-internet", - "version": "5.11.3", + "version": "5.11.7", "private": true, "description": "ATInternet tracking library wrapper for AngularJS", "keywords": [ @@ -36,7 +36,7 @@ "start:watch": "lerna exec --stream --parallel --scope='@ovh-ux/ng-at-internet' --include-dependencies -- yarn run dev:watch" }, "dependencies": { - "@ovh-ux/ovh-at-internet": "^0.10.0" + "@ovh-ux/ovh-at-internet": "^0.12.0" }, "devDependencies": { "@ovh-ux/component-rollup-config": "^13.0.1" diff --git a/packages/components/ng-shell-tracking/CHANGELOG.md b/packages/components/ng-shell-tracking/CHANGELOG.md index 49678475ae12..135e40d2633b 100644 --- a/packages/components/ng-shell-tracking/CHANGELOG.md +++ b/packages/components/ng-shell-tracking/CHANGELOG.md @@ -3,6 +3,38 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [0.5.4](https://github.com/ovh/manager/compare/@ovh-ux/ng-shell-tracking@0.5.3...@ovh-ux/ng-shell-tracking@0.5.4) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/ng-shell-tracking + + + + + +## [0.5.3](https://github.com/ovh/manager/compare/@ovh-ux/ng-shell-tracking@0.5.2...@ovh-ux/ng-shell-tracking@0.5.3) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/ng-shell-tracking + + + + + +## [0.5.2](https://github.com/ovh/manager/compare/@ovh-ux/ng-shell-tracking@0.5.1...@ovh-ux/ng-shell-tracking@0.5.2) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/ng-shell-tracking + + + + + +## [0.5.1](https://github.com/ovh/manager/compare/@ovh-ux/ng-shell-tracking@0.5.0...@ovh-ux/ng-shell-tracking@0.5.1) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/ng-shell-tracking + + + + + # [0.5.0](https://github.com/ovh/manager/compare/@ovh-ux/ng-shell-tracking@0.4.2...@ovh-ux/ng-shell-tracking@0.5.0) (2024-02-21) diff --git a/packages/components/ng-shell-tracking/package.json b/packages/components/ng-shell-tracking/package.json index da2a71e70deb..8926415c3834 100644 --- a/packages/components/ng-shell-tracking/package.json +++ b/packages/components/ng-shell-tracking/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/ng-shell-tracking", - "version": "0.5.0", + "version": "0.5.4", "private": true, "description": "ATInternet tracking library wrapper for AngularJS", "keywords": [ @@ -37,7 +37,7 @@ "start:watch": "lerna exec --stream --parallel --scope='@ovh-ux/ng-shell-tracking' --include-dependencies -- yarn run dev:watch" }, "dependencies": { - "@ovh-ux/ovh-at-internet": "^0.10.0" + "@ovh-ux/ovh-at-internet": "^0.12.0" }, "devDependencies": { "@ovh-ux/component-rollup-config": "^13.0.1" diff --git a/packages/components/ovh-at-internet/CHANGELOG.md b/packages/components/ovh-at-internet/CHANGELOG.md index 31655cf24b32..cc85c831e98b 100644 --- a/packages/components/ovh-at-internet/CHANGELOG.md +++ b/packages/components/ovh-at-internet/CHANGELOG.md @@ -3,6 +3,47 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +# [0.12.0](https://github.com/ovh/manager/compare/@ovh-ux/ovh-at-internet@0.11.2...@ovh-ux/ovh-at-internet@0.12.0) (2024-03-13) + + +### Features + +* pci vouchers app in reactjs ([d6821ce](https://github.com/ovh/manager/commit/d6821cecd3bde7d884054d8e782e9a1e9dbfddac)) + + + + + +## [0.11.2](https://github.com/ovh/manager/compare/@ovh-ux/ovh-at-internet@0.11.1...@ovh-ux/ovh-at-internet@0.11.2) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/ovh-at-internet + + + + + +## [0.11.1](https://github.com/ovh/manager/compare/@ovh-ux/ovh-at-internet@0.11.0...@ovh-ux/ovh-at-internet@0.11.1) (2024-03-07) + + +### Reverts + +* Revert "feat(*): pci vouchers app in reactjs" ([b62c1a8](https://github.com/ovh/manager/commit/b62c1a8b1cfe63dbc420b660667209c324ffa9ab)) + + + + + +# [0.11.0](https://github.com/ovh/manager/compare/@ovh-ux/ovh-at-internet@0.10.0...@ovh-ux/ovh-at-internet@0.11.0) (2024-03-07) + + +### Features + +* pci vouchers app in reactjs ([ad08ee4](https://github.com/ovh/manager/commit/ad08ee4618d6243328eee76af7d1bd459a1a7d83)) + + + + + # [0.10.0](https://github.com/ovh/manager/compare/@ovh-ux/ovh-at-internet@0.9.0...@ovh-ux/ovh-at-internet@0.10.0) (2024-02-21) diff --git a/packages/components/ovh-at-internet/package.json b/packages/components/ovh-at-internet/package.json index d8b46e1df784..82764110cf70 100644 --- a/packages/components/ovh-at-internet/package.json +++ b/packages/components/ovh-at-internet/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/ovh-at-internet", - "version": "0.10.0", + "version": "0.12.0", "private": true, "description": "ATInternet tracking library for OVHcloud.", "keywords": [ @@ -35,7 +35,7 @@ "start:watch": "lerna exec --stream --parallel --scope='@ovh-ux/manager-config' --include-dependencies -- yarn run dev:watch" }, "dependencies": { - "@ovh-ux/manager-config": "^7.3.0", + "@ovh-ux/manager-config": "^7.3.1", "@types/lodash-es": "^4.17.5", "lodash-es": "^4.17.15" } diff --git a/packages/components/ovh-at-internet/src/track.ts b/packages/components/ovh-at-internet/src/track.ts index d1f1d271aaad..b07272011289 100644 --- a/packages/components/ovh-at-internet/src/track.ts +++ b/packages/components/ovh-at-internet/src/track.ts @@ -11,7 +11,7 @@ export interface LegacyTrackingData { chapter1?: string; chapter2?: string; chapter3?: string; - level2: string; + level2?: string; page?: any; [key: string]: any; } diff --git a/packages/components/ovh-shell/CHANGELOG.md b/packages/components/ovh-shell/CHANGELOG.md index b395904ec29e..c44bef309d11 100644 --- a/packages/components/ovh-shell/CHANGELOG.md +++ b/packages/components/ovh-shell/CHANGELOG.md @@ -3,6 +3,47 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +# [3.4.0](https://github.com/ovh/manager/compare/@ovh-ux/shell@3.3.2...@ovh-ux/shell@3.4.0) (2024-03-13) + + +### Features + +* pci vouchers app in reactjs ([d6821ce](https://github.com/ovh/manager/commit/d6821cecd3bde7d884054d8e782e9a1e9dbfddac)) + + + + + +## [3.3.2](https://github.com/ovh/manager/compare/@ovh-ux/shell@3.3.1...@ovh-ux/shell@3.3.2) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/shell + + + + + +## [3.3.1](https://github.com/ovh/manager/compare/@ovh-ux/shell@3.3.0...@ovh-ux/shell@3.3.1) (2024-03-07) + + +### Reverts + +* Revert "feat(*): pci vouchers app in reactjs" ([b62c1a8](https://github.com/ovh/manager/commit/b62c1a8b1cfe63dbc420b660667209c324ffa9ab)) + + + + + +# [3.3.0](https://github.com/ovh/manager/compare/@ovh-ux/shell@3.2.0...@ovh-ux/shell@3.3.0) (2024-03-07) + + +### Features + +* pci vouchers app in reactjs ([ad08ee4](https://github.com/ovh/manager/commit/ad08ee4618d6243328eee76af7d1bd459a1a7d83)) + + + + + # [3.2.0](https://github.com/ovh/manager/compare/@ovh-ux/shell@3.1.0...@ovh-ux/shell@3.2.0) (2024-02-28) diff --git a/packages/components/ovh-shell/package.json b/packages/components/ovh-shell/package.json index 4a3ea91ffebe..d323435fa02f 100644 --- a/packages/components/ovh-shell/package.json +++ b/packages/components/ovh-shell/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/shell", - "version": "3.2.0", + "version": "3.4.0", "private": true, "description": "Communication and interaction between applications", "repository": { @@ -23,10 +23,10 @@ "start:watch": "lerna exec --stream --parallel --scope='@ovh-ux/shell' --include-dependencies -- npm run dev:watch --if-present" }, "dependencies": { - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/ovh-at-internet": "^0.10.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/ovh-at-internet": "^0.12.0", "@ovh-ux/ovh-reket": "^2.1.1", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@ovh-ux/url-builder": "^1.1.1", "@types/react": "^18.0.0", "dompurify": "^2.3.3", diff --git a/packages/components/ovh-shell/src/client/index.ts b/packages/components/ovh-shell/src/client/index.ts index e44786b58926..a03fa11bafe0 100644 --- a/packages/components/ovh-shell/src/client/index.ts +++ b/packages/components/ovh-shell/src/client/index.ts @@ -9,6 +9,7 @@ import { getHeaders } from '@ovh-ux/request-tagger'; import ShellClient from './shell-client'; import StandaloneShellClient from './standalone-shell-client'; import IFrameMessageBus from '../message-bus/iframe'; +import { ShellClientApi } from './api'; function fetchApplications(): Promise> { return useReket(true).get('/applications', { @@ -89,7 +90,9 @@ export function initStandaloneClientApi( return client.init().then(() => client.getApi()); } -export default function init(applicationId: ApplicationId) { +export default async function init( + applicationId: ApplicationId, +): Promise { let initPromise; if (isTopLevelApplication()) { @@ -100,7 +103,7 @@ export default function init(applicationId: ApplicationId) { initPromise = initIFrameClientApi(applicationId); } - return initPromise.then((shellApi) => { + return initPromise.then(async (shellApi) => { shellApi.ux.resetAccountSidebar(); return shellApi.environment .setApplication(applicationId) diff --git a/packages/manager-components/.storybook/i18n.ts b/packages/manager-components/.storybook/i18n.ts index 8395ae804d7f..8ebb4c85921a 100644 --- a/packages/manager-components/.storybook/i18n.ts +++ b/packages/manager-components/.storybook/i18n.ts @@ -2,7 +2,7 @@ import i18n from 'i18next'; import { initReactI18next } from 'react-i18next'; i18n.use(initReactI18next).init({ - fallbackLng: 'fr-FR', + fallbackLng: 'fr_FR', interpolation: { escapeValue: false, }, diff --git a/packages/manager-components/.storybook/preview.tsx b/packages/manager-components/.storybook/preview.tsx index d477bf113d41..f5315b329f63 100644 --- a/packages/manager-components/.storybook/preview.tsx +++ b/packages/manager-components/.storybook/preview.tsx @@ -1,11 +1,16 @@ import React, { Suspense, useEffect } from 'react'; import { I18nextProvider } from 'react-i18next'; +import { odsSetup } from '@ovhcloud/ods-common-core'; import { Preview } from '@storybook/react'; import '../src/tailwind/theme.css'; import '@ovhcloud/ods-theme-blue-jeans/dist/index.css'; import i18n from './i18n'; +import '@ovhcloud/ods-theme-blue-jeans'; + +odsSetup(); + const preview: Preview = { parameters: { actions: { argTypesRegex: '^on[A-Z].*' }, @@ -44,14 +49,14 @@ export const globalTypes = { toolbar: { icon: 'globe', items: [ - { value: 'fr-FR', title: 'Francais' }, - { value: 'en-GB', title: 'English' }, - { value: 'de-DE', title: 'Deutsch' }, - { value: 'es-ES', title: 'Espagne' }, - { value: 'it-IT', title: 'Italy' }, - { value: 'pt-PT', title: 'Portugal' }, - { value: 'pl-PL', title: 'Poland' }, - { value: 'fr-CA', title: 'Canada' }, + { value: 'fr_FR', title: 'Francais' }, + { value: 'en_GB', title: 'English' }, + { value: 'de_DE', title: 'Deutsch' }, + { value: 'es_ES', title: 'Espagne' }, + { value: 'it_IT', title: 'Italy' }, + { value: 'pt_PT', title: 'Portugal' }, + { value: 'pl_PL', title: 'Poland' }, + { value: 'fr_CA', title: 'Canada' }, ], showName: true, }, diff --git a/packages/manager-components/CHANGELOG.md b/packages/manager-components/CHANGELOG.md index b083ce994516..fc545e2dc0ce 100644 --- a/packages/manager-components/CHANGELOG.md +++ b/packages/manager-components/CHANGELOG.md @@ -3,6 +3,24 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +# [1.5.0](https://github.com/ovh/manager/compare/@ovhcloud/manager-components@1.4.1...@ovhcloud/manager-components@1.5.0) (2024-03-13) + +### Features + +- pci vouchers app in reactjs ([d6821ce](https://github.com/ovh/manager/commit/d6821cecd3bde7d884054d8e782e9a1e9dbfddac)) + +## [1.4.1](https://github.com/ovh/manager/compare/@ovhcloud/manager-components@1.4.0...@ovhcloud/manager-components@1.4.1) (2024-03-07) + +### Reverts + +- Revert "feat(\*): pci vouchers app in reactjs" ([b62c1a8](https://github.com/ovh/manager/commit/b62c1a8b1cfe63dbc420b660667209c324ffa9ab)) + +# [1.4.0](https://github.com/ovh/manager/compare/@ovhcloud/manager-components@1.3.0...@ovhcloud/manager-components@1.4.0) (2024-03-07) + +### Features + +- pci vouchers app in reactjs ([ad08ee4](https://github.com/ovh/manager/commit/ad08ee4618d6243328eee76af7d1bd459a1a7d83)) + # [1.3.0](https://github.com/ovh/manager/compare/@ovhcloud/manager-components@1.2.0...@ovhcloud/manager-components@1.3.0) (2024-02-28) ### Features diff --git a/packages/manager-components/jest.config.js b/packages/manager-components/jest.config.js index eced86897817..31b84d1e5a4c 100644 --- a/packages/manager-components/jest.config.js +++ b/packages/manager-components/jest.config.js @@ -1,12 +1,12 @@ module.exports = { + testMatch: ['/src/**/*.{spec,test}.{js,jsx,ts,tsx}'], testEnvironment: 'jsdom', transformIgnorePatterns: [ 'node_modules/(?!lodash-es|@ovh-ux|@ovhcloud|@stencil)', ], setupFilesAfterEnv: ['./jest.setup.ts'], - collectCoverageFrom: ['src/components/**/**.component.tsx'], + collectCoverageFrom: ['src/components/**/*.component.tsx'], moduleFileExtensions: ['ts', 'tsx', 'js', 'jsx', 'json', 'node'], - testMatch: ['/src/components/**/**/*.spec.tsx'], moduleNameMapper: { '.+\\.(css|styl|less|sass|scss|png|jpg|ttf|woff|woff2)$': '/src/_mock_/images.tsx', diff --git a/packages/manager-components/package.json b/packages/manager-components/package.json index e21511fd02f0..d3edd3572640 100644 --- a/packages/manager-components/package.json +++ b/packages/manager-components/package.json @@ -1,7 +1,7 @@ { "name": "@ovhcloud/manager-components", "private": true, - "version": "1.3.0", + "version": "1.5.0", "main": "src/components/index.ts", "repository": { "type": "git", @@ -24,11 +24,9 @@ "@ovhcloud/ods-common-theming": "^17.1.0", "@ovhcloud/ods-components": "^17.1.0", "@ovhcloud/ods-theme-blue-jeans": "^17.1.0", + "@tanstack/react-table": "^8.11.6", "babel-preset-react-app": "^10.0.1", - "i18next": "^20.4.0", "react": "18.2.0", - "react-dom": "18.2.0", - "react-i18next": "^11.18.1", "sass": "1.71.0", "tailwindcss": "3.3.3" }, @@ -64,22 +62,31 @@ "eslint-plugin-storybook": "0.6.13", "file-loader": "^6.2.0", "husky": "8.0.3", + "i18next": "^20.4.0", "jsdom": "22.1.0", "json": "11.0.0", "lint-staged": "13.2.3", "postcss": "8.4.27", "prettier": "3.0.1", "prop-types": "15.8.1", + "react-dom": "18.2.0", + "react-i18next": "^11.18.1", + "react-router-dom": "^6.21.0", "storybook": "7.5.3", + "storybook-addon-react-router-v6": "^2.0.10", "ts-jest": "^29.1.1", "typescript": "^4.3.2", "vite": "4.4.9", "vite-plugin-dts": "3.5.1", - "vitest": "0.34.1" + "vitest": "0.34.1", + "zustand": "^4.5.0" }, - "peerDependencies": { - "react": "18.2.0", - "react-dom": "18.2.0" + "optionalDependencies": { + "i18next": "^20.4.0", + "react-dom": "18.2.0", + "react-i18next": "^11.18.1", + "react-router-dom": "^6.21.0", + "zustand": "^4.5.0" }, "files": [ "dist" diff --git a/packages/manager-components/src/components/datagrid/datagrid.component.tsx b/packages/manager-components/src/components/datagrid/datagrid.component.tsx new file mode 100644 index 000000000000..e448668c1ee6 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/datagrid.component.tsx @@ -0,0 +1,244 @@ +import React from 'react'; +import { + ColumnDef, + ColumnSort as TanstackColumnSort, + PaginationState as TanstackPaginationState, + flexRender, + getCoreRowModel, + useReactTable, +} from '@tanstack/react-table'; +import { + ODS_THEME_COLOR_HUE, + ODS_THEME_COLOR_INTENT, +} from '@ovhcloud/ods-common-theming'; +import { + OsdsIcon, + OsdsPagination, + OsdsText, +} from '@ovhcloud/ods-components/react'; +import { + ODS_ICON_NAME, + ODS_ICON_SIZE, + ODS_TEXT_LEVEL, + ODS_TEXT_SIZE, +} from '@ovhcloud/ods-components'; +import { useTranslation } from 'react-i18next'; +import { DataGridTextCell } from './text-cell.component'; +import './translations'; + +export type ColumnSort = TanstackColumnSort; +export type PaginationState = TanstackPaginationState; +// Note: current prettier version does not supports export type +// we could replace those types with : +// export type { ColumnSort } from '@tanstack/react-table'; +// export type { PaginationState } from '@tanstack/react-table'; + +export interface DatagridColumn { + /** unique column identifier */ + id: string; + /** formatter function to render a column cell */ + cell: (props: T) => JSX.Element; + /** label displayed for the column in the table */ + label: string; + /** is the column sortable ? (defaults is true) */ + isSortable?: boolean; +} + +export interface DatagridProps { + /** list of datagrid columns */ + columns: DatagridColumn[]; + /** list of items (rows) to display in the table */ + items: T[]; + /** total number of items (in case of pagination) */ + totalItems: number; + /** state of pagination (optional if no pagination is required) */ + pagination?: PaginationState; + /** state of column sorting (optional if column sorting is not required) */ + sorting?: ColumnSort; + /** callback to handle pagination change events (optional if no pagination is required) */ + onPaginationChange?: (pagination: PaginationState) => void; + /** callback to handle column sorting change events (optional if column sorting is not required) */ + onSortChange?: (sorting: ColumnSort) => void; +} + +export const Datagrid = ({ + columns, + items, + totalItems, + pagination, + sorting, + onPaginationChange, + onSortChange, +}: DatagridProps) => { + const { t } = useTranslation('datagrid'); + const pageCount = pagination + ? Math.ceil(totalItems / pagination.pageSize) + : 1; + + const table = useReactTable({ + columns: columns.map( + (col): ColumnDef => ({ + accessorKey: col.id, + cell: (props) => col.cell(props.row.original), + header: col.label, + enableSorting: col.isSortable !== false, + }), + ), + data: items, + manualPagination: true, + pageCount, + state: { + pagination: { ...pagination }, + ...(sorting && { + sorting: [sorting], + }), + }, + enableSortingRemoval: false, + manualSorting: true, + sortDescFirst: false, + onStateChange: (updater) => { + if (typeof updater === 'function') { + const state = updater({ ...table.getState(), ...sorting }); + if (onSortChange) onSortChange(state.sorting[0]); + } else if (onSortChange) { + onSortChange(updater.sorting[0]); + } + }, + getCoreRowModel: getCoreRowModel(), + }); + + return ( +
+
+ + + {table.getHeaderGroups().map((headerGroup) => ( + + {headerGroup.headers.map((header) => ( + + ))} + + ))} + + + {table.getRowModel().rows.map((row) => ( + + {row.getVisibleCells().map((cell) => ( + + ))} + + ))} + {table.getRowModel().rows.length === 0 && ( + + + + )} + +
+ {header.isPlaceholder ? null : ( +
+ + <> + {flexRender( + header.column.columnDef.header, + header.getContext(), + )} + + + + + +
+ )} +
+ <> + {flexRender( + cell.column.columnDef.cell, + cell.getContext(), + )} + +
+ + {t('common_pagination_no_results')} + +
+
+ {pagination && ( + { + if (detail.current !== detail.oldCurrent) { + onPaginationChange({ + ...pagination, + pageIndex: detail.current - 1, + pageSize: detail.itemPerPage, + }); + } + }} + onOdsPaginationItemPerPageChanged={({ detail }) => { + if (detail.current !== pagination.pageSize) + onPaginationChange({ + ...pagination, + pageSize: detail.current, + pageIndex: 0, + }); + }} + > + + {t('common_pagination_of')} + + + {t('common_pagination_results')} + + + )} +
+ ); +}; diff --git a/packages/manager-components/src/components/datagrid/datagrid.spec.tsx b/packages/manager-components/src/components/datagrid/datagrid.spec.tsx new file mode 100644 index 000000000000..ee15d435828e --- /dev/null +++ b/packages/manager-components/src/components/datagrid/datagrid.spec.tsx @@ -0,0 +1,170 @@ +import { useState } from 'react'; +import { fireEvent, render, screen } from '@testing-library/react'; +import { + ColumnSort, + Datagrid, + DatagridColumn, + PaginationState, +} from './datagrid.component'; + +jest.mock('react-i18next', () => ({ + useTranslation: () => { + return { + t: (str: string) => str, + i18n: { + changeLanguage: () => new Promise(() => {}), + }, + }; + }, +})); + +const sampleColumns = [ + { + id: 'name', + cell: (name: string) => { + return {name}; + }, + label: 'Name', + }, +]; + +const DatagridTest = ({ + columns, + items, + pageIndex, +}: { + columns: DatagridColumn[]; + items: string[]; + pageIndex: number; +}) => { + const [pagination, setPagination] = useState({ + pageIndex, + pageSize: 2, + }); + const start = pagination.pageIndex * pagination.pageSize; + const end = start + pagination.pageSize; + return ( + {}} + /> + ); +}; + +describe('Paginated datagrid component', () => { + it('should display the correct number of columns', async () => { + const { container } = render( + <>'a', + label: 'a', + }, + { + id: 'b', + cell: () => <>'b', + label: 'b', + }, + { + id: 'c', + cell: () => <>'c', + label: 'c', + }, + ]} + items={[]} + pageIndex={0} + />, + ); + expect(container.querySelectorAll('thead th').length).toBe(3); + }); + + it('should call sort function when clicking columns header', async () => { + const handleSortChange = jest.fn(); + const SortTest = () => { + const [sorting, setSorting] = useState({ id: 'a', desc: true }); + return ( + <>'a', + label: 'a', + }, + { + id: 'b', + cell: () => <>'b', + label: 'b', + }, + ]} + items={[]} + totalItems={0} + pagination={{ pageIndex: 0, pageSize: 1 }} + sorting={sorting} + onPaginationChange={() => {}} + onSortChange={(c: ColumnSort) => { + setSorting(c); + handleSortChange(c); + }} + /> + ); + }; + render(); + const headerA = screen.queryByTestId('header-a'); + expect(headerA).not.toBeNull(); + expect(handleSortChange).not.toHaveBeenCalled(); + fireEvent.click(headerA); + expect(handleSortChange).toHaveBeenCalledWith({ id: 'a', desc: false }); + fireEvent.click(headerA); + expect(handleSortChange).toHaveBeenCalledWith({ id: 'a', desc: true }); + fireEvent.click(headerA); + expect(handleSortChange).toHaveBeenCalledWith({ id: 'a', desc: false }); + const headerB = screen.queryByTestId('header-b'); + fireEvent.click(headerB); + expect(handleSortChange).toHaveBeenCalledWith({ id: 'b', desc: false }); + }); + + it('should display first page of items', async () => { + const { container } = render( + , + ); + expect(screen.queryByText('foo')).not.toBeNull(); + expect(screen.queryByText('bar')).not.toBeNull(); + expect(screen.queryByText('hello')).toBeNull(); + expect(container.querySelectorAll('thead tr').length).toBe(1); + expect(container.querySelectorAll('tbody tr').length).toBe(2); + }); + + it('should display second page of items', async () => { + const { container } = render( + , + ); + expect(screen.queryByText('foo')).toBeNull(); + expect(screen.queryByText('bar')).toBeNull(); + expect(screen.queryByText('hello')).not.toBeNull(); + expect(container.querySelectorAll('thead tr').length).toBe(1); + expect(container.querySelectorAll('tbody tr').length).toBe(1); + }); + + it('should display a message if there are no items', async () => { + const { container } = render( + , + ); + expect(screen.queryByText('common_pagination_no_results')).not.toBeNull(); + expect(container.querySelectorAll('thead tr').length).toBe(1); + expect(container.querySelectorAll('tbody tr').length).toBe(1); + }); +}); diff --git a/packages/manager-components/src/components/datagrid/datagrid.stories.tsx b/packages/manager-components/src/components/datagrid/datagrid.stories.tsx new file mode 100644 index 000000000000..068270f919f3 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/datagrid.stories.tsx @@ -0,0 +1,131 @@ +import React from 'react'; +import { withRouter } from 'storybook-addon-react-router-v6'; +import { useSearchParams } from 'react-router-dom'; +import { Datagrid } from './datagrid.component'; +import { DataGridTextCell } from './text-cell.component'; +import { useDatagridSearchParams } from './useDatagridSearchParams'; + +interface Item { + label: string; + price: number; +} + +const columns = [ + { + id: 'label', + cell: (item: Item) => { + return {item.label}; + }, + label: 'Label', + }, + { + id: 'price', + cell: (item: Item) => { + return {item.price} €; + }, + label: 'Price', + }, +]; + +function sortItems( + itemList: Item[], + sorting: { id: string; desc: boolean }, +): Item[] { + if (!sorting) return itemList; + const order = sorting.desc ? -1 : 1; + if (sorting.id === 'label') + return itemList.sort((a, b) => order * a.label.localeCompare(b.label)); + if (sorting.id === 'price') + return itemList.sort((a, b) => order * (a.price - b.price)); + return itemList; +} + +const DatagridStory = ({ + items, + isPaginated, + isSortable, +}: { + items: Item[]; + isPaginated: boolean; + isSortable: boolean; +}) => { + const [searchParams] = useSearchParams(); + const { + pagination, + setPagination, + sorting, + setSorting, + } = useDatagridSearchParams({ + id: 'validityTo', + desc: false, + }); + const start = isPaginated ? pagination.pageIndex * pagination.pageSize : 0; + const end = isPaginated ? start + pagination.pageSize : items.length; + const paginationAttrs = isPaginated && { + pagination, + onPaginationChange: setPagination, + }; + const sortingAttrs = isSortable && { + sorting, + onSortChange: setSorting, + }; + return ( + <> + {`${searchParams}` && ( + <> +
Search params: ?{`${searchParams}`}
+
+ + )} + + + ); +}; + +export const Empty = { + args: { + items: [], + }, +}; + +export const Basic = { + args: { + items: [...Array(15).keys()].map((_, i) => ({ + label: `Item #${i}`, + price: Math.floor(1 + Math.random() * 100), + })), + }, +}; + +export const Sortable = { + args: { + items: [...Array(15).keys()].map((_, i) => ({ + label: `Item #${i}`, + price: Math.floor(1 + Math.random() * 100), + })), + isSortable: true, + }, +}; + +export const Pagination = { + args: { + items: [...Array(50).keys()].map((_, i) => ({ + label: `Item #${i}`, + price: Math.floor(1 + Math.random() * 100), + })), + isPaginated: true, + isSortable: true, + }, +}; + +export default { + title: 'Components/Paginated datagrid', + component: DatagridStory, + decorators: [withRouter], +}; diff --git a/packages/manager-components/src/components/datagrid/text-cell.component.tsx b/packages/manager-components/src/components/datagrid/text-cell.component.tsx new file mode 100644 index 000000000000..2883ea21a3b6 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/text-cell.component.tsx @@ -0,0 +1,22 @@ +import React, { ReactNode } from 'react'; +import { OsdsText } from '@ovhcloud/ods-components/react'; +import { + ODS_THEME_COLOR_INTENT, + ODS_THEME_TYPOGRAPHY_LEVEL, + ODS_THEME_TYPOGRAPHY_SIZE, +} from '@ovhcloud/ods-common-theming'; + +/** Simple datagrid cell text formatter applying ODS style */ +export function DataGridTextCell({ children }: { children: ReactNode }) { + return ( + + {children} + + ); +} + +export default DataGridTextCell; diff --git a/packages/manager-components/src/components/datagrid/translations/Messages_de_DE.json b/packages/manager-components/src/components/datagrid/translations/Messages_de_DE.json new file mode 100644 index 000000000000..8a3ebfa0b7d4 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/translations/Messages_de_DE.json @@ -0,0 +1,5 @@ +{ + "common_pagination_of": "von", + "common_pagination_results": "Ergebnisse", + "common_pagination_no_results": "Keine Ergebnisse" +} diff --git a/packages/manager-components/src/components/datagrid/translations/Messages_en_GB.json b/packages/manager-components/src/components/datagrid/translations/Messages_en_GB.json new file mode 100644 index 000000000000..05f23a4d3d63 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/translations/Messages_en_GB.json @@ -0,0 +1,5 @@ +{ + "common_pagination_of": "on", + "common_pagination_results": "results", + "common_pagination_no_results": "No result" +} diff --git a/packages/manager-components/src/components/datagrid/translations/Messages_es_ES.json b/packages/manager-components/src/components/datagrid/translations/Messages_es_ES.json new file mode 100644 index 000000000000..525d5d37e2c9 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/translations/Messages_es_ES.json @@ -0,0 +1,5 @@ +{ + "common_pagination_of": "de", + "common_pagination_results": "resultados", + "common_pagination_no_results": "No hay resultados" +} diff --git a/packages/manager-components/src/components/datagrid/translations/Messages_fr_CA.json b/packages/manager-components/src/components/datagrid/translations/Messages_fr_CA.json new file mode 100644 index 000000000000..3c8c5c644469 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/translations/Messages_fr_CA.json @@ -0,0 +1,5 @@ +{ + "common_pagination_of": "sur", + "common_pagination_results": "résultats", + "common_pagination_no_results": "Aucun résultat" +} diff --git a/packages/manager-components/src/components/datagrid/translations/Messages_fr_FR.json b/packages/manager-components/src/components/datagrid/translations/Messages_fr_FR.json new file mode 100644 index 000000000000..3c8c5c644469 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/translations/Messages_fr_FR.json @@ -0,0 +1,5 @@ +{ + "common_pagination_of": "sur", + "common_pagination_results": "résultats", + "common_pagination_no_results": "Aucun résultat" +} diff --git a/packages/manager-components/src/components/datagrid/translations/Messages_it_IT.json b/packages/manager-components/src/components/datagrid/translations/Messages_it_IT.json new file mode 100644 index 000000000000..0ce5d601e81b --- /dev/null +++ b/packages/manager-components/src/components/datagrid/translations/Messages_it_IT.json @@ -0,0 +1,5 @@ +{ + "common_pagination_of": "su", + "common_pagination_results": "risultati", + "common_pagination_no_results": "Nessun risultato" +} diff --git a/packages/manager-components/src/components/datagrid/translations/Messages_pl_PL.json b/packages/manager-components/src/components/datagrid/translations/Messages_pl_PL.json new file mode 100644 index 000000000000..cb6f7d8e5d66 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/translations/Messages_pl_PL.json @@ -0,0 +1,5 @@ +{ + "cpb_vouchers_add_success": "Voucher został dodany.", + "cpb_vouchers_add_error": "Wystąpił problem z dodaniem vouchera. Spróbuj ponownie.", + "common_pagination_no_results": "Brak wyników" +} diff --git a/packages/manager-components/src/components/datagrid/translations/Messages_pt_PT.json b/packages/manager-components/src/components/datagrid/translations/Messages_pt_PT.json new file mode 100644 index 000000000000..c03753a6db35 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/translations/Messages_pt_PT.json @@ -0,0 +1,5 @@ +{ + "common_pagination_of": "em", + "common_pagination_results": "resultados", + "common_pagination_no_results": "Nenhum resultado encontrado" +} diff --git a/packages/manager-components/src/components/datagrid/translations/index.ts b/packages/manager-components/src/components/datagrid/translations/index.ts new file mode 100644 index 000000000000..9a27214e0a16 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/translations/index.ts @@ -0,0 +1,27 @@ +import i18next from 'i18next'; + +import de_DE from './Messages_de_DE.json'; +import en_GB from './Messages_en_GB.json'; +import es_ES from './Messages_es_ES.json'; +import fr_CA from './Messages_fr_CA.json'; +import fr_FR from './Messages_fr_FR.json'; +import it_IT from './Messages_it_IT.json'; +import pl_PL from './Messages_pl_PL.json'; +import pt_PT from './Messages_pt_PT.json'; + +function addTranslations() { + i18next.addResources('de_DE', 'datagrid', de_DE); + i18next.addResources('en_GB', 'datagrid', en_GB); + i18next.addResources('es_ES', 'datagrid', es_ES); + i18next.addResources('fr_CA', 'datagrid', fr_CA); + i18next.addResources('fr_FR', 'datagrid', fr_FR); + i18next.addResources('it_IT', 'datagrid', it_IT); + i18next.addResources('pl_PL', 'datagrid', pl_PL); + i18next.addResources('pt_PT', 'datagrid', pt_PT); +} + +if (i18next.isInitialized) { + addTranslations(); +} else { + i18next.on('initialized', addTranslations); +} diff --git a/packages/manager-components/src/components/datagrid/useDatagridSearchParams.ts b/packages/manager-components/src/components/datagrid/useDatagridSearchParams.ts new file mode 100644 index 000000000000..801010b853b2 --- /dev/null +++ b/packages/manager-components/src/components/datagrid/useDatagridSearchParams.ts @@ -0,0 +1,90 @@ +import { ColumnSort, PaginationState } from '@tanstack/react-table'; +import { useSearchParams } from 'react-router-dom'; + +/** + * This hooks allows to store and synchronize the datagrid pagination & sorting + * state within URL search parameters. Thus the user is able to refresh his page + * without loosing his current pagination and column sorting state. + */ + +/* List of allowed page sizes */ +const PAGE_SIZES = [10, 25, 50, 100, 300]; + +/* Convert URL search params to plain object */ +const getSearchParamsObject = (search: URLSearchParams) => + Object.fromEntries([...search.entries()]); + +/* Parse pagination from URL search params */ +const parsePagination = (params: URLSearchParams): PaginationState => { + const pagination: PaginationState = { + pageIndex: 0, + pageSize: PAGE_SIZES[0], + }; + if (params.has('page')) { + let pageIndex = parseInt(params.get('page'), 10) - 1; + if (Number.isNaN(pageIndex) || pageIndex < 0) pageIndex = 0; + pagination.pageIndex = pageIndex; + } + if (params.has('pageSize')) { + let pageSize = parseInt(params.get('pageSize'), 10); + if (!PAGE_SIZES.includes(pageSize)) [pageSize] = PAGE_SIZES; + pagination.pageSize = pageSize; + } + return pagination; +}; + +/* Parse column sorting from URL search params */ +const parseSorting = ( + params: URLSearchParams, + defaultSorting?: ColumnSort, +): ColumnSort => { + const sorting: ColumnSort = { + id: null, + desc: false, + }; + if (params.has('sort')) { + sorting.id = params.get('sort'); + if (params.has('sortOrder')) { + sorting.desc = params.get('sortOrder') === 'desc'; + } + } else if (defaultSorting) { + return defaultSorting; + } + return sorting; +}; + +/** Use URL search params to store datagrid pagination & column sorting */ +export const useDatagridSearchParams = (defaultSorting?: ColumnSort) => { + const [searchParams, setSearchParams] = useSearchParams(); + + return { + pagination: parsePagination(searchParams), + sorting: parseSorting(searchParams, defaultSorting), + setPagination: ({ pageIndex, pageSize }: PaginationState) => { + if (pageIndex > 0) searchParams.set('page', `${pageIndex + 1}`); + else searchParams.delete('page'); + if (PAGE_SIZES.includes(pageSize) && pageSize !== PAGE_SIZES[0]) + searchParams.set('pageSize', `${pageSize}`); + else searchParams.delete('pageSize'); + setSearchParams({ + ...getSearchParamsObject(searchParams), + }); + }, + setSorting: ({ id, desc }: ColumnSort) => { + if (id) { + searchParams.set('sort', id); + if (desc) { + searchParams.set('sortOrder', 'desc'); + } else { + searchParams.delete('sortOrder'); + } + } else { + searchParams.delete('sort'); + searchParams.delete('sortOrder'); + } + setSearchParams({ + ...getSearchParamsObject(searchParams), + }); + }, + }; +}; diff --git a/packages/manager-components/src/components/index.ts b/packages/manager-components/src/components/index.ts index d93974aa74b5..56d7fd9678d9 100644 --- a/packages/manager-components/src/components/index.ts +++ b/packages/manager-components/src/components/index.ts @@ -3,3 +3,9 @@ export * from './navigation'; export * from './templates'; export * from './typography'; export * from './table/table.component'; + +export * from './datagrid/datagrid.component'; +export * from './datagrid/text-cell.component'; +export * from './datagrid/useDatagridSearchParams'; +export * from './notifications/notifications.component'; +export * from './notifications/useNotifications'; diff --git a/packages/manager-components/src/components/notifications/notifications.component.tsx b/packages/manager-components/src/components/notifications/notifications.component.tsx new file mode 100644 index 000000000000..f58a02971c62 --- /dev/null +++ b/packages/manager-components/src/components/notifications/notifications.component.tsx @@ -0,0 +1,41 @@ +import React, { useEffect, useState, FC } from 'react'; +import { useLocation } from 'react-router-dom'; +import { OdsNotification } from './ods-notification'; +import { useNotifications } from './useNotifications'; + +interface NotificationProps { + /** Clear notifications once they have been displayed (on location changes) */ + clearAfterRead?: boolean; +} + +/** + * This component display the list of notifications. It acts + * as a "flash" component because by default once the notifications have been + * shown they are cleared. It means that you can use this component on multiple + * pages, switching page won't display notifications twice. + * + * It replicates the current behavior of public cloud notifications for + * actions (success / errors / etc) + */ +export const Notifications: FC = ({ + clearAfterRead = true, +}) => { + const location = useLocation(); + const [originLocation] = useState(location); + const { notifications, clearNotifications } = useNotifications(); + + useEffect(() => { + if (clearAfterRead && originLocation.pathname !== location.pathname) + clearNotifications(); + }, [clearAfterRead, location.pathname]); + + return ( + <> + {notifications.map((notification) => ( + + ))} + + ); +}; + +export default Notifications; diff --git a/packages/manager-components/src/components/notifications/notifications.spec.tsx b/packages/manager-components/src/components/notifications/notifications.spec.tsx new file mode 100644 index 000000000000..a7d6af256107 --- /dev/null +++ b/packages/manager-components/src/components/notifications/notifications.spec.tsx @@ -0,0 +1,47 @@ +import { useEffect } from 'react'; +import { render } from '@testing-library/react'; +import { useNotifications, NotificationType } from './useNotifications'; +import { Notifications } from './notifications.component'; + +jest.mock('react-router-dom', () => ({ + ...jest.requireActual('react-router-dom'), + useLocation: () => ({ + pathname: '/foo', + }), +})); + +function AddNotification() { + const { addNotification } = useNotifications(); + useEffect(() => { + addNotification('Notification-1', NotificationType.Success); + addNotification('Notification-2', NotificationType.Warning); + }, []); + return <>; +} + +function ClearNotifications() { + const { clearNotifications } = useNotifications(); + useEffect(() => { + clearNotifications(); + }, []); + return <>; +} + +describe('notifications component', () => { + it('should list notifications', async () => { + let { container } = render(); + expect(container.children.length).toBe(0); + render(); + container = render().container; + expect(container.children.length).toBe(2); + expect(container.children[0].innerHTML).toBe('Notification-1'); + expect(container.children[1].innerHTML).toBe('Notification-2'); + }); + it('should clear notifications', async () => { + let { container } = render(); + expect(container.children.length).not.toBe(0); + render(); + container = render().container; + expect(container.children.length).toBe(0); + }); +}); diff --git a/packages/manager-components/src/components/notifications/notifications.stories.tsx b/packages/manager-components/src/components/notifications/notifications.stories.tsx new file mode 100644 index 000000000000..f15fac0c64de --- /dev/null +++ b/packages/manager-components/src/components/notifications/notifications.stories.tsx @@ -0,0 +1,68 @@ +import React from 'react'; +import { withRouter } from 'storybook-addon-react-router-v6'; +import { OsdsButton } from '@ovhcloud/ods-components/react'; +import { ODS_BUTTON_SIZE } from '@ovhcloud/ods-components'; +import { ODS_THEME_COLOR_INTENT } from '@ovhcloud/ods-common-theming'; +import { Notifications } from './notifications.component'; +import { useNotifications } from './useNotifications'; + +const NotificationsStory = () => { + const { + addSuccess, + addWarning, + addError, + clearNotifications, + } = useNotifications(); + + return ( + <> +
+ addSuccess('success message')} + > + Add success + + addWarning('warning message')} + > + Add warning + + addError('error message')} + > + Add error + + + Clear + +
+
+ +
+ + ); +}; + +export const Primary = { + name: 'Notifications', +}; + +export default { + title: 'Components/Notifications', + component: NotificationsStory, + decorators: [withRouter], +}; diff --git a/packages/manager-components/src/components/notifications/ods-notification.tsx b/packages/manager-components/src/components/notifications/ods-notification.tsx new file mode 100644 index 000000000000..cc78314af6e6 --- /dev/null +++ b/packages/manager-components/src/components/notifications/ods-notification.tsx @@ -0,0 +1,33 @@ +import React from 'react'; +import { OsdsMessage } from '@ovhcloud/ods-components/react'; +import { ODS_MESSAGE_TYPE } from '@ovhcloud/ods-components'; +import { Notification, NotificationType } from './useNotifications'; + +type OdsNotificationProps = { + notification: Notification; +}; + +const getOdsMessageColor = (type: NotificationType) => { + switch (type) { + case NotificationType.Success: + return ODS_MESSAGE_TYPE.success; + case NotificationType.Error: + return ODS_MESSAGE_TYPE.error; + case NotificationType.Warning: + return ODS_MESSAGE_TYPE.warning; + case NotificationType.Info: + return ODS_MESSAGE_TYPE.info; + default: + return ODS_MESSAGE_TYPE.info; + } +}; + +export function OdsNotification({ notification }: OdsNotificationProps) { + return ( + + {notification.content} + + ); +} + +export default OdsNotification; diff --git a/packages/manager-components/src/components/notifications/useNotifications.ts b/packages/manager-components/src/components/notifications/useNotifications.ts new file mode 100644 index 000000000000..12c3e556435e --- /dev/null +++ b/packages/manager-components/src/components/notifications/useNotifications.ts @@ -0,0 +1,51 @@ +import { ReactNode } from 'react'; +import { create } from 'zustand'; + +export enum NotificationType { + Success = 'success', + Error = 'error', + Info = 'info', + Warning = 'warning', +} + +export interface Notification { + /** unique notification identifier */ + uid: number; + content: ReactNode; + type: NotificationType; +} + +export interface NotificationState { + uid: number; + notifications: Notification[]; + addNotification: (content: ReactNode, type: NotificationType) => void; + addSuccess: (content: ReactNode) => void; + addError: (content: ReactNode) => void; + addWarning: (content: ReactNode) => void; + addInfo: (content: ReactNode) => void; + clearNotifications: () => void; +} + +export const useNotifications = create((set, get) => ({ + uid: 0, + notifications: [], + addNotification: (content: ReactNode, type: NotificationType) => + set((state) => ({ + uid: state.uid + 1, + notifications: [ + ...state.notifications, + { uid: state.uid, content, type }, + ], + })), + addSuccess: (content: ReactNode) => + get().addNotification(content, NotificationType.Success), + addError: (content: ReactNode) => + get().addNotification(content, NotificationType.Error), + addWarning: (content: ReactNode) => + get().addNotification(content, NotificationType.Warning), + addInfo: (content: ReactNode) => + get().addNotification(content, NotificationType.Info), + clearNotifications: () => set(() => ({ notifications: [] })), +})); + +export default useNotifications; diff --git a/packages/manager-components/src/tailwind/theme.css b/packages/manager-components/src/tailwind/theme.css index 65dd5f63a7df..b5c61c956711 100644 --- a/packages/manager-components/src/tailwind/theme.css +++ b/packages/manager-components/src/tailwind/theme.css @@ -1 +1,3 @@ +@tailwind base; +@tailwind components; @tailwind utilities; diff --git a/packages/manager-components/tsconfig.json b/packages/manager-components/tsconfig.json index 9ba34f026a41..1690e6ee5559 100644 --- a/packages/manager-components/tsconfig.json +++ b/packages/manager-components/tsconfig.json @@ -13,7 +13,8 @@ "isolatedModules": true, "declaration": true, "declarationDir": "./dist/types", - "jsx": "react" + "jsx": "react-jsx", + "resolveJsonModule": true }, "files": ["global.d.ts"], "include": ["src/**/*", "*.spec.tsx"], diff --git a/packages/manager/apps/carbon-calculator/CHANGELOG.md b/packages/manager/apps/carbon-calculator/CHANGELOG.md index d2408932cb56..93f6d65873dc 100644 --- a/packages/manager/apps/carbon-calculator/CHANGELOG.md +++ b/packages/manager/apps/carbon-calculator/CHANGELOG.md @@ -3,6 +3,38 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [0.3.7](https://github.com/ovh/manager/compare/@ovh-ux/manager-carbon-calculator-app@0.3.6...@ovh-ux/manager-carbon-calculator-app@0.3.7) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-carbon-calculator-app + + + + + +## [0.3.6](https://github.com/ovh/manager/compare/@ovh-ux/manager-carbon-calculator-app@0.3.5...@ovh-ux/manager-carbon-calculator-app@0.3.6) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-carbon-calculator-app + + + + + +## [0.3.5](https://github.com/ovh/manager/compare/@ovh-ux/manager-carbon-calculator-app@0.3.4...@ovh-ux/manager-carbon-calculator-app@0.3.5) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-carbon-calculator-app + + + + + +## [0.3.4](https://github.com/ovh/manager/compare/@ovh-ux/manager-carbon-calculator-app@0.3.3...@ovh-ux/manager-carbon-calculator-app@0.3.4) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-carbon-calculator-app + + + + + ## [0.3.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-carbon-calculator-app@0.3.2...@ovh-ux/manager-carbon-calculator-app@0.3.3) (2024-02-28) **Note:** Version bump only for package @ovh-ux/manager-carbon-calculator-app diff --git a/packages/manager/apps/carbon-calculator/package.json b/packages/manager/apps/carbon-calculator/package.json index 8523ef4fd789..ead9916326dd 100644 --- a/packages/manager/apps/carbon-calculator/package.json +++ b/packages/manager/apps/carbon-calculator/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-carbon-calculator-app", - "version": "0.3.3", + "version": "0.3.7", "private": true, "description": "OVHcloud CarbonCalculator app", "repository": { @@ -21,23 +21,23 @@ "dependencies": { "@ovh-ux/manager-at-internet-configuration": "^1.5.0", "@ovh-ux/manager-carbon-calculator": "^0.4.0", - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-error-page": "^2.4.0", "@ovh-ux/manager-ng-layout-helpers": "^2.9.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-at-internet-ui-router-plugin": "^3.5.0", "@ovh-ux/ng-ovh-api-wrappers": "^5.0.0", "@ovh-ux/ng-ovh-feature-flipping": "^1.1.1", "@ovh-ux/ng-ovh-http": "^5.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-ovh-swimming-poll": "^5.1.1", - "@ovh-ux/ng-shell-tracking": "^0.5.0", + "@ovh-ux/ng-shell-tracking": "^0.5.4", "@ovh-ux/ng-translate-async-loader": "^2.2.1", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", - "@ovh-ux/request-tagger": "^0.1.1", - "@ovh-ux/shell": "^3.2.0", + "@ovh-ux/request-tagger": "^0.2.0", + "@ovh-ux/shell": "^3.4.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "angular": "^1.7.5", diff --git a/packages/manager/apps/carrier-sip/CHANGELOG.md b/packages/manager/apps/carrier-sip/CHANGELOG.md index 8cbe5c75e81b..81a0584c630e 100644 --- a/packages/manager/apps/carrier-sip/CHANGELOG.md +++ b/packages/manager/apps/carrier-sip/CHANGELOG.md @@ -3,6 +3,14 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [3.1.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-carrier-sip-app@3.1.2...@ovh-ux/manager-carrier-sip-app@3.1.3) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-carrier-sip-app + + + + + ## [3.1.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-carrier-sip-app@3.1.1...@ovh-ux/manager-carrier-sip-app@3.1.2) (2024-02-26) **Note:** Version bump only for package @ovh-ux/manager-carrier-sip-app diff --git a/packages/manager/apps/carrier-sip/package.json b/packages/manager/apps/carrier-sip/package.json index 9e7d1fb94cac..04949312b206 100644 --- a/packages/manager/apps/carrier-sip/package.json +++ b/packages/manager/apps/carrier-sip/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-carrier-sip-app", - "version": "3.1.2", + "version": "3.1.3", "private": true, "description": "Carrier SIP Trunk standalone application.", "repository": { @@ -21,19 +21,19 @@ }, "dependencies": { "@ovh-ux/manager-carrier-sip": "^2.3.0", - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-telecom-styles": "^4.7.0", "@ovh-ux/ng-ovh-api-wrappers": "^5.1.0", "@ovh-ux/ng-ovh-checkbox-table": "^2.1.1", "@ovh-ux/ng-ovh-http": "^5.1.1", "@ovh-ux/ng-ovh-mondial-relay": "^8.7.0", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-ovh-swimming-poll": "^5.1.1", "@ovh-ux/ng-ovh-telecom-universe-components": "^7.24.0", "@ovh-ux/ng-translate-async-loader": "^2.2.1", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.22", "CSV-JS": "^1.2.0", diff --git a/packages/manager/apps/catalog/CHANGELOG.md b/packages/manager/apps/catalog/CHANGELOG.md index 653296b8f395..9bb43cb9769f 100644 --- a/packages/manager/apps/catalog/CHANGELOG.md +++ b/packages/manager/apps/catalog/CHANGELOG.md @@ -3,6 +3,47 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +# [1.7.0](https://github.com/ovh/manager/compare/@ovh-ux/manager-catalog-app@1.6.2...@ovh-ux/manager-catalog-app@1.7.0) (2024-03-13) + + +### Features + +* pci vouchers app in reactjs ([d6821ce](https://github.com/ovh/manager/commit/d6821cecd3bde7d884054d8e782e9a1e9dbfddac)) + + + + + +## [1.6.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-catalog-app@1.6.1...@ovh-ux/manager-catalog-app@1.6.2) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-catalog-app + + + + + +## [1.6.1](https://github.com/ovh/manager/compare/@ovh-ux/manager-catalog-app@1.6.0...@ovh-ux/manager-catalog-app@1.6.1) (2024-03-07) + + +### Reverts + +* Revert "feat(*): pci vouchers app in reactjs" ([b62c1a8](https://github.com/ovh/manager/commit/b62c1a8b1cfe63dbc420b660667209c324ffa9ab)) + + + + + +# [1.6.0](https://github.com/ovh/manager/compare/@ovh-ux/manager-catalog-app@1.5.0...@ovh-ux/manager-catalog-app@1.6.0) (2024-03-07) + + +### Features + +* pci vouchers app in reactjs ([ad08ee4](https://github.com/ovh/manager/commit/ad08ee4618d6243328eee76af7d1bd459a1a7d83)) + + + + + # [1.5.0](https://github.com/ovh/manager/compare/@ovh-ux/manager-catalog-app@1.4.1...@ovh-ux/manager-catalog-app@1.5.0) (2024-02-29) diff --git a/packages/manager/apps/catalog/package.json b/packages/manager/apps/catalog/package.json index 27128e3c5733..440cf10f71cd 100644 --- a/packages/manager/apps/catalog/package.json +++ b/packages/manager/apps/catalog/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-catalog-app", - "version": "1.5.0", + "version": "1.7.0", "private": true, "description": "OVHcloud Catalog application", "repository": { @@ -17,16 +17,16 @@ "start:dev": "lerna exec --stream --scope='@ovh-ux/manager-catalog-app' --include-dependencies -- npm run dev --if-present", "start:watch": "lerna exec --stream --parallel --scope='@ovh-ux/manager-catalog-app' --include-dependencies -- npm run dev:watch --if-present", "pretest": "tsc -p tsconfig.e2e.json", - "test": "jest --coverage -u", + "test": "jest", "test:e2e": "tsc && npx playwright test --headed", "test:e2e:ci": "tsc && npx playwright test", "test:e2e:script": "tsc && node ../../../../scripts/run-playwright.js" }, "dependencies": { - "@ovh-ux/manager-core-api": "^0.3.0", - "@ovh-ux/manager-react-core-application": "^0.5.2", - "@ovh-ux/shell": "^3.2.0", - "@ovhcloud/manager-components": "^1.3.0", + "@ovh-ux/manager-core-api": "^0.6.0", + "@ovh-ux/manager-react-core-application": "^0.7.0", + "@ovh-ux/shell": "^3.4.0", + "@ovhcloud/manager-components": "^1.5.0", "@ovhcloud/ods-common-theming": "16.6.0", "@ovhcloud/ods-components": "17.1.0", "@ovhcloud/ods-theme-blue-jeans": "16.6.0", diff --git a/packages/manager/apps/cda/CHANGELOG.md b/packages/manager/apps/cda/CHANGELOG.md index 0b5200f14e37..3e31799011d8 100644 --- a/packages/manager/apps/cda/CHANGELOG.md +++ b/packages/manager/apps/cda/CHANGELOG.md @@ -3,6 +3,38 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [2.1.6](https://github.com/ovh/manager/compare/@ovh-ux/manager-cda-app@2.1.5...@ovh-ux/manager-cda-app@2.1.6) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-cda-app + + + + + +## [2.1.5](https://github.com/ovh/manager/compare/@ovh-ux/manager-cda-app@2.1.4...@ovh-ux/manager-cda-app@2.1.5) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-cda-app + + + + + +## [2.1.4](https://github.com/ovh/manager/compare/@ovh-ux/manager-cda-app@2.1.3...@ovh-ux/manager-cda-app@2.1.4) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-cda-app + + + + + +## [2.1.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-cda-app@2.1.2...@ovh-ux/manager-cda-app@2.1.3) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-cda-app + + + + + ## [2.1.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-cda-app@2.1.1...@ovh-ux/manager-cda-app@2.1.2) (2024-02-26) **Note:** Version bump only for package @ovh-ux/manager-cda-app diff --git a/packages/manager/apps/cda/package.json b/packages/manager/apps/cda/package.json index d2cff21e4689..e43435adacc1 100644 --- a/packages/manager/apps/cda/package.json +++ b/packages/manager/apps/cda/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-cda-app", - "version": "2.1.2", + "version": "2.1.6", "private": true, "repository": { "type": "git", @@ -19,11 +19,11 @@ }, "dependencies": { "@ovh-ux/manager-cda": "^1.9.0", - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-filters": "^0.1.0 || ^1.1.1", "@ovh-ux/manager-ng-layout-helpers": "^2.9.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-at-internet-ui-router-plugin": "^3.5.0", "@ovh-ux/ng-ovh-actions-menu": "^5.1.1", "@ovh-ux/ng-ovh-api-wrappers": "^5.1.0", @@ -31,14 +31,14 @@ "@ovh-ux/ng-ovh-doc-url": "^2.1.1", "@ovh-ux/ng-ovh-http": "^5.1.1", "@ovh-ux/ng-ovh-proxy-request": "^2.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-responsive-popover": "^6.1.1", "@ovh-ux/ng-ovh-sidebar-menu": "^10.5.0", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-ovh-swimming-poll": "^5.1.1", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", "@ovh-ux/ng-ui-router-layout": "^4.3.0", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "angular": "^1.7.5", diff --git a/packages/manager/apps/cloud-connect/CHANGELOG.md b/packages/manager/apps/cloud-connect/CHANGELOG.md index 6680ff8ceb6f..4073d7eb9ddf 100644 --- a/packages/manager/apps/cloud-connect/CHANGELOG.md +++ b/packages/manager/apps/cloud-connect/CHANGELOG.md @@ -3,6 +3,38 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [1.8.6](https://github.com/ovh/manager/compare/@ovh-ux/manager-cloud-connect-app@1.8.5...@ovh-ux/manager-cloud-connect-app@1.8.6) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-cloud-connect-app + + + + + +## [1.8.5](https://github.com/ovh/manager/compare/@ovh-ux/manager-cloud-connect-app@1.8.4...@ovh-ux/manager-cloud-connect-app@1.8.5) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-cloud-connect-app + + + + + +## [1.8.4](https://github.com/ovh/manager/compare/@ovh-ux/manager-cloud-connect-app@1.8.3...@ovh-ux/manager-cloud-connect-app@1.8.4) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-cloud-connect-app + + + + + +## [1.8.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-cloud-connect-app@1.8.2...@ovh-ux/manager-cloud-connect-app@1.8.3) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-cloud-connect-app + + + + + ## [1.8.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-cloud-connect-app@1.8.1...@ovh-ux/manager-cloud-connect-app@1.8.2) (2024-02-26) **Note:** Version bump only for package @ovh-ux/manager-cloud-connect-app diff --git a/packages/manager/apps/cloud-connect/package.json b/packages/manager/apps/cloud-connect/package.json index 9655a2fab9bd..110e6934c0dc 100644 --- a/packages/manager/apps/cloud-connect/package.json +++ b/packages/manager/apps/cloud-connect/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-cloud-connect-app", - "version": "1.8.2", + "version": "1.8.6", "private": true, "description": "OVHcloud Connect standalone application.", "repository": { @@ -20,22 +20,22 @@ }, "dependencies": { "@ovh-ux/manager-cloud-connect": "^1.14.0", - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-ng-layout-helpers": "^2.9.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-at-internet-ui-router-plugin": "^3.5.0", "@ovh-ux/ng-ovh-api-wrappers": "^5.1.0", "@ovh-ux/ng-ovh-cloud-universe-components": "^2.12.0", "@ovh-ux/ng-ovh-http": "^5.1.1", "@ovh-ux/ng-ovh-proxy-request": "^2.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-ovh-swimming-poll": "^5.1.1", "@ovh-ux/ng-ovh-user-pref": "^2.1.1", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", "@ovh-ux/ng-ui-router-layout": "^4.3.0", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "angular": "^1.7.5", diff --git a/packages/manager/apps/container/CHANGELOG.md b/packages/manager/apps/container/CHANGELOG.md index c309178b8e77..e3f7e0a552f4 100644 --- a/packages/manager/apps/container/CHANGELOG.md +++ b/packages/manager/apps/container/CHANGELOG.md @@ -3,6 +3,61 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +# [0.49.0](https://github.com/ovh/manager/compare/@ovh-ux/manager-container-app@0.48.0...@ovh-ux/manager-container-app@0.49.0) (2024-03-18) + + +### Features + +* **network-security:** remove beta label and survey links ([#11034](https://github.com/ovh/manager/issues/11034)) ([5e3f152](https://github.com/ovh/manager/commit/5e3f152c4ca7d752f3945860584f8e746d46b486)) + + + + + +# [0.48.0](https://github.com/ovh/manager/compare/@ovh-ux/manager-container-app@0.47.2...@ovh-ux/manager-container-app@0.48.0) (2024-03-13) + + +### Features + +* pci vouchers app in reactjs ([d6821ce](https://github.com/ovh/manager/commit/d6821cecd3bde7d884054d8e782e9a1e9dbfddac)) + + + + + +## [0.47.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-container-app@0.47.1...@ovh-ux/manager-container-app@0.47.2) (2024-03-11) + + +### Bug Fixes + +* **telecom.sidebar:** set label to service name if empty ([#10973](https://github.com/ovh/manager/issues/10973)) ([8a111f5](https://github.com/ovh/manager/commit/8a111f5217646287a796e2ac011959c64655dbf6)) + + + + + +## [0.47.1](https://github.com/ovh/manager/compare/@ovh-ux/manager-container-app@0.47.0...@ovh-ux/manager-container-app@0.47.1) (2024-03-07) + + +### Reverts + +* Revert "feat(*): pci vouchers app in reactjs" ([b62c1a8](https://github.com/ovh/manager/commit/b62c1a8b1cfe63dbc420b660667209c324ffa9ab)) + + + + + +# [0.47.0](https://github.com/ovh/manager/compare/@ovh-ux/manager-container-app@0.46.2...@ovh-ux/manager-container-app@0.47.0) (2024-03-07) + + +### Features + +* pci vouchers app in reactjs ([ad08ee4](https://github.com/ovh/manager/commit/ad08ee4618d6243328eee76af7d1bd459a1a7d83)) + + + + + ## [0.46.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-container-app@0.46.1...@ovh-ux/manager-container-app@0.46.2) (2024-03-04) diff --git a/packages/manager/apps/container/package.json b/packages/manager/apps/container/package.json index 2baf7aba2415..8eb48cb6e34a 100644 --- a/packages/manager/apps/container/package.json +++ b/packages/manager/apps/container/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-container-app", - "version": "0.46.2", + "version": "0.49.0", "private": true, "description": "OVHcloud Manager Container.", "repository": { @@ -27,13 +27,13 @@ "dependencies": { "@emotion/react": "^11.10.0", "@emotion/styled": "^11.10.0", - "@ovh-ux/manager-config": "^7.3.0", + "@ovh-ux/manager-config": "^7.3.1", "@ovh-ux/manager-vite-config": "^0.5.0", "@ovh-ux/ovh-payment-method": "^0.4.0", - "@ovh-ux/ovh-product-icons": "^0.2.0", + "@ovh-ux/ovh-product-icons": "^0.2.1", "@ovh-ux/ovh-reket": "^2.1.1", - "@ovh-ux/request-tagger": "^0.1.1", - "@ovh-ux/shell": "^3.2.0", + "@ovh-ux/request-tagger": "^0.2.0", + "@ovh-ux/shell": "^3.4.0", "@ovh-ux/ui-kit": "^6.7.7", "@ovhcloud/ods-core": "^14.0.1", "@ovhcloud/ods-stencil": "^14.0.1", diff --git a/packages/manager/apps/container/src/container/common/language/index.tsx b/packages/manager/apps/container/src/container/common/language/index.tsx index 8f4b4ce860d7..f84e395320cc 100644 --- a/packages/manager/apps/container/src/container/common/language/index.tsx +++ b/packages/manager/apps/container/src/container/common/language/index.tsx @@ -1,4 +1,5 @@ import React, { useEffect, useRef, useState } from 'react'; +import { useTranslation } from 'react-i18next'; import { useMediaQuery } from 'react-responsive'; import useClickAway from 'react-use/lib/useClickAway'; @@ -20,6 +21,7 @@ function LanguageMenu({ setUserLocale, userLocale = '', }: Props): JSX.Element { + const { i18n } = useTranslation('language'); const ref = useRef(); const shell = useShell(); const [show, setShow] = useState(false); @@ -41,6 +43,7 @@ function LanguageMenu({ shell.getPlugin('i18n').setLocale(locale); setShow(false); setUserLocale(locale); + i18n.changeLanguage(locale); }; useEffect(() => { diff --git a/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/DedicatedSidebar.tsx b/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/DedicatedSidebar.tsx index 7a02415d2ff8..2e0dd3d3cabc 100644 --- a/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/DedicatedSidebar.tsx +++ b/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/DedicatedSidebar.tsx @@ -258,7 +258,6 @@ export default function DedicatedSidebar() { }, feature['network-security'] && { id: 'dedicated-network-security', - badge: 'beta', label: t('sidebar_network_security'), icon: getIcon('oui-icon oui-icon-shield_concept'), href: navigation.getURL('dedicated', '#/network-security'), diff --git a/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/HostedPrivateCloudSidebar.tsx b/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/HostedPrivateCloudSidebar.tsx index 3d8393c52df0..2d8a8a419216 100644 --- a/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/HostedPrivateCloudSidebar.tsx +++ b/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/HostedPrivateCloudSidebar.tsx @@ -154,7 +154,6 @@ export default function HostedPrivateCloudSidebar() { }, feature['network-security'] && { id: 'hpc-network-security', - badge: 'beta', label: t('sidebar_network_security'), icon: getIcon('oui-icon oui-icon-shield_concept'), href: navigation.getURL('dedicated', '#/network-security'), diff --git a/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/TelecomSidebar.tsx b/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/TelecomSidebar.tsx index 59405d48e7e7..ca3e1e280f8d 100644 --- a/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/TelecomSidebar.tsx +++ b/packages/manager/apps/container/src/container/legacy/server-sidebar/universe/TelecomSidebar.tsx @@ -97,8 +97,9 @@ export default function TelecomSidebar() { const services = await loadServices( `/pack/xdsl/${xdsl.serviceName}/xdslAccess/services`, ); - return services.map((service) => ({ + const servicesLoaded = services.map((service) => ({ ...service, + label: service.label || service.serviceName, keywords: service.extraParams?.length ? service.extraParams[0] : '', @@ -108,6 +109,7 @@ export default function TelecomSidebar() { ), })); + return servicesLoaded; }, })), ...xdslStandalone.map((sdsl) => { diff --git a/packages/manager/apps/container/src/container/nav-reshuffle/sidebar/navigation-tree/services/network.ts b/packages/manager/apps/container/src/container/nav-reshuffle/sidebar/navigation-tree/services/network.ts index 9235bb7db6df..52c9bf4f74ce 100644 --- a/packages/manager/apps/container/src/container/nav-reshuffle/sidebar/navigation-tree/services/network.ts +++ b/packages/manager/apps/container/src/container/nav-reshuffle/sidebar/navigation-tree/services/network.ts @@ -34,7 +34,6 @@ export default { id: 'dedicated-network-security', translation: 'sidebar_network_security', serviceType: 'NETWORK_SECURITY', - badge: 'beta', routing: { application: 'dedicated', hash: '#/network-security', diff --git a/packages/manager/apps/dbaas-logs/CHANGELOG.md b/packages/manager/apps/dbaas-logs/CHANGELOG.md index 2767d979c353..e5211f56560e 100644 --- a/packages/manager/apps/dbaas-logs/CHANGELOG.md +++ b/packages/manager/apps/dbaas-logs/CHANGELOG.md @@ -3,6 +3,38 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [2.1.6](https://github.com/ovh/manager/compare/@ovh-ux/manager-dbaas-logs-app@2.1.5...@ovh-ux/manager-dbaas-logs-app@2.1.6) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-dbaas-logs-app + + + + + +## [2.1.5](https://github.com/ovh/manager/compare/@ovh-ux/manager-dbaas-logs-app@2.1.4...@ovh-ux/manager-dbaas-logs-app@2.1.5) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-dbaas-logs-app + + + + + +## [2.1.4](https://github.com/ovh/manager/compare/@ovh-ux/manager-dbaas-logs-app@2.1.3...@ovh-ux/manager-dbaas-logs-app@2.1.4) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-dbaas-logs-app + + + + + +## [2.1.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-dbaas-logs-app@2.1.2...@ovh-ux/manager-dbaas-logs-app@2.1.3) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-dbaas-logs-app + + + + + ## [2.1.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-dbaas-logs-app@2.1.1...@ovh-ux/manager-dbaas-logs-app@2.1.2) (2024-02-26) **Note:** Version bump only for package @ovh-ux/manager-dbaas-logs-app diff --git a/packages/manager/apps/dbaas-logs/package.json b/packages/manager/apps/dbaas-logs/package.json index 441852a9612e..64786f2c745c 100644 --- a/packages/manager/apps/dbaas-logs/package.json +++ b/packages/manager/apps/dbaas-logs/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-dbaas-logs-app", - "version": "2.1.2", + "version": "2.1.6", "private": true, "description": "Logs Data Platform standalone application.", "repository": { @@ -20,12 +20,12 @@ }, "dependencies": { "@ovh-ux/manager-at-internet-configuration": "^1.5.0", - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-dbaas-logs": "^1.19.0", "@ovh-ux/manager-filters": "^0.1.0 || ^1.1.1", "@ovh-ux/manager-ng-layout-helpers": "^2.9.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-at-internet-ui-router-plugin": "^3.5.0", "@ovh-ux/ng-ovh-actions-menu": "^5.1.1", "@ovh-ux/ng-ovh-api-wrappers": "^5.1.0", @@ -33,7 +33,7 @@ "@ovh-ux/ng-ovh-doc-url": "^2.1.1", "@ovh-ux/ng-ovh-http": "^5.1.1", "@ovh-ux/ng-ovh-proxy-request": "^2.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-responsive-popover": "^6.1.1", "@ovh-ux/ng-ovh-sidebar-menu": "^10.5.0", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", @@ -42,7 +42,7 @@ "@ovh-ux/ng-tail-logs": "^2.1.1", "@ovh-ux/ng-translate-async-loader": "^2.2.1", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "angular": "^1.7.5", diff --git a/packages/manager/apps/dedicated/CHANGELOG.md b/packages/manager/apps/dedicated/CHANGELOG.md index 074d0b3da12b..e25465cfca57 100644 --- a/packages/manager/apps/dedicated/CHANGELOG.md +++ b/packages/manager/apps/dedicated/CHANGELOG.md @@ -3,6 +3,82 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +# [19.27.0](https://github.com/ovh/manager/compare/@ovh-ux/manager-dedicated@19.26.2...@ovh-ux/manager-dedicated@19.27.0) (2024-03-18) + + +### Bug Fixes + +* **i18n:** add missing translations [CDS 2825] ([#11099](https://github.com/ovh/manager/issues/11099)) ([0ebd4af](https://github.com/ovh/manager/commit/0ebd4afd5e9153f2cb784f66c837ce4c314047a8)) +* **ip.firewall:** display select component completely ([4c496ac](https://github.com/ovh/manager/commit/4c496ac34941f8c32b42565bea976afbcdb4fb6c)) +* **ip.gamefirewall:** check ports are not already used ([#10922](https://github.com/ovh/manager/issues/10922)) ([1344575](https://github.com/ovh/manager/commit/1344575aeb0a6f9395d0fec731f2f542ba21b9f2)) +* **ip.gamefirewall:** use same label for protocol display ([f68c44a](https://github.com/ovh/manager/commit/f68c44a75b9a56dc37317ffbe632a6e38c785aad)) +* **network-security:** rework on periodicity labels ([#10900](https://github.com/ovh/manager/issues/10900)) ([09ca920](https://github.com/ovh/manager/commit/09ca92093ca5db85811acb1cda92cad2b5637b70)) +* **security.dashboard:** display timestamp to locale time ([#10907](https://github.com/ovh/manager/issues/10907)) ([0225a5f](https://github.com/ovh/manager/commit/0225a5fba6d0874d04199710d3d6b7eea00124b5)) + + +### Features + +* **dedicated:** change document size indication sentence ([#11089](https://github.com/ovh/manager/issues/11089)) ([e4c2d85](https://github.com/ovh/manager/commit/e4c2d853720f4e1a7f29c865036217edab68000e)) +* **dedicated:** changed identity documents inner title ([#11094](https://github.com/ovh/manager/issues/11094)) ([a6fb5b1](https://github.com/ovh/manager/commit/a6fb5b1609227079ae05f8da18a69106bcdd06dc)) +* **network-security:** display less data on x-axis ([87e0bd1](https://github.com/ovh/manager/commit/87e0bd1977b912d07f89f078069ee9d42f2d4008)) +* **network-security:** remove beta label and survey links ([#11034](https://github.com/ovh/manager/issues/11034)) ([5e3f152](https://github.com/ovh/manager/commit/5e3f152c4ca7d752f3945860584f8e746d46b486)) + + + + + +## [19.26.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-dedicated@19.26.1...@ovh-ux/manager-dedicated@19.26.2) (2024-03-14) + + +### Bug Fixes + +* **dedicated:** mail change did not work ([#11177](https://github.com/ovh/manager/issues/11177)) ([4d213c7](https://github.com/ovh/manager/commit/4d213c79e8edd7092577b73fc7c77a56b3067a7b)) + + + + + +## [19.26.1](https://github.com/ovh/manager/compare/@ovh-ux/manager-dedicated@19.26.0...@ovh-ux/manager-dedicated@19.26.1) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-dedicated + + + + + +# [19.26.0](https://github.com/ovh/manager/compare/@ovh-ux/manager-dedicated@19.25.2...@ovh-ux/manager-dedicated@19.26.0) (2024-03-11) + + +### Bug Fixes + +* **dedicated.account:** remove banner when edition possible ([#11088](https://github.com/ovh/manager/issues/11088)) ([fbb9c3a](https://github.com/ovh/manager/commit/fbb9c3a7d2e67fbcedb90b36e093347512b518d7)) + + +### Features + +* **dedicated.vmware:** fix custom nsx edges sizing ([#11147](https://github.com/ovh/manager/issues/11147)) ([690df2d](https://github.com/ovh/manager/commit/690df2dd800be950cc860f61e3d079bd0eec3821)) +* **dedicated:** add translate for Toronto ([#11051](https://github.com/ovh/manager/issues/11051)) ([5cd3931](https://github.com/ovh/manager/commit/5cd3931ef58df1a499172dc35ab557a54b3be1ed)) + + + + + +## [19.25.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-dedicated@19.25.1...@ovh-ux/manager-dedicated@19.25.2) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-dedicated + + + + + +## [19.25.1](https://github.com/ovh/manager/compare/@ovh-ux/manager-dedicated@19.25.0...@ovh-ux/manager-dedicated@19.25.1) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-dedicated + + + + + # [19.25.0](https://github.com/ovh/manager/compare/@ovh-ux/manager-dedicated@19.24.1...@ovh-ux/manager-dedicated@19.25.0) (2024-03-04) diff --git a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_de_DE.json b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_de_DE.json index 7315d27618a4..96b0c3256ed1 100644 --- a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_de_DE.json +++ b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_de_DE.json @@ -37,7 +37,7 @@ "account_contacts_service_contact_admin": "Administrator-Kontakt", "account_contacts_service_contact_tech": "Technischer Kontakt", "account_contacts_service_contact_billing": "Rechnungskontakt", - "account_contacts_service_infos": "Sie können die Administator-, technischen und Rechnungs-Accounts Ihrer Dienste ändern.", + "account_contacts_service_infos": "Sie können die Administrator-, technischen und Abrechnungs-Accounts Ihrer Dienste ändern.", "account_contacts_service_category_LOGS": "Logs Data Platform ", "account_contacts_service_category_NETAPP": "NetApp" -} \ No newline at end of file +} diff --git a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_en_GB.json b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_en_GB.json index 1d33045f9889..cf7d60e716e6 100644 --- a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_en_GB.json +++ b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_en_GB.json @@ -40,4 +40,4 @@ "account_contacts_service_infos": "You can change the administrator, technical and billing accounts for your services.", "account_contacts_service_category_LOGS": "Logs Data Platform", "account_contacts_service_category_NETAPP": "NetApp" -} \ No newline at end of file +} diff --git a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_es_ES.json b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_es_ES.json index e4dcb9f9fe83..2748eeb13a27 100644 --- a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_es_ES.json +++ b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_es_ES.json @@ -37,7 +37,7 @@ "account_contacts_service_contact_admin": "Contacto administrador", "account_contacts_service_contact_tech": "Contacto técnico ", "account_contacts_service_contact_billing": "Contacto de facturación", - "account_contacts_service_infos": "Puede cambiar las cuentas del contacto administrador, técnico y de facturación de sus servicios.", + "account_contacts_service_infos": "Puede modificar las cuentas del contacto administrador, técnico y de facturación de sus servicios.", "account_contacts_service_category_LOGS": "Logs Data Platform", "account_contacts_service_category_NETAPP": "NetApp" -} \ No newline at end of file +} diff --git a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_fr_CA.json b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_fr_CA.json index c2ec3a4e2c67..04471dbbb3f0 100644 --- a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_fr_CA.json +++ b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_fr_CA.json @@ -37,7 +37,7 @@ "account_contacts_service_contact_admin": "Contact administrateur", "account_contacts_service_contact_tech": "Contact technique", "account_contacts_service_contact_billing": "Contact facturation", - "account_contacts_service_infos": "Vous avez la possibilité de changer les comptes administateur, technique et facturation de vos services.", + "account_contacts_service_infos": "Vous avez la possibilité de changer les comptes administrateur, technique et facturation de vos services.", "account_contacts_service_category_LOGS": "Logs Data Platform", "account_contacts_service_category_NETAPP": "NetApp" -} \ No newline at end of file +} diff --git a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_fr_FR.json b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_fr_FR.json index 8cda1ecb4241..04471dbbb3f0 100644 --- a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_fr_FR.json +++ b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_fr_FR.json @@ -37,7 +37,7 @@ "account_contacts_service_contact_admin": "Contact administrateur", "account_contacts_service_contact_tech": "Contact technique", "account_contacts_service_contact_billing": "Contact facturation", - "account_contacts_service_infos": "Vous avez la possibilité de changer les comptes administateur, technique et facturation de vos services.", + "account_contacts_service_infos": "Vous avez la possibilité de changer les comptes administrateur, technique et facturation de vos services.", "account_contacts_service_category_LOGS": "Logs Data Platform", "account_contacts_service_category_NETAPP": "NetApp" } diff --git a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_it_IT.json b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_it_IT.json index aba0eccc0fe5..a787687fbed4 100644 --- a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_it_IT.json +++ b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_it_IT.json @@ -37,7 +37,7 @@ "account_contacts_service_contact_admin": "Contatto amministratore", "account_contacts_service_contact_tech": "Contatto tecnico", "account_contacts_service_contact_billing": "Contatto di fatturazione", - "account_contacts_service_infos": "Hai la possibilità di modificare gli account amministratore, tecnico e di fatturazione dei tuoi servizi.", + "account_contacts_service_infos": "Hai la possibilità di modificare gli account del contatto amministratore, tecnico e di fatturazione dei tuoi servizi.", "account_contacts_service_category_LOGS": "Logs Data Platform", "account_contacts_service_category_NETAPP": "NetApp" -} \ No newline at end of file +} diff --git a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_pl_PL.json b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_pl_PL.json index 01cd226150b9..559e19b50cb6 100644 --- a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_pl_PL.json +++ b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_pl_PL.json @@ -37,7 +37,7 @@ "account_contacts_service_contact_admin": "Kontakt administracyjny", "account_contacts_service_contact_tech": "Kontakt techniczny", "account_contacts_service_contact_billing": "Kontakt księgowy", - "account_contacts_service_infos": "Możesz zmienić kontakt administracyjny, techniczny i księgowy dla swoich usług.", + "account_contacts_service_infos": "Możesz zmienić kontakt administracyjny, techniczny i księgowy przypisany do Twoich usług.", "account_contacts_service_category_LOGS": "Logs Data Platform", "account_contacts_service_category_NETAPP": "NetApp" -} \ No newline at end of file +} diff --git a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_pt_PT.json b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_pt_PT.json index b6b563e16374..542212869b57 100644 --- a/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_pt_PT.json +++ b/packages/manager/apps/dedicated/client/app/account/contacts/service/translations/Messages_pt_PT.json @@ -37,7 +37,7 @@ "account_contacts_service_contact_admin": "Contacto administrador", "account_contacts_service_contact_tech": "Contacto técnico", "account_contacts_service_contact_billing": "Contacto de faturação", - "account_contacts_service_infos": "Pode alterar as contas do administrador, do responsável técnico e do responsável pela faturação dos seus serviços.", + "account_contacts_service_infos": "Tem a possibilidade de alterar as contas administrador, técnica e de faturação dos seus serviços.", "account_contacts_service_category_LOGS": "Logs Data Platform", "account_contacts_service_category_NETAPP": "NetApp" -} \ No newline at end of file +} diff --git a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_de_DE.json b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_de_DE.json index 290793e0ec48..9212788050c1 100644 --- a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_de_DE.json +++ b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_de_DE.json @@ -2,7 +2,6 @@ "user_account_identity_documents": "Meine Ausweisdokumente", "user_account_identity_documents_sub_title": "Dokumente einreichen", "user_account_identity_documents_intro": "Sie haben Ihren Account erstellt und möchten eine Bestellung über unsere indische Website aufgeben. Aufgrund der geltenden Vorschriften muss vor der Bestellung Ihre Identität überprüft werden.", - "user_account_identity_documents_intro_kyc_reminder": "Vergewissern Sie sich, dass Ihre persönlichen Daten mit dem Namen und der Adresse auf Ihren offiziellen Dokumenten übereinstimmen.", "user_account_identity_documents_list_for_particular": "Als Privatperson müsse Sie folgende Dokumente bereitstellen:", "user_account_identity_documents_list_for_enterprise": "Als Unternehmen müssen Sie folgende Dokumente bereitstellen:", "user_account_identity_documents_list_for_association": "Als Verein oder Verband müssen Sie folgende Dokumente bereitstellen:", @@ -13,8 +12,7 @@ "user_account_identity_documents_list_doc3": "GST-Zertifikat", "user_account_identity_documents_list_doc3_optional": "GST-Zertifikat (optional)", "user_account_identity_documents_description": "Die Dokumente werden nach Vertragsende noch 5 Jahre aufbewahrt.", - "user_account_identity_documents_selection_file_format": "Format: jpg, jpeg, pdf, png Maximale Größe: 10 MB", - "user_account_identity_documents_selection_file_format_invalid": "Nicht unterstütztes Dateiformat. Bitte verwenden Sie eines der zulässigen Formate: jpg, jpeg, pdf und png", + "user_account_identity_documents_selection_file_format": "Format: jpg, jpeg, pdf, png. Die maximale Dateigröße für jedes Dokument beträgt 10 MB.", "user_account_identity_documents_submit": "Meine Dokumente senden", "user_account_identity_documents_submit_success_message_title": "Wir haben Ihre Dokumente erhalten.", "user_account_identity_documents_submit_success_message_description": "Wir haben alle Ihre Dokumente erhalten. Sie werden unseren Teams zur Validierung vorgelegt. Sie werden per E-Mail über die Validierung informiert oder kontaktiert, wenn wir weitere Informationen benötigen.", @@ -23,5 +21,9 @@ "user_account_identity_documents_legal_info1": "OVH S.A.S ist für die Verarbeitung Ihrer personenbezogenen Daten verantwortlich. Die über dieses Formular erhobenen Daten werden verarbeitet, um den Richtlinien zur Cybersicherheit vom 28.04.2022 Rechnung zu tragen, die das CERT-IN gemäß den Bestimmungen des Unterabschnitts (6) von Artikel 70B des Information Technology (IT) Act von 2000 veröffentlicht hat.", "user_account_identity_documents_legal_info2": "Weitere Informationen zur Verarbeitung Ihrer Daten und zu Ihren Rechten finden Sie in unseren Richtlinien zur Nutzung personenbezogener Daten.", "user_account_identity_documents_verification_in_progress_info": "Die Verarbeitung Ihrer Dokumente wird derzeit von unserem Team analysiert.", - "user_account_identity_documents_verification_waiting_info": "Ihre Anfrage wurde analysiert, es werden jedoch weitere Dokumente benötigt. Bitte sehen Sie sich Ihr Support-Ticket an." -} \ No newline at end of file + "user_account_identity_documents_verification_waiting_info": "Ihre Anfrage wurde analysiert, es werden jedoch weitere Dokumente benötigt. Bitte sehen Sie sich Ihr Support-Ticket an.", + "user_account_identity_documents_selection_file_format_invalid": "Nicht unterstütztes Dateiformat. Bitte verwenden Sie eines der zulässigen Formate: jpg, jpeg, pdf und png", + "user_account_identity_documents_intro_ensure_correspondance": "Vergewissern Sie sich, dass Ihre persönlichen Daten mit dem Namen und der Adresse auf Ihren offiziellen Dokumenten übereinstimmen.", + "user_account_identity_documents_intro_kyc_reminder": "Vergewissern Sie sich, dass Ihre persönlichen Daten mit dem Namen und der Adresse auf Ihren offiziellen Dokumenten übereinstimmen.", + "user_account_identity_documents_title": "Überprüfung der Dokumente erforderlich" +} diff --git a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_en_GB.json b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_en_GB.json index 805173cb957f..97c6931bd577 100644 --- a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_en_GB.json +++ b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_en_GB.json @@ -2,7 +2,6 @@ "user_account_identity_documents": "My identity documents", "user_account_identity_documents_sub_title": "Upload your documents", "user_account_identity_documents_intro": "You have created your account and you want to order from our Indian site. The regulations in force require that you verify your identity before ordering.", - "user_account_identity_documents_intro_kyc_reminder": "Please ensure that your personal data matches the name and address in your official documents.", "user_account_identity_documents_list_for_particular": "If you are an individual, the mandatory documents to provide are:", "user_account_identity_documents_list_for_enterprise": "If you are a company, the mandatory documents to provide are:", "user_account_identity_documents_list_for_association": "If you are an organisation, the mandatory documents to provide are:", @@ -13,8 +12,7 @@ "user_account_identity_documents_list_doc3": "GST certificate", "user_account_identity_documents_list_doc3_optional": "GST certificate (optional)", "user_account_identity_documents_description": "The documents will be retained for 5 years after the end of the contract.", - "user_account_identity_documents_selection_file_format": "Format: jpg, jpeg, pdf, png\nMaximum size: 10 MB.", - "user_account_identity_documents_selection_file_format_invalid": "File format not supported. Please use one of the accepted formats: jpg, jpeg, pdf and png", + "user_account_identity_documents_selection_file_format": "Format: jpg, jpeg, pdf, png. The file size limit for each document is 10 MB.", "user_account_identity_documents_submit": "Send my documents", "user_account_identity_documents_submit_success_message_title": "Thank you, we have received your documents!", "user_account_identity_documents_submit_success_message_description": "We have received all of your documents. They will be submitted to our teams for validation. You will be notified of their validation by email, or you will be contacted if we need further information.", @@ -23,5 +21,9 @@ "user_account_identity_documents_legal_info1": "OVH S.A.S is responsible for processing your personal data. The data collected through this form is processed in order to comply with the Cybersecurity Guidelines of 28.04.2022, published by CERT-In pursuant to the provisions of subsection (6) of section 70B of the Information Technology (IT) Act, 2000.", "user_account_identity_documents_legal_info2": "To find out more about how your data is processed, along with your rights, please refer to our Policy on the Use of Personal Data.", "user_account_identity_documents_verification_in_progress_info": "Your documents are currently being processed by our team.", - "user_account_identity_documents_verification_waiting_info": "Your request has been processed but we require additional documents. Please consult your support ticket." -} \ No newline at end of file + "user_account_identity_documents_verification_waiting_info": "Your request has been processed but we require additional documents. Please consult your support ticket.", + "user_account_identity_documents_selection_file_format_invalid": "File format not supported. Please use one of the accepted formats: jpg, jpeg, pdf and png", + "user_account_identity_documents_intro_ensure_correspondance": "Make sure your personal information matches the name and address provided in your official documents.", + "user_account_identity_documents_intro_kyc_reminder": "Please ensure that your personal data matches the name and address in your official documents.", + "user_account_identity_documents_title": "Verification of documents required" +} diff --git a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_es_ES.json b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_es_ES.json index 13b0b0797de7..17a75ad8ff00 100644 --- a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_es_ES.json +++ b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_es_ES.json @@ -2,7 +2,6 @@ "user_account_identity_documents": "Mis documentos de identidad", "user_account_identity_documents_sub_title": "Añada sus documentos", "user_account_identity_documents_intro": "Ha creado su cuenta y quiere realizar un pedido desde nuestro sitio web en India. Según la normativa vigente, es necesario verificar su identidad para poder realizar un pedido.", - "user_account_identity_documents_intro_kyc_reminder": "Asegúrese de que sus datos personales coinciden con el nombre y la dirección que aparecen en sus documentos oficiales.", "user_account_identity_documents_list_for_particular": "Como particular, los documentos que deben presentarse de manera obligatoria son los siguientes:", "user_account_identity_documents_list_for_enterprise": "Como empresa, los documentos que deben presentarse de manera obligatoria son los siguientes:", "user_account_identity_documents_list_for_association": "Como asociación, los documentos que deben presentarse de manera obligatoria son los siguientes:", @@ -13,8 +12,7 @@ "user_account_identity_documents_list_doc3": "Certificado GST", "user_account_identity_documents_list_doc3_optional": "Certificado GST (opcional)", "user_account_identity_documents_description": "Los documentos se conservarán durante 5 años una vez finalizado el contrato.", - "user_account_identity_documents_selection_file_format": "Formato: jpg, jpeg, pdf, png Tamaño máximo: 10 MB.", - "user_account_identity_documents_selection_file_format_invalid": "Formato de archivo no compatible. Por favor, utilice cualquiera de los formatos aceptados: jpg, jpeg, pdf y png.", + "user_account_identity_documents_selection_file_format": "Formato: jpg, jpeg, pdf y png. El tamaño máximo del archivo para cada documento es de 10 MB.", "user_account_identity_documents_submit": "Enviar mis documentos", "user_account_identity_documents_submit_success_message_title": "Gracias, ¡hemos recibido sus documentos!", "user_account_identity_documents_submit_success_message_description": "Le confirmamos que hemos recibido todos sus documentos. A continuación, deberán ser validados por nuestro equipo. Le enviaremos un mensaje de correo electrónico una vez que hayan sido validados. Si es necesaria alguna información adicional, nos pondremos en contacto con usted.", @@ -23,5 +21,9 @@ "user_account_identity_documents_legal_info1": "OVH SAS es el responsable del tratamiento de sus datos personales. Los datos recopilados a través de este formulario son tratados en cumplimiento de las Directrices de Ciberseguridad del 28/04/2022 publicadas por el CERT-In en virtud de las disposiciones de la subsección (6) del artículo 70-B de la Information Technology (IT) Act, 2000.", "user_account_identity_documents_legal_info2": "Para más información sobre el tratamiento de sus datos y sus derechos, consulte la Política de uso de datos personales de OVHcloud.", "user_account_identity_documents_verification_in_progress_info": "Nuestro equipo está analizando el tratamiento de sus documentos.", - "user_account_identity_documents_verification_waiting_info": "Su solicitud ha sido analizada, pero es necesaria información adicional. Consulte su tíquet de soporte." -} \ No newline at end of file + "user_account_identity_documents_verification_waiting_info": "Su solicitud ha sido analizada, pero es necesaria información adicional. Consulte su tíquet de soporte.", + "user_account_identity_documents_selection_file_format_invalid": "Formato de archivo no compatible. Por favor, utilice cualquiera de los formatos aceptados: jpg, jpeg, pdf y png.", + "user_account_identity_documents_intro_ensure_correspondance": "Asegúrese de que sus datos personales coinciden con el nombre y la dirección que aparecen en sus documentos oficiales.", + "user_account_identity_documents_intro_kyc_reminder": "Asegúrese de que sus datos personales coinciden con el nombre y la dirección que aparecen en sus documentos oficiales.", + "user_account_identity_documents_title": "Es necesario verificar los documentos" +} diff --git a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_fr_CA.json b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_fr_CA.json index 3785540228c9..0dc1d2a0ac4a 100644 --- a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_fr_CA.json +++ b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_fr_CA.json @@ -1,5 +1,6 @@ { "user_account_identity_documents": "Mes documents d'identité", + "user_account_identity_documents_title": "Vérification des documents nécessaire", "user_account_identity_documents_sub_title": "Déposez vos documents", "user_account_identity_documents_intro": "Vous avez créé votre compte et vous souhaitez faire une commande depuis notre site Indien. La règlementation en vigueur nécessite une vérification de votre identité avant toute commande.", "user_account_identity_documents_intro_kyc_reminder": "Assurez-vous que vos données personnelles correspondent au nom et à l'adresse figurant dans vos documents officiels.", @@ -13,7 +14,7 @@ "user_account_identity_documents_list_doc3": "Certificat GST", "user_account_identity_documents_list_doc3_optional": "Certificat GST (optionnel)", "user_account_identity_documents_description": "Les documents seront conservés durant 5 ans après la fin du contrat.", - "user_account_identity_documents_selection_file_format": "Format: jpg, jpeg, pdf, png Taille maximale: 10 mo.", + "user_account_identity_documents_selection_file_format": "Format: jpg, jpeg, pdf, png. La taille maximale du fichier pour chaque document est de 10 Mo.", "user_account_identity_documents_selection_file_format_invalid": "Format de fichier non pris en charge. Veuillez utiliser l'un des formats acceptés : jpg, jpeg, pdf et png", "user_account_identity_documents_submit": "Envoyer mes documents", "user_account_identity_documents_submit_success_message_title": "Merci, nous avons bien reçu vos documents!", diff --git a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_fr_FR.json b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_fr_FR.json index 3785540228c9..0dc1d2a0ac4a 100644 --- a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_fr_FR.json +++ b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_fr_FR.json @@ -1,5 +1,6 @@ { "user_account_identity_documents": "Mes documents d'identité", + "user_account_identity_documents_title": "Vérification des documents nécessaire", "user_account_identity_documents_sub_title": "Déposez vos documents", "user_account_identity_documents_intro": "Vous avez créé votre compte et vous souhaitez faire une commande depuis notre site Indien. La règlementation en vigueur nécessite une vérification de votre identité avant toute commande.", "user_account_identity_documents_intro_kyc_reminder": "Assurez-vous que vos données personnelles correspondent au nom et à l'adresse figurant dans vos documents officiels.", @@ -13,7 +14,7 @@ "user_account_identity_documents_list_doc3": "Certificat GST", "user_account_identity_documents_list_doc3_optional": "Certificat GST (optionnel)", "user_account_identity_documents_description": "Les documents seront conservés durant 5 ans après la fin du contrat.", - "user_account_identity_documents_selection_file_format": "Format: jpg, jpeg, pdf, png Taille maximale: 10 mo.", + "user_account_identity_documents_selection_file_format": "Format: jpg, jpeg, pdf, png. La taille maximale du fichier pour chaque document est de 10 Mo.", "user_account_identity_documents_selection_file_format_invalid": "Format de fichier non pris en charge. Veuillez utiliser l'un des formats acceptés : jpg, jpeg, pdf et png", "user_account_identity_documents_submit": "Envoyer mes documents", "user_account_identity_documents_submit_success_message_title": "Merci, nous avons bien reçu vos documents!", diff --git a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_it_IT.json b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_it_IT.json index 13aa63c24f83..b4b1678252b6 100644 --- a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_it_IT.json +++ b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_it_IT.json @@ -2,7 +2,6 @@ "user_account_identity_documents": "I miei documenti d'identità", "user_account_identity_documents_sub_title": "Inserisci i tuoi documenti", "user_account_identity_documents_intro": "Hai creato il tuo account e vuoi effettuare un ordine dal nostro sito indiano. La normativa vigente richiede una verifica dell'identità prima di effettuare qualsiasi ordine.", - "user_account_identity_documents_intro_kyc_reminder": "Assicurati che i tuoi dati personali coincidano con il nome e l’indirizzo che appaiono nei documenti ufficiali.", "user_account_identity_documents_list_for_particular": "Se sei un privato, i documenti obbligatori da fornire sono", "user_account_identity_documents_list_for_enterprise": "Se sei un'azienda, i documenti obbligatori da fornire sono", "user_account_identity_documents_list_for_association": "Se sei un'associazione, i documenti obbligatori da fornire sono", @@ -13,8 +12,7 @@ "user_account_identity_documents_list_doc3": "Certificato GST", "user_account_identity_documents_list_doc3_optional": "Certificato GST (facoltativo)", "user_account_identity_documents_description": "I documenti saranno conservati per cinque anni dalla fine del contratto.", - "user_account_identity_documents_selection_file_format": "Formato: jpg, jpeg, pdf, png Dimensione massima: 10 MB.", - "user_account_identity_documents_selection_file_format_invalid": "Formato di file non supportato. Utilizza uno dei formati accettati: jpg, jpeg, pdf e png", + "user_account_identity_documents_selection_file_format": "Formato: jpg, jpeg, pdf, png. La dimensione massima del file per ogni documento è 10 MB.", "user_account_identity_documents_submit": "Invia i documenti", "user_account_identity_documents_submit_success_message_title": "Grazie, abbiamo ricevuto i tuoi documenti!", "user_account_identity_documents_submit_success_message_description": "Abbiamo ricevuto tutti i documenti, che verranno verificati dai nostri team. Riceverai un'email di conferma di validazione oppure verrai contattato se avremo bisogno di maggiori informazioni.", @@ -23,5 +21,9 @@ "user_account_identity_documents_legal_info1": "OVH S.A.S è il responsabile del trattamento dei tuoi dati personali. I dati raccolti tramite questo modulo sono trattati in conformità con le Direttive sulla cybersicurezza del 28.04.2022 pubblicate dal CERT-IN ai sensi delle disposizioni della sottosezione (6) dell'articolo 70B dell’Information Technology (IT) Act, 2000.", "user_account_identity_documents_legal_info2": "Per maggiori informazioni sul trattamento dei tuoi dati personali e per conoscere i tuoi diritti, consulta la nostra Politica di utilizzo dei dati personali.", "user_account_identity_documents_verification_in_progress_info": "Il trattamento dei documenti è attualmente in fase di analisi da parte dei nostri team.", - "user_account_identity_documents_verification_waiting_info": "La tua richiesta è stata analizzata ma necessita di ulteriori documenti. Consulta il ticket di supporto." -} \ No newline at end of file + "user_account_identity_documents_verification_waiting_info": "La tua richiesta è stata analizzata ma necessita di ulteriori documenti. Consulta il ticket di supporto.", + "user_account_identity_documents_selection_file_format_invalid": "Formato di file non supportato. Utilizza uno dei formati accettati: jpg, jpeg, pdf e png", + "user_account_identity_documents_intro_ensure_correspondance": "Assicurati che i tuoi dati personali coincidano con il nome e l’indirizzo che appaiono nei documenti ufficiali.", + "user_account_identity_documents_intro_kyc_reminder": "Assicurati che i tuoi dati personali coincidano con il nome e l’indirizzo che appaiono nei documenti ufficiali.", + "user_account_identity_documents_title": "Verifica dei documenti necessaria" +} diff --git a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_pl_PL.json b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_pl_PL.json index 8b26ddc8e34b..9abf59a3b984 100644 --- a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_pl_PL.json +++ b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_pl_PL.json @@ -2,7 +2,6 @@ "user_account_identity_documents": "Moje dokumenty tożsamości", "user_account_identity_documents_sub_title": "Prześlij dokumenty", "user_account_identity_documents_intro": "Założyłaś/-eś konto i chcesz złożyć zamówienie na naszej hinduskiej stronie internetowej. Obowiązujące przepisy wymagają sprawdzenia Twojej tożsamości przed złożeniem zamówienia.", - "user_account_identity_documents_intro_kyc_reminder": "Upewnij się, że Twoje imię i nazwisko odpowiada danym osobowym podanym w Twoich oficjalnych dokumentach.", "user_account_identity_documents_list_for_particular": "Jesteś osobą prywatną, wymagane dokumenty to", "user_account_identity_documents_list_for_enterprise": "Reprezentujesz firmę, wymagane dokumenty to", "user_account_identity_documents_list_for_association": "Reprezentujesz stowarzyszenie, wymagane dokumenty to", @@ -13,8 +12,7 @@ "user_account_identity_documents_list_doc3": "Certyfikat GST", "user_account_identity_documents_list_doc3_optional": "Certyfikat GST (opcjonalnie)", "user_account_identity_documents_description": "Dokumenty będą przechowywane przez okres 5 lat od zakończenia umowy.", - "user_account_identity_documents_selection_file_format": "Format: jpg, jpeg, pdf, png Maksymalny rozmiar: 10 MB.", - "user_account_identity_documents_selection_file_format_invalid": "Nieobsługiwany format pliku. Użyj jednego z akceptowanych formatów: jpg, jpeg, pdf i png", + "user_account_identity_documents_selection_file_format": "Format: jpg, jpeg, pdf, png. Maksymalny rozmiar pliku dla każdego dokumentu to 10 MB.", "user_account_identity_documents_submit": "Wyślij dokumenty", "user_account_identity_documents_submit_success_message_title": "Dziękujemy, potwierdzamy, że otrzymaliśmy Twoje dokumenty!", "user_account_identity_documents_submit_success_message_description": "Otrzymaliśmy wszystkie Twoje dokumenty. Przekażemy je naszym zespołom do zatwierdzenia. Wyślemy do Ciebie e-mail z informacją o ich zatwierdzeniu lub skontaktujemy się z Tobą, jeśli będziemy potrzebować dodatkowych informacji.", @@ -23,5 +21,9 @@ "user_account_identity_documents_legal_info1": "Grupa OVH S.A.S jest odpowiedzialna za przetwarzanie Twoich danych osobowych. Dane gromadzone za pomocą tego formularza są przetwarzane w celu zapewnienia zgodności z Wytycznymi dotyczącymi cyberbezpieczeństwa z dnia 28.04.2022 opublikowanymi przez CERT-IN na podstawie przepisów zawartych w podsekcji 6 art. 70B ustawy o technologii informacyjnej (IT) z 2000 r.", "user_account_identity_documents_legal_info2": "Aby dowiedzieć się więcej o przetwarzaniu Twoich danych osobowych i przysługujących Ci prawach, zapoznaj się z naszą Polityką ochrony danych osobowych.", "user_account_identity_documents_verification_in_progress_info": "Twoje dokumenty są obecnie przetwarzane przez nasz zespół.", - "user_account_identity_documents_verification_waiting_info": "Twój wniosek został przeanalizowany, ale wymaga dodatkowych dokumentów. Sprawdź Twoje zgłoszenie pomocy." -} \ No newline at end of file + "user_account_identity_documents_verification_waiting_info": "Twój wniosek został przeanalizowany, ale wymaga dodatkowych dokumentów. Sprawdź Twoje zgłoszenie pomocy.", + "user_account_identity_documents_selection_file_format_invalid": "Nieobsługiwany format pliku. Użyj jednego z akceptowanych formatów: jpg, jpeg, pdf i png", + "user_account_identity_documents_intro_ensure_correspondance": "Upewnij się, że Twoje imię i nazwisko odpowiada danym osobowym podanym w Twoich oficjalnych dokumentach.", + "user_account_identity_documents_intro_kyc_reminder": "Upewnij się, że Twoje imię i nazwisko odpowiada danym osobowym podanym w Twoich oficjalnych dokumentach.", + "user_account_identity_documents_title": "Niezbędna jest weryfikacja dokumentów" +} diff --git a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_pt_PT.json b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_pt_PT.json index 97c1179ef669..c90d98ee15f7 100644 --- a/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_pt_PT.json +++ b/packages/manager/apps/dedicated/client/app/account/identity-documents/translations/Messages_pt_PT.json @@ -2,7 +2,6 @@ "user_account_identity_documents": "Documentos de identificação", "user_account_identity_documents_sub_title": "Apresente os seus documentos", "user_account_identity_documents_intro": "Criou uma conta e deseja efetuar uma encomenda a partir do nosso site indiano. A regulamentação em vigor requer uma verificação da sua identidade antes de qualquer encomenda.", - "user_account_identity_documents_intro_kyc_reminder": "Certifique-se de que os seus dados pessoais correspondem ao nome e endereço que constam nos seus documentos oficiais.", "user_account_identity_documents_list_for_particular": "É um particular. Os documentos obrigatórios a fornecer são", "user_account_identity_documents_list_for_enterprise": "É uma empresa. Os documentos obrigatórios a fornecer são", "user_account_identity_documents_list_for_association": "É uma associação. Os documentos obrigatórios a fornecer são", @@ -13,8 +12,7 @@ "user_account_identity_documents_list_doc3": "Certificado GST", "user_account_identity_documents_list_doc3_optional": "Certificado GST (facultativo)", "user_account_identity_documents_description": "Os documentos serão conservados durante cinco anos após o termo do contrato.", - "user_account_identity_documents_selection_file_format": "Formato: jpg, jpeg, pdf, png. Tamanho máximo: 10 MB.", - "user_account_identity_documents_selection_file_format_invalid": "Formato de ficheiro não suportado. Utilize um dos formatos possíveis: jpg, jpeg, pdf e png", + "user_account_identity_documents_selection_file_format": "Formato: jpg, jpeg, pdf, png. O tamanho máximo do ficheiro para cada documento é de 10 MB.", "user_account_identity_documents_submit": "Enviar os meus documentos", "user_account_identity_documents_submit_success_message_title": "Obrigado. Recebemos com êxito os seus documentos!", "user_account_identity_documents_submit_success_message_description": "Recebemos com êxito todos os seus documentos. Serão sujeitos a validação por parte das nossas equipas. Receberá por e-mail a confirmação da validação, ou será contactado caso seja necessário fornecer mais informações.", @@ -23,5 +21,9 @@ "user_account_identity_documents_legal_info1": "A OVH S.A.S é a responsável pelo tratamento dos seus dados pessoais. Os dados recolhidos através deste formulário são tratados de forma a cumprir as Diretrizes de Cibersegurança de 28/04/2022, publicadas pelo CERT-IN, em conformidade com o disposto na subsecção (6) do artigo 70B do Information Technology (IT) Act de 2000.", "user_account_identity_documents_legal_info2": "Para saber mais sobre o tratamento dos seus dados pessoais e conhecer os seus direitos, pode consultar a nossa Política de Utilização de Dados Pessoais.", "user_account_identity_documents_verification_in_progress_info": "O tratamento dos seus documentos está a ser analisado pela nossa equipa.", - "user_account_identity_documents_verification_waiting_info": "O seu pedido foi analisado, mas necessita de documentos complementares. Consulte o seu ticket de assistência." -} \ No newline at end of file + "user_account_identity_documents_verification_waiting_info": "O seu pedido foi analisado, mas necessita de documentos complementares. Consulte o seu ticket de assistência.", + "user_account_identity_documents_selection_file_format_invalid": "Formato de ficheiro não suportado. Utilize um dos formatos possíveis: jpg, jpeg, pdf e png", + "user_account_identity_documents_intro_ensure_correspondance": "Certifique-se de que os seus dados pessoais correspondem ao nome e endereço que constam nos seus documentos oficiais.", + "user_account_identity_documents_intro_kyc_reminder": "Certifique-se de que os seus dados pessoais correspondem ao nome e endereço que constam nos seus documentos oficiais.", + "user_account_identity_documents_title": "Verificação de documentos necessária" +} diff --git a/packages/manager/apps/dedicated/client/app/account/identity-documents/user-identity-documents.html b/packages/manager/apps/dedicated/client/app/account/identity-documents/user-identity-documents.html index f4f8a238c973..60ee5f3c4dbd 100644 --- a/packages/manager/apps/dedicated/client/app/account/identity-documents/user-identity-documents.html +++ b/packages/manager/apps/dedicated/client/app/account/identity-documents/user-identity-documents.html @@ -26,7 +26,7 @@

diff --git a/packages/manager/apps/dedicated/client/app/account/user/components/newAccountForm/new-account-form-component.html b/packages/manager/apps/dedicated/client/app/account/user/components/newAccountForm/new-account-form-component.html index 314ea5c43b4b..c77eb90cbcce 100644 --- a/packages/manager/apps/dedicated/client/app/account/user/components/newAccountForm/new-account-form-component.html +++ b/packages/manager/apps/dedicated/client/app/account/user/components/newAccountForm/new-account-form-component.html @@ -16,7 +16,10 @@ data-ng-submit="$ctrl.submit()" novalidate > - + diff --git a/packages/manager/apps/dedicated/client/app/account/user/components/newAccountForm/new-account-form-controller.js b/packages/manager/apps/dedicated/client/app/account/user/components/newAccountForm/new-account-form-controller.js index 4917dcac6e15..ca9d0066d046 100644 --- a/packages/manager/apps/dedicated/client/app/account/user/components/newAccountForm/new-account-form-controller.js +++ b/packages/manager/apps/dedicated/client/app/account/user/components/newAccountForm/new-account-form-controller.js @@ -344,7 +344,7 @@ export default class NewAccountFormController { tracking.accountPhoneType = this.model.phoneType; } this.atInternet.trackPage(tracking); - if (result !== 'null') { + if (result !== null) { return this.$q.reject(result); } return result; diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/dedicatedCloud-dashboard.component.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/dedicatedCloud-dashboard.component.js index 0bfc12731211..add4af22094b 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/dedicatedCloud-dashboard.component.js +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/dedicatedCloud-dashboard.component.js @@ -12,6 +12,7 @@ export default { drpGlobalStatus: '<', editDetails: '<', goToDrp: '<', + goToDatacenter: '<', goToDrpDatacenterSelection: '<', goToVpnConfiguration: '<', isDrpActionPossible: '<', diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/dedicatedCloud-dashboard.html b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/dedicatedCloud-dashboard.html index 5198c2e1eace..8c9d1a88fe74 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/dedicatedCloud-dashboard.html +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/dedicatedCloud-dashboard.html @@ -59,6 +59,7 @@ data-drp-availability="$ctrl.drpAvailability" data-drp-global-status="$ctrl.drpGlobalStatus" data-go-to-drp="$ctrl.goToDrp" + data-go-to-datacenter="$ctrl.goToDatacenter" data-go-to-drp-datacenter-selection="$ctrl.goToDrpDatacenterSelection" data-go-to-vpn-configuration="$ctrl.goToVpnConfiguration" data-is-drp-action-possible="$ctrl.isDrpActionPossible" diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/activation-status/activation-status.component.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/activation-status/activation-status.component.js index 5acf0c7f285e..1fc5f21202e6 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/activation-status/activation-status.component.js +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/activation-status/activation-status.component.js @@ -4,6 +4,7 @@ import template from './activation-status.html'; export default { bindings: { statusName: '<', + goToDatacenter: '<', datacentersState: ' diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/nsxt/nsxt.component.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/nsxt/nsxt.component.js index 4a73fcce394b..e75dd239768d 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/nsxt/nsxt.component.js +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/nsxt/nsxt.component.js @@ -4,6 +4,7 @@ import controller from './nsxt.controller'; export default { bindings: { currentService: '<', + goToDatacenter: '<', }, name: 'ovhManagerPccDashboardOptionsNsxt', template, diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/nsxt/nsxt.html b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/nsxt/nsxt.html index 746aaf0b7141..bcb3b2b9176d 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/nsxt/nsxt.html +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/components/nsxt/nsxt.html @@ -18,6 +18,7 @@ class="d-block mt-1" data-status-name=":: $ctrl.optionNsxt.state" data-datacenters-state="$ctrl.optionNsxt.datacentersState" + data-go-to-datacenter="$ctrl.goToDatacenter" > diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/options.component.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/options.component.js index 01f17aada053..ef4698356790 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/options.component.js +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/options.component.js @@ -10,7 +10,7 @@ export default { deleteDrp: '<', drpAvailability: '<', drpGlobalStatus: '<', - + goToDatacenter: '<', goToDrp: '<', goToDrpDatacenterSelection: '<', goToVpnConfiguration: '<', diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/options.html b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/options.html index 748fea3355a7..db36b5961038 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/options.html +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dashboard/tiles/options/options.html @@ -203,6 +203,7 @@ diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.component.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.component.js index e126467770be..1f9b83abb81d 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.component.js +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.component.js @@ -20,6 +20,7 @@ export default { productId: '<', serviceName: '<', setMessage: '<', + goToResizeNsxEdge: '<', }, controller, template, diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.controller.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.controller.js index 7b8b153e3c9c..dcad937f61cc 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.controller.js +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.controller.js @@ -11,21 +11,70 @@ import { DEDICATED_CLOUD_DATACENTER } from '../dedicatedCloud-datacenter.constan export default class { /* @ngInject */ - constructor($translate, DedicatedCloud, dedicatedCloudDrp) { + constructor($translate, DedicatedCloud, dedicatedCloudDrp, $q) { this.$translate = $translate; this.DedicatedCloud = DedicatedCloud; this.dedicatedCloudDrp = dedicatedCloudDrp; + this.$q = $q; this.DRP_STATUS = DEDICATEDCLOUD_DATACENTER_DRP_STATUS; this.DRP_VPN_STATUS = DEDICATEDCLOUD_DATACENTER_DRP_VPN_CONFIGURATION_STATUS; } $onInit() { - this.loading = false; - return this.checkForZertoOptionOrder(); + this.loading = true; + this.pollNsxTaskId = null; + this.$q + .all([ + this.getNsxDetails(), + this.getNsxEdgePendingTask(), + this.checkForZertoOptionOrder(), + ]) + .finally(() => { + this.loading = false; + }); + } + + $onDestroy() { + if (this.pollNsxTaskId) { + this.DedicatedCloud.stopResizeNsxTaskPoller(this.pollNsxTaskId); + } + } + + pollNsxTask(taskId) { + this.pollNsxTaskId = taskId; + this.DedicatedCloud.datacenterResizeNsxTaskPoller(this.serviceName, taskId) + .then(() => { + this.getNsxDetails(); + }) + .finally(() => { + this.pollNsxTaskId = null; + }); + } + + getNsxEdgePendingTask() { + return this.DedicatedCloud.getDatacenterPendingResizeNsxTask( + this.serviceName, + this.datacenter.model.id, + ).then((data) => { + if (data?.length > 0) { + this.pollNsxTask(data[0].taskId); + } + }); + } + + getNsxDetails() { + return this.DedicatedCloud.getDatacenterInfoNsxt( + this.serviceName, + this.datacenter.model.id, + ).then((data) => { + this.datacenter.model.edgesCount = data.length; + this.datacenter.model.edgesLevel = data[0]?.size + ? data[0].size.chatAt(0).toUpperCase() + data[0].size.slice(1) + : ''; + }); } checkForZertoOptionOrder() { - this.loading = true; return this.dedicatedCloudDrp .checkForZertoOptionOrder(this.serviceName) .then((storedDrpInformations) => { @@ -54,9 +103,6 @@ export default class { 'dedicatedCloud_datacenter_drp_get_state_error', )} ${get(error, 'data.message', error.message)}`, ); - }) - .finally(() => { - this.loading = false; }); } diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.html b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.html index 558410401737..185e48093eca 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.html +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/dedicatedCloud-datacenter-dashboard.html @@ -37,7 +37,7 @@ + + + + + + + + + + + + + + + + + + + diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.component.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.component.js new file mode 100644 index 000000000000..f3ff5443e458 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.component.js @@ -0,0 +1,20 @@ +import controller from './dedicatedCloud-datacenter-manage-nsx.controller'; +import template from './dedicatedCloud-datacenter-manage-nsx.html'; + +export default { + bindings: { + goBack: '<', + serviceName: '<', + datacenterId: '<', + setMessage: '<', + nsxEdgeCurrentLevel: '<', + nsxtEdgesScalingCapabilities: '<', + datastoreOrderLink: '<', + hostOrderLink: '<', + trackClick: '<', + trackPage: '<', + trackingPrefix: '<', + }, + controller, + template, +}; diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.constants.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.constants.js new file mode 100644 index 000000000000..7c3fc3c979cf --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.constants.js @@ -0,0 +1,30 @@ +export const TRACKING_SUFFIX = { + ADD_HOST: '::add-host', + ORDER_HOST: '::add-storage', + CONFIRM: '::confirm', + CONFIRM_SUCCESS: '::nsx-success', + CONFIRM_ERROR: '::nsx-error', +}; + +export const NSX_RESOURCES = { + MEDIUM: { + cpu: 4, + storage: 200, + ram: 8, + }, + LARGE: { + cpu: 8, + storage: 200, + ram: 32, + }, + XLARGE: { + cpu: 16, + storage: 200, + ram: 32, + }, +}; + +export default { + TRACKING_SUFFIX, + NSX_RESOURCES, +}; diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.controller.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.controller.js new file mode 100644 index 000000000000..16a440cbedd5 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.controller.js @@ -0,0 +1,57 @@ +import { + NSX_RESOURCES, + TRACKING_SUFFIX, +} from './dedicatedCloud-datacenter-manage-nsx.constants'; +import { EDGES_SIZES } from '../../../datacenters/datacenter.constants'; + +export default class { + /* @ngInject */ + constructor(DedicatedCloud, $translate, coreURLBuilder) { + this.DedicatedCloud = DedicatedCloud; + this.$translate = $translate; + this.coreURLBuilder = coreURLBuilder; + this.NSX_RESOURCES = NSX_RESOURCES; + this.TRACKING_SUFFIX = TRACKING_SUFFIX; + } + + $onInit() { + this.loading = false; + this.nsxSizes = Object.keys(EDGES_SIZES); + this.selectedNsxLevel = null; + this.hasScalingCapabilities = + this.nsxtEdgesScalingCapabilities.length === + Object.keys(EDGES_SIZES).length; + } + + isSizeAvailable(size) { + return this.nsxtEdgesScalingCapabilities.indexOf(size) > -1; + } + + changeNsxSize() { + this.trackClick(this.TRACKING_SUFFIX.CONFIRM); + this.loading = true; + this.DedicatedCloud.resizeNsxtEdgeCluster( + this.serviceName, + this.datacenterId, + this.selectedNsxLevel, + ) + .then(() => { + this.trackPage(this.TRACKING_SUFFIX.CONFIRM_SUCCESS); + this.goBack( + this.$translate.instant('dedicatedCloud_manage_nsx_edge_success'), + ); + }) + .catch(() => { + this.setMessage( + `${this.$translate.instant( + 'dedicatedCloud_datacenter_nsx_resize_error', + )}`, + 'danger', + ); + this.trackPage(this.TRACKING_SUFFIX.CONFIRM_ERROR); + }) + .finally(() => { + this.loading = false; + }); + } +} diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.html b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.html new file mode 100644 index 000000000000..261963f27ff2 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.html @@ -0,0 +1,104 @@ + + + + + + + + + + + + + + + + + + +

+ +
+ +
+
+ + +
+ +
+ +
+
+ +
+ +
+ +
+
+
+
+
+ +
+ + + + + + +
diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/index.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/index.js new file mode 100644 index 000000000000..4fab07e2110d --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges/index.js @@ -0,0 +1,20 @@ +import angular from 'angular'; + +import 'angular-translate'; +import '@ovh-ux/ui-kit'; +import '@ovh-ux/ng-translate-async-loader'; + +import component from './dedicatedCloud-datacenter-manage-nsx.component'; + +const moduleName = 'ovhManagerDedicatedCloudDatacenterManageNsxEdgeComponent'; + +angular + .module(moduleName, [ + 'ngTranslateAsyncLoader', + 'oui', + 'pascalprecht.translate', + ]) + .component('ovhManagerDedicatedCloudDatacenterManageNsxEdges', component) + .run(/* @ngTranslationsInject:json ./translations */); + +export default moduleName; diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/translations/Messages_fr_FR.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/translations/Messages_fr_FR.json index b42660fa5d8f..9adb317e8b75 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/translations/Messages_fr_FR.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dashboard/translations/Messages_fr_FR.json @@ -1,6 +1,29 @@ { "dedicatedCloud_information_title": "Informations générales", "dedicatedCloud_options_title": "Options", + "dedicatedCloud_nsx_edge_title": "NSX Edges", + "dedicatedCloud_nsx_edge_level": "Taille Edge NSX", + "dedicatedCloud_nsx_edge_quantity": "Nombre de Edge NSX", + "dedicatedCloud_nsx_edge_current_level": "Niveau actuel", + "dedicatedCloud_nsx_link_datastore_order": "Ajouter du stockage", + "dedicatedCloud_nsx_link_hosts_order": "Ajouter des hosts", + "dedicatedCloud_manage_nsx_edge_title": "Modifier les noeuds NSX Edge", + "dedicatedCloud_manage_nsx_edge_require_per_node_MEDIUM": "Medium - Taille du dispositif par nœud", + "dedicatedCloud_manage_nsx_edge_require_per_node_LARGE": "Large - Taille du dispositif par nœud", + "dedicatedCloud_manage_nsx_edge_require_per_node_XLARGE": "Extra-large - Taille du dispositif par nœud", + "dedicatedCloud_manage_nsx_edge_current_level": "Niveau actuel de NSX Edge", + "dedicatedCloud_manage_nsx_edge_success": "Votre niveau de NSX Edge a bien été modifié", + "dedicatedCloud_manage_nsx_missing_ressources": "Si une option est grisée, cela signifie que vous ne disposez pas des ressources nécessaires au sein de votre DataCentre Virtuel. Vous devez avoir les ressources CPU, mémoire et disque suffisantes pour le changement de taille de vos NSX Edge.", + "dedicatedCloud_manage_nsx_choice_title_MEDIUM": "NSX Edge moyen", + "dedicatedCloud_manage_nsx_choice_description_MEDIUM": "Convient lorsque seules les fonctionnalités L2 à L4 telles que NAT, le routage, le pare-feu L4, l'équilibreur de charge L4 sont requises et que le débit total est inférieur à 2 Gbits/s.", + "dedicatedCloud_manage_nsx_choice_footer": "{{cpu}} vCPU - {{ram}}Go RAM - {{storage}} Go", + "dedicatedCloud_manage_nsx_choice_title_LARGE": "NSX Edge large", + "dedicatedCloud_manage_nsx_choice_description_LARGE": "Convient lorsque seules les fonctionnalités L2 à L4 telles que NAT, le routage, le pare-feu L4, l'équilibreur de charge L4 sont requises et que le débit total est de 2 à 10 Gbits/s. Il est également approprié lorsque l'équilibreur de charge L7 (par exemple, le déchargement SSL) est requis.", + "dedicatedCloud_manage_nsx_choice_title_XLARGE": "NSX Edge extra-large", + "dedicatedCloud_manage_nsx_choice_description_XLARGE": "Utilisez le format très grand si vous souhaitez configurer un grand nombre d'homologues BGP avec le nœud Edge. Convient lorsque le débit total requis est de plusieurs Gbits/s pour l'équilibreur de charge L7 et le VPN.", + "dedicatedCloud_nsx_task_progress": "En cours", + "dedicatedCloud_datacenter_nsx_resize_error": "Une erreur est survenue", + "dedicatedCloud_tab_datacenter_global_information": "Par défaut, tous virtuels data centers(VDC) NSX disposent d'un cluster NSX Edge composé de 2 NSX Edge. Vous avez ensuite la possibilité de modifier la taille des Edges, vous devez disposer de ressources nécessaires pour modifier la taille ou le nombre des Edges.", "dedicatedCloud_description": "Nom", "dedicatedCloud_datacenter_delete": "Supprimer le datacentre", "dedicatedCloud_datacenter_description": "Description", diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dedicatedCloud-datacenter.html b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dedicatedCloud-datacenter.html index 4ae5edbc9c67..a00a3130ced7 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dedicatedCloud-datacenter.html +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/dedicatedCloud-datacenter.html @@ -21,28 +21,6 @@ > - -
-

- - -
diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_de_DE.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_de_DE.json index 799a23064a82..bc0ec773a607 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_de_DE.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_de_DE.json @@ -8,5 +8,6 @@ "dedicatedCloud_tab_drp": "Disaster Recovery Plan (DRP)", "dedicatedCloud_datacenter_EOL_title": "Ablaufdatum der Dedicated Cloud: 30. September 2022", "dedicatedCloud_datacenter_EOL_part_1": "Im Oktober 2021 hatten wir bereits angekündigt, dass unsere Angebote der Art Dedicated Cloud auslaufen und am 30. September 2022 endgültig eingestellt werden. Dieser Schritt ist im Hinblick auf Ihre VMware-Plattformen von Bedeutung, da damit eine Verbesserung der Dienstqualität, der Performance und der Sicherheit Ihrer Cluster einhergeht. Die Hardware, die vor 2018 für die Angebote vom Typ „Dedicated Cloud“ verwendet wurde, ist nicht dazu geeignet, den höchsten Service-Level nach heutigem Stand zu gewährleisten. Außerdem ist keine Integration mit den neuen VMware-Architekturen möglich.", - "dedicatedCloud_datacenter_EOL_part_2": "Zahlreiche Kunden haben diese Migration bereits geplant und begonnen. Wir möchten dies nun auch Ihnen noch vor dem Stichtag am 30. September 2022 empfehlen." + "dedicatedCloud_datacenter_EOL_part_2": "Zahlreiche Kunden haben diese Migration bereits geplant und begonnen. Wir möchten dies nun auch Ihnen noch vor dem Stichtag am 30. September 2022 empfehlen.", + "dedicatedCloud_datacenter_resize": "Größe ändern" } diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_en_GB.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_en_GB.json index 35d191074753..2f48ef49cf2e 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_en_GB.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_en_GB.json @@ -8,5 +8,6 @@ "dedicatedCloud_tab_drp": "Disaster Recovery Plan (DRP)", "dedicatedCloud_datacenter_EOL_title": "Dedicated Cloud end-of-life date: 30 September 2022", "dedicatedCloud_datacenter_EOL_part_1": "As per our announcement in October 2021, our Dedicated Cloud solutions were reaching the end of their lifecycle, and will be permanently discontinued on 30 September 2022. This step is significant for your VMware platforms as it will improve service quality, performance and security for your clusters. The hardware used for the Dedicated Cloud solutions before 2018 no longer enables us to ensure an optimal service level and integration with new modern VMware architectures.", - "dedicatedCloud_datacenter_EOL_part_2": "Following our previous communications, many customers have started this scheduling and migration process. We encourage you to do the same, so that you are fully prepared before the 30 September 2022 deadline." + "dedicatedCloud_datacenter_EOL_part_2": "Following our previous communications, many customers have started this scheduling and migration process. We encourage you to do the same, so that you are fully prepared before the 30 September 2022 deadline.", + "dedicatedCloud_datacenter_resize": "Resize" } diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_es_ES.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_es_ES.json index e1e72443e475..b24ad705f28f 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_es_ES.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_es_ES.json @@ -8,5 +8,6 @@ "dedicatedCloud_tab_drp": "Plan de recuperación ante desastres (DRP)", "dedicatedCloud_datacenter_EOL_title": "Final del ciclo de vida de la solución Dedicated Cloud: 30 de septiembre de 2022", "dedicatedCloud_datacenter_EOL_part_1": "Como ya anunciamos en octubre de 2021, la solución Dedicated Cloud se acerca al final de su ciclo de vida, por lo que este servicio dejará de estar disponible definitivamente el próximo 30 de septiembre de 2022. Este paso es importante para sus plataformas VMware, ya que permitirá mejorar la calidad del servicio, el rendimiento y la seguridad de sus clusters. Y es que el hardware utilizado en las soluciones Dedicated Cloud, anterior a 2018, ya no nos permite garantizar el mejor nivel de servicio ni la integración de la solución en las arquitecturas modernas de VMware.", - "dedicatedCloud_datacenter_EOL_part_2": "Tras la recepción de nuestras anteriores comunicaciones, muchos de nuestros clientes ya han comenzado a planificar la migración de sus servicios. Así pues, le recomendamos que programe esta operación antes del final del ciclo de vida de la solución el próximo 30 de septiembre de 2022." + "dedicatedCloud_datacenter_EOL_part_2": "Tras la recepción de nuestras anteriores comunicaciones, muchos de nuestros clientes ya han comenzado a planificar la migración de sus servicios. Así pues, le recomendamos que programe esta operación antes del final del ciclo de vida de la solución el próximo 30 de septiembre de 2022.", + "dedicatedCloud_datacenter_resize": "Redimensionar" } diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_fr_CA.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_fr_CA.json index 8ac313d933f2..92fe74508c3b 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_fr_CA.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_fr_CA.json @@ -1,6 +1,7 @@ { "dedicatedCloud_datacenter_no_name": "Datacenter {{t0}}", "dedicatedCloud_datacenter_no_description": "Ajouter une description", + "dedicatedCloud_datacenter_resize": "Redimensionner", "dedicatedCloud_tab_dashboard": "Informations générales", "dedicatedCloud_tab_host": "Hosts", "dedicatedCloud_tab_datastore": "Datastores", diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_fr_FR.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_fr_FR.json index 8ac313d933f2..92fe74508c3b 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_fr_FR.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_fr_FR.json @@ -1,6 +1,7 @@ { "dedicatedCloud_datacenter_no_name": "Datacenter {{t0}}", "dedicatedCloud_datacenter_no_description": "Ajouter une description", + "dedicatedCloud_datacenter_resize": "Redimensionner", "dedicatedCloud_tab_dashboard": "Informations générales", "dedicatedCloud_tab_host": "Hosts", "dedicatedCloud_tab_datastore": "Datastores", diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_it_IT.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_it_IT.json index 1746bd33ed07..a049ae3e4310 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_it_IT.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_it_IT.json @@ -8,5 +8,6 @@ "dedicatedCloud_tab_drp": "Disaster Recovery Plan (DRP)", "dedicatedCloud_datacenter_EOL_title": "Data di fine del ciclo di vita del Dedicated Cloud: 30 settembre 2022", "dedicatedCloud_datacenter_EOL_part_1": "Nell'ottobre 2021 abbiamo annunciato che la nostra soluzione Dedicated Cloud è ormai giunta alla fine del proprio ciclo di vita e sarà definitivamente disattivata il 30 settembre 2022. Questo è uno step importante per le piattaforme VMware e consentirà di migliorare la qualità del servizio, le performance e la sicurezza dei cluster. L’hardware utilizzato per le soluzioni \"Dedicated Cloud\", infatti, è anteriore al 2018 e non ci permette più di garantire il miglior livello di servizio e l'integrazione con le nuove architetture di VMware.", - "dedicatedCloud_datacenter_EOL_part_2": "In seguito alle nostre comunicazioni molti utenti hanno iniziato a pianificare la migrazione. Ti consigliamo di programmare l’operazione con anticipo ed evitare così la data limite del 30 settembre 2022." + "dedicatedCloud_datacenter_EOL_part_2": "In seguito alle nostre comunicazioni molti utenti hanno iniziato a pianificare la migrazione. Ti consigliamo di programmare l’operazione con anticipo ed evitare così la data limite del 30 settembre 2022.", + "dedicatedCloud_datacenter_resize": "Ridimensionare" } diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_pl_PL.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_pl_PL.json index 113febf29562..f266815fcad5 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_pl_PL.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_pl_PL.json @@ -8,5 +8,6 @@ "dedicatedCloud_tab_drp": "Plan Disaster Recovery (DRP)", "dedicatedCloud_datacenter_EOL_title": "Data wygaśnięcia Dedicated Cloud: 30 września 2022", "dedicatedCloud_datacenter_EOL_part_1": "W październiku 2021 roku poinformowaliśmy, że nasza oferta Dedicated Cloud dobiega końca i zostanie definitywnie wycofana z użytku 30 września 2022 roku. Krok ten jest ważny dla platform VMware, ponieważ pozwala zwiększyć jakość usługi, wydajność i bezpieczeństwo klastrów. Sprzęt (sprzed 2018 r.) wykorzystywany w ofercie „Dedicated Cloud” nie pozwala nam już zagwarantować najwyższego poziomu usług i zintegrować go z nowoczesnymi architekturami VMware.", - "dedicatedCloud_datacenter_EOL_part_2": "Po naszych wcześniejszych komunikatach wielu klientów rozpoczęło już planowanie i migrację. Zachęcamy do zrobienia tego samego, zanim upłynie ostateczny termin 30 września 2022 r." + "dedicatedCloud_datacenter_EOL_part_2": "Po naszych wcześniejszych komunikatach wielu klientów rozpoczęło już planowanie i migrację. Zachęcamy do zrobienia tego samego, zanim upłynie ostateczny termin 30 września 2022 r.", + "dedicatedCloud_datacenter_resize": "Skaluj" } diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_pt_PT.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_pt_PT.json index f5305e3cf091..4444a2a4a6e0 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_pt_PT.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenter/translations/Messages_pt_PT.json @@ -8,5 +8,6 @@ "dedicatedCloud_tab_drp": "Plano de recuperação de desastres (DRP)", "dedicatedCloud_datacenter_EOL_title": "Data de fim de vida do Dedicated Cloud: 30 de setembro de 2022", "dedicatedCloud_datacenter_EOL_part_1": "Em outubro de 2021, informámos que as nossas ofertas Dedicated Cloud serão descontinuadas e definitivamente encerradas a 30 de setembro de 2022. Esta etapa é importante para as suas plataformas VMware de forma a melhorar a qualidade do serviço, o desempenho e a segurança dos seus clusters. O hardware das ofertas \"Dedicated Cloud\" utilizado, antes de 2018, já não nos permite assegurar o melhor nível de serviço e a integração com as novas arquiteturas modernas da VMware.", - "dedicatedCloud_datacenter_EOL_part_2": "Na sequência das nossas comunicações anteriores, muitos clientes iniciaram este planeamento e migração, pelo que lhe pedimos que faça o mesmo para evitar esta data-limite de 30 de setembro de 2022." + "dedicatedCloud_datacenter_EOL_part_2": "Na sequência das nossas comunicações anteriores, muitos clientes iniciaram este planeamento e migração, pelo que lhe pedimos que faça o mesmo para evitar esta data-limite de 30 de setembro de 2022.", + "dedicatedCloud_datacenter_resize": "Redimensionar" } diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenter.constants.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenter.constants.js index d5011f359e54..3eb8e4f6478a 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenter.constants.js +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenter.constants.js @@ -1,3 +1,9 @@ +export const EDGES_SIZES = { + MEDIUM: 'M', + LARGE: 'L', + XLARGE: 'XL', +}; + export const REGEX_LEGACY_DATACENTER = /^PREMIER|SDDC/; export const REGEX_EXCLUDE_LEGACY_DATACENTER = /^ESSENTIALS/; @@ -50,6 +56,7 @@ export const MIGRATION_GUIDE = { }; export default { + EDGES_SIZES, REGEX_LEGACY_DATACENTER, REGEX_EXCLUDE_LEGACY_DATACENTER, MIGRATION_GUIDE, diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenters.controller.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenters.controller.js index 903b7f4e86bd..092f9b951843 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenters.controller.js +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenters.controller.js @@ -3,6 +3,7 @@ import { REGEX_LEGACY_DATACENTER, REGEX_EXCLUDE_LEGACY_DATACENTER, MIGRATION_GUIDE, + EDGES_SIZES, } from './datacenter.constants'; export default class { @@ -31,6 +32,16 @@ export default class { return this.addDatacenter(); } + loadDataCenterDetails(id) { + return this.DedicatedCloud.getDatacenterInfoNsxt( + this.dedicatedCloud.serviceName, + id, + ).then((data) => ({ + edgesCount: data.length, + clusterSize: data[0]?.size ? EDGES_SIZES[data[0].size] : '', + })); + } + loadDatacenters({ offset, pageSize }) { return this.DedicatedCloud.getDatacentersInformations( this.dedicatedCloud.serviceName, diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenters.html b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenters.html index 59b6b064b6b4..ba6a88c600ae 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenters.html +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/datacenters.html @@ -18,7 +18,10 @@

data-translate-values="{ href: $ctrl.migrationGuideUrl }" >

- + @@ -72,6 +75,16 @@

>
+ + + + + + in unseren Migrationsanleitungen." -} \ No newline at end of file + "dedicatedCloud_datacenters_migration_banner_first": "Ende der Lebensdauer der VMware NSX-V-Komponente am 15. Januar 2024: Informationen zur Migration finden Sie in der E-Mail vom Juli/August 2023. Weitere technische Informationen finden Sie in unseren Leitfäden.", + "dedicatedCloud_datacenters_migration_banner_second": "Die VMware NSX-V-Komponente WIRD am 15. Januar 2024 DEAKTIVIERT. Weitere Informationen finden Sie in unseren Migrationsleitfäden.", + "dedicatedCloud_datacenters_migration_banner": "End-of-Life der VMware NSX-V-Komponente: Weitere Informationen finden Sie in unseren Migrationsanleitungen.", + "dedicatedCloud_datacenters_cluster": "Cluster-Größe", + "dedicatedCloud_datacenters_edges": "Anzahl der NSX Edges" +} diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_en_GB.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_en_GB.json index 8c43c5227815..d12f00caed66 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_en_GB.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_en_GB.json @@ -82,5 +82,9 @@ "dedicatedCloud_datacenters_commercial_name_NSX-T-DEFAULT": "NSX", "dedicatedCloud_datacenters_commercial_name_NSX-T-WITHOUT-NSX": "NSX", "dedicatedCloud_datacenters_commercial_name_NSX-T-VROPS-WITHOUT-NSX": "NSX with vROps", - "dedicatedCloud_datacenters_migration_banner": "End of Life for VMware NSX-V component: please refer to our migration guides for more information." -} \ No newline at end of file + "dedicatedCloud_datacenters_migration_banner_first": "End of life for the VMware NSX-V component as of 15 January 2024: please refer to the email sent in July/August 2023 for migration options. For technical information, please refer to our guides.", + "dedicatedCloud_datacenters_migration_banner_second": "IMMINENT DEACTIVATION of the VMware NSX-V component effective 15 January 15 2024. Please refer to our migration guides for more information.", + "dedicatedCloud_datacenters_migration_banner": "End of Life for VMware NSX-V component: please refer to our migration guides for more information.", + "dedicatedCloud_datacenters_cluster": "Cluster size", + "dedicatedCloud_datacenters_edges": "Number of NSX Edges" +} diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_es_ES.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_es_ES.json index 9f4c7e787e6d..8290afeb9eaa 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_es_ES.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_es_ES.json @@ -82,5 +82,9 @@ "dedicatedCloud_datacenters_commercial_name_NSX-T-DEFAULT": "NSX", "dedicatedCloud_datacenters_commercial_name_NSX-T-WITHOUT-NSX": "NSX", "dedicatedCloud_datacenters_commercial_name_NSX-T-VROPS-WITHOUT-NSX": "NSX con vROps", - "dedicatedCloud_datacenters_migration_banner": "Final de vida útil del componente VMware NSX-V: consulte nuestras guías de migración para más información." + "dedicatedCloud_datacenters_migration_banner_first": "Final de vida útil del componente VMware NSX-V el día 15 de enero de 2024: consulte el email que le enviamos en julio/agosto de 2023 para conocer las modalidades de migración. Para más información, consulte nuestras guías.", + "dedicatedCloud_datacenters_migration_banner_second": "DESACTIVACIÓN INMINENTE del componente VMware NSX-V a partir del 15 de enero de 2024. Para más información, consulte nuestras guías de migración.", + "dedicatedCloud_datacenters_migration_banner": "Final de vida útil del componente VMware NSX-V: consulte nuestras guías de migración para más información.", + "dedicatedCloud_datacenters_cluster": "Tamaño del clúster", + "dedicatedCloud_datacenters_edges": "Número de NSX Edges" } diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_fr_CA.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_fr_CA.json index 4b9fefe4b479..90239461cdb7 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_fr_CA.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_fr_CA.json @@ -5,6 +5,8 @@ "dedicatedCloud_datacenters_cpu": "Total CPU", "dedicatedCloud_datacenters_ram": "Total RAM", "dedicatedCloud_datacenters_disk": "Total espace disque", + "dedicatedCloud_datacenters_cluster": "Taille du cluster", + "dedicatedCloud_datacenters_edges": "Nombre de NSX Edges", "dedicatedCloud_datacenters_order_host": "Commander un Host", "dedicatedCloud_datacenters_order_datastore": "Commander un Datastore", "dedicatedCloud_datacenters_loading_error": "Une erreur est survenue lors du chargement des informations des datacentres.", diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_fr_FR.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_fr_FR.json index 4b9fefe4b479..90239461cdb7 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_fr_FR.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_fr_FR.json @@ -5,6 +5,8 @@ "dedicatedCloud_datacenters_cpu": "Total CPU", "dedicatedCloud_datacenters_ram": "Total RAM", "dedicatedCloud_datacenters_disk": "Total espace disque", + "dedicatedCloud_datacenters_cluster": "Taille du cluster", + "dedicatedCloud_datacenters_edges": "Nombre de NSX Edges", "dedicatedCloud_datacenters_order_host": "Commander un Host", "dedicatedCloud_datacenters_order_datastore": "Commander un Datastore", "dedicatedCloud_datacenters_loading_error": "Une erreur est survenue lors du chargement des informations des datacentres.", diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_it_IT.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_it_IT.json index 5b652934acee..1c3481c56f0d 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_it_IT.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_it_IT.json @@ -82,5 +82,9 @@ "dedicatedCloud_datacenters_commercial_name_NSX-T-DEFAULT": "NSX", "dedicatedCloud_datacenters_commercial_name_NSX-T-WITHOUT-NSX": "NSX", "dedicatedCloud_datacenters_commercial_name_NSX-T-VROPS-WITHOUT-NSX": "NSX con vROps", - "dedicatedCloud_datacenters_migration_banner": "Fine del ciclo di vita del componente VMware NSX-V: consulta le nostre guide sulla migrazione per maggiori informazioni." + "dedicatedCloud_datacenters_migration_banner_first": "Fine del ciclo di vita del componente VMware NSX-V il 15 gennaio 2024: per conoscere le modalità di migrazione, fai riferimento all'email ricevuta a luglio/agosto 2023. Per maggiori dettagli di carattere tecnico, consulta le nostre guide.", + "dedicatedCloud_datacenters_migration_banner_second": "DISATTIVAZIONE IMMINENTE del componente VMware NSX-V a partire dal 15 gennaio 2024. Per maggiori informazioni, consulta le nostre guide sulla migrazione.", + "dedicatedCloud_datacenters_migration_banner": "Fine del ciclo di vita del componente VMware NSX-V: consulta le nostre guide sulla migrazione per maggiori informazioni.", + "dedicatedCloud_datacenters_cluster": "Dimensione del cluster", + "dedicatedCloud_datacenters_edges": "Numero di NSX Edges" } diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_pl_PL.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_pl_PL.json index cf65481f8b4a..66d37439415d 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_pl_PL.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_pl_PL.json @@ -82,5 +82,9 @@ "dedicatedCloud_datacenters_commercial_name_NSX-T-DEFAULT": "NSX", "dedicatedCloud_datacenters_commercial_name_NSX-T-WITHOUT-NSX": "NSX", "dedicatedCloud_datacenters_commercial_name_NSX-T-VROPS-WITHOUT-NSX": "NSX z vROps", - "dedicatedCloud_datacenters_migration_banner": "Wycofujemy komponent VMware NSX-V: więcej informacji znajdziesz w przewodnikach dotyczących migracji." + "dedicatedCloud_datacenters_migration_banner_first": "Koniec okresu eksploatacji komponentu VMware NSX-V w dniu 15 stycznia 2024 r.: szczegółowe informacje na temat migracji znajdziesz w wiadomości e-mail wysłanej w lipcu/sierpniu 2023 r. Więcej informacji technicznych znajdziesz w naszych przewodnikach.", + "dedicatedCloud_datacenters_migration_banner_second": "Od 15 stycznia 2024 DEZAKTYWACJA komponentu VMware NSX-V. Więcej informacji znajdziesz w przewodnikach dotyczących migracji.", + "dedicatedCloud_datacenters_migration_banner": "Wycofujemy komponent VMware NSX-V: więcej informacji znajdziesz w przewodnikach dotyczących migracji.", + "dedicatedCloud_datacenters_cluster": "Rozmiar klastra", + "dedicatedCloud_datacenters_edges": "Liczba NSX Edges" } diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_pt_PT.json b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_pt_PT.json index 4be4a868fd4a..f4bb0d995544 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_pt_PT.json +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/datacenters/translations/Messages_pt_PT.json @@ -82,5 +82,8 @@ "dedicatedCloud_datacenters_commercial_name_NSX-T-DEFAULT": "NSX", "dedicatedCloud_datacenters_commercial_name_NSX-T-WITHOUT-NSX": "NSX", "dedicatedCloud_datacenters_commercial_name_NSX-T-VROPS-WITHOUT-NSX": "NSX com vROps", - "dedicatedCloud_datacenters_migration_banner": "Descontinuação do componente VMware NSX-V: para mais informações, consulte os nossos guias sobre migração." -} \ No newline at end of file + "dedicatedCloud_datacenters_migration_banner_first": "Fim de vida do componente VMware NSX-V a 15 de janeiro de 2024: consulte o e-mail enviado em julho/agosto de 2023 para conhecer as modalidades de migração. Para mais pormenores técnicos, consulte os nossos manuais.", + "dedicatedCloud_datacenters_migration_banner_second": "DESATIVAÇÃO IMINENTE do componente VMware NSX-V, a 15 de janeiro de 2024. Consulte os nossos manuais de migração para obter mais informações.", + "dedicatedCloud_datacenters_cluster": "Tamanho do cluster", + "dedicatedCloud_datacenters_edges": "Número de NSX Edges" +} diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dedicatedCloud.constant.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dedicatedCloud.constant.js index f7617adc9d55..517163d264df 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dedicatedCloud.constant.js +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dedicatedCloud.constant.js @@ -3,9 +3,16 @@ export const DEDICATED_CLOUD_CONSTANTS = { pccNewGeneration: '2.0', }; +export const TASK_STATUS = { + DONE: 'done', + ERROR: 'error', + CANCELED: 'canceled', +}; + export const UNAVAILABLE_PCC_CODE = [400, 404]; export default { DEDICATED_CLOUD_CONSTANTS, UNAVAILABLE_PCC_CODE, + TASK_STATUS, }; diff --git a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dedicatedCloud.service.js b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dedicatedCloud.service.js index 54ec962696b4..40fbe8121e4e 100644 --- a/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dedicatedCloud.service.js +++ b/packages/manager/apps/dedicated/client/app/components/dedicated-cloud/dedicatedCloud.service.js @@ -15,6 +15,7 @@ import toNumber from 'lodash/toNumber'; import { DEDICATED_CLOUD_CONSTANTS, UNAVAILABLE_PCC_CODE, + TASK_STATUS, } from './dedicatedCloud.constant'; import { VM_ENCRYPTION_KMS } from './security/dedicatedCloud-security.constants'; @@ -331,6 +332,56 @@ class DedicatedCloudService { ); } + getDatacenterInfoNsxt(serviceName, datacenterId, params = {}) { + return this.icebergQuery( + `/dedicatedCloud/${serviceName}/datacenter/${datacenterId}/nsxtEdge`, + params, + ).then(({ data }) => data.filter((item) => item !== null)); + } + + getDatacenterPendingResizeNsxTask(serviceName, datacenterId, params = {}) { + return this.icebergQuery( + `/dedicatedCloud/${serviceName}/datacenter/${datacenterId}/task`, + params, + { + name: 'resizeNsxtEdgeCluster', + }, + ).then(({ data }) => + data.filter((item) => item.state !== TASK_STATUS.DONE), + ); + } + + datacenterResizeNsxTaskPoller(serviceName, taskId) { + return this.Poller.poll( + `/dedicatedCloud/${serviceName}/task/${taskId}`, + null, + { + method: 'get', + namespace: taskId, + interval: 3000, + successRule: (taskResult) => taskResult.state === TASK_STATUS.DONE, + errorRule: (taskResult) => taskResult.state === TASK_STATUS.ERROR, + }, + ); + } + + stopResizeNsxTaskPoller(taskId) { + return this.Poller.kill({ namespace: taskId }); + } + + getDatacenterNsxtEdgesScalingCapabilities(serviceName, datacenterId) { + return this.$http.get( + `/dedicatedCloud/${serviceName}/datacenter/${datacenterId}/nsxtEdgesResizingCapabilities`, + ); + } + + resizeNsxtEdgeCluster(serviceName, datacenterId, size) { + this.$http.post( + `/dedicatedCloud/${serviceName}/datacenter/${datacenterId}/resizeNsxtEdgeCluster`, + { size }, + ); + } + getDatacenterInformations(serviceName, datacenterId, forceRefresh) { return this.OvhHttp.get( '/sws/dedicatedCloud/{serviceName}/datacenters/{datacenterId}', @@ -593,7 +644,7 @@ class DedicatedCloudService { ); } - icebergQuery(url, params) { + icebergQuery(url, params, urlParams = {}) { const { filters, pageSize, @@ -603,7 +654,7 @@ class DedicatedCloudService { defaultFilterColumn, } = params; - let request = this.iceberg(url) + let request = this.iceberg(url, urlParams) .query() .expand('CachedObjectList-Pages') .limit(pageSize) @@ -732,8 +783,8 @@ class DedicatedCloudService { namespace: 'dedicatedCloud.password.update.poll', task, user, - successSates: ['canceled', 'done'], - errorsSates: ['error'], + successSates: [TASK_STATUS.CANCELED, TASK_STATUS.DONE], + errorsSates: [TASK_STATUS.ERROR], }); }); } @@ -1018,8 +1069,8 @@ class DedicatedCloudService { namespace: 'dedicatedCloud.user.update.poll', task, user, - successSates: ['canceled', 'done'], - errorsSates: ['error'], + successSates: [TASK_STATUS.CANCELED, TASK_STATUS.DONE], + errorsSates: [TASK_STATUS.ERROR], }); }); } @@ -1455,19 +1506,19 @@ class DedicatedCloudService { ['apiv6/dedicatedCloud', opts.serviceName, 'task', taskId].join('/'), null, { - successRule: { state: 'done' }, + successRule: { state: TASK_STATUS.DONE }, namespace: 'dedicatedCloud.request', }, ).then( (task) => { this.$rootScope.$broadcast( - ['dedicatedCloud', opts.namespace, 'done'].join('.'), + ['dedicatedCloud', opts.namespace, TASK_STATUS.DONE].join('.'), task, ); }, (err) => { this.$rootScope.$broadcast( - ['dedicatedCloud', opts.namespace, 'error'].join('.'), + ['dedicatedCloud', opts.namespace, TASK_STATUS.ERROR].join('.'), err, ); }, diff --git a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_de_DE.json b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_de_DE.json index b76a5ebb23cc..44b9c617d18e 100644 --- a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_de_DE.json +++ b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_de_DE.json @@ -331,8 +331,6 @@ "server_configuration_installation_title": "Installation des Servers", "server_configuration_installation_info": "Sie sind im Begriff, ein Betriebssystem auf dem Server {{t0}} zu installieren. Wählen Sie den gewünschten Installationstyp aus:", "server_configuration_installation_warning": "Achtung: Bei der Installation werden alle Festplatten gelöscht", - "server_configuration_installation_custom_image_info": "Auf dem nächsten Bildschirm können Sie ein Betriebssystem von einem personalisierten Image aus installieren, indem Sie in „{{t1}}“ die Option „{{t0}}“ auswählen.", - "server_configuration_installation_custom_image_help_link": "Wählen Sie den am besten geeigneten individuellen Installationstyp aus.", "server_configuration_installation_32": "32 Bit", "server_configuration_installation_64": "64 Bit", "server_configuration_installation_deprecated": "Deprecated", @@ -349,7 +347,6 @@ "server_configuration_installation_ZFS": "ZFS", "server_configuration_installation_REISERFS": "ReiserFS", "server_configuration_installation_SWAP": "Swap", - "server_configuration_installation_NONE": "Keine", "server_configuration_installation_UFS": "UFS", "server_configuration_installation_LOGICAL": "logical", "server_configuration_installation_LV": "lv", @@ -376,23 +373,10 @@ "server_configuration_installation_form_ssh_no": "Ohne SSH-Schlüssel", "server_configuration_installation_form_ssh_help": "Fügen Sie im Bereich „Mein Account“ einen Schlüssel hinzu", "server_configuration_installation_form_nbdisk": "Anzahl partitionierter Festplatten:", - "server_configuration_installation_inputs_title": "Spezifische Optionen:", - "server_configuration_installation_inputs_info": "Die unten stehenden Fragen beziehen sich speziell auf das ausgewählte Betriebssystem ({{t0}}). Zwecks Konsistenz mit der API sind sie nur auf Englisch verfasst.", - "server_configuration_installation_inputs_item_placeholder": "Wert vom Typ {{t0}} einfügen", - "server_configuration_installation_inputs_item_placeholder_example": "Zum Beispiel: {{t0}}", - "server_configuration_installation_inputs_item_mandatory": "Dieses Feld ist ein Pflichtfeld.", - "server_configuration_installation_inputs_bad_email": "Die eingegebene E-Mail-Adresse ist ungültig.", - "server_configuration_installation_inputs_bad_hexstring": "Die Zeichenfolge darf nur aus Zahlen und Buchstaben zwischen A und F bestehen.", - "server_configuration_installation_inputs_bad_ip": "Die eingegebene IPv4-Adresse ist ungültig.", - "server_configuration_installation_inputs_bad_required": "Dieses Feld muss ausgefüllt werden.", - "server_configuration_installation_inputs_bad_sshPubKey": "Der öffentliche SSH-Schlüssel ist ungültig: Es werden nur RSA-, ECDSA- und EdDSA-Schlüssel im OpenSSH-Format akzeptiert", - "server_configuration_installation_inputs_bad_url": "Die angegebene URL ist ungültig.", - "server_configuration_installation_inputs_bad_uuid": "Die UUIDv4 ist ungültig.", "server_configuration_installation_ovh_title": "Installation mit einem OVHcloud Template", "server_configuration_installation_ovh_fail_os": "Beim Abruf der für den Server {{t0}} verfügbaren Distributionen ist ein Fehler aufgetreten", "server_configuration_installation_ovh_fail_partition_schemes": "Beim Abruf der Partitionsschemata für den Server {{t0}} ist ein Fehler aufgetreten", "server_configuration_installation_ovh_beta": "Beta", - "server_configuration_installation_ovh_desktop_BACKUP": "Backup", "server_configuration_installation_ovh_desktop_BASIC": "Basic", "server_configuration_installation_ovh_desktop_CUSTOMER": "Personalisiert", "server_configuration_installation_ovh_desktop_DATABASE": "Datenbank", @@ -434,7 +418,6 @@ "server_configuration_installation_ovh_step2_type": "Typ", "server_configuration_installation_ovh_step2_type_disk": "Für diese Installation verwendete Festplatten:", "server_configuration_installation_ovh_step2_type_disk_disable": "Für diese Installation nicht nutzbare Festplatten:", - "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Auch wenn das ausgewählte Disk-Array {{t0}} Festplatten enthält, kann das gewählte Betriebssystem nur auf maximal 2 Festplatten installiert werden.", "server_configuration_installation_ovh_step2_show_all_disk": "Die anderen Festplatten anzeigen", "server_configuration_installation_ovh_step2_hide_all_disk": "Die anderen Festplatten ausblenden", "server_configuration_installation_ovh_step2_file_system": "Dateisystem", @@ -496,7 +479,6 @@ "server_configuration_installation_ovh_step3_partition_size": "Größe: {{t0}}", "server_configuration_installation_ovh_step3_error_integrity": "Beim Kohärenztest Ihrer angepassten Installation ({{t0}}) wurde ein Fehler festgestellt. Die Installation kann nicht durchgeführt werden.", "server_configuration_installation_ovh_step3_error_integrity_info": "Bitte korrigieren Sie den Fehler, indem Sie auf den „Zurück“-Button klicken", - "server_configuration_installation_ovh_step3_scheme": "Partitionierungsschema:", "server_configuration_installation_ovh_step3_partition_variable": "Partition variabler Größe:", "server_configuration_installation_ovh_step3_partition_variable_help": "Diese Partition belegt den verbleibenden Speicherplatz, um das Template für einen Server mit abweichendem Gesamtspeicherplatz anzupassen.", "server_configuration_installation_ovh_step3_partition_variable_info": "Die Partition {{t0}} passt so ihre Größe an, um den noch verfügbaren Speicherplatz eines anderen Servers zu verwenden.", @@ -838,5 +820,26 @@ "server_configuration_intervention_activate_failed": "Bei der Aktivierung der Eingriffe vor Ort auf dem Server {{serverName}} ist ein Fehler aufgetreten.", "server_nutanix_cluster_node_warning_1": "Dieser Dedicated Server ist Teil des Nutanix-Clusters: {{clusterName}}", "server_nutanix_cluster_node_warning_2": "Wir empfehlen Ihnen, Ihre Konfiguration direkt im Dashboard des Servers zu bearbeiten, der mit Ihrem Nutanix-Cluster verbunden ist. Zum Dashboard: {{clusterNodeDashboardLink}}", - "server_nutanix_cluster_node_warning_3": "Alle mit diesem Server verbundenen Abrechnungen sehen Sie in Ihrem Nutanix-Cluster: {{clusterDashboardLink}}" -} \ No newline at end of file + "server_nutanix_cluster_node_warning_3": "Alle mit diesem Server verbundenen Abrechnungen sehen Sie in Ihrem Nutanix-Cluster: {{clusterDashboardLink}}", + "server_rtm_eol_info": "Wichtige Informationen zur Einstellung des veralterten Dienstes Real Time Monitoring. Dieser Dienst wird nur noch bis zum 30. Juni 2022 betrieben. Nach diesem Datum wird die Anzeige der Daten Ihrer Nutzung eingestellt. Dies hat keine Auswirkungen auf den Betrieb Ihres Servers.", + "server_configuration_installation_NONE": "Keine", + "server_configuration_installation_ovh_desktop_BACKUP": "Backup", + "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Auch wenn das ausgewählte Disk-Array {{t0}} Festplatten enthält, kann das gewählte Betriebssystem nur auf maximal 2 Festplatten installiert werden.", + "server_configuration_installation_ovh_step3_scheme": "Partitionierungsschema:", + "server_consumption_explanation_link": "Mehr erfahren", + "server_configuration_installation_inputs_title": "Spezifische Optionen:", + "server_configuration_installation_inputs_info": "Die unten stehenden Fragen beziehen sich speziell auf das ausgewählte Betriebssystem ({{t0}}). Zwecks Konsistenz mit der API sind sie nur auf Englisch verfasst.", + "server_configuration_installation_inputs_item_placeholder": "Wert vom Typ {{t0}} einfügen", + "server_configuration_installation_inputs_item_placeholder_example": "Zum Beispiel: {{t0}}", + "server_configuration_installation_inputs_item_mandatory": "Dieses Feld ist ein Pflichtfeld.", + "server_configuration_installation_inputs_bad_email": "Die eingegebene E-Mail-Adresse ist ungültig.", + "server_configuration_installation_inputs_bad_hexstring": "Die Zeichenfolge darf nur aus Zahlen und Buchstaben zwischen A und F bestehen.", + "server_configuration_installation_inputs_bad_ip": "Die eingegebene IPv4-Adresse ist ungültig.", + "server_configuration_installation_inputs_bad_required": "Dieses Feld muss ausgefüllt werden.", + "server_configuration_installation_inputs_bad_sshPubKey": "Der öffentliche SSH-Schlüssel ist ungültig: Es werden nur RSA-, ECDSA- und EdDSA-Schlüssel im OpenSSH-Format akzeptiert", + "server_configuration_installation_inputs_bad_url": "Die angegebene URL ist ungültig.", + "server_configuration_installation_inputs_bad_uuid": "Die UUIDv4 ist ungültig.", + "server_configuration_installation_custom_image_info": "Auf dem nächsten Bildschirm können Sie ein Betriebssystem von einem personalisierten Image aus installieren, indem Sie in „{{t1}}“ die Option „{{t0}}“ auswählen.", + "server_configuration_installation_custom_image_help_link": "Wählen Sie den am besten geeigneten individuellen Installationstyp aus.", + "server_datacenter_YYZ": "Toronto" +} diff --git a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_en_GB.json b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_en_GB.json index 86a8bdb434a7..21e59bb1abac 100644 --- a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_en_GB.json +++ b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_en_GB.json @@ -331,8 +331,6 @@ "server_configuration_installation_title": "Server installation", "server_configuration_installation_info": "You are about to install an OS on the {{t0}} server. Select the type of installation you would like to use:", "server_configuration_installation_warning": "Warning: all the server's drives will be formatted when installed", - "server_configuration_installation_custom_image_info": "You can install an OS from a custom image on the next screen by choosing \"{{t0}}\" in \"{{t1}}\".", - "server_configuration_installation_custom_image_help_link": "Choose the most suitable custom installation type.", "server_configuration_installation_32": "32 bit", "server_configuration_installation_64": "64 bit", "server_configuration_installation_deprecated": "Deprecated", @@ -349,7 +347,6 @@ "server_configuration_installation_ZFS": "ZFS", "server_configuration_installation_REISERFS": "ReiserFS", "server_configuration_installation_SWAP": "SWAP", - "server_configuration_installation_NONE": "None", "server_configuration_installation_UFS": "UFS", "server_configuration_installation_LOGICAL": "logical", "server_configuration_installation_LV": "LV", @@ -376,23 +373,10 @@ "server_configuration_installation_form_ssh_no": "Without SSH key", "server_configuration_installation_form_ssh_help": "Add a key under the My Account section", "server_configuration_installation_form_nbdisk": "Number of disks partitioned:", - "server_configuration_installation_inputs_title": "Specific options:", - "server_configuration_installation_inputs_info": "The following questions are specific to the operating system selected ({{t0}})", - "server_configuration_installation_inputs_item_placeholder": "Insert a value of type {{t0}}", - "server_configuration_installation_inputs_item_placeholder_example": "For example: {{t0}}", - "server_configuration_installation_inputs_item_mandatory": "This field is mandatory", - "server_configuration_installation_inputs_bad_email": "The email address entered is not valid", - "server_configuration_installation_inputs_bad_hexstring": "Character string must contain only numbers and letters between A and F", - "server_configuration_installation_inputs_bad_ip": "The IPv4 address entered is not valid", - "server_configuration_installation_inputs_bad_required": "Required field", - "server_configuration_installation_inputs_bad_sshPubKey": "The SSH public key is invalid: only RSA, ECDSA and EdDSA keys in OpenSSH format are supported", - "server_configuration_installation_inputs_bad_url": "The URL entered is invalid", - "server_configuration_installation_inputs_bad_uuid": "The UUIDv4 is invalid", "server_configuration_installation_ovh_title": "Installation from an OVHcloud template", "server_configuration_installation_ovh_fail_os": "An error has occurred retrieving the operating systems available for the {{t0}} server", "server_configuration_installation_ovh_fail_partition_schemes": "An error has occurred retrieving the partition diagrams for the {{t0}} server", "server_configuration_installation_ovh_beta": "Beta", - "server_configuration_installation_ovh_desktop_BACKUP": "Backup", "server_configuration_installation_ovh_desktop_BASIC": "Basic", "server_configuration_installation_ovh_desktop_CUSTOMER": "Custom", "server_configuration_installation_ovh_desktop_DATABASE": "Database ", @@ -434,7 +418,6 @@ "server_configuration_installation_ovh_step2_type": "Type", "server_configuration_installation_ovh_step2_type_disk": "Disks used for this installation:", "server_configuration_installation_ovh_step2_type_disk_disable": "Disk cannot be allocated for this installation:", - "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Even if the selected disk group contains {{t0}} disks, the chosen operating system can only be installed on up to 2 disks", "server_configuration_installation_ovh_step2_show_all_disk": "Show other disks", "server_configuration_installation_ovh_step2_hide_all_disk": "Hide other disks", "server_configuration_installation_ovh_step2_file_system": "File system", @@ -496,7 +479,6 @@ "server_configuration_installation_ovh_step3_partition_size": "Size: {{t0}}", "server_configuration_installation_ovh_step3_error_integrity": "An error was detected during the consistency test for your ({{t0}}) custom installation. Unable to install.", "server_configuration_installation_ovh_step3_error_integrity_info": "Please correct the error by clicking on the back button", - "server_configuration_installation_ovh_step3_scheme": "Partitioning scheme:", "server_configuration_installation_ovh_step3_partition_variable": "Variable size partition:", "server_configuration_installation_ovh_step3_partition_variable_help": "This partition will occupy the remaining available space, in order to adapt this template to a server with a different total space.", "server_configuration_installation_ovh_step3_partition_variable_info": "The {{t0}} partition will adapt its size in order to occupy the remaining space of another server", @@ -838,5 +820,26 @@ "server_configuration_intervention_activate_failed": "An error has occurred enabling on-site interventions on server {{serverName}}", "server_nutanix_cluster_node_warning_1": "This dedicated server is part of a Nutanix cluster: {{clusterName}}.", "server_nutanix_cluster_node_warning_2": "We recommend making all of the configuration changes directly in the dashboard of the server linked to your Nutanix cluster: {{clusterNodeDashboardLink}}", - "server_nutanix_cluster_node_warning_3": "All billing actions linked to this server are visible on your Nutanix cluster: {{clusterDashboardLink}}" -} \ No newline at end of file + "server_nutanix_cluster_node_warning_3": "All billing actions linked to this server are visible on your Nutanix cluster: {{clusterDashboardLink}}", + "server_rtm_eol_info": "Important information - the Real Time Monitoring Service will soon be obsolete. It will continue running until 30 June 2022. After this date, we will stop displaying your consumption data. This will not affect your server’s operation.", + "server_configuration_installation_NONE": "None", + "server_configuration_installation_ovh_desktop_BACKUP": "Backup", + "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Even if the selected disk group contains {{t0}} disks, the chosen operating system can only be installed on up to 2 disks", + "server_configuration_installation_ovh_step3_scheme": "Partitioning scheme:", + "server_consumption_explanation_link": "More details", + "server_configuration_installation_inputs_title": "Specific options:", + "server_configuration_installation_inputs_info": "The following questions are specific to the operating system selected ({{t0}})", + "server_configuration_installation_inputs_item_placeholder": "Insert a value of type {{t0}}", + "server_configuration_installation_inputs_item_placeholder_example": "For example: {{t0}}", + "server_configuration_installation_inputs_item_mandatory": "This field is mandatory", + "server_configuration_installation_inputs_bad_email": "The email address entered is not valid", + "server_configuration_installation_inputs_bad_hexstring": "Character string must contain only numbers and letters between A and F", + "server_configuration_installation_inputs_bad_ip": "The IPv4 address entered is not valid", + "server_configuration_installation_inputs_bad_required": "Required field", + "server_configuration_installation_inputs_bad_sshPubKey": "The SSH public key is invalid: only RSA, ECDSA and EdDSA keys in OpenSSH format are supported", + "server_configuration_installation_inputs_bad_url": "The URL entered is invalid", + "server_configuration_installation_inputs_bad_uuid": "The UUIDv4 is invalid", + "server_configuration_installation_custom_image_info": "You can install an OS from a custom image on the next screen by choosing \"{{t0}}\" in \"{{t1}}\".", + "server_configuration_installation_custom_image_help_link": "Choose the most suitable custom installation type.", + "server_datacenter_YYZ": "Toronto" +} diff --git a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_es_ES.json b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_es_ES.json index ab14476109cf..6d957f2beea0 100644 --- a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_es_ES.json +++ b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_es_ES.json @@ -331,8 +331,6 @@ "server_configuration_installation_title": "Instalación del servidor", "server_configuration_installation_info": "Va a activar un SO en el servidor {{t0}}. Elija el tipo de instalación que quiere utilizar:", "server_configuration_installation_warning": "Atención: Todos los discos del servidor serán formateados durante la instalación.", - "server_configuration_installation_custom_image_info": "Puede instalar un SO desde una imagen personalizada en la siguiente pantalla seleccionando «{{t0}}» en «{{t1}}».", - "server_configuration_installation_custom_image_help_link": "Seleccione el tipo de instalación personalizada más adecuado.", "server_configuration_installation_32": "32 bits", "server_configuration_installation_64": "64 bits", "server_configuration_installation_deprecated": "Deprecated", @@ -349,7 +347,6 @@ "server_configuration_installation_ZFS": "ZFS", "server_configuration_installation_REISERFS": "ReiserFS", "server_configuration_installation_SWAP": "SWAP", - "server_configuration_installation_NONE": "Ninguno", "server_configuration_installation_UFS": "UFS", "server_configuration_installation_LOGICAL": "logical", "server_configuration_installation_LV": "lv", @@ -376,23 +373,10 @@ "server_configuration_installation_form_ssh_no": "Sin llave SSH", "server_configuration_installation_form_ssh_help": "Añada una llave en la sección «Mi cuenta».", "server_configuration_installation_form_nbdisk": "Número de discos particionados:", - "server_configuration_installation_inputs_title": "Opciones específicas:", - "server_configuration_installation_inputs_info": "Las siguientes preguntas son específicas del sistema operativo seleccionado ({{t0}}). Para garantizar su consistencia con la API, solo están disponibles en inglés.", - "server_configuration_installation_inputs_item_placeholder": "Insertar un valor de tipo {{t0}}", - "server_configuration_installation_inputs_item_placeholder_example": "Por ejemplo: {{t0}}", - "server_configuration_installation_inputs_item_mandatory": "Este campo es obligatorio.", - "server_configuration_installation_inputs_bad_email": "La dirección de correo electrónico introducida no es válida.", - "server_configuration_installation_inputs_bad_hexstring": "La cadena de caracteres solo puede contener cifras y letras comprendidas entre «a» y «f».", - "server_configuration_installation_inputs_bad_ip": "La dirección IPv4 introducida no es válida.", - "server_configuration_installation_inputs_bad_required": "Este campo es obligatorio.", - "server_configuration_installation_inputs_bad_sshPubKey": "La clave pública SSH no es válida: solo se aceptan claves RSA, ECDSA y EdDSA en formato OpenSSH.", - "server_configuration_installation_inputs_bad_url": "La dirección URL introducida no es válida.", - "server_configuration_installation_inputs_bad_uuid": "El UUIDv4 no es válido.", "server_configuration_installation_ovh_title": "Instalación desde una plantilla de OVHcloud", "server_configuration_installation_ovh_fail_os": "Se ha producido un error al obtener las distribuciones disponibles para el servidor {{t0}}.", "server_configuration_installation_ovh_fail_partition_schemes": "Se ha producido un error al obtener las tablas de particiones para el servidor {{t0}}.", "server_configuration_installation_ovh_beta": "Beta", - "server_configuration_installation_ovh_desktop_BACKUP": "Copia de seguridad", "server_configuration_installation_ovh_desktop_BASIC": "Básico", "server_configuration_installation_ovh_desktop_CUSTOMER": "Personalizado", "server_configuration_installation_ovh_desktop_DATABASE": "Base de datos", @@ -434,7 +418,6 @@ "server_configuration_installation_ovh_step2_type": "Tipo", "server_configuration_installation_ovh_step2_type_disk": "Discos utilizados para la instalación:", "server_configuration_installation_ovh_step2_type_disk_disable": "Disco no válido para la instalación:", - "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Aunque el conjunto de discos seleccionado contenga {{t0}} discos, el sistema operativo elegido solo puede instalarse en 2 discos como máximo.", "server_configuration_installation_ovh_step2_show_all_disk": "Mostrar los otros discos", "server_configuration_installation_ovh_step2_hide_all_disk": "Ocultar los otros discos", "server_configuration_installation_ovh_step2_file_system": "Sistema de archivos", @@ -496,7 +479,6 @@ "server_configuration_installation_ovh_step3_partition_size": "Tamaño: {{t0}}", "server_configuration_installation_ovh_step3_error_integrity": "Se ha detectado un error al probar la coherencia de su instalación personalizada ({{t0}}). No se ha podido realizar la instalación.", "server_configuration_installation_ovh_step3_error_integrity_info": "Corrija el error haciendo clic en «Anterior».", - "server_configuration_installation_ovh_step3_scheme": "Esquema de partición:", "server_configuration_installation_ovh_step3_partition_variable": "Partición de tamaño variable:", "server_configuration_installation_ovh_step3_partition_variable_help": "Esta partición ocupará el espacio disponible restante para adaptar la plantilla a un servidor que tiene un espacio total diferente.", "server_configuration_installation_ovh_step3_partition_variable_info": "La partición {{t0}} adaptará su tamaño para ocupar el espacio disponible restante de otro servidor.", @@ -838,5 +820,26 @@ "server_configuration_intervention_activate_failed": "Se ha producido un error al activar las intervenciones in situ en el servidor {{serverName}}.", "server_nutanix_cluster_node_warning_1": "Este servidor dedicado forma parte de un cluster Nutanix: {{clusterName}}.", "server_nutanix_cluster_node_warning_2": "Le recomendamos que realice las modificaciones de configuración directamente desde el panel de control del servidor asociado a su cluster Nutanix: {{clusterNodeDashboardLink}}", - "server_nutanix_cluster_node_warning_3": "Puede consultar todas las acciones de facturación asociadas a este servidor en su cluster Nutanix: {{clusterDashboardLink}}" + "server_nutanix_cluster_node_warning_3": "Puede consultar todas las acciones de facturación asociadas a este servidor en su cluster Nutanix: {{clusterDashboardLink}}", + "server_rtm_eol_info": "Información importante sobre la obsolescencia de Real Time Monitoring: el servicio seguirá funcionando hasta el 30 de junio de 2022. A partir de esa fecha, sus datos de consumo dejarán de mostrarse, sin que ello afecte al funcionamiento de su servidor.", + "server_configuration_installation_NONE": "Ninguno", + "server_configuration_installation_ovh_desktop_BACKUP": "Copia de seguridad", + "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Aunque el conjunto de discos seleccionado contenga {{t0}} discos, el sistema operativo elegido solo puede instalarse en 2 discos como máximo.", + "server_configuration_installation_ovh_step3_scheme": "Esquema de partición:", + "server_consumption_explanation_link": "Más información", + "server_configuration_installation_inputs_title": "Opciones específicas:", + "server_configuration_installation_inputs_info": "Las siguientes preguntas son específicas del sistema operativo seleccionado ({{t0}}). Para garantizar su consistencia con la API, solo están disponibles en inglés", + "server_configuration_installation_inputs_item_placeholder": "Insertar un valor de tipo {{t0}}", + "server_configuration_installation_inputs_item_placeholder_example": "Por ejemplo: {{t0}}", + "server_configuration_installation_inputs_item_mandatory": "Este campo es obligatorio.", + "server_configuration_installation_inputs_bad_email": "La dirección de correo electrónico introducida no es válida.", + "server_configuration_installation_inputs_bad_hexstring": "La cadena de caracteres solo puede contener cifras y letras comprendidas entre «a» y «f».", + "server_configuration_installation_inputs_bad_ip": "La dirección IPv4 introducida no es válida.", + "server_configuration_installation_inputs_bad_required": "Este campo es obligatorio.", + "server_configuration_installation_inputs_bad_sshPubKey": "La clave pública SSH no es válida: solo se aceptan claves RSA, ECDSA y EdDSA en formato OpenSSH.", + "server_configuration_installation_inputs_bad_url": "La dirección URL introducida no es válida.", + "server_configuration_installation_inputs_bad_uuid": "El UUIDv4 no es válido.", + "server_configuration_installation_custom_image_info": "Puede instalar un SO desde una imagen personalizada en la siguiente pantalla seleccionando «{{t0}}» en «{{t1}}».", + "server_configuration_installation_custom_image_help_link": "Seleccione el tipo de instalación personalizada más adecuado.", + "server_datacenter_YYZ": "Toronto" } diff --git a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_fr_CA.json b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_fr_CA.json index 09d49978c177..d58a491de0fe 100644 --- a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_fr_CA.json +++ b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_fr_CA.json @@ -820,6 +820,7 @@ "server_datacenter_RBX_HZ": "Roubaix", "server_datacenter_GSW": "Clichy", "server_datacenter_YNM": "Mumbai", + "server_datacenter_YYZ": "Toronto", "server_usage_chart_yaxis_label": "Utilisation (en %)", "server_duration_upto": "Jusqu'au {{t0}}", "server_error_ola_activation": "Une erreur est survenue lors de l'activation de votre service : {{error}}", diff --git a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_fr_FR.json b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_fr_FR.json index 09d49978c177..d58a491de0fe 100644 --- a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_fr_FR.json +++ b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_fr_FR.json @@ -820,6 +820,7 @@ "server_datacenter_RBX_HZ": "Roubaix", "server_datacenter_GSW": "Clichy", "server_datacenter_YNM": "Mumbai", + "server_datacenter_YYZ": "Toronto", "server_usage_chart_yaxis_label": "Utilisation (en %)", "server_duration_upto": "Jusqu'au {{t0}}", "server_error_ola_activation": "Une erreur est survenue lors de l'activation de votre service : {{error}}", diff --git a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_it_IT.json b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_it_IT.json index 42f314281435..d75792a13f12 100644 --- a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_it_IT.json +++ b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_it_IT.json @@ -331,8 +331,6 @@ "server_configuration_installation_title": "Installazione del server", "server_configuration_installation_info": "Stai per attivare un OS sul server {{t0}}. Scegli il tipo di installazione da utilizzare:", "server_configuration_installation_warning": "Attenzione: durante l'installazione tutti i dischi del server verranno formattati", - "server_configuration_installation_custom_image_info": "Potrai installare un OS da un'immagine personalizzata nella prossima schermata, scegliendo \"{{t0}}\" in \"{{t1}}\".", - "server_configuration_installation_custom_image_help_link": "Scegli il tipo di installazione personalizzata più appropriato.", "server_configuration_installation_32": "32 bit", "server_configuration_installation_64": "64 bit", "server_configuration_installation_deprecated": "Deprecated", @@ -349,7 +347,6 @@ "server_configuration_installation_ZFS": "ZFS", "server_configuration_installation_REISERFS": "ReiserFS", "server_configuration_installation_SWAP": "Swap", - "server_configuration_installation_NONE": "Nessuno", "server_configuration_installation_UFS": "UFS", "server_configuration_installation_LOGICAL": "logical", "server_configuration_installation_LV": "lv", @@ -376,23 +373,10 @@ "server_configuration_installation_form_ssh_no": "Senza chiave SSH", "server_configuration_installation_form_ssh_help": "Aggiungi una chiave nella sezione \"Il mio account\"", "server_configuration_installation_form_nbdisk": "Numero di dischi partizionati:", - "server_configuration_installation_inputs_title": "Opzioni specifiche:", - "server_configuration_installation_inputs_info": "Le seguenti domande sono specifiche del sistema operativo selezionato ({{t0}}) e sono disponibili esclusivamente in inglese per garantire coerenza con l’API.", - "server_configuration_installation_inputs_item_placeholder": "Inserire un valore di tipo {{t0}}", - "server_configuration_installation_inputs_item_placeholder_example": "Per esempio: {{t0}}", - "server_configuration_installation_inputs_item_mandatory": "Questo campo è obbligatorio", - "server_configuration_installation_inputs_bad_email": "L'indirizzo email inserito non è valido", - "server_configuration_installation_inputs_bad_hexstring": "La stringa di caratteri deve essere composta esclusivamente da cifre e lettere comprese tra A e F", - "server_configuration_installation_inputs_bad_ip": "L'indirizzo IPv4 inserito non è valido", - "server_configuration_installation_inputs_bad_required": "Questo campo è obbligatorio", - "server_configuration_installation_inputs_bad_sshPubKey": "La chiave pubblica SSH non è valida: sono accettate solo le chiavi RSA, ECDSA e EdDSA in formato OpenSSH", - "server_configuration_installation_inputs_bad_url": "L'URL inserito non è valido", - "server_configuration_installation_inputs_bad_uuid": "L’UUIDv4 non è valido", "server_configuration_installation_ovh_title": "Installazione a partire da un template OVHcloud", "server_configuration_installation_ovh_fail_os": "Si è verificato un errore durante il recupero delle distribuzioni disponibili per il server {{t0}}", "server_configuration_installation_ovh_fail_partition_schemes": "Si è verificato un errore durante il recupero degli schemi di partizione per il server {{t0}}", "server_configuration_installation_ovh_beta": "Beta", - "server_configuration_installation_ovh_desktop_BACKUP": "Backup", "server_configuration_installation_ovh_desktop_BASIC": "Base", "server_configuration_installation_ovh_desktop_CUSTOMER": "Personalizzato", "server_configuration_installation_ovh_desktop_DATABASE": "Database", @@ -434,7 +418,6 @@ "server_configuration_installation_ovh_step2_type": "Tipo", "server_configuration_installation_ovh_step2_type_disk": "Dischi utilizzati per questa installazione:", "server_configuration_installation_ovh_step2_type_disk_disable": "Disco non utilizzabile per questa installazione:", - "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Anche se il gruppo di dischi selezionato contiene {{t0}} dischi, il sistema operativo scelto può essere installato solo su un massimo di 2 dischi.", "server_configuration_installation_ovh_step2_show_all_disk": "Visualizza gli altri dischi", "server_configuration_installation_ovh_step2_hide_all_disk": "Nascondi gli altri dischi", "server_configuration_installation_ovh_step2_file_system": "File System", @@ -496,7 +479,6 @@ "server_configuration_installation_ovh_step3_partition_size": "Dimensione: {{t0}}", "server_configuration_installation_ovh_step3_error_integrity": "È stato rilevato un errore durante il test di coerenza della tua installazione personalizzata ({{t0}}). Installazione impossibile.", "server_configuration_installation_ovh_step3_error_integrity_info": "Correggi l'errore cliccando sul pulsante precedente ", - "server_configuration_installation_ovh_step3_scheme": "Schema di partizionamento:", "server_configuration_installation_ovh_step3_partition_variable": "Partizione di dimensione variabile:", "server_configuration_installation_ovh_step3_partition_variable_help": "Questa partizione occuperà lo spazio disponibile residuo per adattare questo template su un server di cui lo spazio totale è differente.", "server_configuration_installation_ovh_step3_partition_variable_info": "La partizione {{t0}} adatterà le sue dimensioni per occupare lo spazio disco disponibile residuo di un altro server", @@ -838,5 +820,26 @@ "server_configuration_intervention_activate_failed": "Si è verificato un errore durante l'attivazione degli interventi in loco sul server {{serverName}}", "server_nutanix_cluster_node_warning_1": "Questo server dedicato fa parte di un cluster Nutanix: {{clusterName}}", "server_nutanix_cluster_node_warning_2": "Consigliamo di apportare tutte le modifiche di configurazione direttamente nella dashboard del server associato al cluster Nutanix: {{clusterNodeDashboardLink}}", - "server_nutanix_cluster_node_warning_3": "Tutte le azioni di fatturazione associate a questo server sono visibili sul cluster Nutanix: {{clusterDashboardLink}}" + "server_nutanix_cluster_node_warning_3": "Tutte le azioni di fatturazione associate a questo server sono visibili sul cluster Nutanix: {{clusterDashboardLink}}", + "server_rtm_eol_info": "Informazione importante sull'obsolescenza di Real Time Monitoring: il servizio continuerà a funzionare fino al 30 giugno 2022. A partire da questa data la visualizzazione dei dati di consumo verrà interrotta, senza impatto sul funzionamento del tuo server.", + "server_configuration_installation_NONE": "Nessuno", + "server_configuration_installation_ovh_desktop_BACKUP": "Backup", + "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Anche se il gruppo di dischi selezionato contiene {{t0}} dischi, il sistema operativo scelto può essere installato solo su un massimo di 2 dischi.", + "server_configuration_installation_ovh_step3_scheme": "Schema di partizionamento:", + "server_consumption_explanation_link": "Più dettagli ", + "server_configuration_installation_inputs_title": "Opzioni specifiche:", + "server_configuration_installation_inputs_info": "Le seguenti domande sono specifiche del sistema operativo selezionato ({{t0}}) e sono disponibili esclusivamente in inglese per garantire coerenza con l’API.", + "server_configuration_installation_inputs_item_placeholder": "Inserire un valore di tipo {{t0}}", + "server_configuration_installation_inputs_item_placeholder_example": "Per esempio: {{t0}}", + "server_configuration_installation_inputs_item_mandatory": "Questo campo è obbligatorio", + "server_configuration_installation_inputs_bad_email": "L'indirizzo email inserito non è valido", + "server_configuration_installation_inputs_bad_hexstring": "La stringa di caratteri deve essere composta esclusivamente da cifre e lettere comprese tra A e F", + "server_configuration_installation_inputs_bad_ip": "L'indirizzo IPv4 inserito non è valido", + "server_configuration_installation_inputs_bad_required": "Questo campo è obbligatorio", + "server_configuration_installation_inputs_bad_sshPubKey": "La chiave pubblica SSH non è valida: sono accettate solo le chiavi RSA, ECDSA e EdDSA in formato OpenSSH", + "server_configuration_installation_inputs_bad_url": "L'URL inserito non è valido", + "server_configuration_installation_inputs_bad_uuid": "L’UUIDv4 non è valido", + "server_configuration_installation_custom_image_info": "Potrai installare un OS da un'immagine personalizzata nella prossima schermata, scegliendo \"{{t0}}\" in \"{{t1}}\".", + "server_configuration_installation_custom_image_help_link": "Scegli il tipo di installazione personalizzata più appropriato.", + "server_datacenter_YYZ": "Toronto" } diff --git a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_pl_PL.json b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_pl_PL.json index af6f4643078e..c591f462156b 100644 --- a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_pl_PL.json +++ b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_pl_PL.json @@ -331,8 +331,6 @@ "server_configuration_installation_title": "Instalacja serwera", "server_configuration_installation_info": "Chcesz zainstalować system operacyjny w serwerze {{t0}}. Wybierz rodzaj instalacji:", "server_configuration_installation_warning": "Uwaga: wszystkie dyski serwera zostaną sformatowane podczas instalacji.", - "server_configuration_installation_custom_image_info": "Na następnym ekranie będziesz mógł zainstalować system operacyjny z niestandardowego obrazu, wybierając „{{t0}}” w „{{t1}}”.", - "server_configuration_installation_custom_image_help_link": "Wybierz najbardziej odpowiedni typ instalacji z niestandardowymi ustawieniami.", "server_configuration_installation_32": "32 bity", "server_configuration_installation_64": "64 bity", "server_configuration_installation_deprecated": "Deprecated", @@ -349,7 +347,6 @@ "server_configuration_installation_ZFS": "ZFS", "server_configuration_installation_REISERFS": "ReiserFS", "server_configuration_installation_SWAP": "SWAP", - "server_configuration_installation_NONE": "Brak", "server_configuration_installation_UFS": "UFS", "server_configuration_installation_LOGICAL": "logical", "server_configuration_installation_LV": "lv", @@ -376,23 +373,10 @@ "server_configuration_installation_form_ssh_no": "Bez klucza SSH", "server_configuration_installation_form_ssh_help": "Dodaj klucz w sekcji Moje konto", "server_configuration_installation_form_nbdisk": "Liczba partycjonowanych dysków:", - "server_configuration_installation_inputs_title": "Opcje specjalne:", - "server_configuration_installation_inputs_info": "Poniższe pytania są specyficzne dla wybranego systemu operacyjnego ({{t0}}): są napisane wyłącznie w języku angielskim, gdyż pozwala to zachować spójność z API.", - "server_configuration_installation_inputs_item_placeholder": "Wprowadź wartość typu {{t0}}", - "server_configuration_installation_inputs_item_placeholder_example": "Na przykład: {{t0}}", - "server_configuration_installation_inputs_item_mandatory": "Uzupełnienie tego pola jest obowiązkowe", - "server_configuration_installation_inputs_bad_email": "Wprowadzony adres e-mail jest nieprawidłowy", - "server_configuration_installation_inputs_bad_hexstring": "Ciąg znaków może składać się wyłącznie z cyfr i liter od A do F", - "server_configuration_installation_inputs_bad_ip": "Wprowadzony adres IPv4 jest nieprawidłowy", - "server_configuration_installation_inputs_bad_required": "Uzupełnienie tego pola jest obowiązkowe", - "server_configuration_installation_inputs_bad_sshPubKey": "Publiczny klucz SSH jest nieprawidłowy: akceptowane są tylko klucze RSA, ECDSA i EdDSA w formacie OpenSSH", - "server_configuration_installation_inputs_bad_url": "Wprowadzony adres URL jest nieprawidłowy", - "server_configuration_installation_inputs_bad_uuid": "UUIDv4 jest nieprawidłowy", "server_configuration_installation_ovh_title": "Instalacja szablonu OVHcloud", "server_configuration_installation_ovh_fail_os": "Wystąpił błąd podczas pobierania dystrybucji dostępnych dla serwera {{t0}}.", "server_configuration_installation_ovh_fail_partition_schemes": "Wystąpił błąd podczas pobierania schematów partycji dla serwera {{t0}}.", "server_configuration_installation_ovh_beta": "Wersja Beta", - "server_configuration_installation_ovh_desktop_BACKUP": "Kopia zapasowa", "server_configuration_installation_ovh_desktop_BASIC": "Podstawowy", "server_configuration_installation_ovh_desktop_CUSTOMER": "Spersonalizowana", "server_configuration_installation_ovh_desktop_DATABASE": "Baza danych", @@ -434,7 +418,6 @@ "server_configuration_installation_ovh_step2_type": "Typ", "server_configuration_installation_ovh_step2_type_disk": "Dyski używane dla tej instalacji:", "server_configuration_installation_ovh_step2_type_disk_disable": "Dysk nieprzypisane podczas instalacji:", - "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Nawet jeśli wybrana macierz dyskowa zawiera {{t0}} dysków, wybrany system operacyjny można zainstalować na maksymalnie 2 dyskach", "server_configuration_installation_ovh_step2_show_all_disk": "Wyświetl inne dyski", "server_configuration_installation_ovh_step2_hide_all_disk": "Ukryj inne dyski", "server_configuration_installation_ovh_step2_file_system": "System plików", @@ -496,7 +479,6 @@ "server_configuration_installation_ovh_step3_partition_size": "Rozmiar: {{t0}}", "server_configuration_installation_ovh_step3_error_integrity": "Wystąpił problem podczas testowania spójności spersonalizowanej instalacji ({{t0}}). Instalacja nie jest możliwa.", "server_configuration_installation_ovh_step3_error_integrity_info": "Popraw konfigurację, klikając na przycisk Wstecz.", - "server_configuration_installation_ovh_step3_scheme": "Schemat partycji:", "server_configuration_installation_ovh_step3_partition_variable": "Partycja o zmiennym rozmiarze:", "server_configuration_installation_ovh_step3_partition_variable_help": "Ta partycja zajmie pozostałą dostępną przestrzeń, aby dostosować ten szablon do serwera, którego całkowita przestrzeń jest inna.", "server_configuration_installation_ovh_step3_partition_variable_info": "Partycja {{t0}}> dostosuje swój rozmiar, aby zająć pozostałą dostępną przestrzeń na innym serwerze.", @@ -838,5 +820,26 @@ "server_configuration_intervention_activate_failed": "Wystąpił błąd podczas włączania interwencji w centrum danych dla serwera {{serverName}}", "server_nutanix_cluster_node_warning_1": "Ten serwer dedykowany jest częścią klastra Nutanix: {{clusterName}}.", "server_nutanix_cluster_node_warning_2": "Zalecamy przeprowadzenie wszystkich zmian konfiguracji bezpośrednio na dashboardzie serwera powiązanego z klastrem Nutanix: {{clusterNodeDashboardLink}}", - "server_nutanix_cluster_node_warning_3": "Wszystkie operacje płatnicze związane z tym serwerem są widoczne w klastrze Nutanix: {{clusterDashboardLink}}" + "server_nutanix_cluster_node_warning_3": "Wszystkie operacje płatnicze związane z tym serwerem są widoczne w klastrze Nutanix: {{clusterDashboardLink}}", + "server_rtm_eol_info": "Ważna informacja dotycząca usługi Real Time Monitoring - usługa będzie działać do 30 czerwca 2022. Po tym terminie wstrzymamy wyświetlanie danych dotyczących zużycia. Nie będzie to miało wpływu na działanie serwera.", + "server_configuration_installation_NONE": "Brak", + "server_configuration_installation_ovh_desktop_BACKUP": "Kopia zapasowa", + "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Nawet jeśli wybrana macierz dyskowa zawiera {{t0}} dysków, wybrany system operacyjny można zainstalować na maksymalnie 2 dyskach", + "server_configuration_installation_ovh_step3_scheme": "Schemat partycji:", + "server_consumption_explanation_link": "Więcej informacji", + "server_configuration_installation_inputs_title": "Opcje specjalne:", + "server_configuration_installation_inputs_info": "Poniższe pytania są związane z wybranym systemem operacyjnym ({{t0}}). Są napisane wyłącznie w języku angielskim, aby były zgodne z API", + "server_configuration_installation_inputs_item_placeholder": "Wprowadź wartość typu {{t0}}", + "server_configuration_installation_inputs_item_placeholder_example": "Na przykład: {{t0}}", + "server_configuration_installation_inputs_item_mandatory": "Uzupełnienie tego pola jest obowiązkowe", + "server_configuration_installation_inputs_bad_email": "Wprowadzony adres e-mail jest nieprawidłowy", + "server_configuration_installation_inputs_bad_hexstring": "Ciąg znaków może składać się wyłącznie z cyfr i liter od A do F", + "server_configuration_installation_inputs_bad_ip": "Wprowadzony adres IPv4 jest nieprawidłowy", + "server_configuration_installation_inputs_bad_required": "Uzupełnienie tego pola jest obowiązkowe", + "server_configuration_installation_inputs_bad_sshPubKey": "Publiczny klucz SSH jest nieprawidłowy: akceptowane są tylko klucze RSA, ECDSA i EdDSA w formacie OpenSSH", + "server_configuration_installation_inputs_bad_url": "Wprowadzony adres URL jest nieprawidłowy", + "server_configuration_installation_inputs_bad_uuid": "UUIDv4 jest nieprawidłowy", + "server_configuration_installation_custom_image_info": "Na następnym ekranie będziesz mógł zainstalować system operacyjny z niestandardowego obrazu, wybierając „{{t0}}” w „{{t1}}”.", + "server_configuration_installation_custom_image_help_link": "Wybierz najbardziej odpowiedni typ instalacji z niestandardowymi ustawieniami.", + "server_datacenter_YYZ": "Toronto" } diff --git a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_pt_PT.json b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_pt_PT.json index 90d2bf575fc4..a4f365762b83 100644 --- a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_pt_PT.json +++ b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/server/translations/Messages_pt_PT.json @@ -331,8 +331,6 @@ "server_configuration_installation_title": "Instalação do servidor", "server_configuration_installation_info": "Está prestes a instalar um SO no servidor {{t0}}. Escolha o tipo de instalação que pretende utilizar:", "server_configuration_installation_warning": "Atenção: todos os discos do servidor serão formatados aquando da instalação.", - "server_configuration_installation_custom_image_info": "Poderá instalar um SO a partir de uma imagem personalizada no próximo ecrã, escolhendo \"{{t0}}\" em \"{{t1}}\".", - "server_configuration_installation_custom_image_help_link": "Selecione o tipo de instalação personalizada mais adequado.", "server_configuration_installation_32": "32 bits", "server_configuration_installation_64": "64 bits", "server_configuration_installation_deprecated": "Deprecated", @@ -349,7 +347,6 @@ "server_configuration_installation_ZFS": "ZFS", "server_configuration_installation_REISERFS": "ReiserFS", "server_configuration_installation_SWAP": "Swap", - "server_configuration_installation_NONE": "Nenhum", "server_configuration_installation_UFS": "UFS", "server_configuration_installation_LOGICAL": "logical", "server_configuration_installation_LV": "lv", @@ -376,23 +373,10 @@ "server_configuration_installation_form_ssh_no": "Sem chave SSH", "server_configuration_installation_form_ssh_help": "Adicione uma chave na seção A minha conta", "server_configuration_installation_form_nbdisk": "Número de discos particionados:", - "server_configuration_installation_inputs_title": "Opções específicas:", - "server_configuration_installation_inputs_info": "As questões abaixo são específicas ao sistema operativo selecionado ({{t0}}). São escritas unicamente em inglês para serem consistentes com a API.", - "server_configuration_installation_inputs_item_placeholder": "Inserir um valor de tipo {{t0}}", - "server_configuration_installation_inputs_item_placeholder_example": "Por exemplo: {{t0}}", - "server_configuration_installation_inputs_item_mandatory": "Este campo é obrigatório", - "server_configuration_installation_inputs_bad_email": "O endereço de e-mail introduzido não é válido", - "server_configuration_installation_inputs_bad_hexstring": "A cadeia de caracteres deve ser composta apenas por números e letras entre A e F", - "server_configuration_installation_inputs_bad_ip": "O endereço IPv4 introduzido não é válido", - "server_configuration_installation_inputs_bad_required": "Campo obrigatório", - "server_configuration_installation_inputs_bad_sshPubKey": "A chave pública SSH é inválida: apenas são aceites as chaves RSA, ECDSA e EdDSA no formato OpenSSH", - "server_configuration_installation_inputs_bad_url": "O URL introduzido é inválido", - "server_configuration_installation_inputs_bad_uuid": "UUIDv4 inválido", "server_configuration_installation_ovh_title": "Instalação a partir de um template OVHcloud", "server_configuration_installation_ovh_fail_os": "Ocorreu um erro aquando da recuperação das distribuições disponíveis para o servidor {{t0}}", "server_configuration_installation_ovh_fail_partition_schemes": "Ocorreu um erro aquando da recuperação dos esquemas de partições disponíveis para o servidor {{t0}}", "server_configuration_installation_ovh_beta": "Beta", - "server_configuration_installation_ovh_desktop_BACKUP": "Backup", "server_configuration_installation_ovh_desktop_BASIC": "Básico", "server_configuration_installation_ovh_desktop_CUSTOMER": "Personalizado", "server_configuration_installation_ovh_desktop_DATABASE": "Base de dados", @@ -434,7 +418,6 @@ "server_configuration_installation_ovh_step2_type": "Tipo", "server_configuration_installation_ovh_step2_type_disk": "Discos utilizados por esta instalação:", "server_configuration_installation_ovh_step2_type_disk_disable": "Discos não utilizados por esta instalação:", - "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Embora o conjunto de discos selecionado contenha {{t0}} discos, o sistema operativo escolhido só pode ser instalado em 2 discos, no máximo", "server_configuration_installation_ovh_step2_show_all_disk": "Mostrar os outros discos", "server_configuration_installation_ovh_step2_hide_all_disk": "Ocultar os outros discos", "server_configuration_installation_ovh_step2_file_system": "Sistema de ficheiros", @@ -496,7 +479,6 @@ "server_configuration_installation_ovh_step3_partition_size": "Tamanho: {{t0}}", "server_configuration_installation_ovh_step3_error_integrity": "Foi detetado um erro aquando do teste de coerência da sua instalação personalizada ({{t0}}). Instalação impossível.", "server_configuration_installation_ovh_step3_error_integrity_info": "Corrija o erro ao clicar no botão anterior", - "server_configuration_installation_ovh_step3_scheme": "Esquema de particionamento:", "server_configuration_installation_ovh_step3_partition_variable": "Partição de tamanho variável:", "server_configuration_installation_ovh_step3_partition_variable_help": "Essa partição ocupará o espaço disponível restante de forma a adaptar este template num servidor onde o espaço total é diferente.", "server_configuration_installation_ovh_step3_partition_variable_info": "A partição {{t0}} irá ajustar o seu tamanho para aproveitar o espaço disponível noutro servidor", @@ -838,5 +820,26 @@ "server_configuration_intervention_activate_failed": "Ocorreu um erro aquando da ativação das intervenções no local no servidor {{serverName}}", "server_nutanix_cluster_node_warning_1": "Este servidor dedicado faz parte de um cluster Nutanix: {{clusterName}}.", "server_nutanix_cluster_node_warning_2": "Recomendamos que efetue todas as alterações de configuração diretamente no painel de controlo do servidor associado ao seu cluster Nutanix: {{clusterNodeDashboardLink}}", - "server_nutanix_cluster_node_warning_3": "Todas as ações de faturação relacionadas com este servidor são visíveis no seu cluster Nutanix: {{clusterDashboardLink}}" -} \ No newline at end of file + "server_nutanix_cluster_node_warning_3": "Todas as ações de faturação relacionadas com este servidor são visíveis no seu cluster Nutanix: {{clusterDashboardLink}}", + "server_rtm_eol_info": "Informação importante relativa à obsolescência do serviço Real Time Monitoring - o serviço continuará a funcionar até 30 de junho de 2022. Após essa data, iremos parar a apresentação dos seus dados de consumo, sem que isso afete o funcionamento do seu servidor.", + "server_configuration_installation_NONE": "Nenhum", + "server_configuration_installation_ovh_desktop_BACKUP": "Backup", + "server_configuration_installation_ovh_step2_type_disk_warning_windows": "Embora o conjunto de discos selecionado contenha {{t0}} discos, o sistema operativo escolhido só pode ser instalado em 2 discos, no máximo", + "server_configuration_installation_ovh_step3_scheme": "Esquema de particionamento:", + "server_consumption_explanation_link": "Mais informações", + "server_configuration_installation_inputs_title": "Opções específicas:", + "server_configuration_installation_inputs_info": "As questões abaixo são específicas ao sistema operativo selecionado ({{t0}}). São escritas unicamente em inglês para serem consistentes com a API.", + "server_configuration_installation_inputs_item_placeholder": "Inserir um valor de tipo {{t0}}", + "server_configuration_installation_inputs_item_placeholder_example": "Por exemplo: {{t0}}", + "server_configuration_installation_inputs_item_mandatory": "Este campo é obrigatório", + "server_configuration_installation_inputs_bad_email": "O endereço de e-mail introduzido não é válido", + "server_configuration_installation_inputs_bad_hexstring": "A cadeia de caracteres deve ser composta apenas por números e letras entre A e F", + "server_configuration_installation_inputs_bad_ip": "O endereço IPv4 introduzido não é válido", + "server_configuration_installation_inputs_bad_required": "Campo obrigatório", + "server_configuration_installation_inputs_bad_sshPubKey": "A chave pública SSH é inválida: apenas são aceites as chaves RSA, ECDSA e EdDSA no formato OpenSSH", + "server_configuration_installation_inputs_bad_url": "O URL introduzido é inválido", + "server_configuration_installation_inputs_bad_uuid": "UUIDv4 inválido", + "server_configuration_installation_custom_image_info": "Poderá instalar um SO a partir de uma imagem personalizada no próximo ecrã, escolhendo \"{{t0}}\" em \"{{t1}}\".", + "server_configuration_installation_custom_image_help_link": "Selecione o tipo de instalação personalizada mais adequado.", + "server_datacenter_YYZ": "Toronto" +} diff --git a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/servers.constants.js b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/servers.constants.js index 54b6bfb3d7a9..ba53536f1b59 100644 --- a/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/servers.constants.js +++ b/packages/manager/apps/dedicated/client/app/dedicated/dedicated-server/servers/servers.constants.js @@ -14,6 +14,7 @@ export const DC_2_ISO = { VIN: 'US', WAW: 'PL', YNM: 'IN', + YYZ: 'CA', }; export const MONITORING_STATUSES = { diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/dashboard/dedicatedCloud-dashboard.routing.js b/packages/manager/apps/dedicated/client/app/dedicatedCloud/dashboard/dedicatedCloud-dashboard.routing.js index b37b9b971edd..63c47c621e98 100644 --- a/packages/manager/apps/dedicated/client/app/dedicatedCloud/dashboard/dedicatedCloud-dashboard.routing.js +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/dashboard/dedicatedCloud-dashboard.routing.js @@ -93,6 +93,12 @@ export default /* @ngInject */ ($stateProvider) => { optionName, }), + goToDatacenter: /* @ngInject */ ($state, productId) => (datacenterId) => + $state.go('app.dedicatedCloud.details.datacenter.details', { + productId, + datacenterId, + }), + disableVmwareOption: /* @ngInject */ ($state) => (option) => $state.go( 'app.dedicatedCloud.details.dashboard.vmware-option-disable', diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/dedicatedCloud.datacenter.dashboard.module.js b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/dedicatedCloud.datacenter.dashboard.module.js index 363cfda9ad0e..be4210e175b7 100644 --- a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/dedicatedCloud.datacenter.dashboard.module.js +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/dedicatedCloud.datacenter.dashboard.module.js @@ -3,6 +3,7 @@ import angular from 'angular'; import datacenterDashboardComponent from '../../../components/dedicated-cloud/datacenter/dashboard'; import deleteDatacenter from './delete'; import deleteDrp from './deleteDrp'; +import manageNsxEdges from './manage-nsx-edges'; import routing from './dedicatedCloud.datacenter.dashboard.routes'; const moduleName = 'ovhManagerDedicatedCloudDatacenterDashboard'; @@ -12,6 +13,7 @@ angular datacenterDashboardComponent, deleteDatacenter, deleteDrp, + manageNsxEdges, ]) .config(routing); diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/dedicatedCloud.datacenter.dashboard.routes.js b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/dedicatedCloud.datacenter.dashboard.routes.js index cf5743360482..eb9956b0aa22 100644 --- a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/dedicatedCloud.datacenter.dashboard.routes.js +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/dedicatedCloud.datacenter.dashboard.routes.js @@ -8,6 +8,72 @@ export default /* @ngInject */ ($stateProvider) => { }, resolve: { breadcrumb: () => null, + serviceName: /* @ngInject */ ($transition$) => + $transition$.params().productId, + datacenterId: /* @ngInject */ ($transition$) => + $transition$.params().datacenterId, + datastoreOrderLink: /* @ngInject */ ( + coreURLBuilder, + serviceName, + datacenterId, + ) => + coreURLBuilder.buildURL( + 'dedicated', + `#/dedicated_cloud/${serviceName}/datacenter/${datacenterId}/datastores/order`, + ), + hostOrderLink: /* @ngInject */ ( + coreURLBuilder, + serviceName, + datacenterId, + ) => + coreURLBuilder.buildURL( + 'dedicated', + `#/dedicated_cloud/${serviceName}/datacenter/${datacenterId}/hosts/order`, + ), + nsxEdgeCurrentLevel: /* @ngInject */ ( + DedicatedCloud, + serviceName, + datacenterId, + ) => { + return DedicatedCloud.getDatacenterInfoNsxt( + serviceName, + datacenterId, + ).then(([data]) => data?.size); + }, + nsxtEdgesScalingCapabilities: /* @ngInject */ ( + DedicatedCloud, + serviceName, + datacenterId, + ) => { + return DedicatedCloud.getDatacenterNsxtEdgesScalingCapabilities( + serviceName, + datacenterId, + ) + .then(({ data }) => data?.size) + .catch(() => []); + }, + goBackToDashboard: /* @ngInject */ ( + $state, + $timeout, + currentService, + setMessage, + ) => (message = false, type = 'success') => { + const reload = message && type === 'success'; + + const promise = $state.go( + 'app.dedicatedCloud.details.datacenter.details.dashboard', + { productId: currentService.serviceName }, + { + reload, + }, + ); + + if (message) { + promise.then(() => $timeout(() => setMessage(message, type))); + } + + return promise; + }, }, }, ); diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/constants.js b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/constants.js new file mode 100644 index 000000000000..25912cea5a86 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/constants.js @@ -0,0 +1,6 @@ +export const NSX_TRACKING_PREFIX = + 'dedicated::dedicatedCloud::details::datacenter::details::dashboard::nsx'; + +export default { + NSX_TRACKING_PREFIX, +}; diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.module.js b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.module.js new file mode 100644 index 000000000000..d6c8c0f5b276 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.module.js @@ -0,0 +1,13 @@ +import angular from 'angular'; + +import datacenterManageNsxEdgesComponent from '../../../../components/dedicated-cloud/datacenter/dashboard/manage-nsx-edges'; +import routing from './dedicatedCloud-datacenter-manage-nsx.routing'; + +const moduleName = 'ovhManagerDedicatedCloudDatacenterManageNsxEdges'; + +angular + .module(moduleName, [datacenterManageNsxEdgesComponent]) + .config(routing) + .run(/* @ngTranslationsInject:json ./translations */); + +export default moduleName; diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.routing.js b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.routing.js new file mode 100644 index 000000000000..dae77caff366 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/dedicatedCloud-datacenter-manage-nsx.routing.js @@ -0,0 +1,36 @@ +import { NSX_TRACKING_PREFIX } from './constants'; + +export default /* @ngInject */ ($stateProvider) => { + $stateProvider.state( + 'app.dedicatedCloud.details.datacenter.details.dashboard.nsx', + { + resolve: { + goBack: /* @ngInject */ (trackClick, goBackToDashboard) => () => { + trackClick('::cancel'); + return goBackToDashboard(); + }, + breadcrumb: /* @ngInject */ ($translate) => + $translate.instant( + 'dedicated_cloud_datacenters_datacenter_manage_nsx_edge', + ), + trackPage: /* @ngInject */ (atInternet) => (hit) => { + return atInternet.trackPage(`${NSX_TRACKING_PREFIX}${hit}`); + }, + trackClick: /* @ngInject */ (atInternet) => (hit) => { + return atInternet.trackClick({ + name: `${NSX_TRACKING_PREFIX}${hit}`, + type: 'action', + }); + }, + }, + atInternet: { + rename: NSX_TRACKING_PREFIX, + }, + url: '/nsx', + views: { + 'pccDatacenterView@app.dedicatedCloud.details.datacenter.details': + 'ovhManagerDedicatedCloudDatacenterManageNsxEdges', + }, + }, + ); +}; diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/index.js b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/index.js new file mode 100644 index 000000000000..0b0cd64b20df --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/index.js @@ -0,0 +1,27 @@ +import angular from 'angular'; +import '@uirouter/angularjs'; +import 'oclazyload'; + +const moduleName = + 'ovhManagerDedicatedCloudDatacenterManageNsxEdgesLazyloading'; + +angular.module(moduleName, ['ui.router', 'oc.lazyLoad']).config( + /* @ngInject */ ($stateProvider) => { + $stateProvider.state( + 'app.dedicatedCloud.details.datacenter.details.dashboard.nsx.**', + { + url: '/nsx', + lazyLoad: ($transition$) => { + const $ocLazyLoad = $transition$.injector().get('$ocLazyLoad'); + return import('./dedicatedCloud-datacenter-manage-nsx.module').then( + (mod) => { + $ocLazyLoad.inject(mod.default || mod); + }, + ); + }, + }, + ); + }, +); + +export default moduleName; diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_de_DE.json b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_de_DE.json new file mode 100644 index 000000000000..36100c3d198d --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_de_DE.json @@ -0,0 +1,3 @@ +{ + "dedicated_cloud_datacenters_datacenter_manage_nsx_edge": "NSX Edges anpassen" +} diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_en_GB.json b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_en_GB.json new file mode 100644 index 000000000000..d63ca7cb63b8 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_en_GB.json @@ -0,0 +1,3 @@ +{ + "dedicated_cloud_datacenters_datacenter_manage_nsx_edge": "Resize NSX Edges" +} diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_es_ES.json b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_es_ES.json new file mode 100644 index 000000000000..a423062ec5b1 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_es_ES.json @@ -0,0 +1,3 @@ +{ + "dedicated_cloud_datacenters_datacenter_manage_nsx_edge": "Redimensionar los NSX Edges" +} diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_fr_CA.json b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_fr_CA.json new file mode 100644 index 000000000000..07aa05955ff6 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_fr_CA.json @@ -0,0 +1,3 @@ +{ + "dedicated_cloud_datacenters_datacenter_manage_nsx_edge": "Redimensionner les NSX Edges" +} diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_fr_FR.json b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_fr_FR.json new file mode 100644 index 000000000000..07aa05955ff6 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_fr_FR.json @@ -0,0 +1,3 @@ +{ + "dedicated_cloud_datacenters_datacenter_manage_nsx_edge": "Redimensionner les NSX Edges" +} diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_it_IT.json b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_it_IT.json new file mode 100644 index 000000000000..7de8011c2c81 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_it_IT.json @@ -0,0 +1,3 @@ +{ + "dedicated_cloud_datacenters_datacenter_manage_nsx_edge": "Ridimensionare NSX Edges" +} diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_pl_PL.json b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_pl_PL.json new file mode 100644 index 000000000000..387a6d0bb306 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_pl_PL.json @@ -0,0 +1,3 @@ +{ + "dedicated_cloud_datacenters_datacenter_manage_nsx_edge": "Skaluj NSX Edge" +} diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_pt_PT.json b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_pt_PT.json new file mode 100644 index 000000000000..ae81510e4547 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/datacenter/dashboard/manage-nsx-edges/translations/Messages_pt_PT.json @@ -0,0 +1,3 @@ +{ + "dedicated_cloud_datacenters_datacenter_manage_nsx_edge": "Redimensionar NSX Edges" +} diff --git a/packages/manager/apps/dedicated/client/app/dedicatedCloud/details/dedicatedCloud.routing.js b/packages/manager/apps/dedicated/client/app/dedicatedCloud/details/dedicatedCloud.routing.js index 0e3611aab153..90810b6196ac 100644 --- a/packages/manager/apps/dedicated/client/app/dedicatedCloud/details/dedicatedCloud.routing.js +++ b/packages/manager/apps/dedicated/client/app/dedicatedCloud/details/dedicatedCloud.routing.js @@ -262,6 +262,14 @@ export default /* @ngInject */ ($stateProvider) => { datacenterId, }, ), + goToResizeNsxEdge: /* @ngInject */ ($state) => (datacenterId) => { + $state.go( + 'app.dedicatedCloud.details.datacenter.details.dashboard.nsx', + { + datacenterId, + }, + ); + }, pccType: /* @ngInject */ (dedicatedCloud) => dedicatedCloud.productReference, setMessage: /* @ngInject */ (Alerter) => ( diff --git a/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/firewall.constant.js b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/firewall.constant.js index ea6d357ed5cc..0ad1ea25046a 100644 --- a/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/firewall.constant.js +++ b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/firewall.constant.js @@ -1,14 +1,3 @@ -export const ALLOWED_LANGUAGES = { - en: { - isDefault: true, - }, - fr: { - isDefault: false, - }, -}; - -export const BASE_URL_SURVEY = 'https://survey.ovh.com/index.php/116651?lang='; - export const FIREWALL_GUIDE_LINKS = { DE: 'https://help.ovhcloud.com/csm/de-dedicated-servers-firewall-network?id=kb_article_view&sysparm_article=KB0030464', @@ -57,8 +46,6 @@ export const FIREWALL_GUIDE_LINKS = { export const EDGE_TRACKING_PREFIX = 'dedicated::ip::firewall'; export default { - ALLOWED_LANGUAGES, - BASE_URL_SURVEY, FIREWALL_GUIDE_LINKS, EDGE_TRACKING_PREFIX, }; diff --git a/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/firewall.module.js b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/firewall.module.js index 6363a581d4f2..bb76fada2f5d 100644 --- a/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/firewall.module.js +++ b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/firewall.module.js @@ -8,6 +8,7 @@ import ruleDeleteTemplate from './rule/delete/ip-ip-firewall-rule-delete.html'; import toggleController from './toggle/ip-ip-firewall-toggle.controller'; import toggleTemplate from './toggle/ip-ip-firewall-toggle.html'; +import './firewall.styles.scss'; const moduleName = 'ovhManagerIpDashboardFirewall'; diff --git a/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/firewall.styles.scss b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/firewall.styles.scss new file mode 100644 index 000000000000..841ee5472d01 --- /dev/null +++ b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/firewall.styles.scss @@ -0,0 +1,5 @@ +.ip-list-firewall { + .overflow-visible { + overflow: visible !important; + } +} diff --git a/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.constants.js b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.constants.js index 2d1fbf730987..b080fc3d956e 100644 --- a/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.constants.js +++ b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.constants.js @@ -10,17 +10,6 @@ export const IP_MITIGATION_RULE_PROTOCOL_PORT = { trackmaniaShootmania: { from: 2350, to: 2450 }, }; -export const ALLOWED_LANGUAGES = { - en: { - isDefault: true, - }, - fr: { - isDefault: false, - }, -}; - -export const BASE_URL_SURVEY = 'https://survey.ovh.com/index.php/187648?lang='; - export const GAME_GUIDE_LINKS = { DE: 'https://help.ovhcloud.com/csm/de-dedicated-servers-game-ddos-firewall?id=kb_article_view&sysparm_article=KB0060678', @@ -70,8 +59,6 @@ export const GAME_TRACKING_PREFIX = 'dedicated::ip::game-firewall'; export default { IP_MITIGATION_RULE_PROTOCOL_PORT, - ALLOWED_LANGUAGES, - BASE_URL_SURVEY, GAME_GUIDE_LINKS, GAME_TRACKING_PREFIX, }; diff --git a/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.controller.js b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.controller.js index ae5ca92ac5f2..f0c8fdd80cf1 100644 --- a/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.controller.js +++ b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.controller.js @@ -1,12 +1,9 @@ -import isObject from 'lodash/isObject'; import findIndex from 'lodash/findIndex'; import remove from 'lodash/remove'; import startCase from 'lodash/startCase'; import { IP_MITIGATION_RULE_PROTOCOL_PORT, - ALLOWED_LANGUAGES, - BASE_URL_SURVEY, GAME_GUIDE_LINKS, GAME_TRACKING_PREFIX, } from './ip-ip-firewall-game.constants'; @@ -79,7 +76,7 @@ export default /* @ngInject */ function IpGameFirewallCtrl( self.loading = false; - self.getProtocoleText = function getProtocoleText(protocol) { + self.getProtocolText = function getProtocolText(protocol) { return startCase(protocol); }; @@ -97,25 +94,6 @@ export default /* @ngInject */ function IpGameFirewallCtrl( self.loading = false; - function initializeUrlSurvey() { - // Get default language - const defaultLanguage = Object.keys(ALLOWED_LANGUAGES).find( - (key) => ALLOWED_LANGUAGES[key].isDefault, - ); - const userLanguage = coreConfig.getUserLanguage(); - - const languageToUse = isObject(ALLOWED_LANGUAGES[userLanguage]) - ? userLanguage - : defaultLanguage; - - // Get user - const user = coreConfig.getUser(); - - // Build url for survey link - const surveyUrl = `${BASE_URL_SURVEY}${languageToUse}&nic=${user.nichandle}`; - return surveyUrl; - } - self.getProtocoleText = function getProtocoleText(protocol) { return startCase(protocol); }; @@ -215,8 +193,6 @@ export default /* @ngInject */ function IpGameFirewallCtrl( } function init(params) { - self.surveyUrl = initializeUrlSurvey(); - self.tracking = { 'game-firewall-add-rule': `${GAME_TRACKING_PREFIX}::add-rule`, 'game-firewall-add-rule-confirm': `${GAME_TRACKING_PREFIX}::add-rule-confirm`, @@ -294,6 +270,42 @@ export default /* @ngInject */ function IpGameFirewallCtrl( }); } + function hasPortsAlreadyUsed() { + return self.table.rules.some((rule) => { + // Check if other rule has no range + if (rule.ports.from === rule.ports.to) { + // Check if new rule has no range + if (self.rule.ports.from === self.rule.ports.to) { + // Check if new rule is not already defined + if (self.rule.ports.from === rule.ports.from) { + return true; + } + } else if (IpGameFirewall.hasRuleIncludedInNewRule(self.rule, rule)) { + // Check if other rule is not included into new rule + return true; + } + } else if (self.rule.ports.from === self.rule.ports.to) { + // Check if new rule has no range + if (IpGameFirewall.hasNewRuleIncludedInRule(self.rule, rule)) { + // Check if new rule is not included into other rule + return true; + } + } else if ( + IpGameFirewall.hasNewRuleIntoRule(self.rule, rule) || + IpGameFirewall.hasNewRulePortToIntoRule(self.rule, rule) || + IpGameFirewall.hasNewRulePortFromIntoRule(self.rule, rule) || + IpGameFirewall.hasRuleIntoNewRule(self.rule, rule) + ) { + // Check if the new rule is not into other rules or + // Check if the new rule port to is not into other rules or + // Check if the new rule port from is not into other rules or + // Check if the rule is not into new rule + return true; + } + return false; + }); + } + $scope.$on('ips.gameFirewall.display.remove', (event, ruleId) => { changeStateRule(ruleId, self.constantes.DELETE_RULE_PENDING); @@ -422,6 +434,18 @@ export default /* @ngInject */ function IpGameFirewallCtrl( return; } + // Check if ports are not already used by other rules + if (hasPortsAlreadyUsed()) { + Alerter.error( + $translate.instant( + 'ip_game_mitigation_firewall_rule_add_ports_already_used', + ), + alert, + ); + self.loading = false; + return; + } + IpGameFirewall.postRule( self.datas.selectedBlock, self.datas.selectedIp, diff --git a/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.html b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.html index 03d1429ae455..9adaa1a58070 100644 --- a/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.html +++ b/packages/manager/apps/dedicated/client/app/ip/components/list/firewall/game/ip-ip-firewall-game.html @@ -35,19 +35,6 @@
- -
@@ -416,7 +403,6 @@ data-oui-tooltip-placement="left" data-ng-click="setAction('ip/firewall/rule/delete/ip-ip-firewall-rule-delete', { ipBlock: IpFirewallCtrl.selectedBlock, ip: IpFirewallCtrl.selectedIp, rule: rule ,tracking : IpFirewallCtrl.tracking['ip-firewall-delete-rule']})" data-ng-show="rule.state === 'ok'" - aria-hidden="true" > aktiviert. UDP-Datenverkehr wird nur auf definierten Regeln zugelassen.", "ip_game_mitigation_firewall_false": "Game-Regeln sind nun deaktiviert. UDP-Datenverkehr zu undefinierten Ports wird zugelassen, die definierten Regeln bleiben erhalten.", "ip_game_mitigation_firewall_firewallModeEnablePending": "Game-Regeln werden aktiviert. UDP-Datenverkehr wird nur auf definierten Regeln zugelassen.", @@ -350,13 +338,6 @@ "ip_game_mitigation_firewall_enable_info_true": "Dadurch sind nur die Spiele geschützt, die definierten Regeln entsprechen. Jeder andere Traffic kann die ausgewählte IP-Adresse ohne jeglichen Schutz erreichen. Möchten Sie fortfahren?", "ip_game_mitigation_firewall_enable_success_true": "Die Standardrichtlinie für den GAME-DDoS-Schutz wird in wenigen Augenblicken deaktiviert.", "ip_game_mitigation_firewall_enable_error_true": "Bei der Deaktivierung der Game-Regeln ist ein Fehler aufgetreten.", - "ip_game_mitigation_firewall_rule_add_invalid_parameters": "Sie müssen die Ports eingeben.", - "ip_game_mitigation_back_link_title": "IP-Adressen verwalten", - "ip_game_mitigation_guide": "Anleitungen", - "ip_game_mitigation_rule_apply": "Bestätigen", - "ip_game_mitigation_rule_cancel": "Abbrechen", - "ip_game_mitigation_like_this": "Gefällt Ihnen das?", - "ip_game_mitigation_like_this_tooltip": "Gefällt Ihnen diese Seite? Teilen Sie uns Ihre Anmerkungen mit!", "ip_firewall_fail": "Bei der Änderung der Firewall-Informationen ist ein Fehler aufgetreten", "ip_firewall_edit_rule": "Regel ändern", "ip_firewall_remove_rule": "Regel löschen", @@ -380,26 +361,12 @@ "ip_firewall_not_yet_activated_short": "Nicht konfiguriert", "ip_firewall_enable_button_title": "Aktivieren", "ip_firewall_disable_button_title": "Deaktivieren", - "ip_firewall_back_link_title": "IP-Adressen verwalten", "ip_firewall_title": "Edge-Network-Firewall-Regeln verwalten", - "ip_firewall_guide": "Anleitungen", - "ip_firewall_description_1": "Konfigurieren Sie den Edge-Schutz für Ihre IP-Adresse. Ihre Firewall-Regeln werden am Rand des OVHcloud Netzwerks angewendet, um eine Überlastung der Verbindungen zu Ihrem Dienst durch Filterung des eingehenden Traffics zu verhindern.", - "ip_firewall_description_2": "Diese Funktion sollte in Verbindung mit der Netzwerk-Firewall auf dem Server verwendet werden, um einen besseren Schutz zu gewährleisten. Es können maximal 20 Regeln pro IP definiert werden.", - "ip_firewall_description_3": "Beachten Sie, dass sich der „Status der TCP-Sitzungen“ (TCP established) auf bestimmte TCP-Protokollflags (TCP flags) bezieht, da die Edge Network Firewall keine TCP-Sitzungen nachverfolgt.", - "ip_firewall_enabled_rules": "Aktiviert", - "ip_firewall_disabled_rules": "Deaktiviert", - "ip_firewall_enabled_rules_description": "Aktivieren Sie die Firewall-Regeln für diese IP-Adresse (bei Deaktivierung bleiben die Regeln nur so lange erhalten, wie das Scrubbing Center aktiv ist). Weitere Informationen hier", - "ip_firewall_enabled_rules_more": "Mehr erfahren", "ip_firewall_add_summary": "Überprüfen Sie die gemachten Angaben, bevor Sie das Hinzufügen der Regel bestätigen.", "ip_firewall_add_title": "Regel hinzufügen", "ip_firewall_add_rule_success": "Die neue Regel wurde hinzugefügt.", "ip_firewall_add_rule_fail": "Beim Hinzufügen der Regel ist ein Fehler aufgetreten.", - "ip_firewall_close_message": "Schließen", "ip_firewall_add_rule_confirm_button_text": "Hinzufügen", - "ip_firewall_like_this": "Gefällt Ihnen das?", - "ip_firewall_like_this_tooltip": "Gefällt Ihnen diese Seite? Teilen Sie uns Ihre Anmerkungen mit!", - "ip_firewall_rule_apply": "Bestätigen", - "ip_firewall_rule_cancel": "Abbrechen", "ip_firewall_modify_title": "Regel bearbeiten", "ip_firewall_modify_rule_success": "Die Regel wurde bearbeitet.", "ip_firewall_modify_rule_fail": "Beim Bearbeiten der Regel ist ein Fehler aufgetreten.", @@ -434,23 +401,13 @@ "ip_firewall_new_question": "Sind Sie sicher, dass Sie die Firewall für die IP {{t0}} erstellen möchten?", "ip_firewall_new_success": "Die Firewall für die IP {{t0}} wird in wenigen Augenblicken erstellt.", "ip_firewall_new_failed": "Bei der Erstellung der Firewall für die IP {{t0}} ist ein Fehler aufgetreten.", - "ip_firewall_add_success": "Die Regel wurde erfolgreich erstellt!", - "ip_firewall_delete_success": "Die Regel wurde gelöscht!", - "ip_firewall_deny_part_1": "Es wurden nur „Akzeptieren“-Regeln und keine „Ablehnen“-Regeln gefunden. Daher wird kein Traffic durch diese Konfiguration blockiert. Wir empfehlen Ihnen die letzte Regel, um Ihre Konfiguration effektiv zu gestalten. Klicken Sie auf ", - "ip_firewall_deny_link": "Ablehnungsregel erstellen,", - "ip_firewall_deny_part_2": " um eine Regel hinzuzufügen.", "ip_firewall_action": "Aktion", - "ip_firewall_mode": "Modus", "ip_firewall_protocol": "Protokoll", "ip_firewall_source_ip": "Quell-IP-Adresse", - "ip_firewall_source_ip_invalid": "Die eingegebene Quell-IP-Adresse ist ungültig.", "ip_firewall_source_port": "Quell-Port", "ip_firewall_source_port_tooltip": "Der Quell-Port muss zwischen 0 und 65535 sein", - "ip_firewall_source_port_not_empty_tooltip": "Der Quell-Port muss leer sein, wenn „Fragmente“ ausgewählt ist.", "ip_firewall_destination_port": "Ziel-Port", "ip_firewall_destination_port_tooltip": "Der Ziel-Port muss zwischen 0 und 65535 sein", - "ip_firewall_destination_port_not_empty_tooltip": "Der Ziel-Port muss leer sein, wenn „Fragmente“ ausgewählt ist.", - "ip_firewall_check_errors": "Die eingegebenen Daten enthalten Fehler. Bitte überprüfen Sie die rot markierten Felder.", "ip_firewall_options": "TCP-Status", "ip_firewall_status": "Status", "ip_firewall_position": "Priorität", @@ -462,7 +419,6 @@ "ip_firewall_rule_status_removalPending": "Wird gelöscht", "ip_firewall_rule_status_OK": "Aktiv", "ip_firewall_rule_status_ok": "Aktiv", - "ip_firewall_rule_status_inactif": "Inaktiv", "ip_firewall_rule_fragments": "Fragmente", "ip_firewall_rule_fragments_tooltip": "Sie können die Fragmente-Option nicht auswählen, wenn Sie einen Quell- und/oder Ziel-Port angegeben haben.", "ip_firewall_rule_flags": "Flaggen", @@ -755,5 +711,50 @@ "ip_repricing_banner_list_item_2": "Ab dem 1. Dezember 2022 für Ihre bestehenden Adressen, die vor dem 6. Oktober 2022 bestellt wurden.", "ip_repricing_banner_link": "Mehr Informationen", "ip_unused_banner_text": "Nicht alle Ihrer IP-Adressen werden derzeit genutzt. IPv4-Adressen werden zu einer immer knapperen Ressource. Wenn Sie sie also nicht benötigen, möchten wir Sie bitten, sie freizugeben.", - "ip_unused_banner_link": "Meine nicht genutzten IPs anzeigen." -} \ No newline at end of file + "ip_unused_banner_link": "Meine nicht genutzten IPs anzeigen.", + "show_all_ips": "IPv4 und IPv6 anzeigen", + "show_ipv4_ips": "IPv4 anzeigen", + "show_ipv6_ips": "IPv6 anzeigen", + "ipv4_ipv6_filter_title": "IPv4/IPv6 Filter", + "ip_game_mitigation_description": "Dies ist die Konfigurationsseite für den GAME-DDoS-Schutz für die ausgewählte IP-Adresse. Es können mehrere Firewall-Regeln konfiguriert werden, um alle Anwendungen, die auf der ausgewählten IP-Adresse gehostet werden, bestmöglich zu schützen.", + "ip_game_mitigation_description_tip": "Tipp: Sie können als Protokoll „Anderes“ wählen, um beliebigen Datenverkehr zu einem oder mehreren spezifischen Ports zuzulassen. Wir empfehlen Ihnen, die Richtlinie „Standard-Ablehnung“ anzuwenden, die den Traffic auf allen anderen (nicht definierten) Ports unterdrückt, um einen besseren Schutz zu gewährleisten.", + "ip_game_mitigation_apply_policy": "Richtlinie „Standard-Ablehnung“ anwenden ", + "ip_game_mitigation_policy_default_help": "Blockieren Sie den gesamten Datenverkehr, der keiner der folgenden Regeln entspricht.", + "ip_game_mitigation_table_start_port": "Start-Port (Bereich)", + "ip_game_mitigation_table_end_port": "End-Port (Bereich)", + "ip_game_mitigation_rule_edit": "Regel ändern", + "ip_game_mitigation_rule_delete": "Regel löschen", + "ip_game_mitigation_firewall_rule_add_invalid_parameters": "Sie müssen die Ports eingeben.", + "ip_game_mitigation_back_link_title": "IP-Adressen verwalten", + "ip_game_mitigation_guide": "Anleitungen", + "ip_game_mitigation_rule_apply": "Bestätigen", + "ip_game_mitigation_rule_cancel": "Abbrechen", + "ip_game_mitigation_like_this": "Gefällt Ihnen das?", + "ip_game_mitigation_like_this_tooltip": "Gefällt Ihnen diese Seite? Teilen Sie uns Ihre Anmerkungen mit!", + "ip_firewall_back_link_title": "IP-Adressen verwalten", + "ip_firewall_guide": "Anleitungen", + "ip_firewall_description_1": "Konfigurieren Sie den Edge-Schutz für Ihre IP-Adresse. Ihre Firewall-Regeln werden am Rand des OVHcloud Netzwerks angewendet, um eine Überlastung der Verbindungen zu Ihrem Dienst durch Filterung des eingehenden Traffics zu verhindern.", + "ip_firewall_description_2": "Diese Funktion sollte in Verbindung mit der Netzwerk-Firewall auf dem Server verwendet werden, um einen besseren Schutz zu gewährleisten. Es können maximal 20 Regeln pro IP definiert werden.", + "ip_firewall_description_3": "Beachten Sie, dass sich der „Status der TCP-Sitzungen“ (TCP established) auf bestimmte TCP-Protokollflags (TCP flags) bezieht, da die Edge Network Firewall keine TCP-Sitzungen nachverfolgt.", + "ip_firewall_enabled_rules": "Aktiviert", + "ip_firewall_disabled_rules": "Deaktiviert", + "ip_firewall_enabled_rules_description": "Aktivieren Sie die Firewall-Regeln für diese IP-Adresse (bei Deaktivierung bleiben die Regeln nur so lange erhalten, wie das Scrubbing Center aktiv ist). Weitere Informationen hier", + "ip_firewall_enabled_rules_more": "Mehr erfahren", + "ip_firewall_close_message": "Schließen", + "ip_firewall_like_this": "Gefällt Ihnen das?", + "ip_firewall_like_this_tooltip": "Gefällt Ihnen diese Seite? Teilen Sie uns Ihre Anmerkungen mit!", + "ip_firewall_rule_apply": "Bestätigen", + "ip_firewall_rule_cancel": "Abbrechen", + "ip_firewall_add_success": "Die Regel wurde erfolgreich erstellt!", + "ip_firewall_delete_success": "Die Regel wurde gelöscht!", + "ip_firewall_deny_part_1": "Es wurden nur „Akzeptieren“-Regeln und keine „Ablehnen“-Regeln gefunden. Daher wird kein Traffic durch diese Konfiguration blockiert. Wir empfehlen Ihnen die letzte Regel, um Ihre Konfiguration effektiv zu gestalten. Klicken Sie auf ", + "ip_firewall_deny_link": "Ablehnungsregel erstellen,", + "ip_firewall_deny_part_2": " um eine Regel hinzuzufügen.", + "ip_firewall_mode": "Modus", + "ip_firewall_source_ip_invalid": "Die eingegebene Quell-IP-Adresse ist ungültig.", + "ip_firewall_source_port_not_empty_tooltip": "Der Quell-Port muss leer sein, wenn „Fragmente“ ausgewählt ist.", + "ip_firewall_destination_port_not_empty_tooltip": "Der Ziel-Port muss leer sein, wenn „Fragmente“ ausgewählt ist.", + "ip_firewall_check_errors": "Die eingegebenen Daten enthalten Fehler. Bitte überprüfen Sie die rot markierten Felder.", + "ip_firewall_rule_status_inactif": "Inaktiv", + "ip_game_mitigation_firewall_rule_add_ports_already_used": "Der Port (oder Portbereich) steht mit einer anderen Regel in Konflikt." +} diff --git a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_en_GB.json b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_en_GB.json index 7c2a7968765d..7f68590d98d4 100644 --- a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_en_GB.json +++ b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_en_GB.json @@ -12,10 +12,6 @@ "ip_ipv4": "IPv4", "ip_ipv6": "IPv6", "ip_ipblock": "IP block", - "show_all_ips": "Show IPv4 and IPv6", - "show_ipv4_ips": "Show IPv4", - "show_ipv6_ips": "Show IPv6", - "ipv4_ipv6_filter_title": "Filter IPv4/IPv6", "ip_taskpending_label": "Ongoing task ", "optional": "Optional", "ip_required_field": "required field", @@ -305,13 +301,7 @@ "ip_game_mitigation_ACTIVATED": "Available", "ip_game_mitigation_ACTIVATED_help": "The Anti-DDoS Game protection option is available for this service.", "ip_game_mitigation_title": "Configure GAME firewall", - "ip_game_mitigation_description": "This is the page for configuring GAME DDoS protection for the selected IP. Multiple firewall rules can be configured to better protect all the applications hosted on the selected IP.", - "ip_game_mitigation_description_tip": "Tip: You can choose “Other” protocol to allow any kind of traffic flow to one or more specific ports. We suggest applying the “Default Deny” policy, which will block all other (unspecified) ports, for enhanced security.", - "ip_game_mitigation_apply_policy": "Apply “Default Deny” policy ", - "ip_game_mitigation_policy_default_help": "Block all traffic that does not meet any of the following rules.", "ip_game_mitigation_table_protocol": "Game protocol", - "ip_game_mitigation_table_start_port": "Start port (range)", - "ip_game_mitigation_table_end_port": "End port (range)", "ip_game_mitigation_table_state": "Status", "ip_game_mitigation_table_error": "GAME firewall rules cannot be retrieved.", "ip_game_mitigation_table_partial_error": "An error occurred when retrieving the rules.", @@ -334,8 +324,6 @@ "ip_game_mitigation_rule_add_port_pattern": "The port must be a whole number greater than zero.", "ip_game_mitigation_rule_add_port_to": "up to port:", "ip_game_mitigation_rule_add_init_error": "An error occurred. The protocol list cannot be retrieved.", - "ip_game_mitigation_rule_edit": "Modify the rule ", - "ip_game_mitigation_rule_delete": "Delete the rule", "ip_game_mitigation_firewall_true": "GAME restriction will be activated. UDP traffic will be authorised on defined rules only.", "ip_game_mitigation_firewall_false": "GAME restriction is now deactivated/. UDP traffic towards undefined ports will be authorised, but defined rules will still apply.", "ip_game_mitigation_firewall_firewallModeEnablePending": "GAME restriction will be activated. UDP traffic will be authorised on defined rules only.", @@ -350,13 +338,6 @@ "ip_game_mitigation_firewall_enable_info_true": "In doing this, the only protected sets will be those that meet defined rules. All other traffic can reach the selected IP without being protected. Do you want to continue?", "ip_game_mitigation_firewall_enable_success_true": "The default GAME DDoS protection policy will be disabled in a few minutes.", "ip_game_mitigation_firewall_enable_error_true": "An error occurred when deactivating GAME restriction mode.", - "ip_game_mitigation_firewall_rule_add_invalid_parameters": "You need to select a port.", - "ip_game_mitigation_back_link_title": "Manage IPs", - "ip_game_mitigation_guide": "Guides", - "ip_game_mitigation_rule_apply": "Validate", - "ip_game_mitigation_rule_cancel": "Cancel", - "ip_game_mitigation_like_this": "Like it?", - "ip_game_mitigation_like_this_tooltip": "Like this page? Send us your feedback!", "ip_firewall_fail": "An error has occurred loading the firewall information", "ip_firewall_edit_rule": "Modify the rule ", "ip_firewall_remove_rule": "Delete the rule", @@ -380,26 +361,12 @@ "ip_firewall_not_yet_activated_short": "Not configured", "ip_firewall_enable_button_title": "Enable", "ip_firewall_disable_button_title": "Disable", - "ip_firewall_back_link_title": "Manage IPs", "ip_firewall_title": "Manage Edge Network Firewall rules", - "ip_firewall_guide": "Guides", - "ip_firewall_description_1": "Configure edge protection for your IP. Your firewall rules will be applied at the edge of the OVHcloud network, which filters inbound traffic to prevent links to your service from getting saturated.", - "ip_firewall_description_2": "It is recommended, for added security, to pair this feature with your server’s network firewall. Only 20 rules can be defined per IP.", - "ip_firewall_description_3": "Please note that “TCP session status” (TCP established) refers to specific TCP protocol flags, as the Edge Network Firewall does not track TCP sessions.", - "ip_firewall_enabled_rules": "Enabled", - "ip_firewall_disabled_rules": "Disabled", - "ip_firewall_enabled_rules_description": "Enable firewall rules for this IP (disabling will result in the rules being kept only when the Scrubbing Centre is active). Find out more here.", - "ip_firewall_enabled_rules_more": "Find out more", "ip_firewall_add_summary": "Please check the information entered before you confirm the adding of the rule.", "ip_firewall_add_title": "Add a rule", "ip_firewall_add_rule_success": "The new rule has been added.", "ip_firewall_add_rule_fail": "An error has occurred adding the rule.", - "ip_firewall_close_message": "Close", "ip_firewall_add_rule_confirm_button_text": "Add", - "ip_firewall_like_this": "Like it?", - "ip_firewall_like_this_tooltip": "Like this page? Send us your feedback!", - "ip_firewall_rule_apply": "Validate", - "ip_firewall_rule_cancel": "Cancel", "ip_firewall_modify_title": "Modify a rule", "ip_firewall_modify_rule_success": "The rule has been modified.", "ip_firewall_modify_rule_fail": "An error has occurred modifying the rule. ", @@ -434,23 +401,13 @@ "ip_firewall_new_question": "Are you sure you want to create the firewall on the {{t0}} IP?", "ip_firewall_new_success": "The firewall will be created in a few moments on the {{t0}} IP.", "ip_firewall_new_failed": "An error has occurred creating the firewall on the {{t0}} IP.", - "ip_firewall_add_success": "The rule has been created!", - "ip_firewall_delete_success": "The rule has been deleted!", - "ip_firewall_deny_part_1": "We have detected only “Accept” rules and no “Deny” rules, so no traffic will be blocked by this configuration. We recommend the last rule for effective configuration. Click here ", - "ip_firewall_deny_link": "create Deny rule", - "ip_firewall_deny_part_2": " to add a rule.", "ip_firewall_action": "Action", - "ip_firewall_mode": "Mode", "ip_firewall_protocol": "Protocol", "ip_firewall_source_ip": "Source IP", - "ip_firewall_source_ip_invalid": "The source IP entered is invalid.", "ip_firewall_source_port": "Source port", "ip_firewall_source_port_tooltip": "The source port must be between 0 and 65535.", - "ip_firewall_source_port_not_empty_tooltip": "The source port must be empty when “Fragments” is selected.", "ip_firewall_destination_port": "Destination port", "ip_firewall_destination_port_tooltip": "The destination port must be between 0 and 65535.", - "ip_firewall_destination_port_not_empty_tooltip": "The destination port must be empty when “Fragments” is selected.", - "ip_firewall_check_errors": "There are errors in the data entered, please check the fields in red.", "ip_firewall_options": "TCP status", "ip_firewall_status": "Status", "ip_firewall_position": "Priority", @@ -462,7 +419,6 @@ "ip_firewall_rule_status_removalPending": "Deleting", "ip_firewall_rule_status_OK": "Active", "ip_firewall_rule_status_ok": "Active", - "ip_firewall_rule_status_inactif": "Disabled", "ip_firewall_rule_fragments": "Fragments", "ip_firewall_rule_fragments_tooltip": "You cannot select the fragment option if you have defined a source port and/or destination port.", "ip_firewall_rule_flags": "Flags", @@ -755,5 +711,50 @@ "ip_repricing_banner_list_item_2": "For IPs ordered before 06 October 2022, the change will come into effect from 01 December 2022 onwards.", "ip_repricing_banner_link": "More information", "ip_unused_banner_text": "You have unused IP addresses. Since IPv4 addresses are becoming increasingly scarce as a resource, please release them if you do not need them.", - "ip_unused_banner_link": "View unused IPs." -} \ No newline at end of file + "ip_unused_banner_link": "View unused IPs.", + "show_all_ips": "Show IPv4 and IPv6", + "show_ipv4_ips": "Show IPv4", + "show_ipv6_ips": "Show IPv6", + "ipv4_ipv6_filter_title": "Filter IPv4/IPv6", + "ip_game_mitigation_description": "This is the page for configuring GAME DDoS protection for the selected IP. Multiple firewall rules can be configured to better protect all the applications hosted on the selected IP.", + "ip_game_mitigation_description_tip": "Tip: You can choose “Other” protocol to allow any kind of traffic flow to one or more specific ports. We suggest applying the “Default Deny” policy, which will block all other (unspecified) ports, for enhanced security.", + "ip_game_mitigation_apply_policy": "Apply “Default Deny” policy ", + "ip_game_mitigation_policy_default_help": "Block all traffic that does not meet any of the following rules.", + "ip_game_mitigation_table_start_port": "Start port (range)", + "ip_game_mitigation_table_end_port": "End port (range)", + "ip_game_mitigation_rule_edit": "Modify the rule ", + "ip_game_mitigation_rule_delete": "Delete the rule", + "ip_game_mitigation_firewall_rule_add_invalid_parameters": "You need to select a port.", + "ip_game_mitigation_back_link_title": "Manage IPs", + "ip_game_mitigation_guide": "Guides", + "ip_game_mitigation_rule_apply": "Validate", + "ip_game_mitigation_rule_cancel": "Cancel", + "ip_game_mitigation_like_this": "Like it?", + "ip_game_mitigation_like_this_tooltip": "Like this page? Send us your feedback!", + "ip_firewall_back_link_title": "Manage IPs", + "ip_firewall_guide": "Guides", + "ip_firewall_description_1": "Configure edge protection for your IP. Your firewall rules will be applied at the edge of the OVHcloud network, which filters inbound traffic to prevent links to your service from getting saturated.", + "ip_firewall_description_2": "It is recommended, for added security, to pair this feature with your server’s network firewall. Only 20 rules can be defined per IP.", + "ip_firewall_description_3": "Please note that “TCP session status” (TCP established) refers to specific TCP protocol flags, as the Edge Network Firewall does not track TCP sessions.", + "ip_firewall_enabled_rules": "Enabled", + "ip_firewall_disabled_rules": "Disabled", + "ip_firewall_enabled_rules_description": "Enable firewall rules for this IP (disabling will result in the rules being kept only when the Scrubbing Centre is active). Find out more here.", + "ip_firewall_enabled_rules_more": "Find out more", + "ip_firewall_close_message": "Close", + "ip_firewall_like_this": "Like it?", + "ip_firewall_like_this_tooltip": "Like this page? Send us your feedback!", + "ip_firewall_rule_apply": "Validate", + "ip_firewall_rule_cancel": "Cancel", + "ip_firewall_add_success": "The rule has been created!", + "ip_firewall_delete_success": "The rule has been deleted!", + "ip_firewall_deny_part_1": "We have detected only “Accept” rules and no “Deny” rules, so no traffic will be blocked by this configuration. We recommend the last rule for effective configuration. Click here ", + "ip_firewall_deny_link": "create Deny rule", + "ip_firewall_deny_part_2": " to add a rule.", + "ip_firewall_mode": "Mode", + "ip_firewall_source_ip_invalid": "The source IP entered is invalid.", + "ip_firewall_source_port_not_empty_tooltip": "The source port must be empty when “Fragments” is selected.", + "ip_firewall_destination_port_not_empty_tooltip": "The destination port must be empty when “Fragments” is selected.", + "ip_firewall_check_errors": "There are errors in the data entered, please check the fields in red.", + "ip_firewall_rule_status_inactif": "Disabled", + "ip_game_mitigation_firewall_rule_add_ports_already_used": "The port (or port range) conflicts with another rule." +} diff --git a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_es_ES.json b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_es_ES.json index 079b4c000993..be23e7a5c3f5 100644 --- a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_es_ES.json +++ b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_es_ES.json @@ -12,10 +12,6 @@ "ip_ipv4": "IPv4", "ip_ipv6": "IPv6", "ip_ipblock": "Bloque de IP", - "show_all_ips": "Mostrar las IPv4 e IPv6", - "show_ipv4_ips": "Mostrar las IPv4", - "show_ipv6_ips": "Mostrar las IPv6", - "ipv4_ipv6_filter_title": "Filtro IPv4/IPv6", "ip_taskpending_label": "Tarea en curso", "optional": "Opcional", "ip_required_field": "Campo obligatorio", @@ -305,13 +301,7 @@ "ip_game_mitigation_ACTIVATED": "Disponible", "ip_game_mitigation_ACTIVATED_help": "La opción de protección anti-DDoS Game está disponible para este servicio.", "ip_game_mitigation_title": "Configurar el firewall Game", - "ip_game_mitigation_description": "Esta es la página de configuración de la protección DDoS Game para la dirección IP seleccionada. Es posible configurar varias reglas de firewall para proteger mejor todas las aplicaciones alojadas en la dirección IP seleccionada.", - "ip_game_mitigation_description_tip": "Consejo: puede elegir otro protocolo para autorizar el tráfico arbitrario hacia uno o varios puertos específicos. La recomendamos que aplique la política de «Denegación por omisión», que eliminará el tráfico en el resto de puertos (no definidos) para una mejor protección.", - "ip_game_mitigation_apply_policy": "Aplicar la política de «Denegación por omisión» ", - "ip_game_mitigation_policy_default_help": "Bloquee todo el tráfico que no se ajuste a ninguna de las reglas siguientes.", "ip_game_mitigation_table_protocol": "Protocolo", - "ip_game_mitigation_table_start_port": "Puerto de arranque (rango)", - "ip_game_mitigation_table_end_port": "Puerto final (rango)", "ip_game_mitigation_table_state": "Estado", "ip_game_mitigation_table_error": "No se han podido cargar las reglas del firewall Game.", "ip_game_mitigation_table_partial_error": "Se ha producido un error al cargar las reglas.", @@ -334,8 +324,6 @@ "ip_game_mitigation_rule_add_port_pattern": "El puerto debe ser un número entero positivo.", "ip_game_mitigation_rule_add_port_to": "hasta el puerto:", "ip_game_mitigation_rule_add_init_error": "Se ha producido un error. No se ha podido cargar la lita de protocolos.", - "ip_game_mitigation_rule_edit": "Modificar la regla", - "ip_game_mitigation_rule_delete": "Eliminar la regla", "ip_game_mitigation_firewall_true": "La restricción «Game» está ahora activada. Solo se permite el tráfico UDP según las reglas establecidas.", "ip_game_mitigation_firewall_false": "La restricción «Game» está ahora desactivada. Se permite el tráfico UDP hacia los puertos no determinados, pero se siguen aplicando las reglas establecidas.", "ip_game_mitigation_firewall_firewallModeEnablePending": "La restricción «Game» va a activarse. Solo se permitirá el tráfico UDP según las reglas establecidas.", @@ -350,13 +338,6 @@ "ip_game_mitigation_firewall_enable_info_true": "Si selecciona esta opción, solo se protegerán los juegos que cumplan con las reglas definidas. El resto del tráfico podrá alcanzar la IP seleccionada sin ningún tipo de protección. ¿Seguro/a que quiere continuar?", "ip_game_mitigation_firewall_enable_success_true": "La política de protección DDoS Game por defecto se desactivará en unos instantes.", "ip_game_mitigation_firewall_enable_error_true": "Se ha producido un error al desactivar el modo de restricción «Game».", - "ip_game_mitigation_firewall_rule_add_invalid_parameters": "Es obligatorio introducir los puertos.", - "ip_game_mitigation_back_link_title": "Gestionar las direcciones IP", - "ip_game_mitigation_guide": "Guías", - "ip_game_mitigation_rule_apply": "Confirmar", - "ip_game_mitigation_rule_cancel": "Cancelar", - "ip_game_mitigation_like_this": "¿Le gusta?", - "ip_game_mitigation_like_this_tooltip": "¿Le gusta esta página? ¡Envíenos sus comentarios!", "ip_firewall_fail": "Se ha producido un error al cargar la información del firewall.", "ip_firewall_edit_rule": "Editar la regla", "ip_firewall_remove_rule": "Eliminar la regla", @@ -380,26 +361,12 @@ "ip_firewall_not_yet_activated_short": "No configurado", "ip_firewall_enable_button_title": "Activar", "ip_firewall_disable_button_title": "Desactivar", - "ip_firewall_back_link_title": "Gestionar las direcciones IP", "ip_firewall_title": "Administrar las reglas de Edge Network Firewall", - "ip_firewall_guide": "Guías", - "ip_firewall_description_1": "Configure la protección Edge de su dirección IP. Las reglas de firewall se aplicarán en la periferia de la red de OVHcloud para evitar la saturación de los enlaces hacia su servicio filtrando el tráfico entrante.", - "ip_firewall_description_2": "Esta función debe utilizarse en combinación con el firewall de red en su servidor para una protección óptima. Puede definir un máximo de 20 reglas por dirección IP.", - "ip_firewall_description_3": "Tenga en cuenta que el «estado de las sesiones TCP» («TCP established») hace referencia a los indicadores de protocolo TCP («TCP flags») específicos, ya que el Edge Network Firewall no rastrea las sesiones TCP.", - "ip_firewall_enabled_rules": "Activado", - "ip_firewall_disabled_rules": "Desactivado", - "ip_firewall_enabled_rules_description": "Active las reglas de firewall para esta dirección IP. Si las desactiva, las reglas solo se mantendrán durante el tiempo en el que el Scrubbing Center permanezca activo. Más información aquí", - "ip_firewall_enabled_rules_more": "Más información", "ip_firewall_add_summary": "Compruebe que la información introducida es correcta antes de confirmar la creación de la regla.", "ip_firewall_add_title": "Añadir una regla", "ip_firewall_add_rule_success": "Se ha añadido la nueva regla.", "ip_firewall_add_rule_fail": "Se ha producido un error al añadir la regla.", - "ip_firewall_close_message": "Cerrar", "ip_firewall_add_rule_confirm_button_text": "Añadir", - "ip_firewall_like_this": "¿Le gusta?", - "ip_firewall_like_this_tooltip": "¿Le gusta esta página? ¡Envíenos sus comentarios!", - "ip_firewall_rule_apply": "Confirmar", - "ip_firewall_rule_cancel": "Cancelar", "ip_firewall_modify_title": "Modificar una regla", "ip_firewall_modify_rule_success": "Se ha modificado la regla.", "ip_firewall_modify_rule_fail": "Se ha producido un error al editar la regla.", @@ -434,23 +401,13 @@ "ip_firewall_new_question": "¿Seguro que quiere activar la creación del firewall en la IP {{t0}}?", "ip_firewall_new_success": "El firewall va a crearse en la IP {{t0}}.", "ip_firewall_new_failed": "Se ha producido un error al crear el firewall en la IP {{t0}}.", - "ip_firewall_add_success": "La regla se ha creado correctamente.", - "ip_firewall_delete_success": "La regla se ha eliminado correctamente.", - "ip_firewall_deny_part_1": "Solo se han detectado reglas de tipo «Aceptar» y ninguna regla de tipo «Denegar», por lo que esta configuración no bloqueará ningún tráfico. Le recomendamos la última regla para que su configuración sea eficaz. Haga clic aquí ", - "ip_firewall_deny_link": "crear una regla de denegación", - "ip_firewall_deny_part_2": " para añadir la regla.", "ip_firewall_action": "Acción", - "ip_firewall_mode": "Modo", "ip_firewall_protocol": "Protocolo", "ip_firewall_source_ip": "Dirección IP de origen", - "ip_firewall_source_ip_invalid": "La dirección IP de origen introducida no es válida.", "ip_firewall_source_port": "Puerto de origen", "ip_firewall_source_port_tooltip": "El puerto de origen debe estar comprendido entre 0 y 65535.", - "ip_firewall_source_port_not_empty_tooltip": "El puerto de origen debe estar vacío cuando se selecciona la opción «Fragmentos».", "ip_firewall_destination_port": "Puerto de destino", "ip_firewall_destination_port_tooltip": "El puerto de destino debe estar comprendido entre 0 y 65535.", - "ip_firewall_destination_port_not_empty_tooltip": "El puerto de destino debe estar vacío cuando se selecciona la opción «Fragmentos».", - "ip_firewall_check_errors": "Hay errores en los datos introducidos. Por favor, compruebe los campos marcados en rojo.", "ip_firewall_options": "Estado TCP", "ip_firewall_status": "Estado", "ip_firewall_position": "Prioridad", @@ -462,7 +419,6 @@ "ip_firewall_rule_status_removalPending": "Eliminando", "ip_firewall_rule_status_OK": "Activo", "ip_firewall_rule_status_ok": "Activo", - "ip_firewall_rule_status_inactif": "Inactivo", "ip_firewall_rule_fragments": "Fragmentos", "ip_firewall_rule_fragments_tooltip": "No puede elegir la opción de fragmentación habiendo establecido un puerto de origen y/o de destino.", "ip_firewall_rule_flags": "Banderas", @@ -755,5 +711,50 @@ "ip_repricing_banner_list_item_2": "A partir del 1 de diciembre de 2022 para las direcciones existentes (contratadas antes del 6 de octubre de 2022).", "ip_repricing_banner_link": "Más información", "ip_unused_banner_text": "Tiene direcciones IP no utilizadas. Las direcciones IPv4 son un recurso cada vez más escaso, por lo que, si no las necesita, le recomendamos que las libere.", - "ip_unused_banner_link": "Ver mis direcciones IP no utilizadas." -} \ No newline at end of file + "ip_unused_banner_link": "Ver mis direcciones IP no utilizadas.", + "show_all_ips": "Mostrar las IPv4 e IPv6", + "show_ipv4_ips": "Mostrar las IPv4", + "show_ipv6_ips": "Mostrar las IPv6", + "ipv4_ipv6_filter_title": "Filtro IPv4/IPv6", + "ip_game_mitigation_description": "Esta es la página de configuración de la protección DDoS Game para la dirección IP seleccionada. Es posible configurar varias reglas de firewall para proteger mejor todas las aplicaciones alojadas en la dirección IP seleccionada.", + "ip_game_mitigation_description_tip": "Consejo: puede elegir otro protocolo para autorizar el tráfico arbitrario hacia uno o varios puertos específicos. La recomendamos que aplique la política de «Denegación por omisión», que eliminará el tráfico en el resto de puertos (no definidos) para una mejor protección.", + "ip_game_mitigation_apply_policy": "Aplicar la política de «Denegación por omisión» ", + "ip_game_mitigation_policy_default_help": "Bloquee todo el tráfico que no se ajuste a ninguna de las reglas siguientes.", + "ip_game_mitigation_table_start_port": "Puerto de arranque (rango)", + "ip_game_mitigation_table_end_port": "Puerto final (rango)", + "ip_game_mitigation_rule_edit": "Modificar la regla", + "ip_game_mitigation_rule_delete": "Eliminar la regla", + "ip_game_mitigation_firewall_rule_add_invalid_parameters": "Es obligatorio introducir los puertos.", + "ip_game_mitigation_back_link_title": "Gestionar las direcciones IP", + "ip_game_mitigation_guide": "Guías", + "ip_game_mitigation_rule_apply": "Confirmar", + "ip_game_mitigation_rule_cancel": "Cancelar", + "ip_game_mitigation_like_this": "¿Le gusta?", + "ip_game_mitigation_like_this_tooltip": "¿Le gusta esta página? ¡Envíenos sus comentarios!", + "ip_firewall_back_link_title": "Gestionar las direcciones IP", + "ip_firewall_guide": "Guías", + "ip_firewall_description_1": "Configure la protección Edge de su dirección IP. Las reglas de firewall se aplicarán en la periferia de la red de OVHcloud para evitar la saturación de los enlaces hacia su servicio filtrando el tráfico entrante.", + "ip_firewall_description_2": "Esta función debe utilizarse en combinación con el firewall de red en su servidor para una protección óptima. Puede definir un máximo de 20 reglas por dirección IP.", + "ip_firewall_description_3": "Tenga en cuenta que el «estado de las sesiones TCP» («TCP established») hace referencia a los indicadores de protocolo TCP («TCP flags») específicos, ya que el Edge Network Firewall no rastrea las sesiones TCP.", + "ip_firewall_enabled_rules": "Activado", + "ip_firewall_disabled_rules": "Desactivado", + "ip_firewall_enabled_rules_description": "Active las reglas de firewall para esta dirección IP. Si las desactiva, las reglas solo se mantendrán durante el tiempo en el que el Scrubbing Center permanezca activo. Más información aquí", + "ip_firewall_enabled_rules_more": "Más información", + "ip_firewall_close_message": "Cerrar", + "ip_firewall_like_this": "¿Le gusta?", + "ip_firewall_like_this_tooltip": "¿Le gusta esta página? ¡Envíenos sus comentarios!", + "ip_firewall_rule_apply": "Confirmar", + "ip_firewall_rule_cancel": "Cancelar", + "ip_firewall_add_success": "La regla se ha creado correctamente.", + "ip_firewall_delete_success": "La regla se ha eliminado correctamente.", + "ip_firewall_deny_part_1": "Solo se han detectado reglas de tipo «Aceptar» y ninguna regla de tipo «Denegar», por lo que esta configuración no bloqueará ningún tráfico. Le recomendamos la última regla para que su configuración sea eficaz. Haga clic aquí ", + "ip_firewall_deny_link": "crear una regla de denegación", + "ip_firewall_deny_part_2": " para añadir la regla.", + "ip_firewall_mode": "Modo", + "ip_firewall_source_ip_invalid": "La dirección IP de origen introducida no es válida.", + "ip_firewall_source_port_not_empty_tooltip": "El puerto de origen debe estar vacío cuando se selecciona la opción «Fragmentos».", + "ip_firewall_destination_port_not_empty_tooltip": "El puerto de destino debe estar vacío cuando se selecciona la opción «Fragmentos».", + "ip_firewall_check_errors": "Hay errores en los datos introducidos. Por favor, compruebe los campos marcados en rojo.", + "ip_firewall_rule_status_inactif": "Inactivo", + "ip_game_mitigation_firewall_rule_add_ports_already_used": "El puerto (o el rango de puertos) entra(n) en conflicto con otra regla." +} diff --git a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_fr_CA.json b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_fr_CA.json index 7d433544740e..29935e7b3f22 100644 --- a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_fr_CA.json +++ b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_fr_CA.json @@ -351,6 +351,7 @@ "ip_game_mitigation_firewall_enable_success_true": "La politique par défaut de protection DDoS du GAME va être désactivée dans quelques instants.", "ip_game_mitigation_firewall_enable_error_true": "Une erreur est survenue lors de la désactivation du mode restriction GAME.", "ip_game_mitigation_firewall_rule_add_invalid_parameters": "La saisie des ports est obligatoire.", + "ip_game_mitigation_firewall_rule_add_ports_already_used": "Le port (ou la plage de ports) est en conflit avec une autre règle.", "ip_game_mitigation_back_link_title": "Gérer les IPs", "ip_game_mitigation_guide": "Guides", "ip_game_mitigation_rule_apply": "Valider", diff --git a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_fr_FR.json b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_fr_FR.json index 7d433544740e..41e13c533e21 100644 --- a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_fr_FR.json +++ b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_fr_FR.json @@ -351,12 +351,11 @@ "ip_game_mitigation_firewall_enable_success_true": "La politique par défaut de protection DDoS du GAME va être désactivée dans quelques instants.", "ip_game_mitigation_firewall_enable_error_true": "Une erreur est survenue lors de la désactivation du mode restriction GAME.", "ip_game_mitigation_firewall_rule_add_invalid_parameters": "La saisie des ports est obligatoire.", + "ip_game_mitigation_firewall_rule_add_ports_already_used": "Le port (ou la plage de ports) est en conflit avec une autre règle.", "ip_game_mitigation_back_link_title": "Gérer les IPs", "ip_game_mitigation_guide": "Guides", "ip_game_mitigation_rule_apply": "Valider", "ip_game_mitigation_rule_cancel": "Annuler", - "ip_game_mitigation_like_this": "Vous aimez ?", - "ip_game_mitigation_like_this_tooltip": "Vous aimez cette page ? Faites nous part de vos remarques !", "ip_firewall_fail": "Une erreur est survenue lors du chargement des informations du firewall", "ip_firewall_edit_rule": "Modifier la règle", "ip_firewall_remove_rule": "Supprimer la règle", @@ -396,8 +395,6 @@ "ip_firewall_add_rule_fail": "Une erreur est survenue lors de l'ajout de la règle.", "ip_firewall_close_message": "Fermer", "ip_firewall_add_rule_confirm_button_text": "Ajouter", - "ip_firewall_like_this": "Vous aimez ?", - "ip_firewall_like_this_tooltip": "Vous aimez cette page ? Faites nous part de vos remarques !", "ip_firewall_rule_apply": "Valider", "ip_firewall_rule_cancel": "Annuler", "ip_firewall_modify_title": "Modifier une règle", diff --git a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_it_IT.json b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_it_IT.json index 744ce11448ba..6fc651d8be6e 100644 --- a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_it_IT.json +++ b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_it_IT.json @@ -12,10 +12,6 @@ "ip_ipv4": "IPv4", "ip_ipv6": "IPv6", "ip_ipblock": "Blocco IP", - "show_all_ips": "Mostrare gli IPv4 e IPv6", - "show_ipv4_ips": "Mostrare gli IPv4", - "show_ipv6_ips": "Mostrare gli IPv6", - "ipv4_ipv6_filter_title": "Filtro IPv4/IPv6", "ip_taskpending_label": "Operazione in corso", "optional": "Opzionale", "ip_required_field": "campo obbligatorio ", @@ -129,7 +125,6 @@ "ip_table_header_ip_address_invalid": "Inserisci un IPv6 valido", "ip_table_header_country": "Paese", "ip_table_header_country_help": "Paese di provenienza dell'indirizzo IP. Disponibile esclusivamente per gli IP geolocalizzati (Additional IP).", - "ip_table_header_campus": "Campus", "ip_table_header_campus_help": "Il campus definisce la localizzazione dell'indirizzo IP a cui è associato il servizio. Nel caso degli Additional IP, il campus definisce anche la localizzazione dei servizi su cui può essere trasferito l'indirizzo IP.", "ip_table_header_reverse": "Reverse DNS", "ip_table_header_reverse_help": "Record DNS che permette la risoluzione inversa (indirizzo IP verso hostname).", @@ -305,13 +300,7 @@ "ip_game_mitigation_ACTIVATED": "Disponibile", "ip_game_mitigation_ACTIVATED_help": "L'opzione di protezione anti-DDoS Game è disponibile per questo servizio.", "ip_game_mitigation_title": "Configurare il Game Firewall", - "ip_game_mitigation_description": "Questa è la pagina di configurazione della protezione DDoS Game per l’indirizzo IP selezionato. È possibile configurare più regole firewall per proteggere al meglio tutte le applicazioni ospitate sull'indirizzo IP selezionato.", - "ip_game_mitigation_description_tip": "Suggerimento: è possibile scegliere \"altro\" protocollo per autorizzare il traffico arbitrario verso una o più porte specifiche. Consigliamo di applicare la politica predefinita \"Nega tutto\", che rimuoverà il traffico su tutte le altre porte (non definite) per una migliore protezione.", - "ip_game_mitigation_apply_policy": "Applicare la strategia predefinita \"Nega tutto\" ", - "ip_game_mitigation_policy_default_help": "Blocca tutto il traffico che non risponde a nessuna delle regole seguenti.", "ip_game_mitigation_table_protocol": "Protocollo di gioco", - "ip_game_mitigation_table_start_port": "Porta iniziale (intervallo)", - "ip_game_mitigation_table_end_port": "Porta finale (intervallo)", "ip_game_mitigation_table_state": "Stato", "ip_game_mitigation_table_error": "Impossibile recuperare le regole del Game Firewall.", "ip_game_mitigation_table_partial_error": "Errore durante il recupero della regola.", @@ -334,8 +323,6 @@ "ip_game_mitigation_rule_add_port_pattern": "La porta deve essere un numero intero positivo.", "ip_game_mitigation_rule_add_port_to": "fino alla porta:", "ip_game_mitigation_rule_add_init_error": "Errore: impossibile recuperare elenco dei protocolli.", - "ip_game_mitigation_rule_edit": "Modifica la regola", - "ip_game_mitigation_rule_delete": "Cancella la regola", "ip_game_mitigation_firewall_true": "La modalità restriction GAME è stata attivata. Il traffico in UDP è consentito solo per le regole definite", "ip_game_mitigation_firewall_false": "La restrizione GAME è stata disattivata. Il traffico UDP verso le porte non definite è consentito ma le regole definite sono ancora valide", "ip_game_mitigation_firewall_firewallModeEnablePending": "La modalità restriction GAME verrà attivata. Il traffico in UDP sarà consentito solo per le regole definite", @@ -350,13 +337,6 @@ "ip_game_mitigation_firewall_enable_info_true": "In questo modo, i giochi protetti saranno solo quelli che rispondono alle regole definite. Il resto del traffico potrà raggiungere l'IP selezionato senza nessuna protezione. Vuoi continuare?", "ip_game_mitigation_firewall_enable_success_true": "La politica predefinita di protezione DDoS Game verrà disattivata tra pochi minuti.", "ip_game_mitigation_firewall_enable_error_true": "Errore durante la disattivazione della modalità restriction GAME.", - "ip_game_mitigation_firewall_rule_add_invalid_parameters": "Inserire le porte è obbligatorio.", - "ip_game_mitigation_back_link_title": "Gestisci gli indirizzi IP", - "ip_game_mitigation_guide": "Guide", - "ip_game_mitigation_rule_apply": "Confermare", - "ip_game_mitigation_rule_cancel": "Annullare", - "ip_game_mitigation_like_this": "Ti piace?", - "ip_game_mitigation_like_this_tooltip": "Ti piace questa pagina? Condividi con noi i tuoi commenti!", "ip_firewall_fail": "Si è verificato un errore durante il caricamento delle informazioni del firewall", "ip_firewall_edit_rule": "Modifica la regola", "ip_firewall_remove_rule": "Cancella la regola", @@ -380,26 +360,12 @@ "ip_firewall_not_yet_activated_short": "Non configurato", "ip_firewall_enable_button_title": "Attiva", "ip_firewall_disable_button_title": "Disattiva", - "ip_firewall_back_link_title": "Gestire gli indirizzi IP", "ip_firewall_title": "Gestire le regole di Edge Network Firewall", - "ip_firewall_guide": "Guide", - "ip_firewall_description_1": "Configura la protezione Edge del tuo indirizzo IP. Le regole firewall verranno applicate nella parte più esterna della rete OVHcloud per evitare la saturazione dei collegamenti verso il tuo servizio filtrando il traffico in entrata.", - "ip_firewall_description_2": "Questa funzionalità deve essere utilizzata in linea con il firewall di rete sul server per una maggiore protezione. È possibile definire un massimo di 20 regole per IP.", - "ip_firewall_description_3": "Ricordiamo che lo \"stato delle sessioni TCP\" (TCP established) fa riferimento a indicatori di protocollo TCP (TCP flags) specifici, perché l'Edge Network Firewall non traccia le sessioni TCP.", - "ip_firewall_enabled_rules": "Attivato", - "ip_firewall_disabled_rules": "Disattivato", - "ip_firewall_enabled_rules_description": "Attiva le regole firewall per questo indirizzo IP (la disattivazione comporterà il mantenimento delle regole solo per il tempo in cui è attivo lo Scrubbing Center). Per maggiori informazioni, clicca qui.", - "ip_firewall_enabled_rules_more": "Scopri di più", "ip_firewall_add_summary": "Verifica le informazioni inserite prima di confermare l'aggiunta della regola.", "ip_firewall_add_title": "Aggiungi una regola", "ip_firewall_add_rule_success": "La nuova regola è stata aggiunta.", "ip_firewall_add_rule_fail": "Si è verificato un errore durante l'aggiunta della regola.", - "ip_firewall_close_message": "Chiudere", "ip_firewall_add_rule_confirm_button_text": "Aggiungi", - "ip_firewall_like_this": "Ti piace?", - "ip_firewall_like_this_tooltip": "Ti piace questa pagina? Condividi con noi i tuoi commenti!", - "ip_firewall_rule_apply": "Confermare", - "ip_firewall_rule_cancel": "Annullare", "ip_firewall_modify_title": "Modifica una regola", "ip_firewall_modify_rule_success": "La regola è stata modificata.", "ip_firewall_modify_rule_fail": "Si è verificato un errore durante la modifica della regola.", @@ -434,23 +400,13 @@ "ip_firewall_new_question": "Vuoi davvero attivare la creazione del firewall sull'IP {{t0}}?", "ip_firewall_new_success": "Il firewall sarà creato in pochi minuti sull'IP {{t0}}.", "ip_firewall_new_failed": "Si è verificato un errore durante la creazione del firewall sull'IP {{t0}}", - "ip_firewall_add_success": "La regola è stata creata correttamente!", - "ip_firewall_delete_success": "La regola è stata eliminata correttamente!", - "ip_firewall_deny_part_1": "Abbiamo rilevato solo regole \"Consenti\" e nessuna regola \"Rifiuta\", perciò nessun traffico sarà bloccato da questa configurazione. Consigliamo l’ultima regola per rendere efficace la tua configurazione. Clicca qui ", - "ip_firewall_deny_link": "creare una regola di negazione", - "ip_firewall_deny_part_2": " per aggiungere la regola.", "ip_firewall_action": "Azione", - "ip_firewall_mode": "Modo", "ip_firewall_protocol": "Protocollo", "ip_firewall_source_ip": "Indirizzo IP sorgente", - "ip_firewall_source_ip_invalid": "L'indirizzo IP sorgente inserito non è valido.", "ip_firewall_source_port": "Porta sorgente", "ip_firewall_source_port_tooltip": "La porta sorgente deve essere compresa fra 0 e 65535", - "ip_firewall_source_port_not_empty_tooltip": "La porta sorgente deve essere vuota quando è selezionato \"Frammenti\".", "ip_firewall_destination_port": "Porta di destinazione", "ip_firewall_destination_port_tooltip": "La porta di destinazione deve essere compresa fra 0 e 65535", - "ip_firewall_destination_port_not_empty_tooltip": "La porta di destinazione deve essere vuota quando è selezionato \"Frammenti\".", - "ip_firewall_check_errors": "Sono presenti errori nei dati inseriti, controlla i campi evidenziati in rosso.", "ip_firewall_options": "Stato TCP", "ip_firewall_status": "Stato", "ip_firewall_position": "Priorità", @@ -462,7 +418,6 @@ "ip_firewall_rule_status_removalPending": "In corso di eliminazione", "ip_firewall_rule_status_OK": "Attivo", "ip_firewall_rule_status_ok": "Attivo", - "ip_firewall_rule_status_inactif": "Disattivo", "ip_firewall_rule_fragments": "Fragment", "ip_firewall_rule_fragments_tooltip": "Non è possibile scegliere l'opzione di frammentazione avendo definito una porta sorgente o una porta di destinazione.", "ip_firewall_rule_flags": "Flags", @@ -751,9 +706,55 @@ "ip_administration_title": "Gestisci", "ip_addresses_grid_header": "I tuoi indirizzi IP pubblici e servizi associati", "ip_repricing_banner": "La tariffazione degli indirizzi IPv4 aggiuntivi (Additional IP) è stata aggiornata.", - "ip_repricing_banner_list_item_1": "Dal 6 ottobre 2022, per i nuovi indirizzi.", "ip_repricing_banner_list_item_2": "Dal 1° dicembre 2022, per gli indirizzi esistenti (ordinati prima del 6 ottobre 2022).", "ip_repricing_banner_link": "Ulteriori informazioni", "ip_unused_banner_text": "Disponi di indirizzi IP non utilizzati. Gli indirizzi IPv4 sono una risorsa sempre più rara. Se non effettivamente necessari, consigliamo pertanto di liberarli.", - "ip_unused_banner_link": "Visualizza i miei IP non utilizzati" -} \ No newline at end of file + "ip_unused_banner_link": "Visualizza i miei IP non utilizzati", + "ip_table_header_campus": "Campus", + "ip_repricing_banner_list_item_1": "Dal 6 ottobre 2022, per i nuovi indirizzi.", + "show_all_ips": "Mostrare gli IPv4 e IPv6", + "show_ipv4_ips": "Mostrare gli IPv4", + "show_ipv6_ips": "Mostrare gli IPv6", + "ipv4_ipv6_filter_title": "Filtro IPv4/IPv6", + "ip_game_mitigation_description": "Questa è la pagina di configurazione della protezione DDoS Game per l’indirizzo IP selezionato. È possibile configurare più regole firewall per proteggere al meglio tutte le applicazioni ospitate sull'indirizzo IP selezionato.", + "ip_game_mitigation_description_tip": "Suggerimento: è possibile scegliere \"altro\" protocollo per autorizzare il traffico arbitrario verso una o più porte specifiche. Consigliamo di applicare la politica predefinita \"Nega tutto\", che rimuoverà il traffico su tutte le altre porte (non definite) per una migliore protezione.", + "ip_game_mitigation_apply_policy": "Applicare la strategia predefinita \"Nega tutto\" ", + "ip_game_mitigation_policy_default_help": "Blocca tutto il traffico che non risponde a nessuna delle regole seguenti.", + "ip_game_mitigation_table_start_port": "Porta iniziale (intervallo)", + "ip_game_mitigation_table_end_port": "Porta finale (intervallo)", + "ip_game_mitigation_rule_edit": "Modifica la regola", + "ip_game_mitigation_rule_delete": "Cancella la regola", + "ip_game_mitigation_firewall_rule_add_invalid_parameters": "Inserire le porte è obbligatorio.", + "ip_game_mitigation_back_link_title": "Gestisci gli indirizzi IP", + "ip_game_mitigation_guide": "Guide", + "ip_game_mitigation_rule_apply": "Confermare", + "ip_game_mitigation_rule_cancel": "Annullare", + "ip_game_mitigation_like_this": "Ti piace?", + "ip_game_mitigation_like_this_tooltip": "Ti piace questa pagina? Condividi con noi i tuoi commenti!", + "ip_firewall_back_link_title": "Gestire gli indirizzi IP", + "ip_firewall_guide": "Guide", + "ip_firewall_description_1": "Configura la protezione Edge del tuo indirizzo IP. Le regole firewall verranno applicate nella parte più esterna della rete OVHcloud per evitare la saturazione dei collegamenti verso il tuo servizio filtrando il traffico in entrata.", + "ip_firewall_description_2": "Questa funzionalità deve essere utilizzata in linea con il firewall di rete sul server per una maggiore protezione. È possibile definire un massimo di 20 regole per IP.", + "ip_firewall_description_3": "Ricordiamo che lo \"stato delle sessioni TCP\" (TCP established) fa riferimento a indicatori di protocollo TCP (TCP flags) specifici, perché l'Edge Network Firewall non traccia le sessioni TCP.", + "ip_firewall_enabled_rules": "Attivato", + "ip_firewall_disabled_rules": "Disattivato", + "ip_firewall_enabled_rules_description": "Attiva le regole firewall per questo indirizzo IP (la disattivazione comporterà il mantenimento delle regole solo per il tempo in cui è attivo lo Scrubbing Center). Per maggiori informazioni, clicca qui.", + "ip_firewall_enabled_rules_more": "Scopri di più", + "ip_firewall_close_message": "Chiudere", + "ip_firewall_like_this": "Ti piace?", + "ip_firewall_like_this_tooltip": "Ti piace questa pagina? Condividi con noi i tuoi commenti!", + "ip_firewall_rule_apply": "Confermare", + "ip_firewall_rule_cancel": "Annullare", + "ip_firewall_add_success": "La regola è stata creata correttamente!", + "ip_firewall_delete_success": "La regola è stata eliminata correttamente!", + "ip_firewall_deny_part_1": "Abbiamo rilevato solo regole \"Consenti\" e nessuna regola \"Rifiuta\", perciò nessun traffico sarà bloccato da questa configurazione. Consigliamo l’ultima regola per rendere efficace la tua configurazione. Clicca qui ", + "ip_firewall_deny_link": "creare una regola di negazione", + "ip_firewall_deny_part_2": " per aggiungere la regola.", + "ip_firewall_mode": "Modo", + "ip_firewall_source_ip_invalid": "L'indirizzo IP sorgente inserito non è valido.", + "ip_firewall_source_port_not_empty_tooltip": "La porta sorgente deve essere vuota quando è selezionato \"Frammenti\".", + "ip_firewall_destination_port_not_empty_tooltip": "La porta di destinazione deve essere vuota quando è selezionato \"Frammenti\".", + "ip_firewall_check_errors": "Sono presenti errori nei dati inseriti, controlla i campi evidenziati in rosso.", + "ip_firewall_rule_status_inactif": "Disattivo", + "ip_game_mitigation_firewall_rule_add_ports_already_used": "La porta (o intervallo di porte) è in conflitto con un'altra regola." +} diff --git a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_pl_PL.json b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_pl_PL.json index b260f17e63c9..0354fb452cf3 100644 --- a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_pl_PL.json +++ b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_pl_PL.json @@ -12,10 +12,6 @@ "ip_ipv4": "IPv4", "ip_ipv6": "IPv6", "ip_ipblock": "Blok IP", - "show_all_ips": "Wyświetl adresy IPv4 i IPv6", - "show_ipv4_ips": "Wyświetl adresy IPv4", - "show_ipv6_ips": "Wyświetl adresy IPv6", - "ipv4_ipv6_filter_title": "Filtr IPv4/IPv6", "ip_taskpending_label": "Trwa realizacja zadania", "optional": "Opcjonalny", "ip_required_field": "pola obowiązkowe", @@ -305,13 +301,7 @@ "ip_game_mitigation_ACTIVATED": "Dostępny", "ip_game_mitigation_ACTIVATED_help": "Opcja ochrony Anty-DDoS Game jest dostępna dla tej usługi.", "ip_game_mitigation_title": "Skonfiguruj GAME Firewall", - "ip_game_mitigation_description": "To jest strona konfiguracji ochrony DDoS GAME dla wybranego adresu IP. Możesz skonfigurować wiele reguł zapory sieciowej, aby jak najlepiej chronić wszystkie aplikacje hostowane pod wybranym adresem IP.", - "ip_game_mitigation_description_tip": "Wskazówka: możesz wybrać „inny” protokół, aby zezwolić na dowolny ruch do określonego portu lub portów. W celu zapewnienia lepszej ochrony sugerujemy włączenie polityki „Blokuj pozostałe”, która odrzuci cały ruch sieciowy, dla którego nie ma zdefiniowanych reguł.", - "ip_game_mitigation_apply_policy": "Zastosuj politykę „Blokuj pozostałe”. ", - "ip_game_mitigation_policy_default_help": "Blokuj cały ruch, który nie pasuje do żadnej z poniższych reguł.", "ip_game_mitigation_table_protocol": "Protokół", - "ip_game_mitigation_table_start_port": "Port początkowy (zakres)", - "ip_game_mitigation_table_end_port": "Port końcowy (zakres)", "ip_game_mitigation_table_state": "Status", "ip_game_mitigation_table_error": "Nie można pobrać reguł GAME Firewall.", "ip_game_mitigation_table_partial_error": "Wystąpił błąd podczas pobierania informacji o regułach.", @@ -334,8 +324,6 @@ "ip_game_mitigation_rule_add_port_pattern": "Port musi być dodatnią liczbą całkowitą.", "ip_game_mitigation_rule_add_port_to": "do portu:", "ip_game_mitigation_rule_add_init_error": "Wystąpił błąd. Nie można pobrać listy protokołów.", - "ip_game_mitigation_rule_edit": "Zmień regułę", - "ip_game_mitigation_rule_delete": "Usuń regułę", "ip_game_mitigation_firewall_true": "Ograniczenie GAME zostało \nwłączone. Ruch UDP jest dozwolony tylko dla zdefiniowanych reguł.", "ip_game_mitigation_firewall_false": "Ograniczenie GAME zostało wyłączone. Ruch UDP do nie zdefiniowanych portów jest dozwolony, ale zdefiniowane reguły są nadal stosowane.", "ip_game_mitigation_firewall_firewallModeEnablePending": "Ograniczenie GAME zostanie włączone. Ruch UDP będzie dozwolony tylko dla zdefiniowanych reguł.", @@ -350,13 +338,6 @@ "ip_game_mitigation_firewall_enable_info_true": "W ten sposób chronione będą tylko te gry, dla których zostały ustawione określone reguły. Każdy inny ruch będzie mógł dotrzeć do wybranego IP bez żadnej ochrony. Czy chcesz kontynuować?", "ip_game_mitigation_firewall_enable_success_true": "Domyślna reguła ochrony DDoS GAME zostanie za kilka chwil wyłączona.", "ip_game_mitigation_firewall_enable_error_true": "Wystąpił błąd podczas wyłączania trybu ograniczenia GAME.", - "ip_game_mitigation_firewall_rule_add_invalid_parameters": "Podanie numerów portów jest obowiązkowe.", - "ip_game_mitigation_back_link_title": "Zarządzanie adresami IP", - "ip_game_mitigation_guide": "Przewodniki", - "ip_game_mitigation_rule_apply": "Zatwierdź", - "ip_game_mitigation_rule_cancel": "Anuluj", - "ip_game_mitigation_like_this": "Podoba Ci się?", - "ip_game_mitigation_like_this_tooltip": "Podoba Ci się ta strona? Podziel się z nami swoimi uwagami!", "ip_firewall_fail": "Wystąpił błąd podczas pobierania informacji na temat usługi firewall", "ip_firewall_edit_rule": "Zmień regułę", "ip_firewall_remove_rule": "Usuń regułę", @@ -380,26 +361,12 @@ "ip_firewall_not_yet_activated_short": "Brak konfiguracji", "ip_firewall_enable_button_title": "Włącz", "ip_firewall_disable_button_title": "Wyłącz", - "ip_firewall_back_link_title": "Zarządzanie adresami IP", "ip_firewall_title": "Zarządzanie regułami Edge Network Firewall", - "ip_firewall_guide": "Przewodniki", - "ip_firewall_description_1": "Skonfiguruj ochronę Edge dla adresu IP. Reguły zapory zostaną włączone na brzegu sieci OVHcloud. Filtrowanie ruchu przychodzącego pozwoli zapobiec wysyceniu łączy do Twojej usługi.", - "ip_firewall_description_2": "Aby zapewnić lepszą ochronę, funkcji tej należy używać w połączeniu z zaporą sieciową na serwerze. Możesz zdefiniować maksymalnie 20 reguł na adres IP.", - "ip_firewall_description_3": "Pamiętaj, że „stan sesji TCP” (TCP established) odnosi się do określonych flag protokołu TCP (TCP flags), ponieważ Edge Network Firewall nie śledzi sesji TCP.", - "ip_firewall_enabled_rules": "Włączone", - "ip_firewall_disabled_rules": "Wyłączone", - "ip_firewall_enabled_rules_description": "Włącz reguły zapory dla tego adresu IP (wyłączenie spowoduje, że reguły zostaną użyte tylko w czasie gdy Scrubbing Center będzie aktywny). Więcej informacji znajdziesz tutaj.", - "ip_firewall_enabled_rules_more": "Dowiedz się więcej", "ip_firewall_add_summary": "Sprawdź podane informacje zanim potwierdzisz dodanie reguły.", "ip_firewall_add_title": "Dodaj regułę", "ip_firewall_add_rule_success": "Nowa reguła została dodana.", "ip_firewall_add_rule_fail": "Wystąpił błąd podczas dodawania reguły.", - "ip_firewall_close_message": "Zamknij", "ip_firewall_add_rule_confirm_button_text": "Dodaj", - "ip_firewall_like_this": "Podoba Ci się?", - "ip_firewall_like_this_tooltip": "Podoba Ci się ta strona? Podziel się z nami swoimi uwagami!", - "ip_firewall_rule_apply": "Zatwierdź", - "ip_firewall_rule_cancel": "Anuluj", "ip_firewall_modify_title": "Zmień regułę", "ip_firewall_modify_rule_success": "Reguła została zmodyfikowana.", "ip_firewall_modify_rule_fail": "Wystąpił błąd podczas zmiany reguły.", @@ -434,23 +401,13 @@ "ip_firewall_new_question": "Czy chcesz włączyć usługę firewall dla IP {{t0}}?", "ip_firewall_new_success": "Usługa firewall dla IP {{t0}} zostanie włączona w ciągu kilku minut.", "ip_firewall_new_failed": "Wystąpił błąd podczas tworzenia usługi firewall dla IP {{t0}}", - "ip_firewall_add_success": "Reguła została utworzona!", - "ip_firewall_delete_success": "Reguła została usunięta!", - "ip_firewall_deny_part_1": "Wykryliśmy tylko reguły „Akceptuj” i brak reguł „Odrzuć”, zatem konfiguracja ta nie będzie blokować żadnego ruchu. Sugerujemy użycie ostatniej reguły, dzięki której konfiguracja będzie skuteczna. Kliknij tutaj ", - "ip_firewall_deny_link": "Utwórz regułę odrzucenia", - "ip_firewall_deny_part_2": " aby dodać regułę.", "ip_firewall_action": "Operacja", - "ip_firewall_mode": "Tryb", "ip_firewall_protocol": "Protokół", "ip_firewall_source_ip": "Źródłowy adres IP", - "ip_firewall_source_ip_invalid": "Wprowadzony źródłowy adres IP jest nieprawidłowy.", "ip_firewall_source_port": "Port źródłowy", "ip_firewall_source_port_tooltip": "Port źródłowy musi być zawarty między 0 i 65535", - "ip_firewall_source_port_not_empty_tooltip": "Dla zaznaczonej opcji fragmentacji nie podajemy adresów portów źródłowych.", "ip_firewall_destination_port": "Port docelowy", "ip_firewall_destination_port_tooltip": "Port docelowy musi być zawarty między 0 i 65535", - "ip_firewall_destination_port_not_empty_tooltip": "Dla zaznaczonej opcji fragmentacji nie podajemy adresów portów docelowych.", - "ip_firewall_check_errors": "Wprowadzone dane zawierają błędy. Sprawdź pola zaznaczone na czerwono.", "ip_firewall_options": "Stan TCP", "ip_firewall_status": "Status", "ip_firewall_position": "Priorytet", @@ -462,7 +419,6 @@ "ip_firewall_rule_status_removalPending": "Trwa usuwanie", "ip_firewall_rule_status_OK": "Aktywna", "ip_firewall_rule_status_ok": "Aktywna", - "ip_firewall_rule_status_inactif": "Nieaktywna", "ip_firewall_rule_fragments": "Fragmenty", "ip_firewall_rule_fragments_tooltip": "Nie możesz wybrać opcji fragmentu definiując port źródłowy i/lub port docelowy. ", "ip_firewall_rule_flags": "Flagi", @@ -755,5 +711,50 @@ "ip_repricing_banner_list_item_2": "Od 1 grudnia 2022 r. ceny istniejących adresów (zamówionych przed 6 października 2022).", "ip_repricing_banner_link": "Więcej informacji", "ip_unused_banner_text": "Dysponujesz adresami IP, których nie używasz. Adresy IPv4 są zasobem deficytowym, zatem jeśli ich nie potrzebujesz, prosimy o ich zwolnienie.", - "ip_unused_banner_link": "Sprawdź nieużywane adresy IP." -} \ No newline at end of file + "ip_unused_banner_link": "Sprawdź nieużywane adresy IP.", + "show_all_ips": "Wyświetl adresy IPv4 i IPv6", + "show_ipv4_ips": "Wyświetl adresy IPv4", + "show_ipv6_ips": "Wyświetl adresy IPv6", + "ipv4_ipv6_filter_title": "Filtr IPv4/IPv6", + "ip_game_mitigation_description": "To jest strona konfiguracji ochrony DDoS GAME dla wybranego adresu IP. Możesz skonfigurować wiele reguł zapory sieciowej, aby jak najlepiej chronić wszystkie aplikacje hostowane pod wybranym adresem IP.", + "ip_game_mitigation_description_tip": "Wskazówka: możesz wybrać „inny” protokół, aby zezwolić na dowolny ruch do określonego portu lub portów. W celu zapewnienia lepszej ochrony sugerujemy włączenie polityki „Blokuj pozostałe”, która odrzuci cały ruch sieciowy, dla którego nie ma zdefiniowanych reguł.", + "ip_game_mitigation_apply_policy": "Zastosuj politykę „Blokuj pozostałe”. ", + "ip_game_mitigation_policy_default_help": "Blokuj cały ruch, który nie pasuje do żadnej z poniższych reguł.", + "ip_game_mitigation_table_start_port": "Port początkowy (zakres)", + "ip_game_mitigation_table_end_port": "Port końcowy (zakres)", + "ip_game_mitigation_rule_edit": "Zmień regułę", + "ip_game_mitigation_rule_delete": "Usuń regułę", + "ip_game_mitigation_firewall_rule_add_invalid_parameters": "Podanie numerów portów jest obowiązkowe.", + "ip_game_mitigation_back_link_title": "Zarządzanie adresami IP", + "ip_game_mitigation_guide": "Przewodniki", + "ip_game_mitigation_rule_apply": "Zatwierdź", + "ip_game_mitigation_rule_cancel": "Anuluj", + "ip_game_mitigation_like_this": "Podoba Ci się?", + "ip_game_mitigation_like_this_tooltip": "Podoba Ci się ta strona? Podziel się z nami swoimi uwagami!", + "ip_firewall_back_link_title": "Zarządzanie adresami IP", + "ip_firewall_guide": "Przewodniki", + "ip_firewall_description_1": "Skonfiguruj ochronę Edge dla adresu IP. Reguły zapory zostaną włączone na brzegu sieci OVHcloud. Filtrowanie ruchu przychodzącego pozwoli zapobiec wysyceniu łączy do Twojej usługi.", + "ip_firewall_description_2": "Aby zapewnić lepszą ochronę, funkcji tej należy używać w połączeniu z zaporą sieciową na serwerze. Możesz zdefiniować maksymalnie 20 reguł na adres IP.", + "ip_firewall_description_3": "Pamiętaj, że „stan sesji TCP” (TCP established) odnosi się do określonych flag protokołu TCP (TCP flags), ponieważ Edge Network Firewall nie śledzi sesji TCP.", + "ip_firewall_enabled_rules": "Włączone", + "ip_firewall_disabled_rules": "Wyłączone", + "ip_firewall_enabled_rules_description": "Włącz reguły zapory dla tego adresu IP (wyłączenie spowoduje, że reguły zostaną użyte tylko w czasie gdy Scrubbing Center będzie aktywny). Więcej informacji znajdziesz tutaj.", + "ip_firewall_enabled_rules_more": "Dowiedz się więcej", + "ip_firewall_close_message": "Zamknij", + "ip_firewall_like_this": "Podoba Ci się?", + "ip_firewall_like_this_tooltip": "Podoba Ci się ta strona? Podziel się z nami swoimi uwagami!", + "ip_firewall_rule_apply": "Zatwierdź", + "ip_firewall_rule_cancel": "Anuluj", + "ip_firewall_add_success": "Reguła została utworzona!", + "ip_firewall_delete_success": "Reguła została usunięta!", + "ip_firewall_deny_part_1": "Wykryliśmy tylko reguły „Akceptuj” i brak reguł „Odrzuć”, zatem konfiguracja ta nie będzie blokować żadnego ruchu. Sugerujemy użycie ostatniej reguły, dzięki której konfiguracja będzie skuteczna. Kliknij tutaj ", + "ip_firewall_deny_link": "Utwórz regułę odrzucenia", + "ip_firewall_deny_part_2": " aby dodać regułę.", + "ip_firewall_mode": "Tryb", + "ip_firewall_source_ip_invalid": "Wprowadzony źródłowy adres IP jest nieprawidłowy.", + "ip_firewall_source_port_not_empty_tooltip": "Dla zaznaczonej opcji fragmentacji nie podajemy adresów portów źródłowych.", + "ip_firewall_destination_port_not_empty_tooltip": "Dla zaznaczonej opcji fragmentacji nie podajemy adresów portów docelowych.", + "ip_firewall_check_errors": "Wprowadzone dane zawierają błędy. Sprawdź pola zaznaczone na czerwono.", + "ip_firewall_rule_status_inactif": "Nieaktywna", + "ip_game_mitigation_firewall_rule_add_ports_already_used": "Port (lub zakres portów) jest w konflikcie z inną regułą." +} diff --git a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_pt_PT.json b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_pt_PT.json index 350be9d7bbab..c34d691cc008 100644 --- a/packages/manager/apps/dedicated/client/app/ip/translations/Messages_pt_PT.json +++ b/packages/manager/apps/dedicated/client/app/ip/translations/Messages_pt_PT.json @@ -12,10 +12,6 @@ "ip_ipv4": "IPv4", "ip_ipv6": "IPv6", "ip_ipblock": "Bloqueio de IP", - "show_all_ips": "Mostrar os IPv4 e IPv6", - "show_ipv4_ips": "Mostrar os IPv4", - "show_ipv6_ips": "Mostrar os IPv6", - "ipv4_ipv6_filter_title": "Filtro IPv4/IPv6", "ip_taskpending_label": "Trabalho em curso", "optional": "Opcional", "ip_required_field": "campo obrigatório", @@ -305,13 +301,7 @@ "ip_game_mitigation_ACTIVATED": "Disponível", "ip_game_mitigation_ACTIVATED_help": "A opção de proteção anti-DDoS Game está disponível para este serviço.", "ip_game_mitigation_title": "Configurar a GAME firewall", - "ip_game_mitigation_description": "Esta é a página de configuração da proteção DDoS GAME para o endereço IP selecionado. Podem ser configuradas várias regras de firewall para proteger melhor todas as aplicações alojadas no endereço IP selecionado.", - "ip_game_mitigation_description_tip": "Dica: pode escolher « outro » protocolo para autorizar um tráfego arbitrário para uma ou várias portas específicas. Sugerimos que aplique a política « Recusa por defeito » que irá eliminar o tráfego em todas as outras portas (não definidas) para uma melhor proteção.", - "ip_game_mitigation_apply_policy": "Aplicar a estratégia « Recusa por defeito » ", - "ip_game_mitigation_policy_default_help": "Bloqueie todo o tráfego que não corresponda a nenhuma das seguintes regras.", "ip_game_mitigation_table_protocol": "Protocolo de jogo", - "ip_game_mitigation_table_start_port": "Porta de arranque (intervalo)", - "ip_game_mitigation_table_end_port": "Porta final (intervalo)", "ip_game_mitigation_table_state": "Estado", "ip_game_mitigation_table_error": "Não foi possível recuperar as regras da GAME firewall.", "ip_game_mitigation_table_partial_error": "Ocorreu um erro ao recuperar as regras.", @@ -334,8 +324,6 @@ "ip_game_mitigation_rule_add_port_pattern": "A porta deve ser um número inteiro positivo.", "ip_game_mitigation_rule_add_port_to": "até à porta:", "ip_game_mitigation_rule_add_init_error": "Ocorreu um erro. Não é possível recuperar a lista dos protocolos.", - "ip_game_mitigation_rule_edit": "Modificar a regra", - "ip_game_mitigation_rule_delete": "Eliminar a regra", "ip_game_mitigation_firewall_true": "A restrição GAME foi ativada, o tráfego é autorizado em UDP com as regras definidas", "ip_game_mitigation_firewall_false": "A restrição GAME foi desativada, o tráfego UDP para as portas não definidas será autorizado mas as regras definidas permanecerão aplicadas", "ip_game_mitigation_firewall_firewallModeEnablePending": "A restrição GAME vai ser ativada, o tráfego será autorizado em UDP unicamente com as regras definidas", @@ -350,13 +338,6 @@ "ip_game_mitigation_firewall_enable_info_true": "Ao fazê-lo, os únicos jogos protegidos serão os que correspondem a regras definidas. Qualquer outro tráfego poderá atingir o IP selecionado sem qualquer proteção. Deseja continuar?", "ip_game_mitigation_firewall_enable_success_true": "A política por defeito de proteção DDoS da GAME será desativada dentro de alguns instantes.", "ip_game_mitigation_firewall_enable_error_true": "Ocorreu um erro aquando da desativação do modo de restrição GAME.", - "ip_game_mitigation_firewall_rule_add_invalid_parameters": "É obrigatório introduzir portas.", - "ip_game_mitigation_back_link_title": "Gerir endereços IP", - "ip_game_mitigation_guide": "Manuais", - "ip_game_mitigation_rule_apply": "Validar", - "ip_game_mitigation_rule_cancel": "Anular", - "ip_game_mitigation_like_this": "Gostou?", - "ip_game_mitigation_like_this_tooltip": "Gostou desta página? Partilhe connosco as suas observações!", "ip_firewall_fail": "Ocorreu um erro aquando do carregamento das informações da firewall", "ip_firewall_edit_rule": "Modificar a regra", "ip_firewall_remove_rule": "Eliminar a regra", @@ -380,26 +361,12 @@ "ip_firewall_not_yet_activated_short": "Não configurado", "ip_firewall_enable_button_title": "Ativar", "ip_firewall_disable_button_title": "Desativar", - "ip_firewall_back_link_title": "Gerir endereços IP", "ip_firewall_title": "Gerir as regras da Edge Network Firewall", - "ip_firewall_guide": "Manuais", - "ip_firewall_description_1": "Configure a proteção Edge do seu endereço IP. As suas regras de firewall serão aplicadas no limite da rede OVHcloud, de forma a evitar a saturação das ligações para o seu serviço ao filtrar o tráfego de entrada.", - "ip_firewall_description_2": "Para uma melhor proteção, esta função deve ser usada adequadamente com a firewall de rede do seu servidor. Podem ser definidas um máximo de 20 regras por IP.", - "ip_firewall_description_3": "Tenha em conta que o « estado das sessões TCP » (TCP established) refere-se a indicadores de protocolo TCP (TCP flags) específicos, uma vez que o Edge Network Firewall não vigia as sessões TCP.", - "ip_firewall_enabled_rules": "Ativado", - "ip_firewall_disabled_rules": "Desativado", - "ip_firewall_enabled_rules_description": "Ative as regras da firewall para este endereço IP (a desativação levará à manutenção das regras apenas durante o tempo em que o Scrubbing Center estiver ativo). Saiba mais aqui", - "ip_firewall_enabled_rules_more": "Saber mais", "ip_firewall_add_summary": "Queira verificar as informações introduzidas antes de validar a adição da regra.", "ip_firewall_add_title": "Adicionar uma regra", "ip_firewall_add_rule_success": "A nova regra foi adicionada.", "ip_firewall_add_rule_fail": "Ocorreu um erro durante a adição da regra.", - "ip_firewall_close_message": "Fechar", "ip_firewall_add_rule_confirm_button_text": "Adicionar", - "ip_firewall_like_this": "Gostou?", - "ip_firewall_like_this_tooltip": "Gostou desta página? Partilhe connosco as suas observações!", - "ip_firewall_rule_apply": "Validar", - "ip_firewall_rule_cancel": "Anular", "ip_firewall_modify_title": "Modificar uma regra", "ip_firewall_modify_rule_success": "A regra foi modificada.", "ip_firewall_modify_rule_fail": "Ocorreu um erro aquando da modificação da regra.", @@ -434,23 +401,13 @@ "ip_firewall_new_question": "Tem a certeza de que deseja ativar a firewall para o IP {{t0}}?", "ip_firewall_new_success": "A firewall será criada dentro de alguns instantes para o IP {{t0}}", "ip_firewall_new_failed": "Ocorreu um erro durante a criação da firewall para o IP {{t0}}", - "ip_firewall_add_success": "A regra foi criada com sucesso!", - "ip_firewall_delete_success": "A regra foi eliminada com sucesso!", - "ip_firewall_deny_part_1": "Detetámos apenas regras \"Aceitar\" e nenhuma regra \"Recusar\", pelo que nenhum tráfego será bloqueado por esta configuração. Sugerimos-lhe a última regra para tornar a sua configuração eficaz. Clique aqui ", - "ip_firewall_deny_link": "criar uma regra de recusa", - "ip_firewall_deny_part_2": " para adicionar uma regra.", "ip_firewall_action": "Ação", - "ip_firewall_mode": "Modo", "ip_firewall_protocol": "Protocolo", "ip_firewall_source_ip": "Endereço IP de origem", - "ip_firewall_source_ip_invalid": "O endereço IP de origem introduzido não é válido.", "ip_firewall_source_port": "Porta de origem", "ip_firewall_source_port_tooltip": "A porta source deve estar compreendida entre 0 e 65535", - "ip_firewall_source_port_not_empty_tooltip": "A porta de origem deve estar vazia quando selecionar « Fragmentos ».", "ip_firewall_destination_port": "Porta de destino", "ip_firewall_destination_port_tooltip": "A porta de destino deve ser compreendida entre 0 e 65535", - "ip_firewall_destination_port_not_empty_tooltip": "A porta de destino deve estar vazia quando selecionar « Fragmentos ».", - "ip_firewall_check_errors": "Existem erros nos dados introduzidos, queira verificar os campos assinalados a vermelho.", "ip_firewall_options": "Estado TCP", "ip_firewall_status": "Estado", "ip_firewall_position": "Prioridade", @@ -462,7 +419,6 @@ "ip_firewall_rule_status_removalPending": "Eliminação em curso", "ip_firewall_rule_status_OK": "Ativo", "ip_firewall_rule_status_ok": "Ativo", - "ip_firewall_rule_status_inactif": "Inativo", "ip_firewall_rule_fragments": "Fragments", "ip_firewall_rule_fragments_tooltip": "Não pode escolher a opção fragment sem antes definir uma porta source e/ou uma porta de destino.", "ip_firewall_rule_flags": "Bandeiras", @@ -755,5 +711,50 @@ "ip_repricing_banner_list_item_2": "A partir de 1 de dezembro de 2022, para os endereços existentes (encomendados antes de 6 de outubro de 2022).", "ip_repricing_banner_link": "Mais informações", "ip_unused_banner_text": "Tem endereços IP não utilizados. Como os endereços IPv4 são um recurso cada vez mais escasso, sugerimos que os liberte caso não precise deles.", - "ip_unused_banner_link": "Ver os meus endereços IP não utilizados." -} \ No newline at end of file + "ip_unused_banner_link": "Ver os meus endereços IP não utilizados.", + "show_all_ips": "Mostrar os IPv4 e IPv6", + "show_ipv4_ips": "Mostrar os IPv4", + "show_ipv6_ips": "Mostrar os IPv6", + "ipv4_ipv6_filter_title": "Filtro IPv4/IPv6", + "ip_game_mitigation_description": "Esta é a página de configuração da proteção DDoS GAME para o endereço IP selecionado. Podem ser configuradas várias regras de firewall para proteger melhor todas as aplicações alojadas no endereço IP selecionado.", + "ip_game_mitigation_description_tip": "Dica: pode escolher « outro » protocolo para autorizar um tráfego arbitrário para uma ou várias portas específicas. Sugerimos que aplique a política « Recusa por defeito » que irá eliminar o tráfego em todas as outras portas (não definidas) para uma melhor proteção.", + "ip_game_mitigation_apply_policy": "Aplicar a estratégia « Recusa por defeito » ", + "ip_game_mitigation_policy_default_help": "Bloqueie todo o tráfego que não corresponda a nenhuma das seguintes regras.", + "ip_game_mitigation_table_start_port": "Porta de arranque (intervalo)", + "ip_game_mitigation_table_end_port": "Porta final (intervalo)", + "ip_game_mitigation_rule_edit": "Modificar a regra", + "ip_game_mitigation_rule_delete": "Eliminar a regra", + "ip_game_mitigation_firewall_rule_add_invalid_parameters": "É obrigatório introduzir portas.", + "ip_game_mitigation_back_link_title": "Gerir endereços IP", + "ip_game_mitigation_guide": "Manuais", + "ip_game_mitigation_rule_apply": "Validar", + "ip_game_mitigation_rule_cancel": "Anular", + "ip_game_mitigation_like_this": "Gostou?", + "ip_game_mitigation_like_this_tooltip": "Gostou desta página? Partilhe connosco as suas observações!", + "ip_firewall_back_link_title": "Gerir endereços IP", + "ip_firewall_guide": "Manuais", + "ip_firewall_description_1": "Configure a proteção Edge do seu endereço IP. As suas regras de firewall serão aplicadas no limite da rede OVHcloud, de forma a evitar a saturação das ligações para o seu serviço ao filtrar o tráfego de entrada.", + "ip_firewall_description_2": "Para uma melhor proteção, esta função deve ser usada adequadamente com a firewall de rede do seu servidor. Podem ser definidas um máximo de 20 regras por IP.", + "ip_firewall_description_3": "Tenha em conta que o « estado das sessões TCP » (TCP established) refere-se a indicadores de protocolo TCP (TCP flags) específicos, uma vez que o Edge Network Firewall não vigia as sessões TCP.", + "ip_firewall_enabled_rules": "Ativado", + "ip_firewall_disabled_rules": "Desativado", + "ip_firewall_enabled_rules_description": "Ative as regras da firewall para este endereço IP (a desativação levará à manutenção das regras apenas durante o tempo em que o Scrubbing Center estiver ativo). Saiba mais aqui", + "ip_firewall_enabled_rules_more": "Saber mais", + "ip_firewall_close_message": "Fechar", + "ip_firewall_like_this": "Gostou?", + "ip_firewall_like_this_tooltip": "Gostou desta página? Partilhe connosco as suas observações!", + "ip_firewall_rule_apply": "Validar", + "ip_firewall_rule_cancel": "Anular", + "ip_firewall_add_success": "A regra foi criada com sucesso!", + "ip_firewall_delete_success": "A regra foi eliminada com sucesso!", + "ip_firewall_deny_part_1": "Detetámos apenas regras \"Aceitar\" e nenhuma regra \"Recusar\", pelo que nenhum tráfego será bloqueado por esta configuração. Sugerimos-lhe a última regra para tornar a sua configuração eficaz. Clique aqui ", + "ip_firewall_deny_link": "criar uma regra de recusa", + "ip_firewall_deny_part_2": " para adicionar uma regra.", + "ip_firewall_mode": "Modo", + "ip_firewall_source_ip_invalid": "O endereço IP de origem introduzido não é válido.", + "ip_firewall_source_port_not_empty_tooltip": "A porta de origem deve estar vazia quando selecionar « Fragmentos ».", + "ip_firewall_destination_port_not_empty_tooltip": "A porta de destino deve estar vazia quando selecionar « Fragmentos ».", + "ip_firewall_check_errors": "Existem erros nos dados introduzidos, queira verificar os campos assinalados a vermelho.", + "ip_firewall_rule_status_inactif": "Inativo", + "ip_game_mitigation_firewall_rule_add_ports_already_used": "A porta (ou intervalo de portas) está em conflito com outra regra." +} diff --git a/packages/manager/apps/dedicated/client/app/network-security/network-security.constant.js b/packages/manager/apps/dedicated/client/app/network-security/network-security.constant.js index 63493e141377..8ecd96527d67 100644 --- a/packages/manager/apps/dedicated/client/app/network-security/network-security.constant.js +++ b/packages/manager/apps/dedicated/client/app/network-security/network-security.constant.js @@ -6,17 +6,6 @@ export const ENTITY = { EVENT: 'event', }; -export const ALLOWED_LANGUAGES = { - en: { - isDefault: true, - }, - fr: { - isDefault: false, - }, -}; - -export const BASE_URL_SURVEY = 'https://survey.ovh.com/index.php/558299?lang='; - export const GUIDE_LINKS = { DE: 'https://help.ovhcloud.com/csm/de-network-security-dashboard?id=kb_article_view&sysparm_article=KB0060677', @@ -68,8 +57,6 @@ export default { API_PATH, PAGE_SIZE, ENTITY, - ALLOWED_LANGUAGES, - BASE_URL_SURVEY, GUIDE_LINKS, TRACKING_PREFIX, }; diff --git a/packages/manager/apps/dedicated/client/app/network-security/network-security.controller.js b/packages/manager/apps/dedicated/client/app/network-security/network-security.controller.js index 8824d0d694e4..319ea47c77af 100644 --- a/packages/manager/apps/dedicated/client/app/network-security/network-security.controller.js +++ b/packages/manager/apps/dedicated/client/app/network-security/network-security.controller.js @@ -1,36 +1,15 @@ -import isObject from 'lodash/isObject'; -import { - ALLOWED_LANGUAGES, - BASE_URL_SURVEY, - GUIDE_LINKS, -} from './network-security.constant'; +import { GUIDE_LINKS } from './network-security.constant'; export default class NetworkSecurityController { /* @ngInject */ constructor(coreConfig, networkSecurityService) { this.coreConfig = coreConfig; this.networkSecurityService = networkSecurityService; - this.ALLOWED_LANGUAGES = ALLOWED_LANGUAGES; - this.BASE_URL_SURVEY = BASE_URL_SURVEY; - this.guideLink = - GUIDE_LINKS[coreConfig.getUser().ovhSubsidiary] || GUIDE_LINKS.DEFAULT; } $onInit() { - // Get default language - const defaultLanguage = Object.keys(this.ALLOWED_LANGUAGES).find( - (key) => this.ALLOWED_LANGUAGES[key].isDefault, - ); - const userLanguage = this.coreConfig.getUserLanguage(); - - const languageToUse = isObject(this.ALLOWED_LANGUAGES[userLanguage]) - ? userLanguage - : defaultLanguage; - - // Get user - const user = this.coreConfig.getUser(); - - // Build url for survey link - this.surveyUrl = `${this.BASE_URL_SURVEY}${languageToUse}&nic=${user.nichandle}`; + this.guideLink = + GUIDE_LINKS[this.coreConfig.getUser().ovhSubsidiary] || + GUIDE_LINKS.DEFAULT; } } diff --git a/packages/manager/apps/dedicated/client/app/network-security/network-security.html b/packages/manager/apps/dedicated/client/app/network-security/network-security.html index 8a9a775028ee..fd4baf912736 100644 --- a/packages/manager/apps/dedicated/client/app/network-security/network-security.html +++ b/packages/manager/apps/dedicated/client/app/network-security/network-security.html @@ -20,19 +20,6 @@
- - diff --git a/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.constant.js b/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.constant.js index 7bfc8d14491c..edacdcbeef62 100644 --- a/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.constant.js +++ b/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.constant.js @@ -1,20 +1,20 @@ export const PAGE_SIZE = 300; export const TRAFFIC_PERIODS = [ - { key: 'last6h', value: 'network_security_dashboard_filter_last_6h' }, - { key: 'last24h', value: 'network_security_dashboard_filter_last_24h' }, - { key: 'lastWeek', value: 'network_security_dashboard_filter_last_week' }, + { key: 'last6h', value: 'network_security_dashboard_filter_6_hours' }, + { key: 'last24h', value: 'network_security_dashboard_filter_24_hours' }, + { key: 'last7d', value: 'network_security_dashboard_filter_7_days' }, { - key: 'last2weeks', - value: 'network_security_dashboard_filter_last_2_weeks', + key: 'last14d', + value: 'network_security_dashboard_filter_14_days', }, ]; export const TRAFFIC_PERIOD_LIST = { last6h: 'last6h', last24h: 'last24h', - lastWeek: 'lastWeek', - last2weeks: 'last2weeks', + last7d: 'last7d', + last14d: 'last14d', }; export const CHART = { @@ -53,6 +53,30 @@ export const CHART = { tooltips: { mode: 'label', intersect: false, + callbacks: { + title: (context) => { + // Retrieve user language + const userLanguage = navigator.language; + + // Configure dateTime format to display like DD/MM/YYYY hh:mm:ss (for FR) or MM/DD/YY, hh:mm:ss (for US) + const dateTimeFormat = new Intl.DateTimeFormat(userLanguage, { + hourCycle: 'h23', + timeStyle: 'medium', + dateStyle: 'short', + }); + + // Retrieve user local time zone + const timeZoneOffset = + (new Date(context[0].label).getTimezoneOffset() / 60) * -1; + const sign = timeZoneOffset > 0 ? '+' : ''; + + // Format title like DD/MM/YYYY hh:mm:ss UTC+1 (for FR) or MM/DD/YY, hh:mm:ss UTC-2 (for US) + const title = `${dateTimeFormat.format( + new Date(context[0].label), + )} UTC${sign}${timeZoneOffset}`; + return title; + }, + }, }, scales: { yAxes: [ @@ -85,13 +109,19 @@ export const CHART = { display: true, source: 'auto', autoSkip: true, - }, - time: { - displayFormats: { - hour: 'YYYY-MM-DD HH:MM', + callback: (val, index) => { + const { language } = navigator; + const dateTimeFormat = new Intl.DateTimeFormat(language, { + hourCycle: 'h23', + timeStyle: 'medium', + dateStyle: 'short', + }); + // Display one label out of 5 + return index % 5 === 0 + ? dateTimeFormat.format(new Date(val)) + : ''; }, }, - type: 'time', }, ], }, diff --git a/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.controller.js b/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.controller.js index bce5f6168991..dc5435456ca6 100644 --- a/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.controller.js +++ b/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.controller.js @@ -47,6 +47,16 @@ export default class TrafficController { ...this.CHART.options, }; this.isSubnetValid = true; + + // Retrieve time zone offset to initialize value of UTC + const timeZoneOffset = (new Date().getTimezoneOffset() / 60) * -1; + this.timeZoneLabel = this.$translate.instant( + 'network_security_dashboard_time_zone', + { + timeZoneOffset: + timeZoneOffset > 0 ? `+${timeZoneOffset}` : timeZoneOffset, + }, + ); } selectService() { @@ -78,7 +88,6 @@ export default class TrafficController { checkSelectedSubnet(value) { let isSubnetValid = true; - console.log('value', value); if (!value || (value.indexOf('/') === -1 && !ipaddr.isValid(value))) { isSubnetValid = false; @@ -121,10 +130,10 @@ export default class TrafficController { case this.TRAFFIC_PERIOD_LIST.last6h: after.setTime(after.getTime() - 6 * 60 * 60 * 1000); break; - case this.TRAFFIC_PERIOD_LIST.lastWeek: + case this.TRAFFIC_PERIOD_LIST.last7d: after.setDate(after.getDate() - 7); break; - case this.TRAFFIC_PERIOD_LIST.last2weeks: + case this.TRAFFIC_PERIOD_LIST.last14d: after.setDate(after.getDate() - 14); break; default: diff --git a/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.html b/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.html index f3da3d248cc8..87e3e98c06bb 100644 --- a/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.html +++ b/packages/manager/apps/dedicated/client/app/network-security/traffic/traffic.html @@ -51,14 +51,17 @@ class="oui-label mr-2" data-translate="network_security_dashboard_period_filter" > - +
+ + +
- - - - - - - - - - - - - - + + + + + OVHcloud + + +
+ + + diff --git a/packages/manager/apps/pci-vouchers/package.json b/packages/manager/apps/pci-vouchers/package.json new file mode 100644 index 000000000000..4833b1ed7ee4 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/package.json @@ -0,0 +1,66 @@ +{ + "name": "@ovh-ux/manager-pci-vouchers-app", + "version": "0.1.0", + "private": true, + "type": "module", + "scripts": { + "build": "tsc --project tsconfig.build.json && vite build", + "coverage": "vitest run --coverage", + "dev": "vite", + "lint": "eslint ./src", + "start": "lerna exec --stream --scope='@ovh-ux/manager-pci-vouchers-app' --include-dependencies -- npm run build --if-present", + "start:dev": "lerna exec --stream --scope='@ovh-ux/manager-pci-vouchers-app' --include-dependencies -- npm run dev --if-present", + "start:watch": "lerna exec --stream --parallel --scope='@ovh-ux/manager-pci-vouchers-app' --include-dependencies -- npm run dev:watch --if-present", + "test": "vitest run" + }, + "dependencies": { + "@ovh-ux/manager-config": "^7.3.0", + "@ovh-ux/manager-core-api": "^0.6.0", + "@ovh-ux/manager-react-shell-client": "^0.3.0", + "@ovh-ux/manager-tailwind-config": "^0.1.0", + "@ovh-ux/shell": "^3.4.0", + "@ovhcloud/manager-components": "^1.5.0", + "@ovhcloud/ods-common-core": "^17.1.0", + "@ovhcloud/ods-common-theming": "^17.1.0", + "@ovhcloud/ods-components": "^17.1.0", + "@ovhcloud/ods-theme-blue-jeans": "^17.1.0", + "@tanstack/react-query": "^5.14.2", + "@tanstack/react-query-devtools": "^5.14.2", + "@tanstack/react-table": "^8.11.6", + "date-fns": "^3.0.4", + "element-internals-polyfill": "^1.3.10", + "i18next": "^23.7.11", + "i18next-http-backend": "^2.4.2", + "react": "^18.2.0", + "react-dom": "^18.2.0", + "react-hook-form": "^7.47.0", + "react-i18next": "^13.5.0", + "react-router-dom": "^6.21.0", + "zustand": "^4.5.0" + }, + "devDependencies": { + "@jest/globals": "^29.7.0", + "@ovh-ux/manager-vite-config": "^0.5.0", + "@testing-library/dom": "^9.3.3", + "@testing-library/jest-dom": "^6.1.5", + "@testing-library/react": "^14.1.2", + "@testing-library/user-event": "^13.2.1", + "@types/jest": "^29.5.11", + "@types/react": "^18.2.45", + "@types/react-dom": "^18.2.18", + "@vitejs/plugin-react": "^4.2.1", + "@vitest/coverage-v8": "^1.2.0", + "autoprefixer": "^10.4.16", + "eslint": "^8.56.0", + "postcss": "^8.4.32", + "rollup": "^4.4.0", + "tailwindcss": "^3.4.0", + "typescript": "^5.3.3", + "vite": "^3.0.2", + "vitest": "^1.2.0" + }, + "regions": [ + "CA", + "EU" + ] +} diff --git a/packages/manager/apps/pci-vouchers/postcss.config.cjs b/packages/manager/apps/pci-vouchers/postcss.config.cjs new file mode 100644 index 000000000000..12a703d900da --- /dev/null +++ b/packages/manager/apps/pci-vouchers/postcss.config.cjs @@ -0,0 +1,6 @@ +module.exports = { + plugins: { + tailwindcss: {}, + autoprefixer: {}, + }, +}; diff --git a/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_de_DE.json b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_de_DE.json new file mode 100644 index 000000000000..a5305cc51bdd --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_de_DE.json @@ -0,0 +1,4 @@ +{ + "pci_projects_project_activate_project_banner_message": "Sie befinden sich derzeit im „Discovery“-Modus. Um die Erstellung der Ressource abzuschließen, müssen Sie das Projekt aktivieren.", + "pci_projects_project_activate_project_banner_cta": "Projekt aktivieren" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_en_GB.json b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_en_GB.json new file mode 100644 index 000000000000..a4ee475f9340 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_en_GB.json @@ -0,0 +1,4 @@ +{ + "pci_projects_project_activate_project_banner_message": "You are currently in Discovery mode. To finish creating your resource, you must activate your project.", + "pci_projects_project_activate_project_banner_cta": "Activate project" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_es_ES.json b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_es_ES.json new file mode 100644 index 000000000000..fa3d077a1cb1 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_es_ES.json @@ -0,0 +1,4 @@ +{ + "pci_projects_project_activate_project_banner_message": "Actualmente está en modo Discovery. Para terminar de crear el recurso, deberá activar su proyecto.", + "pci_projects_project_activate_project_banner_cta": "Activar el proyecto" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_fr_CA.json b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_fr_CA.json new file mode 100644 index 000000000000..610f81b2fd45 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_fr_CA.json @@ -0,0 +1,4 @@ +{ + "pci_projects_project_activate_project_banner_message": "Vous êtes actuellement en mode \"Découverte\". Pour finaliser la création de votre ressource, vous devez activer votre projet.", + "pci_projects_project_activate_project_banner_cta": "Activer le projet" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_fr_FR.json b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_fr_FR.json new file mode 100644 index 000000000000..610f81b2fd45 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_fr_FR.json @@ -0,0 +1,4 @@ +{ + "pci_projects_project_activate_project_banner_message": "Vous êtes actuellement en mode \"Découverte\". Pour finaliser la création de votre ressource, vous devez activer votre projet.", + "pci_projects_project_activate_project_banner_cta": "Activer le projet" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_it_IT.json b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_it_IT.json new file mode 100644 index 000000000000..1a7510bcac10 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_it_IT.json @@ -0,0 +1,4 @@ +{ + "pci_projects_project_activate_project_banner_message": "Al momento stai utilizzando la modalità \"Discovery\". Per completare la creazione della tua risorsa, è necessario attivare il progetto.", + "pci_projects_project_activate_project_banner_cta": "Attivare il progetto" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_pl_PL.json b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_pl_PL.json new file mode 100644 index 000000000000..1fe0a98475ed --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_pl_PL.json @@ -0,0 +1,4 @@ +{ + "pci_projects_project_activate_project_banner_message": "Aktualnie jesteś w trybie Discovery. Aby dokończyć tworzenie zasobów, aktywowuj projekt.", + "pci_projects_project_activate_project_banner_cta": "Aktywuj projekt" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_pt_PT.json b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_pt_PT.json new file mode 100644 index 000000000000..8515fbdb5e46 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/activate-project-banner/Messages_pt_PT.json @@ -0,0 +1,4 @@ +{ + "pci_projects_project_activate_project_banner_message": "Atualmente, encontra-se no modo Descoberta. Para finalizar a criação do seu recurso, deve ativar o seu projeto.", + "pci_projects_project_activate_project_banner_cta": "Ativar o projeto" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/common/Messages_de_DE.json b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_de_DE.json new file mode 100644 index 000000000000..e9cfe255f5fc --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_de_DE.json @@ -0,0 +1,39 @@ +{ + "cpb_project_management_credit_vouchers": "Guthaben und Gutscheine", + "cpb_vouchers_your_voucher": "Ihr Gutschein", + "cpb_vouchers_your_voucher_add": "Meinen Gutschein hinzufügen", + "cpb_vouchers_get_error": "Die Liste der Gutscheine kann nicht angezeigt werden.", + "cpb_vouchers_bill_ref": "Rechnung Nr. {{billId}}", + "cpb_vouchers_products_all": "Alle", + "cpb_vouchers_name_credit_provisionning": "Cloud Guthaben", + "cpb_vouchers_credit_comment": "Das Cloud Guthaben kann weder übertragen noch zurückerstattet werden. Es hat keinen Geldwert, und nicht genutztes Guthaben verfällt nach Ablauf von 13 Monaten.", + "common_confirm": "Bestätigen", + "common_cancel": "Abbrechen", + "cpb_vouchers_voucher_cell": "Zugehöriger Gutschein", + "cpb_vouchers_name_cell": "Name", + "cpb_vouchers_total_credit_cell": "Ursprünglicher Wert", + "cpb_vouchers_available_credit_cell": "Verbleibendes Guthaben", + "cpb_vouchers_validity_from_cell": "Aktivierungsdatum", + "cpb_vouchers_validity_to_cell": "Gültigkeitsdatum", + "cpb_vouchers_products_cell": "Kompatible Produkte", + "cpb_vouchers_add_button": "Gutschein aktivieren", + "cpb_vouchers_add_credit_button": "Cloud Guthaben aufladen", + "cpb_vouchers_add_explain_bis": "Bei jeder Rechnungsausstellung wird der Rechnungsbetrag zuerst von Ihrem unten aufgeführten Cloud Guthaben, danach von Ihrem Digital Launch Pad Account und dann Ihrem Treue-Account abgezogen. Eventuell vorhandene Außenstände werden anschließend über Ihr hinterlegtes Zahlungsmittel abgerechnet (Details zu den drei letztgenannten Zahlungsarten finden Sie in Ihrem Kundencenter im Bereich „Abrechnung\").", + + "common_pagination_of": "von", + "common_pagination_results": "Ergebnisse", + + "cpb_vouchers_add_success": "Der Gutschein wurde erfolgreich hinzugefügt.", + "cpb_vouchers_add_error": "Der Gutschein konnte nicht hinzugefügt werden. Bitte versuchen Sie es erneut.", + + "cpb_vouchers_add_credit_title": "Cloud-Guthaben aufladen", + "cpb_vouchers_add_credit_info": "Wählen Sie den Betrag (ohne Mehrwertsteuer) aus, mit dem dieses Projekt aufgeladen werden soll. Sobald der Bestellschein beglichen wurde, wird dieses Guthaben für die Abrechnungen für Abos und Verbrauch dieses Projekts in den nächsten 12 Monaten verwendet.", + "cpb_vouchers_add_credit_amount": "Betrag der Aufladung ({{ currency }} zzgl. MwSt.)", + "cpb_vouchers_add_credit_valid": "Bestellschein erstellen", + "cpb_vouchers_add_credit_success": "Der Bestellschein für Ihr Guthaben in Höhe von {{ amount }} ist hier verfügbar.", + "cpb_vouchers_add_credit_load_err": "Beim Laden des Cloud-Guthabens ist ein Fehler aufgetreten.", + "cpb_vouchers_bill_ref": "Rechnung Nr. {{billId}}", + "common_field_error_required": "Bitte füllen Sie dieses Feld aus.", + "common_field_error_number": "Bitte geben Sie einen gültigen Zahlenwert ein.", + "common_field_error_min": "Bitte geben Sie einen Wert größer oder gleich {{min}} ein." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/common/Messages_en_GB.json b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_en_GB.json new file mode 100644 index 000000000000..c67a8fce0dea --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_en_GB.json @@ -0,0 +1,39 @@ +{ + "cpb_project_management_credit_vouchers": "Credits & Vouchers", + "cpb_vouchers_your_voucher": "Your voucher", + "cpb_vouchers_your_voucher_add": "Upload my voucher", + "cpb_vouchers_get_error": "Oops. We're unable to display list of vouchers.", + "cpb_vouchers_bill_ref": "Bill n° {{billId}}", + "cpb_vouchers_products_all": "All", + "cpb_vouchers_name_credit_provisionning": "Cloud credit", + "cpb_vouchers_credit_comment": "Public Cloud credit may not be transferred or reimbursed. It has no monetary value and any credit not used within 13 months will be lost.", + "common_confirm": "Confirm", + "common_cancel": "Cancel", + "cpb_vouchers_voucher_cell": "Associated voucher", + "cpb_vouchers_name_cell": "Name", + "cpb_vouchers_total_credit_cell": "Initial value", + "cpb_vouchers_available_credit_cell": "Remaining credit", + "cpb_vouchers_validity_from_cell": "Activation date", + "cpb_vouchers_validity_to_cell": "Validity date", + "cpb_vouchers_products_cell": "Eligible products", + "cpb_vouchers_add_button": "Use a voucher", + "cpb_vouchers_add_credit_button": "Buy Public Cloud credit", + "cpb_vouchers_add_explain_bis": "Whenever an invoice is issued, the amount owed is debited from your Cloud credit (see below), then in turn from your Digital Launch Pad account, and then from your loyalty account. And lastly, your potential debit balance is paid using the payment method we have on file (details regarding those three payment methods are available in the \"Billing\" section of the OVH Control Panel).", + + "common_pagination_of": "on", + "common_pagination_results": "results", + + "cpb_vouchers_add_success": "Voucher successfully uploaded.", + "cpb_vouchers_add_error": "Oops. We are unable to add this voucher. Please try again.", + + "cpb_vouchers_add_credit_title": "Buy Public Cloud credit", + "cpb_vouchers_add_credit_info": "Select the total (ex. VAT) you would like to credit for this project. Once the purchase order has been settled, this credit will be used for bills and project usage invoiced over the following 12 months.", + "cpb_vouchers_add_credit_amount": "Amount to credit (ex. VAT {{ currency }})", + "cpb_vouchers_add_credit_valid": "Generate a purchase order", + "cpb_vouchers_add_credit_success": "The purchase order for your {{ amount }} credit is available here.", + "cpb_vouchers_add_credit_load_err": "Oops! An error has occurred loading the cloud credit purchase.", + "cpb_vouchers_bill_ref": "Bill n° {{billId}}", + "common_field_error_required": "Please fill in this field.", + "common_field_error_number": "Please enter a valid numeric value.", + "common_field_error_min": "Please enter a value greater than or equal to {{min}}." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/common/Messages_es_ES.json b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_es_ES.json new file mode 100644 index 000000000000..3c1711cb1436 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_es_ES.json @@ -0,0 +1,39 @@ +{ + "cpb_project_management_credit_vouchers": "Crédito y códigos promocionales", + "cpb_vouchers_your_voucher": "Su código promocional", + "cpb_vouchers_your_voucher_add": "Añadir mi código promocional", + "cpb_vouchers_get_error": "¡Vaya! No se ha podido mostrar la lista de códigos promocionales.", + "cpb_vouchers_bill_ref": "Factura n.° {{billId}}", + "cpb_vouchers_products_all": "Todos", + "cpb_vouchers_name_credit_provisionning": "Crédito cloud ", + "cpb_vouchers_credit_comment": "El crédito cloud no es transferible ni reembolsable y no tiene ningún valor monetario. Si no se utiliza en un plazo de 13 meses, se pierde.", + "common_confirm": "Confirmar", + "common_cancel": "Cancelar", + "cpb_vouchers_voucher_cell": "Código promocional asociado", + "cpb_vouchers_name_cell": "Nombre", + "cpb_vouchers_total_credit_cell": "Valor inicial", + "cpb_vouchers_available_credit_cell": "Crédito restante", + "cpb_vouchers_validity_from_cell": "Fecha de activación", + "cpb_vouchers_validity_to_cell": "Fecha de validez", + "cpb_vouchers_products_cell": "Productos compatibles", + "cpb_vouchers_add_button": "Activar un código promocional", + "cpb_vouchers_add_credit_button": "Comprar crédito cloud", + "cpb_vouchers_add_explain_bis": "Cada factura se cargará de forma automática en su crédito cloud (abajo), a continuación en su cuenta Digital Launch Pad y, por último, en su cuenta de fidelidad. El posible saldo deudor se liquidará mediante la forma de pago registrada (en la sección «Facturación» de su área de cliente encontrará información sobre estas tres últimas formas de pago). ", + + "common_pagination_of": "de", + "common_pagination_results": "resultados", + + "cpb_vouchers_add_success": "El código promocional se ha añadido correctamente.", + "cpb_vouchers_add_error": "¡Vaya! No hemos podido añadir el código promocional. Por favor, vuelva a intentarlo.", + + "cpb_vouchers_add_credit_title": "Comprar crédito cloud", + "cpb_vouchers_add_credit_info": "Seleccione el importe que desea recargar (IVA no incluido) para este proyecto. Una vez abonada la orden de pedido, el crédito se utilizará para las cuotas fijas y el consumo de las facturas de este proyecto que se emitan en los próximos 12 meses.", + "cpb_vouchers_add_credit_amount": "Importe a recargar ({{ currency }}, IVA no incl.)", + "cpb_vouchers_add_credit_valid": "Generar una orden de pedido", + "cpb_vouchers_add_credit_success": "La orden de pedido de crédito por un importe de {{ amount }} está disponible aquí.", + "cpb_vouchers_add_credit_load_err": "¡Vaya! Se ha producido un error al carga la compra de crédito cloud.", + "cpb_vouchers_bill_ref": "Factura n.° {{billId}}", + "common_field_error_required": "Complete este campo.", + "common_field_error_number": "Introduzca un valor numérico válido.", + "common_field_error_min": "Introduzca un valor superior o igual a {{min}}." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/common/Messages_fr_CA.json b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_fr_CA.json new file mode 100644 index 000000000000..4342965ae950 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_fr_CA.json @@ -0,0 +1,38 @@ +{ + "cpb_project_management_credit_vouchers": "Crédits & Vouchers", + "cpb_vouchers_your_voucher": "Votre voucher", + "cpb_vouchers_your_voucher_add": "Ajouter mon voucher", + "cpb_vouchers_get_error": "Oups, nous n'arrivons pas à afficher la liste des vouchers.", + "cpb_vouchers_products_all": "Tous", + "cpb_vouchers_name_credit_provisionning": "Crédit Cloud", + "cpb_vouchers_credit_comment": "Le crédit cloud n'est pas transférable, ni remboursable. Il n'a aucune valeur monétaire et tout crédit non utilisé dans les 13 mois sera perdu.", + "common_confirm": "Confirmer", + "common_cancel": "Annuler", + "cpb_vouchers_voucher_cell": "Voucher associé", + "cpb_vouchers_name_cell": "Nom", + "cpb_vouchers_total_credit_cell": "Valeur initiale", + "cpb_vouchers_available_credit_cell": "Crédit restant", + "cpb_vouchers_validity_from_cell": "Date d'activation", + "cpb_vouchers_validity_to_cell": "Date de validité", + "cpb_vouchers_products_cell": "Produits éligibles", + "cpb_vouchers_add_button": "Activer un voucher", + "cpb_vouchers_add_credit_button": "Acheter du crédit cloud", + "cpb_vouchers_add_explain_bis": "A chaque émission de facture, le montant dû est débité de votre crédit Cloud (ci-dessous), puis successivement de votre votre compte Digital LaunchPad puis de votre compte fidélité. Le solde débiteur éventuel est enfin réglé à l'aide de votre moyen paiement enregistré (le détail concernant ces trois derniers modes de paiement est disponible dans la section \"Facturation\" de votre espace client).", + + "common_pagination_of": "sur", + "common_pagination_results": "résultats", + + "cpb_vouchers_add_success": "Le voucher a été ajouté avec succès.", + "cpb_vouchers_add_error": "Oups, nous n'arrivons pas a ajouter ce voucher. Veuillez réessayer.", + + "cpb_vouchers_add_credit_title": "Acheter du crédit cloud", + "cpb_vouchers_add_credit_info": "Choisissez la somme (hors taxes) à créditer sur ce projet. Une fois le bon de commande réglé, ce crédit sera utilisé pour les forfaits et consommations de ce projet pour les factures éditées au cours des 12 prochains mois.", + "cpb_vouchers_add_credit_amount": "Somme à créditer (HT {{ currency }})", + "cpb_vouchers_add_credit_valid": "Générer un bon de commande", + "cpb_vouchers_add_credit_success": "Le bon de commande pour votre crédit de {{ amount }} est disponible ici.", + "cpb_vouchers_add_credit_load_err": "Oups, une erreur est survenue lors du chargement de l’achat de crédit cloud.", + "cpb_vouchers_bill_ref": "Facture n° {{billId}}", + "common_field_error_required": "Veuillez compléter ce champ.", + "common_field_error_number": "Veuillez saisir une valeur numérique valide.", + "common_field_error_min": "Veuillez saisir une valeur plus grande ou égale à {{min}}." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/common/Messages_fr_FR.json b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_fr_FR.json new file mode 100644 index 000000000000..4342965ae950 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_fr_FR.json @@ -0,0 +1,38 @@ +{ + "cpb_project_management_credit_vouchers": "Crédits & Vouchers", + "cpb_vouchers_your_voucher": "Votre voucher", + "cpb_vouchers_your_voucher_add": "Ajouter mon voucher", + "cpb_vouchers_get_error": "Oups, nous n'arrivons pas à afficher la liste des vouchers.", + "cpb_vouchers_products_all": "Tous", + "cpb_vouchers_name_credit_provisionning": "Crédit Cloud", + "cpb_vouchers_credit_comment": "Le crédit cloud n'est pas transférable, ni remboursable. Il n'a aucune valeur monétaire et tout crédit non utilisé dans les 13 mois sera perdu.", + "common_confirm": "Confirmer", + "common_cancel": "Annuler", + "cpb_vouchers_voucher_cell": "Voucher associé", + "cpb_vouchers_name_cell": "Nom", + "cpb_vouchers_total_credit_cell": "Valeur initiale", + "cpb_vouchers_available_credit_cell": "Crédit restant", + "cpb_vouchers_validity_from_cell": "Date d'activation", + "cpb_vouchers_validity_to_cell": "Date de validité", + "cpb_vouchers_products_cell": "Produits éligibles", + "cpb_vouchers_add_button": "Activer un voucher", + "cpb_vouchers_add_credit_button": "Acheter du crédit cloud", + "cpb_vouchers_add_explain_bis": "A chaque émission de facture, le montant dû est débité de votre crédit Cloud (ci-dessous), puis successivement de votre votre compte Digital LaunchPad puis de votre compte fidélité. Le solde débiteur éventuel est enfin réglé à l'aide de votre moyen paiement enregistré (le détail concernant ces trois derniers modes de paiement est disponible dans la section \"Facturation\" de votre espace client).", + + "common_pagination_of": "sur", + "common_pagination_results": "résultats", + + "cpb_vouchers_add_success": "Le voucher a été ajouté avec succès.", + "cpb_vouchers_add_error": "Oups, nous n'arrivons pas a ajouter ce voucher. Veuillez réessayer.", + + "cpb_vouchers_add_credit_title": "Acheter du crédit cloud", + "cpb_vouchers_add_credit_info": "Choisissez la somme (hors taxes) à créditer sur ce projet. Une fois le bon de commande réglé, ce crédit sera utilisé pour les forfaits et consommations de ce projet pour les factures éditées au cours des 12 prochains mois.", + "cpb_vouchers_add_credit_amount": "Somme à créditer (HT {{ currency }})", + "cpb_vouchers_add_credit_valid": "Générer un bon de commande", + "cpb_vouchers_add_credit_success": "Le bon de commande pour votre crédit de {{ amount }} est disponible ici.", + "cpb_vouchers_add_credit_load_err": "Oups, une erreur est survenue lors du chargement de l’achat de crédit cloud.", + "cpb_vouchers_bill_ref": "Facture n° {{billId}}", + "common_field_error_required": "Veuillez compléter ce champ.", + "common_field_error_number": "Veuillez saisir une valeur numérique valide.", + "common_field_error_min": "Veuillez saisir une valeur plus grande ou égale à {{min}}." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/common/Messages_it_IT.json b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_it_IT.json new file mode 100644 index 000000000000..1a890cecde26 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_it_IT.json @@ -0,0 +1,39 @@ +{ + "cpb_project_management_credit_vouchers": "Crediti e voucher", + "cpb_vouchers_your_voucher": "Il tuo voucher", + "cpb_vouchers_your_voucher_add": "Aggiungi un voucher", + "cpb_vouchers_get_error": "Impossibile visualizzare la lista dei voucher", + "cpb_vouchers_bill_ref": "Fattura n. {{billId}}", + "cpb_vouchers_products_all": "Tutti", + "cpb_vouchers_name_credit_provisionning": "Credito Cloud", + "cpb_vouchers_credit_comment": "Il credito Cloud non è trasferibile né rimborsabile e non ha valore monetario. Il credito non utilizzato entro 13 mesi verrà perso.", + "common_confirm": "Conferma", + "common_cancel": "Annulla", + "cpb_vouchers_voucher_cell": "Voucher associato", + "cpb_vouchers_name_cell": "Nome", + "cpb_vouchers_total_credit_cell": "Valore iniziale", + "cpb_vouchers_available_credit_cell": "Credito residuo", + "cpb_vouchers_validity_from_cell": "Data di attivazione", + "cpb_vouchers_validity_to_cell": "Data di validità", + "cpb_vouchers_products_cell": "Prodotti compatibili", + "cpb_vouchers_add_button": "Attiva un voucher", + "cpb_vouchers_add_credit_button": "Acquista credito Cloud", + "cpb_vouchers_add_explain_bis": "Per ogni fattura, verifichiamo che tu abbia un voucher o un altro tipo di credito. L'eventuale importo residuo deve essere saldato utilizzando la modalità di pagamento che hai registrato (i dettagli relativi alle modalità di pagamento sono disponibili nella sezione \"Fatturazione\" del tuo Spazio Cliente OVH).", + + "common_pagination_of": "su", + "common_pagination_results": "risultati", + + "cpb_vouchers_add_success": "Il voucher è stato aggiunto correttamente.", + "cpb_vouchers_add_error": "Impossibile aggiungere questo voucher, ti preghiamo di riprovare.", + + "cpb_vouchers_add_credit_title": "Acquista credito Cloud", + "cpb_vouchers_add_credit_info": "Scegli l'importo (IVA esclusa) da assegnare a questo progetto. Una volta saldato l’ordine, il credito verrà utilizzato nei prossimi 12 mesi per il pagamento delle fatture relative ai forfait e ai consumi del progetto.", + "cpb_vouchers_add_credit_amount": "Somma da accreditare (+IVA {{ currency }}):", + "cpb_vouchers_add_credit_valid": "Genera un ordine", + "cpb_vouchers_add_credit_success": "Il buono d'ordine relativo al tuo credito di {{ amount }} è disponibile qui.", + "cpb_vouchers_add_credit_load_err": "Si è verificato un errore durante il caricamento dell'acquisto di credito Cloud.", + "cpb_vouchers_bill_ref": "Fattura n. {{billId}}", + "common_field_error_required": "Completa questo campo", + "common_field_error_number": "Inserisci un valore numerico valido", + "common_field_error_min": "Inserisci un valore maggiore o uguale a {{min}}" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/common/Messages_pl_PL.json b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_pl_PL.json new file mode 100644 index 000000000000..d083eba2af62 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_pl_PL.json @@ -0,0 +1,39 @@ +{ + "cpb_project_management_credit_vouchers": "Zasilenia i vouchery", + "cpb_vouchers_your_voucher": "Twój voucher", + "cpb_vouchers_your_voucher_add": "Dodaj voucher", + "cpb_vouchers_get_error": "Wystąpił problem z wyświetleniem listy voucherów.", + "cpb_vouchers_bill_ref": "Faktura nr {{billId}}", + "cpb_vouchers_products_all": "Wszystkie", + "cpb_vouchers_name_credit_provisionning": "Zasilenie konta cloud", + "cpb_vouchers_credit_comment": "Zasilenie cloud to opcja płatności, której nie można przenieść na inny projekt i za którą nie można wykonać zwrotu. Nie ma ona żadnej wartości pieniężnej a zasilenie niewykorzystane przez 13 miesięcy zostanie utracone.", + "common_confirm": "Potwierdź", + "common_cancel": "Anuluj", + "cpb_vouchers_voucher_cell": "Przypisany voucher", + "cpb_vouchers_name_cell": "Nazwa", + "cpb_vouchers_total_credit_cell": "Wartość początkowa", + "cpb_vouchers_available_credit_cell": "Pozostałe zasilenie", + "cpb_vouchers_validity_from_cell": "Data aktywacji", + "cpb_vouchers_validity_to_cell": "Data ważności", + "cpb_vouchers_products_cell": "Produkty spełniające wymagania", + "cpb_vouchers_add_button": "Dodaj voucher", + "cpb_vouchers_add_credit_button": "Zamów zasilenie konta cloud", + "cpb_vouchers_add_explain_bis": "Po wystawieniu faktury kwota do zapłaty jest pobierana z konta cloud, następnie z konta Digital LaunchPad i z konta przedpłaconego. Saldo ujemne jest regulowane za pomocą zarejestrowanego sposobu płatności.", + + "common_pagination_of": "z", + "common_pagination_results": "wyniki", + + "cpb_vouchers_add_success": "Voucher został dodany.", + "cpb_vouchers_add_error": "Wystąpił problem z dodaniem vouchera. Spróbuj ponownie.", + + "cpb_vouchers_add_credit_title": "Zamów zasilenie konta cloud", + "cpb_vouchers_add_credit_info": "Wybierz kwotę (netto), jaką chcesz zasilić ten projekt. Po opłaceniu zamówienia Twoje konto zostanie zasilone. Kwotę tę będziesz mógł wykorzystać do opłacenia faktur wystawionych w ciągu kolejnych 12 miesięcy za zasoby tego projektu.", + "cpb_vouchers_add_credit_amount": "Kwota do zasilenia (netto {{ currency }} ):", + "cpb_vouchers_add_credit_valid": "Utwórz zamówienie", + "cpb_vouchers_add_credit_success": "Zamówienie dotyczące zasilenia na kwotę {{ amount }} jest dostępne tutaj.", + "cpb_vouchers_add_credit_load_err": "Wystąpił błąd pobierania informacji o zamówieniu zasilenia konta cloud.", + "cpb_vouchers_bill_ref": "Faktura nr {{billId}}", + "common_field_error_required": "Wypełnij to pole.", + "common_field_error_number": "Wprowadź poprawną wartość liczbową.", + "common_field_error_min": "Wprowadź wartość większą lub równą {{min}}." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/common/Messages_pt_PT.json b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_pt_PT.json new file mode 100644 index 000000000000..96db833c7e09 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/common/Messages_pt_PT.json @@ -0,0 +1,39 @@ +{ + "cpb_project_management_credit_vouchers": "Créditos e Vouchers", + "cpb_vouchers_your_voucher": "O seu voucher", + "cpb_vouchers_your_voucher_add": "Adicionar o meu voucher", + "cpb_vouchers_get_error": "Lamentamos, mas não foi possível carregar a lista de vouchers.", + "cpb_vouchers_bill_ref": "Fatura n° {{billId}}", + "cpb_vouchers_products_all": "Todos", + "cpb_vouchers_name_credit_provisionning": "Crédito Cloud", + "cpb_vouchers_credit_comment": "O crédito cloud não é transferível ou reembolsável. Não tem qualquer valor monetário e todo o crédito não utilizado durante 13 meses será perdido.", + "common_confirm": "Confirmar", + "common_cancel": "Anular", + "cpb_vouchers_voucher_cell": "Voucher associado", + "cpb_vouchers_name_cell": "Nome", + "cpb_vouchers_total_credit_cell": "Valor inicial", + "cpb_vouchers_available_credit_cell": "Crédito atual", + "cpb_vouchers_validity_from_cell": "Data de ativação", + "cpb_vouchers_validity_to_cell": "Data de validade", + "cpb_vouchers_products_cell": "Produtos elegíveis", + "cpb_vouchers_add_button": "Ativar um voucher", + "cpb_vouchers_add_credit_button": "Adquirir um crédito cloud", + "cpb_vouchers_add_explain_bis": "A cada emissão da fatura, o montante devido é debitado do seu crédito Cloud (abaixo), e depois sucessivamente da sua conta Digital LaunchPad e depois da sua conta fidelidade. O saldo que ficar em dívida será pago através do seu método de pagamento registado (os detalhes dos três últimos métodos de pagamento estão disponíveis na secção \"Faturação\" da sua Área de Cliente).", + + "common_pagination_of": "em", + "common_pagination_results": "resultados", + + "cpb_vouchers_add_success": "O voucher foi adicionado com sucesso.", + "cpb_vouchers_add_error": "Lamentamos, mas não foi possível adicionar este voucher. Tente novamente mais tarde.", + + "cpb_vouchers_add_credit_title": "Adquirir um crédito cloud", + "cpb_vouchers_add_credit_info": "Selecione o montante (sem IVA) que pretende creditar para este projeto. Uma vez o pagamento efetuado, o crédito será utilizado para os tarifários e consumos deste projeto para as faturas editadas durante os próximos 12 meses.", + "cpb_vouchers_add_credit_amount": "Montante a creditar ({{ currency }} s/IVA)", + "cpb_vouchers_add_credit_valid": "Gerar uma nota de encomenda", + "cpb_vouchers_add_credit_success": "A nota de encomenda para o seu crédito de {{ amount }} está disponível aqui.", + "cpb_vouchers_add_credit_load_err": "Lamentamos, mas ocorreu um erro ao adquirir o crédito cloud.", + "cpb_vouchers_bill_ref": "Fatura n° {{billId}}", + "common_field_error_required": "Preencha o campo.", + "common_field_error_number": "Introduza um valor numérico válido.", + "common_field_error_min": "Introduza um valor superior ou igual a {{min}}." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/error/Messages_de_DE.json b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_de_DE.json new file mode 100644 index 000000000000..8e10000b4500 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_de_DE.json @@ -0,0 +1,8 @@ +{ + "manager_error_page_title": "Hoppla!", + "manager_error_page_button_cancel": "Abbrechen", + "manager_error_page_detail_code": "Fehlercode: ", + "manager_error_page_action_reload_label": "Erneut versuchen", + "manager_error_page_action_home_label": "Zurück zur Startseite", + "manager_error_page_default": "Beim Laden der Seite ist ein Fehler aufgetreten." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/error/Messages_en_GB.json b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_en_GB.json new file mode 100644 index 000000000000..b17691e2bc6d --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_en_GB.json @@ -0,0 +1,8 @@ +{ + "manager_error_page_title": "Oops!", + "manager_error_page_button_cancel": "Cancel", + "manager_error_page_detail_code": "Error code: ", + "manager_error_page_action_reload_label": "Try again", + "manager_error_page_action_home_label": "Back to homepage", + "manager_error_page_default": "An error has occurred loading the page." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/error/Messages_es_ES.json b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_es_ES.json new file mode 100644 index 000000000000..15fc5f79256d --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_es_ES.json @@ -0,0 +1,8 @@ +{ + "manager_error_page_title": "¡Vaya!", + "manager_error_page_button_cancel": "Cancelar", + "manager_error_page_detail_code": "Código de error: ", + "manager_error_page_action_reload_label": "Volver a intentarlo", + "manager_error_page_action_home_label": "Volver a la página de inicio", + "manager_error_page_default": "Se ha producido un error al cargar la página." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/error/Messages_fr_CA.json b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_fr_CA.json new file mode 100644 index 000000000000..2c575c63588e --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_fr_CA.json @@ -0,0 +1,8 @@ +{ + "manager_error_page_title": "Oops …!", + "manager_error_page_button_cancel": "Annuler", + "manager_error_page_detail_code": "Code d'erreur : ", + "manager_error_page_action_reload_label": "Réessayer", + "manager_error_page_action_home_label": "Retour à la page d'accueil", + "manager_error_page_default": "Une erreur est survenue lors du chargement de la page." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/error/Messages_fr_FR.json b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_fr_FR.json new file mode 100644 index 000000000000..2c575c63588e --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_fr_FR.json @@ -0,0 +1,8 @@ +{ + "manager_error_page_title": "Oops …!", + "manager_error_page_button_cancel": "Annuler", + "manager_error_page_detail_code": "Code d'erreur : ", + "manager_error_page_action_reload_label": "Réessayer", + "manager_error_page_action_home_label": "Retour à la page d'accueil", + "manager_error_page_default": "Une erreur est survenue lors du chargement de la page." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/error/Messages_it_IT.json b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_it_IT.json new file mode 100644 index 000000000000..fa5055b8cec5 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_it_IT.json @@ -0,0 +1,8 @@ +{ + "manager_error_page_title": "Ops!", + "manager_error_page_button_cancel": "Annullare", + "manager_error_page_detail_code": "Codice di errore: ", + "manager_error_page_action_reload_label": "Riprova", + "manager_error_page_action_home_label": "Torna alla home page", + "manager_error_page_default": "Si è verificato un errore durante il caricamento della pagina." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/error/Messages_pl_PL.json b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_pl_PL.json new file mode 100644 index 000000000000..eceb9bcca2ca --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_pl_PL.json @@ -0,0 +1,8 @@ +{ + "manager_error_page_title": "Ojej...", + "manager_error_page_button_cancel": "Anuluj", + "manager_error_page_detail_code": "Kod błędu: ", + "manager_error_page_action_reload_label": "Spróbuj ponownie", + "manager_error_page_action_home_label": "Powrót do strony głównej", + "manager_error_page_default": "Wystąpił błąd podczas ładowania strony." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/error/Messages_pt_PT.json b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_pt_PT.json new file mode 100644 index 000000000000..25fac9551c86 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/error/Messages_pt_PT.json @@ -0,0 +1,8 @@ +{ + "manager_error_page_title": "Oops!", + "manager_error_page_button_cancel": "Anular", + "manager_error_page_detail_code": "Código de erro: ", + "manager_error_page_action_reload_label": "Tentar novamente", + "manager_error_page_action_home_label": "Voltar para a página inicial", + "manager_error_page_default": "Ocorreu um erro ao carregar a página." +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_de_DE.json b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_de_DE.json new file mode 100644 index 000000000000..c2ad5ae4adf8 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_de_DE.json @@ -0,0 +1,34 @@ +{ + "pci_project_guides_header": "Anleitungen", + "pci_project_guides_header_all_guides": "Alle Anleitungen", + "pci_project_guides_header_all_storage_guides": "Alle Storage- und Backup-Anleitungen", + "pci_project_guides_header_first_steps_with_instances": "Erste Schritte mit den Instanzen", + "pci_project_guides_header_ip_fail_over": "Failover-IP", + "pci_project_guides_header_user_root_and_password": "Root-Benutzer und Passwort", + "pci_project_guides_header_reverse_dns": "Reverse DNS", + "pci_project_guides_header_first_steps_with_databases": "Erste Schritte mit den Datenbanken (EN)", + "pci_project_guides_header_mongo_db_capabilities_and_limitations": "MongoDB – Kapazitäten und Einschränkungen (EN)", + "pci_project_guides_header_mysql_capabilities_and_limitations": "MySQL – Kapazitäten und Einschränkungen (EN)", + "pci_project_guides_header_create_a_cluster": "Einen Cluster erstellen (EN)", + "pci_project_guides_header_deploy_an_application": "Eine Anwendung deployen (EN)", + "pci_project_guides_header_loadbalancer_kube": "Kubernetes Load Balancer", + "pci_project_guides_header_faq_managed_private_registry": "Managed Private Registry (Harbor) FAQ", + "pci_project_guides_header_create_a_managed_private_register": "Managed Private Registry erstellen (EN)", + "pci_project_guides_header_create_and_use_a_private_image": "Privates Image erstellen und verwenden (EN)", + "pci_project_guides_header_differences_between_ai_notebooks_ai_training_ai_apps": "Die Unterschiede zwischen AI Notebooks, AI Training und AI Deploy (EN)", + "pci_project_guides_header_ai_apps_capabilities_and_limitations": "AI Deploy - Kapazitäten und Einschränkungen (EN)", + "pci_project_guides_header_accessing_your_ai_apps_with_tokens": "Per Token auf Ihre KI-Anwendung zugreifen", + "pci_project_guides_header_presentation_of_data_processing": "Einführung Data Processing (EN)", + "pci_project_guides_header_data_processing_capabilities_and_limitations": "Data Processing – Kapazitäten und Einschränkungen (EN)", + "pci_project_guides_header_submit_a_java_scala_job": "Java/Scala Job senden (EN)", + "pci_project_guides_header_ai_notebooks_startup": "Erste Schritte (EN)", + "pci_project_guides_header_ai_notebooks_definition": "Definition (EN)", + "pci_project_guides_header_using_data_form_object_storage": "Object Storage Daten verwenden", + "pci_project_guides_header_ai_training_capabilities_and_limitations": "AI Training – Kapazitäten und Einschränkungen (EN)", + "pci_project_guides_header_submit_a_job_via_the_user_interface": "Einen Job über das Benutzerinterface senden (EN)", + "pci_project_guides_header_managing_a_custom_image": "Individuelles Image verwalten (EN)", + "pci_project_guides_header_deploying_a_custom_model": "Benutzerdefiniertes Modell einrichten (EN)", + "pci_project_guides_header_models_definition": "Modelle – Definition (EN)", + "pci_project_guides_header_exporting_a_tensorflow_model": "TensorFlow-Modell exportieren (EN)", + "pci_project_guides_header_public_cloud_guides": "Alle Anleitungen zu Public Cloud" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_en_GB.json b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_en_GB.json new file mode 100644 index 000000000000..43b0f2978285 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_en_GB.json @@ -0,0 +1,34 @@ +{ + "pci_project_guides_header": "Guides", + "pci_project_guides_header_all_guides": "All guides", + "pci_project_guides_header_all_storage_guides": "All storage and backup guides", + "pci_project_guides_header_first_steps_with_instances": "Getting started with instances", + "pci_project_guides_header_ip_fail_over": "Failover IP", + "pci_project_guides_header_user_root_and_password": "Root user and password", + "pci_project_guides_header_reverse_dns": "Reverse DNS", + "pci_project_guides_header_first_steps_with_databases": "Getting started with databases (EN)", + "pci_project_guides_header_mongo_db_capabilities_and_limitations": "MongoDB - Capabilities and limitations (EN)", + "pci_project_guides_header_mysql_capabilities_and_limitations": "MySQL - Capabilities and limitations (EN)", + "pci_project_guides_header_create_a_cluster": "Creating a cluster (EN)", + "pci_project_guides_header_deploy_an_application": "Deploying an application (EN)", + "pci_project_guides_header_loadbalancer_kube": "Kubernetes Load Balancer", + "pci_project_guides_header_faq_managed_private_registry": "Managed Private Registry FAQ (Harbor)", + "pci_project_guides_header_create_a_managed_private_register": "Creating a Managed Private Registry (EN)", + "pci_project_guides_header_create_and_use_a_private_image": "Creating and using a private image (EN)", + "pci_project_guides_header_differences_between_ai_notebooks_ai_training_ai_apps": "Differences between AI Notebooks, AI Training, AI Deploy (EN)", + "pci_project_guides_header_ai_apps_capabilities_and_limitations": "AI Deploy - Capabilities and limitations (EN)", + "pci_project_guides_header_accessing_your_ai_apps_with_tokens": "Accessing your AI application with tokens", + "pci_project_guides_header_presentation_of_data_processing": "Introduction to Data Processing (EN)", + "pci_project_guides_header_data_processing_capabilities_and_limitations": "Data Processing - Capabilities and limitations (EN)", + "pci_project_guides_header_submit_a_java_scala_job": "Submitting a Java/Scala job (EN)", + "pci_project_guides_header_ai_notebooks_startup": "Startup (EN)", + "pci_project_guides_header_ai_notebooks_definition": "Definition (EN)", + "pci_project_guides_header_using_data_form_object_storage": "Using Object Storage data (EN)", + "pci_project_guides_header_ai_training_capabilities_and_limitations": "AI Training - Capabilities and limitations (EN)", + "pci_project_guides_header_submit_a_job_via_the_user_interface": "Submitting a job via the user interface (EN)", + "pci_project_guides_header_managing_a_custom_image": "Managing a custom image (EN)", + "pci_project_guides_header_deploying_a_custom_model": "Deploying a custom model (EN)", + "pci_project_guides_header_models_definition": "Models - definition (EN)", + "pci_project_guides_header_exporting_a_tensorflow_model": "Exporting a TensorFlow model (EN)", + "pci_project_guides_header_public_cloud_guides": "All Public Cloud guides" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_es_ES.json b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_es_ES.json new file mode 100644 index 000000000000..fd17719e2696 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_es_ES.json @@ -0,0 +1,34 @@ +{ + "pci_project_guides_header": "Guías", + "pci_project_guides_header_all_guides": "Todas las guías", + "pci_project_guides_header_all_storage_guides": "Todas las guías de almacenamiento y backup", + "pci_project_guides_header_first_steps_with_instances": "Primeros pasos con instancias", + "pci_project_guides_header_ip_fail_over": "IP failover", + "pci_project_guides_header_user_root_and_password": "Usuario root y contraseña", + "pci_project_guides_header_reverse_dns": "Registro DNS inverso", + "pci_project_guides_header_first_steps_with_databases": "Primeros pasos con bases de datos (EN)", + "pci_project_guides_header_mongo_db_capabilities_and_limitations": "MongoDB: capacidades y limitaciones (EN)", + "pci_project_guides_header_mysql_capabilities_and_limitations": "MySQL: capacidades y limitaciones (EN)", + "pci_project_guides_header_create_a_cluster": "Crear un cluster (EN)", + "pci_project_guides_header_deploy_an_application": "Desplegar una app (EN)", + "pci_project_guides_header_loadbalancer_kube": "Load Balancer Kubernetes", + "pci_project_guides_header_faq_managed_private_registry": "FAQ sobre Managed Private Registry (Harbor)", + "pci_project_guides_header_create_a_managed_private_register": "Crear un registro privado administrado (EN)", + "pci_project_guides_header_create_and_use_a_private_image": "Crear y utilizar una imagen privada (EN)", + "pci_project_guides_header_differences_between_ai_notebooks_ai_training_ai_apps": "Diferencias entre AI Notebooks, AI Training y AI Deploy (EN)", + "pci_project_guides_header_ai_apps_capabilities_and_limitations": "AI Deploy: capacidades y limitaciones (EN)", + "pci_project_guides_header_accessing_your_ai_apps_with_tokens": "Acceder a una app de IA con tokens", + "pci_project_guides_header_presentation_of_data_processing": "Data Processing: presentación (EN)", + "pci_project_guides_header_data_processing_capabilities_and_limitations": "Data Processing: capacidades y limitaciones (EN)", + "pci_project_guides_header_submit_a_java_scala_job": "Enviar un job Java/Scala (EN)", + "pci_project_guides_header_ai_notebooks_startup": "Primeros pasos (EN)", + "pci_project_guides_header_ai_notebooks_definition": "Definición (EN)", + "pci_project_guides_header_using_data_form_object_storage": "Utilizar los datos de Object Storage (EN)", + "pci_project_guides_header_ai_training_capabilities_and_limitations": "AI Training: capacidades y limitaciones (EN)", + "pci_project_guides_header_submit_a_job_via_the_user_interface": "Enviar un job a través de la interfaz de usuario (EN)", + "pci_project_guides_header_managing_a_custom_image": "Gestión de una imagen personalizada (EN)", + "pci_project_guides_header_deploying_a_custom_model": "Desplegar un modelo personalizado (EN)", + "pci_project_guides_header_models_definition": "Modelos: definición (EN)", + "pci_project_guides_header_exporting_a_tensorflow_model": "Exportar un modelo TensorFlow (EN)", + "pci_project_guides_header_public_cloud_guides": "Todas las guías de Public Cloud" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_fr_CA.json b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_fr_CA.json new file mode 100644 index 000000000000..4466d95915a5 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_fr_CA.json @@ -0,0 +1,34 @@ +{ + "pci_project_guides_header": "Guides", + "pci_project_guides_header_all_guides": "Tous les guides", + "pci_project_guides_header_all_storage_guides": "Tous les guides stockage et sauvegarde", + "pci_project_guides_header_first_steps_with_instances": "Premiers pas avec les instances", + "pci_project_guides_header_ip_fail_over": "IP fail-over", + "pci_project_guides_header_user_root_and_password": "Utilisateur root et mot de passe", + "pci_project_guides_header_reverse_dns": "Reverse DNS", + "pci_project_guides_header_first_steps_with_databases": "Premiers pas avec les bases de données (EN)", + "pci_project_guides_header_mongo_db_capabilities_and_limitations": "MongoDB - Capacités et limitations (EN)", + "pci_project_guides_header_mysql_capabilities_and_limitations": "MySQL - Capacités et limitations (EN)", + "pci_project_guides_header_create_a_cluster": "Créer un cluster (EN)", + "pci_project_guides_header_deploy_an_application": "Déployer une application (EN)", + "pci_project_guides_header_loadbalancer_kube": "LoadBalancer Kubernetes", + "pci_project_guides_header_faq_managed_private_registry": "FAQ Managed Private Registry (Harbor)", + "pci_project_guides_header_create_a_managed_private_register": "Créer un Registre privé géré (EN)", + "pci_project_guides_header_create_and_use_a_private_image": "Créer et utiliser une image privée (EN)", + "pci_project_guides_header_differences_between_ai_notebooks_ai_training_ai_apps": "Différences entre AI Notebooks, AI Training, AI Deploy (EN)", + "pci_project_guides_header_ai_apps_capabilities_and_limitations": "AI Deploy - Capacités et limitations (EN)", + "pci_project_guides_header_accessing_your_ai_apps_with_tokens": "Accéder à votre application IA avec des tokens", + "pci_project_guides_header_presentation_of_data_processing": "Présentation de Data Processing (EN)", + "pci_project_guides_header_data_processing_capabilities_and_limitations": "Data Processing - Capacités et limitations (EN)", + "pci_project_guides_header_submit_a_java_scala_job": "Soumettre un job Java/Scala (EN)", + "pci_project_guides_header_ai_notebooks_startup": "Démarrage (EN)", + "pci_project_guides_header_ai_notebooks_definition": "Définition (EN)", + "pci_project_guides_header_using_data_form_object_storage": "Utiliser les données de l'Object Storage (EN)", + "pci_project_guides_header_ai_training_capabilities_and_limitations": "AI Training - Capacités et limitations (EN)", + "pci_project_guides_header_submit_a_job_via_the_user_interface": "Soumettre un job via l'interface utilisateur (EN)", + "pci_project_guides_header_managing_a_custom_image": "Gestion d'une image personnalisée (EN)", + "pci_project_guides_header_deploying_a_custom_model": "Déployer un modèle personnalisé (EN)", + "pci_project_guides_header_models_definition": "Modèles - définition (EN)", + "pci_project_guides_header_exporting_a_tensorflow_model": "Exporter un modèle TensorFlow (EN)", + "pci_project_guides_header_public_cloud_guides": "Tous les guides Public Cloud" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_fr_FR.json b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_fr_FR.json new file mode 100644 index 000000000000..4466d95915a5 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_fr_FR.json @@ -0,0 +1,34 @@ +{ + "pci_project_guides_header": "Guides", + "pci_project_guides_header_all_guides": "Tous les guides", + "pci_project_guides_header_all_storage_guides": "Tous les guides stockage et sauvegarde", + "pci_project_guides_header_first_steps_with_instances": "Premiers pas avec les instances", + "pci_project_guides_header_ip_fail_over": "IP fail-over", + "pci_project_guides_header_user_root_and_password": "Utilisateur root et mot de passe", + "pci_project_guides_header_reverse_dns": "Reverse DNS", + "pci_project_guides_header_first_steps_with_databases": "Premiers pas avec les bases de données (EN)", + "pci_project_guides_header_mongo_db_capabilities_and_limitations": "MongoDB - Capacités et limitations (EN)", + "pci_project_guides_header_mysql_capabilities_and_limitations": "MySQL - Capacités et limitations (EN)", + "pci_project_guides_header_create_a_cluster": "Créer un cluster (EN)", + "pci_project_guides_header_deploy_an_application": "Déployer une application (EN)", + "pci_project_guides_header_loadbalancer_kube": "LoadBalancer Kubernetes", + "pci_project_guides_header_faq_managed_private_registry": "FAQ Managed Private Registry (Harbor)", + "pci_project_guides_header_create_a_managed_private_register": "Créer un Registre privé géré (EN)", + "pci_project_guides_header_create_and_use_a_private_image": "Créer et utiliser une image privée (EN)", + "pci_project_guides_header_differences_between_ai_notebooks_ai_training_ai_apps": "Différences entre AI Notebooks, AI Training, AI Deploy (EN)", + "pci_project_guides_header_ai_apps_capabilities_and_limitations": "AI Deploy - Capacités et limitations (EN)", + "pci_project_guides_header_accessing_your_ai_apps_with_tokens": "Accéder à votre application IA avec des tokens", + "pci_project_guides_header_presentation_of_data_processing": "Présentation de Data Processing (EN)", + "pci_project_guides_header_data_processing_capabilities_and_limitations": "Data Processing - Capacités et limitations (EN)", + "pci_project_guides_header_submit_a_java_scala_job": "Soumettre un job Java/Scala (EN)", + "pci_project_guides_header_ai_notebooks_startup": "Démarrage (EN)", + "pci_project_guides_header_ai_notebooks_definition": "Définition (EN)", + "pci_project_guides_header_using_data_form_object_storage": "Utiliser les données de l'Object Storage (EN)", + "pci_project_guides_header_ai_training_capabilities_and_limitations": "AI Training - Capacités et limitations (EN)", + "pci_project_guides_header_submit_a_job_via_the_user_interface": "Soumettre un job via l'interface utilisateur (EN)", + "pci_project_guides_header_managing_a_custom_image": "Gestion d'une image personnalisée (EN)", + "pci_project_guides_header_deploying_a_custom_model": "Déployer un modèle personnalisé (EN)", + "pci_project_guides_header_models_definition": "Modèles - définition (EN)", + "pci_project_guides_header_exporting_a_tensorflow_model": "Exporter un modèle TensorFlow (EN)", + "pci_project_guides_header_public_cloud_guides": "Tous les guides Public Cloud" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_it_IT.json b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_it_IT.json new file mode 100644 index 000000000000..d5d3f275713b --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_it_IT.json @@ -0,0 +1,34 @@ +{ + "pci_project_guides_header": "Guide", + "pci_project_guides_header_all_guides": "Tutte le guide", + "pci_project_guides_header_all_storage_guides": "Tutte le guide di storage e backup", + "pci_project_guides_header_first_steps_with_instances": "Iniziare a utilizzare le istanze", + "pci_project_guides_header_ip_fail_over": "IP Failover", + "pci_project_guides_header_user_root_and_password": "Utente root e password", + "pci_project_guides_header_reverse_dns": "Reverse DNS", + "pci_project_guides_header_first_steps_with_databases": "Iniziare a utilizzare i database (EN)", + "pci_project_guides_header_mongo_db_capabilities_and_limitations": "MongoDB - Funzionalità e limiti (EN)", + "pci_project_guides_header_mysql_capabilities_and_limitations": "MySQL - Funzionalità e limiti (EN)", + "pci_project_guides_header_create_a_cluster": "Creare un cluster (EN)", + "pci_project_guides_header_deploy_an_application": "Eseguire un'applicazione (EN)", + "pci_project_guides_header_loadbalancer_kube": "Load Balancer Kubernetes", + "pci_project_guides_header_faq_managed_private_registry": "FAQ Managed Private Registry (Harbor)", + "pci_project_guides_header_create_a_managed_private_register": "Creare un Registro privato gestito (EN)", + "pci_project_guides_header_create_and_use_a_private_image": "Creare e utilizzare un'immagine privata (EN)", + "pci_project_guides_header_differences_between_ai_notebooks_ai_training_ai_apps": "Differenze tra AI Notebooks, AI Training, AI Deploy (EN)", + "pci_project_guides_header_ai_apps_capabilities_and_limitations": "AI Deploy - Capacità e limitazioni (EN)", + "pci_project_guides_header_accessing_your_ai_apps_with_tokens": "Accedere a un’applicazione di IA tramite token", + "pci_project_guides_header_presentation_of_data_processing": "Presentazione di Data Processing (EN)", + "pci_project_guides_header_data_processing_capabilities_and_limitations": "Data Processing - Funzionalità e limiti (EN)", + "pci_project_guides_header_submit_a_java_scala_job": "Inviare un job Java/Scala (EN)", + "pci_project_guides_header_ai_notebooks_startup": "Primi passi (EN)", + "pci_project_guides_header_ai_notebooks_definition": "Definizione (EN)", + "pci_project_guides_header_using_data_form_object_storage": "Utilizzare i dati dell'Object Storage (EN)", + "pci_project_guides_header_ai_training_capabilities_and_limitations": "AI Training - Funzionalità e limiti (EN)", + "pci_project_guides_header_submit_a_job_via_the_user_interface": "Inviare un job tramite l'interfaccia utente (EN)", + "pci_project_guides_header_managing_a_custom_image": "Gestire un'immagine personalizzata (EN)", + "pci_project_guides_header_deploying_a_custom_model": "Eseguire un modello personalizzato (EN)", + "pci_project_guides_header_models_definition": "Modelli - definizione (EN)", + "pci_project_guides_header_exporting_a_tensorflow_model": "Esportare un modello TensorFlow (EN)", + "pci_project_guides_header_public_cloud_guides": "Tutte le guide Public Cloud" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_pl_PL.json b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_pl_PL.json new file mode 100644 index 000000000000..9ba010141c5d --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_pl_PL.json @@ -0,0 +1,34 @@ +{ + "pci_project_guides_header": "Przewodniki", + "pci_project_guides_header_all_guides": "Wszystkie przewodniki", + "pci_project_guides_header_all_storage_guides": "Wszystkie przewodniki dotyczące przestrzeni dyskowej i kopii zapasowych", + "pci_project_guides_header_first_steps_with_instances": "Pierwsze kroki z instancjami", + "pci_project_guides_header_ip_fail_over": "IP Failover", + "pci_project_guides_header_user_root_and_password": "Użytkownik root i hasło", + "pci_project_guides_header_reverse_dns": "Rewers DNS", + "pci_project_guides_header_first_steps_with_databases": "Pierwsze kroki z bazami danych (EN)", + "pci_project_guides_header_mongo_db_capabilities_and_limitations": "MongoDB - możliwości i ograniczenia (EN)", + "pci_project_guides_header_mysql_capabilities_and_limitations": "MySQL - możliwości i ograniczenia (EN)", + "pci_project_guides_header_create_a_cluster": "Utwórz klaster (EN)", + "pci_project_guides_header_deploy_an_application": "Uruchom aplikację (EN)", + "pci_project_guides_header_loadbalancer_kube": "Load Balancer Kubernetes", + "pci_project_guides_header_faq_managed_private_registry": "FAQ Managed Private Registry (Harbor)", + "pci_project_guides_header_create_a_managed_private_register": "Utwórz zarządzany Prywatny rejestr (EN)", + "pci_project_guides_header_create_and_use_a_private_image": "Utwórz i korzystaj z prywatnego obrazu (EN)", + "pci_project_guides_header_differences_between_ai_notebooks_ai_training_ai_apps": "Różnice między AI Notebooks, AI Training, AI Deploy (EN)", + "pci_project_guides_header_ai_apps_capabilities_and_limitations": "AI Deploy - Możliwości i ograniczenia (EN)", + "pci_project_guides_header_accessing_your_ai_apps_with_tokens": "Dostęp do aplikacji AI z tokenami", + "pci_project_guides_header_presentation_of_data_processing": "Prezentacja Data Processing (EN)", + "pci_project_guides_header_data_processing_capabilities_and_limitations": "Data Processing - możliwości i ograniczenia (EN)", + "pci_project_guides_header_submit_a_java_scala_job": "Dodaj zadanie Java/Scala (EN)", + "pci_project_guides_header_ai_notebooks_startup": "Uruchomienie (EN)", + "pci_project_guides_header_ai_notebooks_definition": "Definicja (EN)", + "pci_project_guides_header_using_data_form_object_storage": "Korzystaj z danych Object Storage (EN)", + "pci_project_guides_header_ai_training_capabilities_and_limitations": "AI Training - możliwości i ograniczenia (EN)", + "pci_project_guides_header_submit_a_job_via_the_user_interface": "Dodaj zadanie za pomocą interfejsu użytkownika (EN)", + "pci_project_guides_header_managing_a_custom_image": "Zarządzanie spersonalizowanym obrazem (EN)", + "pci_project_guides_header_deploying_a_custom_model": "Uruchom spersonalizowany model (EN)", + "pci_project_guides_header_models_definition": "Modele - definicja (EN)", + "pci_project_guides_header_exporting_a_tensorflow_model": "Eksportuj model TensorFlow (EN)", + "pci_project_guides_header_public_cloud_guides": "Wszystkie przewodniki Public Cloud" +} diff --git a/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_pt_PT.json b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_pt_PT.json new file mode 100644 index 000000000000..a2e73af33a20 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/public/translations/guides-header/Messages_pt_PT.json @@ -0,0 +1,34 @@ +{ + "pci_project_guides_header": "Manuais", + "pci_project_guides_header_all_guides": "Todos os manuais", + "pci_project_guides_header_all_storage_guides": "Todos os manuais de armazenamento e backup", + "pci_project_guides_header_first_steps_with_instances": "Primeiros passos com as instâncias", + "pci_project_guides_header_ip_fail_over": "IP Failover", + "pci_project_guides_header_user_root_and_password": "Utilizador root e palavra-passe", + "pci_project_guides_header_reverse_dns": "Reverse DNS", + "pci_project_guides_header_first_steps_with_databases": "Primeiros passos com as bases de dados (EN)", + "pci_project_guides_header_mongo_db_capabilities_and_limitations": "MongoDB - Capacidades e limitações (EN)", + "pci_project_guides_header_mysql_capabilities_and_limitations": "MySQL - Capacidades e limitações (EN)", + "pci_project_guides_header_create_a_cluster": "Criar um cluster (EN)", + "pci_project_guides_header_deploy_an_application": "Implementar uma aplicação (EN)", + "pci_project_guides_header_loadbalancer_kube": "LoadBalancer Kubernetes", + "pci_project_guides_header_faq_managed_private_registry": "FAQ Managed Private Registry (Harbor)", + "pci_project_guides_header_create_a_managed_private_register": "Criar um registo privado gerido (EN)", + "pci_project_guides_header_create_and_use_a_private_image": "Criar e utilizar uma imagem privada (EN)", + "pci_project_guides_header_differences_between_ai_notebooks_ai_training_ai_apps": "Diferenças entre AI Notebooks, AI Training, AI Deploy (EN)", + "pci_project_guides_header_ai_apps_capabilities_and_limitations": "AI Deploy - Capacidades e limitações (EN)", + "pci_project_guides_header_accessing_your_ai_apps_with_tokens": "Aceder à sua aplicação IA com tokens", + "pci_project_guides_header_presentation_of_data_processing": "Apresentação do Data Processing (EN)", + "pci_project_guides_header_data_processing_capabilities_and_limitations": "Data Processing - Capacidades e limitações (EN)", + "pci_project_guides_header_submit_a_java_scala_job": "Submeter um job Java/Scala (EN)", + "pci_project_guides_header_ai_notebooks_startup": "Arranque (EN)", + "pci_project_guides_header_ai_notebooks_definition": "Definição (EN)", + "pci_project_guides_header_using_data_form_object_storage": "Utilizar os dados do Object Storage (EN)", + "pci_project_guides_header_ai_training_capabilities_and_limitations": "AI Training - Capacidades e limitações (EN)", + "pci_project_guides_header_submit_a_job_via_the_user_interface": "Submeter um job através da interface de utilizador (EN)", + "pci_project_guides_header_managing_a_custom_image": "Gestão de uma imagem personalizada (EN)", + "pci_project_guides_header_deploying_a_custom_model": "Implementar um modelo personalizado (EN)", + "pci_project_guides_header_models_definition": "Modelos - definição (EN)", + "pci_project_guides_header_exporting_a_tensorflow_model": "Exportar um modelo TensorFlow (EN)", + "pci_project_guides_header_public_cloud_guides": "Todos os manuais do Public Cloud" +} diff --git a/packages/manager/apps/pci-vouchers/src/App.tsx b/packages/manager/apps/pci-vouchers/src/App.tsx new file mode 100644 index 000000000000..89094db8cf27 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/App.tsx @@ -0,0 +1,26 @@ +import { RouterProvider, createHashRouter } from 'react-router-dom'; +import { QueryClientProvider } from '@tanstack/react-query'; +import { ReactQueryDevtools } from '@tanstack/react-query-devtools'; +import { odsSetup } from '@ovhcloud/ods-common-core'; + +import appRoutes from '@/routes'; +import queryClient from './queryClient'; + +import '@ovhcloud/ods-theme-blue-jeans'; + +odsSetup(); + +const router = createHashRouter(appRoutes); + +function App() { + return ( + <> + + + + + + ); +} + +export default App; diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/__test-utils__/contextRenders.tsx b/packages/manager/apps/pci-vouchers/src/__tests__/__test-utils__/contextRenders.tsx new file mode 100644 index 000000000000..cec287691e76 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/__test-utils__/contextRenders.tsx @@ -0,0 +1,34 @@ +import React from 'react'; +import { render } from '@testing-library/react'; +import { I18nextProvider } from 'react-i18next'; +import { initShell } from '@ovh-ux/shell'; +import { QueryClient, QueryClientProvider } from '@tanstack/react-query'; + +import i18n from '../config/i18nTestConfig'; +import { ApplicationProvider } from '../../context'; +import { ContainerProvider } from '../../core/container'; + +const renderWithI18n = (children, { ...renderOptions }) => { + return render( + {children}, + renderOptions, + ); +}; + +const renderWithShell = async (children, { environment, ...renderOptions }) => { + const shell = await initShell(); + const queryClient = new QueryClient(); + + return render( + + + + {children} + + + , + renderOptions, + ); +}; + +export { renderWithI18n, renderWithShell }; diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/components/AddVoucherModal.spec.tsx b/packages/manager/apps/pci-vouchers/src/__tests__/components/AddVoucherModal.spec.tsx new file mode 100644 index 000000000000..bc46cacbe336 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/components/AddVoucherModal.spec.tsx @@ -0,0 +1,82 @@ +import 'element-internals-polyfill'; +import { describe, expect, vi } from 'vitest'; +import { QueryClientProvider } from '@tanstack/react-query'; +import { act, fireEvent, render, screen } from '@testing-library/react'; +import '@testing-library/jest-dom'; + +import AddVoucherModal from '@/components/vouchers/AddVoucherModal'; +import { useAddVoucher } from '@/hooks/useVouchers'; +import queryClient from '@/queryClient'; + +vi.mock('@ovh-ux/manager-react-shell-client', async () => ({ + useEnvironment: () => ({ + user: {}, + }), +})); + +vi.mock('react-i18next', () => ({ + // this mock makes sure any components using the translation hook can use it without a warning being shown + useTranslation: () => { + return { + t: (str: string) => str, + i18n: { + changeLanguage: () => new Promise(() => {}), + }, + }; + }, + initReactI18next: { + type: '3rdParty', + init: () => {}, + }, +})); + +vi.mock('@/hooks/useVouchers', () => { + const add = vi.fn(() => {}); + return { + useAddVoucher: () => ({ + add, + }), + }; +}); + +function renderModal() { + render( + + {}} + onError={() => {}} + onSuccess={() => {}} + > + , + , + ); +} + +describe('Add voucher modal', () => { + it('should call the add function with given voucher id', async () => { + const useAdd = useAddVoucher({ + projectId: 'foo', + onSuccess: () => {}, + onError: () => {}, + }); + renderModal(); + const voucherInput = screen.getByTestId('voucherId'); + const submitButton = screen.getByTestId('submitButton'); + expect(useAdd.add).not.toHaveBeenCalled(); + act(() => { + fireEvent.change(voucherInput, { + target: { + value: 'hello', + }, + }); + // it seems we have to manually trigger the ods event + voucherInput.odsValueChange.emit({ value: 'hello' }); + }); + expect(voucherInput.value).toBe('hello'); + act(() => { + fireEvent.click(submitButton); + }); + expect(useAdd.add).toHaveBeenCalledWith('hello'); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/components/AvailableCredit.spec.tsx b/packages/manager/apps/pci-vouchers/src/__tests__/components/AvailableCredit.spec.tsx new file mode 100644 index 000000000000..bf2f3353e92f --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/components/AvailableCredit.spec.tsx @@ -0,0 +1,27 @@ +import { describe, expect, vi } from 'vitest'; +import { render, screen, waitFor } from '@testing-library/react'; +import { ReactNode } from 'react'; +import '@testing-library/jest-dom'; + +import CreditCell from '@/components/vouchers/listing/Credit'; +import { Credit } from '@/interface'; + +vi.mock('@ovhcloud/manager-components', async () => ({ + DataGridTextCell: ({ children }: { children: ReactNode }) => <>{children}, +})); + +describe('AvailableCredit component display Voucher available Credit', () => { + it('render available credit', async () => { + const availableCredit: Credit = { + text: '9,99€', + value: 9.99, + currencyCode: '€', + }; + + render(); + const priceText = await screen.findByText(availableCredit.text); + await waitFor(() => { + expect(priceText).toBeInTheDocument(); + }); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/components/BreadCrumbs.spec.tsx b/packages/manager/apps/pci-vouchers/src/__tests__/components/BreadCrumbs.spec.tsx new file mode 100644 index 000000000000..ebc5bec5000a --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/components/BreadCrumbs.spec.tsx @@ -0,0 +1,36 @@ +import { describe, expect, vi } from 'vitest'; +import { render, screen } from '@testing-library/react'; +import BreadCrumbs from '@/components/BreadCrumbs'; + +vi.mock('react-router-dom', async () => ({ + useMatches: () => { + return [ + { + data: 'foo', + handle: { + crumb: (i: string) => `crumb-${i}`, + }, + }, + { + data: 'bar', + handle: { + crumb: (i: string) => `crumb-${i}`, + }, + }, + { + data: 'baz', + handle: {}, + }, + ]; + }, +})); + +describe('BreadCrumbs component', () => { + it('should list react router matches', async () => { + render(); + const crumbs = screen.getAllByText(/crumb/); + expect(crumbs.length).toBe(2); + expect(crumbs[0].innerHTML).toBe('crumb-foo'); + expect(crumbs[1].innerHTML).toBe('crumb-bar'); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/components/BuyCreditModal.spec.tsx b/packages/manager/apps/pci-vouchers/src/__tests__/components/BuyCreditModal.spec.tsx new file mode 100644 index 000000000000..aa4d5da2c62c --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/components/BuyCreditModal.spec.tsx @@ -0,0 +1,148 @@ +import 'element-internals-polyfill'; +import { describe, expect, vi } from 'vitest'; +import { QueryClientProvider } from '@tanstack/react-query'; +import { act, fireEvent, render, screen } from '@testing-library/react'; +import '@testing-library/jest-dom'; + +import BuyCreditModal from '@/components/vouchers/BuyCreditModal'; +import { useBuyCredit } from '@/hooks/useVouchers'; +import queryClient from '@/queryClient'; + +// HTMLElement.prototype.attachInternals = () => {}; + +vi.mock('@ovh-ux/manager-react-shell-client', async () => ({ + useEnvironment: () => ({ + user: {}, + }), +})); + +vi.mock('react-i18next', () => ({ + // this mock makes sure any components using the translation hook can use it without a warning being shown + useTranslation: () => { + return { + t: (str: string) => str, + i18n: { + changeLanguage: () => new Promise(() => {}), + }, + }; + }, + initReactI18next: { + type: '3rdParty', + init: () => {}, + }, +})); + +vi.mock('@/hooks/useVouchers', () => { + const buy = vi.fn(() => {}); + return { + useBuyCredit: () => ({ + buy, + }), + }; +}); + +function renderModal() { + render( + + {}} + onError={() => {}} + onSuccess={() => {}} + > + , + , + ); +} + +describe('Buy credit modal', () => { + it('should call the buy function with given amount', async () => { + const useBuy = useBuyCredit({ + projectId: 'foo', + onSuccess: () => {}, + onError: () => {}, + }); + renderModal(); + const amountInput = screen.getByTestId('amountInput'); + const submitButton = screen.getByTestId('submitButton'); + expect(useBuy.buy).not.toHaveBeenCalled(); + act(() => { + fireEvent.change(amountInput, { + target: { + value: 25, + }, + }); + // it seems we have to manually trigger the ods event + amountInput.odsValueChange.emit({ value: 25 }); + }); + expect(amountInput.value).toBe(25); + act(() => { + fireEvent.click(submitButton); + }); + expect(useBuy.buy).toHaveBeenCalledWith(25); + }); + + it('should disable submit button if no amount is specified', async () => { + renderModal(); + const amountInput = screen.getByTestId('amountInput'); + const submitButton = screen.getByTestId('submitButton'); + expect(submitButton).not.toHaveAttribute('disabled'); + act(() => { + fireEvent.change(amountInput, { + target: { + value: 0, + }, + }); + // it seems we have to manually trigger the ods event + amountInput.odsValueChange.emit({ value: 0 }); + }); + expect(amountInput.value).toBe(0); + expect(submitButton).toHaveAttribute('disabled'); + }); + + it('should only allows numerical values for amount', async () => { + renderModal(); + const amountInput = screen.getByTestId('amountInput'); + const submitButton = screen.getByTestId('submitButton'); + expect(submitButton).not.toHaveAttribute('disabled'); + act(() => { + fireEvent.change(amountInput, { + target: { + value: 'hello', + }, + }); + // it seems we have to manually trigger the ods event + amountInput.odsValueChange.emit({ value: 'hello' }); + }); + expect(amountInput.value).toBe(NaN); + expect(submitButton).toHaveAttribute('disabled'); + }); + + it('should only allows up to 8 digits for amount', async () => { + render( + + {}} + onError={() => {}} + onSuccess={() => {}} + > + , + , + ); + const amountInput = screen.getByTestId('amountInput'); + const submitButton = screen.getByTestId('submitButton'); + expect(submitButton).not.toHaveAttribute('disabled'); + act(() => { + fireEvent.change(amountInput, { + target: { + value: 123456789, + }, + }); + // it seems we have to manually trigger the ods event + amountInput.odsValueChange.emit({ value: 123456789 }); + }); + expect(amountInput.value).toBe(123456789); + expect(submitButton).toHaveAttribute('disabled'); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/Credit.spec.tsx b/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/Credit.spec.tsx new file mode 100644 index 000000000000..d78c6c445026 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/Credit.spec.tsx @@ -0,0 +1,21 @@ +import { describe, expect, vi } from 'vitest'; +import { render, screen, waitFor } from '@testing-library/react'; +import '@testing-library/jest-dom'; +import { ReactNode } from 'react'; +import Credit from '@/components/vouchers/listing/Credit'; + +vi.mock('@ovhcloud/manager-components', async () => ({ + DataGridTextCell: ({ children }: { children: ReactNode }) => <>{children}, +})); + +describe('Datagrid Listing Credit', () => { + it('should display credit text', async () => { + render(); + + const productContent = screen.getByText('10 €'); + + await waitFor(() => { + expect(productContent).toBeInTheDocument(); + }); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/DisplayName.spec.tsx b/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/DisplayName.spec.tsx new file mode 100644 index 000000000000..7211f3aba542 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/DisplayName.spec.tsx @@ -0,0 +1,75 @@ +import { describe, expect, vi } from 'vitest'; +import { QueryClient, QueryClientProvider } from '@tanstack/react-query'; +import { render, screen, waitFor } from '@testing-library/react'; +import '@testing-library/jest-dom'; +import { ReactNode } from 'react'; +import DisplayName from '@/components/vouchers/listing/DisplayName'; + +vi.mock('react-i18next', () => ({ + // this mock makes sure any components using the translate hook can use it without a warning being shown + useTranslation: () => { + return { + t: (str: string) => str, + i18n: { + changeLanguage: () => new Promise(() => {}), + }, + }; + }, + initReactI18next: { + type: '3rdParty', + init: () => {}, + }, +})); + +vi.mock('@/data/bill', () => { + return { + getBill: () => ({ + pdfUrl: 'http://ovh.com', + }), + }; +}); + +vi.mock('@ovhcloud/manager-components', async () => ({ + DataGridTextCell: ({ children }: { children: ReactNode }) => <>{children}, +})); + +describe('Datagrid Listing Product', () => { + it('should display product description', async () => { + render( + , + ); + + const productContent = screen.getByText('Voucher description'); + + await waitFor(() => { + expect(productContent).toBeInTheDocument(); + }); + }); + + it('should display bill url', async () => { + const queryClient = new QueryClient(); + render( + + + , + ); + + const spinnerElement = screen.getByTestId('spinner'); + expect(spinnerElement).toBeInTheDocument(); + + await waitFor(() => { + const provisionningContent = screen.getByText( + 'cpb_vouchers_name_credit_provisionning', + ); + + const billContent = screen.getByText('cpb_vouchers_bill_ref'); + + expect(provisionningContent).toBeInTheDocument(); + expect(billContent).toBeInTheDocument(); + }); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/Product.spec.tsx b/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/Product.spec.tsx new file mode 100644 index 000000000000..a7e4bcc465b2 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/Product.spec.tsx @@ -0,0 +1,47 @@ +import { describe, expect, vi } from 'vitest'; +import { render, screen, waitFor } from '@testing-library/react'; +import '@testing-library/jest-dom'; +import { ReactNode } from 'react'; +import Product from '@/components/vouchers/listing/Product'; + +vi.mock('@ovhcloud/manager-components', async () => ({ + DataGridTextCell: ({ children }: { children: ReactNode }) => <>{children}, +})); + +vi.mock('react-i18next', () => ({ + // this mock makes sure any components using the translate hook can use it without a warning being shown + useTranslation: () => { + return { + t: (str: string) => str, + i18n: { + changeLanguage: () => new Promise(() => {}), + }, + }; + }, + initReactI18next: { + type: '3rdParty', + init: () => {}, + }, +})); + +describe('Datagrid Listing Product', () => { + it('should display list of products', async () => { + render(); + + const productContent = screen.getByText('A, B'); + + await waitFor(() => { + expect(productContent).toBeInTheDocument(); + }); + }); + + it('should display default text if no product defined', async () => { + render(); + + const productContent = screen.getByText('cpb_vouchers_products_all'); + + await waitFor(() => { + expect(productContent).toBeInTheDocument(); + }); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/Validity.spec.tsx b/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/Validity.spec.tsx new file mode 100644 index 000000000000..e408bd118667 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/components/vouchers/listing/Validity.spec.tsx @@ -0,0 +1,88 @@ +import { ReactNode } from 'react'; +import { describe, expect, vi } from 'vitest'; +import { useTranslation } from 'react-i18next'; +import { format } from 'date-fns'; +import * as dateFnsLocales from 'date-fns/locale'; +import { render, screen, waitFor } from '@testing-library/react'; +import '@testing-library/jest-dom'; + +import Validity from '@/components/vouchers/listing/Validity'; + +const mocks = vi.hoisted(() => { + return { + useTranslation: vi.fn(), + }; +}); + +vi.mock('react-i18next', () => { + return { + useTranslation: mocks.useTranslation, + initReactI18next: { + type: '3rdParty', + init: () => {}, + }, + }; +}); + +vi.mock('date-fns', () => { + const formatMock = vi.fn(() => 'formattedDate'); + return { + format: formatMock, + }; +}); + +vi.mock('@ovhcloud/manager-components', async () => ({ + DataGridTextCell: ({ children }: { children: ReactNode }) => <>{children}, +})); + +describe('Datagrid Validity Cell', () => { + it('should display date based on language', async () => { + mocks.useTranslation.mockImplementationOnce(() => ({ + t: (str: string) => str, + i18n: { + language: 'fr_FR', + }, + })); + + // const trans = useTranslation('common') + expect(useTranslation).not.toHaveBeenCalled(); + expect(format).not.toHaveBeenCalled(); + + render(); + + const formattedDate = screen.getByText('formattedDate'); + + await waitFor(() => { + expect(useTranslation).toHaveBeenCalled(); + expect(format).toHaveBeenCalledWith( + new Date('2007-01-09T09:41:00.000Z'), + 'PPpp', + { locale: dateFnsLocales.fr }, + ); + expect(formattedDate).toBeInTheDocument(); + }); + }); + + it('should display date based on language DE', async () => { + mocks.useTranslation.mockImplementationOnce(() => ({ + t: (str: string) => str, + i18n: { + language: 'de_DE', + }, + })); + + render(); + + const formattedDate2 = screen.getByText('formattedDate'); + + await waitFor(() => { + expect(useTranslation).toHaveBeenCalled(); + expect(format).toHaveBeenCalledWith( + new Date('2007-01-09T09:41:00.000Z'), + 'PPpp', + { locale: dateFnsLocales.de }, + ); + expect(formattedDate2).toBeInTheDocument(); + }); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/config/i18nTestConfig.js b/packages/manager/apps/pci-vouchers/src/__tests__/config/i18nTestConfig.js new file mode 100644 index 000000000000..40bdd456f5f7 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/config/i18nTestConfig.js @@ -0,0 +1,11 @@ +import i18n from 'i18next'; +import { initReactI18next } from 'react-i18next'; + +i18n.use(initReactI18next).init({ + lng: 'fr', + fallbackLng: 'fr', + // have a common namespace used around the full app + ns: [], +}); + +export default i18n; diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/core/HidePreloader.spec.tsx b/packages/manager/apps/pci-vouchers/src/__tests__/core/HidePreloader.spec.tsx new file mode 100644 index 000000000000..b3972b769da1 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/core/HidePreloader.spec.tsx @@ -0,0 +1,21 @@ +import { describe, vi } from 'vitest'; +import { render } from '@testing-library/react'; +import { useUX } from '@ovh-ux/manager-react-shell-client'; +import HidePreloader from '@/core/HidePreloader'; + +vi.mock('@ovh-ux/manager-react-shell-client', () => { + const hidePreloader = vi.fn(() => {}); + return { + useUX: () => ({ + hidePreloader, + }), + }; +}); + +describe('HidePreloader', () => { + it('should call hidePreloader function from shell ux plugin', async () => { + expect(useUX().hidePreloader).not.toHaveBeenCalled(); + render(); + expect(useUX().hidePreloader).toHaveBeenCalled(); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/data/bill.spec.ts b/packages/manager/apps/pci-vouchers/src/__tests__/data/bill.spec.ts new file mode 100644 index 000000000000..b7e010f57468 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/data/bill.spec.ts @@ -0,0 +1,25 @@ +import { describe, expect, vi } from 'vitest'; +import { v6 } from '@ovh-ux/manager-core-api'; +import { getBill } from '@/data/bill'; + +vi.mock('@ovh-ux/manager-core-api', () => { + const get = vi.fn(() => { + return Promise.resolve({ data: {} }); + }); + return { + v6: { + get, + }, + }; +}); + +describe('bill data', () => { + afterEach(() => { + vi.clearAllMocks(); + }); + it('should call me bill api', async () => { + expect(v6.get).not.toHaveBeenCalled(); + getBill('123'); + expect(v6.get).toHaveBeenCalledWith(`/me/bill/123`); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/data/project.spec.ts b/packages/manager/apps/pci-vouchers/src/__tests__/data/project.spec.ts new file mode 100644 index 000000000000..85646dbce022 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/data/project.spec.ts @@ -0,0 +1,25 @@ +import { describe, expect, vi } from 'vitest'; +import { v6 } from '@ovh-ux/manager-core-api'; +import { getProject } from '@/data/project'; + +vi.mock('@ovh-ux/manager-core-api', () => { + const get = vi.fn(() => { + return Promise.resolve({ data: null }); + }); + return { + v6: { + get, + }, + }; +}); + +describe('project data', () => { + afterEach(() => { + vi.clearAllMocks(); + }); + it('should call cloud project apiv6 with project id', async () => { + expect(v6.get).not.toHaveBeenCalled(); + getProject('foo'); + expect(v6.get).toHaveBeenCalledWith('/cloud/project/foo'); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/data/utils.spec.ts b/packages/manager/apps/pci-vouchers/src/__tests__/data/utils.spec.ts new file mode 100644 index 000000000000..b36167dc58ae --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/data/utils.spec.ts @@ -0,0 +1,83 @@ +import { describe, expect, vi } from 'vitest'; +import { v6 } from '@ovh-ux/manager-core-api'; +import { + creditComparator, + defaultCompareFunction, + validityComparator, +} from '@/data/utils'; +import { Voucher } from '@/interface'; + +const voucherA = { + id: 1, + bill: null, + products: null, + description: 'description', + voucher: 'AAA', + validity: { + from: null, + to: '2007-01-09T09:41:00+00:00', + }, + total_credit: { + text: '200 €', + value: 200, + currencyCode: 'EUR', + }, + available_credit: { + text: '50 €', + value: 50, + currencyCode: 'EUR', + }, + used_credit: { + text: '150 €', + value: 150, + currencyCode: 'EUR', + }, +}; + +const voucherB = { + id: 2, + bill: null, + products: null, + description: 'description', + voucher: 'ABA', + validity: { + from: '2007-01-09T09:41:00+00:00', + to: '2006-01-09T09:41:00+00:00', + }, + total_credit: { + text: '100 €', + value: 100, + currencyCode: 'EUR', + }, + available_credit: { + text: '90 €', + value: 90, + currencyCode: 'EUR', + }, + used_credit: { + text: '10 €', + value: 10, + currencyCode: 'EUR', + }, +}; + +describe('utils data', () => { + it('should compare voucher keys', async () => { + const sortFunction = defaultCompareFunction('voucher'); + expect(sortFunction(voucherA, voucherB)).toBe(-1); + }); + + it('should compare voucher credit', async () => { + const availableSortFunction = creditComparator('available_credit'); + const totalSortFunction = creditComparator('total_credit'); + expect(availableSortFunction(voucherA, voucherB)).toBe(-1); + expect(totalSortFunction(voucherA, voucherB)).toBe(1); + }); + + it('should compare validity', async () => { + const fromSortFunction = validityComparator('from'); + const toSortFunction = validityComparator('to'); + expect(fromSortFunction(voucherA, voucherB)).toBe(-1); + expect(toSortFunction(voucherA, voucherB)).toBe(1); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/data/voucher.spec.ts b/packages/manager/apps/pci-vouchers/src/__tests__/data/voucher.spec.ts new file mode 100644 index 000000000000..e63b0ea8fd02 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/data/voucher.spec.ts @@ -0,0 +1,38 @@ +import { describe, expect, vi } from 'vitest'; +import { v6 } from '@ovh-ux/manager-core-api'; +import { addVoucher, buyCredit } from '@/data/voucher'; + +vi.mock('@ovh-ux/manager-core-api', () => { + const post = vi.fn(() => { + return Promise.resolve({ data: {} }); + }); + return { + v6: { + post, + }, + }; +}); + +describe('voucher data', () => { + afterEach(() => { + vi.clearAllMocks(); + }); + it('should post voucher code when adding a voucher', async () => { + expect(v6.post).not.toHaveBeenCalled(); + addVoucher('projectid123', 'voucherid123'); + expect(v6.post).toHaveBeenCalledWith('/cloud/project/projectid123/credit', { + code: 'voucherid123', + }); + }); + it('should post amount when buying credit', async () => { + expect(v6.post).not.toHaveBeenCalled(); + const result = await buyCredit('projectid123', 25); + expect(v6.post).toHaveBeenCalledWith( + '/order/cloud/project/projectid123/credit', + { + amount: 25, + }, + ); + expect(result.amount).toBe(25); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/__tests__/data/vouchers.spec.ts b/packages/manager/apps/pci-vouchers/src/__tests__/data/vouchers.spec.ts new file mode 100644 index 000000000000..6c7b697ee7bb --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/__tests__/data/vouchers.spec.ts @@ -0,0 +1,72 @@ +import { describe, expect, vi } from 'vitest'; +import { fetchIcebergV6 } from '@ovh-ux/manager-core-api'; +import { getAllVouchers, paginateResults } from '@/data/vouchers'; + +vi.mock('@ovh-ux/manager-core-api', () => { + const mock = vi.fn(() => { + return Promise.resolve({ data: {} }); + }); + return { + fetchIcebergV6: mock, + }; +}); + +function voucherList(count: number) { + return new Array(count).map((i) => ({ + id: i, + bill: `bill-${i}`, + products: `product-${i}`, + description: `description-${i}`, + voucher: `voucher-${i}`, + validity: { from: '', to: '' }, + total_credit: { text: '', value: 0, currencyCode: '' }, + available_credit: { text: '', value: 0, currencyCode: '' }, + used_credit: { text: '', value: 0, currencyCode: '' }, + })); +} + +describe('vouchers data', () => { + afterEach(() => { + vi.clearAllMocks(); + }); + it('should call credit api to list vouchers', async () => { + expect(fetchIcebergV6).not.toHaveBeenCalled(); + getAllVouchers('123'); + expect(fetchIcebergV6).toHaveBeenCalledWith({ + route: `/cloud/project/123/credit`, + disableCache: true, + }); + }); + it('should paginate results', async () => { + expect( + paginateResults(voucherList(11), { + pageIndex: 0, + pageSize: 5, + }).pageCount, + ).toBe(3); + expect( + paginateResults(voucherList(11), { + pageIndex: 9, + pageSize: 5, + }).rows.length, + ).toBe(0); + expect( + paginateResults(voucherList(11), { + pageIndex: 2, + pageSize: 5, + }).rows.length, + ).toBe(1); + expect( + paginateResults(voucherList(17), { + pageIndex: 0, + pageSize: 3, + }).rows.length, + ).toBe(3); + expect( + paginateResults(voucherList(11), { + pageIndex: 1, + pageSize: 5, + }).rows.length, + ).toBe(5); + }); +}); diff --git a/packages/manager/apps/pci-vouchers/src/components/BreadCrumbs.tsx b/packages/manager/apps/pci-vouchers/src/components/BreadCrumbs.tsx new file mode 100644 index 000000000000..ef5640a35cfa --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/BreadCrumbs.tsx @@ -0,0 +1,24 @@ +import { useMatches } from 'react-router-dom'; + +interface Handle { + crumb: CallableFunction; +} + +export default function BreadCrumbs() { + const matches = useMatches(); + const crumbs = matches + // first get rid of any matches that don't have handle and crumb + .filter((match) => Boolean((match.handle as Handle)?.crumb)) + // now map them into an array of elements, passing the loader + // data to each one + .map((match) => (match.handle as Handle).crumb(match.data)); + return ( + <> +
    + {crumbs.map((crumb, index) => ( +
  1. {crumb}
  2. + ))} +
+ + ); +} diff --git a/packages/manager/apps/pci-vouchers/src/components/activate-project-banner/ActivateProjectBanner.tsx b/packages/manager/apps/pci-vouchers/src/components/activate-project-banner/ActivateProjectBanner.tsx new file mode 100644 index 000000000000..55c04ecf026f --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/activate-project-banner/ActivateProjectBanner.tsx @@ -0,0 +1,43 @@ +import { OsdsButton, OsdsMessage } from '@ovhcloud/ods-components/react'; +import { ODS_BUTTON_SIZE, ODS_MESSAGE_TYPE } from '@ovhcloud/ods-components'; +import { ODS_THEME_COLOR_INTENT } from '@ovhcloud/ods-common-theming'; +import { useTranslation } from 'react-i18next'; +import { useNavigation } from '@ovh-ux/manager-react-shell-client'; + +export default function ActivateProjectBanner({ + projectId, +}: { + projectId: string; +}) { + const [t] = useTranslation('activate-project-banner'); + const { navigateTo } = useNavigation(); + const activateDiscoveryProject = async () => { + await navigateTo( + 'public-cloud', + `#/pci/projects/${projectId}/activate`, + {}, + ); + }; + return ( + +
+ + + {t('pci_projects_project_activate_project_banner_cta')} + +
+
+ ); +} diff --git a/packages/manager/apps/pci-vouchers/src/components/common.module.css b/packages/manager/apps/pci-vouchers/src/components/common.module.css new file mode 100644 index 000000000000..8c4aceade79c --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/common.module.css @@ -0,0 +1,28 @@ +.linkContainer a { + font-family: 'Source Sans Pro', sans-serif; + font-weight: 600; + color: rgb(0, 80, 215); + transition: background-size 0.2s ease-in 0s, color 0.1s ease-in-out 0s; + background-position: 0 100%; + background-repeat: no-repeat; + background-size: 0 2px; + background-image: linear-gradient(currentcolor, currentcolor); + outline: none; + cursor: pointer; + text-decoration: none; + user-select: auto; +} + +.linkContainer a:hover { + transition: background-size 0.2s ease-out 0s; + background-size: 100% 2px; +} + +.linkContainer a:focus { + transition: background-size 0.2s ease-out 0s; + background-size: 100% 2px; +} + +.linkContainer a:active { + transition: color ease-in-out 0s; +} diff --git a/packages/manager/apps/pci-vouchers/src/components/error-page/ErrorPage.tsx b/packages/manager/apps/pci-vouchers/src/components/error-page/ErrorPage.tsx new file mode 100644 index 000000000000..c78608fe267c --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/error-page/ErrorPage.tsx @@ -0,0 +1,104 @@ +import { useTranslation } from 'react-i18next'; +import { ODS_THEME_COLOR_INTENT } from '@ovhcloud/ods-common-theming'; +import { + ODS_BUTTON_SIZE, + ODS_BUTTON_VARIANT, + ODS_MESSAGE_TYPE, + ODS_TEXT_LEVEL, + ODS_TEXT_SIZE, +} from '@ovhcloud/ods-components'; +import { + OsdsButton, + OsdsMessage, + OsdsText, +} from '@ovhcloud/ods-components/react'; + +import oopsImage from './oops.png'; + +type ErrorPageProps = { + errorMessage?: string; + xOvhQueryId?: string; + reloadPage: () => void; + navigateToHomepage: () => void; +}; + +export default function ErrorPage({ + errorMessage, + xOvhQueryId, + reloadPage, + navigateToHomepage, +}: ErrorPageProps) { + const { t } = useTranslation('error'); + + return ( +
+
+
+ +
+ + {t('manager_error_page_title')} + + +
+ + {t('manager_error_page_default')} + + {errorMessage && ( + <> +
+ + {errorMessage} + + + )} + {xOvhQueryId && ( + <> +
+ + {t('manager_error_page_detail_code', { code: xOvhQueryId })} + + + )} +
+
+ +
+ navigateToHomepage()} + > + {t('manager_error_page_action_home_label')} + + reloadPage()} + > + {t('manager_error_page_action_reload_label')} + +
+
+
+ ); +} diff --git a/packages/manager/apps/pci-vouchers/src/components/error-page/oops.png b/packages/manager/apps/pci-vouchers/src/components/error-page/oops.png new file mode 100644 index 000000000000..413028afad19 Binary files /dev/null and b/packages/manager/apps/pci-vouchers/src/components/error-page/oops.png differ diff --git a/packages/manager/apps/pci-vouchers/src/components/guides/GuidesHeader.tsx b/packages/manager/apps/pci-vouchers/src/components/guides/GuidesHeader.tsx new file mode 100644 index 000000000000..d539cada0fee --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/guides/GuidesHeader.tsx @@ -0,0 +1,64 @@ +import { useEnvironment } from '@ovh-ux/manager-react-shell-client'; +import { + OsdsButton, + OsdsIcon, + OsdsText, + OsdsMenu, +} from '@ovhcloud/ods-components/react'; +import { + ODS_BUTTON_SIZE, + ODS_BUTTON_VARIANT, + ODS_ICON_NAME, + ODS_ICON_SIZE, +} from '@ovhcloud/ods-components'; +import { + ODS_THEME_COLOR_INTENT, + ODS_THEME_TYPOGRAPHY_SIZE, +} from '@ovhcloud/ods-common-theming'; +import { useTranslation } from 'react-i18next'; + +import { GUIDES_LIST } from '@/guides-header.constants'; +import GuidesHeaderItem from '@/components/guides/GuidesHeaderItem'; + +export default function GuidesHeader() { + const { t } = useTranslation('guides-header'); + const guidesHeadersPci = 'pci_project_guides_header'; + const guidesHeadersCategory = 'storage'; + const { ovhSubsidiary } = useEnvironment().getUser(); + const guideList = GUIDES_LIST[guidesHeadersCategory]; + + return ( + + + + + {t(guidesHeadersPci, { ns: 'guides-header' })} + + + + {Object.keys(guideList).map((guide, index) => ( + + ))} + + ); +} diff --git a/packages/manager/apps/pci-vouchers/src/components/guides/GuidesHeaderItem.tsx b/packages/manager/apps/pci-vouchers/src/components/guides/GuidesHeaderItem.tsx new file mode 100644 index 000000000000..2d00fe1f385b --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/guides/GuidesHeaderItem.tsx @@ -0,0 +1,63 @@ +import { + OsdsButton, + OsdsText, + OsdsIcon, + OsdsMenuItem, +} from '@ovhcloud/ods-components/react'; +import { + ODS_BUTTON_SIZE, + ODS_BUTTON_VARIANT, + ODS_ICON_NAME, + ODS_ICON_SIZE, +} from '@ovhcloud/ods-components'; +import { + ODS_THEME_COLOR_INTENT, + ODS_THEME_TYPOGRAPHY_SIZE, +} from '@ovhcloud/ods-common-theming'; +import { OdsHTMLAnchorElementTarget } from '@ovhcloud/ods-common-core'; +import { useTracking } from '@ovh-ux/manager-react-shell-client'; + +interface GuidesHeaderItemProps { + href: string; + label: string; + tracking?: string; +} +export default function GuidesHeaderItem({ + href, + label, + tracking, +}: GuidesHeaderItemProps) { + const { trackClick } = useTracking(); + return ( + + { + trackClick({ + name: `${tracking}`, + type: 'action', + }); + }} + > + + + {label} + + + + + + ); +} diff --git a/packages/manager/apps/pci-vouchers/src/components/vouchers/AddVoucherModal.tsx b/packages/manager/apps/pci-vouchers/src/components/vouchers/AddVoucherModal.tsx new file mode 100644 index 000000000000..fc7e5b43d1b5 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/vouchers/AddVoucherModal.tsx @@ -0,0 +1,106 @@ +import { + OsdsButton, + OsdsModal, + OsdsFormField, + OsdsInput, + OsdsSpinner, + OsdsText, +} from '@ovhcloud/ods-components/react'; +import { + ODS_BUTTON_VARIANT, + ODS_INPUT_TYPE, + ODS_SPINNER_SIZE, + OdsInputValueChangeEvent, +} from '@ovhcloud/ods-components'; +import { + ODS_THEME_COLOR_INTENT, + ODS_THEME_TYPOGRAPHY_LEVEL, +} from '@ovhcloud/ods-common-theming'; +import { useCallback, useState } from 'react'; +import { useTranslation } from 'react-i18next'; +import { useAddVoucher } from '@/hooks/useVouchers'; + +interface AddVoucherModalProps { + projectId: string; + onClose: () => void; + onSuccess: () => void; + onError: (cause: Error) => void; +} + +export default function AddVoucherModal({ + projectId, + onClose, + onSuccess, + onError, +}: AddVoucherModalProps) { + const { t } = useTranslation('common'); + const { add, isPending } = useAddVoucher({ + projectId: `${projectId}`, + onError: (err) => { + onClose(); + onError(err); + }, + onSuccess: () => { + onClose(); + onSuccess(); + }, + }); + const [voucherCode, setVoucherCode] = useState(''); + + const handleInputChange = useCallback( + (event: OdsInputValueChangeEvent) => { + setVoucherCode(`${event.detail.value}`); + }, + [setVoucherCode], + ); + + return ( + <> + + + {!isPending && ( + <> + + + {t('cpb_vouchers_your_voucher')} + + + + + )} + {isPending && } + + + {t('common_cancel')} + + add(voucherCode)} + data-testid="submitButton" + > + {t('common_confirm')} + + + + ); +} diff --git a/packages/manager/apps/pci-vouchers/src/components/vouchers/BuyCreditModal.tsx b/packages/manager/apps/pci-vouchers/src/components/vouchers/BuyCreditModal.tsx new file mode 100644 index 000000000000..6163f54ab197 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/vouchers/BuyCreditModal.tsx @@ -0,0 +1,156 @@ +import { + OsdsButton, + OsdsFormField, + OsdsInput, + OsdsModal, + OsdsSpinner, + OsdsText, +} from '@ovhcloud/ods-components/react'; +import { + ODS_BUTTON_VARIANT, + ODS_INPUT_TYPE, + ODS_SPINNER_SIZE, + OdsInputValueChangeEvent, +} from '@ovhcloud/ods-components'; +import { + ODS_THEME_COLOR_INTENT, + ODS_THEME_TYPOGRAPHY_LEVEL, +} from '@ovhcloud/ods-common-theming'; + +import { useCallback, useState } from 'react'; +import { useTranslation } from 'react-i18next'; +import { useEnvironment } from '@ovh-ux/manager-react-shell-client'; +import { useBuyCredit } from '@/hooks/useVouchers'; + +interface BuyCreditModalProps { + projectId: string; + onClose: () => void; + onSuccess: (amount: number, url: string) => void; + onError: (cause: Error) => void; +} + +export default function BuyCreditModal({ + projectId, + onClose, + onSuccess, + onError, +}: BuyCreditModalProps) { + const { t } = useTranslation('common'); + const env = useEnvironment(); + const [amount, setAmount] = useState(10); + const { buy, isPending } = useBuyCredit({ + projectId: `${projectId}`, + onError: (err) => { + onClose(); + onError(err); + }, + onSuccess: (response) => { + onClose(); + onSuccess(response.amount, response.url); + }, + }); + + const isMinimalAmount = !Number.isNaN(amount) && amount >= 1; + + const isValidInputAmount = !!( + !Number.isNaN(amount) && + amount > 0 && + amount <= 200_000 + ); + + const handleInputChange = useCallback( + (event: OdsInputValueChangeEvent) => { + setAmount(parseInt(`${event.detail.value}`, 10)); + }, + [setAmount], + ); + + return ( + <> + + + {!isPending && ( + <> + {t('cpb_vouchers_add_credit_info')} + + + {t('cpb_vouchers_add_credit_amount', { + currency: env.user?.currency?.symbol, + })} + + + + {!isMinimalAmount && ( + + {t('common_field_error_min', { + min: 1, + })} + + )} + + {!isValidInputAmount && ( + + {t('common_field_error_number')} + + )} + + + )} + {isPending && ( +
+ +
+ )} +
+ + {t('common_cancel')} + + buy(amount)} + data-testid="submitButton" + > + {t('cpb_vouchers_add_credit_valid')} + +
+ + ); +} diff --git a/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/Credit.tsx b/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/Credit.tsx new file mode 100644 index 000000000000..ced7e1bd9000 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/Credit.tsx @@ -0,0 +1,10 @@ +import { DataGridTextCell } from '@ovhcloud/manager-components'; +import { Credit } from '@/interface'; + +export default function CreditCell({ + credit, +}: { + credit: Pick; +}) { + return {credit.text || ''}; +} diff --git a/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/DisplayName.tsx b/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/DisplayName.tsx new file mode 100644 index 000000000000..b68fbb894b86 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/DisplayName.tsx @@ -0,0 +1,48 @@ +import { useTranslation } from 'react-i18next'; +import { useQuery } from '@tanstack/react-query'; +import { DataGridTextCell } from '@ovhcloud/manager-components'; +import { OsdsSpinner } from '@ovhcloud/ods-components/react'; +import { ODS_SPINNER_SIZE } from '@ovhcloud/ods-components'; +import { Voucher } from '@/interface'; +import { getBill } from '@/data/bill'; +import style from '@/components/common.module.css'; + +export default function DisplayName({ + voucher, +}: { + voucher: Pick; +}) { + const { t } = useTranslation('common'); + if (voucher.bill) { + const { data } = useQuery({ + queryKey: ['bill', voucher.bill], + queryFn: () => getBill(`${voucher.bill}`), + }); + return ( + + {t('cpb_vouchers_name_credit_provisionning')} +
+ {data && ( + + )} + {!data && ( + + )} +
+ ); + } + return {voucher.description}; +} diff --git a/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/Product.tsx b/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/Product.tsx new file mode 100644 index 000000000000..285f5f7e8556 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/Product.tsx @@ -0,0 +1,11 @@ +import { useTranslation } from 'react-i18next'; +import { DataGridTextCell } from '@ovhcloud/manager-components'; + +export default function Product({ product }: { product: string[] | null }) { + const { t } = useTranslation('common'); + return ( + + {product?.join(', ') || t('cpb_vouchers_products_all')} + + ); +} diff --git a/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/Validity.tsx b/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/Validity.tsx new file mode 100644 index 000000000000..157f51154627 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/components/vouchers/listing/Validity.tsx @@ -0,0 +1,31 @@ +import { format } from 'date-fns'; +import * as dateFnsLocales from 'date-fns/locale'; +import { useRef } from 'react'; +import { useTranslation } from 'react-i18next'; +import { DataGridTextCell } from '@ovhcloud/manager-components'; +import getLocale from '@/data/date'; + +export default function Validity({ date }: { date: string | null }) { + const { i18n } = useTranslation('common'); + + const locales = useRef({ ...dateFnsLocales }).current; + + let displayDate = ''; + + if (date) { + const userLocale = getLocale(i18n.language); + + if (userLocale in locales) { + const localeId = userLocale as keyof typeof locales; + displayDate = format(new Date(date), 'PPpp', { + locale: locales[localeId], + }); + } else { + displayDate = format(new Date(date), 'PPpp', { + locale: locales.fr, + }); + } + } + + return {displayDate}; +} diff --git a/packages/manager/apps/pci-vouchers/src/core/HidePreloader.tsx b/packages/manager/apps/pci-vouchers/src/core/HidePreloader.tsx new file mode 100644 index 000000000000..8a4a8e7783df --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/core/HidePreloader.tsx @@ -0,0 +1,12 @@ +import { useUX } from '@ovh-ux/manager-react-shell-client'; +import { useEffect } from 'react'; + +export default function HidePreloader() { + const ux = useUX(); + + useEffect(() => { + ux.hidePreloader(); + }, []); + + return null; +} diff --git a/packages/manager/apps/pci-vouchers/src/core/ShellRoutingSync.tsx b/packages/manager/apps/pci-vouchers/src/core/ShellRoutingSync.tsx new file mode 100644 index 000000000000..d4559e10ab48 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/core/ShellRoutingSync.tsx @@ -0,0 +1,18 @@ +import { useRouting } from '@ovh-ux/manager-react-shell-client'; +import { useEffect } from 'react'; +import { useLocation } from 'react-router-dom'; + +export default function ShellRoutingSync() { + const location = useLocation(); + const routing = useRouting(); + + useEffect(() => { + routing.stopListenForHashChange(); + }, []); + + useEffect(() => { + routing.onHashChange(); + }, [location]); + + return null; +} diff --git a/packages/manager/apps/pci-vouchers/src/data/bill.ts b/packages/manager/apps/pci-vouchers/src/data/bill.ts new file mode 100644 index 000000000000..32fc32cce4e4 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/data/bill.ts @@ -0,0 +1,14 @@ +import { v6 } from '@ovh-ux/manager-core-api'; + +export async function getBill(billId: string) { + return v6 + .get(`/me/bill/${billId}`) + .then(({ data }) => data) + .catch(({ response }) => + Promise.reject(new Error(response?.data?.message)), + ); +} + +export default { + getBill, +}; diff --git a/packages/manager/apps/pci-vouchers/src/data/date.ts b/packages/manager/apps/pci-vouchers/src/data/date.ts new file mode 100644 index 000000000000..d50cca7af287 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/data/date.ts @@ -0,0 +1,11 @@ +// convert language to date-fns locale +export default function getLocale(language: string) { + if (language === 'en_GB') { + return 'enGB'; + } + if (language === 'fr_CA') { + return 'frCA'; + } + const [locale] = language.split('_'); + return locale; +} diff --git a/packages/manager/apps/pci-vouchers/src/data/project.ts b/packages/manager/apps/pci-vouchers/src/data/project.ts new file mode 100644 index 000000000000..bd7c4830bca4 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/data/project.ts @@ -0,0 +1,25 @@ +import { v6 } from '@ovh-ux/manager-core-api'; + +export interface Project { + access: string; + creationDate: string; + description: string; + projectName: string; + project_id: string; + status: string; + unleash: boolean; + planCode: string; +} + +export const DISCOVERY_PROJECT_PLANCODE = 'project.discovery'; + +export const getProject = async (projectId: string): Promise => { + const response = await v6.get(`/cloud/project/${projectId}`); + return response.data as Project; +}; + +export const isDiscoveryProject = (project: Project | undefined) => { + return project?.planCode === DISCOVERY_PROJECT_PLANCODE; +}; + +export default getProject; diff --git a/packages/manager/apps/pci-vouchers/src/data/utils.ts b/packages/manager/apps/pci-vouchers/src/data/utils.ts new file mode 100644 index 000000000000..a540a5d22185 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/data/utils.ts @@ -0,0 +1,33 @@ +import { Credit, Voucher } from '@/interface'; + +export const defaultCompareFunction = (key: keyof Voucher) => ( + a: Voucher, + b: Voucher, +) => { + const aValue = a[key] || ''; + const bValue = b[key] || ''; + + return (aValue as string).localeCompare(bValue as string); +}; + +export const creditComparator = (key: 'available_credit' | 'total_credit') => { + return (a: Voucher, b: Voucher) => { + const aValue = (a[key] as Credit)?.value; + const bValue = (b[key] as Credit)?.value; + + if (aValue > bValue) { + return 1; + } + return aValue < bValue ? -1 : 0; + }; +}; + +export const validityComparator = (key: 'from' | 'to') => ( + a: Voucher, + b: Voucher, +) => { + const aValue = a.validity[key] || ''; + const bValue = b.validity[key] || ''; + + return (aValue as string).localeCompare(bValue as string); +}; diff --git a/packages/manager/apps/pci-vouchers/src/data/voucher.ts b/packages/manager/apps/pci-vouchers/src/data/voucher.ts new file mode 100644 index 000000000000..2d693cae45be --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/data/voucher.ts @@ -0,0 +1,40 @@ +import { v6 } from '@ovh-ux/manager-core-api'; + +export async function addVoucher(projectId: string, code: string) { + return v6 + .post(`/cloud/project/${projectId}/credit`, { + code, + }) + .then(({ data }) => data) + .catch(({ response }) => + Promise.reject(new Error(response?.data?.message)), + ); +} + +export type BuyCreditResult = { + url: string; + amount: number; +}; + +export async function buyCredit( + projectId: string, + amount: number, +): Promise { + return v6 + .post(`/order/cloud/project/${projectId}/credit`, { amount }) + .then( + ({ data }) => + ({ + amount, + url: data.url, + } as BuyCreditResult), + ) + .catch(({ response }) => + Promise.reject(new Error(response?.data?.message)), + ); +} + +export default { + addVoucher, + buyCredit, +}; diff --git a/packages/manager/apps/pci-vouchers/src/data/vouchers.ts b/packages/manager/apps/pci-vouchers/src/data/vouchers.ts new file mode 100644 index 000000000000..bca1b1ab527a --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/data/vouchers.ts @@ -0,0 +1,66 @@ +import { fetchIcebergV6 } from '@ovh-ux/manager-core-api'; +import { ColumnSort, PaginationState } from '@ovhcloud/manager-components'; +import { Voucher } from '@/interface'; +import { + creditComparator, + defaultCompareFunction, + validityComparator, +} from './utils'; + +export type VouchersOptions = { + pagination: PaginationState; + sorting: ColumnSort; +}; + +export const getAllVouchers = async (projectId: string): Promise => { + const { data } = await fetchIcebergV6({ + route: `/cloud/project/${projectId}/credit`, + disableCache: true, + }); + + return data; +}; + +export const paginateResults = ( + items: Voucher[], + pagination: PaginationState, +) => { + return { + rows: items.slice( + pagination.pageIndex * pagination.pageSize, + (pagination.pageIndex + 1) * pagination.pageSize, + ), + pageCount: Math.ceil(items.length / pagination.pageSize), + totalRows: items.length, + }; +}; + +export const filterVouchers = ( + vouchers: Voucher[], + sorting: ColumnSort, +): Voucher[] => { + const data = [...vouchers]; + + if (sorting) { + const { id: sortKey, desc } = sorting; + + if (['available_credit', 'total_credit'].includes(sortKey)) { + data.sort( + creditComparator(sortKey as 'available_credit' | 'total_credit'), + ); + } else if (sortKey === 'validityFrom') { + data.sort(validityComparator('from')); + } else if (sortKey === 'validityTo') { + data.sort(validityComparator('to')); + } else { + data.sort(defaultCompareFunction(sortKey as keyof Voucher)); + } + if (desc) { + data.reverse(); + } + } + + return data; +}; + +export default getAllVouchers; diff --git a/packages/manager/apps/pci-vouchers/src/guides-header.constants.ts b/packages/manager/apps/pci-vouchers/src/guides-header.constants.ts new file mode 100644 index 000000000000..91f7b21cc48e --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/guides-header.constants.ts @@ -0,0 +1,817 @@ +interface GuideLinks { + [key: string]: string | undefined; + FR?: string; + GB: string; + DE?: string; + ES?: string; + IT?: string; + PL?: string; + PT?: string; + IE: string; + DEFAULT: string; + US?: string; + ASIA: string; + AU: string; + CA: string; + QC?: string; + SG: string; + WE: string; + WS?: string; + MA?: string; + TN?: string; + SN?: string; + IN?: string; +} + +interface Guide { + key: string; + url: GuideLinks; + tracking?: string; +} + +interface GuideList { + storage: { + [key: string]: Guide; + }; + objectStorage: { + [key: string]: Guide; + }; + instances: { + [key: string]: Guide; + }; + databases: { + [key: string]: Guide; + }; + kubernetes: { + [key: string]: Guide; + }; + private_registry: { + [key: string]: Guide; + }; + ai_machine_learning: { + [key: string]: Guide; + }; + data_processing: { + [key: string]: Guide; + }; + ai_notenooks: { + [key: string]: Guide; + }; + ai_training: { + [key: string]: Guide; + }; + ml_serving: { + [key: string]: Guide; + }; + private_network: { + [key: string]: Guide; + }; +} + +export const PUBLIC_CLOUD_GUIDES: GuideLinks = { + FR: 'https://docs.ovh.com/fr/public-cloud/', + GB: 'https://docs.ovh.com/gb/en/public-cloud/', + DE: 'https://docs.ovh.com/de/public-cloud/', + ES: 'https://docs.ovh.com/es/public-cloud/', + IT: 'https://docs.ovh.com/it/public-cloud/', + PL: 'https://docs.ovh.com/pl/public-cloud/', + PT: 'https://docs.ovh.com/pt/public-cloud/', + IE: 'https://docs.ovh.com/ie/en/public-cloud/', + DEFAULT: 'https://docs.ovh.com/gb/en/public-cloud/', + US: + 'https://support.us.ovhcloud.com/hc/en-us/categories/115000515130-Public-Cloud-Services', + ASIA: 'https://docs.ovh.com/asia/en/public-cloud/', + AU: 'https://docs.ovh.com/au/en/public-cloud/', + CA: 'https://docs.ovh.com/ca/en/public-cloud/', + QC: 'https://docs.ovh.com/ca/fr/public-cloud/', + SG: 'https://docs.ovh.com/sg/en/public-cloud/', + WE: 'https://docs.ovh.com/us/en/public-cloud/', + WS: 'https://docs.ovh.com/us/es/public-cloud/', + MA: 'https://docs.ovh.com/fr/public-cloud/', + TN: 'https://docs.ovh.com/fr/public-cloud/', + SN: 'https://docs.ovh.com/fr/public-cloud/', + IN: 'https://docs.ovh.com/asia/en/public-cloud/', +}; + +export const PUBLIC_CLOUD_STORAGE_GUIDES: GuideLinks = { + FR: 'https://docs.ovh.com/fr/storage/', + GB: 'https://docs.ovh.com/gb/en/storage/', + DE: 'https://docs.ovh.com/de/storage/', + ES: 'https://docs.ovh.com/es/storage/', + IT: 'https://docs.ovh.com/it/storage/', + PL: 'https://docs.ovh.com/pl/storage/', + PT: 'https://docs.ovh.com/pt/storage/', + IE: 'https://docs.ovh.com/ie/en/storage/', + DEFAULT: 'https://docs.ovh.com/gb/en/storage/', + US: 'https://support.us.ovhcloud.com/hc/en-us/sections/115000624590-Storage', + ASIA: 'https://docs.ovh.com/asia/en/storage/', + AU: 'https://docs.ovh.com/au/en/storage/', + CA: 'https://docs.ovh.com/ca/en/storage/', + QC: 'https://docs.ovh.com/ca/fr/storage/', + SG: 'https://docs.ovh.com/sg/en/storage/', + WE: 'https://docs.ovh.com/us/en/storage/', + WS: 'https://docs.ovh.com/us/es/storage/', + MA: 'https://docs.ovh.com/fr/storage/', + TN: 'https://docs.ovh.com/fr/storage/', + SN: 'https://docs.ovh.com/fr/storage/', + IN: 'https://docs.ovh.com/asia/en/storage/', +}; + +export const FIRST_STEPS_WITH_INSTANCES: GuideLinks = { + FR: + 'https://docs.ovh.com/fr/public-cloud/premiers-pas-instance-public-cloud/', + GB: 'https://docs.ovh.com/gb/en/public-cloud/public-cloud-first-steps/', + DE: 'https://docs.ovh.com/de/public-cloud/public-cloud-erste-schritte/', + ES: 'https://docs.ovh.com/es/public-cloud/public-cloud-primeros-pasos/', + IT: 'https://docs.ovh.com/it/public-cloud/primi-passi-public-cloud/', + PL: 'https://docs.ovh.com/pl/public-cloud/public-cloud-pierwsze-kroki/', + PT: 'https://docs.ovh.com/pt/public-cloud/public-cloud-primeiros-passos/', + IE: 'https://docs.ovh.com/ie/en/public-cloud/public-cloud-first-steps/', + DEFAULT: 'https://docs.ovh.com/gb/en/public-cloud/public-cloud-first-steps/', + US: + 'https://support.us.ovhcloud.com/hc/en-us/articles/4481009956243-How-to-Manage-Your-Public-Cloud-Instance', + ASIA: 'https://docs.ovh.com/asia/en/public-cloud/public-cloud-first-steps/', + AU: 'https://docs.ovh.com/au/en/public-cloud/public-cloud-first-steps/', + CA: 'https://docs.ovh.com/ca/en/public-cloud/public-cloud-first-steps/', + QC: + 'https://docs.ovh.com/ca/fr/public-cloud/premiers-pas-instance-public-cloud/', + SG: 'https://docs.ovh.com/sg/en/public-cloud/public-cloud-first-steps/', + WE: 'https://docs.ovh.com/us/en/public-cloud/public-cloud-first-steps/', + WS: 'https://docs.ovh.com/us/es/public-cloud/public-cloud-primeros-pasos/', + IN: 'https://docs.ovh.com/asia/en/public-cloud/public-cloud-first-steps/', +}; + +export const IP_FAIL_OVER: GuideLinks = { + FR: 'https://docs.ovh.com/fr/public-cloud/configurer_une_ip_failover/', + GB: 'https://docs.ovh.com/gb/en/public-cloud/configure_a_failover_ip/', + DE: 'https://docs.ovh.com/de/public-cloud/failover-ip-konfigurieren-pci/', + ES: 'https://docs.ovh.com/es/public-cloud/configurer-une-ip-failover/', + IT: 'https://docs.ovh.com/it/public-cloud/configura-un-ip-failover/', + PL: 'https://docs.ovh.com/pl/public-cloud/konfiguracja-adresu-ip-failover/', + PT: 'https://docs.ovh.com/pt/public-cloud/configurer-une-ip-failover/', + IE: 'https://docs.ovh.com/ie/en/public-cloud/configure_a_failover_ip/', + DEFAULT: 'https://docs.ovh.com/gb/en/public-cloud/configure_a_failover_ip/', + US: + 'https://support.us.ovhcloud.com/hc/en-us/articles/115001588270-How-to-Order-Failover-IPs', + ASIA: 'https://docs.ovh.com/asia/en/public-cloud/configure_a_failover_ip/', + AU: 'https://docs.ovh.com/au/en/public-cloud/configure_a_failover_ip/', + CA: 'https://docs.ovh.com/ca/en/public-cloud/configure_a_failover_ip/', + QC: 'https://docs.ovh.com/ca/fr/public-cloud/configurer_une_ip_failover/', + SG: 'https://docs.ovh.com/sg/en/public-cloud/configure_a_failover_ip/', + WE: 'https://docs.ovh.com/us/en/public-cloud/configure_a_failover_ip/', + WS: 'https://docs.ovh.com/us/es/public-cloud/configurer-une-ip-failover/', + IN: 'https://docs.ovh.com/asia/en/public-cloud/configure_a_failover_ip/', +}; + +export const USER_ROOT_AND_PASSWORD: GuideLinks = { + FR: + 'https://docs.ovh.com/fr/public-cloud/passer-root-et-definir-un-mot-de-passe/', + GB: + 'https://docs.ovh.com/gb/en/public-cloud/become_the_root_user_and_select_a_password/', + DE: + 'https://docs.ovh.com/de/public-cloud/root-rechte_erlangen_und_passwort_festlegen/', + ES: + 'https://docs.ovh.com/es/public-cloud/conectarse_como_usuario_root_y_establecer_una_contrasena/', + IT: + 'https://docs.ovh.com/it/public-cloud/imposta_una_password_amministratore/', + PL: 'https://docs.ovh.com/pl/public-cloud/dostep_root_i_zdefiniowanie_hasla/', + PT: + 'https://docs.ovh.com/pt/public-cloud/tornar-se_root_e_definir_uma_palavra-passe/', + IE: + 'https://docs.ovh.com/ie/en/public-cloud/become_the_root_user_and_select_a_password/', + DEFAULT: + 'https://docs.ovh.com/gb/en/public-cloud/become_the_root_user_and_select_a_password/', + US: + 'https://support.us.ovhcloud.com/hc/en-us/articles/360002208690-How-to-Access-a-Public-Cloud-Instance-via-VNC', + ASIA: + 'https://docs.ovh.com/asia/en/public-cloud/become_the_root_user_and_select_a_password/', + AU: + 'https://docs.ovh.com/au/en/public-cloud/become_the_root_user_and_select_a_password/', + CA: + 'https://docs.ovh.com/ca/en/public-cloud/become_the_root_user_and_select_a_password/', + QC: + 'https://docs.ovh.com/ca/fr/public-cloud/passer-root-et-definir-un-mot-de-passe/', + SG: + 'https://docs.ovh.com/sg/en/public-cloud/become_the_root_user_and_select_a_password/', + WE: + 'https://docs.ovh.com/us/en/public-cloud/become_the_root_user_and_select_a_password/', + WS: + 'https://docs.ovh.com/us/es/public-cloud/conectarse_como_usuario_root_y_establecer_una_contrasena/', + IN: + 'https://docs.ovh.com/asia/en/public-cloud/become_the_root_user_and_select_a_password/', +}; + +export const REVERSE_DNS: GuideLinks = { + FR: + 'https://docs.ovh.com/fr/public-cloud/configurer-le-reverse-dns-dune-instance/', + GB: 'https://docs.ovh.com/gb/en/public-cloud/configure-reverse-dns-instance/', + DE: 'https://docs.ovh.com/de/public-cloud/reverse-dns-konfigurieren-instanz/', + ES: + 'https://docs.ovh.com/es/public-cloud/configurar-el-inverso-dns-de-una-instancia/', + IT: + 'https://docs.ovh.com/it/public-cloud/configura_il_reverse_dns_della_tua_istanza/', + PL: + 'https://docs.ovh.com/pl/public-cloud/konfiguracja_rewersu_dns_instancji/', + PT: + 'https://docs.ovh.com/pt/public-cloud/configurar_a_reverse_dns_de_uma_instancia/', + IE: 'https://docs.ovh.com/ie/en/public-cloud/configure-reverse-dns-instance/', + DEFAULT: + 'https://docs.ovh.com/gb/en/public-cloud/configure-reverse-dns-instance/', + US: + 'https://support.us.ovhcloud.com/hc/en-us/articles/360002181530-How-to-Configure-Reverse-DNS', + ASIA: + 'https://docs.ovh.com/asia/en/public-cloud/configure-reverse-dns-instance/', + AU: 'https://docs.ovh.com/au/en/public-cloud/configure-reverse-dns-instance/', + CA: 'https://docs.ovh.com/ca/en/public-cloud/configure-reverse-dns-instance/', + QC: + 'https://docs.ovh.com/ca/fr/public-cloud/configurer-le-reverse-dns-dune-instance/', + SG: 'https://docs.ovh.com/sg/en/public-cloud/configure-reverse-dns-instance/', + WE: 'https://docs.ovh.com/us/en/public-cloud/configure-reverse-dns-instance/', + WS: + 'https://docs.ovh.com/us/es/public-cloud/configurar-el-inverso-dns-de-una-instancia/', + IN: + 'https://docs.ovh.com/asia/en/public-cloud/configure-reverse-dns-instance/', +}; + +export const FIRST_STEPS_WITH_DATABASES: GuideLinks = { + FR: 'https://docs.ovh.com/fr/publiccloud/databases/getting-started/', + GB: 'https://docs.ovh.com/gb/en/publiccloud/databases/getting-started/', + DE: 'https://docs.ovh.com/de/publiccloud/databases/getting-started/', + ES: 'https://docs.ovh.com/es/publiccloud/databases/getting-started/', + IT: 'https://docs.ovh.com/it/publiccloud/databases/getting-started/', + PL: 'https://docs.ovh.com/pl/publiccloud/databases/getting-started/', + PT: 'https://docs.ovh.com/pt/publiccloud/databases/getting-started/', + IE: 'https://docs.ovh.com/ie/en/publiccloud/databases/getting-started/', + DEFAULT: 'https://docs.ovh.com/gb/en/publiccloud/databases/getting-started/', + ASIA: 'https://docs.ovh.com/asia/en/publiccloud/databases/getting-started/', + AU: 'https://docs.ovh.com/au/en/publiccloud/databases/getting-started/', + CA: 'https://docs.ovh.com/ca/en/publiccloud/databases/getting-started/', + QC: 'https://docs.ovh.com/ca/fr/publiccloud/databases/getting-started/', + SG: 'https://docs.ovh.com/sg/en/publiccloud/databases/getting-started/', + WE: 'https://docs.ovh.com/us/en/publiccloud/databases/getting-started/', + WS: 'https://docs.ovh.com/us/es/publiccloud/databases/getting-started/', + IN: 'https://docs.ovh.com/asia/en/publiccloud/databases/getting-started/', +}; + +export const MONGO_DB_CAPABILITIES_AND_LIMITATIONS: GuideLinks = { + FR: 'https://docs.ovh.com/fr/publiccloud/databases/mongodb/capabilities/', + GB: 'https://docs.ovh.com/gb/en/publiccloud/databases/mongodb/capabilities/', + DE: 'https://docs.ovh.com/de/publiccloud/databases/mongodb/capabilities/', + ES: 'https://docs.ovh.com/es/publiccloud/databases/mongodb/capabilities/', + IT: 'https://docs.ovh.com/it/publiccloud/databases/mongodb/capabilities/', + PL: 'https://docs.ovh.com/pl/publiccloud/databases/mongodb/capabilities/', + PT: 'https://docs.ovh.com/pt/publiccloud/databases/mongodb/capabilities/', + IE: 'https://docs.ovh.com/ie/en/publiccloud/databases/mongodb/capabilities/', + DEFAULT: + 'https://docs.ovh.com/gb/en/publiccloud/databases/mongodb/capabilities/', + ASIA: + 'https://docs.ovh.com/asia/en/publiccloud/databases/mongodb/capabilities/', + AU: 'https://docs.ovh.com/au/en/publiccloud/databases/mongodb/capabilities/', + CA: 'https://docs.ovh.com/ca/en/publiccloud/databases/mongodb/capabilities/', + QC: 'https://docs.ovh.com/ca/fr/publiccloud/databases/mongodb/capabilities/', + SG: 'https://docs.ovh.com/sg/en/publiccloud/databases/mongodb/capabilities/', + WE: 'https://docs.ovh.com/us/en/publiccloud/databases/mongodb/capabilities/', + WS: 'https://docs.ovh.com/us/es/publiccloud/databases/mongodb/capabilities/', + IN: + 'https://docs.ovh.com/asia/en/publiccloud/databases/mongodb/capabilities/', +}; + +export const MYSQL_CAPABILITIES_AND_LIMITATIONS: GuideLinks = { + FR: 'https://docs.ovh.com/fr/publiccloud/databases/mysql/capabilities/', + GB: 'https://docs.ovh.com/gb/en/publiccloud/databases/mysql/capabilities/', + DE: 'https://docs.ovh.com/de/publiccloud/databases/mysql/capabilities/', + ES: 'https://docs.ovh.com/es/publiccloud/databases/mysql/capabilities/', + IT: 'https://docs.ovh.com/it/publiccloud/databases/mysql/capabilities/', + PL: 'https://docs.ovh.com/pl/publiccloud/databases/mysql/capabilities/', + PT: 'https://docs.ovh.com/pt/publiccloud/databases/mysql/capabilities/', + IE: 'https://docs.ovh.com/ie/en/publiccloud/databases/mysql/capabilities/', + DEFAULT: + 'https://docs.ovh.com/gb/en/publiccloud/databases/mysql/capabilities/', + ASIA: + 'https://docs.ovh.com/asia/en/publiccloud/databases/mysql/capabilities/', + AU: 'https://docs.ovh.com/au/en/publiccloud/databases/mysql/capabilities/', + CA: 'https://docs.ovh.com/ca/en/publiccloud/databases/mysql/capabilities/', + QC: 'https://docs.ovh.com/ca/fr/publiccloud/databases/mysql/capabilities/', + SG: 'https://docs.ovh.com/sg/en/publiccloud/databases/mysql/capabilities/', + WE: 'https://docs.ovh.com/us/en/publiccloud/databases/mysql/capabilities/', + WS: 'https://docs.ovh.com/us/es/publiccloud/databases/mysql/capabilities/', + IN: 'https://docs.ovh.com/asia/en/publiccloud/databases/mysql/capabilities/', +}; + +export const CREATE_A_CLUSTER: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/kubernetes/creating-a-cluster/', + IE: 'https://docs.ovh.com/ie/en/kubernetes/creating-a-cluster/', + DEFAULT: 'https://docs.ovh.com/gb/en/kubernetes/creating-a-cluster/', + US: + 'https://support.us.ovhcloud.com/hc/en-us/articles/1500004767902-How-to-Create-a-Cluster-in-OVHcloud-Managed-Kubernetes', + ASIA: 'https://docs.ovh.com/asia/en/kubernetes/creating-a-cluster/', + AU: 'https://docs.ovh.com/au/en/kubernetes/creating-a-cluster/', + CA: 'https://docs.ovh.com/ca/en/kubernetes/creating-a-cluster/', + SG: 'https://docs.ovh.com/sg/en/kubernetes/creating-a-cluster/', + WE: 'https://docs.ovh.com/us/en/kubernetes/creating-a-cluster/', +}; + +export const DEPLOY_AN_APPLICATION: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/kubernetes/deploying-an-application/', + IE: 'https://docs.ovh.com/ie/en/kubernetes/deploying-an-application/', + DEFAULT: 'https://docs.ovh.com/gb/en/kubernetes/deploying-an-application/', + US: + 'https://support.us.ovhcloud.com/hc/en-us/articles/1500004771762-How-to-Deploy-an-Application-on-an-OVHcloud-Managed-Kubernetes-Cluster', + ASIA: 'https://docs.ovh.com/asia/en/kubernetes/deploying-an-application/', + AU: 'https://docs.ovh.com/au/en/kubernetes/deploying-an-application/', + CA: 'https://docs.ovh.com/ca/en/kubernetes/deploying-an-application/', + SG: 'https://docs.ovh.com/sg/en/kubernetes/deploying-an-application/', + WE: 'https://docs.ovh.com/us/en/kubernetes/deploying-an-application/', + IN: 'https://docs.ovh.com/asia/en/kubernetes/deploying-an-application/', +}; + +export const LOADBALANCER_KUBE: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/kubernetes/using-lb/', + IE: 'https://docs.ovh.com/ie/en/kubernetes/using-lb/', + DEFAULT: 'https://docs.ovh.com/gb/en/kubernetes/using-lb/', + US: + 'https://support.us.ovhcloud.com/hc/en-us/articles/1500004806361-How-to-Use-the-OVHcloud-Managed-Kubernetes-Load-Balancer', + ASIA: 'https://docs.ovh.com/asia/en/kubernetes/using-lb/', + AU: 'https://docs.ovh.com/au/en/kubernetes/using-lb/', + CA: 'https://docs.ovh.com/ca/en/kubernetes/using-lb/', + SG: 'https://docs.ovh.com/sg/en/kubernetes/using-lb/', + WE: 'https://docs.ovh.com/us/en/kubernetes/using-lb/', + IN: 'https://docs.ovh.com/asia/en/kubernetes/using-lb/', +}; + +export const FAQ_MANAGED_PRIVATE_REGISTRY: GuideLinks = { + FR: 'https://docs.ovh.com/fr/private-registry/managed-private-registry-faq/', + GB: + 'https://docs.ovh.com/gb/en/private-registry/managed-private-registry-faq/', + IE: + 'https://docs.ovh.com/ie/en/private-registry/managed-private-registry-faq/', + DEFAULT: + 'https://docs.ovh.com/gb/en/private-registry/managed-private-registry-faq/', + ASIA: + 'https://docs.ovh.com/asia/en/private-registry/managed-private-registry-faq/', + AU: + 'https://docs.ovh.com/au/en/private-registry/managed-private-registry-faq/', + CA: + 'https://docs.ovh.com/ca/en/private-registry/managed-private-registry-faq/', + SG: + 'https://docs.ovh.com/sg/en/private-registry/managed-private-registry-faq/', + WE: + 'https://docs.ovh.com/us/en/private-registry/managed-private-registry-faq/', + IN: + 'https://docs.ovh.com/asia/en/private-registry/managed-private-registry-faq/', +}; + +export const CREATE_A_MANAGED_PRIVATE_REGISTER: GuideLinks = { + GB: + 'https://docs.ovh.com/gb/en/private-registry/creating-a-private-registry/', + IE: + 'https://docs.ovh.com/ie/en/private-registry/creating-a-private-registry/', + DEFAULT: + 'https://docs.ovh.com/gb/en/private-registry/creating-a-private-registry/', + ASIA: + 'https://docs.ovh.com/asia/en/private-registry/creating-a-private-registry/', + AU: + 'https://docs.ovh.com/au/en/private-registry/creating-a-private-registry/', + CA: + 'https://docs.ovh.com/ca/en/private-registry/creating-a-private-registry/', + SG: + 'https://docs.ovh.com/sg/en/private-registry/creating-a-private-registry/', + WE: + 'https://docs.ovh.com/us/en/private-registry/creating-a-private-registry/', + IN: + 'https://docs.ovh.com/asia/en/private-registry/creating-a-private-registry/', +}; + +export const CREATE_AND_USE_A_PRIVATE_IMAGE: GuideLinks = { + GB: + 'https://docs.ovh.com/gb/en/private-registry/creating-and-using-a-private-image/', + IE: + 'https://docs.ovh.com/ie/en/private-registry/creating-and-using-a-private-image/', + DEFAULT: + 'https://docs.ovh.com/gb/en/private-registry/creating-and-using-a-private-image/', + ASIA: + 'https://docs.ovh.com/asia/en/private-registry/creating-and-using-a-private-image/', + AU: + 'https://docs.ovh.com/au/en/private-registry/creating-and-using-a-private-image/', + CA: + 'https://docs.ovh.com/ca/en/private-registry/creating-and-using-a-private-image/', + SG: + 'https://docs.ovh.com/sg/en/private-registry/creating-and-using-a-private-image/', + WE: + 'https://docs.ovh.com/us/en/private-registry/creating-and-using-a-private-image/', +}; + +export const DIFFERENCES_BETWEEN_AI_NOTEBOOKS_AI_TRAINING_AI_APPS: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/publiccloud/ai/ai-comparative-tables/', + IE: 'https://docs.ovh.com/ie/en/publiccloud/ai/ai-comparative-tables/', + DEFAULT: 'https://docs.ovh.com/gb/en/publiccloud/ai/ai-comparative-tables/', + ASIA: 'https://docs.ovh.com/asia/en/publiccloud/ai/ai-comparative-tables/', + AU: 'https://docs.ovh.com/au/en/publiccloud/ai/ai-comparative-tables/', + CA: 'https://docs.ovh.com/ca/en/publiccloud/ai/ai-comparative-tables/', + SG: 'https://docs.ovh.com/sg/en/publiccloud/ai/ai-comparative-tables/', + WE: 'https://docs.ovh.com/us/en/publiccloud/ai/ai-comparative-tables/', + IN: 'https://docs.ovh.com/asia/en/publiccloud/ai/ai-comparative-tables/', +}; + +export const AI_APPS_CAPABILITIES_AND_LIMITATIONS: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/publiccloud/ai/apps/capabilities/', + IE: 'https://docs.ovh.com/ie/en/publiccloud/ai/apps/capabilities/', + DEFAULT: 'https://docs.ovh.com/gb/en/publiccloud/ai/apps/capabilities/', + ASIA: 'https://docs.ovh.com/asia/en/publiccloud/ai/apps/capabilities/', + AU: 'https://docs.ovh.com/au/en/publiccloud/ai/apps/capabilities/', + CA: 'https://docs.ovh.com/ca/en/publiccloud/ai/apps/capabilities/', + SG: 'https://docs.ovh.com/sg/en/publiccloud/ai/apps/capabilities/', + WE: 'https://docs.ovh.com/us/en/publiccloud/ai/apps/capabilities/', + IN: 'https://docs.ovh.com/asia/en/publiccloud/ai/apps/capabilities/', +}; + +export const ACCESSING_YOUR_AI_APPS_WITH_TOKENS: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/publiccloud/ai/ai-apps-tokens/', + IE: 'https://docs.ovh.com/ie/en/publiccloud/ai/ai-apps-tokens/', + DEFAULT: 'https://docs.ovh.com/gb/en/publiccloud/ai/ai-apps-tokens/', + ASIA: 'https://docs.ovh.com/asia/en/publiccloud/ai/ai-apps-tokens/', + AU: 'https://docs.ovh.com/au/en/publiccloud/ai/ai-apps-tokens/', + CA: 'https://docs.ovh.com/ca/en/publiccloud/ai/ai-apps-tokens/', + SG: 'https://docs.ovh.com/sg/en/publiccloud/ai/ai-apps-tokens/', + WE: 'https://docs.ovh.com/us/en/publiccloud/ai/ai-apps-tokens/', + IN: 'https://docs.ovh.com/asia/en/publiccloud/ai/ai-apps-tokens/', +}; + +export const PRESENTATION_OF_DATA_PROCESSING: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/data-processing/overview/', + IE: 'https://docs.ovh.com/ie/en/data-processing/overview/', + DEFAULT: 'https://docs.ovh.com/gb/en/data-processing/overview/', + ASIA: 'https://docs.ovh.com/asia/en/data-processing/overview/', + AU: 'https://docs.ovh.com/au/en/data-processing/overview/', + CA: 'https://docs.ovh.com/ca/en/data-processing/overview/', + SG: 'https://docs.ovh.com/sg/en/data-processing/overview/', + WE: 'https://docs.ovh.com/us/en/data-processing/overview/', + IN: 'https://docs.ovh.com/asia/en/data-processing/overview/', +}; + +export const DATA_PROCESSING_CAPABILITIES_AND_LIMITATIONS: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/data-processing/capabilities/', + IE: 'https://docs.ovh.com/ie/en/data-processing/capabilities/', + DEFAULT: 'https://docs.ovh.com/gb/en/data-processing/capabilities/', + ASIA: 'https://docs.ovh.com/asia/en/data-processing/capabilities/', + AU: 'https://docs.ovh.com/au/en/data-processing/capabilities/', + CA: 'https://docs.ovh.com/ca/en/data-processing/capabilities/', + SG: 'https://docs.ovh.com/sg/en/data-processing/capabilities/', + WE: 'https://docs.ovh.com/us/en/data-processing/capabilities/', + IN: 'https://docs.ovh.com/asia/en/data-processing/capabilities/', +}; + +export const SUBMIT_A_JAVA_SCALA_JOB: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/data-processing/submit-javascala/', + IE: 'https://docs.ovh.com/ie/en/data-processing/submit-javascala/', + DEFAULT: 'https://docs.ovh.com/gb/en/data-processing/submit-javascala/', + ASIA: 'https://docs.ovh.com/asia/en/data-processing/submit-javascala/', + AU: 'https://docs.ovh.com/au/en/data-processing/submit-javascala/', + CA: 'https://docs.ovh.com/ca/en/data-processing/submit-javascala/', + SG: 'https://docs.ovh.com/sg/en/data-processing/submit-javascala/', + WE: 'https://docs.ovh.com/us/en/data-processing/submit-javascala/', + IN: 'https://docs.ovh.com/asia/en/data-processing/submit-javascala/', +}; + +export const AI_NOTEBOOKS_STARTUP: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/publiccloud/ai/cli/getting-started-cli/', + IE: 'https://docs.ovh.com/ie/en/publiccloud/ai/cli/getting-started-cli/', + DEFAULT: 'https://docs.ovh.com/gb/en/publiccloud/ai/cli/getting-started-cli/', + ASIA: 'https://docs.ovh.com/asia/en/publiccloud/ai/cli/getting-started-cli/', + AU: 'https://docs.ovh.com/au/en/publiccloud/ai/cli/getting-started-cli/', + CA: 'https://docs.ovh.com/ca/en/publiccloud/ai/cli/getting-started-cli/', + SG: 'https://docs.ovh.com/sg/en/publiccloud/ai/cli/getting-started-cli/', + WE: 'https://docs.ovh.com/us/en/publiccloud/ai/cli/getting-started-cli/', + IN: 'https://docs.ovh.com/asia/en/publiccloud/ai/cli/getting-started-cli/', +}; + +export const AI_NOTEBOOKS_DEFINITION: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/publiccloud/ai/notebooks/definition/', + IE: 'https://docs.ovh.com/ie/en/publiccloud/ai/notebooks/definition/', + DEFAULT: 'https://docs.ovh.com/gb/en/publiccloud/ai/notebooks/definition/', + ASIA: 'https://docs.ovh.com/asia/en/publiccloud/ai/notebooks/definition/', + AU: 'https://docs.ovh.com/au/en/publiccloud/ai/notebooks/definition/', + CA: 'https://docs.ovh.com/ca/en/publiccloud/ai/notebooks/definition/', + SG: 'https://docs.ovh.com/sg/en/publiccloud/ai/notebooks/definition/', + WE: 'https://docs.ovh.com/us/en/publiccloud/ai/notebooks/definition/', + IN: 'https://docs.ovh.com/asia/en/publiccloud/ai/notebooks/definition/', +}; + +export const USING_DATA_FORM_OBJECT_STORAGE: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/publiccloud/ai/notebooks/manage-data-ui/', + IE: 'https://docs.ovh.com/ie/en/publiccloud/ai/notebooks/manage-data-ui/', + DEFAULT: + 'https://docs.ovh.com/gb/en/publiccloud/ai/notebooks/manage-data-ui/', + ASIA: 'https://docs.ovh.com/asia/en/publiccloud/ai/notebooks/manage-data-ui/', + AU: 'https://docs.ovh.com/au/en/publiccloud/ai/notebooks/manage-data-ui/', + CA: 'https://docs.ovh.com/ca/en/publiccloud/ai/notebooks/manage-data-ui/', + SG: 'https://docs.ovh.com/sg/en/publiccloud/ai/notebooks/manage-data-ui/', + WE: 'https://docs.ovh.com/us/en/publiccloud/ai/notebooks/manage-data-ui/', + IN: 'https://docs.ovh.com/asia/en/publiccloud/ai/notebooks/manage-data-ui/', +}; + +export const AI_TRAINING_CAPABILITIES_AND_LIMITATIONS: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/publiccloud/ai/training/capabilities/', + IE: 'https://docs.ovh.com/ie/en/publiccloud/ai/training/capabilities/', + DEFAULT: 'https://docs.ovh.com/gb/en/ai-training/capabilities/', + ASIA: 'https://docs.ovh.com/asia/en/publiccloud/ai/training/capabilities/', + AU: 'https://docs.ovh.com/au/en/publiccloud/ai/training/capabilities/', + CA: 'https://docs.ovh.com/ca/en/publiccloud/ai/training/capabilities/', + SG: 'https://docs.ovh.com/sg/en/publiccloud/ai/training/capabilities/', + WE: 'https://docs.ovh.com/us/en/publiccloud/ai/training/capabilities/', + IN: 'https://docs.ovh.com/asia/en/publiccloud/ai/training/capabilities/', +}; + +export const SUBMIT_A_JOB_VIA_THE_USER_INTERFACE: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/publiccloud/ai/training/submit-job/', + IE: 'https://docs.ovh.com/ie/en/publiccloud/ai/training/submit-job/', + DEFAULT: 'https://docs.ovh.com/gb/en/ai-training/submit-job/', + ASIA: 'https://docs.ovh.com/asia/en/publiccloud/ai/training/submit-job/', + AU: 'https://docs.ovh.com/au/en/publiccloud/ai/training/submit-job/', + CA: 'https://docs.ovh.com/ca/en/publiccloud/ai/training/submit-job/', + SG: 'https://docs.ovh.com/sg/en/publiccloud/ai/training/submit-job/', + WE: 'https://docs.ovh.com/us/en/publiccloud/ai/training/submit-job/', + IN: 'https://docs.ovh.com/asia/en/publiccloud/ai/training/submit-job/', +}; + +export const MANAGING_A_CUSTOM_IMAGE: GuideLinks = { + GB: + 'https://docs.ovh.com/gb/en/publiccloud/ai/training/build-use-custom-image/', + IE: + 'https://docs.ovh.com/ie/en/publiccloud/ai/training/build-use-custom-image/', + DEFAULT: 'https://docs.ovh.com/gb/en/ai-training/build-use-custom-image/', + ASIA: + 'https://docs.ovh.com/asia/en/publiccloud/ai/training/build-use-custom-image/', + AU: + 'https://docs.ovh.com/au/en/publiccloud/ai/training/build-use-custom-image/', + CA: + 'https://docs.ovh.com/ca/en/publiccloud/ai/training/build-use-custom-image/', + SG: + 'https://docs.ovh.com/sg/en/publiccloud/ai/training/build-use-custom-image/', + WE: + 'https://docs.ovh.com/us/en/publiccloud/ai/training/build-use-custom-image/', + IN: + 'https://docs.ovh.com/asia/en/publiccloud/ai/training/build-use-custom-image/', +}; + +export const DEPLOYING_A_CUSTOM_MODEL: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/ml-serving/deploy-serialized-models/', + IE: 'https://docs.ovh.com/ie/en/ml-serving/deploy-serialized-models/', + DEFAULT: 'https://docs.ovh.com/gb/en/ml-serving/deploy-serialized-models/', + ASIA: 'https://docs.ovh.com/asia/en/ml-serving/deploy-serialized-models/', + AU: 'https://docs.ovh.com/au/en/ml-serving/deploy-serialized-models/', + CA: 'https://docs.ovh.com/ca/en/ml-serving/deploy-serialized-models/', + SG: 'https://docs.ovh.com/sg/en/ml-serving/deploy-serialized-models/', + WE: 'https://docs.ovh.com/us/en/ml-serving/deploy-serialized-models/', + IN: 'https://docs.ovh.com/asia/en/ml-serving/deploy-serialized-models/', +}; + +export const MODELS_DEFINITION: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/ml-serving/models/', + IE: 'https://docs.ovh.com/ie/en/ml-serving/models/', + DEFAULT: 'https://docs.ovh.com/gb/en/ml-serving/models/', + ASIA: 'https://docs.ovh.com/asia/en/ml-serving/models/', + AU: 'https://docs.ovh.com/au/en/ml-serving/models/', + CA: 'https://docs.ovh.com/ca/en/ml-serving/models/', + SG: 'https://docs.ovh.com/sg/en/ml-serving/models/', + WE: 'https://docs.ovh.com/us/en/ml-serving/models/', + IN: 'https://docs.ovh.com/asia/en/ml-serving/models/', +}; + +export const EXPORTING_A_TENSORFLOW_MODEL: GuideLinks = { + GB: 'https://docs.ovh.com/gb/en/ml-serving/export-tensorflow-models/', + IE: 'https://docs.ovh.com/ie/en/ml-serving/export-tensorflow-models/', + DEFAULT: 'https://docs.ovh.com/gb/en/ml-serving/export-tensorflow-models/', + ASIA: 'https://docs.ovh.com/asia/en/ml-serving/export-tensorflow-models/', + AU: 'https://docs.ovh.com/au/en/ml-serving/export-tensorflow-models/', + CA: 'https://docs.ovh.com/ca/en/ml-serving/export-tensorflow-models/', + SG: 'https://docs.ovh.com/sg/en/ml-serving/export-tensorflow-models/', + WE: 'https://docs.ovh.com/us/en/ml-serving/export-tensorflow-models/', + IN: 'https://docs.ovh.com/asia/en/ml-serving/export-tensorflow-models/', +}; + +export const PREFIX_UNIVERSE_NAME = 'public-cloud'; + +export const DEFAULT_GUIDES = { + public_cloud_guides: { + url: PUBLIC_CLOUD_GUIDES, + key: 'all_guides', + tracking: '::guides::go_to_all_guides', + }, + first_steps_with_instances: { + url: FIRST_STEPS_WITH_INSTANCES, + key: 'first_steps_with_instances', + tracking: '::guides::go_to_instances_guide', + }, +}; + +export const GUIDES_LIST: GuideList = { + storage: { + public_cloud_storage_guides: { + url: PUBLIC_CLOUD_STORAGE_GUIDES, + key: 'all_storage_guides', + tracking: '::guides::go_to_storage', + }, + first_steps_with_instances: { + url: FIRST_STEPS_WITH_INSTANCES, + key: 'first_steps_with_instances', + tracking: '::guides::go_to_instances_guide', + }, + ip_fail_over: { + url: IP_FAIL_OVER, + key: 'ip_fail_over', + tracking: '::guides::go_to_configure_a_failover_ip', + }, + user_root_and_password: { + url: USER_ROOT_AND_PASSWORD, + key: 'user_root_and_password', + tracking: '::guides::go_to_become_the_root_user_and_select_a_password', + }, + reverse_dns: { + url: REVERSE_DNS, + key: 'reverse_dns', + tracking: '::guides::go_to_configure_reverse_dns_instance', + }, + }, + objectStorage: { + public_cloud_storage_guides: { + url: PUBLIC_CLOUD_STORAGE_GUIDES, + key: 'all_storage_guides', + tracking: '::guides::go_to_storage', + }, + public_cloud_guides: { + url: PUBLIC_CLOUD_GUIDES, + key: 'public_cloud_guides', + tracking: '::guides::go_to_public_cloud_storage', + }, + }, + instances: { + ...DEFAULT_GUIDES, + ip_fail_over: { + url: IP_FAIL_OVER, + key: 'ip_fail_over', + tracking: '::guides::go_to_configure_a_failover_ip', + }, + user_root_and_password: { + url: USER_ROOT_AND_PASSWORD, + key: 'user_root_and_password', + tracking: '::guides::go_to_become_the_root_user_and_select_a_password', + }, + reverse_dns: { + url: REVERSE_DNS, + key: 'reverse_dns', + tracking: '::guides::go_to_configure_reverse_dns_instance', + }, + }, + databases: { + ...DEFAULT_GUIDES, + first_steps_with_databases: { + url: FIRST_STEPS_WITH_DATABASES, + key: 'first_steps_with_databases', + tracking: '::guides::go_to_getting_started', + }, + mongo_db_capabilities_and_limitations: { + url: MONGO_DB_CAPABILITIES_AND_LIMITATIONS, + key: 'mongo_db_capabilities_and_limitations', + tracking: '::guides::go_to_mongodb_capabilities', + }, + mysql_capabilities_and_limitations: { + url: MYSQL_CAPABILITIES_AND_LIMITATIONS, + key: 'mysql_capabilities_and_limitations', + tracking: '::guides::go_to_mysql_capabilities', + }, + }, + kubernetes: { + ...DEFAULT_GUIDES, + create_a_cluster: { + url: CREATE_A_CLUSTER, + key: 'create_a_cluster', + tracking: '::guides::go_to_creating_a_cluster', + }, + deploy_an_application: { + url: DEPLOY_AN_APPLICATION, + key: 'deploy_an_application', + tracking: '::guides::go_to_deploying_an_application', + }, + loadbalancer_kube: { + url: LOADBALANCER_KUBE, + key: 'loadbalancer_kube', + tracking: '::guides::go_to_using_lb', + }, + }, + private_registry: { + ...DEFAULT_GUIDES, + faq_managed_private_registry: { + url: FAQ_MANAGED_PRIVATE_REGISTRY, + key: 'faq_managed_private_registry', + tracking: '::guides::go_to_managed_private_registry_faq', + }, + create_a_managed_private_register: { + url: CREATE_A_MANAGED_PRIVATE_REGISTER, + key: 'create_a_managed_private_register', + tracking: '::guides::go_to_creating_a_private_registry', + }, + create_and_use_a_private_image: { + url: CREATE_AND_USE_A_PRIVATE_IMAGE, + key: 'create_and_use_a_private_image', + tracking: '::guides::go_to_creating_and_using_a_private_image', + }, + }, + ai_machine_learning: { + ...DEFAULT_GUIDES, + differences_between_ai_notebooks_ai_training_ai_apps: { + url: DIFFERENCES_BETWEEN_AI_NOTEBOOKS_AI_TRAINING_AI_APPS, + key: 'differences_between_ai_notebooks_ai_training_ai_apps', + tracking: '::guides::go_to_ai_comparative_tables', + }, + ai_apps_capabilities_and_limitations: { + url: AI_APPS_CAPABILITIES_AND_LIMITATIONS, + key: 'ai_apps_capabilities_and_limitations', + tracking: '::guides::go_to_capabilities', + }, + accessing_your_ai_apps_with_tokens: { + url: ACCESSING_YOUR_AI_APPS_WITH_TOKENS, + key: 'accessing_your_ai_apps_with_tokens', + tracking: '::guides::go_to_ai_apps_tokens', + }, + }, + data_processing: { + ...DEFAULT_GUIDES, + presentation_of_data_processing: { + url: PRESENTATION_OF_DATA_PROCESSING, + key: 'presentation_of_data_processing', + tracking: '::guides::go_to_overview', + }, + data_processing_capabilities_and_limitations: { + url: DATA_PROCESSING_CAPABILITIES_AND_LIMITATIONS, + key: 'data_processing_capabilities_and_limitations', + tracking: '::guides::go_to_capabilities', + }, + submit_a_java_scala_job: { + url: SUBMIT_A_JAVA_SCALA_JOB, + key: 'submit_a_java_scala_job', + tracking: '::guides::go_to_submit_javascala', + }, + }, + ai_notenooks: { + ...DEFAULT_GUIDES, + ai_notebooks_startup: { + url: AI_NOTEBOOKS_STARTUP, + key: 'ai_notebooks_startup', + tracking: '::guides::go_to_getting_started_cli', + }, + ai_notebooks_definition: { + url: AI_NOTEBOOKS_DEFINITION, + key: 'ai_notebooks_definition', + tracking: '::guides::go_to_definition', + }, + using_data_form_object_storage: { + url: USING_DATA_FORM_OBJECT_STORAGE, + key: 'using_data_form_object_storage', + tracking: '::guides::go_to_access_object_storage_data', + }, + }, + ai_training: { + ...DEFAULT_GUIDES, + ai_training_capabilities_and_limitations: { + url: AI_TRAINING_CAPABILITIES_AND_LIMITATIONS, + key: 'ai_training_capabilities_and_limitations', + tracking: '::guides::go_to_capabilities', + }, + submit_a_job_via_the_user_interface: { + url: SUBMIT_A_JOB_VIA_THE_USER_INTERFACE, + key: 'submit_a_job_via_the_user_interface', + tracking: '::guides::go_to_submit_job', + }, + managing_a_custom_image: { + url: MANAGING_A_CUSTOM_IMAGE, + key: 'managing_a_custom_image', + tracking: '::guides::go_to_build_use_custom_image', + }, + }, + ml_serving: { + ...DEFAULT_GUIDES, + deploying_a_custom_model: { + url: DEPLOYING_A_CUSTOM_MODEL, + key: 'deploying_a_custom_model', + tracking: '::guides::go_to_deploy_serialized_models', + }, + models_definition: { + url: MODELS_DEFINITION, + key: 'models_definition', + tracking: '::guides::go_to_models', + }, + exporting_a_tensorflow_model: { + url: EXPORTING_A_TENSORFLOW_MODEL, + key: 'exporting_a_tensorflow_model', + tracking: '::guides::go_to_export_tensorflow_models', + }, + }, + private_network: { + ...DEFAULT_GUIDES, + }, +}; + +export default { + GUIDES_LIST, +}; diff --git a/packages/manager/apps/pci-vouchers/src/hooks/useProject.ts b/packages/manager/apps/pci-vouchers/src/hooks/useProject.ts new file mode 100644 index 000000000000..6d89044a63eb --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/hooks/useProject.ts @@ -0,0 +1,27 @@ +import { QueryOptions, useQuery } from '@tanstack/react-query'; +import { getProject, Project } from '@/data/project'; + +export interface ResponseAPIError { + message: string; + stack: string; + name: string; + code: string; + response?: { + headers?: { + [key: string]: string; + 'x-ovh-queryid': string; + }; + }; +} + +export const useProject = ( + projectId: string, + opt?: QueryOptions, +) => + useQuery({ + queryKey: ['project', projectId], + queryFn: () => getProject(projectId), + ...opt, + }); + +export default useProject; diff --git a/packages/manager/apps/pci-vouchers/src/hooks/useVouchers.ts b/packages/manager/apps/pci-vouchers/src/hooks/useVouchers.ts new file mode 100644 index 000000000000..3011702985fd --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/hooks/useVouchers.ts @@ -0,0 +1,111 @@ +import { useMemo } from 'react'; +import { useMutation, useQuery } from '@tanstack/react-query'; +import { addVoucher, buyCredit, BuyCreditResult } from '@/data/voucher'; +import { + filterVouchers, + getAllVouchers, + paginateResults, + VouchersOptions, +} from '@/data/vouchers'; +import queryClient from '@/queryClient'; + +type AddVoucherProps = { + projectId: string; + onError: (cause: Error) => void; + onSuccess: () => void; +}; + +export function useAddVoucher({ + projectId, + onError, + onSuccess, +}: AddVoucherProps) { + const mutation = useMutation({ + mutationFn: (code: string) => { + return addVoucher(`${projectId}`, code); + }, + onError, + onSuccess: async () => { + await queryClient.invalidateQueries({ + queryKey: ['project', projectId, 'vouchers'], + }); + onSuccess(); + }, + }); + + return { + add: (code: string) => { + return mutation.mutate(code); + }, + ...mutation, + }; +} + +// const VOUCHERS_POLLING_INTERVAL = 5000; + +export const useAllVouchers = (projectId: string) => { + return useQuery({ + queryKey: ['project', projectId, 'vouchers'], + queryFn: () => getAllVouchers(projectId), + retry: false, + ...{ + keepPreviousData: true, + }, + }); +}; + +export const useVouchers = ( + projectId: string, + { pagination, sorting }: VouchersOptions, +) => { + // retrieve All vouchers from API + const { + data: vouchers, + error: allVouchersError, + isLoading: allVouchersLoading, + } = useAllVouchers(projectId); + + return useMemo(() => { + return { + isLoading: allVouchersLoading, + error: allVouchersError, + data: paginateResults( + filterVouchers(vouchers || [], sorting), + pagination, + ), + }; + }, [vouchers, sorting, pagination]); +}; + +export type BuyCreditProps = { + projectId: string; + onError: (cause: Error) => void; + onSuccess: (result: BuyCreditResult) => void; +}; + +export function useBuyCredit({ + projectId, + onError, + onSuccess, +}: BuyCreditProps) { + const mutation = useMutation({ + mutationFn: (amount: number) => { + return buyCredit(`${projectId}`, amount); + }, + onError, + onSuccess, + }); + + return { + buy: (amount: number) => { + return mutation.mutate(amount); + }, + ...mutation, + }; +} + +export default { + useAddVoucher, + useBuyCredit, + useVouchers, +}; diff --git a/packages/manager/apps/pci-vouchers/src/i18n.ts b/packages/manager/apps/pci-vouchers/src/i18n.ts new file mode 100644 index 000000000000..3834ec5c3234 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/i18n.ts @@ -0,0 +1,33 @@ +import i18n from 'i18next'; +import I18NextHttpBackend from 'i18next-http-backend'; +import { initReactI18next } from 'react-i18next'; + +export default async function initI18n( + locale = 'fr_FR', + availablesLocales = ['fr_FR'], +) { + await i18n + .use(initReactI18next) + .use(I18NextHttpBackend) + .use({ + type: 'postProcessor', + name: 'normalize', + process: (value: string) => + value ? value.replace(/&/g, '&') : value, + }) + .init({ + lng: locale, + fallbackLng: 'fr_FR', + supportedLngs: availablesLocales, + defaultNS: 'common', + ns: ['common', 'guides-header'], // namespaces to load by default + backend: { + loadPath: (lngs: string[], namespaces: string[]) => + `${import.meta.env.BASE_URL}translations/${namespaces[0]}/Messages_${ + lngs[0] + }.json`, + }, + postProcess: 'normalize', + }); + return i18n; +} diff --git a/packages/manager/apps/pci-vouchers/src/index.css b/packages/manager/apps/pci-vouchers/src/index.css new file mode 100644 index 000000000000..d0e30d40cd1b --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/index.css @@ -0,0 +1,7 @@ +@tailwind base; +@tailwind components; +@tailwind utilities; + +.application { + @apply mx-11 mt-8; +} diff --git a/packages/manager/apps/pci-vouchers/src/interface/index.ts b/packages/manager/apps/pci-vouchers/src/interface/index.ts new file mode 100644 index 000000000000..55d4a4527ab4 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/interface/index.ts @@ -0,0 +1,20 @@ +export interface Credit { + text: string; + value: number; + currencyCode: string; +} + +export type Voucher = { + id: number; + bill: string | null; + products: string | null; + description: string; + voucher: string; + validity: { + from: string | null; + to: string | null; + }; + total_credit: Credit; + available_credit: Credit; + used_credit: Credit; +}; diff --git a/packages/manager/apps/pci-vouchers/src/main.tsx b/packages/manager/apps/pci-vouchers/src/main.tsx new file mode 100644 index 000000000000..c650d581525e --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/main.tsx @@ -0,0 +1,51 @@ +import React from 'react'; +import ReactDOM from 'react-dom/client'; +import { + ShellProvider, + initShellContext, +} from '@ovh-ux/manager-react-shell-client'; +import App from './App'; +import initI18n from './i18n'; + +import './index.css'; + +import '@/vite-hmr.ts'; + +const init = async ( + appName: string, + { reloadOnLocaleChange } = { reloadOnLocaleChange: false }, +) => { + const context = await initShellContext(appName); + + const region = context.environment.getRegion(); + try { + await import(`./config-${region}.js`); + } catch (error) { + // nothing to do + } + + const locales = await context.shell.i18n.getAvailableLocales(); + + const i18n = await initI18n( + context.environment.getUserLocale(), + locales.map(({ key }) => key), + ); + + context.shell.i18n.onLocaleChange(({ locale }: { locale: string }) => { + if (reloadOnLocaleChange) { + window.top?.location.reload(); + } else { + i18n.changeLanguage(locale); + } + }); + + ReactDOM.createRoot(document.getElementById('root')!).render( + + + + + , + ); +}; + +init('pci-vouchers'); diff --git a/packages/manager/apps/pci-vouchers/src/pages/AddVoucherPage.tsx b/packages/manager/apps/pci-vouchers/src/pages/AddVoucherPage.tsx new file mode 100644 index 000000000000..6fd112be9e87 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/pages/AddVoucherPage.tsx @@ -0,0 +1,33 @@ +import { useNavigate, useParams } from 'react-router-dom'; +import { useTranslation } from 'react-i18next'; +import { useNotifications } from '@ovhcloud/manager-components'; +import AddVoucherModal from '@/components/vouchers/AddVoucherModal'; + +export default function AddVoucherPage() { + const { projectId } = useParams(); + const { t } = useTranslation('common'); + const { addError, addSuccess } = useNotifications(); + const navigate = useNavigate(); + const onClose = () => { + navigate('..'); + }; + return ( + <> + { + addSuccess(t('cpb_vouchers_add_success')); + }} + onError={(error: Error) => { + addError( + <> + {t('cpb_vouchers_add_error')} + {error && ` (${error.message})`} + , + ); + }} + /> + + ); +} diff --git a/packages/manager/apps/pci-vouchers/src/pages/BuyCreditPage.tsx b/packages/manager/apps/pci-vouchers/src/pages/BuyCreditPage.tsx new file mode 100644 index 000000000000..4c3e0e6cb3c8 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/pages/BuyCreditPage.tsx @@ -0,0 +1,45 @@ +import { useNavigate, useParams } from 'react-router-dom'; +import { useTranslation } from 'react-i18next'; +import { useNotifications } from '@ovhcloud/manager-components'; +import BuyCreditModal from '@/components/vouchers/BuyCreditModal'; +import style from '@/components/common.module.css'; + +export default function BuyCreditPage() { + const { projectId } = useParams(); + const { t } = useTranslation('common'); + const { addError, addSuccess } = useNotifications(); + const navigate = useNavigate(); + const onClose = () => { + navigate('..'); + }; + return ( + <> + { + addSuccess( + , + ); + }} + onError={(error: Error) => { + addError( + <> + {t('cpb_vouchers_add_error')} + {error && ` (${error.message})`} + , + ); + }} + /> + + ); +} diff --git a/packages/manager/apps/pci-vouchers/src/pages/Layout.tsx b/packages/manager/apps/pci-vouchers/src/pages/Layout.tsx new file mode 100644 index 000000000000..6bc10e8a0f0a --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/pages/Layout.tsx @@ -0,0 +1,65 @@ +import { Outlet, useParams, useRouteError } from 'react-router-dom'; + +import { useNavigation } from '@ovh-ux/manager-react-shell-client'; +import { Suspense } from 'react'; +import BreadCrumbs from '@/components/BreadCrumbs'; +import ShellRoutingSync from '@/core/ShellRoutingSync'; +import HidePreloader from '@/core/HidePreloader'; +import useProject, { ResponseAPIError } from '@/hooks/useProject'; + +import ErrorPage from '@/components/error-page/ErrorPage'; + +export default function Layout() { + const { projectId } = useParams(); + const { error, isSuccess } = useProject(projectId || '', { retry: false }); + + if (error) { + error.message = `Project ${projectId} doesn't exists`; + throw error; + } + return ( +
+ + + + {isSuccess && ( + <> + + + + )} + +
+ ); +} + +export const ErrorBoundary = () => { + const error = useRouteError(); + const nav = useNavigation(); + + const redirectionApplication = 'public-cloud'; + + const navigateToHomePage = () => { + nav.navigateTo(redirectionApplication, '', {}); + }; + + const reloadPage = () => { + nav.reload(); + }; + + return ( + + reloadPage()} + navigateToHomepage={() => navigateToHomePage()} + errorMessage={(error as ResponseAPIError)?.message || ''} + xOvhQueryId={ + (error as ResponseAPIError)?.response?.headers?.['x-ovh-queryid'] || + '' + } + /> + + + + ); +}; diff --git a/packages/manager/apps/pci-vouchers/src/pages/ListingPage.tsx b/packages/manager/apps/pci-vouchers/src/pages/ListingPage.tsx new file mode 100644 index 000000000000..9667a3fa459f --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/pages/ListingPage.tsx @@ -0,0 +1,232 @@ +import { useEffect, useState } from 'react'; +import { Outlet, useHref, useParams } from 'react-router-dom'; +import { useTranslation } from 'react-i18next'; +import { + Datagrid, + DataGridTextCell, + useDatagridSearchParams, + Notifications, +} from '@ovhcloud/manager-components'; + +import { + OsdsText, + OsdsDivider, + OsdsBreadcrumb, + OsdsButton, + OsdsMessage, + OsdsSpinner, +} from '@ovhcloud/ods-components/react'; +import { + ODS_BUTTON_SIZE, + ODS_BUTTON_VARIANT, + ODS_DIVIDER_SIZE, + ODS_MESSAGE_TYPE, + ODS_SPINNER_SIZE, +} from '@ovhcloud/ods-components'; +import { + ODS_THEME_COLOR_INTENT, + ODS_THEME_TYPOGRAPHY_LEVEL, + ODS_THEME_TYPOGRAPHY_SIZE, +} from '@ovhcloud/ods-common-theming'; + +import { useNavigation } from '@ovh-ux/manager-react-shell-client'; + +import { Voucher } from '@/interface'; + +import useProject from '@/hooks/useProject'; +import { useVouchers } from '@/hooks/useVouchers'; + +import GuidesHeader from '@/components/guides/GuidesHeader'; + +import Credit from '@/components/vouchers/listing/Credit'; +import DisplayName from '@/components/vouchers/listing/DisplayName'; +import Validity from '@/components/vouchers/listing/Validity'; +import { isDiscoveryProject } from '@/data/project'; +import ActivateProjectBanner from '@/components/activate-project-banner/ActivateProjectBanner'; + +export default function ListingPage() { + const { t } = useTranslation('common'); + const { t: tError } = useTranslation('error'); + + const navigation = useNavigation(); + const { projectId } = useParams(); + const [urlProject, setUrlProject] = useState(''); + useEffect(() => { + navigation + .getURL('public-cloud', `#/pci/projects/${projectId}`, {}) + .then((data) => { + setUrlProject(data as string); + }); + }, [projectId, navigation]); + + const { data: project } = useProject(projectId || ''); + + const columns = [ + { + id: 'description', + cell: (props: Voucher) => { + return ; + }, + label: t('cpb_vouchers_name_cell'), + }, + { + id: 'products', + cell: (props: Voucher) => { + return ( + + {props.products || t('cpb_vouchers_products_all')} + + ); + }, + label: t('cpb_vouchers_products_cell'), + }, + { + id: 'voucher', + cell: (props: Voucher) => { + return {props.voucher}; + }, + label: t('cpb_vouchers_voucher_cell'), + }, + { + id: 'validityFrom', + cell: (props: Voucher) => { + return ; + }, + label: t('cpb_vouchers_validity_from_cell'), + }, + + { + id: 'total_credit', + cell: (props: Voucher) => { + return ; + }, + label: t('cpb_vouchers_total_credit_cell'), + }, + { + id: 'validityTo', + cell: (props: Voucher) => { + return ; + }, + label: t('cpb_vouchers_validity_to_cell'), + }, + { + id: 'available_credit', + cell: (props: Voucher) => { + return ; + }, + label: t('cpb_vouchers_available_credit_cell'), + }, + ]; + + const { + pagination, + setPagination, + sorting, + setSorting, + } = useDatagridSearchParams(); + + const { error, data: vouchers, isLoading } = useVouchers(projectId || '', { + pagination, + sorting, + }); + + const hrefAdd = useHref('./add'); + const hrefCredit = useHref('./credit/buy'); + + return ( + <> + {project && ( + + )} +
+ + {t('cpb_project_management_credit_vouchers')} + + +
+ + + + {t('cpb_vouchers_add_explain_bis')} + + + + {t('cpb_vouchers_credit_comment')} + + + {isDiscoveryProject(project) && ( + + )} + +
+ + {t('cpb_vouchers_add_button')} + + + {t('cpb_vouchers_add_credit_button')} + +
+ + {error && ( + + {tError('manager_error_page_default')} + + )} + + {isLoading && !error && ( +
+ +
+ )} + + {!isLoading && !error && ( +
+ +
+ )} + + + ); +} diff --git a/packages/manager/apps/pci-vouchers/src/queryClient.ts b/packages/manager/apps/pci-vouchers/src/queryClient.ts new file mode 100644 index 000000000000..e3a6fb388e53 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/queryClient.ts @@ -0,0 +1,11 @@ +import { QueryClient } from '@tanstack/react-query'; + +export const queryClient = new QueryClient({ + defaultOptions: { + queries: { + staleTime: 300_000, + }, + }, +}); + +export default queryClient; diff --git a/packages/manager/apps/pci-vouchers/src/routes.tsx b/packages/manager/apps/pci-vouchers/src/routes.tsx new file mode 100644 index 000000000000..9a925b3deabe --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/routes.tsx @@ -0,0 +1,43 @@ +const lazyRouteConfig = (importFn: CallableFunction) => { + return { + lazy: async () => { + const { default: moduleDefault, ...moduleExports } = await importFn(); + + return { + Component: moduleDefault, + ...moduleExports, + }; + }, + }; +}; + +export default [ + { + path: '/', + ...lazyRouteConfig(() => import('@/pages/Layout')), + }, + { + path: '/pci/projects/:projectId/vouchers', + ...lazyRouteConfig(() => import('@/pages/Layout')), + children: [ + { + path: '', + ...lazyRouteConfig(() => import('@/pages/ListingPage')), + children: [ + { + path: 'add', + ...lazyRouteConfig(() => import('@/pages/AddVoucherPage')), + }, + { + path: 'credit/buy', + ...lazyRouteConfig(() => import('@/pages/BuyCreditPage')), + }, + ], + }, + ], + }, + { + path: '*', + element: <>Not found page, + }, +]; diff --git a/packages/manager/apps/pci-vouchers/src/vite-env.d.ts b/packages/manager/apps/pci-vouchers/src/vite-env.d.ts new file mode 100644 index 000000000000..11f02fe2a006 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/vite-env.d.ts @@ -0,0 +1 @@ +/// diff --git a/packages/manager/apps/pci-vouchers/src/vite-hmr.ts b/packages/manager/apps/pci-vouchers/src/vite-hmr.ts new file mode 100644 index 000000000000..473d87630039 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/src/vite-hmr.ts @@ -0,0 +1,5 @@ +if (import.meta.hot) { + import.meta.hot.on('iframe-reload', () => { + window.location.reload(); + }); +} diff --git a/packages/manager/apps/pci-vouchers/tailwind.config.js b/packages/manager/apps/pci-vouchers/tailwind.config.js new file mode 100644 index 000000000000..5f21408bbf42 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/tailwind.config.js @@ -0,0 +1,10 @@ +import config from '@ovh-ux/manager-tailwind-config'; + +/** @type {import('tailwindcss').Config} */ +module.exports = { + ...config, + content: [ + './src/**/*.{js,jsx,ts,tsx}', + '../../../manager-components/src/**/*.{js,jsx,ts,tsx}', + ], +}; diff --git a/packages/manager/apps/pci-vouchers/tsconfig.build.json b/packages/manager/apps/pci-vouchers/tsconfig.build.json new file mode 100644 index 000000000000..4dc23fb9c4c5 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/tsconfig.build.json @@ -0,0 +1,4 @@ +{ + "extends": "./tsconfig.json", + "exclude": ["src/__tests__"] +} diff --git a/packages/manager/apps/pci-vouchers/tsconfig.json b/packages/manager/apps/pci-vouchers/tsconfig.json new file mode 100644 index 000000000000..505c45e7762d --- /dev/null +++ b/packages/manager/apps/pci-vouchers/tsconfig.json @@ -0,0 +1,30 @@ +{ + "compilerOptions": { + "target": "ES2020", + "useDefineForClassFields": true, + "lib": ["ES2020", "DOM", "DOM.Iterable"], + "module": "ESNext", + "skipLibCheck": true, + + /* Bundler mode */ + "moduleResolution": "node", + "allowImportingTsExtensions": true, + "resolveJsonModule": true, + "isolatedModules": true, + "noEmit": true, + "jsx": "react-jsx", + + /* Linting */ + "noUnusedParameters": true, + "noFallthroughCasesInSwitch": true, + + "paths": { + "@/*": ["./src/*"], + "react": ["./node_modules/@types/react"] + }, + "allowSyntheticDefaultImports": true, + "esModuleInterop": true + }, + "include": ["src"], + "exclude": ["node_modules", "dist", "types"] +} diff --git a/packages/manager/apps/pci-vouchers/vite.config.ts b/packages/manager/apps/pci-vouchers/vite.config.ts new file mode 100644 index 000000000000..8302c9c21984 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/vite.config.ts @@ -0,0 +1,26 @@ +import { defineConfig } from 'vite'; +import { getBaseConfig } from '@ovh-ux/manager-vite-config'; +import tailwindcss from 'tailwindcss'; + +const baseConfig = getBaseConfig({}); + +export default defineConfig({ + ...baseConfig, + root: '', + css: { + postcss: { + plugins: [tailwindcss], + }, + }, + resolve: { + ...baseConfig.resolve, + dedupe: [ + 'i18next', + 'react', + 'react-dom', + 'react-i18next', + 'react-router-dom', + 'zustand', + ], + }, +}); diff --git a/packages/manager/apps/pci-vouchers/vitest.config.js b/packages/manager/apps/pci-vouchers/vitest.config.js new file mode 100644 index 000000000000..1323d60d79e1 --- /dev/null +++ b/packages/manager/apps/pci-vouchers/vitest.config.js @@ -0,0 +1,32 @@ +import path from 'path'; +import { defineConfig } from 'vite'; +import react from '@vitejs/plugin-react'; + +// https://vitejs.dev/config/ +export default defineConfig({ + plugins: [react()], + test: { + globals: true, + environment: 'jsdom', + coverage: { + include: ['src'], + exclude: [ + 'src/interface', + 'src/__tests__', + 'src/guides-header.constants.ts', + 'src/vite-*.ts', + 'src/App.tsx', + 'src/core/ShellRoutingSync.tsx', + 'src/i18n.ts', + 'src/main.tsx', + 'src/routes.tsx', + ], + }, + }, + resolve: { + alias: { + '@': path.resolve(__dirname, 'src'), + }, + mainFields: ['module'], + }, +}); diff --git a/packages/manager/apps/pci/CHANGELOG.md b/packages/manager/apps/pci/CHANGELOG.md index f16e97e25470..1a985a10b064 100644 --- a/packages/manager/apps/pci/CHANGELOG.md +++ b/packages/manager/apps/pci/CHANGELOG.md @@ -3,6 +3,46 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [4.1.11](https://github.com/ovh/manager/compare/@ovh-ux/manager-pci-app@4.1.10...@ovh-ux/manager-pci-app@4.1.11) (2024-03-18) + +**Note:** Version bump only for package @ovh-ux/manager-pci-app + + + + + +## [4.1.10](https://github.com/ovh/manager/compare/@ovh-ux/manager-pci-app@4.1.9...@ovh-ux/manager-pci-app@4.1.10) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-pci-app + + + + + +## [4.1.9](https://github.com/ovh/manager/compare/@ovh-ux/manager-pci-app@4.1.8...@ovh-ux/manager-pci-app@4.1.9) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-pci-app + + + + + +## [4.1.8](https://github.com/ovh/manager/compare/@ovh-ux/manager-pci-app@4.1.7...@ovh-ux/manager-pci-app@4.1.8) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-pci-app + + + + + +## [4.1.7](https://github.com/ovh/manager/compare/@ovh-ux/manager-pci-app@4.1.6...@ovh-ux/manager-pci-app@4.1.7) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-pci-app + + + + + ## [4.1.6](https://github.com/ovh/manager/compare/@ovh-ux/manager-pci-app@4.1.5...@ovh-ux/manager-pci-app@4.1.6) (2024-03-04) **Note:** Version bump only for package @ovh-ux/manager-pci-app diff --git a/packages/manager/apps/pci/package.json b/packages/manager/apps/pci/package.json index c889f959b03f..8b8def52f24f 100644 --- a/packages/manager/apps/pci/package.json +++ b/packages/manager/apps/pci/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-pci-app", - "version": "4.1.6", + "version": "4.1.11", "private": true, "description": "Public Cloud Instance standalone application.", "repository": { @@ -24,13 +24,13 @@ "@ovh-ux/manager-banner": "^1.3.1", "@ovh-ux/manager-cloud-styles": "^1.7.0", "@ovh-ux/manager-components": "^1.11.0", - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-filters": "^1.1.1", "@ovh-ux/manager-ng-layout-helpers": "^2.9.0", - "@ovh-ux/manager-pci": "^6.28.0", + "@ovh-ux/manager-pci": "^6.30.1", "@ovh-ux/manager-trusted-nic": "^1.2.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-at-internet-ui-router-plugin": "^3.5.0", "@ovh-ux/ng-ovh-api-wrappers": "^5.1.0", "@ovh-ux/ng-ovh-cloud-universe-components": "^2.12.0", @@ -40,7 +40,7 @@ "@ovh-ux/ng-ovh-http": "^5.1.1", "@ovh-ux/ng-ovh-payment-method": "^9.14.0", "@ovh-ux/ng-ovh-proxy-request": "^2.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-responsive-popover": "^6.1.1", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-ovh-swimming-poll": "^5.1.1", @@ -52,7 +52,7 @@ "@ovh-ux/ng-translate-async-loader": "^2.2.1", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", "@ovh-ux/ng-ui-router-layout": "^4.3.0", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "angular": "^1.7.5", diff --git a/packages/manager/apps/public-cloud/CHANGELOG.md b/packages/manager/apps/public-cloud/CHANGELOG.md index e0b06519eab9..1e857efa1357 100644 --- a/packages/manager/apps/public-cloud/CHANGELOG.md +++ b/packages/manager/apps/public-cloud/CHANGELOG.md @@ -3,6 +3,46 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [6.2.8](https://github.com/ovh/manager/compare/@ovh-ux/manager-public-cloud@6.2.7...@ovh-ux/manager-public-cloud@6.2.8) (2024-03-18) + +**Note:** Version bump only for package @ovh-ux/manager-public-cloud + + + + + +## [6.2.7](https://github.com/ovh/manager/compare/@ovh-ux/manager-public-cloud@6.2.6...@ovh-ux/manager-public-cloud@6.2.7) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-public-cloud + + + + + +## [6.2.6](https://github.com/ovh/manager/compare/@ovh-ux/manager-public-cloud@6.2.5...@ovh-ux/manager-public-cloud@6.2.6) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-public-cloud + + + + + +## [6.2.5](https://github.com/ovh/manager/compare/@ovh-ux/manager-public-cloud@6.2.4...@ovh-ux/manager-public-cloud@6.2.5) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-public-cloud + + + + + +## [6.2.4](https://github.com/ovh/manager/compare/@ovh-ux/manager-public-cloud@6.2.3...@ovh-ux/manager-public-cloud@6.2.4) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-public-cloud + + + + + ## [6.2.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-public-cloud@6.2.2...@ovh-ux/manager-public-cloud@6.2.3) (2024-03-04) **Note:** Version bump only for package @ovh-ux/manager-public-cloud diff --git a/packages/manager/apps/public-cloud/package.json b/packages/manager/apps/public-cloud/package.json index af7a1cb3b8c6..d5070a8d7de1 100644 --- a/packages/manager/apps/public-cloud/package.json +++ b/packages/manager/apps/public-cloud/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-public-cloud", - "version": "6.2.3", + "version": "6.2.8", "private": true, "description": "OVHcloud Public Cloud control panel.", "repository": { @@ -27,13 +27,13 @@ "@ovh-ux/manager-catalog-price": "^1.8.0", "@ovh-ux/manager-cloud-styles": "^1.7.0", "@ovh-ux/manager-components": "^1.11.0", - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-error-page": "^2.4.0", "@ovh-ux/manager-ng-layout-helpers": "^2.9.0", - "@ovh-ux/manager-pci": "^6.28.0", + "@ovh-ux/manager-pci": "^6.30.1", "@ovh-ux/manager-telecom-styles": "^4.7.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-at-internet-ui-router-plugin": "^3.5.0", "@ovh-ux/ng-ovh-actions-menu": "^5.1.1", "@ovh-ux/ng-ovh-api-wrappers": "^5.1.0", @@ -44,7 +44,7 @@ "@ovh-ux/ng-ovh-http": "^5.1.1", "@ovh-ux/ng-ovh-payment-method": "^9.14.0", "@ovh-ux/ng-ovh-proxy-request": "^2.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-responsive-popover": "^6.1.1", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-ovh-swimming-poll": "^5.1.1", @@ -52,13 +52,13 @@ "@ovh-ux/ng-ovh-utils": "^14.3.0", "@ovh-ux/ng-pagination-front": "^10.3.0", "@ovh-ux/ng-q-allsettled": "^2.1.1", - "@ovh-ux/ng-shell-tracking": "^0.5.0", + "@ovh-ux/ng-shell-tracking": "^0.5.4", "@ovh-ux/ng-tail-logs": "^2.1.1", "@ovh-ux/ng-translate-async-loader": "^2.2.1", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", "@ovh-ux/ng-ui-router-layout": "^4.3.0", - "@ovh-ux/request-tagger": "^0.1.1", - "@ovh-ux/shell": "^3.2.0", + "@ovh-ux/request-tagger": "^0.2.0", + "@ovh-ux/shell": "^3.4.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "angular": "^1.7.5", diff --git a/packages/manager/apps/restricted/CHANGELOG.md b/packages/manager/apps/restricted/CHANGELOG.md index de9ac3e3e374..c6cdc8665a8e 100644 --- a/packages/manager/apps/restricted/CHANGELOG.md +++ b/packages/manager/apps/restricted/CHANGELOG.md @@ -3,6 +3,14 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [0.3.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-restricted-app@0.3.2...@ovh-ux/manager-restricted-app@0.3.3) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-restricted-app + + + + + ## [0.3.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-restricted-app@0.3.1...@ovh-ux/manager-restricted-app@0.3.2) (2024-02-28) **Note:** Version bump only for package @ovh-ux/manager-restricted-app diff --git a/packages/manager/apps/restricted/package.json b/packages/manager/apps/restricted/package.json index f120e5eb4204..c17484bd45e6 100644 --- a/packages/manager/apps/restricted/package.json +++ b/packages/manager/apps/restricted/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-restricted-app", - "version": "0.3.2", + "version": "0.3.3", "private": true, "description": "OVHcloud Manager Restricted Access App.", "repository": { @@ -20,9 +20,9 @@ "start:watch": "lerna exec --stream --parallel --scope='@ovh-ux/manager-restricted-app' --include-dependencies -- npm run dev:watch --if-present" }, "dependencies": { - "@ovh-ux/manager-config": "^7.3.0", + "@ovh-ux/manager-config": "^7.3.1", "@ovh-ux/manager-vite-config": "^0.5.0", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@ovh-ux/ui-kit": "^6.7.7", "bootstrap": "4.6.0", "font-awesome": "^4.7.0", diff --git a/packages/manager/apps/sharepoint/CHANGELOG.md b/packages/manager/apps/sharepoint/CHANGELOG.md index 97db46aca036..c38bcfeb20e8 100644 --- a/packages/manager/apps/sharepoint/CHANGELOG.md +++ b/packages/manager/apps/sharepoint/CHANGELOG.md @@ -3,6 +3,38 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [0.9.7](https://github.com/ovh/manager/compare/@ovh-ux/manager-sharepoint-app@0.9.6...@ovh-ux/manager-sharepoint-app@0.9.7) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-sharepoint-app + + + + + +## [0.9.6](https://github.com/ovh/manager/compare/@ovh-ux/manager-sharepoint-app@0.9.5...@ovh-ux/manager-sharepoint-app@0.9.6) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-sharepoint-app + + + + + +## [0.9.5](https://github.com/ovh/manager/compare/@ovh-ux/manager-sharepoint-app@0.9.4...@ovh-ux/manager-sharepoint-app@0.9.5) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-sharepoint-app + + + + + +## [0.9.4](https://github.com/ovh/manager/compare/@ovh-ux/manager-sharepoint-app@0.9.3...@ovh-ux/manager-sharepoint-app@0.9.4) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-sharepoint-app + + + + + ## [0.9.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-sharepoint-app@0.9.2...@ovh-ux/manager-sharepoint-app@0.9.3) (2024-03-04) **Note:** Version bump only for package @ovh-ux/manager-sharepoint-app diff --git a/packages/manager/apps/sharepoint/package.json b/packages/manager/apps/sharepoint/package.json index fe073e373e0c..3b157c710058 100644 --- a/packages/manager/apps/sharepoint/package.json +++ b/packages/manager/apps/sharepoint/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-sharepoint-app", - "version": "0.9.3", + "version": "0.9.7", "private": true, "repository": { "type": "git", @@ -19,16 +19,16 @@ }, "dependencies": { "@ovh-ux/manager-advices": "^1.8.0", - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-ng-layout-helpers": "^2.9.0", "@ovh-ux/manager-sharepoint": "^2.11.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-ovh-api-wrappers": "^5.1.0", "@ovh-ux/ng-ovh-http": "^5.1.1", "@ovh-ux/ng-ovh-payment-method": "^9.14.0", "@ovh-ux/ng-ovh-proxy-request": "^2.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-ovh-swimming-poll": "^5.1.1", "@ovh-ux/ng-ovh-user-pref": "^2.1.1", @@ -36,7 +36,7 @@ "@ovh-ux/ng-ovh-web-universe-components": "^9.14.0", "@ovh-ux/ng-translate-async-loader": "^2.2.1", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "angular": "^1.7.5", diff --git a/packages/manager/apps/sign-up/CHANGELOG.md b/packages/manager/apps/sign-up/CHANGELOG.md index 41dbd4e21d65..eece013305a8 100644 --- a/packages/manager/apps/sign-up/CHANGELOG.md +++ b/packages/manager/apps/sign-up/CHANGELOG.md @@ -3,6 +3,49 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +# [3.5.0](https://github.com/ovh/manager/compare/@ovh-ux/sign-up-app@3.4.6...@ovh-ux/sign-up-app@3.5.0) (2024-03-18) + + +### Features + +* **signup:** added helper text for address field ([#10998](https://github.com/ovh/manager/issues/10998)) ([09cefc2](https://github.com/ovh/manager/commit/09cefc2d1d54bbbde6ff74ec42ddf2924b714288)) + + + + + +## [3.4.6](https://github.com/ovh/manager/compare/@ovh-ux/sign-up-app@3.4.5...@ovh-ux/sign-up-app@3.4.6) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/sign-up-app + + + + + +## [3.4.5](https://github.com/ovh/manager/compare/@ovh-ux/sign-up-app@3.4.4...@ovh-ux/sign-up-app@3.4.5) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/sign-up-app + + + + + +## [3.4.4](https://github.com/ovh/manager/compare/@ovh-ux/sign-up-app@3.4.3...@ovh-ux/sign-up-app@3.4.4) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/sign-up-app + + + + + +## [3.4.3](https://github.com/ovh/manager/compare/@ovh-ux/sign-up-app@3.4.2...@ovh-ux/sign-up-app@3.4.3) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/sign-up-app + + + + + ## [3.4.2](https://github.com/ovh/manager/compare/@ovh-ux/sign-up-app@3.4.1...@ovh-ux/sign-up-app@3.4.2) (2024-02-26) **Note:** Version bump only for package @ovh-ux/sign-up-app diff --git a/packages/manager/apps/sign-up/package.json b/packages/manager/apps/sign-up/package.json index 02eb396f0f86..538d85077a18 100644 --- a/packages/manager/apps/sign-up/package.json +++ b/packages/manager/apps/sign-up/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/sign-up-app", - "version": "3.4.2", + "version": "3.5.0", "private": true, "description": "Sign-up form application.", "repository": { @@ -21,18 +21,18 @@ }, "dependencies": { "@ovh-ux/manager-at-internet-configuration": "^1.5.0", - "@ovh-ux/manager-config": "^7.3.0", + "@ovh-ux/manager-config": "^7.3.1", "@ovh-ux/manager-cookie-policy": "^1.5.0", - "@ovh-ux/manager-core": "^12.16.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/manager-core": "^12.16.1", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-at-internet-ui-router-plugin": "^3.5.0", "@ovh-ux/ng-ovh-feature-flipping": "^1.1.1", "@ovh-ux/ng-ovh-http": "^5.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-translate-async-loader": "^2.2.1", - "@ovh-ux/request-tagger": "^0.1.1", - "@ovh-ux/sign-up": "^2.14.0", + "@ovh-ux/request-tagger": "^0.2.0", + "@ovh-ux/sign-up": "^2.15.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "angular": "^1.7.8", diff --git a/packages/manager/apps/sign-up/src/constants.js b/packages/manager/apps/sign-up/src/constants.js index e33176180d5b..977773c9017c 100644 --- a/packages/manager/apps/sign-up/src/constants.js +++ b/packages/manager/apps/sign-up/src/constants.js @@ -23,8 +23,10 @@ export const HOME_PAGE = { WS: 'https://www.ovh.com/us/es/', }; +export const INDIAN_SUBSIDIARY = 'IN'; + export const SUBSIDIARIES_LABEL_SUFFIX = { - IN: '_kyc_reminder', + [INDIAN_SUBSIDIARY]: '_kyc_reminder', DEFAULT: '', }; @@ -59,4 +61,5 @@ export default { SANITIZATION, FEATURES, SUBSIDIARIES_LABEL_SUFFIX, + INDIAN_SUBSIDIARY, }; diff --git a/packages/manager/apps/sign-up/src/details/routing.js b/packages/manager/apps/sign-up/src/details/routing.js index 3414939e938c..23079d46f228 100644 --- a/packages/manager/apps/sign-up/src/details/routing.js +++ b/packages/manager/apps/sign-up/src/details/routing.js @@ -1,3 +1,5 @@ +import { INDIAN_SUBSIDIARY } from '../constants'; + export const state = { name: 'sign-up.details', url: 'details', @@ -15,6 +17,8 @@ export const state = { name: `accountcreation::${field}::${value}`, }); }, + isIndianSubsidiary: /* @ngInject */ (subsidiary) => + subsidiary === INDIAN_SUBSIDIARY, }, atInternet: { rename: 'accountcreation-step2', diff --git a/packages/manager/apps/sign-up/src/form/component.js b/packages/manager/apps/sign-up/src/form/component.js index 42f96f9bccda..aa788cca9a35 100644 --- a/packages/manager/apps/sign-up/src/form/component.js +++ b/packages/manager/apps/sign-up/src/form/component.js @@ -14,5 +14,7 @@ export default { isSmsConsentAvailable: '<', needkyc: '<', goToKycDocumentUploadPage: '<', + user: '<', + subsidiary: '<', }, }; diff --git a/packages/manager/apps/sign-up/src/form/form.controller.js b/packages/manager/apps/sign-up/src/form/form.controller.js index d07c7c6e0ee8..4aaa1a26725c 100644 --- a/packages/manager/apps/sign-up/src/form/form.controller.js +++ b/packages/manager/apps/sign-up/src/form/form.controller.js @@ -3,19 +3,15 @@ import isFunction from 'lodash/isFunction'; import some from 'lodash/some'; import { SUBSIDIARIES_LABEL_SUFFIX } from '../constants'; -const OVH_SUBSIDIARY_ITEM_NAME = 'ovhSubsidiaryCreationForm'; - export default class SignUpFormAppCtrl { /* @ngInject */ - constructor($location, atInternet, coreConfig) { - this.$location = $location; + constructor(atInternet) { this.atInternet = atInternet; this.isActivityStepVisible = false; this.saveError = null; this.isValid = false; this.smsConsent = false; - this.user = coreConfig.getUser(); this.loading = { init: true, @@ -94,13 +90,9 @@ export default class SignUpFormAppCtrl { if (this.needkyc) this.goToKycDocumentUploadPage(); // call to finishSignUp binding if (isFunction(this.finishSignUp)) { - return this.finishSignUp(this.smsConsent) - .then(() => { - localStorage.removeItem(OVH_SUBSIDIARY_ITEM_NAME); - }) - .catch((error) => { - this.saveError = error; - }); + return this.finishSignUp(this.smsConsent).catch((error) => { + this.saveError = error; + }); } return null; @@ -112,13 +104,8 @@ export default class SignUpFormAppCtrl { this.saveError = null; this.loading.init = true; - const { ovhSubsidiary } = this.$location.search(); - if (ovhSubsidiary && ovhSubsidiary.match(/^[\w]{2}$/)) { - localStorage.setItem(OVH_SUBSIDIARY_ITEM_NAME, ovhSubsidiary); - } - const subsidiary = ovhSubsidiary || this.user.ovhSubsidiary; this.subsidiaryLabelSuffix = - SUBSIDIARIES_LABEL_SUFFIX[subsidiary] || + SUBSIDIARIES_LABEL_SUFFIX[this.subsidiary] || SUBSIDIARIES_LABEL_SUFFIX.DEFAULT; if (this.me.state === 'incomplete') { diff --git a/packages/manager/apps/sign-up/src/routing.js b/packages/manager/apps/sign-up/src/routing.js index ef67640a6d46..916caadbed18 100644 --- a/packages/manager/apps/sign-up/src/routing.js +++ b/packages/manager/apps/sign-up/src/routing.js @@ -57,6 +57,7 @@ export const state = { ssoAuthentication .getSsoAuthPendingPromise() .then(() => ssoAuthentication.user), + cancelStep: /* @ngInject */ ($location, ssoAuthentication) => () => { ssoAuthentication.logout($location.search().onsuccess); }, @@ -157,6 +158,9 @@ export const state = { customObject: { event: 'ACCOUNT_CREATION_VALIDATION' }, }); }, + + subsidiary: /* @ngInject */ ($location, coreConfig) => + $location.search().ovhSubsidiary || coreConfig.getUser().ovhSubsidiary, }, atInternet: { ignore: true, diff --git a/packages/manager/apps/sms/CHANGELOG.md b/packages/manager/apps/sms/CHANGELOG.md index ae2a37d18f95..5f773742c4bf 100644 --- a/packages/manager/apps/sms/CHANGELOG.md +++ b/packages/manager/apps/sms/CHANGELOG.md @@ -3,6 +3,38 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [8.0.26](https://github.com/ovh/manager/compare/@ovh-ux/manager-sms-app@8.0.25...@ovh-ux/manager-sms-app@8.0.26) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-sms-app + + + + + +## [8.0.25](https://github.com/ovh/manager/compare/@ovh-ux/manager-sms-app@8.0.24...@ovh-ux/manager-sms-app@8.0.25) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-sms-app + + + + + +## [8.0.24](https://github.com/ovh/manager/compare/@ovh-ux/manager-sms-app@8.0.23...@ovh-ux/manager-sms-app@8.0.24) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-sms-app + + + + + +## [8.0.23](https://github.com/ovh/manager/compare/@ovh-ux/manager-sms-app@8.0.22...@ovh-ux/manager-sms-app@8.0.23) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-sms-app + + + + + ## [8.0.22](https://github.com/ovh/manager/compare/@ovh-ux/manager-sms-app@8.0.21...@ovh-ux/manager-sms-app@8.0.22) (2024-02-26) **Note:** Version bump only for package @ovh-ux/manager-sms-app diff --git a/packages/manager/apps/sms/package.json b/packages/manager/apps/sms/package.json index 3ce92d1d3ab6..0c0f5785a05c 100644 --- a/packages/manager/apps/sms/package.json +++ b/packages/manager/apps/sms/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-sms-app", - "version": "8.0.22", + "version": "8.0.26", "private": true, "description": "SMS standalone application.", "repository": { @@ -20,19 +20,19 @@ }, "dependencies": { "@ovh-ux/manager-advices": "^1.8.0", - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-ng-layout-helpers": "^2.9.0", "@ovh-ux/manager-sms": "^8.16.0", "@ovh-ux/manager-telecom-styles": "^4.7.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-at-internet-ui-router-plugin": "^3.5.0", "@ovh-ux/ng-ovh-api-wrappers": "^5.1.0", "@ovh-ux/ng-ovh-checkbox-table": "^2.1.1", "@ovh-ux/ng-ovh-contracts": "^4.5.0", "@ovh-ux/ng-ovh-feature-flipping": "^1.1.1", "@ovh-ux/ng-ovh-http": "^5.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-ovh-swimming-poll": "^5.1.1", "@ovh-ux/ng-ovh-telecom-universe-components": "^7.24.0", @@ -40,7 +40,7 @@ "@ovh-ux/ng-pagination-front": "^10.3.0", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", "@ovh-ux/ng-ui-router-layout": "^4.3.0", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@uirouter/angularjs": "^1.0.23", "CSV-JS": "^1.2.0", "angular": "^1.7.5", diff --git a/packages/manager/apps/support/CHANGELOG.md b/packages/manager/apps/support/CHANGELOG.md index e193782bc676..5a72d8be4728 100644 --- a/packages/manager/apps/support/CHANGELOG.md +++ b/packages/manager/apps/support/CHANGELOG.md @@ -3,6 +3,38 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [2.10.6](https://github.com/ovh/manager/compare/@ovh-ux/manager-support-app@2.10.5...@ovh-ux/manager-support-app@2.10.6) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-support-app + + + + + +## [2.10.5](https://github.com/ovh/manager/compare/@ovh-ux/manager-support-app@2.10.4...@ovh-ux/manager-support-app@2.10.5) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-support-app + + + + + +## [2.10.4](https://github.com/ovh/manager/compare/@ovh-ux/manager-support-app@2.10.3...@ovh-ux/manager-support-app@2.10.4) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-support-app + + + + + +## [2.10.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-support-app@2.10.2...@ovh-ux/manager-support-app@2.10.3) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-support-app + + + + + ## [2.10.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-support-app@2.10.1...@ovh-ux/manager-support-app@2.10.2) (2024-02-26) **Note:** Version bump only for package @ovh-ux/manager-support-app diff --git a/packages/manager/apps/support/package.json b/packages/manager/apps/support/package.json index 8be6fc8b362b..74f50b7b2eab 100644 --- a/packages/manager/apps/support/package.json +++ b/packages/manager/apps/support/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-support-app", - "version": "2.10.2", + "version": "2.10.6", "private": true, "description": "Support standalone application.", "repository": { @@ -17,19 +17,19 @@ "start:watch": "lerna exec --stream --parallel --scope='@ovh-ux/manager-support-app' --include-dependencies -- npm run dev:watch --if-present" }, "dependencies": { - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", - "@ovh-ux/manager-support": "^1.22.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", + "@ovh-ux/manager-support": "^1.22.1", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-ovh-api-wrappers": "^5.1.0", "@ovh-ux/ng-ovh-http": "^5.1.1", "@ovh-ux/ng-ovh-proxy-request": "^2.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-ovh-swimming-poll": "^5.1.1", "@ovh-ux/ng-ovh-user-pref": "^2.1.1", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "angular": "^1.7.8", diff --git a/packages/manager/apps/telecom-dashboard/CHANGELOG.md b/packages/manager/apps/telecom-dashboard/CHANGELOG.md index 4d7961d0d6a3..6537dce139fb 100644 --- a/packages/manager/apps/telecom-dashboard/CHANGELOG.md +++ b/packages/manager/apps/telecom-dashboard/CHANGELOG.md @@ -3,6 +3,38 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [7.1.6](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom-dashboard-app@7.1.5...@ovh-ux/manager-telecom-dashboard-app@7.1.6) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-telecom-dashboard-app + + + + + +## [7.1.5](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom-dashboard-app@7.1.4...@ovh-ux/manager-telecom-dashboard-app@7.1.5) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-telecom-dashboard-app + + + + + +## [7.1.4](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom-dashboard-app@7.1.3...@ovh-ux/manager-telecom-dashboard-app@7.1.4) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-telecom-dashboard-app + + + + + +## [7.1.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom-dashboard-app@7.1.2...@ovh-ux/manager-telecom-dashboard-app@7.1.3) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-telecom-dashboard-app + + + + + ## [7.1.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom-dashboard-app@7.1.1...@ovh-ux/manager-telecom-dashboard-app@7.1.2) (2024-02-26) **Note:** Version bump only for package @ovh-ux/manager-telecom-dashboard-app diff --git a/packages/manager/apps/telecom-dashboard/package.json b/packages/manager/apps/telecom-dashboard/package.json index 6ed7d20f1bf4..58bafe1df334 100644 --- a/packages/manager/apps/telecom-dashboard/package.json +++ b/packages/manager/apps/telecom-dashboard/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-telecom-dashboard-app", - "version": "7.1.2", + "version": "7.1.6", "private": true, "description": "Telecom dashboard standalone application.", "repository": { @@ -20,21 +20,21 @@ }, "dependencies": { "@ovh-ux/manager-banner": "^1.3.1", - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-telecom-dashboard": "^6.5.0", "@ovh-ux/manager-telecom-styles": "^4.7.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-at-internet-ui-router-plugin": "^3.5.0", "@ovh-ux/ng-ovh-checkbox-table": "^2.1.1", "@ovh-ux/ng-ovh-http": "^5.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-ovh-swimming-poll": "^5.1.1", "@ovh-ux/ng-ovh-telecom-universe-components": "^7.24.0", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", "@ovh-ux/ng-ui-router-title": "^3.1.1", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "CSV-JS": "^1.2.0", diff --git a/packages/manager/apps/telecom-task/CHANGELOG.md b/packages/manager/apps/telecom-task/CHANGELOG.md index ec09cd30337d..f2924f7044cc 100644 --- a/packages/manager/apps/telecom-task/CHANGELOG.md +++ b/packages/manager/apps/telecom-task/CHANGELOG.md @@ -3,6 +3,14 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [7.1.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom-task-app@7.1.2...@ovh-ux/manager-telecom-task-app@7.1.3) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-telecom-task-app + + + + + ## [7.1.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom-task-app@7.1.1...@ovh-ux/manager-telecom-task-app@7.1.2) (2024-02-26) **Note:** Version bump only for package @ovh-ux/manager-telecom-task-app diff --git a/packages/manager/apps/telecom-task/package.json b/packages/manager/apps/telecom-task/package.json index aeebe474e652..479aaa8bcec0 100644 --- a/packages/manager/apps/telecom-task/package.json +++ b/packages/manager/apps/telecom-task/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-telecom-task-app", - "version": "7.1.2", + "version": "7.1.3", "private": true, "description": "Telecom task standalone application.", "repository": { @@ -19,19 +19,19 @@ "start:watch": "lerna exec --stream --parallel --scope='@ovh-ux/manager-telecom-task-app' --include-dependencies -- npm run dev:watch --if-present" }, "dependencies": { - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-telecom-styles": "^4.7.0", "@ovh-ux/manager-telecom-task": "^6.4.0", "@ovh-ux/ng-ovh-checkbox-table": "^2.1.1", "@ovh-ux/ng-ovh-http": "^5.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", "@ovh-ux/ng-ovh-swimming-poll": "^5.1.1", "@ovh-ux/ng-ovh-telecom-universe-components": "^7.24.0", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", "@ovh-ux/ng-ui-router-title": "^3.1.1", - "@ovh-ux/request-tagger": "^0.1.1", + "@ovh-ux/request-tagger": "^0.2.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "CSV-JS": "^1.2.0", diff --git a/packages/manager/apps/telecom/CHANGELOG.md b/packages/manager/apps/telecom/CHANGELOG.md index 5645241ddc50..7c207ad5b58d 100644 --- a/packages/manager/apps/telecom/CHANGELOG.md +++ b/packages/manager/apps/telecom/CHANGELOG.md @@ -3,6 +3,49 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +# [15.10.0](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom@15.9.6...@ovh-ux/manager-telecom@15.10.0) (2024-03-18) + + +### Features + +* **telecom:** rework on search buildings with street number ([8e40815](https://github.com/ovh/manager/commit/8e40815b799768fd7fd03b45cca37c2819b36cd4)) + + + + + +## [15.9.6](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom@15.9.5...@ovh-ux/manager-telecom@15.9.6) (2024-03-13) + +**Note:** Version bump only for package @ovh-ux/manager-telecom + + + + + +## [15.9.5](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom@15.9.4...@ovh-ux/manager-telecom@15.9.5) (2024-03-11) + +**Note:** Version bump only for package @ovh-ux/manager-telecom + + + + + +## [15.9.4](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom@15.9.3...@ovh-ux/manager-telecom@15.9.4) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-telecom + + + + + +## [15.9.3](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom@15.9.2...@ovh-ux/manager-telecom@15.9.3) (2024-03-07) + +**Note:** Version bump only for package @ovh-ux/manager-telecom + + + + + ## [15.9.2](https://github.com/ovh/manager/compare/@ovh-ux/manager-telecom@15.9.1...@ovh-ux/manager-telecom@15.9.2) (2024-03-04) **Note:** Version bump only for package @ovh-ux/manager-telecom diff --git a/packages/manager/apps/telecom/package.json b/packages/manager/apps/telecom/package.json index ab420d9d97eb..ee433c361d3b 100644 --- a/packages/manager/apps/telecom/package.json +++ b/packages/manager/apps/telecom/package.json @@ -1,6 +1,6 @@ { "name": "@ovh-ux/manager-telecom", - "version": "15.9.2", + "version": "15.10.0", "private": true, "description": "OVHcloud Telecom control panel.", "repository": { @@ -25,18 +25,18 @@ "@ovh-ux/manager-banner": "^1.3.1", "@ovh-ux/manager-beta-preference": "^1.0.0", "@ovh-ux/manager-carrier-sip": "^2.3.0", - "@ovh-ux/manager-config": "^7.3.0", - "@ovh-ux/manager-core": "^12.16.0", + "@ovh-ux/manager-config": "^7.3.1", + "@ovh-ux/manager-core": "^12.16.1", "@ovh-ux/manager-error-page": "^2.4.0", "@ovh-ux/manager-freefax": "^7.9.0", - "@ovh-ux/manager-models": "^1.14.10", + "@ovh-ux/manager-models": "^1.14.11", "@ovh-ux/manager-ng-layout-helpers": "^2.9.0", "@ovh-ux/manager-overthebox": "^6.12.0", "@ovh-ux/manager-sms": "^8.16.0", "@ovh-ux/manager-telecom-dashboard": "^6.5.0", "@ovh-ux/manager-telecom-styles": "^4.7.0", "@ovh-ux/manager-telecom-task": "^6.4.0", - "@ovh-ux/ng-at-internet": "^5.11.3", + "@ovh-ux/ng-at-internet": "^5.11.7", "@ovh-ux/ng-at-internet-ui-router-plugin": "^3.5.0", "@ovh-ux/ng-ovh-actions-menu": "^5.1.1", "@ovh-ux/ng-ovh-api-wrappers": "^5.1.0", @@ -51,7 +51,7 @@ "@ovh-ux/ng-ovh-mondial-relay": "^8.7.0", "@ovh-ux/ng-ovh-payment-method": "^9.14.0", "@ovh-ux/ng-ovh-proxy-request": "^2.1.1", - "@ovh-ux/ng-ovh-request-tagger": "^1.2.1", + "@ovh-ux/ng-ovh-request-tagger": "^1.2.2", "@ovh-ux/ng-ovh-responsive-popover": "^6.1.1", "@ovh-ux/ng-ovh-simple-country-list": "^2.1.1", "@ovh-ux/ng-ovh-sso-auth": "^4.8.1", @@ -62,14 +62,14 @@ "@ovh-ux/ng-ovh-user-pref": "^2.1.1", "@ovh-ux/ng-pagination-front": "^10.3.0", "@ovh-ux/ng-q-allsettled": "^2.1.1", - "@ovh-ux/ng-shell-tracking": "^0.5.0", + "@ovh-ux/ng-shell-tracking": "^0.5.4", "@ovh-ux/ng-tail-logs": "^2.1.1", "@ovh-ux/ng-translate-async-loader": "^2.2.1", "@ovh-ux/ng-ui-router-breadcrumb": "^1.3.1", "@ovh-ux/ng-ui-router-layout": "^4.3.0", "@ovh-ux/ng-ui-router-title": "^3.1.1", - "@ovh-ux/request-tagger": "^0.1.1", - "@ovh-ux/shell": "^3.2.0", + "@ovh-ux/request-tagger": "^0.2.0", + "@ovh-ux/shell": "^3.4.0", "@ovh-ux/ui-kit": "^6.7.7", "@uirouter/angularjs": "^1.0.23", "CSV-JS": "^1.0.0", diff --git a/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/index.js b/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/index.js index dfae5f0813e7..277c77b7ca8b 100644 --- a/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/index.js +++ b/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/index.js @@ -5,6 +5,7 @@ import uiRouter from '@uirouter/angularjs'; import angularTranslate from 'angular-translate'; import eligibilityAddress from './move-eligibility-address.component'; +import service from './move-eligibility-address.service'; const moduleName = 'ovhManagerTelecomPackMoveEligibilityAddress'; @@ -15,6 +16,7 @@ angular angularTranslate, 'oui', ]) - .component('packMoveEligibilityAddress', eligibilityAddress); + .component('packMoveEligibilityAddress', eligibilityAddress) + .service('moveEligibilityAddressService', service); export default moduleName; diff --git a/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/move-eligibility-address.controller.js b/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/move-eligibility-address.controller.js index 342be0bc0327..592bdb015e9f 100644 --- a/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/move-eligibility-address.controller.js +++ b/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/move-eligibility-address.controller.js @@ -8,6 +8,7 @@ export default class { constructor( $scope, $translate, + moveEligibilityAddressService, OvhApiConnectivityEligibility, OvhApiConnectivityEligibilitySearch, TucToast, @@ -15,6 +16,7 @@ export default class { ) { this.$scope = $scope; this.$translate = $translate; + this.moveEligibilityAddressService = moveEligibilityAddressService; this.OvhApiConnectivityEligibility = OvhApiConnectivityEligibility; this.OvhApiConnectivityEligibilitySearch = OvhApiConnectivityEligibilitySearch; this.TucToast = TucToast; @@ -123,16 +125,49 @@ export default class { /** * Check that the street name match with a street object - * @param {String} streetName Name of the street + * @param {String} street Name of the street * @returns {boolean} */ checkSelectedStreets(street) { + this.getStreetNumbers(); return ( street && this.streets.some(({ streetName }) => streetName === street.streetName) ); } + /** + * Get street numbers from the street + */ + getStreetNumbers() { + if (this.address.street && this.address.street.streetCode) { + this.searchStreetNumbers(this.address.street.streetCode); + } + } + + /** + * Search street numbers from the selected street + * @param {String} streetCode street code of the selected street + */ + searchStreetNumbers(streetCode) { + this.address.numberStreet = null; + this.loaders.streetNumbers = true; + this.loading = true; + this.moveEligibilityAddressService + .searchStreetNumber(streetCode) + .then((response) => { + if (response.status === 'pending') { + setTimeout(() => { + this.searchStreetNumbers(streetCode); + }, 5000); + } else { + this.streetNumbers = response.result; + delete this.loaders.streetNumbers; + this.loading = false; + } + }); + } + /** * Test address for copper eligibility * @returns Promise @@ -145,13 +180,13 @@ export default class { this.$scope, { streetCode: this.address.street.streetCode, - streetNumber: this.address.streetNumber, + streetNumber: this.address.streetNumber.number, }, ); } return this.OvhApiConnectivityEligibility.v6().testAddress(this.$scope, { streetCode: this.address.street.streetCode, - streetNumber: this.address.streetNumber, + streetNumber: this.address.streetNumber.number, }); } @@ -170,18 +205,63 @@ export default class { /** * Retrieve buildings for the address */ - searchBuildings() { - return this.OvhApiConnectivityEligibilitySearch.v6() - .searchBuildings(this.$scope, { - streetCode: this.address.street.streetCode, - streetNumber: this.address.streetNumber, - }) - .then((data) => { - return data.result.length > 0 ? data.result : null; - }) - .catch((error) => { - this.loading = false; - this.TucToast.error(error); + searchBuildings(copper) { + this.moveEligibilityAddressService + .searchBuildings( + this.address.streetNumber.hexacle, + this.address.street.streetCode, + this.address.streetNumber.number, + ) + .then((response) => { + if (response.status === 'pending') { + setTimeout(() => { + this.searchBuildings(copper); + }, 5000); + } else { + const buildings = response.result; + if (buildings?.length) { + if (buildings.length === 1) { + // Eligibility fiber + const [building] = buildings; + this.testFiberEligibility(building.reference).then(() => { + // send line offers + this.sendLineOffers( + copper, + this.fiber, + 'address', + ELIGIBILITY_LINE_STATUS.create, + building, + ); + this.displayResult = true; + this.displaySearchResult = true; + this.displaySearch = false; + this.loading = false; + }); + } else { + // Display buildings list + this.buildings = buildings; + + this.copper = copper; + this.displayListOfBuildings = true; + this.loading = false; + this.displaySearch = false; + this.displayResult = true; + this.displaySearchResult = true; + } + } else { + // send line offers + this.sendLineOffers( + copper, + this.fiber, + 'address', + ELIGIBILITY_LINE_STATUS.create, + ); + this.displayResult = true; + this.displaySearchResult = true; + this.displaySearch = false; + this.loading = false; + } + } }); } @@ -265,50 +345,7 @@ export default class { }); this.copperEligibilityByAddress().then((copper) => { - this.searchBuildings().then((buildings) => { - if (buildings) { - if (buildings.length === 1) { - // Eligibility fiber - const [building] = buildings; - this.testFiberEligibility(building.reference).then(() => { - // send line offers - this.sendLineOffers( - copper, - this.fiber, - 'address', - ELIGIBILITY_LINE_STATUS.create, - building, - ); - this.displayResult = true; - this.displaySearchResult = true; - this.displaySearch = false; - this.loading = false; - }); - } else { - // Display buildings list - this.buildings = buildings; - - this.copper = copper; - this.displayListOfBuildings = true; - this.loading = false; - this.displaySearch = false; - this.displayResult = true; - this.displaySearchResult = true; - } - } else { - // send line offers - this.sendLineOffers( - copper, - this.fiber, - 'address', - ELIGIBILITY_LINE_STATUS.create, - ); - this.displayResult = true; - this.displaySearchResult = true; - this.displaySearch = false; - this.loading = false; - } - }); + this.searchBuildings(copper); }); } diff --git a/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/move-eligibility-address.html b/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/move-eligibility-address.html index 12e902166e4f..f56e562d6f24 100644 --- a/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/move-eligibility-address.html +++ b/packages/manager/apps/telecom/src/app/telecom/pack/move/eligibility/address/move-eligibility-address.html @@ -54,25 +54,6 @@ >
-
- - -
+
+ + +