Merge branch 'feature/translations' of github.com:ONLYOFFICE/AppServer into feature/translations

This commit is contained in:
Artem Tarasov 2021-05-21 15:47:08 +03:00
commit 90a04bcfc7
12 changed files with 85 additions and 49 deletions

View File

@ -48,7 +48,9 @@ namespace Frontend.Translations.Tests
var translationFile = new TranslationFile(path);
translationFile.Translations = jsonTranslation.Properties().Select(p => new TranslationItem(p.Name, (string)p.Value)).ToList();
translationFile.Translations = jsonTranslation.Properties()
.Select(p => new TranslationItem(p.Name, (string)p.Value))
.ToList();
TranslationFiles.Add(translationFile);
}
@ -56,19 +58,19 @@ namespace Frontend.Translations.Tests
var javascriptFiles = (from wsPath in Workspaces
let clientDir = Path.Combine(BasePath, wsPath)
from file in Directory.EnumerateFiles(clientDir, "*.js", SearchOption.AllDirectories)
where file.Contains("src\\")
where !file.Contains("dist\\")
select file)
.ToList();
javascriptFiles.AddRange(from wsPath in Workspaces
let clientDir = Path.Combine(BasePath, wsPath)
from file in Directory.EnumerateFiles(clientDir, "*.jsx", SearchOption.AllDirectories)
where file.Contains("src\\")
where !file.Contains("dist\\")
select file);
JavaScriptFiles = new List<JavaScriptFile>();
var pattern1 = "[.{\\s\\(]t\\(\\s*[\"\'`]([a-zA-Z0-9_.:_\\$\\s{}/_-]+)[\"\'`]\\s*[\\),]";
var pattern1 = "[.{\\s\\(]t\\(\\s*[\"\'`]([a-zA-Z0-9_.:_\\s{}/_-]+)[\"\'`]\\s*[\\),]";
var pattern2 = "i18nKey=\"([a-zA-Z0-9_.-]+)\"";
var regexp = new Regex($"({pattern1})|({pattern2})", RegexOptions.Multiline | RegexOptions.ECMAScript);
@ -79,7 +81,11 @@ namespace Frontend.Translations.Tests
var matches = regexp.Matches(jsFileText);
var translationKeys = matches.Select(m => m.Groups[2].Value == "" ? m.Groups[4].Value : m.Groups[2].Value).ToList();
var translationKeys = matches
.Select(m => m.Groups[2].Value == ""
? m.Groups[4].Value
: m.Groups[2].Value)
.ToList();
if (!translationKeys.Any())
continue;
@ -117,11 +123,18 @@ namespace Frontend.Translations.Tests
.ToList();
var enGroup = groupedByLng.Find(f => f.Lng == "en");
var expectedCount = enGroup.Count;
foreach (var lng in groupedByLng.Where(g => g.Lng != "en"))
{
Assert.AreEqual(enGroup.Count, lng.Count, "language '{0}' is not equals 'en' by translated files count", lng.Lng);
}
var otherLngs = groupedByLng.Where(g => g.Lng != "en");
var incompleteList = otherLngs
.Where(lng => lng.Count != expectedCount)
.Select(lng => $"{lng.Lng} (Count={lng.Count})")
.ToList();
Assert.AreEqual(0, incompleteList.Count,
"languages '{0}' are not equal 'en' (Count= {1}) by translated files count",
string.Join(", ", incompleteList), expectedCount);
//Assert.AreEqual(true, groupedByLng.All(g => g.Count == enGroup.Count));
}
@ -137,17 +150,24 @@ namespace Frontend.Translations.Tests
Keys = grp
.SelectMany(k => k.Translations)
.OrderByDescending(itm => itm.Key)
.ToList()
})
.ToList();
var enGroup = groupedByLng.Find(f => f.Lng == "en");
var expectedCount = enGroup.Keys.Count();
var expectedCount = enGroup.Keys.Count;
foreach (var lng in groupedByLng.Where(g => g.Lng != "en"))
{
Assert.AreEqual(expectedCount, lng.Keys.Count(), "language '{0}' is not equals 'en' by translated keys count", lng.Lng);
}
var otherLngs = groupedByLng.Where(g => g.Lng != "en");
var incompleteList = otherLngs
.Where(lng => lng.Keys.Count != expectedCount)
.Select(lng => $"{lng.Lng} (Count={lng.Keys.Count})")
.ToList();
Assert.AreEqual(0, incompleteList.Count,
"languages '{0}' are not equal 'en' (Count= {1}) by translated keys count",
string.Join(", ", incompleteList), expectedCount);
//Assert.AreEqual(true, groupedByLng.All(g => g.Keys.Count() == enGroup.Keys.Count()));
}
@ -167,7 +187,9 @@ namespace Frontend.Translations.Tests
var notFoundJsKeys = allJsTranslationKeys.Except(allEnKeys);
Assert.AreEqual(0, notFoundJsKeys.Count(), "Some i18n-keys are not exist in translations in 'en' language: Keys: '{0}'", string.Join(", ", notFoundJsKeys));
Assert.AreEqual(0, notFoundJsKeys.Count(),
"Some i18n-keys are not exist in translations in 'en' language: Keys: '{0}'",
string.Join(", ", notFoundJsKeys));
}
[Test]
@ -187,7 +209,9 @@ namespace Frontend.Translations.Tests
var notFoundi18nKeys = allEnKeys.Except(allJsTranslationKeys);
Assert.AreEqual(0, notFoundi18nKeys.Count(), "Some i18n-keys are not found in js: Keys: '{0}'", string.Join(", ", notFoundi18nKeys));
Assert.AreEqual(0, notFoundi18nKeys.Count(),
"Some i18n-keys are not found in js: Keys: '{0}'",
string.Join(", ", notFoundi18nKeys));
}
}
}

View File

@ -110,20 +110,20 @@ export const ConflictResolveType = Object.freeze({
});
export const providersData = Object.freeze({
Google: {
label: "SignInWithGoogle",
label: "Google",
icon: "/static/images/share.google.react.svg",
},
Facebook: {
label: "SignInWithFacebook",
label: "Facebook",
icon: "/static/images/share.facebook.react.svg",
},
Twitter: {
label: "SignInWithTwitter",
label: "Twitter",
icon: "/static/images/share.twitter.react.svg",
iconOptions: { color: "#2AA3EF" },
},
LinkedIn: {
label: "SignInWithLinkedIn",
label: "LinkedIn",
icon: "/static/images/share.linkedin.react.svg",
},
});

View File

@ -224,3 +224,16 @@ export function toCommunityHostname(hostname) {
return communityHostname;
}
export function getProviderTranslation(provider, t) {
switch (provider) {
case "Google":
return t("SignInWithGoogle");
case "Facebook":
return t("SignInWithFacebook");
case "Twitter":
return t("SignInWithTwitter");
case "LinkedIn":
return t("SignInWithLinkedIn");
}
}

View File

@ -9,7 +9,11 @@ import Link from "@appserver/components/link";
import ProfileInfo from "./ProfileInfo/ProfileInfo";
import toastr from "studio/toastr";
import React from "react";
import { combineUrl, isMe } from "@appserver/common/utils";
import {
combineUrl,
isMe,
getProviderTranslation,
} from "@appserver/common/utils";
import styled from "styled-components";
import { withRouter } from "react-router";
@ -208,7 +212,7 @@ class SectionBodyContent extends React.PureComponent {
<FacebookButton
noHover={true}
iconName={icon}
label={t(label)}
label={getProviderTranslation(label, t)}
className="socialButton"
$iconOptions={iconOptions}
/>
@ -216,7 +220,7 @@ class SectionBodyContent extends React.PureComponent {
<SocialButton
noHover={true}
iconName={icon}
label={t(label)}
label={getProviderTranslation(label, t)}
className="socialButton"
$iconOptions={iconOptions}
/>

View File

@ -69,10 +69,6 @@
"ProductsAndInstruments": "Module und Tools",
"ProductUserOpportunities": "Profile und Gruppen anschauen",
"ProjectsProduct": "Projekte",
"ProjectsUserCapabilityCreate": "Meilensteine, Aufgaben, Diskussionen, Dokumente erstellen und bearbeiten",
"ProjectsUserCapabilityForm": "Projektteam bilden und Zugriffsrechte bestimmen",
"ProjectsUserCapabilityTrack": "Zeit für Aufgaben verfolgen, Berichte generieren",
"ProjectsUserCapabilityView": "Projekte anschauen und an Diskussionen teilnehmen",
"RestoreDefaultButton": "Standardmäßige Einstellungen",
"SetDefaultTitle": "Standardtitel setzen",
"SetPeopleAdmin": "Administrator des Moduls Personen auswählen",

View File

@ -78,10 +78,6 @@
"ProductsAndInstruments": "Modules \u0026 tools",
"ProductUserOpportunities": "View profiles and groups",
"ProjectsProduct": "Projects",
"ProjectsUserCapabilityCreate": "Create and edit milestones, tasks, discussions, documents",
"ProjectsUserCapabilityForm": "Form a project team and set access rights",
"ProjectsUserCapabilityTrack": "Track time for tasks, generate reports",
"ProjectsUserCapabilityView": "View projects and take part in discussions",
"RegistrationDate": "Registration date",
"RestoreDefaultButton": "Restore to Default",

View File

@ -78,10 +78,6 @@
"ProductsAndInstruments": "Модули и инструменты",
"ProductUserOpportunities": "Просматривать профили и группы",
"ProjectsProduct": "Проекты",
"ProjectsUserCapabilityCreate": "Создавать и редактировать вехи, задачи, обсуждения, документы",
"ProjectsUserCapabilityForm": "Формировать команду проекта и устанавливать права доступа",
"ProjectsUserCapabilityTrack": "Учитывать время выполнения задач, генерировать отчеты",
"ProjectsUserCapabilityView": "Просматривать проекты и участвовать в обсуждениях",
"RegistrationDate": "Дата регистрации",
"RestoreDefaultButton": "Настройки по умолчанию",
"SetDefaultTitle": "Установить заголовок по умолчанию",

View File

@ -186,7 +186,7 @@ class Form extends React.PureComponent {
size="big"
tabIndex={2}
label={
isLoading ? t("Common:LoadingProcessing") : t("Common:OkButton")
isLoading ? t("Common:LoadingProcessing") : t("Common:OKButton")
}
isDisabled={isLoading}
isLoading={isLoading}

View File

@ -18,7 +18,11 @@ import FacebookButton from "@appserver/components/facebook-button";
import EmailInput from "@appserver/components/email-input";
import { getAuthProviders } from "@appserver/common/api/settings";
import PageLayout from "@appserver/common/components/PageLayout";
import { combineUrl, createPasswordHash } from "@appserver/common/utils";
import {
combineUrl,
createPasswordHash,
getProviderTranslation,
} from "@appserver/common/utils";
import { AppServerConfig, providersData } from "@appserver/common/constants";
import { isMobile } from "react-device-detect";
import { desktop } from "@appserver/components/utils/device";
@ -182,7 +186,7 @@ class Confirm extends React.PureComponent {
>
<FacebookButton
iconName={icon}
label={t(label)}
label={getProviderTranslation(label, t)}
className="socialButton"
$iconOptions={iconOptions}
data-url={faceBookData.url}
@ -213,7 +217,7 @@ class Confirm extends React.PureComponent {
<div className="buttonWrapper" key={`${item.provider}ProviderItem`}>
<SocialButton
iconName={icon}
label={t(label)}
label={getProviderTranslation(label, t)}
className={`socialButton ${className ? className : ""}`}
$iconOptions={iconOptions}
data-url={item.url}

View File

@ -46,10 +46,10 @@ class Body extends React.PureComponent {
setPaymentsLicense(null, fd)
.then(() => {
toastr.success(t("LoadingLicenseSuccess"), "");
toastr.success(t("SuccessLoadingLicense"), "");
})
.catch((error) => {
toastr.error(t("LoadingLicenseError"), "LicenseIsNotValid", 0, true);
toastr.error(t("ErrorLoadingLicense"), "LicenseIsNotValid", 0, true);
console.log(error);
});
};

View File

@ -45,10 +45,9 @@ const Separator = styled.div`
class ThirdPartyServices extends React.Component {
constructor(props) {
super(props);
const { t } = props;
document.title = `${t("ThirdPartyAuthorization")} ${t(
"OrganizationName"
)}`;
const { t, setDocumentTitle } = props;
setDocumentTitle(`${t("ThirdPartyAuthorization")}`);
this.state = {
dialogVisible: false,
@ -203,7 +202,7 @@ ThirdPartyServices.propTypes = {
};
export default inject(({ setup, auth }) => {
const { settingsStore } = auth;
const { settingsStore, setDocumentTitle } = auth;
const { urlAuthKeys } = settingsStore;
const {
getConsumers,
@ -219,5 +218,6 @@ export default inject(({ setup, auth }) => {
getConsumers,
updateConsumerProps,
setSelectedConsumer,
setDocumentTitle,
};
})(withTranslation(["Settings", "Common"])(observer(ThirdPartyServices)));

View File

@ -19,7 +19,10 @@ import ForgotPasswordModalDialog from "./sub-components/forgot-password-modal-di
import Register from "./sub-components/register-container";
import { getAuthProviders } from "@appserver/common/api/settings";
import { checkPwd } from "@appserver/common/desktop";
import { createPasswordHash } from "@appserver/common/utils";
import {
createPasswordHash,
getProviderTranslation,
} from "@appserver/common/utils";
import { providersData } from "@appserver/common/constants";
import { inject, observer } from "mobx-react";
import i18n from "./i18n";
@ -350,7 +353,7 @@ const Form = (props) => {
>
<FacebookButton
iconName={icon}
label={t(label)}
label={getProviderTranslation(label, t)}
className="socialButton"
$iconOptions={iconOptions}
data-url={faceBookData.url}
@ -380,7 +383,7 @@ const Form = (props) => {
<div className="buttonWrapper" key={`${item.provider}ProviderItem`}>
<SocialButton
iconName={icon}
label={t(label)}
label={getProviderTranslation(label, t)}
className={`socialButton ${className ? className : ""}`}
$iconOptions={iconOptions}
data-url={item.url}