Translations: Tests: Fix ForbiddenValueElementsTest/ForbiddenKeysElementsTest

This commit is contained in:
Alexey Safronov 2024-07-19 14:47:18 +04:00
parent 080f560a38
commit bf55d700ea

View File

@ -29,14 +29,14 @@ using System.Collections.Generic;
using System.Diagnostics; using System.Diagnostics;
using System.IO; using System.IO;
using System.Linq; using System.Linq;
using System.Reflection; using System.Reflection;
using System.Security.Cryptography; using System.Security.Cryptography;
using System.Text; using System.Text;
using System.Text.RegularExpressions; using System.Text.RegularExpressions;
using Frontend.Tests; using Frontend.Tests;
using Frontend.Tests.Models; using Frontend.Tests.Models;
using Newtonsoft.Json; using Newtonsoft.Json;
using Newtonsoft.Json.Linq; using Newtonsoft.Json.Linq;
@ -47,7 +47,7 @@ using WeCantSpell.Hunspell;
namespace Frontend.Tests; namespace Frontend.Tests;
public class LocalesTest public class LocalesTest
{ {
public static string BasePath public static string BasePath
{ {
get get
@ -56,18 +56,18 @@ public class LocalesTest
} }
} }
public static bool Save public static bool Save
{ {
get get
{ {
bool save; bool save;
if (bool.TryParse(Environment.GetEnvironmentVariable("SAVE"), out save)) if (bool.TryParse(Environment.GetEnvironmentVariable("SAVE"), out save))
{ {
return save; return save;
} }
return false; return false;
} }
} }
public List<string> Workspaces { get; set; } public List<string> Workspaces { get; set; }
@ -77,13 +77,14 @@ public class LocalesTest
public List<KeyValuePair<string, string>> NotTranslatedToasts { get; set; } public List<KeyValuePair<string, string>> NotTranslatedToasts { get; set; }
public List<KeyValuePair<string, string>> NotTranslatedProps { get; set; } public List<KeyValuePair<string, string>> NotTranslatedProps { get; set; }
public List<LanguageItem> CommonTranslations { get; set; } public List<LanguageItem> CommonTranslations { get; set; }
public List<ParseJsonError> ParseJsonErrors { get; set; } public List<ParseJsonError> ParseJsonErrors { get; set; }
public static string ConvertPathToOS { get; private set; } public static string ConvertPathToOS { get; private set; }
public List<string> ForbiddenElements { get { return new List<string>() { "ONLYOFFICE", "DOCSPACE" }; } } public List<string> ForbiddenElements { get { return new List<string>() { "ONLYOFFICE", "DOCSPACE" }; } }
//public List<JsonEncodingError> WrongEncodingJsonErrors { get; set; } public List<string> SkipForbiddenKeys = new List<string> { "OrganizationName", "ProductName", "ProductEditorsName" };
//public List<JsonEncodingError> WrongEncodingJsonErrors { get; set; }
private static readonly string _md5ExcludesPath = Path.GetFullPath(Utils.ConvertPathToOS("../../../md5-excludes.json")); private static readonly string _md5ExcludesPath = Path.GetFullPath(Utils.ConvertPathToOS("../../../md5-excludes.json"));
private static readonly string _spellCheckCommonExcludesPath = Path.GetFullPath(Utils.ConvertPathToOS("../../../spellcheck-excludes-common.json")); private static readonly string _spellCheckCommonExcludesPath = Path.GetFullPath(Utils.ConvertPathToOS("../../../spellcheck-excludes-common.json"));
private static readonly string _spellCheckExcludesPath = Path.GetFullPath(Utils.ConvertPathToOS("../../../spellcheck-excludes.json")); private static readonly string _spellCheckExcludesPath = Path.GetFullPath(Utils.ConvertPathToOS("../../../spellcheck-excludes.json"));
@ -104,7 +105,7 @@ public class LocalesTest
[OneTimeSetUp] [OneTimeSetUp]
public void Setup() public void Setup()
{ {
ParseJsonErrors = new List<ParseJsonError>(); ParseJsonErrors = new List<ParseJsonError>();
//WrongEncodingJsonErrors = new List<JsonEncodingError>(); //WrongEncodingJsonErrors = new List<JsonEncodingError>();
@ -357,14 +358,14 @@ public class LocalesTest
TestContext.Progress.WriteLine($"Found CommonTranslations = {CommonTranslations.Count()}. First path is '{CommonTranslations.FirstOrDefault()?.Path}'"); TestContext.Progress.WriteLine($"Found CommonTranslations = {CommonTranslations.Count()}. First path is '{CommonTranslations.FirstOrDefault()?.Path}'");
TestContext.Progress.WriteLine($"Found Md5Excludes = {Md5Excludes.Count} Path to file '{_md5ExcludesPath}'"); TestContext.Progress.WriteLine($"Found Md5Excludes = {Md5Excludes.Count} Path to file '{_md5ExcludesPath}'");
TestContext.Progress.WriteLine($"Found SpellCheckCommonExcludes = {SpellCheckCommonExcludes.Count} Path to file '{_spellCheckCommonExcludesPath}'"); TestContext.Progress.WriteLine($"Found SpellCheckCommonExcludes = {SpellCheckCommonExcludes.Count} Path to file '{_spellCheckCommonExcludesPath}'");
TestContext.Progress.WriteLine($"Save spell check excludes = {Save} Path to file '{_spellCheckExcludesPath}'"); TestContext.Progress.WriteLine($"Save spell check excludes = {Save} Path to file '{_spellCheckExcludesPath}'");
} }
[Test, Order(1)] [Test, Order(1)]
[Category("Locales")] [Category("Locales")]
public void LanguageTranslatedPercentTest() public void LanguageTranslatedPercentTest()
@ -499,7 +500,7 @@ public class LocalesTest
.ToList(); .ToList();
Assert.AreEqual(0, duplicates.Count, string.Join(", ", duplicates.Select(d => JObject.FromObject(d).ToString()))); Assert.AreEqual(0, duplicates.Count, string.Join(", ", duplicates.Select(d => JObject.FromObject(d).ToString())));
} }
[Test, Order(6)] [Test, Order(6)]
[Category("Locales")] [Category("Locales")]
@ -514,10 +515,10 @@ public class LocalesTest
.Where(f => !f.Path.Contains("Banner.js")) // skip Banner.js (translations from firebase) .Where(f => !f.Path.Contains("Banner.js")) // skip Banner.js (translations from firebase)
.SelectMany(j => j.TranslationKeys) .SelectMany(j => j.TranslationKeys)
.Select(k => k.Substring(k.IndexOf(":") + 1)) .Select(k => k.Substring(k.IndexOf(":") + 1))
.Distinct(); .Distinct();
//var foo = JavaScriptFiles //var foo = JavaScriptFiles
// .Where(f => !f.Path.Contains("Banner.js")) // .Where(f => !f.Path.Contains("Banner.js"))
// .Where(t => t.TranslationKeys.Any(k => k == "foo")).FirstOrDefault(); // .Where(t => t.TranslationKeys.Any(k => k == "foo")).FirstOrDefault();
var notFoundJsKeys = allJsTranslationKeys.Except(allEnKeys); var notFoundJsKeys = allJsTranslationKeys.Except(allEnKeys);
@ -525,8 +526,8 @@ public class LocalesTest
Assert.AreEqual(0, notFoundJsKeys.Count(), Assert.AreEqual(0, notFoundJsKeys.Count(),
"Some i18n-keys are not exist in translations in 'en' language: Keys:\r\n{0}", "Some i18n-keys are not exist in translations in 'en' language: Keys:\r\n{0}",
string.Join("\r\n", notFoundJsKeys)); string.Join("\r\n", notFoundJsKeys));
} }
[Test, Order(7)] [Test, Order(7)]
[Category("Locales")] [Category("Locales")]
public void DublicatesFilesByMD5HashTest() public void DublicatesFilesByMD5HashTest()
@ -541,8 +542,8 @@ public class LocalesTest
.ToList(); .ToList();
Assert.AreEqual(0, duplicatesByMD5.Count, "Dublicates by MD5 hash:\r\n" + string.Join("\r\n", duplicatesByMD5.Select(d => $"\r\nMD5='{d.Key}':\r\n{string.Join("\r\n", d.Paths.Select(p => p))}'"))); Assert.AreEqual(0, duplicatesByMD5.Count, "Dublicates by MD5 hash:\r\n" + string.Join("\r\n", duplicatesByMD5.Select(d => $"\r\nMD5='{d.Key}':\r\n{string.Join("\r\n", d.Paths.Select(p => p))}'")));
} }
[Test, Order(8)] [Test, Order(8)]
[Category("Locales")] [Category("Locales")]
public void UselessTranslationKeysTest() public void UselessTranslationKeysTest()
@ -627,8 +628,8 @@ public class LocalesTest
{ {
Language = g.Key, Language = g.Key,
TranslationsWithVariables = g.ToList() TranslationsWithVariables = g.ToList()
.SelectMany(t => t.Translations.Select(k => new TranslationItem($"{t.FileName}:{k.Key}", k.Value))) .SelectMany(t => t.Translations.Select(k => new TranslationItem($"{t.FileName}:{k.Key}", k.Value)))
//.Where(k => k.Value.IndexOf("{{") != -1) //.Where(k => k.Value.IndexOf("{{") != -1)
.Select(t => new .Select(t => new
{ {
t.Key, t.Key,
@ -654,12 +655,12 @@ public class LocalesTest
var i = 0; var i = 0;
var errorsCount = 0; var errorsCount = 0;
foreach (var enKeyWithVariables in enWithVariables) foreach (var enKeyWithVariables in enWithVariables)
{ {
foreach (var lng in otherLanguagesWithVariables) foreach (var lng in otherLanguagesWithVariables)
{ {
var lngKey = lng.TranslationsWithVariables var lngKey = lng.TranslationsWithVariables
.Where(t => t.Key == enKeyWithVariables.Key) .Where(t => t.Key == enKeyWithVariables.Key)
.FirstOrDefault(); .FirstOrDefault();
if (lngKey == null) if (lngKey == null)
@ -671,8 +672,8 @@ public class LocalesTest
} }
if (enKeyWithVariables.Variables.Count != lngKey.Variables.Count) if (enKeyWithVariables.Variables.Count != lngKey.Variables.Count)
{ {
// wrong // wrong
message += $"{++i}. lng='{lng.Language}' key='{lngKey.Key}' has less variables then 'en' language have " + message += $"{++i}. lng='{lng.Language}' key='{lngKey.Key}' has less variables then 'en' language have " +
$"(en={enKeyWithVariables.Variables.Count}|{lng.Language}={lngKey.Variables.Count})\r\n" + $"(en={enKeyWithVariables.Variables.Count}|{lng.Language}={lngKey.Variables.Count})\r\n" +
$"'en': '{enKeyWithVariables.Value}'\r\n'{lng.Language}': '{lngKey.Value}'\r\n\r\n"; $"'en': '{enKeyWithVariables.Value}'\r\n'{lng.Language}': '{lngKey.Value}'\r\n\r\n";
@ -680,10 +681,10 @@ public class LocalesTest
} }
if (!lngKey.Variables.All(v => enKeyWithVariables.Variables.Contains(v))) if (!lngKey.Variables.All(v => enKeyWithVariables.Variables.Contains(v)))
{ {
// wrong // wrong
message += $"{++i}. lng='{lng.Language}' key='{lngKey.Key}' has not equals variables of 'en' language have \r\n" + message += $"{++i}. lng='{lng.Language}' key='{lngKey.Key}' has not equals variables of 'en' language have \r\n" +
$"'{enKeyWithVariables.Value}' Variables=[{string.Join(",", enKeyWithVariables.Variables)}]\r\n" + $"'{enKeyWithVariables.Value}' Variables=[{string.Join(",", enKeyWithVariables.Variables)}]\r\n" +
$"'{lngKey.Value}' Variables=[{string.Join(",", lngKey.Variables)}]\r\n\r\n"; $"'{lngKey.Value}' Variables=[{string.Join(",", lngKey.Variables)}]\r\n\r\n";
errorsCount++; errorsCount++;
} }
@ -708,8 +709,8 @@ public class LocalesTest
{ {
Language = g.Key, Language = g.Key,
TranslationsWithTags = g.ToList() TranslationsWithTags = g.ToList()
.SelectMany(t => t.Translations) .SelectMany(t => t.Translations)
//.Where(k => k.Value.IndexOf("<") != -1) //.Where(k => k.Value.IndexOf("<") != -1)
.Select(t => new .Select(t => new
{ {
t.Key, t.Key,
@ -735,22 +736,22 @@ public class LocalesTest
var i = 0; var i = 0;
var errorsCount = 0; var errorsCount = 0;
foreach (var enKeyWithTags in enWithTags) foreach (var enKeyWithTags in enWithTags)
{ {
foreach (var lng in otherLanguagesWithTags) foreach (var lng in otherLanguagesWithTags)
{ {
var lngKey = lng.TranslationsWithTags var lngKey = lng.TranslationsWithTags
.Where(t => t.Key == enKeyWithTags.Key) .Where(t => t.Key == enKeyWithTags.Key)
.FirstOrDefault(); .FirstOrDefault();
if (lngKey == null) if (lngKey == null)
{ {
// wrong // wrong
//message += $"{++i}. lng='{lng.Language}' key='{enKeyWithTags.Key}' not found\r\n\r\n"; //message += $"{++i}. lng='{lng.Language}' key='{enKeyWithTags.Key}' not found\r\n\r\n";
//errorsCount++; //errorsCount++;
continue; continue;
} }
if (enKeyWithTags.Tags.Count != lngKey.Tags.Count) if (enKeyWithTags.Tags.Count != lngKey.Tags.Count)
{ {
// wrong // wrong
@ -758,8 +759,8 @@ public class LocalesTest
$"(en={enKeyWithTags.Tags.Count}|{lng.Language}={lngKey.Tags.Count})\r\n" + $"(en={enKeyWithTags.Tags.Count}|{lng.Language}={lngKey.Tags.Count})\r\n" +
$"'en': '{enKeyWithTags.Value}'\r\n'{lng.Language}': '{lngKey.Value}'\r\n\r\n"; $"'en': '{enKeyWithTags.Value}'\r\n'{lng.Language}': '{lngKey.Value}'\r\n\r\n";
errorsCount++; errorsCount++;
} }
if (!lngKey.Tags.All(v => enKeyWithTags.Tags.Contains(v))) if (!lngKey.Tags.All(v => enKeyWithTags.Tags.Contains(v)))
{ {
// wrong // wrong
@ -767,9 +768,9 @@ public class LocalesTest
$"'{enKeyWithTags.Value}' Tags=[{string.Join(",", enKeyWithTags.Tags)}]\r\n" + $"'{enKeyWithTags.Value}' Tags=[{string.Join(",", enKeyWithTags.Tags)}]\r\n" +
$"'{lngKey.Value}' Tags=[{string.Join(",", lngKey.Tags)}]\r\n\r\n"; $"'{lngKey.Value}' Tags=[{string.Join(",", lngKey.Tags)}]\r\n\r\n";
errorsCount++; errorsCount++;
} }
} }
} }
/*foreach (var lng in otherLanguagesWithTags) /*foreach (var lng in otherLanguagesWithTags)
@ -809,19 +810,18 @@ public class LocalesTest
}*/ }*/
Assert.AreEqual(0, errorsCount, message); Assert.AreEqual(0, errorsCount, message);
} }
[Test, Order(13)] [Test, Order(13)]
[Category("Locales")] [Category("Locales")]
public void ForbiddenValueElementsTest() public void ForbiddenValueElementsTest()
{ {
var message = $"Next keys have forbidden values `{string.Join(",", ForbiddenElements)}`:\r\n\r\n"; var message = $"Next keys have forbidden values `{string.Join(",", ForbiddenElements)}`:\r\n\r\n";
var exists = false; var exists = false;
var i = 0; var i = 0;
foreach (var module in ModuleFolders) foreach (var module in ModuleFolders)
{ {
if (module.AvailableLanguages == null) if (module.AvailableLanguages == null)
@ -844,38 +844,41 @@ public class LocalesTest
message += string.Join("\r\n", keys) + "\r\n\r\n"; message += string.Join("\r\n", keys) + "\r\n\r\n";
} }
} }
foreach (var lng in CommonTranslations) foreach (var lng in CommonTranslations)
{ {
var translationItems = lng.Translations.Where(f => ForbiddenElements.Any(elem => f.Value.ToUpper().Contains(elem))).ToList(); var translationItems = lng.Translations
.Where(elem => !SkipForbiddenKeys.Exists(k => k == elem.Key))
if (!translationItems.Any()) .Where(f => ForbiddenElements.Any(elem => f.Value.ToUpper().Contains(elem)))
continue; .ToList();
exists = true; if (!translationItems.Any())
continue;
message += $"{++i}. Language '{lng.Language}' (Count: {translationItems.Count}). Path '{lng.Path}' " +
$"Keys:\r\n\r\n"; exists = true;
var keys = translationItems.Select(t => t.Key).ToList(); message += $"{++i}. Language '{lng.Language}' (Count: {translationItems.Count}). Path '{lng.Path}' " +
$"Keys:\r\n\r\n";
var keys = translationItems.Select(t => t.Key).ToList();
message += string.Join("\r\n", keys) + "\r\n\r\n"; message += string.Join("\r\n", keys) + "\r\n\r\n";
} }
Assert.AreEqual(false, exists, message); Assert.AreEqual(false, exists, message);
} }
[Test, Order(14)] [Test, Order(14)]
[Category("Locales")] [Category("Locales")]
public void ForbiddenKeysElementsTest() public void ForbiddenKeysElementsTest()
{ {
var message = $"Next keys have forbidden elements in names `{string.Join(",", ForbiddenElements)}`:\r\n\r\n"; var message = $"Next keys have forbidden elements in names `{string.Join(",", ForbiddenElements)}`:\r\n\r\n";
var exists = false; var exists = false;
var i = 0; var i = 0;
foreach (var module in ModuleFolders) foreach (var module in ModuleFolders)
{ {
if (module.AvailableLanguages == null) if (module.AvailableLanguages == null)
@ -883,9 +886,8 @@ public class LocalesTest
foreach (var lng in module.AvailableLanguages) foreach (var lng in module.AvailableLanguages)
{ {
var translationItems = lng.Translations.Where(f => ForbiddenElements.Any(elem => f.Key.ToUpper().Contains(elem))).ToList(); var translationItems = lng.Translations.Where(f => ForbiddenElements.Any(elem => f.Key.ToUpper().Contains(elem))).ToList();
if (!translationItems.Any()) if (!translationItems.Any())
continue; continue;
@ -899,28 +901,31 @@ public class LocalesTest
message += string.Join("\r\n", keys) + "\r\n\r\n"; message += string.Join("\r\n", keys) + "\r\n\r\n";
} }
} }
foreach (var lng in CommonTranslations) foreach (var lng in CommonTranslations)
{ {
var translationItems = lng.Translations.Where(f => ForbiddenElements.Any(elem => f.Key.ToUpper().Contains(elem))).ToList(); var translationItems = lng.Translations
.Where(elem => !SkipForbiddenKeys.Exists(k => k == elem.Key))
if (!translationItems.Any()) .Where(f => ForbiddenElements.Any(elem => f.Key.ToUpper().Contains(elem)))
continue; .ToList();
exists = true; if (!translationItems.Any())
continue;
message += $"{++i}. Language '{lng.Language}' (Count: {translationItems.Count}). Path '{lng.Path}' " +
$"Keys:\r\n\r\n"; exists = true;
var keys = translationItems.Select(t => t.Key).ToList(); message += $"{++i}. Language '{lng.Language}' (Count: {translationItems.Count}). Path '{lng.Path}' " +
$"Keys:\r\n\r\n";
var keys = translationItems.Select(t => t.Key).ToList();
message += string.Join("\r\n", keys) + "\r\n\r\n"; message += string.Join("\r\n", keys) + "\r\n\r\n";
} }
Assert.AreEqual(false, exists, message); Assert.AreEqual(false, exists, message);
} }
[Test, Order(15)] [Test, Order(15)]
[Category("Locales")] [Category("Locales")]
public void EmptyValueKeysTest() public void EmptyValueKeysTest()
@ -1023,8 +1028,8 @@ public class LocalesTest
} }
Assert.AreEqual(false, exists, message); Assert.AreEqual(false, exists, message);
} }
[Test, Order(16)] [Test, Order(16)]
[Category("Locales")] [Category("Locales")]
public void NotTranslatedKeysTest() public void NotTranslatedKeysTest()
@ -1070,8 +1075,8 @@ public class LocalesTest
} }
Assert.AreEqual(false, exists, message); Assert.AreEqual(false, exists, message);
} }
[Test, Order(17)] [Test, Order(17)]
[Category("Locales")] [Category("Locales")]
public void NotTranslatedCommonKeysTest() public void NotTranslatedCommonKeysTest()
@ -1113,7 +1118,7 @@ public class LocalesTest
[Test, Order(18)] [Test, Order(18)]
[Category("Locales")] [Category("Locales")]
public void NotAllLanguageTranslatedTest() public void NotAllLanguageTranslatedTest()
{ {
var groupedByLng = TranslationFiles var groupedByLng = TranslationFiles
.GroupBy(t => t.Language) .GroupBy(t => t.Language)
.Select(grp => new { Lng = grp.Key, Count = grp.Count(), Files = grp.ToList() }) .Select(grp => new { Lng = grp.Key, Count = grp.Count(), Files = grp.ToList() })
@ -1165,8 +1170,8 @@ public class LocalesTest
} }
Assert.AreEqual(0, incompleteList.Count, message); Assert.AreEqual(0, incompleteList.Count, message);
} }
[Test, Order(19)] [Test, Order(19)]
[Category("SpellCheck")] [Category("SpellCheck")]
public void SpellCheckTest() public void SpellCheckTest()
@ -1207,43 +1212,43 @@ public class LocalesTest
if (result.HasProblems) if (result.HasProblems)
{ {
var incorrectWords = result.SpellIssues var incorrectWords = result.SpellIssues
.Where(t => !SpellCheckCommonExcludes .Where(t => !SpellCheckCommonExcludes
.Exists(e => e.Equals(t.Word, StringComparison.InvariantCultureIgnoreCase))) .Exists(e => e.Equals(t.Word, StringComparison.InvariantCultureIgnoreCase)))
.Select(issue => $"'{issue.Word}' " + .Select(issue => $"'{issue.Word}' " +
$"Suggestion: '{issue.Suggestions.FirstOrDefault()}'") $"Suggestion: '{issue.Suggestions.FirstOrDefault()}'")
.ToList(); .ToList();
if (!incorrectWords.Any()) if (!incorrectWords.Any())
continue; continue;
message += $"{++i}. lng='{group.Language}' file='{g.FilePath}'\r\nkey='{item.Key}' " + message += $"{++i}. lng='{group.Language}' file='{g.FilePath}'\r\nkey='{item.Key}' " +
$"value='{item.Value}'\r\nIncorrect words:\r\n" + $"value='{item.Value}'\r\nIncorrect words:\r\n" +
$"{string.Join("\r\n", incorrectWords)}\r\n\r\n"; $"{string.Join("\r\n", incorrectWords)}\r\n\r\n";
errorsCount++; errorsCount++;
if (Save) if (Save)
{ {
foreach (var word in result.SpellIssues foreach (var word in result.SpellIssues
.Where(issue => issue.Suggestions.Any()) .Where(issue => issue.Suggestions.Any())
.Select(issue => issue.Word)) .Select(issue => issue.Word))
{ {
if (!spellCheckExclude.Excludes.Contains(word)) if (!spellCheckExclude.Excludes.Contains(word))
{ {
spellCheckExclude.Excludes.Add(word); spellCheckExclude.Excludes.Add(word);
} }
} }
} }
} }
} }
} }
} }
if (Save) if (Save)
{ {
spellCheckExclude.Excludes.Sort(); spellCheckExclude.Excludes.Sort();
list.Add(spellCheckExclude); list.Add(spellCheckExclude);
} }
} }
catch (NotSupportedException) catch (NotSupportedException)
@ -1253,135 +1258,135 @@ public class LocalesTest
} }
} }
if (Save) if (Save)
{ {
string json = JsonConvert.SerializeObject(list, Formatting.Indented); string json = JsonConvert.SerializeObject(list, Formatting.Indented);
File.WriteAllText(_spellCheckExcludesPath, json, Encoding.UTF8); File.WriteAllText(_spellCheckExcludesPath, json, Encoding.UTF8);
TestContext.Progress.WriteLine($"File spellcheck-excludes.json has been saved to '{_spellCheckExcludesPath}'"); TestContext.Progress.WriteLine($"File spellcheck-excludes.json has been saved to '{_spellCheckExcludesPath}'");
} }
Assert.AreEqual(0, errorsCount, message); Assert.AreEqual(0, errorsCount, message);
} }
/* [Test, Order(17)] /* [Test, Order(17)]
[Category("Locales")] [Category("Locales")]
public void UselessModuleTranslationKeysTest() public void UselessModuleTranslationKeysTest()
{ {
var notFoundi18nKeys = new List<KeyValuePair<string, List<string>>>(); var notFoundi18nKeys = new List<KeyValuePair<string, List<string>>>();
var message = $"Some i18n-keys are not found in Module or Common translations: \r\nKeys: \r\n\r\n"; var message = $"Some i18n-keys are not found in Module or Common translations: \r\nKeys: \r\n\r\n";
var index = 0; var index = 0;
for (int i = 0; i < ModuleFolders.Count; i++) for (int i = 0; i < ModuleFolders.Count; i++)
{ {
var module = ModuleFolders[i]; var module = ModuleFolders[i];
if (module.AppliedJsTranslationKeys == null && module.AvailableLanguages != null) if (module.AppliedJsTranslationKeys == null && module.AvailableLanguages != null)
{ {
message += $"{++index}. 'ANY LANGUAGES' '{module.Path}' NOT USED\r\n"; message += $"{++index}. 'ANY LANGUAGES' '{module.Path}' NOT USED\r\n";
var list = module.AvailableLanguages var list = module.AvailableLanguages
.SelectMany(l => l.Translations.Select(t => t.Key).ToList()) .SelectMany(l => l.Translations.Select(t => t.Key).ToList())
.ToList(); .ToList();
notFoundi18nKeys.Add(new KeyValuePair<string, List<string>>("ANY LANGUAGES", list)); notFoundi18nKeys.Add(new KeyValuePair<string, List<string>>("ANY LANGUAGES", list));
continue; continue;
} }
var exepts = new List<string> { "Error", "Done", "Warning", "Alert", "Info" }; var exepts = new List<string> { "Error", "Done", "Warning", "Alert", "Info" };
var notCommonKeys = module.AppliedJsTranslationKeys var notCommonKeys = module.AppliedJsTranslationKeys
.Except(exepts) .Except(exepts)
.Where(k => !k.StartsWith("Common:")) .Where(k => !k.StartsWith("Common:"))
.OrderBy(t => t) .OrderBy(t => t)
.ToList(); .ToList();
var onlyCommonKeys = module.AppliedJsTranslationKeys var onlyCommonKeys = module.AppliedJsTranslationKeys
.Except(notCommonKeys) .Except(notCommonKeys)
.Select(k => k.Replace("Common:", "")) .Select(k => k.Replace("Common:", ""))
.OrderBy(t => t) .OrderBy(t => t)
.ToList(); .ToList();
notCommonKeys = notCommonKeys.Select(k => k.Substring(k.IndexOf(":") + 1)).ToList(); notCommonKeys = notCommonKeys.Select(k => k.Substring(k.IndexOf(":") + 1)).ToList();
if (onlyCommonKeys.Any()) if (onlyCommonKeys.Any())
{ {
foreach (var lng in CommonTranslations) foreach (var lng in CommonTranslations)
{ {
var list = onlyCommonKeys var list = onlyCommonKeys
.Except(lng.Translations.Select(t => t.Key)) .Except(lng.Translations.Select(t => t.Key))
.ToList(); .ToList();
if (!list.Any()) if (!list.Any())
continue; continue;
message += $"{++index}. '{lng.Language}' '{module.Path}' \r\n {string.Join("\r\n", list)} \r\n"; message += $"{++index}. '{lng.Language}' '{module.Path}' \r\n {string.Join("\r\n", list)} \r\n";
notFoundi18nKeys.Add(new KeyValuePair<string, List<string>>(lng.Language, list)); notFoundi18nKeys.Add(new KeyValuePair<string, List<string>>(lng.Language, list));
} }
} }
if (module.AvailableLanguages == null) if (module.AvailableLanguages == null)
{ {
if (notCommonKeys.Any()) if (notCommonKeys.Any())
{ {
var commonEnKeys = CommonTranslations.First(c => c.Language == "en").Translations.Select(t => t.Key).ToList(); var commonEnKeys = CommonTranslations.First(c => c.Language == "en").Translations.Select(t => t.Key).ToList();
var list = notCommonKeys var list = notCommonKeys
.Except(commonEnKeys.Select(k => k)) .Except(commonEnKeys.Select(k => k))
.ToList(); .ToList();
if (list.Any()) if (list.Any())
{ {
message += $"{++index}. 'ANY LANGUAGES' '{module.Path}' \r\n {string.Join("\r\n", list)} \r\n"; message += $"{++index}. 'ANY LANGUAGES' '{module.Path}' \r\n {string.Join("\r\n", list)} \r\n";
notFoundi18nKeys.Add(new KeyValuePair<string, List<string>>("ANY LANGUAGES", list)); notFoundi18nKeys.Add(new KeyValuePair<string, List<string>>("ANY LANGUAGES", list));
} }
} }
continue; continue;
} }
foreach (var lng in module.AvailableLanguages) foreach (var lng in module.AvailableLanguages)
{ {
var list = lng.Translations var list = lng.Translations
.Select(t => t.Key) .Select(t => t.Key)
.Except(notCommonKeys) .Except(notCommonKeys)
.ToList(); .ToList();
if (!list.Any()) if (!list.Any())
continue; continue;
message += $"{++index}. '{lng.Language}' '{module.Path}' \r\n {string.Join("\r\n", list)} \r\n"; message += $"{++index}. '{lng.Language}' '{module.Path}' \r\n {string.Join("\r\n", list)} \r\n";
notFoundi18nKeys.Add(new KeyValuePair<string, List<string>>(lng.Language, list)); notFoundi18nKeys.Add(new KeyValuePair<string, List<string>>(lng.Language, list));
} }
} }
Assert.AreEqual(0, notFoundi18nKeys.Count, message); Assert.AreEqual(0, notFoundi18nKeys.Count, message);
}*/ }*/
//[Test] //[Test]
//[Category("Locales")] //[Category("Locales")]
//public void TranslationsEncodingTest() //public void TranslationsEncodingTest()
//{ //{
// /*//Convert to UTF-8 // /*//Convert to UTF-8
// foreach (var issue in WrongEncodingJsonErrors) // foreach (var issue in WrongEncodingJsonErrors)
// { // {
// if (issue.DetectionDetail.Encoding == null) // if (issue.DetectionDetail.Encoding == null)
// continue; // continue;
// ConvertFileEncoding(issue.Path, issue.Path, issue.DetectionDetail.Encoding, Encoding.UTF8); // ConvertFileEncoding(issue.Path, issue.Path, issue.DetectionDetail.Encoding, Encoding.UTF8);
// }*/ // }*/
// var message = $"Next files have encoding issues:\r\n\r\n"; // var message = $"Next files have encoding issues:\r\n\r\n";
// Assert.AreEqual(0, WrongEncodingJsonErrors.Count, // Assert.AreEqual(0, WrongEncodingJsonErrors.Count,
// message + string.Join("\r\n", WrongEncodingJsonErrors // message + string.Join("\r\n", WrongEncodingJsonErrors
// .Select(e => $"File path = '{e.Path}' potentially wrong file encoding: {e.DetectionDetail.EncodingName}"))); // .Select(e => $"File path = '{e.Path}' potentially wrong file encoding: {e.DetectionDetail.EncodingName}")));
//} //}
/*[Test] /*[Test]
public void TempTest() public void TempTest()
{ {
@ -1468,8 +1473,8 @@ public class LocalesTest
UpdateKeys(lng.Path, newKeys); UpdateKeys(lng.Path, newKeys);
} }
}*/ }*/
public static void SaveNotFoundKeys(string pathToJson, List<string> newKeys) public static void SaveNotFoundKeys(string pathToJson, List<string> newKeys)
{ {
if (!File.Exists(pathToJson)) if (!File.Exists(pathToJson))
@ -1488,8 +1493,8 @@ public class LocalesTest
var sortedJsonString = JsonConvert.SerializeObject(result, Formatting.Indented); var sortedJsonString = JsonConvert.SerializeObject(result, Formatting.Indented);
File.WriteAllText(pathToJson, sortedJsonString, Encoding.UTF8); File.WriteAllText(pathToJson, sortedJsonString, Encoding.UTF8);
} }
public static void SaveNotFoundLanguage(string existJsonPath, string notExistJsonPath) public static void SaveNotFoundLanguage(string existJsonPath, string notExistJsonPath)
{ {
if (!File.Exists(existJsonPath) || File.Exists(notExistJsonPath)) if (!File.Exists(existJsonPath) || File.Exists(notExistJsonPath))
@ -1513,8 +1518,8 @@ public class LocalesTest
Directory.CreateDirectory(fullPathOnly); Directory.CreateDirectory(fullPathOnly);
File.WriteAllText(notExistJsonPath, sortedJsonString, Encoding.UTF8); File.WriteAllText(notExistJsonPath, sortedJsonString, Encoding.UTF8);
} }
public static void UpdateKeys(string pathToJson, List<TranslationItem> newKeys) public static void UpdateKeys(string pathToJson, List<TranslationItem> newKeys)
{ {
if (!File.Exists(pathToJson) || !newKeys.Any()) if (!File.Exists(pathToJson) || !newKeys.Any())
@ -1608,8 +1613,8 @@ public class LocalesTest
var sortedJsonString = JsonConvert.SerializeObject(result, Formatting.Indented); var sortedJsonString = JsonConvert.SerializeObject(result, Formatting.Indented);
File.WriteAllText(pathToJson, sortedJsonString, Encoding.UTF8); File.WriteAllText(pathToJson, sortedJsonString, Encoding.UTF8);
} }
public static Tuple<string, string> getPaths(string language) public static Tuple<string, string> getPaths(string language)
{ {
const string dictionariesPath = @"../../../dictionaries"; const string dictionariesPath = @"../../../dictionaries";
@ -1630,84 +1635,84 @@ public class LocalesTest
var affPath = Utils.ConvertPathToOS(Path.Combine(path, language, $"{language}.aff")); var affPath = Utils.ConvertPathToOS(Path.Combine(path, language, $"{language}.aff"));
return new Tuple<string, string>(dicPath, affPath); return new Tuple<string, string>(dicPath, affPath);
} }
public static void ConvertFileEncoding(string sourcePath, string destPath, Encoding sourceEncoding, Encoding destEncoding) public static void ConvertFileEncoding(string sourcePath, string destPath, Encoding sourceEncoding, Encoding destEncoding)
{ {
// If the destination's parent doesn't exist, create it. // If the destination's parent doesn't exist, create it.
var parent = Path.GetDirectoryName(Path.GetFullPath(destPath)); var parent = Path.GetDirectoryName(Path.GetFullPath(destPath));
if (!Directory.Exists(parent)) if (!Directory.Exists(parent))
{ {
Directory.CreateDirectory(parent); Directory.CreateDirectory(parent);
} }
// If the source and destination encodings are the same, just copy the file. // If the source and destination encodings are the same, just copy the file.
if (sourceEncoding == destEncoding) if (sourceEncoding == destEncoding)
{ {
File.Copy(sourcePath, destPath, true); File.Copy(sourcePath, destPath, true);
return; return;
} }
// Convert the file. // Convert the file.
string tempName = null; string tempName = null;
try try
{ {
tempName = Path.GetTempFileName(); tempName = Path.GetTempFileName();
using (StreamReader sr = new StreamReader(sourcePath, sourceEncoding, false)) using (StreamReader sr = new StreamReader(sourcePath, sourceEncoding, false))
{ {
using (StreamWriter sw = new StreamWriter(tempName, false, destEncoding)) using (StreamWriter sw = new StreamWriter(tempName, false, destEncoding))
{ {
int charsRead; int charsRead;
char[] buffer = new char[128 * 1024]; char[] buffer = new char[128 * 1024];
while ((charsRead = sr.ReadBlock(buffer, 0, buffer.Length)) > 0) while ((charsRead = sr.ReadBlock(buffer, 0, buffer.Length)) > 0)
{ {
sw.Write(buffer, 0, charsRead); sw.Write(buffer, 0, charsRead);
} }
} }
} }
File.Delete(destPath); File.Delete(destPath);
File.Move(tempName, destPath); File.Move(tempName, destPath);
} }
finally finally
{ {
File.Delete(tempName); File.Delete(tempName);
} }
} }
/* [Test] /* [Test]
public void MoveKeysToCommon() public void MoveKeysToCommon()
{ {
var findKeys = new List<string> { var findKeys = new List<string> {
"SharingPanel:CustomFilter", "SharingPanel:CustomFilter",
"SharingPanel:ReadOnly", "SharingPanel:ReadOnly",
"SharingPanel:DenyAccess", "SharingPanel:DenyAccess",
"SharingPanel:Comment", "SharingPanel:Comment",
"SharingPanel:ShareVia" "SharingPanel:ShareVia"
}; };
//var findKeys = new List<string> { //var findKeys = new List<string> {
// "Translations:DownloadApps", // "Translations:DownloadApps",
//}; //};
foreach (var findKey in findKeys) foreach (var findKey in findKeys)
{ {
var splitted = findKey.Split(":"); var splitted = findKey.Split(":");
var file = splitted[0]; var file = splitted[0];
var key = splitted[1]; var key = splitted[1];
var tFiles = TranslationFiles.Where(t => t.FileName.Equals($"{file}.json", StringComparison.InvariantCultureIgnoreCase)); var tFiles = TranslationFiles.Where(t => t.FileName.Equals($"{file}.json", StringComparison.InvariantCultureIgnoreCase));
foreach (var tFile in tFiles) foreach (var tFile in tFiles)
{ {
var tKeys = tFile.Translations.Where(t => t.Key == key); var tKeys = tFile.Translations.Where(t => t.Key == key);
foreach (var tKey in tKeys) foreach (var tKey in tKeys)
{ {
var commonPath = Utils.ConvertPathToOS(Path.Combine(BasePath, "public/locales", tFile.Language, "Common.json")); var commonPath = Utils.ConvertPathToOS(Path.Combine(BasePath, "public/locales", tFile.Language, "Common.json"));
AddKeyValue(commonPath, tKey.Key, tKey.Value); AddKeyValue(commonPath, tKey.Key, tKey.Value);
RemoveKey(tFile.FilePath, key); RemoveKey(tFile.FilePath, key);
} }
} }
} }
} */ } */
} }