diff --git a/Makefile b/Makefile index a26d406160c..17ddb3a3db2 100755 --- a/Makefile +++ b/Makefile @@ -133,6 +133,7 @@ locales: msgfmt -o modules/media/locale/ja/LC_MESSAGES/media.mo modules/media/locale/ja/LC_MESSAGES/media.po msgfmt -o modules/module_manager/locale/ja/LC_MESSAGES/module_manager.mo modules/module_manager/locale/ja/LC_MESSAGES/module_manager.po msgfmt -o modules/mri_violations/locale/ja/LC_MESSAGES/mri_violations.mo modules/mri_violations/locale/ja/LC_MESSAGES/mri_violations.po + msgfmt -o modules/my_preferences/locale/hi/LC_MESSAGES/my_preferences.mo modules/my_preferences/locale/hi/LC_MESSAGES/my_preferences.po msgfmt -o modules/next_stage/locale/ja/LC_MESSAGES/next_stage.mo modules/next_stage/locale/ja/LC_MESSAGES/next_stage.po msgfmt -o modules/next_stage/locale/es/LC_MESSAGES/next_stage.mo modules/next_stage/locale/es/LC_MESSAGES/next_stage.po msgfmt -o modules/oidc/locale/ja/LC_MESSAGES/oidc.mo modules/oidc/locale/ja/LC_MESSAGES/oidc.po diff --git a/locale/hi/LC_MESSAGES/loris.po b/locale/hi/LC_MESSAGES/loris.po index a10786ac046..e19c9f495a2 100644 --- a/locale/hi/LC_MESSAGES/loris.po +++ b/locale/hi/LC_MESSAGES/loris.po @@ -113,6 +113,9 @@ msgstr "रिपोर्ट्स" msgid "TimePoint" msgstr "समय बिंदु" +msgid "Module" +msgstr "मॉड्यूल" + # Common select option labels msgid "Yes" msgstr "हाँ" @@ -120,12 +123,12 @@ msgstr "हाँ" msgid "No" msgstr "नहीं" -msgid "Create" -msgstr "बनाएँ" - msgid "N/A" msgstr "लागू नहीं" +msgid "Create" +msgstr "बनाएँ" + # Filters msgid "Selection Filter" msgstr "चयन फ़िल्टर" @@ -165,9 +168,6 @@ msgstr "दौरे का लेबल" msgid "Site" msgstr "साइट" -msgid "Module" -msgstr "मॉड्यूल" - msgid "Project" msgstr "परियोजना" @@ -235,6 +235,12 @@ msgstr "भाषा" msgid "Ethnicity" msgstr "जातीयता" +msgid "Save" +msgstr "सहेजें" + +msgid "Reset" +msgstr "रीसेट करें" + # Data table strings msgid "{{pageCount}} rows displayed of {{totalCount}}." msgstr "{{totalCount}} में से {{pageCount}} पंक्तियाँ प्रदर्शित" @@ -245,6 +251,22 @@ msgstr "प्रति पृष्ठ अधिकतम पंक्तिय msgid "Download Data as CSV" msgstr "डेटा को CSV के रूप में डाउनलोड करें" +#: php/libraries/Password.class.inc +msgid "The password is too short" +msgstr "पासवर्ड बहुत छोटा है" + +msgid "The password is not complex enough." +msgstr "पासवर्ड पर्याप्त जटिल नहीं है।" + +msgid "This password is known to be exposed in online data breaches." +msgstr "यह पासवर्ड ऑनलाइन डेटा उल्लंघनों में उजागर होने के लिए जाना जाता है।" + +msgid "Data Supervisors to Email" +msgstr "ईमेल करने के लिए डेटा पर्यवेक्षक" + +msgid "Invalid email address" +msgstr "अमान्य ईमेल पता" + # Dashboard panel strings msgid "Views" msgstr "दृश्य" @@ -254,11 +276,57 @@ msgid "NEW" msgstr "नया" msgid "Updated" -msgstr "अपडेट किया गया" +msgstr "अद्यतन किया गया" msgid "Uploaded" msgstr "अपलोड किया गया" +# User Account related +msgid "Password Rules" +msgstr "पासवर्ड नियम" + +msgid "Username" +msgstr "उपयोगकर्ता नाम" + +msgid "First name" +msgstr "पहला नाम" + +msgid "First name is required and should not exceed 120 characters" +msgstr "पहला नाम आवश्यक है और 120 अक्षरों से अधिक नहीं होना चाहिए।" + +msgid "Last name" +msgstr "अंतिम नाम" + +msgid "Last name is required and should not exceed 120 characters" +msgstr "अंतिम नाम आवश्यक है और 120 अक्षरों से अधिक नहीं होना चाहिए।" + +msgid "Email address" +msgstr "ईमेल पता" + +msgid "New Password" +msgstr "नया पासवर्ड" + +msgid "Confirm Password" +msgstr "पासवर्ड की पुष्टि करें" + +msgid "Email address is required" +msgstr "ईमेल पता आवश्यक है" + +msgid "The password must be at least 8 characters long." +msgstr "पासवर्ड कम से कम 8 अक्षरों का होना चाहिए।" + +msgid "The password cannot be your username or email address." +msgstr "पासवर्ड आपका उपयोगकर्ता नाम या ईमेल पता नहीं हो सकता।" + +msgid "Please choose a unique password." +msgstr "कृपया एक अद्वितीय पासवर्ड चुनें।" + +msgid "No special characters are required but your password must be sufficiently complex to be accepted." +msgstr "कोई विशेष अक्षर आवश्यक नहीं हैं, लेकिन पासवर्ड पर्याप्त जटिल होना चाहिए ताकि उसे स्वीकार किया जा सके।" + +msgid "We suggest using a password manager to generate one for you." +msgstr "हम सुझाव देते हैं कि आपके लिए पासवर्ड बनाने हेतु पासवर्ड मैनेजर का उपयोग करें।" + msgid "Total" msgstr "कुल" diff --git a/locale/loris.pot b/locale/loris.pot index 5322575d009..d6c467ab0ff 100644 --- a/locale/loris.pot +++ b/locale/loris.pot @@ -122,10 +122,10 @@ msgstr "" msgid "No" msgstr "" -msgid "Create" +msgid "N/A" msgstr "" -msgid "N/A" +msgid "Create" msgstr "" # Filters @@ -240,6 +240,12 @@ msgstr "" msgid "Ethnicity" msgstr "" +msgid "Save" +msgstr "" + +msgid "Reset" +msgstr "" + # Data table strings msgid "{{pageCount}} rows displayed of {{totalCount}}." msgstr "" @@ -254,6 +260,22 @@ msgstr "" msgid "Views" msgstr "" +#: php/libraries/Password.class.inc +msgid "The password is too short" +msgstr "" + +msgid "The password is not complex enough." +msgstr "" + +msgid "This password is known to be exposed in online data breaches." +msgstr "" + +msgid "Data Supervisors to Email" +msgstr "" + +msgid "Invalid email address" +msgstr "" + # Common strings on widgets msgid "NEW" msgstr "" @@ -264,6 +286,51 @@ msgstr "" msgid "Uploaded" msgstr "" +# User Account related +msgid "Password Rules" +msgstr "" + +msgid "Username" +msgstr "" + +msgid "First name" +msgstr "" + +msgid "First name is required and should not exceed 120 characters" +msgstr "" + +msgid "Last name" +msgstr "" + +msgid "Last name is required and should not exceed 120 characters" +msgstr "" + +msgid "Email address" +msgstr "" + +msgid "New Password" +msgstr "" + +msgid "Confirm Password" +msgstr "" + +msgid "Email address is required" +msgstr "" + +msgid "The password must be at least 8 characters long." +msgstr "" + +msgid "The password cannot be your username or email address." +msgstr "" + +msgid "Please choose a unique password." +msgstr "" + +msgid "No special characters are required but your password must be sufficiently complex to be accepted." +msgstr "" + +msgid "We suggest using a password manager to generate one for you." +msgstr "" msgid "Total" msgstr "" diff --git a/modules/my_preferences/locale/hi/LC_MESSAGES/my_preferences.po b/modules/my_preferences/locale/hi/LC_MESSAGES/my_preferences.po new file mode 100644 index 00000000000..8b54649b398 --- /dev/null +++ b/modules/my_preferences/locale/hi/LC_MESSAGES/my_preferences.po @@ -0,0 +1,55 @@ +# Default LORIS strings to be translated (English). +# Copy this to a language specific file and add translations to the +# new file. +# Copyright (C) 2025 +# This file is distributed under the same license as the LORIS package. +# Dave MacFarlane , 2025. +# +msgid "" +msgstr "" +"Project-Id-Version: LORIS 27\n" +"Report-Msgid-Bugs-To: https://github.com/aces/Loris/issues\n" +"POT-Creation-Date: 2025-04-08 14:37-0400\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"Language: hi\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" + +msgid "My Preferences" +msgstr "मेरी प्राथमिकताएँ" + +msgid "Edit My Information" +msgstr "मेरी जानकारी संपादित करें" + +msgid "Notifications" +msgstr "सूचनाएँ" + +msgid "Your email address must be less than 255 characters long" +msgstr "आपका ईमेल पता 255 अक्षरों से कम होना चाहिए।" + +msgid "Language preference" +msgstr "भाषा वरीयता" + +msgid "Operation" +msgstr "क्रिया" + +msgid "Description" +msgstr "विवरण" + +msgid "The email address already exists" +msgstr "ईमेल पता पहले से मौजूद है" + +msgid "Your password cannot be your email" +msgstr "आपका पासवर्ड आपका ईमेल नहीं हो सकता।" + +msgid "Your password cannot be your username" +msgstr "आपका पासवर्ड आपका उपयोगकर्ता नाम नहीं हो सकता।" + +msgid "The passwords do not match" +msgstr "पासवर्ड मेल नहीं खाते।" + +msgid "New and old passwords are identical" +msgstr "नया और पुराना पासवर्ड समान हैं।" \ No newline at end of file diff --git a/modules/my_preferences/locale/my_preferences.pot b/modules/my_preferences/locale/my_preferences.pot new file mode 100644 index 00000000000..b83fd0bb954 --- /dev/null +++ b/modules/my_preferences/locale/my_preferences.pot @@ -0,0 +1,55 @@ +# Default LORIS strings to be translated (English). +# Copy this to a language specific file and add translations to the +# new file. +# Copyright (C) 2025 +# This file is distributed under the same license as the LORIS package. +# Dave MacFarlane , 2025. +# +msgid "" +msgstr "" +"Project-Id-Version: LORIS 27\n" +"Report-Msgid-Bugs-To: https://github.com/aces/Loris/issues\n" +"POT-Creation-Date: 2025-04-08 14:37-0400\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" + +msgid "My Preferences" +msgstr "" + +msgid "Edit My Information" +msgstr "" + +msgid "Notifications" +msgstr "" + +msgid "Your email address must be less than 255 characters long" +msgstr "" + +msgid "Language preference" +msgstr "" + +msgid "Operation" +msgstr "" + +msgid "Description" +msgstr "" + +msgid "The email address already exists" +msgstr "" + +msgid "Your password cannot be your email" +msgstr "" + +msgid "Your password cannot be your username" +msgstr "" + +msgid "The passwords do not match" +msgstr "" + +msgid "New and old passwords are identical" +msgstr "" diff --git a/modules/my_preferences/php/my_preferences.class.inc b/modules/my_preferences/php/my_preferences.class.inc index 8ff9e520452..f1ac6509250 100644 --- a/modules/my_preferences/php/my_preferences.class.inc +++ b/modules/my_preferences/php/my_preferences.class.inc @@ -9,12 +9,11 @@ namespace LORIS\my_preferences; */ class My_Preferences extends \NDB_Form { - private const PASSWORD_ERROR_IS_EMAIL = 'Your password cannot be your email.'; - private const PASSWORD_ERROR_IS_USER = 'Your password cannot be ' . - 'your user name.'; - private const PASSWORD_ERROR_NO_MATCH = 'The passwords do not match.'; - private const PASSWORD_ERROR_NO_CHANGE = 'New and old passwords are ' . - 'identical: please choose another one'; + // Use gettext for error messages + private const PASSWORD_ERROR_IS_EMAIL = 'Your password cannot be your email'; + private const PASSWORD_ERROR_IS_USER = 'Your password cannot be your username'; + private const PASSWORD_ERROR_NO_MATCH = 'The passwords do not match'; + private const PASSWORD_ERROR_NO_CHANGE = 'New and old passwords are identical'; /** * Computes the initial values this page will be filled with. @@ -72,8 +71,8 @@ class My_Preferences extends \NDB_Form $defaults['examiner_radiologist'] = 'N'; } } - if ($vals[0]=='Y') { - $defaults['ex_'.$cid] ='on'; + if ($vals[0] == 'Y') { + $defaults['ex_'.$cid] = 'on'; } } @@ -86,7 +85,8 @@ class My_Preferences extends \NDB_Form foreach ($operations as $operation => $services) { unset($services['desc']); foreach ($services as $service => $subscribed) { - $var_name = "notif_".$module."_".$operation."_".$service; + $var_name + = "notif_".$module."_".$operation."_".$service; if ($subscribed==='Y') { $defaults[$var_name] = 'on'; @@ -223,21 +223,22 @@ class My_Preferences extends \NDB_Form //get notification details $notifier_list = \NDB_Notifier::getNotificationModuleServices(); $notifier_services = \NDB_Notifier::getNotificationServices(); - //------------------------------------------------------------ // user name - $this->addScoreColumn('UserID', 'User name'); + $this->addScoreColumn('UserID', dgettext('loris', 'Username')); // full name // The supplied pattern is: // - must have at least one non-whitespace characters (i.e. required) // - once leading and trailing spaces are stripped, the field should // not exceed 120 chars - $firstNameInvalidMsg = "First name is required and " - . "should not exceed 120 characters"; + $firstNameInvalidMsg = dgettext( + 'loris', + "First name is required and should not exceed 120 characters" + ); $this->addBasicText( 'First_name', - 'First name', + dgettext('loris', 'First name'), [], [ 'oninvalid' => "this.setCustomValidity('$firstNameInvalidMsg')", @@ -250,11 +251,13 @@ class My_Preferences extends \NDB_Form // - must have at least one non-whitespace characters (i.e. required) // - once leading and trailing spaces are stripped, the field should // not exceed 120 chars - $lastNameInvalidMsg = "Last name is required and " - . "should not exceed 120 characters"; + $lastNameInvalidMsg = dgettext( + 'loris', + "Last name is required and should not exceed 120 characters" + ); $this->addBasicText( 'Last_name', - 'Last name', + dgettext('loris', 'Last name'), [], [ 'oninvalid' => "this.setCustomValidity('$lastNameInvalidMsg')", @@ -267,36 +270,65 @@ class My_Preferences extends \NDB_Form // email address $this->addBasicText( 'Email', - 'Email address', + dgettext('loris', 'Email address'), [], [ - 'oninvalid' => "this.setCustomValidity('Email address is required')", + 'oninvalid' => "this.setCustomValidity( + '" . dgettext( + 'loris', + 'Email address is required' + ) . "')", 'onchange' => "this.setCustomValidity('')", ] ); // email address rules - $this->addRule('Email', 'Email address is required', 'required'); $this->addRule( 'Email', - 'Your email address must be less than 255 characters long', + dgettext( + 'loris', + 'Email address is required' + ), + 'required' + ); + $this->addRule( + 'Email', + dgettext( + 'my_preferences', + 'Your email address must be less than 255 characters long' + ), 'maxlength', "255" ); // password - $this->form->addElement('password', 'Password_hash', 'New Password'); - $this->form->addElement('password', '__Confirm', 'Confirm Password'); + $this->form->addElement( + 'password', + 'Password_hash', + dgettext('loris', 'New Password') + ); + $this->form->addElement( + 'password', + '__Confirm', + dgettext('loris', 'Confirm Password') + ); // language preference $languages = \Utility::getLanguageList(); - $this->addSelect('language_preference', 'Language preference', $languages); + $this->addSelect( + 'language_preference', + dgettext( + 'my_preferences', + 'Language preference' + ), + $languages + ); // Notification headers $nGroup = []; - $nGroup[] = $this->createLabel("Module"); - $nGroup[] = $this->createLabel("Operation"); - $nGroup[] = $this->createLabel("Description"); + $nGroup[] = $this->createLabel(dgettext('loris', "Module")); + $nGroup[] = $this->createLabel(dgettext('my_preferences', "Operation")); + $nGroup[] = $this->createLabel(dgettext('my_preferences', "Description")); foreach ($notifier_services as $serv) { $nGroup[] = $this->createLabel($serv); @@ -312,7 +344,7 @@ class My_Preferences extends \NDB_Form // Notification rows $notification_rows =[]; foreach ($notifier_list as $module=>$operation_services) { - foreach ($operation_services as $operation=>$services) { + foreach ($operation_services as $operation => $services) { $nGroup = []; $nGroup[] = $this->createLabel($module); $nGroup[] = $this->createLabel($operation); @@ -320,27 +352,26 @@ class My_Preferences extends \NDB_Form unset($services['desc']); // Check for permissions - $display =true; + $display = true; foreach ($services['perm'] as $permission) { if (!$user->hasPermission($permission)) { - $display =false; + $display = false; break; } } unset($services['perm']); - foreach ($services as $service=>$avail) { - if ($avail==='Y' && $display) { + foreach ($services as $service => $avail) { + if ($avail === 'Y' && $display) { $nGroup[] = $this->createCheckbox( "notif_".$module."_".$operation."_".$service, "" ); } else { $nGroup[] = $this->createLabel( - "N/A" + dgettext('loris', "N/A") ); } - } $this->addGroup( @@ -349,7 +380,7 @@ class My_Preferences extends \NDB_Form '', $this->_GUIDelimiter ); - $notification_rows[] ="row_".$module."_".$operation; + $notification_rows[] = "row_".$module."_".$operation; unset($nGroup); } } @@ -397,18 +428,27 @@ class My_Preferences extends \NDB_Form $plaintext = $values['Password_hash']; if ($values['Email'] === $plaintext) { - $errors['Password_Group'] = self::PASSWORD_ERROR_IS_EMAIL; + $errors['Password_Group'] = dgettext( + 'my_preferences', + self::PASSWORD_ERROR_IS_EMAIL + ); } // Make sure the user is not using their username as their password. if ($this->identifier === $plaintext) { - $errors['Password_Group'] = self::PASSWORD_ERROR_IS_USER; + $errors['Password_Group'] = dgettext( + 'my_preferences', + self::PASSWORD_ERROR_IS_USER + ); } // Ensure that the password and confirm password fields match. // TODO This validation should be done on the front-end instead. if ($values['Password_hash'] !== $values['__Confirm']) { - $errors['Password_Group'] = self::PASSWORD_ERROR_NO_MATCH; + $errors['Password_Group'] = dgettext( + 'my_preferences', + self::PASSWORD_ERROR_NO_MATCH + ); return $errors; } @@ -421,21 +461,25 @@ class My_Preferences extends \NDB_Form $decoded = htmlspecialchars_decode($plaintext); new \Password($decoded); // New password must be different than current one - if (! \User::factory($this->identifier)->isPasswordDifferent( - $decoded - ) + if (!\User::factory($this->identifier)->isPasswordDifferent($decoded) ) { - $errors['Password_Group'] = self::PASSWORD_ERROR_NO_CHANGE; + $errors['Password_Group'] = dgettext( + 'my_preferences', + self::PASSWORD_ERROR_NO_CHANGE + ); } } catch (\InvalidArgumentException $e) { - $errors['Password_Group'] = $e->getMessage(); + $errors['Password_Group'] = dgettext( + 'my_preferences', + $e->getMessage() + ); } } // Validate email $emailError = $this->_getEmailError($DB, $values['Email']); if (!is_null($emailError)) { - $errors['Email'] = $emailError; + $errors['Email'] = dgettext('my_preferences', $emailError); } return $errors; @@ -456,7 +500,7 @@ class My_Preferences extends \NDB_Form $email = filter_var($email, FILTER_SANITIZE_EMAIL); if (!filter_var($email, FILTER_VALIDATE_EMAIL)) { // If email not syntactically valid - return "Invalid email address"; + return dgettext('loris', "Invalid email address"); } // check email address' uniqueness @@ -470,7 +514,7 @@ class My_Preferences extends \NDB_Form // Email already exists in database if ($result > 0) { - return 'The email address already exists'; + return dgettext('my_preferences', 'The email address already exists'); } return null; @@ -516,4 +560,3 @@ class My_Preferences extends \NDB_Form ); } } - diff --git a/modules/my_preferences/templates/form_my_preferences.tpl b/modules/my_preferences/templates/form_my_preferences.tpl index 7a1534f6740..437bf525ba9 100644 --- a/modules/my_preferences/templates/form_my_preferences.tpl +++ b/modules/my_preferences/templates/form_my_preferences.tpl @@ -1,13 +1,13 @@
-

Password Rules

+

{dgettext("loris", "Password Rules")}

    -
  • The password must be at least 8 characters long.
  • -
  • The password cannot be your username or email address.
  • -
  • No special characters are required but your password must be sufficiently complex to be accepted.
  • +
  • {dgettext("loris", "The password must be at least 8 characters long.")}
  • +
  • {dgettext("loris", "The password cannot be your username or email address.")}
  • +
  • {dgettext("loris", "No special characters are required but your password must be sufficiently complex to be accepted.")}
-

Please choose a unique password.

-

We suggest using a password manager to generate one for you.

-

Edit My Information

+

{dgettext("loris", "Please choose a unique password.")}

+

{dgettext("loris", "We suggest using a password manager to generate one for you.")}

+

{dgettext("my_preferences", "Edit My Information")}

{foreach from=$form.errors item=error}
  • {$error}
  • @@ -38,7 +38,8 @@
    {$form.Last_name.html}
    -
    +
    +
    @@ -71,7 +72,7 @@


    -

    Notifications

    +

    {dgettext("my_preferences", "Notifications")}

    {foreach key=gkey item=gitem from=$form.notification_headers.elements} @@ -110,13 +111,12 @@
    - +
    - +
    - {$form.hidden|default} diff --git a/php/libraries/Password.class.inc b/php/libraries/Password.class.inc index 13c95c3f80f..b06c207669b 100644 --- a/php/libraries/Password.class.inc +++ b/php/libraries/Password.class.inc @@ -105,11 +105,19 @@ class Password // Check length and complexity separately in order to return a precise // error message upon failure. if (!$this->_hasSufficientLength($value)) { - throw new \InvalidArgumentException('The password is too short'); + throw new \InvalidArgumentException( + dgettext( + 'loris', + 'The password is too short' + ) + ); } if (!$this->_hasSufficientComplexity($value)) { throw new \InvalidArgumentException( - 'The password is not complex enough.' + dgettext( + 'loris', + 'The password is not complex enough.' + ) ); } if (\NDB_Factory::singleton()->config()->settingEnabled( @@ -118,8 +126,11 @@ class Password ) { if ($this->_pwned($value)) { throw new \InvalidArgumentException( - 'This password is known to be exposed in online data ' - . 'breaches.' + dgettext( + 'loris', + 'This password is known to be exposed in online data' + . ' breaches.' + ) ); } }