From 7ca3465c677e3c65e8621a646a8356947b329478 Mon Sep 17 00:00:00 2001 From: Mohamed-Hacene Date: Tue, 28 May 2024 14:53:04 +0200 Subject: [PATCH 01/13] feat: update cookie lang and front server side translation --- frontend/src/lib/components/SideBar/SideBarFooter.svelte | 2 +- frontend/src/routes/(app)/+layout.server.ts | 2 +- frontend/src/routes/ParaglideJsProvider.svelte | 7 ++++--- 3 files changed, 6 insertions(+), 5 deletions(-) diff --git a/frontend/src/lib/components/SideBar/SideBarFooter.svelte b/frontend/src/lib/components/SideBar/SideBarFooter.svelte index 9a2ffc4fa4..58020d65d3 100644 --- a/frontend/src/lib/components/SideBar/SideBarFooter.svelte +++ b/frontend/src/lib/components/SideBar/SideBarFooter.svelte @@ -39,7 +39,7 @@ value = event?.target?.value; setLanguageTag(value); // sessionStorage.setItem('lang', value); - setCookie('lang', value); + setCookie('ciso_lang', value); } const popupUser: PopupSettings = { diff --git a/frontend/src/routes/(app)/+layout.server.ts b/frontend/src/routes/(app)/+layout.server.ts index 1b8832b7e1..1c90561b78 100644 --- a/frontend/src/routes/(app)/+layout.server.ts +++ b/frontend/src/routes/(app)/+layout.server.ts @@ -8,6 +8,6 @@ export const load = loadFlash(async ({ locals, url, cookies }) => { if (!locals.user && !url.pathname.includes('/login')) { redirect(302, `/login?next=${url.pathname}`); } - setLanguageTag(cookies.get('lang') || sourceLanguageTag); + setLanguageTag(cookies.get('ciso_lang') || sourceLanguageTag); return { user: locals.user }; }) satisfies LayoutServerLoad; diff --git a/frontend/src/routes/ParaglideJsProvider.svelte b/frontend/src/routes/ParaglideJsProvider.svelte index 471b8f58ca..777a8ae3a9 100644 --- a/frontend/src/routes/ParaglideJsProvider.svelte +++ b/frontend/src/routes/ParaglideJsProvider.svelte @@ -7,18 +7,19 @@ } from '$paraglide/runtime'; import { onDestroy, onMount } from 'svelte'; import { browser } from '$app/environment'; - import { getCookie, deleteCookie } from '$lib/utils/cookies'; + import { getCookie, deleteCookie, setCookie } from '$lib/utils/cookies'; onMount(() => { // const valueFromSession = sessionStorage.getItem('lang') || sourceLanguageTag; - const valueFromCookies = getCookie('lang') || sourceLanguageTag; + const valueFromCookies = getCookie('ciso_lang') || sourceLanguageTag; // @ts-ignore + setCookie('ciso_lang', valueFromCookies); setLanguageTag(valueFromCookies); }); onDestroy(() => { if (browser) { - deleteCookie('lang'); + deleteCookie('ciso_lang'); // sessionStorage.removeItem('lang'); } }); From f5458d31c5bda9cae955c838e460ca52526704d6 Mon Sep 17 00:00:00 2001 From: Mohamed-Hacene Date: Tue, 28 May 2024 14:53:59 +0200 Subject: [PATCH 02/13] locale: add backend core fr locales --- backend/core/locale/fr/LC_MESSAGES/django.po | 1151 ++++++++++++++++++ 1 file changed, 1151 insertions(+) create mode 100644 backend/core/locale/fr/LC_MESSAGES/django.po diff --git a/backend/core/locale/fr/LC_MESSAGES/django.po b/backend/core/locale/fr/LC_MESSAGES/django.po new file mode 100644 index 0000000000..c783272af1 --- /dev/null +++ b/backend/core/locale/fr/LC_MESSAGES/django.po @@ -0,0 +1,1151 @@ +# SOME DESCRIPTIVE TITLE. +# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER +# This file is distributed under the same license as the PACKAGE package. +# FIRST AUTHOR , YEAR. +# +#, fuzzy +msgid "" +msgstr "" +"Project-Id-Version: PACKAGE VERSION\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2024-05-23 15:19+0200\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"Language: \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n > 1);\n" +#: admin_config.py:6 +msgid "Editor" +msgstr "" + +#: admin_config.py:7 +msgid "Menu" +msgstr "" + +#: base_models.py:10 filters.py:324 +msgid "Created at" +msgstr "" + +#: base_models.py:11 +msgid "Updated at" +msgstr "" + +#: base_models.py:12 +msgid "published" +msgstr "" + +#: base_models.py:110 models.py:52 templates/core/action_plan_pdf.html:35 +#: templates/snippets/mp_data.html:58 templates/snippets/ri_list_nested.html:16 +msgid "Name" +msgstr "" + +#: base_models.py:111 models.py:54 templates/core/action_plan_pdf.html:36 +#: templates/snippets/mp_data.html:59 templates/snippets/ra_data.html:43 +msgid "Description" +msgstr "" + +#: filters.py:28 filters.py:30 +msgid "Order by" +msgstr "" + +#: filters.py:121 +msgid "Search applied control..." +msgstr "" + +#: filters.py:137 filters.py:166 filters.py:194 filters.py:219 filters.py:251 +#: filters.py:347 filters.py:370 filters.py:398 filters.py:425 filters.py:452 +#: filters.py:479 +msgid "name" +msgstr "" + +#: filters.py:138 filters.py:167 filters.py:195 filters.py:220 filters.py:252 +#: filters.py:348 filters.py:371 filters.py:399 filters.py:426 filters.py:453 +#: filters.py:480 +msgid "Name (descending)" +msgstr "" + +#: filters.py:139 filters.py:196 templates/core/action_plan_pdf.html:14 +#: templates/snippets/mp_data.html:5 +msgid "Domain" +msgstr "" + +#: filters.py:140 filters.py:197 +msgid "Domain (descending)" +msgstr "" + +#: filters.py:141 +msgid "reference control" +msgstr "" + +#: filters.py:142 +msgid "Reference control (descending)" +msgstr "" + +#: filters.py:156 +msgid "Search domain..." +msgstr "" + +#: filters.py:168 filters.py:372 filters.py:400 filters.py:427 filters.py:454 +#: filters.py:481 +msgid "description" +msgstr "" + +#: filters.py:169 filters.py:373 filters.py:401 filters.py:428 filters.py:455 +#: filters.py:482 +msgid "Description (descending)" +msgstr "" + +#: filters.py:183 +msgid "Search project..." +msgstr "" + +#: filters.py:212 +msgid "Search threat..." +msgstr "" + +#: filters.py:240 +msgid "Search function..." +msgstr "" + +#: filters.py:253 +msgid "provider" +msgstr "" + +#: filters.py:254 +msgid "Provider (descending)" +msgstr "" + +#: filters.py:276 +msgid "Yes" +msgstr "" + +#: filters.py:277 +msgid "No" +msgstr "" + +#: filters.py:305 +msgid "Search user..." +msgstr "" + +#: filters.py:318 +msgid "Email" +msgstr "" + +#: filters.py:319 +msgid "Email (descending)" +msgstr "" + +#: filters.py:320 +msgid "First name" +msgstr "" + +#: filters.py:321 +msgid "First name (descending)" +msgstr "" + +#: filters.py:322 +msgid "Last name" +msgstr "" + +#: filters.py:323 +msgid "Last name (descending)" +msgstr "" + +#: filters.py:325 +msgid "Created at (descending)" +msgstr "" + +#: filters.py:339 +msgid "Search user group..." +msgstr "" + +#: filters.py:358 +msgid "Search compliance assessment..." +msgstr "" + +#: filters.py:388 +msgid "Search requirement assessment..." +msgstr "" + +#: filters.py:415 +msgid "Search requirement..." +msgstr "" + +#: filters.py:442 +msgid "Search evidence..." +msgstr "" + +#: filters.py:469 +msgid "Search framework..." +msgstr "" + +#: models.py:39 models.py:93 +msgid "URN" +msgstr "" + +#: models.py:42 +msgid "Reference ID" +msgstr "" + +#: models.py:45 +msgid "Locale" +msgstr "" + +#: models.py:47 +msgid "Default locale" +msgstr "" + +#: models.py:49 models.py:400 +msgid "Provider" +msgstr "" + +#: models.py:55 +msgid "Annotation" +msgstr "" + +#: models.py:95 +msgid "Copyright" +msgstr "" + +#: models.py:97 models.py:867 +msgid "Version" +msgstr "" + +#: models.py:102 +msgid "Packager of the library" +msgstr "" + +#: models.py:103 +msgid "Packager" +msgstr "" + +#: models.py:218 +msgid "Dependencies" +msgstr "" + +#: models.py:299 templates/snippets/ri_list_nested.html:19 +msgid "Threat" +msgstr "" + +#: models.py:300 models.py:524 models.py:1223 +msgid "Threats" +msgstr "" + +#: models.py:320 models.py:838 +msgid "Policy" +msgstr "" + +#: models.py:321 +msgid "Process" +msgstr "" + +#: models.py:322 +msgid "Technical" +msgstr "" + +#: models.py:323 +msgid "Physical" +msgstr "" + +#: models.py:339 models.py:727 templates/core/action_plan_pdf.html:37 +msgid "Category" +msgstr "" + +#: models.py:343 models.py:550 +msgid "Typical evidence" +msgstr "" + +#: models.py:349 templates/snippets/mp_data.html:61 +msgid "Reference control" +msgstr "" + +#: models.py:350 models.py:530 +msgid "Reference controls" +msgstr "" + +#: models.py:385 +msgid "JSON definition" +msgstr "" + +#: models.py:387 +msgid "" +"JSON definition of the risk matrix. See the documentation for more " +"information." +msgstr "" + +#: models.py:393 +msgid "enabled" +msgstr "" + +#: models.py:396 +msgid "" +"If the risk matrix is set as disabled, it will not be available for " +"selection for new risk assessments." +msgstr "" + +#: models.py:458 models.py:1400 +msgid "Minimum score" +msgstr "" + +#: models.py:459 models.py:1401 +msgid "Maximum score" +msgstr "" + +#: models.py:461 models.py:1403 +msgid "Score definition" +msgstr "" + +#: models.py:464 +msgid "Implementation groups definition" +msgstr "" + +#: models.py:475 models.py:538 models.py:1387 +#: templates/core/action_plan_pdf.html:20 +msgid "Framework" +msgstr "" + +#: models.py:476 +msgid "Frameworks" +msgstr "" + +#: models.py:542 +msgid "Parent URN" +msgstr "" + +#: models.py:544 +msgid "Order ID" +msgstr "" + +#: models.py:546 +msgid "Implementation groups" +msgstr "" + +#: models.py:548 +msgid "Assessable" +msgstr "" + +#: models.py:554 +msgid "RequirementNode" +msgstr "" + +#: models.py:555 +msgid "RequirementNodes" +msgstr "" + +#: models.py:563 +msgid "Undefined" +msgstr "" + +#: models.py:564 +msgid "Design" +msgstr "" + +#: models.py:565 +msgid "Development" +msgstr "" + +#: models.py:566 +msgid "Production" +msgstr "" + +#: models.py:567 +msgid "EndOfLife" +msgstr "" + +#: models.py:568 +msgid "Dropped" +msgstr "" + +#: models.py:571 +msgid "Internal reference" +msgstr "" + +#: models.py:577 models.py:734 models.py:874 models.py:1654 +#: templates/snippets/mp_data.html:65 templates/snippets/ri_list_nested.html:31 +msgid "Status" +msgstr "" + +#: models.py:582 models.py:860 models.py:1295 +#: templates/core/action_plan_pdf.html:16 templates/snippets/mp_data.html:7 +msgid "Project" +msgstr "" + +#: models.py:583 +msgid "Projects" +msgstr "" + +#: models.py:616 +msgid "Primary" +msgstr "" + +#: models.py:617 +msgid "Support" +msgstr "" + +#: models.py:620 +msgid "business value" +msgstr "" + +#: models.py:623 +msgid "type" +msgstr "" + +#: models.py:626 +msgid "parent assets" +msgstr "" + +#: models.py:632 models.py:1210 +msgid "Assets" +msgstr "" + +#: models.py:633 +msgid "Asset" +msgstr "" + +#: models.py:663 +msgid "Attachment for evidence (eg. screenshot, log file, etc.)" +msgstr "" + +#: models.py:664 +msgid "Attachment" +msgstr "" + +#: models.py:670 +msgid "Link to the evidence (eg. Jira ticket, etc.)" +msgstr "" + +#: models.py:671 models.py:753 templates/snippets/mp_data.html:64 +msgid "Link" +msgstr "" + +#: models.py:677 +msgid "Evidence" +msgstr "" + +#: models.py:678 models.py:719 models.py:1668 +msgid "Evidences" +msgstr "" + +#: models.py:694 models.py:853 +msgid "Planned" +msgstr "" + +#: models.py:695 +msgid "Active" +msgstr "" + +#: models.py:696 +msgid "Inactive" +msgstr "" + +#: models.py:701 +msgid "Small" +msgstr "" + +#: models.py:702 models.py:1187 tests/test_helpers.py:77 +#: tests/test_helpers.py:142 +msgid "Medium" +msgstr "" + +#: models.py:703 +msgid "Large" +msgstr "" + +#: models.py:704 +msgid "Extra Large" +msgstr "" + +#: models.py:714 +msgid "Reference Control" +msgstr "" + +#: models.py:739 +msgid "Estimated Time of Arrival" +msgstr "" + +#: models.py:740 models.py:894 templates/core/action_plan_pdf.html:38 +#: templates/snippets/mp_data.html:62 +msgid "ETA" +msgstr "" + +#: models.py:745 +msgid "Date after which the applied control is no longer valid" +msgstr "" + +#: models.py:746 models.py:1737 templates/core/action_plan_pdf.html:39 +msgid "Expiry date" +msgstr "" + +#: models.py:752 +msgid "External url for action follow-up (eg. Jira ticket)" +msgstr "" + +#: models.py:760 +msgid "Relative effort of the measure (using T-Shirt sizing)" +msgstr "" + +#: models.py:761 templates/core/action_plan_pdf.html:40 +#: templates/snippets/mp_data.html:63 +msgid "Effort" +msgstr "" + +#: models.py:767 +msgid "Applied control" +msgstr "" + +#: models.py:768 models.py:1217 models.py:1684 +msgid "Applied controls" +msgstr "" + +#: models.py:839 +msgid "Policies" +msgstr "" + +#: models.py:854 models.py:1644 +msgid "In progress" +msgstr "" + +#: models.py:855 +msgid "In review" +msgstr "" + +#: models.py:856 +msgid "Done" +msgstr "" + +#: models.py:857 +msgid "Deprecated" +msgstr "" + +#: models.py:866 +msgid "Version of the compliance assessment (eg. 1.0, 2.0, etc.)" +msgstr "" + +#: models.py:881 +msgid "Authors" +msgstr "" + +#: models.py:887 +msgid "Reviewers" +msgstr "" + +#: models.py:893 +msgid "Estimated time of arrival" +msgstr "" + +#: models.py:899 models.py:900 +msgid "Due date" +msgstr "" + +#: models.py:913 +msgid "WARNING! After choosing it, you will not be able to change it" +msgstr "" + +#: models.py:914 +msgid "Risk matrix" +msgstr "" + +#: models.py:918 templates/snippets/ra_data.html:8 +msgid "Risk assessment" +msgstr "" + +#: models.py:919 +msgid "Risk assessments" +msgstr "" + +#: models.py:943 +msgid "{}: Risk assessment is still in progress" +msgstr "" + +#: models.py:953 +msgid "{}: No author assigned to this risk assessment" +msgstr "" + +#: models.py:964 +msgid "{}: RiskAssessment is empty. No risk scenario declared yet" +msgstr "" + +#: models.py:982 +msgid "{} current risk level has not been assessed" +msgstr "" + +#: models.py:993 +msgid "" +"{} residual risk level has not been assessed. If no additional measures are " +"applied, it should be at the same level as the current risk" +msgstr "" + +#: models.py:1003 +msgid "{} residual risk level is higher than the current one" +msgstr "" + +#: models.py:1013 +msgid "{} residual risk probability is higher than the current one" +msgstr "" + +#: models.py:1023 +msgid "{} residual risk impact is higher than the current one" +msgstr "" + +#: models.py:1042 +msgid "{}: residual risk level has been lowered without any specific measure" +msgstr "" + +#: models.py:1054 +msgid "{} risk accepted but no risk acceptance attached" +msgstr "" + +#: models.py:1075 +msgid "{} does not have an ETA" +msgstr "" + +#: models.py:1085 +msgid "{} ETA is in the past now. Consider updating its status or the date" +msgstr "" + +#: models.py:1096 +msgid "" +"{} does not have an estimated effort. This will help you for prioritization" +msgstr "" + +#: models.py:1107 +msgid "" +"{}: Applied control does not have an external link attached. This will help " +"you for follow-up" +msgstr "" + +#: models.py:1126 +msgid "{}: Acceptance has no expiry date" +msgstr "" + +#: models.py:1138 +msgid "{}: Acceptance has expired. Consider updating the status or the date" +msgstr "" + +#: models.py:1165 +msgid "Open" +msgstr "" + +#: models.py:1166 +msgid "Mitigate" +msgstr "" + +#: models.py:1167 +msgid "Accept" +msgstr "" + +#: models.py:1168 +msgid "Avoid" +msgstr "" + +#: models.py:1169 +msgid "Transfer" +msgstr "" + +#: models.py:1174 +msgid "--" +msgstr "" + +#: models.py:1176 +msgid "The strength of the knowledge supporting the assessment is undefined" +msgstr "" + +#: models.py:1180 tests/test_helpers.py:76 tests/test_helpers.py:141 +msgid "Low" +msgstr "" + +#: models.py:1182 +msgid "The strength of the knowledge supporting the assessment is low" +msgstr "" + +#: models.py:1189 +msgid "The strength of the knowledge supporting the assessment is medium" +msgstr "" + +#: models.py:1194 tests/test_helpers.py:78 tests/test_helpers.py:143 +msgid "High" +msgstr "" + +#: models.py:1196 +msgid "The strength of the knowledge supporting the assessment is high" +msgstr "" + +#: models.py:1205 templates/snippets/mp_data.html:9 +msgid "RiskAssessment" +msgstr "" + +#: models.py:1212 +msgid "Assets impacted by the risk scenario" +msgstr "" + +#: models.py:1230 +msgid "" +"The existing controls to manage this risk. Edit the risk scenario to add " +"extra applied controls." +msgstr "" + +#: models.py:1232 templates/snippets/mp_data.html:48 +#: templates/snippets/ri_list_nested.html:22 +msgid "Existing controls" +msgstr "" + +#: models.py:1238 +msgid "Current probability" +msgstr "" + +#: models.py:1241 +msgid "Current impact" +msgstr "" + +#: models.py:1245 +msgid "Current level" +msgstr "" + +#: models.py:1247 +msgid "" +"The risk level given the current measures. Automatically updated on Save, " +"based on the chosen risk matrix" +msgstr "" + +#: models.py:1253 +msgid "Residual probability" +msgstr "" + +#: models.py:1256 +msgid "Residual impact" +msgstr "" + +#: models.py:1260 +msgid "Residual level" +msgstr "" + +#: models.py:1262 +msgid "" +"The risk level when all the extra measures are done. Automatically updated " +"on Save, based on the chosen risk matrix" +msgstr "" + +#: models.py:1270 +msgid "Treatment status" +msgstr "" + +#: models.py:1275 +msgid "Strength of Knowledge" +msgstr "" + +#: models.py:1276 +msgid "The strength of the knowledge supporting the assessment" +msgstr "" + +#: models.py:1279 models.py:1749 +msgid "Justification" +msgstr "" + +#: models.py:1285 +msgid "Risk scenario" +msgstr "" + +#: models.py:1286 models.py:1714 +msgid "Risk scenarios" +msgstr "" + +#: models.py:1352 +msgid ": " +msgstr "" + +#: models.py:1381 models.py:1647 +msgid "Compliant" +msgstr "" + +#: models.py:1382 +msgid "Non compliant (minor)" +msgstr "" + +#: models.py:1383 +msgid "Non compliant (major)" +msgstr "" + +#: models.py:1384 models.py:1648 +msgid "Not applicable" +msgstr "" + +#: models.py:1394 +msgid "Result" +msgstr "" + +#: models.py:1397 +msgid "Selected implementation groups" +msgstr "" + +#: models.py:1407 models.py:1675 +msgid "Compliance assessment" +msgstr "" + +#: models.py:1408 +msgid "Compliance assessments" +msgstr "" + +#: models.py:1544 +msgid "{}: Compliance assessment is still in progress" +msgstr "" + +#: models.py:1556 +msgid "{}: No author assigned to this compliance assessment" +msgstr "" + +#: models.py:1581 +msgid "" +"{}: Requirement assessment status is compliant or partially compliant with " +"no applied control applied" +msgstr "" + +#: models.py:1602 +msgid "{}: Applied control has no reference control selected" +msgstr "" + +#: models.py:1624 +msgid "{}: Evidence has no file uploaded" +msgstr "" + +#: models.py:1643 +msgid "To do" +msgstr "" + +#: models.py:1645 +msgid "Non compliant" +msgstr "" + +#: models.py:1646 +msgid "Partially compliant" +msgstr "" + +#: models.py:1659 +msgid "Score" +msgstr "" + +#: models.py:1663 +msgid "Is scored" +msgstr "" + +#: models.py:1671 +msgid "Observation" +msgstr "" + +#: models.py:1679 +msgid "Requirement" +msgstr "" + +#: models.py:1689 +msgid "Selected" +msgstr "" + +#: models.py:1696 +msgid "Requirement assessment" +msgstr "" + +#: models.py:1697 +msgid "Requirement assessments" +msgstr "" + +#: models.py:1705 +msgid "Created" +msgstr "" + +#: models.py:1706 +msgid "Submitted" +msgstr "" + +#: models.py:1707 +msgid "Accepted" +msgstr "" + +#: models.py:1708 +msgid "Rejected" +msgstr "" + +#: models.py:1709 +msgid "Revoked" +msgstr "" + +#: models.py:1716 +msgid "" +"Select the risk scenarios to be accepted, attention they must be part of the " +"chosen domain" +msgstr "" + +#: models.py:1722 +msgid "Risk owner and approver identity" +msgstr "" + +#: models.py:1723 utils.py:48 utils.py:55 utils.py:58 +msgid "Approver" +msgstr "" + +#: models.py:1732 +msgid "State" +msgstr "" + +#: models.py:1735 +msgid "Specify when the risk acceptance will no longer apply" +msgstr "" + +#: models.py:1740 +msgid "Acceptance date" +msgstr "" + +#: models.py:1743 +msgid "Rejection date" +msgstr "" + +#: models.py:1746 +msgid "Revocation date" +msgstr "" + +#: models.py:1758 +msgid "Risk acceptance" +msgstr "" + +#: models.py:1759 +msgid "Risk acceptances" +msgstr "" + +#: templates/core/action_plan_pdf.html:18 +msgid "Audit" +msgstr "" + +#: templates/core/action_plan_pdf.html:22 +msgid "Associated applied controls" +msgstr "" + +#: templates/core/action_plan_pdf.html:23 +msgid "Separated by status and sorted by eta" +msgstr "" + +#: templates/core/action_plan_pdf.html:41 +msgid "Matching requirements" +msgstr "" + +#: templates/core/action_plan_pdf.html:58 +msgid "No entries found" +msgstr "" + +#: templates/registration/first_connexion_email.html:14 +msgid "Welcome to CISO Assistant!" +msgstr "" + +#: templates/registration/first_connexion_email.html:15 +#: templates/registration/password_reset_email.html:23 +msgid "Your all-in-one GRC Management Platform" +msgstr "" + +#: templates/registration/first_connexion_email.html:33 +msgid "" +"You have been granted access to CISO Assistant. To get started, use the link " +"below to define your password:" +msgstr "" + +#: templates/registration/first_connexion_email.html:38 +msgid "Set my password" +msgstr "" + +#: templates/registration/first_connexion_email.html:41 +#: templates/registration/password_reset_email.html:43 +msgid "An issue with the link? copy and paste the following in your browser" +msgstr "" + +#: templates/registration/first_connexion_email.html:49 +msgid "" +"This link can only be used once. In case of an issue, you can access your " +"instance" +msgstr "" + +#: templates/registration/first_connexion_email.html:49 +#: templates/registration/first_connexion_email.html:58 +#: templates/registration/password_reset_email.html:51 +msgid "here" +msgstr "" + +#: templates/registration/first_connexion_email.html:49 +msgid "and request a password reset" +msgstr "" + +#: templates/registration/first_connexion_email.html:54 +#: templates/registration/password_reset_email.html:55 +msgid "" +"If you, or your organization, did not make this request, you can simply " +"ignore this email" +msgstr "" + +#: templates/registration/first_connexion_email.html:58 +msgid "Learn more about CISO Assistant" +msgstr "" + +#: templates/registration/first_connexion_email.html:63 +#: templates/registration/password_reset_email.html:58 +msgid "Sincerely" +msgstr "" + +#: templates/registration/first_connexion_email.html:64 +#: templates/registration/password_reset_email.html:59 +msgid "CISO Assistant Team" +msgstr "" + +#: templates/registration/password_reset_email.html:32 +msgid "Hello" +msgstr "" + +#: templates/registration/password_reset_email.html:36 +msgid "" +"We have received a password reset request for this email. Click below to " +"proceed:" +msgstr "" + +#: templates/registration/password_reset_email.html:40 +msgid "Reset my password" +msgstr "" + +#: templates/registration/password_reset_email.html:50 +msgid "" +"This link can only be used once. In case of an issue, go to your instance" +msgstr "" + +#: templates/registration/password_reset_email.html:51 +msgid "and request a new password reset" +msgstr "" + +#: templates/snippets/mp_data.html:11 +msgid "Associated risk scenarios" +msgstr "" + +#: templates/snippets/mp_data.html:20 +msgid "" +"Risk risk_assessment seems to be empty. Measure Plan cannot be generated." +msgstr "" + +#: templates/snippets/mp_data.html:43 +msgid "No associated measure" +msgstr "" + +#: templates/snippets/mp_data.html:54 +msgid "Additional measures" +msgstr "" + +#: templates/snippets/mp_data.html:60 +msgid "Type" +msgstr "" + +#: templates/snippets/ra_data.html:13 +msgid "Risk matrix:" +msgstr "" + +#: templates/snippets/ra_data.html:18 +msgid "Authors:" +msgstr "" + +#: templates/snippets/ra_data.html:25 +msgid "Reviewers:" +msgstr "" + +#: templates/snippets/ra_data.html:32 +msgid "Status:" +msgstr "" + +#: templates/snippets/ra_data.html:35 +msgid "ETA:" +msgstr "" + +#: templates/snippets/ra_data.html:36 +msgid "Due date:" +msgstr "" + +#: templates/snippets/ra_data.html:37 +msgid "Created at:" +msgstr "" + +#: templates/snippets/ra_data.html:38 +msgid "Updated at:" +msgstr "" + +#: templates/snippets/ra_data.html:51 +msgid "Associated Risk scenarios" +msgstr "" + +#: templates/snippets/ra_data.html:56 +msgid "Risk matrix view" +msgstr "" + +#: templates/snippets/ra_data.html:59 +msgid "Current" +msgstr "" + +#: templates/snippets/ra_data.html:67 +msgid "Residual" +msgstr "" + +#: templates/snippets/ri_list_nested.html:13 +msgid "ID" +msgstr "" + +#: templates/snippets/ri_list_nested.html:25 +msgid "Current risk level" +msgstr "" + +#: templates/snippets/ri_list_nested.html:28 +msgid "Residual risk level" +msgstr "" + +#: templates/snippets/ri_list_nested.html:34 +msgid "Suggested measures" +msgstr "" + +#: templates/snippets/ri_list_nested.html:115 +msgid "No scenario found." +msgstr "" + +#: templates/snippets/risk_legend.html:4 +msgid "Risk levels" +msgstr "" + +#: templates/snippets/risk_matrix.html:40 +#: templates/snippets/risk_matrix.html:86 +msgid "Impact" +msgstr "" + +#: templates/snippets/risk_matrix.html:46 +msgid "Probability" +msgstr "" + +#: tests/test_helpers.py:75 tests/test_helpers.py:140 +msgid "Very Low" +msgstr "" + +#: tests/test_helpers.py:79 tests/test_helpers.py:144 +msgid "Very High" +msgstr "" + +#: utils.py:45 utils.py:53 +msgid "Administrator" +msgstr "" + +#: utils.py:46 utils.py:56 +msgid "Domain manager" +msgstr "" + +#: utils.py:47 utils.py:57 +msgid "Analyst" +msgstr "" + +#: utils.py:49 utils.py:54 utils.py:59 +msgid "Reader" +msgstr "" + +#: utils.py:68 +msgid "French" +msgstr "" + +#: utils.py:69 +msgid "English" +msgstr "" From 168a80f05f540e910766e3d7de6e586ed9f52353 Mon Sep 17 00:00:00 2001 From: Mohamed-Hacene Date: Tue, 28 May 2024 15:54:55 +0200 Subject: [PATCH 03/13] feat: improve translations and x-rays --- backend/core/models.py | 21 + frontend/messages/en.json | 24 +- frontend/messages/fr.json | 2 +- .../components/Breadcrumbs/Breadcrumbs.svelte | 12 +- .../lib/components/Chart/DonutChart.svelte | 2 +- .../lib/components/Chart/RadarChart.svelte | 2 +- .../Forms/AutocompleteSelect.svelte | 4 +- .../src/lib/components/Forms/Select.svelte | 4 +- .../Modals/MissingConstraintsModal.svelte | 2 +- .../components/ModelTable/ModelTable.svelte | 12 +- .../ModelTable/UserGroupNameDisplay.svelte | 2 +- .../components/SideBar/SideBarCategory.svelte | 2 +- .../lib/components/SideBar/SideBarItem.svelte | 2 +- frontend/src/lib/utils/locales.ts | 637 +++++++++--------- frontend/src/routes/(app)/+layout.svelte | 4 +- .../(app)/[model=urlmodel]/+page.server.ts | 8 +- .../(app)/[model=urlmodel]/+page.svelte | 6 +- .../[id=uuid]/+page.server.ts | 12 +- .../[model=urlmodel]/[id=uuid]/+page.svelte | 14 +- .../[id=uuid]/edit/+page.server.ts | 2 +- .../src/routes/(app)/analytics/+page.svelte | 2 +- .../(app)/analytics/composer/+page.svelte | 2 +- .../[id=uuid]/+page.svelte | 6 +- .../[id=uuid]/TreeViewItemLead.svelte | 2 +- .../(app)/evidences/[id=uuid]/+page.svelte | 2 +- .../(app)/frameworks/[id=uuid]/+page.svelte | 2 +- .../routes/(app)/libraries/+page.server.ts | 2 +- .../src/routes/(app)/my-profile/+page.svelte | 2 +- .../[id=uuid]/+page.server.ts | 2 +- .../[id=uuid]/+page.svelte | 4 +- .../[id=uuid]/+page.server.ts | 4 +- .../risk-assessments/[id=uuid]/+page.svelte | 2 +- .../risk-scenarios/[id=uuid]/+page.svelte | 32 +- .../[id=uuid]/edit/+page.svelte | 2 +- .../[id=uuid]/edit/RiskLevel.svelte | 4 +- .../(app)/scoring-assistant/selector.svelte | 4 +- .../users/[id=uuid]/edit/+page.server.ts | 2 +- frontend/src/routes/(app)/x-rays/+page.svelte | 13 +- frontend/tests/functional/nav.test.ts | 2 +- 39 files changed, 462 insertions(+), 403 deletions(-) diff --git a/backend/core/models.py b/backend/core/models.py index b910eafb02..cd0c0d8f6f 100644 --- a/backend/core/models.py +++ b/backend/core/models.py @@ -943,6 +943,7 @@ def quality_check(self) -> dict: "msg": _("{}: Risk assessment is still in progress").format( str(self) ), + "msgid": "riskAssessmentInProgress", "obj_type": "risk_assessment", "object": _object, } @@ -953,6 +954,7 @@ def quality_check(self) -> dict: "msg": _("{}: No author assigned to this risk assessment").format( str(self) ), + "msgid": "riskAssessmentNoAuthor", "obj_type": "risk_assessment", "object": _object, } @@ -963,6 +965,7 @@ def quality_check(self) -> dict: "msg": _( "{}: RiskAssessment is empty. No risk scenario declared yet" ).format(self), + "msgid": "riskAssessmentEmpty", "obj_type": "risk_assessment", "object": _object, } @@ -982,6 +985,7 @@ def quality_check(self) -> dict: "msg": _("{} current risk level has not been assessed").format( ri["name"] ), + "msgid": "riskScenarioNoCurrentLevel", "obj_type": "riskscenario", "object": ri, } @@ -992,6 +996,7 @@ def quality_check(self) -> dict: "msg": _( "{} residual risk level has not been assessed. If no additional measures are applied, it should be at the same level as the current risk" ).format(ri["name"]), + "msgid": "riskScenarioNoResidualLevel", "obj_type": "riskscenario", "object": ri, } @@ -1002,6 +1007,7 @@ def quality_check(self) -> dict: "msg": _( "{} residual risk level is higher than the current one" ).format(ri["name"]), + "msgid": "riskScenarioResidualHigherThanCurrent", "obj_type": "riskscenario", "object": ri, } @@ -1012,6 +1018,7 @@ def quality_check(self) -> dict: "msg": _( "{} residual risk probability is higher than the current one" ).format(ri["name"]), + "msgid": "riskScenarioResidualProbaHigherThanCurrent", "obj_type": "riskscenario", "object": ri, } @@ -1022,6 +1029,7 @@ def quality_check(self) -> dict: "msg": _( "{} residual risk impact is higher than the current one" ).format(ri["name"]), + "msgid": "riskScenarioResidualImpactHigherThanCurrent", "obj_type": "riskscenario", "object": ri, } @@ -1041,6 +1049,7 @@ def quality_check(self) -> dict: "msg": _( "{}: residual risk level has been lowered without any specific measure" ).format(ri["name"]), + "msgid": "riskScenarioResidualLoweredWithoutMeasures", "obj_type": "riskscenario", "object": ri, } @@ -1053,6 +1062,7 @@ def quality_check(self) -> dict: "msg": _( "{} risk accepted but no risk acceptance attached" ).format(ri), + "msgid": "riskScenarioAcceptedNoAcceptance", "obj_type": "riskscenario", "object": ri, } @@ -1073,6 +1083,7 @@ def quality_check(self) -> dict: warnings_lst.append( { "msg": _("{} does not have an ETA").format(mtg["name"]), + "msgid": "appliedControlNoETA", "obj_type": "appliedcontrol", "object": {"name": mtg["name"], "id": mtg["id"]}, } @@ -1084,6 +1095,7 @@ def quality_check(self) -> dict: "msg": _( "{} ETA is in the past now. Consider updating its status or the date" ).format(mtg["name"]), + "msgid": "appliedControlETAInPast", "obj_type": "appliedcontrol", "object": {"name": mtg["name"], "id": mtg["id"]}, } @@ -1095,6 +1107,7 @@ def quality_check(self) -> dict: "msg": _( "{} does not have an estimated effort. This will help you for prioritization" ).format(mtg["name"]), + "msgid": "appliedControlNoEffort", "obj_type": "appliedcontrol", "object": {"name": mtg["name"], "id": mtg["id"]}, } @@ -1106,6 +1119,7 @@ def quality_check(self) -> dict: "msg": _( "{}: Applied control does not have an external link attached. This will help you for follow-up" ).format(mtg["name"]), + "msgid": "appliedControlNoLink", "obj_type": "appliedcontrol", "object": {"name": mtg["name"], "id": mtg["id"]}, } @@ -1126,6 +1140,7 @@ def quality_check(self) -> dict: "msg": _("{}: Acceptance has no expiry date").format( ra["name"] ), + "msgid": "riskAcceptanceNoExpiryDate", "obj_type": "appliedcontrol", "object": ra, } @@ -1137,6 +1152,7 @@ def quality_check(self) -> dict: "msg": _( "{}: Acceptance has expired. Consider updating the status or the date" ).format(ra["name"]), + "msgid": "riskAcceptanceExpired", "obj_type": "riskacceptance", "object": ra, } @@ -1544,6 +1560,7 @@ def quality_check(self) -> dict: "msg": _("{}: Compliance assessment is still in progress").format( str(self) ), + "msgid": "complianceAssessmentInProgress", "obj_type": "complianceassessment", "object": _object, } @@ -1555,6 +1572,7 @@ def quality_check(self) -> dict: "msg": _( "{}: No author assigned to this compliance assessment" ).format(str(self)), + "msgid": "complianceAssessmentNoAuthor", "obj_type": "complianceassessment", "object": _object, } @@ -1580,6 +1598,7 @@ def quality_check(self) -> dict: "msg": _( "{}: Requirement assessment status is compliant or partially compliant with no applied control applied" ).format(requirement_assessment["repr"]), + "msgid": "requirementAssessmentNoAppliedControl", "obj_type": "requirementassessment", "object": requirement_assessment, } @@ -1601,6 +1620,7 @@ def quality_check(self) -> dict: "msg": _( "{}: Applied control has no reference control selected" ).format(applied_control["name"]), + "msgid": "appliedControlNoReferenceControl", "obj_type": "appliedcontrol", "object": applied_control, } @@ -1624,6 +1644,7 @@ def quality_check(self) -> dict: "msg": _("{}: Evidence has no file uploaded").format( evidence["name"] ), + "msgid": "evidenceNoFile", "obj_type": "evidence", "object": evidence, } diff --git a/frontend/messages/en.json b/frontend/messages/en.json index c60d2e3d5f..9dde93c478 100644 --- a/frontend/messages/en.json +++ b/frontend/messages/en.json @@ -530,5 +530,27 @@ "incoming": "Incoming", "outdated": "Outdated", "exportBackupDescription": "This will serialize and create a backup of the database, including users and RBAC. Evidences and other files are not included in the backup.", - "importBackupDescription": "This will deserialize and restore the database from a backup. This will overwrite all existing data, including users and RBAC and cannot be undone." + "importBackupDescription": "This will deserialize and restore the database from a backup. This will overwrite all existing data, including users and RBAC and cannot be undone.", + "riskAssessmentInProgress": "Risk assessment is still in progress", + "riskAssessmentNoAuthor": "No author assigned to this risk assessment", + "riskAssessmentEmpty": "RiskAssessment is empty. No risk scenario declared yet", + "riskScenarioNoCurrentLevel": "Current risk level has not been assessed", + "riskScenarioNoResidualLevel": "Residual risk level has not been assessed. If no additional measures are applied, it should be at the same level as the current risk", + "riskScenarioResidualHigherThanCurrent": "Residual risk level is higher than the current one", + "riskScenarioResidualProbaHigherThanCurrent": "Residual risk probability is higher than the current one", + "riskScenarioResidualImpactHigherThanCurrent": "Residual risk impact is higher than the current one", + "riskScenarioResidualLoweredWithoutMeasures": "Residual risk level has been lowered without any specific measure", + "riskScenarioAcceptedNoAcceptance": "Risk accepted but no risk acceptance attached", + "appliedControlNoETA": "Does not have an ETA", + "appliedControlETAInPast": "ETA is in the past now. Consider updating its status or the date", + "appliedControlNoEffort": "Does not have an estimated effort. This will help you for prioritization", + "appliedControlNoLink": "Applied control does not have an external link attached. This will help you for follow-up", + "riskAcceptanceNoExpiryDate": "Acceptance has no expiry date", + "riskAcceptanceExpired": "Acceptance has expired. Consider updating the status or the date", + "complianceAssessmentInProgress": "Compliance assessment is still in progress", + "complianceAssessmentNoAuthor": "No author assigned to this compliance assessment", + "requirementAssessmentNoAppliedControl": "Requirement assessment status is compliant or partially compliant with no applied control applied", + "appliedControlNoReferenceControl": "Applied control has no reference control selected", + "evidenceNoFile": "Evidence has no file uploaded" + } diff --git a/frontend/messages/fr.json b/frontend/messages/fr.json index a533c60009..ce6078a628 100644 --- a/frontend/messages/fr.json +++ b/frontend/messages/fr.json @@ -530,5 +530,5 @@ "incoming": "En approche", "outdated": "Dépassé", "exportBackupDescription": "Cela va sérialiser et créer une sauvegarde de la base de données, y compris les utilisateurs et RBAC. Les preuves et autres fichiers ne sont pas inclus dans la sauvegarde.", - "importBackupDescription": "Cela va désérialiser et restaurer la base de données à partir d'une sauvegarde. Cela va écraser toutes les données existantes, y compris les utilisateurs et RBAC. Cette action est irréversible." + "importBackupDescription": "Cela va désérialiser et restaurer la base de données à partir d'une sauvegarde. Cela va écraser toutes les données existantes, y compris les utilisateurs et RBAC. Cette action est irréversible.", } diff --git a/frontend/src/lib/components/Breadcrumbs/Breadcrumbs.svelte b/frontend/src/lib/components/Breadcrumbs/Breadcrumbs.svelte index 277b3dd9ce..a46e750e33 100644 --- a/frontend/src/lib/components/Breadcrumbs/Breadcrumbs.svelte +++ b/frontend/src/lib/components/Breadcrumbs/Breadcrumbs.svelte @@ -65,8 +65,8 @@ {#if c.icon} {/if} - {#if localItems(languageTag())[c.label]} - {localItems(languageTag())[c.label]} + {#if localItems()[c.label]} + {localItems()[c.label]} {:else} {c.label} {/if} @@ -82,8 +82,8 @@ {#if c.icon} {/if} - {#if localItems(languageTag())[c.label]} - {localItems(languageTag())[c.label]} + {#if localItems()[c.label]} + {localItems()[c.label]} {:else} {c.label} {/if} @@ -93,8 +93,8 @@ {#if c.icon} {/if} - {#if localItems(languageTag())[c.label]} - {localItems(languageTag())[c.label]} + {#if localItems()[c.label]} + {localItems()[c.label]} {:else} {c.label} {/if} diff --git a/frontend/src/lib/components/Chart/DonutChart.svelte b/frontend/src/lib/components/Chart/DonutChart.svelte index 77335e0e19..5f55885428 100644 --- a/frontend/src/lib/components/Chart/DonutChart.svelte +++ b/frontend/src/lib/components/Chart/DonutChart.svelte @@ -16,7 +16,7 @@ for (const index in values) { if (values[index].localName) { - values[index].name = localItems(languageTag())[values[index].localName]; + values[index].name = localItems()[values[index].localName]; } } diff --git a/frontend/src/lib/components/Chart/RadarChart.svelte b/frontend/src/lib/components/Chart/RadarChart.svelte index 1c3075c419..465f36c43d 100644 --- a/frontend/src/lib/components/Chart/RadarChart.svelte +++ b/frontend/src/lib/components/Chart/RadarChart.svelte @@ -16,7 +16,7 @@ for (const index in values) { if (values[index].localName) { - values[index].name = localItems(languageTag())[values[index].localName]; + values[index].name = localItems()[values[index].localName]; } } diff --git a/frontend/src/lib/components/Forms/AutocompleteSelect.svelte b/frontend/src/lib/components/Forms/AutocompleteSelect.svelte index c426a332d5..f57f0107ca 100644 --- a/frontend/src/lib/components/Forms/AutocompleteSelect.svelte +++ b/frontend/src/lib/components/Forms/AutocompleteSelect.svelte @@ -89,8 +89,8 @@ {#if option.suggested} {option.label} (suggested) - {:else if translateOptions && localItems(languageTag())[toCamelCase(option.label)]} - {localItems(languageTag())[toCamelCase(option.label)]} + {:else if translateOptions && localItems()[toCamelCase(option.label)]} + {localItems()[toCamelCase(option.label)]} {:else} {option.label} {/if} diff --git a/frontend/src/lib/components/Forms/Select.svelte b/frontend/src/lib/components/Forms/Select.svelte index 880c543404..1fec2750e4 100644 --- a/frontend/src/lib/components/Forms/Select.svelte +++ b/frontend/src/lib/components/Forms/Select.svelte @@ -62,8 +62,8 @@ {/if} {#each options as option}