diff --git a/common/ASC.Api.Core/Auth/ConfirmAuthHandler.cs b/common/ASC.Api.Core/Auth/ConfirmAuthHandler.cs index 9b4d611e27..29f1cba800 100644 --- a/common/ASC.Api.Core/Auth/ConfirmAuthHandler.cs +++ b/common/ASC.Api.Core/Auth/ConfirmAuthHandler.cs @@ -53,7 +53,7 @@ namespace ASC.Api.Core.Auth { return SecurityContext.IsAuthenticated ? Task.FromResult(AuthenticateResult.Success(new AuthenticationTicket(Context.User, new AuthenticationProperties(), Scheme.Name))) - : Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(HttpStatusCode.Unauthorized.ToString()))); + : Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(nameof(HttpStatusCode.Unauthorized)))); } EmailValidationKeyProvider.ValidationResult checkKeyResult; @@ -105,14 +105,14 @@ namespace ASC.Api.Core.Auth var result = checkKeyResult switch { EmailValidationKeyProvider.ValidationResult.Ok => AuthenticateResult.Success(new AuthenticationTicket(Context.User, new AuthenticationProperties(), Scheme.Name)), - _ => AuthenticateResult.Fail(new AuthenticationException(HttpStatusCode.Unauthorized.ToString())) + _ => AuthenticateResult.Fail(new AuthenticationException(nameof(HttpStatusCode.Unauthorized))) }; return Task.FromResult(result); } } - public class ConfirmAuthHandlerExtension + public static class ConfirmAuthHandlerExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.Api.Core/Auth/CookieAuthHandler.cs b/common/ASC.Api.Core/Auth/CookieAuthHandler.cs index 1316ab3185..13590079a6 100644 --- a/common/ASC.Api.Core/Auth/CookieAuthHandler.cs +++ b/common/ASC.Api.Core/Auth/CookieAuthHandler.cs @@ -50,7 +50,7 @@ namespace ASC.Api.Core.Auth return Task.FromResult( result ? AuthenticateResult.Success(new AuthenticationTicket(Context.User, new AuthenticationProperties(), Scheme.Name)) : - AuthenticateResult.Fail(new AuthenticationException(HttpStatusCode.Unauthorized.ToString())) + AuthenticateResult.Fail(new AuthenticationException(nameof(HttpStatusCode.Unauthorized))) ); } } diff --git a/common/ASC.Api.Core/Core/ApiContext.cs b/common/ASC.Api.Core/Core/ApiContext.cs index 62f61ba1ba..09215626e2 100644 --- a/common/ASC.Api.Core/Core/ApiContext.cs +++ b/common/ASC.Api.Core/Core/ApiContext.cs @@ -41,8 +41,8 @@ namespace ASC.Api.Core { private static int MaxCount = 1000; public IHttpContextAccessor HttpContextAccessor { get; set; } - public Tenant tenant; - public Tenant Tenant { get { return tenant ??= TenantManager.GetCurrentTenant(HttpContextAccessor?.HttpContext); } } + private Tenant _tenant; + public Tenant Tenant { get { return _tenant ??= TenantManager.GetCurrentTenant(HttpContextAccessor?.HttpContext); } } public ApiContext(IHttpContextAccessor httpContextAccessor, SecurityContext securityContext, TenantManager tenantManager) { diff --git a/common/ASC.Api.Core/Core/ApiDateTime.cs b/common/ASC.Api.Core/Core/ApiDateTime.cs index 8a4e79495e..a481eec906 100644 --- a/common/ASC.Api.Core/Core/ApiDateTime.cs +++ b/common/ASC.Api.Core/Core/ApiDateTime.cs @@ -37,7 +37,7 @@ using ASC.Core; namespace ASC.Api.Core { [TypeConverter(typeof(ApiDateTimeTypeConverter))] - public class ApiDateTime : IComparable, IComparable + public sealed class ApiDateTime : IComparable, IComparable { internal static readonly string[] Formats = new[] { @@ -88,7 +88,7 @@ namespace ASC.Api.Core public static ApiDateTime Parse(string data, TimeZoneInfo tz, TenantManager tenantManager, TimeZoneConverter timeZoneConverter) { - if (string.IsNullOrEmpty(data)) throw new ArgumentNullException("data"); + if (string.IsNullOrEmpty(data)) throw new ArgumentNullException(nameof(data)); if (data.Length < 7) throw new ArgumentException("invalid date time format"); @@ -97,7 +97,7 @@ namespace ASC.Api.Core { //Parse time var tzOffset = TimeSpan.Zero; - if (offsetPart.Contains(":") && TimeSpan.TryParse(offsetPart.TrimStart('+'), out tzOffset)) + if (offsetPart.Contains(':') && TimeSpan.TryParse(offsetPart.TrimStart('+'), out tzOffset)) { return new ApiDateTime(dateTime, tzOffset); } @@ -251,7 +251,7 @@ namespace ASC.Api.Core { if (obj is null) return false; if (ReferenceEquals(this, obj)) return true; - if (obj.GetType() != typeof(ApiDateTime)) return false; + if (!(obj is ApiDateTime)) return false; return Equals((ApiDateTime)obj); } diff --git a/common/ASC.Api.Core/Core/BaseStartup.cs b/common/ASC.Api.Core/Core/BaseStartup.cs index 165fdf11ea..e2f50f1c1f 100644 --- a/common/ASC.Api.Core/Core/BaseStartup.cs +++ b/common/ASC.Api.Core/Core/BaseStartup.cs @@ -23,7 +23,6 @@ using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Builder; using Microsoft.AspNetCore.Diagnostics.HealthChecks; using Microsoft.AspNetCore.Hosting; -using Microsoft.AspNetCore.Http.Extensions; using Microsoft.AspNetCore.HttpOverrides; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.Authorization; @@ -68,6 +67,7 @@ namespace ASC.Api.Core services.AddCustomHealthCheck(Configuration); services.AddHttpContextAccessor(); services.AddMemoryCache(); + services.AddHttpClient(); if (AddAndUseSession) services.AddSession(); @@ -131,7 +131,7 @@ namespace ASC.Api.Core DIHelper.RegisterProducts(Configuration, HostEnvironment.ContentRootPath); } - var builder = services.AddMvcCore(config => + services.AddMvcCore(config => { config.Conventions.Add(new ControllerNameAttributeConvention()); diff --git a/common/ASC.Api.Core/Core/CustomHealthCheck.cs b/common/ASC.Api.Core/Core/CustomHealthCheck.cs index 57a8990396..29b56aa66d 100644 --- a/common/ASC.Api.Core/Core/CustomHealthCheck.cs +++ b/common/ASC.Api.Core/Core/CustomHealthCheck.cs @@ -24,7 +24,7 @@ namespace ASC.Api.Core.Core var connectionString = configurationExtension.GetConnectionStrings("default"); - if (String.Compare(connectionString.ProviderName, "MySql.Data.MySqlClient") == 0) + if (string.Equals(connectionString.ProviderName, "MySql.Data.MySqlClient")) { hcBuilder.AddMySql(connectionString.ConnectionString, name: "mysqldb", @@ -32,7 +32,7 @@ namespace ASC.Api.Core.Core ); } - if (String.Compare(connectionString.ProviderName, "Npgsql") == 0) + if (string.Equals(connectionString.ProviderName, "Npgsql")) { hcBuilder.AddNpgSql(connectionString.ConnectionString, name: "postgredb", diff --git a/common/ASC.Api.Core/Middleware/ProductSecurityFilter.cs b/common/ASC.Api.Core/Middleware/ProductSecurityFilter.cs index cbc2cd13b1..779a5ea9ab 100644 --- a/common/ASC.Api.Core/Middleware/ProductSecurityFilter.cs +++ b/common/ASC.Api.Core/Middleware/ProductSecurityFilter.cs @@ -103,16 +103,16 @@ namespace ASC.Api.Core.Middleware if (!string.IsNullOrEmpty(url)) { var module = url.Split('/')[0]; - if (products.ContainsKey(module)) + if (products.TryGetValue(module, out var communityProduct)) { - return products[module]; + return communityProduct; } } } - if (products.ContainsKey(name)) + if (products.TryGetValue(name, out var product)) { - return products[name]; + return product; } return default; } diff --git a/common/ASC.Api.Core/Middleware/TenantStatusFilter.cs b/common/ASC.Api.Core/Middleware/TenantStatusFilter.cs index 8eda940670..8a04954c49 100644 --- a/common/ASC.Api.Core/Middleware/TenantStatusFilter.cs +++ b/common/ASC.Api.Core/Middleware/TenantStatusFilter.cs @@ -34,7 +34,7 @@ namespace ASC.Api.Core.Middleware if (tenant == null) { context.Result = new StatusCodeResult((int)HttpStatusCode.NotFound); - log.WarnFormat("Tenant {0} not found", tenant.TenantId); + log.WarnFormat("Current tenant not found"); return; } diff --git a/common/ASC.Api.Core/Model/EmployeeWraperFull.cs b/common/ASC.Api.Core/Model/EmployeeWraperFull.cs index aafc1dd727..ddc5f1095c 100644 --- a/common/ASC.Api.Core/Model/EmployeeWraperFull.cs +++ b/common/ASC.Api.Core/Model/EmployeeWraperFull.cs @@ -262,7 +262,7 @@ namespace ASC.Web.Api.Models { var listAdminModules = userInfo.GetListAdminModules(WebItemSecurity); - if (listAdminModules.Any()) + if (listAdminModules.Count > 0) result.ListAdminModules = listAdminModules; } @@ -283,7 +283,7 @@ namespace ASC.Web.Api.Models } } - if (contacts.Any()) + if (contacts.Count > 0) { employeeWraperFull.Contacts = contacts; } diff --git a/common/ASC.Api.Core/Routing/FormatRoute.cs b/common/ASC.Api.Core/Routing/FormatRoute.cs index c10998e402..d18cc4adbd 100644 --- a/common/ASC.Api.Core/Routing/FormatRoute.cs +++ b/common/ASC.Api.Core/Routing/FormatRoute.cs @@ -10,7 +10,7 @@ namespace ASC.Web.Api.Routing public bool Check { get; set; } public bool DisableFormat { get; set; } - public CustomHttpMethodAttribute(string method, string template = null, bool check = true, int order = 1) + protected CustomHttpMethodAttribute(string method, string template = null, bool check = true, int order = 1) : base(new List() { method }, $"[controller]{(template != null ? $"/{template}" : "")}") { Check = check; diff --git a/common/ASC.Common/Caching/AscCache.cs b/common/ASC.Common/Caching/AscCache.cs index 2a62898ad2..92a461f2e7 100644 --- a/common/ASC.Common/Caching/AscCache.cs +++ b/common/ASC.Common/Caching/AscCache.cs @@ -30,8 +30,6 @@ using System.Linq; using System.Runtime.Caching; using System.Text.RegularExpressions; -using Google.Protobuf; - using Microsoft.Extensions.Caching.Memory; namespace ASC.Common.Caching @@ -55,7 +53,7 @@ namespace ASC.Common.Caching public static void OnClearCache() { - var keys = MemoryCache.Default.Select(r => r.Key).ToList(); + var keys = MemoryCache.Default.Select(r => r.Key); foreach (var k in keys) { @@ -114,7 +112,7 @@ namespace ASC.Common.Caching public void Remove(Regex pattern) { var copy = MemoryCacheKeys.ToDictionary(p => p.Key, p => p.Value); - var keys = copy.Select(p => p.Key).Where(k => pattern.IsMatch(k)).ToArray(); + var keys = copy.Select(p => p.Key).Where(k => pattern.IsMatch(k)); foreach (var key in keys) { diff --git a/common/ASC.Common/Collections/CachedDictionaryBase.cs b/common/ASC.Common/Collections/CachedDictionaryBase.cs index 9f6b15018a..68de00e0df 100644 --- a/common/ASC.Common/Collections/CachedDictionaryBase.cs +++ b/common/ASC.Common/Collections/CachedDictionaryBase.cs @@ -89,7 +89,7 @@ namespace ASC.Collections protected string BuildKey(string key, string rootkey) { - return string.Format("{0}-{1}-{2}", baseKey, rootkey, key); + return $"{baseKey}-{rootkey}-{key}"; } protected abstract object GetObjectFromCache(string fullKey); @@ -106,7 +106,7 @@ namespace ASC.Collections protected virtual bool FitsCondition(object cached) { - return cached != null && cached is T; + return cached is T; } public virtual T Get(string rootkey, string key, Func defaults) diff --git a/common/ASC.Common/Collections/HttpRequestDictionary.cs b/common/ASC.Common/Collections/HttpRequestDictionary.cs index cf8e2b0c4f..9aa3f06475 100644 --- a/common/ASC.Common/Collections/HttpRequestDictionary.cs +++ b/common/ASC.Common/Collections/HttpRequestDictionary.cs @@ -29,7 +29,7 @@ namespace ASC.Collections { public sealed class HttpRequestDictionary : CachedDictionaryBase { - private class CachedItem + private sealed class CachedItem { internal T Value { get; set; } diff --git a/common/ASC.Common/DIHelper.cs b/common/ASC.Common/DIHelper.cs index 4af584677f..f07571420a 100644 --- a/common/ASC.Common/DIHelper.cs +++ b/common/ASC.Common/DIHelper.cs @@ -97,14 +97,14 @@ namespace ASC.Common public Type Service { get; } public Type Additional { get; set; } - public DIAttribute() { } + protected DIAttribute() { } - public DIAttribute(Type service) + protected DIAttribute(Type service) { Service = service; } - public DIAttribute(Type service, Type implementation) + protected DIAttribute(Type service, Type implementation) { Implementation = implementation; Service = service; @@ -233,7 +233,7 @@ namespace ASC.Common } else { - Type c = null; + Type c; var a1 = a.GetGenericTypeDefinition(); var b = a.GetGenericArguments().FirstOrDefault(); @@ -297,7 +297,7 @@ namespace ASC.Common } else { - Type c = null; + Type c; var a1 = a.GetGenericTypeDefinition(); var b = a.GetGenericArguments().FirstOrDefault(); diff --git a/common/ASC.Common/Data/StreamExtension.cs b/common/ASC.Common/Data/StreamExtension.cs index c856976971..655a7c13a6 100644 --- a/common/ASC.Common/Data/StreamExtension.cs +++ b/common/ASC.Common/Data/StreamExtension.cs @@ -27,22 +27,26 @@ using System; using System.IO; -public static class StreamExtension -{ - public const int BufferSize = 2048; //NOTE: set to 2048 to fit in minimum tcp window - - public static void StreamCopyTo(this Stream srcStream, Stream dstStream, int length) - { - if (srcStream == null) throw new ArgumentNullException("srcStream"); - if (dstStream == null) throw new ArgumentNullException("dstStream"); - var buffer = new byte[BufferSize]; - int totalRead = 0; - int readed; - while ((readed = srcStream.Read(buffer, 0, length - totalRead > BufferSize ? BufferSize : length - totalRead)) > 0 && totalRead < length) +namespace ASC.Common.Data +{ + public static class StreamExtension + { + public const int BufferSize = 2048; //NOTE: set to 2048 to fit in minimum tcp window + + public static void StreamCopyTo(this Stream srcStream, Stream dstStream, int length) { - dstStream.Write(buffer, 0, readed); - totalRead += readed; - } - } -} + if (srcStream == null) throw new ArgumentNullException(nameof(srcStream)); + if (dstStream == null) throw new ArgumentNullException(nameof(dstStream)); + + var buffer = new byte[BufferSize]; + int totalRead = 0; + int readed; + while ((readed = srcStream.Read(buffer, 0, length - totalRead > BufferSize ? BufferSize : length - totalRead)) > 0 && totalRead < length) + { + dstStream.Write(buffer, 0, readed); + totalRead += readed; + } + } + } +} \ No newline at end of file diff --git a/common/ASC.Common/Data/TempStream.cs b/common/ASC.Common/Data/TempStream.cs index 0b6ee90911..196af2f604 100644 --- a/common/ASC.Common/Data/TempStream.cs +++ b/common/ASC.Common/Data/TempStream.cs @@ -32,7 +32,7 @@ namespace ASC.Common public Stream GetBuffered(Stream srcStream) { - if (srcStream == null) throw new ArgumentNullException("srcStream"); + if (srcStream == null) throw new ArgumentNullException(nameof(srcStream)); if (!srcStream.CanSeek || srcStream.CanTimeout) { //Buffer it diff --git a/common/ASC.Common/DependencyInjection/AutofacExtension.cs b/common/ASC.Common/DependencyInjection/AutofacExtension.cs index 8dec7cb508..70cb4b7530 100644 --- a/common/ASC.Common/DependencyInjection/AutofacExtension.cs +++ b/common/ASC.Common/DependencyInjection/AutofacExtension.cs @@ -120,7 +120,7 @@ namespace ASC.Common.DependencyInjection void LoadAssembly(string type) { - var dll = type.Substring(type.IndexOf(",") + 1).Trim(); + var dll = type.Substring(type.IndexOf(',') + 1).Trim(); var path = GetFullPath(dll); if (!string.IsNullOrEmpty(path)) diff --git a/common/ASC.Common/Logging/Log.cs b/common/ASC.Common/Logging/Log.cs index 56f8e4eab5..15bbd01e03 100644 --- a/common/ASC.Common/Logging/Log.cs +++ b/common/ASC.Common/Logging/Log.cs @@ -875,7 +875,7 @@ namespace ASC.Common.Logging } } - public class LoggerExtension where T : class, ILog, new() + public static class LoggerExtension where T : class, ILog, new() { public static void RegisterLog(DIHelper services) { @@ -883,11 +883,11 @@ namespace ASC.Common.Logging } } - public class LogNLogExtension : LoggerExtension + public static class LogNLogExtension { public static void Register(DIHelper services) { - RegisterLog(services); + LoggerExtension.RegisterLog(services); } } } diff --git a/common/ASC.Common/Logging/SelfCleaningTarget.cs b/common/ASC.Common/Logging/SelfCleaningTarget.cs index bcf43b3c17..86a7f5c125 100644 --- a/common/ASC.Common/Logging/SelfCleaningTarget.cs +++ b/common/ASC.Common/Logging/SelfCleaningTarget.cs @@ -53,10 +53,8 @@ namespace ASC.Common.Logging const string key = "cleanPeriod"; - if (NLog.LogManager.Configuration.Variables.Keys.Contains(key)) + if (LogManager.Configuration.Variables.TryGetValue(key, out var variable)) { - var variable = NLog.LogManager.Configuration.Variables[key]; - if (variable != null && !string.IsNullOrEmpty(variable.Text)) { int.TryParse(variable.Text, out value); @@ -111,7 +109,7 @@ namespace ASC.Common.Logging { Exception = err, Level = LogLevel.Error, - Message = string.Format("file: {0}, dir: {1}, mess: {2}", filePath, dirPath, err.Message), + Message = $"file: {filePath}, dir: {dirPath}, mess: {err.Message}", LoggerName = "SelfCleaningTarget" }); } diff --git a/common/ASC.Common/Logging/SpecialFolderPathConverter.cs b/common/ASC.Common/Logging/SpecialFolderPathConverter.cs index e96bdfcd35..4d63ed3da6 100644 --- a/common/ASC.Common/Logging/SpecialFolderPathConverter.cs +++ b/common/ASC.Common/Logging/SpecialFolderPathConverter.cs @@ -49,7 +49,7 @@ namespace ASC.Common.Logging var args = Environment.CommandLine.Split(' '); for (var i = 0; i < args.Length - 1; i++) { - if (args[i].Equals(Option.Substring(CMD_LINE.Length), StringComparison.InvariantCultureIgnoreCase)) + if (args[i].Contains(Option, StringComparison.InvariantCultureIgnoreCase)) { result = args[i + 1]; } diff --git a/common/ASC.Common/Mapping/MappingProfile.cs b/common/ASC.Common/Mapping/MappingProfile.cs index 3d16f3f228..dcd17805ae 100644 --- a/common/ASC.Common/Mapping/MappingProfile.cs +++ b/common/ASC.Common/Mapping/MappingProfile.cs @@ -44,8 +44,7 @@ namespace ASC.Common.Mapping var types = assembly.GetExportedTypes() .Where(t => t.GetInterfaces().Any(i => - i.IsGenericType && i.GetGenericTypeDefinition() == typeof(IMapFrom<>))) - .ToList(); + i.IsGenericType && i.GetGenericTypeDefinition() == typeof(IMapFrom<>))); foreach (var type in types) { diff --git a/common/ASC.Common/Security/AscRandom.cs b/common/ASC.Common/Security/AscRandom.cs index 2e3fe2c5f2..e50ea7fe2c 100644 --- a/common/ASC.Common/Security/AscRandom.cs +++ b/common/ASC.Common/Security/AscRandom.cs @@ -30,8 +30,8 @@ namespace ASC.Common.Security { public class AscRandom : Random { - private int inext; - private int inextp; + private int _inext; + private int _inextp; private const int MBIG = int.MaxValue; private const int MSEED = 161803398; private const int MZ = 0; @@ -51,7 +51,7 @@ namespace ASC.Common.Security var num3 = 1; for (var i = 1; i < seeds.Length - 1; i++) { - var index = (21 * i) % (seeds.Length - 1); + var index = 21 * i % (seeds.Length - 1); seeds[index] = num3; num3 = num2 - num3; if (num3 < 0) @@ -71,8 +71,8 @@ namespace ASC.Common.Security } } } - inext = 0; - inextp = 21; + _inext = 0; + _inextp = 21; } public override int Next(int maxValue) @@ -96,8 +96,8 @@ namespace ASC.Common.Security private int InternalSample() { - var inext = this.inext; - var inextp = this.inextp; + var inext = this._inext; + var inextp = this._inextp; if (++inext >= seeds.Length - 1) { inext = 1; @@ -116,8 +116,8 @@ namespace ASC.Common.Security num += int.MaxValue; } seeds[inext] = num; - this.inext = inext; - this.inextp = inextp; + this._inext = inext; + this._inextp = inextp; return num; } } diff --git a/common/ASC.Common/Security/Authorizing/AuthorizingException.cs b/common/ASC.Common/Security/Authorizing/AuthorizingException.cs index e1ab1be442..3b2e59f9fa 100644 --- a/common/ASC.Common/Security/Authorizing/AuthorizingException.cs +++ b/common/ASC.Common/Security/Authorizing/AuthorizingException.cs @@ -28,6 +28,7 @@ using System; using System.Runtime.Serialization; +using System.Text; #endregion @@ -95,30 +96,27 @@ namespace ASC.Common.Security.Authorizing if (denyActions == null || denyActions.Length == 0) throw new ArgumentNullException(nameof(denyActions)); if (actions.Length != denySubjects.Length || actions.Length != denyActions.Length) throw new ArgumentException(); - var reasons = ""; + + var sb = new StringBuilder(); for (var i = 0; i < actions.Length; i++) { - var reason = ""; - if (denySubjects[i] != null && denyActions[i] != null) - reason = string.Format("{0}:{1} access denied {2}.", - actions[i].Name, - (denySubjects[i] is IRole ? "role:" : "") + denySubjects[i].Name, - denyActions[i].Name - ); + var action = actions[i]; + var denyAction = denyActions[i]; + var denySubject = denySubjects[i]; + + string reason; + if (denySubject != null && denyAction != null) + reason = $"{action.Name}:{(denySubject is IRole ? "role:" : "") + denySubject.Name} access denied {denyAction.Name}."; else - reason = string.Format("{0}: access denied.", actions[i].Name); + reason = $"{action.Name}: access denied."; if (i != actions.Length - 1) reason += ", "; - reasons += reason; + sb.Append(reason); } + var reasons = sb.ToString(); var sactions = ""; Array.ForEach(actions, action => { sactions += action.ToString() + ", "; }); - var message = string.Format( - "\"{0}\" access denied \"{1}\". Cause: {2}.", - (subject is IRole ? "role:" : "") + subject.Name, - sactions, - reasons - ); + var message = $"\"{(subject is IRole ? "role:" : "") + subject.Name}\" access denied \"{sactions}\". Cause: {reasons}."; return message; } } diff --git a/common/ASC.Common/Security/Authorizing/Constants.cs b/common/ASC.Common/Security/Authorizing/Constants.cs index e327050929..f325f1951a 100644 --- a/common/ASC.Common/Security/Authorizing/Constants.cs +++ b/common/ASC.Common/Security/Authorizing/Constants.cs @@ -28,7 +28,7 @@ using System; namespace ASC.Common.Security.Authorizing { - public sealed class Constants + public static class Constants { public static readonly Role Admin = new Role(new Guid("cd84e66b-b803-40fc-99f9-b2969a54a1de"), "Admin"); diff --git a/common/ASC.Common/Security/Authorizing/Domain/Role.cs b/common/ASC.Common/Security/Authorizing/Domain/Role.cs index df93ff3b94..3099de7f86 100644 --- a/common/ASC.Common/Security/Authorizing/Domain/Role.cs +++ b/common/ASC.Common/Security/Authorizing/Domain/Role.cs @@ -75,7 +75,7 @@ namespace ASC.Common.Security.Authorizing public override string ToString() { - return string.Format("Role: {0}", Name); + return $"Role: {Name}"; } } } \ No newline at end of file diff --git a/common/ASC.Common/Security/Cryptography/Hasher.cs b/common/ASC.Common/Security/Cryptography/Hasher.cs index f404b66370..c25cdc2eac 100644 --- a/common/ASC.Common/Security/Cryptography/Hasher.cs +++ b/common/ASC.Common/Security/Cryptography/Hasher.cs @@ -30,7 +30,7 @@ using System.Text; namespace ASC.Security.Cryptography { - public sealed class Hasher + public static class Hasher { private const HashAlg DefaultAlg = HashAlg.SHA256; diff --git a/common/ASC.Common/Threading/DistributedTask.cs b/common/ASC.Common/Threading/DistributedTask.cs index 2365f358c3..83e0bf608a 100644 --- a/common/ASC.Common/Threading/DistributedTask.cs +++ b/common/ASC.Common/Threading/DistributedTask.cs @@ -55,7 +55,7 @@ namespace ASC.Common.Threading } protected set { - DistributedTaskCache.Id = value?.ToString() ?? ""; + DistributedTaskCache.Id = value ?? ""; } } diff --git a/common/ASC.Common/Threading/DistributedTaskQueue.cs b/common/ASC.Common/Threading/DistributedTaskQueue.cs index dbe2954ada..2454e50c28 100644 --- a/common/ASC.Common/Threading/DistributedTaskQueue.cs +++ b/common/ASC.Common/Threading/DistributedTaskQueue.cs @@ -135,7 +135,7 @@ namespace ASC.Common.Threading public class DistributedTaskQueue { - public static readonly int InstanceId; + public static readonly int InstanceId = Process.GetCurrentProcess().Id; private string key; private TaskScheduler Scheduler { get; set; } = TaskScheduler.Default; @@ -157,12 +157,6 @@ namespace ASC.Common.Threading public DistributedTaskCacheNotify DistributedTaskCacheNotify { get; set; } - static DistributedTaskQueue() - { - InstanceId = Process.GetCurrentProcess().Id; - } - - public void QueueTask(DistributedTaskProgress taskProgress) { QueueTask((a, b) => taskProgress.RunJob(), taskProgress); @@ -238,7 +232,7 @@ namespace ASC.Common.Threading using var scope = ServiceProvider.CreateScope(); var task = scope.ServiceProvider.GetService(); task.DistributedTaskCache = cache; - if (task != null && task.Publication == null) + if (task.Publication == null) { task.Publication = GetPublication(); } @@ -255,7 +249,7 @@ namespace ASC.Common.Threading { var task = new DistributedTask(); task.DistributedTaskCache = cache; - if (task != null && task.Publication == null) + if (task.Publication == null) { task.Publication = GetPublication(); } diff --git a/common/ASC.Common/Utils/DnsLookup.cs b/common/ASC.Common/Utils/DnsLookup.cs index c4f99322f4..49eb2c398c 100644 --- a/common/ASC.Common/Utils/DnsLookup.cs +++ b/common/ASC.Common/Utils/DnsLookup.cs @@ -101,7 +101,7 @@ namespace ASC.Common.Utils var dnsMessage = GetDnsMessage(domainName); - return dnsMessage.AnswerRecords.Any(); + return dnsMessage.AnswerRecords.Count != 0; } /// diff --git a/common/ASC.Common/Utils/HtmlUtil.cs b/common/ASC.Common/Utils/HtmlUtil.cs index 631455bf36..3837d983d4 100644 --- a/common/ASC.Common/Utils/HtmlUtil.cs +++ b/common/ASC.Common/Utils/HtmlUtil.cs @@ -102,9 +102,9 @@ namespace ASC.Common.Utils { if (string.IsNullOrEmpty(searchText) || string.IsNullOrEmpty(htmlText)) return htmlText; - var regexpstr = Worder.Matches(searchText).Cast().Select(m => m.Value).Distinct().Aggregate((r, n) => r + "|" + n); + var regexpstr = Worder.Matches(searchText).Select(m => m.Value).Distinct().Aggregate((r, n) => r + "|" + n); var wordsFinder = new Regex(Regex.Escape(regexpstr), RegexOptions.Compiled | RegexOptions.IgnoreCase | RegexOptions.CultureInvariant | RegexOptions.Multiline); - return wordsFinder.Replace(htmlText, m => string.Format("{0}", m.Value, withoutLink ? " bold" : string.Empty)); + return wordsFinder.Replace(htmlText, m => "" + m.Value + ""); } } } \ No newline at end of file diff --git a/common/ASC.Common/Utils/HttpRequestExtensions.cs b/common/ASC.Common/Utils/HttpRequestExtensions.cs index 5d03a133b4..5ecccafd33 100644 --- a/common/ASC.Common/Utils/HttpRequestExtensions.cs +++ b/common/ASC.Common/Utils/HttpRequestExtensions.cs @@ -186,7 +186,7 @@ namespace System.Web } const StringComparison cmp = StringComparison.OrdinalIgnoreCase; - if (0 < s.Length && (s.StartsWith("0", cmp))) + if (0 < s.Length && s.StartsWith('0')) { s = Uri.UriSchemeHttp + s.Substring(1); } @@ -194,7 +194,7 @@ namespace System.Web { s = Uri.UriSchemeHttp + s.Substring(3); } - else if (0 < s.Length && (s.StartsWith("1", cmp))) + else if (0 < s.Length && s.StartsWith('1')) { s = Uri.UriSchemeHttps + s.Substring(1); } diff --git a/common/ASC.Common/Utils/JsonWebToken.cs b/common/ASC.Common/Utils/JsonWebToken.cs index 25481d3cb8..f68576bb39 100644 --- a/common/ASC.Common/Utils/JsonWebToken.cs +++ b/common/ASC.Common/Utils/JsonWebToken.cs @@ -37,7 +37,7 @@ using Formatting = Newtonsoft.Json.Formatting; namespace ASC.Web.Core.Files { - public class JsonWebToken + public static class JsonWebToken { public static string Encode(object payload, string key) { diff --git a/common/ASC.Common/Utils/MailAddressUtils.cs b/common/ASC.Common/Utils/MailAddressUtils.cs index 96ef7ea071..a8c08b9c07 100644 --- a/common/ASC.Common/Utils/MailAddressUtils.cs +++ b/common/ASC.Common/Utils/MailAddressUtils.cs @@ -66,7 +66,7 @@ namespace ASC.Common.Utils private static string ToSmtpAddress(string address, string displayName) { - return string.Format("\"{0}\" <{1}>", displayName, address); + return $"\"{displayName}\" <{address}>"; } } } diff --git a/common/ASC.Common/Utils/RandomString.cs b/common/ASC.Common/Utils/RandomString.cs index 2a8d3bd77f..2b268f8bd1 100644 --- a/common/ASC.Common/Utils/RandomString.cs +++ b/common/ASC.Common/Utils/RandomString.cs @@ -24,7 +24,7 @@ */ -using System; +using System.Security.Cryptography; using System.Text; namespace ASC.Common.Utils @@ -35,10 +35,9 @@ namespace ASC.Common.Utils { const string valid = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890"; var res = new StringBuilder(); - var rnd = new Random(); while (0 < length--) { - res.Append(valid[rnd.Next(valid.Length)]); + res.Append(valid[RandomNumberGenerator.GetInt32(valid.Length)]); } return res.ToString(); } diff --git a/common/ASC.Common/Utils/TimeZoneConverter/TimeZoneConverter.cs b/common/ASC.Common/Utils/TimeZoneConverter/TimeZoneConverter.cs index 6a3ab2d8dd..28be6abef0 100644 --- a/common/ASC.Common/Utils/TimeZoneConverter/TimeZoneConverter.cs +++ b/common/ASC.Common/Utils/TimeZoneConverter/TimeZoneConverter.cs @@ -122,7 +122,7 @@ namespace ASC.Common.Utils if (mapZone != null) return mapZone.WindowsTimeZoneId; - Log.Error(string.Format("OlsonTimeZone {0} not found", olsonTimeZoneId)); + Log.Error("OlsonTimeZone " + olsonTimeZoneId + " not found"); return defaultIfNoMatch ? "UTC" : null; } @@ -139,7 +139,7 @@ namespace ASC.Common.Utils if (mapZone != null) return mapZone.OlsonTimeZoneId; - Log.Error(string.Format("WindowsTimeZone {0} not found", windowsTimeZoneId)); + Log.Error("WindowsTimeZone " + windowsTimeZoneId + " not found"); return defaultIfNoMatch ? "Etc/GMT" : null; } diff --git a/common/ASC.Common/Utils/VelocityFormatter.cs b/common/ASC.Common/Utils/VelocityFormatter.cs index fecb88be69..b6e532c002 100644 --- a/common/ASC.Common/Utils/VelocityFormatter.cs +++ b/common/ASC.Common/Utils/VelocityFormatter.cs @@ -58,7 +58,7 @@ namespace ASC.Common.Utils } } - public class VelocityFormatter + public static class VelocityFormatter { private static bool initialized; private static readonly ConcurrentDictionary patterns = new ConcurrentDictionary(); diff --git a/common/ASC.Common/Utils/Wildcard.cs b/common/ASC.Common/Utils/Wildcard.cs index e3a36da22c..a08b686e7c 100644 --- a/common/ASC.Common/Utils/Wildcard.cs +++ b/common/ASC.Common/Utils/Wildcard.cs @@ -51,8 +51,8 @@ namespace ASC.Common.Utils { var offsetInput = 0; var isAsterix = false; - int i; - for (i = 0; i < pattern.Length;) + int i = 0; + while (i < pattern.Length) { switch (pattern[i]) { @@ -98,7 +98,7 @@ namespace ASC.Common.Utils while (i < pattern.Length && pattern[i] == '*') ++i; - return (offsetInput == input.Length); + return offsetInput == input.Length; } } } \ No newline at end of file diff --git a/common/ASC.Common/Web/MimeMapping.cs b/common/ASC.Common/Web/MimeMapping.cs index eeefcc7d18..7f019839ea 100644 --- a/common/ASC.Common/Web/MimeMapping.cs +++ b/common/ASC.Common/Web/MimeMapping.cs @@ -857,7 +857,7 @@ namespace ASC.Common.Web foreach (DictionaryEntry entry in extensionToMimeMappingTable) { var mime = (string)entry.Value; - if (mime == mimeMapping.ToLowerInvariant()) return (string)entry.Key; + if (mime.Equals(mimeMapping, StringComparison.OrdinalIgnoreCase)) return (string)entry.Key; if (!mimeSynonyms.ContainsKey(mime)) continue; if (mimeSynonyms[mime].Contains(mimeMapping.ToLowerInvariant())) return (string)entry.Key; } diff --git a/common/ASC.Common/Web/VirtualPathUtility.cs b/common/ASC.Common/Web/VirtualPathUtility.cs index dc08c41c32..da4916e11f 100644 --- a/common/ASC.Common/Web/VirtualPathUtility.cs +++ b/common/ASC.Common/Web/VirtualPathUtility.cs @@ -2,7 +2,7 @@ namespace ASC.Common.Web { - public class VirtualPathUtility + public static class VirtualPathUtility { public static string ToAbsolute(string virtualPath) { diff --git a/common/ASC.Core.Common/ASC.Core.Common.csproj b/common/ASC.Core.Common/ASC.Core.Common.csproj index b17305d29c..1884764312 100644 --- a/common/ASC.Core.Common/ASC.Core.Common.csproj +++ b/common/ASC.Core.Common/ASC.Core.Common.csproj @@ -56,6 +56,7 @@ runtime; build; native; contentfiles; analyzers; buildtransitive + diff --git a/common/ASC.Core.Common/BaseCommonLinkUtility.cs b/common/ASC.Core.Common/BaseCommonLinkUtility.cs index 75c153b414..8ef62e58ef 100644 --- a/common/ASC.Core.Common/BaseCommonLinkUtility.cs +++ b/common/ASC.Core.Common/BaseCommonLinkUtility.cs @@ -90,6 +90,9 @@ namespace ASC.Core.Common if (HttpContextAccessor?.HttpContext?.Request != null) { var u = HttpContextAccessor?.HttpContext.Request.GetUrlRewriter(); + + if (u == null) throw new ArgumentNullException("u"); + uriBuilder = new UriBuilder(u.Scheme, LOCALHOST, u.Port); } _serverRoot = uriBuilder; @@ -125,6 +128,9 @@ namespace ASC.Core.Common if (HttpContextAccessor?.HttpContext?.Request != null) { var u = HttpContextAccessor?.HttpContext?.Request.GetUrlRewriter(); + + if (u == null) throw new ArgumentNullException("u"); + result = new UriBuilder(u.Scheme, u.Host, u.Port); if (CoreBaseSettings.Standalone && !result.Uri.IsLoopback) @@ -179,7 +185,7 @@ namespace ASC.Core.Common virtualPath.StartsWith("https://", StringComparison.InvariantCultureIgnoreCase)) return virtualPath; - if (string.IsNullOrEmpty(virtualPath) || virtualPath.StartsWith("/")) + if (virtualPath.StartsWith('/')) { return ServerRootPath + virtualPath; } @@ -193,7 +199,7 @@ namespace ASC.Core.Common return VirtualPathUtility.ToAbsolute(virtualPath); } - if (string.IsNullOrEmpty(virtualPath) || virtualPath.StartsWith("/")) + if (string.IsNullOrEmpty(virtualPath) || virtualPath.StartsWith('/')) { return virtualPath; } @@ -211,7 +217,7 @@ namespace ASC.Core.Common if (string.IsNullOrEmpty(lang)) { - url = matches.Cast().Aggregate(url, (current, match) => current.Replace(match.Value, string.Empty)); + url = matches.Aggregate(url, (current, match) => current.Replace(match.Value, string.Empty)); } else { diff --git a/common/ASC.Core.Common/Billing/BillingClient.cs b/common/ASC.Core.Common/Billing/BillingClient.cs index 297c40b75e..f4f4d229e6 100644 --- a/common/ASC.Core.Common/Billing/BillingClient.cs +++ b/common/ASC.Core.Common/Billing/BillingClient.cs @@ -53,6 +53,8 @@ namespace ASC.Core.Billing private const int AvangatePaymentSystemId = 1; + static readonly HttpClient HttpClient = new HttpClient(); + public BillingClient(IConfiguration configuration) : this(false, configuration) @@ -159,13 +161,21 @@ namespace ASC.Core.Billing string url; var paymentUrl = (Uri)null; var upgradeUrl = (Uri)null; - if (paymentUrls.TryGetValue(p, out url) && !string.IsNullOrEmpty(url = ToUrl(url))) + if (paymentUrls.TryGetValue(p, out url)) { - paymentUrl = new Uri(url); + url = ToUrl(url); + if (!string.IsNullOrEmpty(url)) + { + paymentUrl = new Uri(url); + } } - if (upgradeUrls.TryGetValue(p, out url) && !string.IsNullOrEmpty(url = ToUrl(url))) + if (upgradeUrls.TryGetValue(p, out url)) { - upgradeUrl = new Uri(url); + url = ToUrl(url); + if (!string.IsNullOrEmpty(url)) + { + upgradeUrl = new Uri(url); + } } urls[p] = Tuple.Create(paymentUrl, upgradeUrl); } @@ -176,7 +186,7 @@ namespace ASC.Core.Billing { if (productIds == null) { - throw new ArgumentNullException("productIds"); + throw new ArgumentNullException(nameof(productIds)); } var parameters = productIds.Select(pid => Tuple.Create("ProductId", pid)).ToList(); @@ -185,15 +195,13 @@ namespace ASC.Core.Billing var result = Request("GetProductsPrices", null, parameters.ToArray()); var prices = JsonSerializer.Deserialize>>>(result); - if (prices.ContainsKey(AvangatePaymentSystemId)) + if (prices.TryGetValue(AvangatePaymentSystemId, out var pricesPaymentSystem)) { - var pricesPaymentSystem = prices[AvangatePaymentSystemId]; - return productIds.Select(productId => { - if (pricesPaymentSystem.ContainsKey(productId)) + if (pricesPaymentSystem.TryGetValue(productId, out var prices)) { - return new { ProductId = productId, Prices = pricesPaymentSystem[productId] }; + return new { ProductId = productId, Prices = prices }; } return new { ProductId = productId, Prices = new Dictionary() }; }) @@ -210,7 +218,7 @@ namespace ASC.Core.Billing { var now = DateTime.UtcNow.ToString("yyyyMMddHHmmss"); var hash = WebEncoders.Base64UrlEncode(hasher.ComputeHash(Encoding.UTF8.GetBytes(string.Join("\n", now, pkey)))); - return string.Format("ASC {0}:{1}:{2}", pkey, now, hash); + return "ASC " + pkey + ":" + now + ":" + hash; } } @@ -226,8 +234,7 @@ namespace ASC.Core.Billing request.Headers.Add("Authorization", CreateAuthToken(_billingKey, _billingSecret)); } - using var httpClient = new HttpClient(); - httpClient.Timeout = TimeSpan.FromMilliseconds(60000); + HttpClient.Timeout = TimeSpan.FromMilliseconds(60000); var data = new Dictionary>(); if (!string.IsNullOrEmpty(portalId)) @@ -250,7 +257,7 @@ namespace ASC.Core.Billing request.Content = new StringContent(body, Encoding.UTF8, "application/json"); string result; - using (var response = httpClient.Send(request)) + using (var response = HttpClient.Send(request)) using (var stream = response.Content.ReadAsStream()) { if (stream == null) @@ -272,7 +279,7 @@ namespace ASC.Core.Billing return result; } - var @params = (parameters ?? Enumerable.Empty>()).Select(p => string.Format("{0}: {1}", p.Item1, p.Item2)); + var @params = parameters.Select(p => p.Item1 + ": " + p.Item2); var info = new { Method = method, PortalId = portalId, Params = string.Join(", ", @params) }; if (result.Contains("{\"Message\":\"error: cannot find ")) { diff --git a/common/ASC.Core.Common/Billing/CouponManager.cs b/common/ASC.Core.Common/Billing/CouponManager.cs index 6c801e33f0..f83815f3b3 100644 --- a/common/ASC.Core.Common/Billing/CouponManager.cs +++ b/common/ASC.Core.Common/Billing/CouponManager.cs @@ -28,7 +28,6 @@ using System; using System.Collections.Generic; using System.Configuration; using System.Linq; -using System.Net; using System.Net.Http; using System.Security.Cryptography; using System.Text; @@ -47,7 +46,8 @@ namespace ASC.Core.Common.Billing [Singletone] public class CouponManager { - private IEnumerable Products { get; set; } + private IEnumerable Products { get; set; } + private IHttpClientFactory ClientFactory { get; } private IEnumerable Groups { get; set; } private readonly int Percent; private readonly int Schedule; @@ -55,13 +55,15 @@ namespace ASC.Core.Common.Billing private readonly byte[] Secret; private readonly Uri BaseAddress; private readonly string ApiVersion; - private readonly SemaphoreSlim SemaphoreSlim = new SemaphoreSlim(1, 1); - private readonly ILog Log; + private readonly SemaphoreSlim SemaphoreSlim; + private readonly ILog Log; + - public CouponManager(IOptionsMonitor option) + public CouponManager(IOptionsMonitor option, IHttpClientFactory clientFactory) { SemaphoreSlim = new SemaphoreSlim(1, 1); - Log = option.CurrentValue; + Log = option.CurrentValue; + ClientFactory = clientFactory; try { @@ -98,7 +100,7 @@ namespace ASC.Core.Common.Billing { using var httpClient = PrepaireClient(); using var content = new StringContent(await Promotion.GeneratePromotion(Log, this, tenantManager, Percent, Schedule), Encoding.Default, "application/json"); - using var response = await httpClient.PostAsync(string.Format("{0}/promotions/", ApiVersion), content); + using var response = await httpClient.PostAsync($"{ApiVersion}/promotions/", content); if (!response.IsSuccessStatusCode) throw new Exception(response.ReasonPhrase); @@ -112,24 +114,28 @@ namespace ASC.Core.Common.Billing Log.Error(ex.Message, ex); throw; } + } + + internal Task> GetProducts() + { + if (Products != null) return Task.FromResult(Products); + return InternalGetProducts(); } - internal async Task> GetProducts() - { - if (Products != null) return Products; - + private async Task> InternalGetProducts() + { await SemaphoreSlim.WaitAsync(); if (Products != null) { SemaphoreSlim.Release(); return Products; - } + } try { using var httpClient = PrepaireClient(); - using var response = await httpClient.GetAsync(string.Format("{0}/products/?Limit=1000&Enabled=true", ApiVersion)); + using var response = await httpClient.GetAsync($"{ApiVersion}/products/?Limit=1000&Enabled=true"); if (!response.IsSuccessStatusCode) throw new Exception(response.ReasonPhrase); @@ -153,9 +159,12 @@ namespace ASC.Core.Common.Billing private HttpClient PrepaireClient() { - ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12 | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls; - const string applicationJson = "application/json"; - using var httpClient = new HttpClient { BaseAddress = BaseAddress, Timeout = TimeSpan.FromMinutes(3) }; + const string applicationJson = "application/json"; + + var httpClient = ClientFactory.CreateClient(); + httpClient.BaseAddress = BaseAddress; + httpClient.Timeout = TimeSpan.FromMinutes(3); + httpClient.DefaultRequestHeaders.TryAddWithoutValidation("accept", applicationJson); httpClient.DefaultRequestHeaders.TryAddWithoutValidation("Content-Type", applicationJson); httpClient.DefaultRequestHeaders.TryAddWithoutValidation("X-Avangate-Authentication", CreateAuthHeader()); @@ -176,9 +185,9 @@ namespace ASC.Core.Common.Billing } var stringBuilder = new StringBuilder(); - stringBuilder.AppendFormat("code='{0}' ", VendorCode); - stringBuilder.AppendFormat("date='{0}' ", date); - stringBuilder.AppendFormat("hash='{0}'", sBuilder); + stringBuilder.Append($"code='{VendorCode}' "); + stringBuilder.Append($"date='{date}' "); + stringBuilder.Append($"hash='{sBuilder}'"); return stringBuilder.ToString(); } } diff --git a/common/ASC.Core.Common/Billing/License/LicenseReader.cs b/common/ASC.Core.Common/Billing/License/LicenseReader.cs index c8bb46ade0..8f8df79c71 100644 --- a/common/ASC.Core.Common/Billing/License/LicenseReader.cs +++ b/common/ASC.Core.Common/Billing/License/LicenseReader.cs @@ -26,7 +26,6 @@ using System; using System.IO; -using System.Linq; using ASC.Common; using ASC.Common.Logging; @@ -153,7 +152,7 @@ namespace ASC.Core.Billing private static void SaveLicense(Stream licenseStream, string path) { - if (licenseStream == null) throw new ArgumentNullException("licenseStream"); + if (licenseStream == null) throw new ArgumentNullException(nameof(licenseStream)); if (licenseStream.CanSeek) { @@ -189,7 +188,7 @@ namespace ASC.Core.Billing { license.PortalCount = TenantManager.GetTenantQuota(Tenant.DEFAULT_TENANT).CountPortals; } - var activePortals = TenantManager.GetTenants().Count(); + var activePortals = TenantManager.GetTenants().Count; if (activePortals > 1 && license.PortalCount < activePortals) { throw new LicensePortalException("License portal count", license.OriginalLicense); diff --git a/common/ASC.Core.Common/Billing/TariffService.cs b/common/ASC.Core.Common/Billing/TariffService.cs index 5deee5f5c1..4e07ccdcad 100644 --- a/common/ASC.Core.Common/Billing/TariffService.cs +++ b/common/ASC.Core.Common/Billing/TariffService.cs @@ -239,7 +239,7 @@ namespace ASC.Core.Billing var quota = QuotaService.GetTenantQuotas().SingleOrDefault(q => q.AvangateId == lastPayment.ProductId); if (quota == null) { - throw new InvalidOperationException(string.Format("Quota with id {0} not found for portal {1}.", lastPayment.ProductId, GetPortalId(tenantId))); + throw new InvalidOperationException($"Quota with id {lastPayment.ProductId} not found for portal {GetPortalId(tenantId)}."); } var asynctariff = Tariff.CreateDefault(); @@ -279,7 +279,7 @@ namespace ASC.Core.Billing { if (tariff == null) { - throw new ArgumentNullException("tariff"); + throw new ArgumentNullException(nameof(tariff)); } var q = QuotaService.GetTenantQuota(tariff.QuotaId); @@ -362,7 +362,7 @@ namespace ASC.Core.Billing var key = tenant.HasValue ? GetBillingUrlCacheKey(tenant.Value) - : string.Format("notenant{0}", !string.IsNullOrEmpty(affiliateId) ? "_" + affiliateId : ""); + : string.Format($"notenant{(!string.IsNullOrEmpty(affiliateId) ? "_" + affiliateId : "")}"); key += quota.Visible ? "" : "0"; if (!(Cache.Get>>(key) is IDictionary> urls)) { @@ -432,7 +432,7 @@ namespace ASC.Core.Billing { if (productIds == null) { - throw new ArgumentNullException("productIds"); + throw new ArgumentNullException(nameof(productIds)); } try { @@ -503,10 +503,10 @@ namespace ASC.Core.Billing using var tx = CoreDbContext.Database.BeginTransaction(); // last record is not the same - var count = CoreDbContext.Tariffs - .Count(r => r.Tenant == tenant && r.Tariff == tariffInfo.QuotaId && r.Stamp == tariffInfo.DueDate && r.Quantity == tariffInfo.Quantity); + var any = CoreDbContext.Tariffs + .Any(r => r.Tenant == tenant && r.Tariff == tariffInfo.QuotaId && r.Stamp == tariffInfo.DueDate && r.Quantity == tariffInfo.Quantity); - if (tariffInfo.DueDate == DateTime.MaxValue || renewal || count == 0) + if (tariffInfo.DueDate == DateTime.MaxValue || renewal || any) { var efTariff = new DbTariff { diff --git a/common/ASC.Core.Common/Caching/AzRecordStore.cs b/common/ASC.Core.Common/Caching/AzRecordStore.cs index d983357dda..d1230f551d 100644 --- a/common/ASC.Core.Common/Caching/AzRecordStore.cs +++ b/common/ASC.Core.Common/Caching/AzRecordStore.cs @@ -68,9 +68,9 @@ namespace ASC.Core.Caching if (r == null) return; var id = r.ObjectId ?? string.Empty; - if (byObjectId.ContainsKey(id)) + if (byObjectId.TryGetValue(id, out var list)) { - byObjectId[id].RemoveAll(a => a.SubjectId == r.SubjectId && a.ActionId == r.ActionId && a.Reaction == r.Reaction); + list.RemoveAll(a => a.SubjectId == r.SubjectId && a.ActionId == r.ActionId && a.Reaction == r.Reaction); } } diff --git a/common/ASC.Core.Common/Caching/CachedAzService.cs b/common/ASC.Core.Common/Caching/CachedAzService.cs index 9aecec13d9..2150ebcb76 100644 --- a/common/ASC.Core.Common/Caching/CachedAzService.cs +++ b/common/ASC.Core.Common/Caching/CachedAzService.cs @@ -87,7 +87,7 @@ namespace ASC.Core.Caching public CachedAzService(DbAzService service, AzServiceCache azServiceCache) { - this.service = service ?? throw new ArgumentNullException("service"); + this.service = service ?? throw new ArgumentNullException(nameof(service)); Cache = azServiceCache.Cache; cacheNotify = azServiceCache.CacheNotify; CacheExpiration = TimeSpan.FromMinutes(10); @@ -100,8 +100,9 @@ namespace ASC.Core.Caching var aces = Cache.Get(key); if (aces == null) { - var records = service.GetAces(tenant, default); - Cache.Insert(key, aces = new AzRecordStore(records), DateTime.UtcNow.Add(CacheExpiration)); + var records = service.GetAces(tenant, default); + aces = new AzRecordStore(records); + Cache.Insert(key, aces, DateTime.UtcNow.Add(CacheExpiration)); } return aces; } diff --git a/common/ASC.Core.Common/Caching/CachedQuotaService.cs b/common/ASC.Core.Common/Caching/CachedQuotaService.cs index 7a490d5c54..f8ff5be388 100644 --- a/common/ASC.Core.Common/Caching/CachedQuotaService.cs +++ b/common/ASC.Core.Common/Caching/CachedQuotaService.cs @@ -127,7 +127,7 @@ namespace ASC.Core.Caching public CachedQuotaService(DbQuotaService service, QuotaServiceCache quotaServiceCache) : this() { - Service = service ?? throw new ArgumentNullException("service"); + Service = service ?? throw new ArgumentNullException(nameof(service)); QuotaServiceCache = quotaServiceCache; Cache = quotaServiceCache.Cache; CacheNotify = quotaServiceCache.CacheNotify; diff --git a/common/ASC.Core.Common/Caching/CachedSubscriptionService.cs b/common/ASC.Core.Common/Caching/CachedSubscriptionService.cs index fbe6d7bc15..9d3448b0a9 100644 --- a/common/ASC.Core.Common/Caching/CachedSubscriptionService.cs +++ b/common/ASC.Core.Common/Caching/CachedSubscriptionService.cs @@ -114,7 +114,7 @@ namespace ASC.Core.Caching public CachedSubscriptionService(DbSubscriptionService service, SubscriptionServiceCache subscriptionServiceCache) { - this.service = service ?? throw new ArgumentNullException("service"); + this.service = service ?? throw new ArgumentNullException(nameof(service)); cache = subscriptionServiceCache.Cache; notifyRecord = subscriptionServiceCache.NotifyRecord; notifyMethod = subscriptionServiceCache.NotifyMethod; @@ -201,7 +201,8 @@ namespace ASC.Core.Caching { var records = service.GetSubscriptions(tenant, sourceId, actionId); var methods = service.GetSubscriptionMethods(tenant, sourceId, actionId, null); - cache.Insert(key, store = new SubsciptionsStore(records, methods), DateTime.UtcNow.Add(CacheExpiration)); + store = new SubsciptionsStore(records, methods); + cache.Insert(key, store, DateTime.UtcNow.Add(CacheExpiration)); } return store; } diff --git a/common/ASC.Core.Common/Caching/CachedTenantService.cs b/common/ASC.Core.Common/Caching/CachedTenantService.cs index 1aa26b16da..a5f52d0653 100644 --- a/common/ASC.Core.Common/Caching/CachedTenantService.cs +++ b/common/ASC.Core.Common/Caching/CachedTenantService.cs @@ -73,8 +73,9 @@ namespace ASC.Core.Caching { var store = Cache.Get(KEY); if (store == null) - { - Cache.Insert(KEY, store = new TenantStore(), DateTime.UtcNow.Add(CacheExpiration)); + { + store = new TenantStore(); + Cache.Insert(KEY, store, DateTime.UtcNow.Add(CacheExpiration)); } return store; } @@ -204,7 +205,7 @@ namespace ASC.Core.Caching public CachedTenantService(DbTenantService service, TenantServiceCache tenantServiceCache, ICache cache) : this() { this.cache = cache; - Service = service ?? throw new ArgumentNullException("service"); + Service = service ?? throw new ArgumentNullException(nameof(service)); TenantServiceCache = tenantServiceCache; CacheNotifyItem = tenantServiceCache.CacheNotifyItem; CacheNotifySettings = tenantServiceCache.CacheNotifySettings; @@ -298,8 +299,9 @@ namespace ASC.Core.Caching var data = cache.Get(cacheKey); if (data == null) { - data = Service.GetTenantSettings(tenant, key); - cache.Insert(cacheKey, data ?? new byte[0], DateTime.UtcNow + SettingsExpiration); + data = Service.GetTenantSettings(tenant, key); + + cache.Insert(cacheKey, data ?? Array.Empty(), DateTime.UtcNow + SettingsExpiration); } return data == null ? null : data.Length == 0 ? null : data; } diff --git a/common/ASC.Core.Common/Caching/CachedUserService.cs b/common/ASC.Core.Common/Caching/CachedUserService.cs index ce07a463b3..1660d0fb8d 100644 --- a/common/ASC.Core.Common/Caching/CachedUserService.cs +++ b/common/ASC.Core.Common/Caching/CachedUserService.cs @@ -207,7 +207,7 @@ namespace ASC.Core.Caching UserServiceCache userServiceCache ) : this() { - Service = service ?? throw new ArgumentNullException("service"); + Service = service ?? throw new ArgumentNullException(nameof(service)); CoreBaseSettings = coreBaseSettings; UserServiceCache = userServiceCache; Cache = userServiceCache.Cache; @@ -322,7 +322,7 @@ namespace ASC.Core.Caching group = Service.GetGroup(tenant, id); if (group != null) Cache.Insert(key, group, CacheExpiration); - }; + } return group; } diff --git a/common/ASC.Core.Common/Configuration/AmiPublicDnsSyncService.cs b/common/ASC.Core.Common/Configuration/AmiPublicDnsSyncService.cs index 37f3747262..42909c8c1a 100644 --- a/common/ASC.Core.Common/Configuration/AmiPublicDnsSyncService.cs +++ b/common/ASC.Core.Common/Configuration/AmiPublicDnsSyncService.cs @@ -54,13 +54,13 @@ namespace ASC.Core.Configuration { using var scope = ServiceProvider.CreateScope(); var scopeClass = scope.ServiceProvider.GetService(); - var (tenantManager, coreBaseSettings) = scopeClass; + var (tenantManager, coreBaseSettings, clientFactory) = scopeClass; if (coreBaseSettings.Standalone) { var tenants = tenantManager.GetTenants(false).Where(t => MappedDomainNotSettedByUser(t.MappedDomain)); if (tenants.Any()) { - var dnsname = GetAmiPublicDnsName(); + var dnsname = GetAmiPublicDnsName(clientFactory); foreach (var tenant in tenants.Where(t => !string.IsNullOrEmpty(dnsname) && t.MappedDomain != dnsname)) { tenant.MappedDomain = dnsname; @@ -75,7 +75,7 @@ namespace ASC.Core.Configuration return string.IsNullOrEmpty(domain) || Regex.IsMatch(domain, "^ec2.+\\.compute\\.amazonaws\\.com$", RegexOptions.CultureInvariant | RegexOptions.IgnoreCase); } - private static string GetAmiPublicDnsName() + private static string GetAmiPublicDnsName(IHttpClientFactory clientFactory) { try { @@ -83,7 +83,7 @@ namespace ASC.Core.Configuration request.RequestUri = new Uri("http://169.254.169.254/latest/meta-data/public-hostname"); request.Method = HttpMethod.Get; - using var httpClient = new HttpClient(); + var httpClient = clientFactory.CreateClient(); httpClient.Timeout = TimeSpan.FromMilliseconds(5000); using var responce = httpClient.Send(request); @@ -106,16 +106,18 @@ namespace ASC.Core.Configuration { private TenantManager TenantManager { get; } private CoreBaseSettings CoreBaseSettings { get; } + private IHttpClientFactory ClientFactory { get; } - public AmiPublicDnsSyncServiceScope(TenantManager tenantManager, CoreBaseSettings coreBaseSettings) + public AmiPublicDnsSyncServiceScope(TenantManager tenantManager, CoreBaseSettings coreBaseSettings, IHttpClientFactory clientFactory) { TenantManager = tenantManager; CoreBaseSettings = coreBaseSettings; + ClientFactory = clientFactory; } - public void Deconstruct(out TenantManager tenantManager, out CoreBaseSettings coreBaseSettings) + public void Deconstruct(out TenantManager tenantManager, out CoreBaseSettings coreBaseSettings, out IHttpClientFactory clientFactory) { - (tenantManager, coreBaseSettings) = (TenantManager, CoreBaseSettings); + (tenantManager, coreBaseSettings, clientFactory) = (TenantManager, CoreBaseSettings, ClientFactory); } } } diff --git a/common/ASC.Core.Common/Configuration/Constants.cs b/common/ASC.Core.Common/Configuration/Constants.cs index 98bfcedb06..852ebdd246 100644 --- a/common/ASC.Core.Common/Configuration/Constants.cs +++ b/common/ASC.Core.Common/Configuration/Constants.cs @@ -32,7 +32,7 @@ using ASC.Common.Security.Authorizing; namespace ASC.Core.Configuration { - public sealed class Constants + public static class Constants { public static readonly string NotifyEMailSenderSysName = "email.sender"; diff --git a/common/ASC.Core.Common/Configuration/Consumer.cs b/common/ASC.Core.Common/Configuration/Consumer.cs index 6ff6375c34..a86dfba373 100644 --- a/common/ASC.Core.Common/Configuration/Consumer.cs +++ b/common/ASC.Core.Common/Configuration/Consumer.cs @@ -50,13 +50,13 @@ namespace ASC.Core.Common.Configuration protected readonly Dictionary Props; public IEnumerable ManagedKeys { - get { return Props.Select(r => r.Key).ToList(); } + get { return Props.Select(r => r.Key); } } protected readonly Dictionary Additional; public virtual IEnumerable AdditionalKeys { - get { return Additional.Select(r => r.Key).ToList(); } + get { return Additional.Select(r => r.Key); } } public ICollection Keys { get { return AllProps.Keys; } } @@ -88,7 +88,7 @@ namespace ASC.Core.Common.Configuration public bool IsSet { - get { return Props.Any() && !Props.All(r => string.IsNullOrEmpty(this[r.Key])); } + get { return Props.Count > 0 && !Props.All(r => string.IsNullOrEmpty(this[r.Key])); } } static Consumer() @@ -152,7 +152,7 @@ namespace ASC.Core.Common.Configuration Props = props ?? new Dictionary(); Additional = additional ?? new Dictionary(); - if (props != null && props.Any()) + if (props != null && props.Count > 0) { CanSet = props.All(r => string.IsNullOrEmpty(r.Value)); } @@ -245,10 +245,7 @@ namespace ASC.Core.Common.Configuration if (string.IsNullOrEmpty(value)) { - if (AllProps.ContainsKey(name)) - { - value = AllProps[name]; - } + AllProps.TryGetValue(name, out value); } return value; @@ -339,7 +336,7 @@ namespace ASC.Core.Common.Configuration public override IEnumerable AdditionalKeys { - get { return base.AdditionalKeys.Where(r => r != HandlerTypeKey && r != "cdn").ToList(); } + get { return base.AdditionalKeys.Where(r => r != HandlerTypeKey && r != "cdn"); } } protected override string GetSettingsKey(string name) @@ -354,9 +351,9 @@ namespace ASC.Core.Common.Configuration HandlerType = Type.GetType(additional[HandlerTypeKey]); - if (additional.ContainsKey(CdnKey)) + if (additional.TryGetValue(CdnKey, out var value)) { - Cdn = GetCdn(additional[CdnKey]); + Cdn = GetCdn(value); } } diff --git a/common/ASC.Core.Common/Configuration/SmtpSettings.cs b/common/ASC.Core.Common/Configuration/SmtpSettings.cs index 70161bcf61..08c1641427 100644 --- a/common/ASC.Core.Common/Configuration/SmtpSettings.cs +++ b/common/ASC.Core.Common/Configuration/SmtpSettings.cs @@ -54,7 +54,7 @@ namespace ASC.Core.Configuration public bool IsDefaultSettings { get; internal set; } - public static SmtpSettings Empty = new SmtpSettings(); + public static readonly SmtpSettings Empty = new SmtpSettings(); private SmtpSettings() { @@ -83,17 +83,17 @@ namespace ASC.Core.Configuration { if (string.IsNullOrEmpty(host)) { - throw new ArgumentException("Empty smtp host.", "host"); + throw new ArgumentException("Empty smtp host.", nameof(host)); } if (string.IsNullOrEmpty(senderAddress)) { - throw new ArgumentException("Empty sender address.", "senderAddress"); + throw new ArgumentException("Empty sender address.", nameof(senderAddress)); } Host = host; Port = port; SenderAddress = senderAddress; - SenderDisplayName = senderDisplayName ?? throw new ArgumentNullException("senderDisplayName"); + SenderDisplayName = senderDisplayName ?? throw new ArgumentNullException(nameof(senderDisplayName)); } public void SetCredentials(string userName, string password) @@ -105,11 +105,11 @@ namespace ASC.Core.Configuration { if (string.IsNullOrEmpty(userName)) { - throw new ArgumentException("Empty user name.", "userName"); + throw new ArgumentException("Empty user name.", nameof(userName)); } if (string.IsNullOrEmpty(password)) { - throw new ArgumentException("Empty password.", "password"); + throw new ArgumentException("Empty password.", nameof(password)); } CredentialsUserName = userName; CredentialsUserPassword = password; diff --git a/common/ASC.Core.Common/Context/Impl/AuthorizationManager.cs b/common/ASC.Core.Common/Context/Impl/AuthorizationManager.cs index 5f0e9609f5..87ef0515ba 100644 --- a/common/ASC.Core.Common/Context/Impl/AuthorizationManager.cs +++ b/common/ASC.Core.Common/Context/Impl/AuthorizationManager.cs @@ -100,7 +100,7 @@ namespace ASC.Core public void RemoveAllAces(ISecurityObjectId id) { - foreach (var r in GetAces(Guid.Empty, Guid.Empty, id).ToArray()) + foreach (var r in GetAces(Guid.Empty, Guid.Empty, id)) { RemoveAce(r); } diff --git a/common/ASC.Core.Common/Context/Impl/CoreConfiguration.cs b/common/ASC.Core.Common/Context/Impl/CoreConfiguration.cs index 76f919a932..d3f4eb1e7f 100644 --- a/common/ASC.Core.Common/Context/Impl/CoreConfiguration.cs +++ b/common/ASC.Core.Common/Context/Impl/CoreConfiguration.cs @@ -43,15 +43,27 @@ namespace ASC.Core [Singletone] public class CoreBaseSettings { - private bool? standalone; + private bool? standalone; + private string basedomain; private bool? personal; private bool? customMode; - private IConfiguration Configuration { get; } + private IConfiguration Configuration { get; } public CoreBaseSettings(IConfiguration configuration) { Configuration = configuration; + } + public string Basedomain + { + get + { + if (basedomain == null) + { + basedomain = Configuration["core:base-domain"] ?? string.Empty; + } + return basedomain; + } } public bool Standalone @@ -64,13 +76,13 @@ namespace ASC.Core get { //TODO:if (CustomMode && HttpContext.Current != null && HttpContext.Current.Request.SailfishApp()) return true; - return personal ?? (bool)(personal = string.Compare(Configuration["core:personal"], "true", true) == 0); + return personal ?? (bool)(personal = Configuration["core:personal"].Equals("true", StringComparison.OrdinalIgnoreCase)); } } public bool CustomMode { - get { return customMode ?? (bool)(customMode = string.Compare(Configuration["core:custom-mode"], "true", true) == 0); } + get { return customMode ?? (bool)(customMode = Configuration["core:custom-mode"].Equals("true", StringComparison.OrdinalIgnoreCase)); } } } @@ -108,31 +120,24 @@ namespace ASC.Core [Scope(typeof(ConfigureCoreSettings))] public class CoreSettings { - private string basedomain; - public string BaseDomain { get { - if (basedomain == null) - { - basedomain = Configuration["core:base-domain"] ?? string.Empty; - } - string result; - if (CoreBaseSettings.Standalone || string.IsNullOrEmpty(basedomain)) + if (CoreBaseSettings.Standalone || string.IsNullOrEmpty(CoreBaseSettings.Basedomain)) { - result = GetSetting("BaseDomain") ?? basedomain; + result = GetSetting("BaseDomain") ?? CoreBaseSettings.Basedomain; } else { - result = basedomain; + result = CoreBaseSettings.Basedomain; } return result; } set { - if (CoreBaseSettings.Standalone || string.IsNullOrEmpty(basedomain)) + if (CoreBaseSettings.Standalone || string.IsNullOrEmpty(CoreBaseSettings.Basedomain)) { SaveSetting("BaseDomain", value); } @@ -162,7 +167,7 @@ namespace ASC.Core { var baseHost = BaseDomain; - if (string.IsNullOrEmpty(hostedRegion) || string.IsNullOrEmpty(baseHost) || !baseHost.Contains(".")) + if (string.IsNullOrEmpty(hostedRegion) || string.IsNullOrEmpty(baseHost) || baseHost.IndexOf('.') < 0) { return baseHost; } @@ -174,7 +179,7 @@ namespace ASC.Core { if (string.IsNullOrEmpty(key)) { - throw new ArgumentNullException("key"); + throw new ArgumentNullException(nameof(key)); } byte[] bytes = null; if (value != null) @@ -188,7 +193,7 @@ namespace ASC.Core { if (string.IsNullOrEmpty(key)) { - throw new ArgumentNullException("key"); + throw new ArgumentNullException(nameof(key)); } var bytes = TenantService.GetTenantSettings(tenant, key); @@ -209,8 +214,9 @@ namespace ASC.Core // thread safe key = GetSetting("PortalId"); if (string.IsNullOrEmpty(key)) - { - SaveSetting("PortalId", key = Guid.NewGuid().ToString()); + { + key = Guid.NewGuid().ToString(); + SaveSetting("PortalId", key); } } } diff --git a/common/ASC.Core.Common/Context/Impl/PaymentManager.cs b/common/ASC.Core.Common/Context/Impl/PaymentManager.cs index 33b679222d..d8837644ea 100644 --- a/common/ASC.Core.Common/Context/Impl/PaymentManager.cs +++ b/common/ASC.Core.Common/Context/Impl/PaymentManager.cs @@ -50,15 +50,17 @@ namespace ASC.Core private readonly string partnerKey; private TenantManager TenantManager { get; } - private IConfiguration Configuration { get; } + private IConfiguration Configuration { get; } + private IHttpClientFactory ClientFactory { get; } - public PaymentManager(TenantManager tenantManager, ITariffService tariffService, IConfiguration configuration) + public PaymentManager(TenantManager tenantManager, ITariffService tariffService, IConfiguration configuration, IHttpClientFactory clientFactory) { TenantManager = tenantManager; this.tariffService = tariffService; Configuration = configuration; partnerUrl = (Configuration["core:payment:partners"] ?? "https://partners.onlyoffice.com/api").TrimEnd('/'); - partnerKey = (Configuration["core:machinekey"] ?? "C5C1F4E85A3A43F5B3202C24D97351DF"); + partnerKey = Configuration["core:machinekey"] ?? "C5C1F4E85A3A43F5B3202C24D97351DF"; + ClientFactory = clientFactory; } @@ -102,7 +104,7 @@ namespace ASC.Core { if (string.IsNullOrEmpty(key)) { - throw new ArgumentNullException("key"); + throw new ArgumentNullException(nameof(key)); } var now = DateTime.UtcNow; @@ -112,7 +114,7 @@ namespace ASC.Core request.Headers.Add("Authorization", GetPartnerAuthHeader(actionUrl)); request.RequestUri = new Uri(partnerUrl + actionUrl); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); @@ -133,7 +135,7 @@ namespace ASC.Core var now = DateTime.UtcNow.ToString("yyyyMMddHHmmss", CultureInfo.InvariantCulture); var data = string.Join("\n", now, "/api/" + url.TrimStart('/')); //data: UTC DateTime (yyyy:MM:dd HH:mm:ss) + \n + url var hash = WebEncoders.Base64UrlEncode(hasher.ComputeHash(Encoding.UTF8.GetBytes(data))); - return string.Format("ASC :{0}:{1}", now, hash); + return $"ASC :{now}:{hash}"; } } diff --git a/common/ASC.Core.Common/Context/Impl/SubscriptionManager.cs b/common/ASC.Core.Common/Context/Impl/SubscriptionManager.cs index 531267bd95..5a8d54f609 100644 --- a/common/ASC.Core.Common/Context/Impl/SubscriptionManager.cs +++ b/common/ASC.Core.Common/Context/Impl/SubscriptionManager.cs @@ -42,19 +42,13 @@ namespace ASC.Core private TenantManager TenantManager { get; } private ICache Cache { get; set; } - public static readonly object CacheLocker; - public static readonly List Groups; - - static SubscriptionManager() - { - CacheLocker = new object(); - Groups = new List + public static readonly object CacheLocker = new object(); + public static readonly List Groups = Groups = new List { Constants.Admin.ID, Constants.Everyone.ID, Constants.User.ID }; - } public SubscriptionManager(ISubscriptionService service, TenantManager tenantManager, ICache cache) { @@ -123,7 +117,7 @@ namespace ASC.Core m = methods.FirstOrDefault(); } - return m != null ? m.Methods : new string[0]; + return m != null ? m.Methods : Array.Empty(); } public string[] GetRecipients(string sourceID, string actionID, string objectID) diff --git a/common/ASC.Core.Common/Context/Impl/TenantManager.cs b/common/ASC.Core.Common/Context/Impl/TenantManager.cs index 1247aec31d..a68a9437ec 100644 --- a/common/ASC.Core.Common/Context/Impl/TenantManager.cs +++ b/common/ASC.Core.Common/Context/Impl/TenantManager.cs @@ -198,7 +198,7 @@ namespace ASC.Core public Tenant SetTenantVersion(Tenant tenant, int version) { - if (tenant == null) throw new ArgumentNullException("tenant"); + if (tenant == null) throw new ArgumentNullException(nameof(tenant)); if (tenant.Version != version) { tenant.Version = version; diff --git a/common/ASC.Core.Common/Context/Impl/UserManager.cs b/common/ASC.Core.Common/Context/Impl/UserManager.cs index 3a2ffe8fff..bec401d493 100644 --- a/common/ASC.Core.Common/Context/Impl/UserManager.cs +++ b/common/ASC.Core.Common/Context/Impl/UserManager.cs @@ -175,13 +175,13 @@ namespace ASC.Core public UserInfo GetUserBySid(string sid) { return GetUsersInternal() - .FirstOrDefault(u => u.Sid != null && string.Compare(u.Sid, sid, StringComparison.CurrentCultureIgnoreCase) == 0) ?? Constants.LostUser; + .FirstOrDefault(u => u.Sid != null && u.Sid.Equals(sid, StringComparison.CurrentCultureIgnoreCase)) ?? Constants.LostUser; } public UserInfo GetSsoUserByNameId(string nameId) { return GetUsersInternal() - .FirstOrDefault(u => !string.IsNullOrEmpty(u.SsoNameId) && string.Compare(u.SsoNameId, nameId, StringComparison.CurrentCultureIgnoreCase) == 0) ?? Constants.LostUser; + .FirstOrDefault(u => !string.IsNullOrEmpty(u.SsoNameId) && u.SsoNameId.Equals(nameId, StringComparison.CurrentCultureIgnoreCase)) ?? Constants.LostUser; } public bool IsUserNameExists(string username) { @@ -239,7 +239,7 @@ namespace ASC.Core public UserInfo[] Search(string text, EmployeeStatus status, Guid groupId) { - if (text == null || text.Trim() == string.Empty) return new UserInfo[0]; + if (text == null || text.Trim().Length == 0) return new UserInfo[0]; var words = text.Split(new[] { ' ' }, StringSplitOptions.RemoveEmptyEntries); if (words.Length == 0) return new UserInfo[0]; diff --git a/common/ASC.Core.Common/Context/SecurityContext.cs b/common/ASC.Core.Common/Context/SecurityContext.cs index b0ca20ff20..218702e095 100644 --- a/common/ASC.Core.Common/Context/SecurityContext.cs +++ b/common/ASC.Core.Common/Context/SecurityContext.cs @@ -113,8 +113,8 @@ namespace ASC.Core public string AuthenticateMe(string login, string passwordHash) { - if (login == null) throw new ArgumentNullException("login"); - if (passwordHash == null) throw new ArgumentNullException("passwordHash"); + if (login == null) throw new ArgumentNullException(nameof(login)); + if (passwordHash == null) throw new ArgumentNullException(nameof(passwordHash)); var tenantid = TenantManager.GetCurrentTenant().TenantId; var u = UserManager.GetUsersByPasswordHash(tenantid, login, passwordHash); @@ -134,6 +134,9 @@ namespace ASC.Core if (HttpContextAccessor?.HttpContext != null) { var request = HttpContextAccessor?.HttpContext.Request; + + if (request == null) throw new ArgumentNullException("request"); + ipFrom = "from " + (request.Headers["X-Forwarded-For"].ToString() ?? request.GetUserHostAddress()); address = "for " + request.GetUrlRewriter(); } @@ -189,6 +192,9 @@ namespace ASC.Core if (HttpContextAccessor?.HttpContext != null) { var request = HttpContextAccessor?.HttpContext.Request; + + if (request == null) throw new ArgumentNullException("request"); + address = "for " + request.GetUrlRewriter(); ipFrom = "from " + (request.Headers["X-Forwarded-For"].ToString() ?? request.GetUserHostAddress()); } diff --git a/common/ASC.Core.Common/Context/WorkContext.cs b/common/ASC.Core.Common/Context/WorkContext.cs index c9d5f1f75a..68abd257e2 100644 --- a/common/ASC.Core.Common/Context/WorkContext.cs +++ b/common/ASC.Core.Common/Context/WorkContext.cs @@ -171,7 +171,7 @@ namespace ASC.Core } } - public class WorkContextExtension + public static class WorkContextExtension { public static void Register(DIHelper dIHelper) { diff --git a/common/ASC.Core.Common/Core/DBResourceManager.cs b/common/ASC.Core.Common/Core/DBResourceManager.cs index 0a0395a6a0..d44c3375f9 100644 --- a/common/ASC.Core.Common/Core/DBResourceManager.cs +++ b/common/ASC.Core.Common/Core/DBResourceManager.cs @@ -50,7 +50,7 @@ namespace TMResourceData { public class DBResourceManager : ResourceManager { - public static bool WhiteLableEnabled = false; + public static readonly bool WhiteLableEnabled = false; private readonly ConcurrentDictionary resourceSets = new ConcurrentDictionary(); public DBResourceManager(string filename, Assembly assembly) @@ -125,7 +125,7 @@ namespace TMResourceData private static bool Accept(Assembly a) { var n = a.GetName().Name; - return (n.StartsWith("ASC.") || n.StartsWith("App_GlobalResources")) && a.GetManifestResourceNames().Any(); + return (n.StartsWith("ASC.") || n.StartsWith("App_GlobalResources")) && a.GetManifestResourceNames().Length > 0; } @@ -174,11 +174,11 @@ namespace TMResourceData { if (culture == null) { - throw new ArgumentNullException("culture"); + throw new ArgumentNullException(nameof(culture)); } if (string.IsNullOrEmpty(filename)) { - throw new ArgumentNullException("filename"); + throw new ArgumentNullException(nameof(filename)); } DbContext = dbContext; @@ -248,7 +248,7 @@ namespace TMResourceData private Dictionary GetResources() { - var key = string.Format("{0}/{1}", filename, culture); + var key = $"{filename}/{culture}"; if (!(cache.Get(key) is Dictionary dic)) { lock (locker) @@ -257,7 +257,8 @@ namespace TMResourceData if (dic == null) { var policy = cacheTimeout == TimeSpan.Zero ? null : new CacheItemPolicy() { AbsoluteExpiration = DateTimeOffset.Now.Add(cacheTimeout) }; - cache.Set(key, dic = LoadResourceSet(filename, culture), policy); + dic = LoadResourceSet(filename, culture); + cache.Set(key, dic, policy); } } } @@ -283,7 +284,7 @@ namespace TMResourceData { private readonly ILog log; private readonly ConcurrentDictionary whiteLabelDictionary; - public string DefaultLogoText; + public string DefaultLogoText { get; set; } private IConfiguration Configuration { get; } @@ -341,7 +342,7 @@ namespace TMResourceData { var newTextReplacement = newText; - if (resourceValue.Contains("<") && resourceValue.Contains(">") || resourceName.StartsWith("pattern_")) + if (resourceValue.IndexOf('<') >= 0 && resourceValue.IndexOf('>') >= 0 || resourceName.StartsWith("pattern_")) { newTextReplacement = HttpUtility.HtmlEncode(newTextReplacement); } diff --git a/common/ASC.Core.Common/Core/UserGroupRef.cs b/common/ASC.Core.Common/Core/UserGroupRef.cs index 7b7fc291da..cba8c9fe17 100644 --- a/common/ASC.Core.Common/Core/UserGroupRef.cs +++ b/common/ASC.Core.Common/Core/UserGroupRef.cs @@ -27,7 +27,6 @@ using System; using System.Diagnostics; -using ASC.Common.Caching; using ASC.Core.Caching; namespace ASC.Core diff --git a/common/ASC.Core.Common/Core/UserInfo.cs b/common/ASC.Core.Common/Core/UserInfo.cs index 4bd972457d..f7dde01308 100644 --- a/common/ASC.Core.Common/Core/UserInfo.cs +++ b/common/ASC.Core.Common/Core/UserInfo.cs @@ -112,7 +112,7 @@ namespace ASC.Core.Users public override string ToString() { - return string.Format("{0} {1}", FirstName, LastName).Trim(); + return $"{FirstName} {LastName}".Trim(); } public override int GetHashCode() @@ -138,7 +138,7 @@ namespace ASC.Core.Users string[] IDirectRecipient.Addresses { - get { return !string.IsNullOrEmpty(Email) ? new[] { Email } : new string[0]; } + get { return !string.IsNullOrEmpty(Email) ? new[] { Email } : Array.Empty(); } } public bool CheckActivation @@ -168,7 +168,7 @@ namespace ASC.Core.Users var sBuilder = new StringBuilder(); foreach (var contact in ContactsList) { - sBuilder.AppendFormat("{0}|", contact); + sBuilder.Append($"{contact}|"); } return sBuilder.ToString(); } diff --git a/common/ASC.Core.Common/Data/DbAzService.cs b/common/ASC.Core.Common/Data/DbAzService.cs index b6a5d06f89..b7feb320fd 100644 --- a/common/ASC.Core.Common/Data/DbAzService.cs +++ b/common/ASC.Core.Common/Data/DbAzService.cs @@ -75,9 +75,8 @@ namespace ASC.Core.Data foreach (var a in tenantAces) { var key = string.Concat(a.Tenant.ToString(), a.SubjectId.ToString(), a.ActionId.ToString(), a.ObjectId); - if (commonAces.ContainsKey(key)) + if (commonAces.TryGetValue(key, out var common)) { - var common = commonAces[key]; commonAces.Remove(key); if (common.Reaction == a.Reaction) { @@ -126,15 +125,13 @@ namespace ASC.Core.Data private bool ExistEscapeRecord(AzRecord r) { - var count = UserDbContext.Acl + return UserDbContext.Acl .Where(a => a.Tenant == Tenant.DEFAULT_TENANT) .Where(a => a.Subject == r.SubjectId) .Where(a => a.Action == r.ActionId) .Where(a => a.Object == (r.ObjectId ?? string.Empty)) .Where(a => a.AceType == r.Reaction) - .Count(); - - return count != 0; + .Any(); } private void DeleteRecord(AzRecord r) diff --git a/common/ASC.Core.Common/Data/DbQuotaService.cs b/common/ASC.Core.Common/Data/DbQuotaService.cs index 0c271f2242..1711343f18 100644 --- a/common/ASC.Core.Common/Data/DbQuotaService.cs +++ b/common/ASC.Core.Common/Data/DbQuotaService.cs @@ -115,7 +115,7 @@ namespace ASC.Core.Data public TenantQuota SaveTenantQuota(TenantQuota quota) { - if (quota == null) throw new ArgumentNullException("quota"); + if (quota == null) throw new ArgumentNullException(nameof(quota)); var dbQuota = new DbQuota { @@ -155,7 +155,7 @@ namespace ASC.Core.Data public void SetTenantQuotaRow(TenantQuotaRow row, bool exchange) { - if (row == null) throw new ArgumentNullException("row"); + if (row == null) throw new ArgumentNullException(nameof(row)); using var tx = CoreDbContext.Database.BeginTransaction(); diff --git a/common/ASC.Core.Common/Data/DbSettingsManager.cs b/common/ASC.Core.Common/Data/DbSettingsManager.cs index f17b2f1027..25a22cfce5 100644 --- a/common/ASC.Core.Common/Data/DbSettingsManager.cs +++ b/common/ASC.Core.Common/Data/DbSettingsManager.cs @@ -148,13 +148,21 @@ namespace ASC.Core.Data private int tenantID; private int TenantID { - get { return tenantID != 0 ? tenantID : (tenantID = TenantManager.GetCurrentTenant().TenantId); } + get + { + if (tenantID == 0) tenantID = TenantManager.GetCurrentTenant().TenantId; + return tenantID; + } } // private Guid? currentUserID; private Guid CurrentUserID { - get { return ((Guid?)(currentUserID ??= AuthContext.CurrentAccount.ID)).Value; } + get + { + currentUserID ??= AuthContext.CurrentAccount.ID; + return currentUserID.Value; + } } public bool SaveSettings(T settings, int tenantId) where T : ISettings @@ -177,7 +185,7 @@ namespace ASC.Core.Data public bool SaveSettingsFor(T settings, int tenantId, Guid userId) where T : ISettings { - if (settings == null) throw new ArgumentNullException("settings"); + if (settings == null) throw new ArgumentNullException(nameof(settings)); try { var key = settings.ID.ToString() + tenantId + userId; diff --git a/common/ASC.Core.Common/Data/DbSubscriptionService.cs b/common/ASC.Core.Common/Data/DbSubscriptionService.cs index 1420c3a2df..5c15dc0d1c 100644 --- a/common/ASC.Core.Common/Data/DbSubscriptionService.cs +++ b/common/ASC.Core.Common/Data/DbSubscriptionService.cs @@ -69,8 +69,8 @@ namespace ASC.Core.Data public string[] GetRecipients(int tenant, string sourceId, string actionId, string objectId) { - if (sourceId == null) throw new ArgumentNullException("sourceId"); - if (actionId == null) throw new ArgumentNullException("actionId"); + if (sourceId == null) throw new ArgumentNullException(nameof(sourceId)); + if (actionId == null) throw new ArgumentNullException(nameof(actionId)); var q = GetQuery(tenant, sourceId, actionId) .Where(r => r.Object == (objectId ?? string.Empty)) @@ -83,8 +83,8 @@ namespace ASC.Core.Data public IEnumerable GetSubscriptions(int tenant, string sourceId, string actionId) { - if (sourceId == null) throw new ArgumentNullException("sourceId"); - if (actionId == null) throw new ArgumentNullException("actionId"); + if (sourceId == null) throw new ArgumentNullException(nameof(sourceId)); + if (actionId == null) throw new ArgumentNullException(nameof(actionId)); var q = GetQuery(tenant, sourceId, actionId); return GetSubscriptions(q, tenant); @@ -108,7 +108,7 @@ namespace ASC.Core.Data public SubscriptionRecord GetSubscription(int tenant, string sourceId, string actionId, string recipientId, string objectId) { - if (recipientId == null) throw new ArgumentNullException("recipientId"); + if (recipientId == null) throw new ArgumentNullException(nameof(recipientId)); var q = GetQuery(tenant, sourceId, actionId) .Where(r => r.Recipient == recipientId) @@ -119,9 +119,9 @@ namespace ASC.Core.Data public bool IsUnsubscribe(int tenant, string sourceId, string actionId, string recipientId, string objectId) { - if (recipientId == null) throw new ArgumentNullException("recipientId"); - if (sourceId == null) throw new ArgumentNullException("sourceId"); - if (actionId == null) throw new ArgumentNullException("actionId"); + if (recipientId == null) throw new ArgumentNullException(nameof(recipientId)); + if (sourceId == null) throw new ArgumentNullException(nameof(sourceId)); + if (actionId == null) throw new ArgumentNullException(nameof(actionId)); var q = UserDbContext.Subscriptions .Where(r => r.Source == sourceId && @@ -136,7 +136,7 @@ namespace ASC.Core.Data } else { - q = q = q.Where(r => r.Object == string.Empty);; + q = q.Where(r => r.Object == string.Empty); } return q.Any(); @@ -144,9 +144,9 @@ namespace ASC.Core.Data public string[] GetSubscriptions(int tenant, string sourceId, string actionId, string recipientId, bool checkSubscribe) { - if (recipientId == null) throw new ArgumentNullException("recipientId"); - if (sourceId == null) throw new ArgumentNullException("sourceId"); - if (actionId == null) throw new ArgumentNullException("actionId"); + if (recipientId == null) throw new ArgumentNullException(nameof(recipientId)); + if (sourceId == null) throw new ArgumentNullException(nameof(sourceId)); + if (actionId == null) throw new ArgumentNullException(nameof(actionId)); var q = GetQuery(tenant, sourceId, actionId) .Where(r=> r.Recipient == recipientId) @@ -163,7 +163,7 @@ namespace ASC.Core.Data public void SaveSubscription(SubscriptionRecord s) { - if (s == null) throw new ArgumentNullException("s"); + if (s == null) throw new ArgumentNullException(nameof(s)); var subs = new Subscription { @@ -186,8 +186,8 @@ namespace ASC.Core.Data public void RemoveSubscriptions(int tenant, string sourceId, string actionId, string objectId) { - if (sourceId == null) throw new ArgumentNullException("sourceId"); - if (actionId == null) throw new ArgumentNullException("actionId"); + if (sourceId == null) throw new ArgumentNullException(nameof(sourceId)); + if (actionId == null) throw new ArgumentNullException(nameof(actionId)); using var tr = UserDbContext.Database.BeginTransaction(); var q = UserDbContext.Subscriptions @@ -195,7 +195,7 @@ namespace ASC.Core.Data .Where(r => r.Source == sourceId) .Where(r => r.Action == actionId); - if (objectId != string.Empty) + if (objectId.Length != 0) { q = q.Where(r => r.Object == (objectId ?? string.Empty)); } @@ -213,8 +213,8 @@ namespace ASC.Core.Data public IEnumerable GetSubscriptionMethods(int tenant, string sourceId, string actionId, string recipientId) { - if (sourceId == null) throw new ArgumentNullException("sourceId"); - if (actionId == null) throw new ArgumentNullException("actionId"); + if (sourceId == null) throw new ArgumentNullException(nameof(sourceId)); + if (actionId == null) throw new ArgumentNullException(nameof(actionId)); var q = UserDbContext.SubscriptionMethods .Where(r => r.Tenant == -1 || r.Tenant == tenant) @@ -258,7 +258,7 @@ namespace ASC.Core.Data public void SetSubscriptionMethod(SubscriptionMethod m) { - if (m == null) throw new ArgumentNullException("m"); + if (m == null) throw new ArgumentNullException(nameof(m)); using var tr = UserDbContext.Database.BeginTransaction(); @@ -297,8 +297,8 @@ namespace ASC.Core.Data private IQueryable GetQuery(int tenant, string sourceId, string actionId) { - if (sourceId == null) throw new ArgumentNullException("sourceId"); - if (actionId == null) throw new ArgumentNullException("actionId"); + if (sourceId == null) throw new ArgumentNullException(nameof(sourceId)); + if (actionId == null) throw new ArgumentNullException(nameof(actionId)); return UserDbContext.Subscriptions diff --git a/common/ASC.Core.Common/Data/DbTenantService.cs b/common/ASC.Core.Common/Data/DbTenantService.cs index caadc2beae..f87e802feb 100644 --- a/common/ASC.Core.Common/Data/DbTenantService.cs +++ b/common/ASC.Core.Common/Data/DbTenantService.cs @@ -1,31 +1,31 @@ -/* - * - * (c) Copyright Ascensio System Limited 2010-2018 - * - * This program is freeware. You can redistribute it and/or modify it under the terms of the GNU - * General Public License (GPL) version 3 as published by the Free Software Foundation (https://www.gnu.org/copyleft/gpl.html). - * In accordance with Section 7(a) of the GNU GPL its Section 15 shall be amended to the effect that - * Ascensio System SIA expressly excludes the warranty of non-infringement of any third-party rights. - * - * THIS PROGRAM IS DISTRIBUTED WITHOUT ANY WARRANTY; WITHOUT EVEN THE IMPLIED WARRANTY OF MERCHANTABILITY OR - * FITNESS FOR A PARTICULAR PURPOSE. For more details, see GNU GPL at https://www.gnu.org/copyleft/gpl.html - * - * You can contact Ascensio System SIA by email at sales@onlyoffice.com - * - * The interactive user interfaces in modified source and object code versions of ONLYOFFICE must display - * Appropriate Legal Notices, as required under Section 5 of the GNU GPL version 3. - * - * Pursuant to Section 7 § 3(b) of the GNU GPL you must retain the original ONLYOFFICE logo which contains - * relevant author attributions when distributing the software. If the display of the logo in its graphic - * form is not reasonably feasible for technical reasons, you must include the words "Powered by ONLYOFFICE" - * in every copy of the program you distribute. - * Pursuant to Section 7 § 3(e) we decline to grant you any rights under trademark law for use of our trademarks. - * -*/ - - -using System; -using System.Collections.Generic; +/* + * + * (c) Copyright Ascensio System Limited 2010-2018 + * + * This program is freeware. You can redistribute it and/or modify it under the terms of the GNU + * General Public License (GPL) version 3 as published by the Free Software Foundation (https://www.gnu.org/copyleft/gpl.html). + * In accordance with Section 7(a) of the GNU GPL its Section 15 shall be amended to the effect that + * Ascensio System SIA expressly excludes the warranty of non-infringement of any third-party rights. + * + * THIS PROGRAM IS DISTRIBUTED WITHOUT ANY WARRANTY; WITHOUT EVEN THE IMPLIED WARRANTY OF MERCHANTABILITY OR + * FITNESS FOR A PARTICULAR PURPOSE. For more details, see GNU GPL at https://www.gnu.org/copyleft/gpl.html + * + * You can contact Ascensio System SIA by email at sales@onlyoffice.com + * + * The interactive user interfaces in modified source and object code versions of ONLYOFFICE must display + * Appropriate Legal Notices, as required under Section 5 of the GNU GPL version 3. + * + * Pursuant to Section 7 § 3(b) of the GNU GPL you must retain the original ONLYOFFICE logo which contains + * relevant author attributions when distributing the software. If the display of the logo in its graphic + * form is not reasonably feasible for technical reasons, you must include the words "Powered by ONLYOFFICE" + * in every copy of the program you distribute. + * Pursuant to Section 7 § 3(e) we decline to grant you any rights under trademark law for use of our trademarks. + * +*/ + + +using System; +using System.Collections.Generic; using System.Linq; using System.Linq.Expressions; using System.Text; @@ -34,17 +34,17 @@ using ASC.Common; using ASC.Core.Common.EF; using ASC.Core.Common.EF.Context; using ASC.Core.Common.EF.Model; -using ASC.Core.Tenants; +using ASC.Core.Tenants; using ASC.Core.Users; using ASC.Security.Cryptography; using Microsoft.EntityFrameworkCore; using Microsoft.Extensions.Options; -namespace ASC.Core.Data +namespace ASC.Core.Data { - [Scope] - public class ConfigureDbTenantService : IConfigureNamedOptions + [Scope] + public class ConfigureDbTenantService : IConfigureNamedOptions { private TenantDomainValidator TenantDomainValidator { get; } private DbContextManager DbContextManager { get; } @@ -71,8 +71,8 @@ namespace ASC.Core.Data } [Scope] - public class DbTenantService : ITenantService - { + public class DbTenantService : ITenantService + { private List forbiddenDomains; internal TenantDomainValidator TenantDomainValidator { get; set; } @@ -84,7 +84,7 @@ namespace ASC.Core.Data private static Expression> FromDbTenantToTenant { get; set; } private static Expression> FromTenantUserToTenant { get; set; } - static DbTenantService() + static DbTenantService() { FromDbTenantToTenant = r => new Tenant { @@ -131,15 +131,15 @@ namespace ASC.Core.Data LazyUserDbContext = new Lazy(() => DbContextManager.Value); TenantDomainValidator = tenantDomainValidator; MachinePseudoKeys = machinePseudoKeys; - } - - public void ValidateDomain(string domain) - { + } + + public void ValidateDomain(string domain) + { using var tr = TenantDbContext.Database.BeginTransaction(); - ValidateDomain(domain, Tenant.DEFAULT_TENANT, true); - } - - public IEnumerable GetTenants(DateTime from, bool active = true) + ValidateDomain(domain, Tenant.DEFAULT_TENANT, true); + } + + public IEnumerable GetTenants(DateTime from, bool active = true) { var q = TenantsQuery(); @@ -152,8 +152,8 @@ namespace ASC.Core.Data { q = q.Where(r => r.LastModified >= from); } - - return q.Select(FromDbTenantToTenant).ToList(); + + return q.Select(FromDbTenantToTenant).ToList(); } public IEnumerable GetTenants(List ids) @@ -162,10 +162,10 @@ namespace ASC.Core.Data return q.Where(r => ids.Contains(r.Id) && r.Status == TenantStatus.Active).Select(FromDbTenantToTenant).ToList(); } - - public IEnumerable GetTenants(string login, string passwordHash) - { - if (string.IsNullOrEmpty(login)) throw new ArgumentNullException("login"); + + public IEnumerable GetTenants(string login, string passwordHash) + { + if (string.IsNullOrEmpty(login)) throw new ArgumentNullException(nameof(login)); IQueryable query() => TenantsQuery() .Where(r => r.Status == TenantStatus.Active) @@ -183,7 +183,7 @@ namespace ASC.Core.Data }) .Where(r => r.User.Status == EmployeeStatus.Active) .Where(r => r.DbTenant.Status == TenantStatus.Active) - .Where(r => r.User.Removed == false); + .Where(r => !r.User.Removed); if (passwordHash == null) { @@ -238,70 +238,71 @@ namespace ASC.Core.Data //new password result = result.Concat(q.Select(FromTenantUserToTenant)).ToList(); - result.Distinct(); - return result; - } - } - - public Tenant GetTenant(int id) - { + return result.Distinct(); + } + } + + public Tenant GetTenant(int id) + { return TenantsQuery() .Where(r => r.Id == id) - .Select(FromDbTenantToTenant) - .SingleOrDefault(); - } - - public Tenant GetTenant(string domain) - { - if (string.IsNullOrEmpty(domain)) throw new ArgumentNullException("domain"); + .Select(FromDbTenantToTenant) + .SingleOrDefault(); + } + + public Tenant GetTenant(string domain) + { + if (string.IsNullOrEmpty(domain)) throw new ArgumentNullException(nameof(domain)); domain = domain.ToLowerInvariant(); return TenantsQuery() - .Where(r => r.Alias == domain || r.MappedDomain == domain) - .OrderBy(a => a.Status == TenantStatus.Restoring ? TenantStatus.Active : a.Status) + .Where(r => r.Alias == domain || r.MappedDomain == domain) + .OrderBy(a => a.Status == TenantStatus.Restoring ? TenantStatus.Active : a.Status) .ThenByDescending(a => a.Status == TenantStatus.Restoring ? 0 : a.Id) - .Select(FromDbTenantToTenant) - .FirstOrDefault(); - } - - public Tenant GetTenantForStandaloneWithoutAlias(string ip) - { - return TenantsQuery() + .Select(FromDbTenantToTenant) + .FirstOrDefault(); + } + + public Tenant GetTenantForStandaloneWithoutAlias(string ip) + { + return TenantsQuery() .OrderBy(a => a.Status) .ThenByDescending(a => a.Id) - .Select(FromDbTenantToTenant) - .FirstOrDefault(); - } - - public Tenant SaveTenant(CoreSettings coreSettings, Tenant t) - { - if (t == null) throw new ArgumentNullException("tenant"); - + .Select(FromDbTenantToTenant) + .FirstOrDefault(); + } + + public Tenant SaveTenant(CoreSettings coreSettings, Tenant t) + { + if (t == null) throw new ArgumentNullException("tenant"); + using var tx = TenantDbContext.Database.BeginTransaction(); - - if (!string.IsNullOrEmpty(t.MappedDomain)) - { - var baseUrl = coreSettings.GetBaseDomain(t.HostedRegion); - - if (baseUrl != null && t.MappedDomain.EndsWith("." + baseUrl, StringComparison.InvariantCultureIgnoreCase)) - { - ValidateDomain(t.MappedDomain.Substring(0, t.MappedDomain.Length - baseUrl.Length - 1), t.TenantId, false); - } - else - { - ValidateDomain(t.MappedDomain, t.TenantId, false); - } - } - - if (t.TenantId == Tenant.DEFAULT_TENANT) - { + + if (!string.IsNullOrEmpty(t.MappedDomain)) + { + var baseUrl = coreSettings.GetBaseDomain(t.HostedRegion); + + if (baseUrl != null && t.MappedDomain.EndsWith("." + baseUrl, StringComparison.InvariantCultureIgnoreCase)) + { + ValidateDomain(t.MappedDomain.Substring(0, t.MappedDomain.Length - baseUrl.Length - 1), t.TenantId, false); + } + else + { + ValidateDomain(t.MappedDomain, t.TenantId, false); + } + } + + if (t.TenantId == Tenant.DEFAULT_TENANT) + { t.Version = TenantDbContext.TenantVersion .Where(r => r.DefaultVersion == 1 || r.Id == 0) .OrderByDescending(r => r.Id) .Select(r => r.Id) - .FirstOrDefault(); + .FirstOrDefault(); + + t.LastModified = DateTime.UtcNow; var tenant = new DbTenant { @@ -320,7 +321,7 @@ namespace ASC.Core.Data Status = t.Status, StatusChanged = t.StatusChangeDate, PaymentId = t.PaymentId, - LastModified = t.LastModified = DateTime.UtcNow, + LastModified = t.LastModified, Industry = t.Industry, Spam = t.Spam, Calls = t.Calls @@ -328,9 +329,9 @@ namespace ASC.Core.Data tenant = TenantDbContext.Tenants.Add(tenant).Entity; TenantDbContext.SaveChanges(); - t.TenantId = tenant.Id; - } - else + t.TenantId = tenant.Id; + } + else { var tenant = TenantDbContext.Tenants .Where(r => r.Id == t.TenantId) @@ -356,10 +357,10 @@ namespace ASC.Core.Data tenant.Spam = t.Spam; tenant.Calls = t.Calls; } - TenantDbContext.SaveChanges(); - } - - if (string.IsNullOrEmpty(t.PartnerId) && string.IsNullOrEmpty(t.AffiliateId) && string.IsNullOrEmpty(t.Campaign)) + TenantDbContext.SaveChanges(); + } + + if (string.IsNullOrEmpty(t.PartnerId) && string.IsNullOrEmpty(t.AffiliateId) && string.IsNullOrEmpty(t.Campaign)) { var p = TenantDbContext.TenantPartner .Where(r => r.TenantId == t.TenantId) @@ -368,9 +369,9 @@ namespace ASC.Core.Data if (p != null) { TenantDbContext.TenantPartner.Remove(p); - } - } - else + } + } + else { var tenantPartner = new DbTenantPartner { @@ -380,18 +381,18 @@ namespace ASC.Core.Data Campaign = t.Campaign }; - TenantDbContext.TenantPartner.Add(tenantPartner); - } - + TenantDbContext.TenantPartner.Add(tenantPartner); + } + tx.Commit(); - - //CalculateTenantDomain(t); - return t; - } - - public void RemoveTenant(int id, bool auto = false) - { - var postfix = auto ? "_auto_deleted" : "_deleted"; + + //CalculateTenantDomain(t); + return t; + } + + public void RemoveTenant(int id, bool auto = false) + { + var postfix = auto ? "_auto_deleted" : "_deleted"; using var tx = TenantDbContext.Database.BeginTransaction(); @@ -416,28 +417,28 @@ namespace ASC.Core.Data TenantDbContext.SaveChanges(); - tx.Commit(); - } - - public IEnumerable GetTenantVersions() - { + tx.Commit(); + } + + public IEnumerable GetTenantVersions() + { return TenantDbContext.TenantVersion - .Where(r => r.Visible == true) + .Where(r => r.Visible) .Select(r => new TenantVersion(r.Id, r.Version)) - .ToList(); - } - - - public byte[] GetTenantSettings(int tenant, string key) - { + .ToList(); + } + + + public byte[] GetTenantSettings(int tenant, string key) + { return TenantDbContext.CoreSettings .Where(r => r.Tenant == tenant) .Where(r => r.Id == key) .Select(r => r.Value) - .FirstOrDefault(); - } - - public void SetTenantSettings(int tenant, string key, byte[] data) + .FirstOrDefault(); + } + + public void SetTenantSettings(int tenant, string key, byte[] data) { using var tx = TenantDbContext.Database.BeginTransaction(); @@ -465,73 +466,72 @@ namespace ASC.Core.Data TenantDbContext.AddOrUpdate(r => r.CoreSettings, settings); } TenantDbContext.SaveChanges(); - tx.Commit(); - } - - private IQueryable TenantsQuery() + tx.Commit(); + } + + private IQueryable TenantsQuery() { - return TenantDbContext.Tenants; - } - - private void ValidateDomain(string domain, int tenantId, bool validateCharacters) - { - // size - TenantDomainValidator.ValidateDomainLength(domain); - - // characters - if (validateCharacters) - { - TenantDomainValidator.ValidateDomainCharacters(domain); - } - - // forbidden or exists - var exists = false; - domain = domain.ToLowerInvariant(); - if (!exists) - { - if (forbiddenDomains == null) - { - forbiddenDomains = TenantDbContext.TenantForbiden.Select(r => r.Address).ToList(); - } - exists = tenantId != 0 && forbiddenDomains.Contains(domain); - } - if (!exists) - { - exists = 0 < TenantDbContext.Tenants.Where(r => r.Alias == domain && r.Id != tenantId).Count(); - } - if (!exists) - { - exists = 0 < TenantDbContext.Tenants + return TenantDbContext.Tenants; + } + + private void ValidateDomain(string domain, int tenantId, bool validateCharacters) + { + // size + TenantDomainValidator.ValidateDomainLength(domain); + + // characters + if (validateCharacters) + { + TenantDomainValidator.ValidateDomainCharacters(domain); + } + + // forbidden or exists + var exists = false; + + domain = domain.ToLowerInvariant(); + if (forbiddenDomains == null) + { + forbiddenDomains = TenantDbContext.TenantForbiden.Select(r => r.Address).ToList(); + } + exists = tenantId != 0 && forbiddenDomains.Contains(domain); + + if (!exists) + { + exists = TenantDbContext.Tenants.Where(r => r.Alias == domain && r.Id != tenantId).Any(); + } + if (!exists) + { + exists = TenantDbContext.Tenants .Where(r => r.MappedDomain == domain && r.Id != tenantId && !(r.Status == TenantStatus.RemovePending || r.Status == TenantStatus.Restoring)) - .Count(); - } - if (exists) - { - // cut number suffix - while (true) - { - if (6 < domain.Length && char.IsNumber(domain, domain.Length - 1)) - { - domain = domain[0..^1]; - } - else - { - break; - } - } + .Any(); + } + if (exists) + { + // cut number suffix + while (true) + { + if (6 < domain.Length && char.IsNumber(domain, domain.Length - 1)) + { + domain = domain[0..^1]; + } + else + { + break; + } + } var existsTenants = TenantDbContext.TenantForbiden.Where(r => r.Address.StartsWith(domain)).Select(r => r.Address) .Union(TenantDbContext.Tenants.Where(r => r.Alias.StartsWith(domain) && r.Id != tenantId).Select(r => r.Alias)) - .Union(TenantDbContext.Tenants.Where(r => r.MappedDomain.StartsWith(domain) && r.Id != tenantId && r.Status != TenantStatus.RemovePending).Select(r => r.MappedDomain)); - - throw new TenantAlreadyExistsException("Address busy.", existsTenants); - } + .Union(TenantDbContext.Tenants.Where(r => r.MappedDomain.StartsWith(domain) && r.Id != tenantId && r.Status != TenantStatus.RemovePending).Select(r => r.MappedDomain)); + + throw new TenantAlreadyExistsException("Address busy.", existsTenants); + } } protected string GetPasswordHash(Guid userId, string password) { return Hasher.Base64Hash(password + userId + Encoding.UTF8.GetString(MachinePseudoKeys.GetMachineConstant()), HashAlg.SHA512); - } + } } public class TenantUserSecurity @@ -539,5 +539,5 @@ namespace ASC.Core.Data public DbTenant DbTenant { get; set; } public User User { get; set; } public UserSecurity UserSecurity { get; set; } - } -} + } +} diff --git a/common/ASC.Core.Common/Data/DbUserService.cs b/common/ASC.Core.Common/Data/DbUserService.cs index 2ca8648a92..bbfd2b4877 100644 --- a/common/ASC.Core.Common/Data/DbUserService.cs +++ b/common/ASC.Core.Common/Data/DbUserService.cs @@ -239,7 +239,7 @@ namespace ASC.Core.Data public UserInfo GetUserByPasswordHash(int tenant, string login, string passwordHash) { - if (string.IsNullOrEmpty(login)) throw new ArgumentNullException("login"); + if (string.IsNullOrEmpty(login)) throw new ArgumentNullException(nameof(login)); if (Guid.TryParse(login, out var userId)) { @@ -373,7 +373,7 @@ namespace ASC.Core.Data .Select(r => r.Photo) .FirstOrDefault(); - return photo ?? new byte[0]; + return photo ?? Array.Empty(); } public IEnumerable GetUsers(int tenant) @@ -556,7 +556,7 @@ namespace ASC.Core.Data public UserInfo SaveUser(int tenant, UserInfo user) { - if (user == null) throw new ArgumentNullException("user"); + if (user == null) throw new ArgumentNullException(nameof(user)); if (string.IsNullOrEmpty(user.UserName)) throw new ArgumentOutOfRangeException("Empty username."); if (user.ID == default) user.ID = Guid.NewGuid(); @@ -709,17 +709,15 @@ namespace ASC.Core.Data q = q.Where(r => !r.Removed); - if (includeGroups != null && includeGroups.Any()) + if (includeGroups != null && includeGroups.Count > 0) { - Expression or = Expression.Empty(); - foreach (var ig in includeGroups) { q = q.Where(r => r.Groups.Any(a => !a.Removed && a.Tenant == r.Tenant && a.UserId == r.Id && ig.Any(r => r == a.GroupId))); } } - if (excludeGroups != null && excludeGroups.Any()) + if (excludeGroups != null && excludeGroups.Count > 0) { foreach (var eg in excludeGroups) { diff --git a/common/ASC.Core.Common/EF/Context/BaseDbContext.cs b/common/ASC.Core.Common/EF/Context/BaseDbContext.cs index 771201928c..8509b4e565 100644 --- a/common/ASC.Core.Common/EF/Context/BaseDbContext.cs +++ b/common/ASC.Core.Common/EF/Context/BaseDbContext.cs @@ -17,7 +17,6 @@ namespace ASC.Core.Common.EF public class BaseDbContext : DbContext { - public string baseName; public BaseDbContext() { } public BaseDbContext(DbContextOptions options) : base(options) { @@ -29,7 +28,7 @@ namespace ASC.Core.Common.EF public ConnectionStringSettings ConnectionStringSettings { get; set; } protected internal Provider Provider { get; set; } - public static ServerVersion ServerVersion = ServerVersion.Parse("8.0.25"); + public static readonly ServerVersion ServerVersion = ServerVersion.Parse("8.0.25"); protected virtual Dictionary> ProviderContext { get { return null; } @@ -66,7 +65,7 @@ namespace ASC.Core.Common.EF { if (!string.IsNullOrEmpty(MigrateAssembly)) { - r = r.MigrationsAssembly(MigrateAssembly); + r.MigrationsAssembly(MigrateAssembly); } }); break; @@ -133,10 +132,16 @@ namespace ASC.Core.Common.EF } } } - public async ValueTask DisposeAsync() - { - if (Context == null) return; + public ValueTask DisposeAsync() + { + if (Context == null) return ValueTask.CompletedTask; + + return InternalDisposeAsync(); + } + + private async ValueTask InternalDisposeAsync() + { foreach (var c in Context) { if (c != null) diff --git a/common/ASC.Core.Common/EF/Context/ConfigureDbContext.cs b/common/ASC.Core.Common/EF/Context/ConfigureDbContext.cs index a77ab7943f..275913a117 100644 --- a/common/ASC.Core.Common/EF/Context/ConfigureDbContext.cs +++ b/common/ASC.Core.Common/EF/Context/ConfigureDbContext.cs @@ -39,7 +39,7 @@ namespace ASC.Core.Common.EF public class ConfigureMultiRegionalDbContext : IConfigureNamedOptions> where T : BaseDbContext, new() { - public string baseName = "default"; + private readonly string _baseName = "default"; private ConfigurationExtension Configuration { get; } private DbContextManager DbContext { get; } @@ -57,7 +57,7 @@ namespace ASC.Core.Common.EF foreach (var c in Configuration.GetConnectionStrings().Where(r => r.Name.Equals(name, cmp) || r.Name.StartsWith(name + ".", cmp) || - r.Name.Equals(baseName, cmp) || r.Name.StartsWith(baseName + ".", cmp) + r.Name.Equals(_baseName, cmp) || r.Name.StartsWith(_baseName + ".", cmp) )) { context.Context.Add(DbContext.Get(c.Name)); @@ -66,7 +66,7 @@ namespace ASC.Core.Common.EF public void Configure(MultiRegionalDbContext context) { - Configure(baseName, context); + Configure(_baseName, context); } } } diff --git a/common/ASC.Core.Common/EF/LinqExtensions.cs b/common/ASC.Core.Common/EF/LinqExtensions.cs index aebb788ec9..c2959d56b3 100644 --- a/common/ASC.Core.Common/EF/LinqExtensions.cs +++ b/common/ASC.Core.Common/EF/LinqExtensions.cs @@ -31,7 +31,7 @@ namespace ASC.Core.Common.EF private static PropertyInfo GetPropertyInfo(Type objType, string name) { var properties = objType.GetProperties(); - var matchedProperty = properties.FirstOrDefault(p => p.Name.ToLower() == name.ToLower()); + var matchedProperty = properties.FirstOrDefault(p => p.Name.Equals(name, StringComparison.OrdinalIgnoreCase)); if (matchedProperty == null) throw new ArgumentException("name"); diff --git a/common/ASC.Core.Common/Encryption/EncryptionSettings.cs b/common/ASC.Core.Common/Encryption/EncryptionSettings.cs index cdac5e98a1..7764765c15 100644 --- a/common/ASC.Core.Common/Encryption/EncryptionSettings.cs +++ b/common/ASC.Core.Common/Encryption/EncryptionSettings.cs @@ -131,19 +131,18 @@ namespace ASC.Core.Encryption if (length < 1 || length > 128) { - throw new ArgumentException("password_length_incorrect", "length"); + throw new ArgumentException("password_length_incorrect", nameof(length)); } if (numberOfNonAlphanumericCharacters > length || numberOfNonAlphanumericCharacters < 0) { - throw new ArgumentException("min_required_non_alphanumeric_characters_incorrect", "numberOfNonAlphanumericCharacters"); + throw new ArgumentException("min_required_non_alphanumeric_characters_incorrect", nameof(numberOfNonAlphanumericCharacters)); } - var array = new byte[length]; var array2 = new char[length]; var num = 0; - array = RandomNumberGenerator.GetBytes(length); + var array = RandomNumberGenerator.GetBytes(length); for (var i = 0; i < length; i++) { @@ -172,16 +171,15 @@ namespace ASC.Core.Encryption if (num < numberOfNonAlphanumericCharacters) { - var random = new Random(); for (var j = 0; j < numberOfNonAlphanumericCharacters - num; j++) { int num3; do { - num3 = random.Next(0, length); + num3 = RandomNumberGenerator.GetInt32(0, length); } while (!char.IsLetterOrDigit(array2[num3])); - array2[num3] = punctuations[random.Next(0, punctuations.Length)]; + array2[num3] = punctuations[RandomNumberGenerator.GetInt32(0, punctuations.Length)]; } } diff --git a/common/ASC.Core.Common/MultiRegionHostedSolution.cs b/common/ASC.Core.Common/MultiRegionHostedSolution.cs index 2bb36d0b11..e8d11ae066 100644 --- a/common/ASC.Core.Common/MultiRegionHostedSolution.cs +++ b/common/ASC.Core.Common/MultiRegionHostedSolution.cs @@ -107,7 +107,7 @@ namespace ASC.Core error = exception; } } - if (!result.Any() && error != null) + if (result.Count == 0 && error != null) { throw error; } @@ -204,11 +204,10 @@ namespace ASC.Core private void Initialize() { var connectionStrings = ConfigurationExtension.GetConnectionStrings(); - var dbConnectionStrings = ConfigurationExtension.GetConnectionStrings(dbid); if (Convert.ToBoolean(Configuraion["core.multi-hosted.config-only"] ?? "false")) { - foreach (var cs in ConfigurationExtension.GetConnectionStrings()) + foreach (var cs in connectionStrings) { if (cs.Name.StartsWith(dbid + ".")) { diff --git a/common/ASC.Core.Common/Notify/Channels/SenderChannel.cs b/common/ASC.Core.Common/Notify/Channels/SenderChannel.cs index 5f83c54ac8..92f8b1eda9 100644 --- a/common/ASC.Core.Common/Notify/Channels/SenderChannel.cs +++ b/common/ASC.Core.Common/Notify/Channels/SenderChannel.cs @@ -35,7 +35,6 @@ namespace ASC.Notify.Channels { private readonly ISink firstSink; private readonly ISink senderSink; - private readonly Context context; public string SenderName @@ -47,18 +46,19 @@ namespace ASC.Notify.Channels public SenderChannel(Context context, string senderName, ISink decorateSink, ISink senderSink) { - this.context = context ?? throw new ArgumentNullException("context"); - this.SenderName = senderName ?? throw new ArgumentNullException("senderName"); + this.SenderName = senderName ?? throw new ArgumentNullException(nameof(senderName)); this.firstSink = decorateSink; - this.senderSink = senderSink ?? throw new ApplicationException(string.Format("channel with tag {0} not created sender sink", senderName)); + this.senderSink = senderSink ?? throw new ApplicationException($"channel with tag {senderName} not created sender sink"); - var dispatcherSink = new DispatchSink(SenderName, this.context.DispatchEngine); + + context = context ?? throw new ArgumentNullException(nameof(context)); + var dispatcherSink = new DispatchSink(SenderName, context.DispatchEngine); this.firstSink = AddSink(firstSink, dispatcherSink); } public void SendAsync(INoticeMessage message) { - if (message == null) throw new ArgumentNullException("message"); + if (message == null) throw new ArgumentNullException(nameof(message)); firstSink.ProcessMessageAsync(message); } diff --git a/common/ASC.Core.Common/Notify/Context.cs b/common/ASC.Core.Common/Notify/Context.cs index c99517a4b5..f158e3035f 100644 --- a/common/ASC.Core.Common/Notify/Context.cs +++ b/common/ASC.Core.Common/Notify/Context.cs @@ -131,7 +131,7 @@ namespace ASC.Notify var pattern = source.GetPatternProvider().GetPattern(a, s); if (pattern == null) { - throw new NotifyException(string.Format("In notify source {0} pattern not found for action {1} and sender {2}", source.ID, a.ID, s)); + throw new NotifyException($"In notify source {source.ID} pattern not found for action {a.ID} and sender {s}"); } } catch (Exception error) diff --git a/common/ASC.Core.Common/Notify/Cron/CronExpression.cs b/common/ASC.Core.Common/Notify/Cron/CronExpression.cs index 555266d412..ea1e8fe9c9 100644 --- a/common/ASC.Core.Common/Notify/Cron/CronExpression.cs +++ b/common/ASC.Core.Common/Notify/Cron/CronExpression.cs @@ -277,13 +277,13 @@ namespace ASC.Notify.Cron break; } - if (exprOn == DayOfMonth && expr.IndexOf('L') != -1 && expr.Length > 1 && expr.IndexOf(",") >= 0) + if (exprOn == DayOfMonth && expr.IndexOf('L') != -1 && expr.Length > 1 && expr.IndexOf(',') >= 0) { throw new FormatException( "Support for specifying 'L' and 'LW' with other days of the month is not implemented"); } - if (exprOn == DayOfWeek && expr.IndexOf('L') != -1 && expr.Length > 1 && expr.IndexOf(",") >= 0) + if (exprOn == DayOfWeek && expr.IndexOf('L') != -1 && expr.Length > 1 && expr.IndexOf(',') >= 0) { throw new FormatException( "Support for specifying 'L' with other days of the week is not implemented"); @@ -350,8 +350,7 @@ namespace ASC.Notify.Cron sval = GetMonthNumber(sub) + 1; if (sval <= 0) { - throw new FormatException(string.Format(CultureInfo.InvariantCulture, - "Invalid Month value: '{0}'", sub)); + throw new FormatException($"Invalid Month value: '{sub}'"); } if (s.Length > i + 3) { @@ -363,8 +362,7 @@ namespace ASC.Notify.Cron eval = GetMonthNumber(sub) + 1; if (eval <= 0) { - throw new FormatException( - string.Format(CultureInfo.InvariantCulture, "Invalid Month value: '{0}'", sub)); + throw new FormatException($"Invalid Month value: '{sub}'"); } } } @@ -374,8 +372,7 @@ namespace ASC.Notify.Cron sval = GetDayOfWeekNumber(sub); if (sval < 0) { - throw new FormatException(string.Format(CultureInfo.InvariantCulture, - "Invalid Day-of-Week value: '{0}'", sub)); + throw new FormatException($"Invalid Day-of-Week value: '{sub}'"); } if (s.Length > i + 3) { @@ -387,8 +384,7 @@ namespace ASC.Notify.Cron eval = GetDayOfWeekNumber(sub); if (eval < 0) { - throw new FormatException( - string.Format(CultureInfo.InvariantCulture, "Invalid Day-of-Week value: '{0}'", sub)); + throw new FormatException($"Invalid Day-of-Week value: '{sub}'"); } } else if (c == '#') @@ -417,21 +413,20 @@ namespace ASC.Notify.Cron } else { - throw new FormatException( - string.Format(CultureInfo.InvariantCulture, "Illegal characters for this position: '{0}'", sub)); + throw new FormatException($"Illegal characters for this position: '{sub}'"); } if (eval != -1) { incr = 1; } AddToSet(sval, eval, incr, type); - return (i + 3); + return i + 3; } if (c == '?') { i++; if ((i + 1) < s.Length - && (s[i] != ' ' && s[i + 1] != '\t')) + && s[i] != ' ' && s[i + 1] != '\t') { throw new FormatException("Illegal character after '?': " + s[i]); @@ -552,8 +547,8 @@ namespace ASC.Notify.Cron if (c >= '0' && c <= '9') { var vs = GetValue(val, s, i); - val = vs.theValue; - i = vs.pos; + val = vs.TheValue; + i = vs.Pos; } i = CheckNext(i, s, val, type); return i; @@ -670,11 +665,11 @@ namespace ASC.Notify.Cron if (c >= '0' && c <= '9') { var vs = GetValue(v, s, i); - var v1 = vs.theValue; + var v1 = vs.TheValue; end = v1; - i = vs.pos; + i = vs.Pos; } - if (i < s.Length && ((s[i]) == '/')) + if (i < s.Length && (s[i] == '/')) { i++; c = s[i]; @@ -689,9 +684,9 @@ namespace ASC.Notify.Cron if (c >= '0' && c <= '9') { var vs = GetValue(v2, s, i); - var v3 = vs.theValue; + var v3 = vs.TheValue; AddToSet(val, end, v3, type); - i = vs.pos; + i = vs.Pos; return i; } else @@ -721,9 +716,9 @@ namespace ASC.Notify.Cron if (c >= '0' && c <= '9') { var vs = GetValue(v2, s, i); - var v3 = vs.theValue; + var v3 = vs.TheValue; AddToSet(val, end, v3, type); - i = vs.pos; + i = vs.Pos; return i; } else @@ -742,43 +737,43 @@ namespace ASC.Notify.Cron var buf = new StringBuilder(); buf.Append("seconds: "); buf.Append(GetExpressionSetSummary(seconds)); - buf.Append("\n"); + buf.Append('\n'); buf.Append("minutes: "); buf.Append(GetExpressionSetSummary(minutes)); - buf.Append("\n"); + buf.Append('\n'); buf.Append("hours: "); buf.Append(GetExpressionSetSummary(hours)); - buf.Append("\n"); + buf.Append('\n'); buf.Append("daysOfMonth: "); buf.Append(GetExpressionSetSummary(daysOfMonth)); - buf.Append("\n"); + buf.Append('\n'); buf.Append("months: "); buf.Append(GetExpressionSetSummary(months)); - buf.Append("\n"); + buf.Append('\n'); buf.Append("daysOfWeek: "); buf.Append(GetExpressionSetSummary(daysOfWeek)); - buf.Append("\n"); + buf.Append('\n'); buf.Append("lastdayOfWeek: "); buf.Append(lastdayOfWeek); - buf.Append("\n"); + buf.Append('\n'); buf.Append("nearestWeekday: "); buf.Append(nearestWeekday); - buf.Append("\n"); + buf.Append('\n'); buf.Append("NthDayOfWeek: "); buf.Append(nthdayOfWeek); - buf.Append("\n"); + buf.Append('\n'); buf.Append("lastdayOfMonth: "); buf.Append(lastdayOfMonth); - buf.Append("\n"); + buf.Append('\n'); buf.Append("calendardayOfWeek: "); buf.Append(calendardayOfWeek); - buf.Append("\n"); + buf.Append('\n'); buf.Append("calendardayOfMonth: "); buf.Append(calendardayOfMonth); - buf.Append("\n"); + buf.Append('\n'); buf.Append("years: "); buf.Append(GetExpressionSetSummary(years)); - buf.Append("\n"); + buf.Append('\n'); return buf.ToString(); } @@ -799,7 +794,7 @@ namespace ASC.Notify.Cron var val = iVal.ToString(CultureInfo.InvariantCulture); if (!first) { - buf.Append(","); + buf.Append(','); } buf.Append(val); first = false; @@ -811,7 +806,7 @@ namespace ASC.Notify.Cron { for (; i < s.Length && (s[i] == ' ' || s[i] == '\t'); i++) { - ; + } return i; } @@ -820,7 +815,7 @@ namespace ASC.Notify.Cron { for (; i < s.Length && (s[i] != ' ' || s[i] != '\t'); i++) { - ; + } return i; } @@ -1009,10 +1004,11 @@ namespace ASC.Notify.Cron protected virtual ValueSet GetValue(int v, string s, int i) { var c = s[i]; - var s1 = v.ToString(CultureInfo.InvariantCulture); + var sb = new StringBuilder(); + sb.Append(v.ToString(CultureInfo.InvariantCulture)); while (c >= '0' && c <= '9') { - s1 += c; + sb.Append(c); i++; if (i >= s.Length) { @@ -1023,13 +1019,13 @@ namespace ASC.Notify.Cron var val = new ValueSet(); if (i < s.Length) { - val.pos = i; + val.Pos = i; } else { - val.pos = i + 1; + val.Pos = i + 1; } - val.theValue = Convert.ToInt32(s1, CultureInfo.InvariantCulture); + val.TheValue = Convert.ToInt32(sb.ToString(), CultureInfo.InvariantCulture); return val; } @@ -1121,7 +1117,7 @@ namespace ASC.Notify.Cron } else { - sec = ((int)seconds.First()); + sec = (int)seconds.First(); d = d.AddMinutes(1); } d = new DateTime(d.Year, d.Month, d.Day, d.Hour, d.Minute, sec, d.Millisecond); @@ -1133,7 +1129,7 @@ namespace ASC.Notify.Cron if (st != null && st.Count != 0) { t = min; - min = ((int)st.First()); + min = (int)st.First(); } else { @@ -1253,7 +1249,7 @@ namespace ASC.Notify.Cron tcal = new DateTime(tcal.Year, mon, day, hr, min, sec); if (tcal.ToUniversalTime() < afterTimeUtc) { - day = ((int)daysOfMonth.First()); + day = (int)daysOfMonth.First(); mon++; } } @@ -1271,7 +1267,7 @@ namespace ASC.Notify.Cron } else { - day = ((int)daysOfMonth.First()); + day = (int)daysOfMonth.First(); mon++; } if (day != t || mon != tmon) @@ -1299,9 +1295,9 @@ namespace ASC.Notify.Cron { if (lastdayOfWeek) { - var dow = ((int)daysOfWeek.First()); + var dow = (int)daysOfWeek.First(); - var cDow = ((int)d.DayOfWeek); + var cDow = (int)d.DayOfWeek; var daysToAdd = 0; if (cDow < dow) { @@ -1342,9 +1338,9 @@ namespace ASC.Notify.Cron } else if (nthdayOfWeek != 0) { - var dow = ((int)daysOfWeek.First()); + var dow = (int)daysOfWeek.First(); - var cDow = ((int)d.DayOfWeek); + var cDow = (int)d.DayOfWeek; var daysToAdd = 0; if (cDow < dow) { @@ -1393,12 +1389,12 @@ namespace ASC.Notify.Cron else { var cDow = ((int)d.DayOfWeek) + 1; - var dow = ((int)daysOfWeek.First()); + var dow = (int)daysOfWeek.First(); st = daysOfWeek.TailSet(cDow); if (st != null && st.Count > 0) { - dow = ((int)st.First()); + dow = (int)st.First(); } var daysToAdd = 0; if (cDow < dow) @@ -1448,15 +1444,15 @@ namespace ASC.Notify.Cron return null; } - st = months.TailSet((mon)); + st = months.TailSet(mon); if (st != null && st.Count != 0) { t = mon; - mon = ((int)st.First()); + mon = (int)st.First(); } else { - mon = ((int)months.First()); + mon = (int)months.First(); year++; } if (mon != t) @@ -1466,11 +1462,11 @@ namespace ASC.Notify.Cron } d = new DateTime(d.Year, mon, d.Day, d.Hour, d.Minute, d.Second); year = d.Year; - st = years.TailSet((year)); + st = years.TailSet(year); if (st != null && st.Count != 0) { t = year; - year = ((int)st.First()); + year = (int)st.First(); } else { @@ -1531,7 +1527,7 @@ namespace ASC.Notify.Cron public class ValueSet { - public int pos; - public int theValue; + public int Pos { get; set; } + public int TheValue { get; set; } } } \ No newline at end of file diff --git a/common/ASC.Core.Common/Notify/Cron/ISet.cs b/common/ASC.Core.Common/Notify/Cron/ISet.cs index 10f8cb5538..3995ba2896 100644 --- a/common/ASC.Core.Common/Notify/Cron/ISet.cs +++ b/common/ASC.Core.Common/Notify/Cron/ISet.cs @@ -37,7 +37,7 @@ namespace ASC.Notify.Cron #endregion - public interface ISet : ICollection, IList + public interface ISet : IList { #region Methods diff --git a/common/ASC.Core.Common/Notify/Cron/TreeSet.cs b/common/ASC.Core.Common/Notify/Cron/TreeSet.cs index 4624d5528c..5caa0046ad 100644 --- a/common/ASC.Core.Common/Notify/Cron/TreeSet.cs +++ b/common/ASC.Core.Common/Notify/Cron/TreeSet.cs @@ -139,8 +139,8 @@ namespace ASC.Notify.Cron private bool AddWithoutSorting(object obj) { - bool inserted; - if (!(inserted = Contains(obj))) + bool inserted = Contains(obj); + if (!inserted) { base.Add(obj); } diff --git a/common/ASC.Core.Common/Notify/DirectSubscriptionProvider.cs b/common/ASC.Core.Common/Notify/DirectSubscriptionProvider.cs index 7ae665ae8c..07b0b2088a 100644 --- a/common/ASC.Core.Common/Notify/DirectSubscriptionProvider.cs +++ b/common/ASC.Core.Common/Notify/DirectSubscriptionProvider.cs @@ -41,32 +41,32 @@ namespace ASC.Core.Notify public DirectSubscriptionProvider(string sourceID, SubscriptionManager subscriptionManager, IRecipientProvider recipientProvider) { - if (string.IsNullOrEmpty(sourceID)) throw new ArgumentNullException("sourceID"); + if (string.IsNullOrEmpty(sourceID)) throw new ArgumentNullException(nameof(sourceID)); this.sourceID = sourceID; - this.subscriptionManager = subscriptionManager ?? throw new ArgumentNullException("subscriptionManager"); - this.recipientProvider = recipientProvider ?? throw new ArgumentNullException("recipientProvider"); + this.subscriptionManager = subscriptionManager ?? throw new ArgumentNullException(nameof(subscriptionManager)); + this.recipientProvider = recipientProvider ?? throw new ArgumentNullException(nameof(recipientProvider)); } public object GetSubscriptionRecord(INotifyAction action, IRecipient recipient, string objectID) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); return subscriptionManager.GetSubscriptionRecord(sourceID, action.ID, recipient.ID, objectID); } public string[] GetSubscriptions(INotifyAction action, IRecipient recipient, bool checkSubscribe = true) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); return subscriptionManager.GetSubscriptions(sourceID, action.ID, recipient.ID, checkSubscribe); } public IRecipient[] GetRecipients(INotifyAction action, string objectID) { - if (action == null) throw new ArgumentNullException("action"); + if (action == null) throw new ArgumentNullException(nameof(action)); return subscriptionManager.GetRecipients(sourceID, action.ID, objectID) .Select(r => recipientProvider.GetRecipient(r)) @@ -76,53 +76,53 @@ namespace ASC.Core.Notify public string[] GetSubscriptionMethod(INotifyAction action, IRecipient recipient) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); return subscriptionManager.GetSubscriptionMethod(sourceID, action.ID, recipient.ID); } public void UpdateSubscriptionMethod(INotifyAction action, IRecipient recipient, params string[] senderNames) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); subscriptionManager.UpdateSubscriptionMethod(sourceID, action.ID, recipient.ID, senderNames); } public bool IsUnsubscribe(IDirectRecipient recipient, INotifyAction action, string objectID) { - if (recipient == null) throw new ArgumentNullException("recipient"); - if (action == null) throw new ArgumentNullException("action"); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); + if (action == null) throw new ArgumentNullException(nameof(action)); return subscriptionManager.IsUnsubscribe(sourceID, recipient.ID, action.ID, objectID); } public void Subscribe(INotifyAction action, string objectID, IRecipient recipient) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); subscriptionManager.Subscribe(sourceID, action.ID, objectID, recipient.ID); } public void UnSubscribe(INotifyAction action, string objectID, IRecipient recipient) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); subscriptionManager.Unsubscribe(sourceID, action.ID, objectID, recipient.ID); } public void UnSubscribe(INotifyAction action) { - if (action == null) throw new ArgumentNullException("action"); + if (action == null) throw new ArgumentNullException(nameof(action)); subscriptionManager.UnsubscribeAll(sourceID, action.ID); } public void UnSubscribe(INotifyAction action, string objectID) { - if (action == null) throw new ArgumentNullException("action"); + if (action == null) throw new ArgumentNullException(nameof(action)); subscriptionManager.UnsubscribeAll(sourceID, action.ID, objectID); } diff --git a/common/ASC.Core.Common/Notify/EmailSenderSink.cs b/common/ASC.Core.Common/Notify/EmailSenderSink.cs index 3b99a635fc..abcca2d244 100644 --- a/common/ASC.Core.Common/Notify/EmailSenderSink.cs +++ b/common/ASC.Core.Common/Notify/EmailSenderSink.cs @@ -49,7 +49,7 @@ namespace ASC.Core.Notify public EmailSenderSink(INotifySender sender, IServiceProvider serviceProvider, IOptionsMonitor options) { - this.sender = sender ?? throw new ArgumentNullException("sender"); + this.sender = sender ?? throw new ArgumentNullException(nameof(sender)); ServiceProvider = serviceProvider; Log = options.Get("ASC.Notify"); } diff --git a/common/ASC.Core.Common/Notify/Engine/DispatchEngine.cs b/common/ASC.Core.Common/Notify/Engine/DispatchEngine.cs index b9686b7a9b..6f5d6a8d81 100644 --- a/common/ASC.Core.Common/Notify/Engine/DispatchEngine.cs +++ b/common/ASC.Core.Common/Notify/Engine/DispatchEngine.cs @@ -47,7 +47,7 @@ namespace ASC.Notify.Engine { log = options.Get("ASC.Notify"); logMessages = options.Get("ASC.Notify.Messages"); - this.context = context ?? throw new ArgumentNullException("context"); + this.context = context ?? throw new ArgumentNullException(nameof(context)); logOnly = "log".Equals(configuration["core:notify:postman"], StringComparison.InvariantCultureIgnoreCase); log.DebugFormat("LogOnly: {0}", logOnly); } diff --git a/common/ASC.Core.Common/Notify/Engine/InterceptorStorage.cs b/common/ASC.Core.Common/Notify/Engine/InterceptorStorage.cs index 41ed08dc5d..89f7136fdc 100644 --- a/common/ASC.Core.Common/Notify/Engine/InterceptorStorage.cs +++ b/common/ASC.Core.Common/Notify/Engine/InterceptorStorage.cs @@ -54,8 +54,8 @@ namespace ASC.Notify.Engine public void Add(ISendInterceptor interceptor) { - if (interceptor == null) throw new ArgumentNullException("interceptor"); - if (string.IsNullOrEmpty(interceptor.Name)) throw new ArgumentException("empty name property", "interceptor"); + if (interceptor == null) throw new ArgumentNullException(nameof(interceptor)); + if (string.IsNullOrEmpty(interceptor.Name)) throw new ArgumentException("empty name property", nameof(interceptor)); switch (interceptor.Lifetime) { @@ -72,7 +72,7 @@ namespace ASC.Notify.Engine public ISendInterceptor Get(string name) { - if (string.IsNullOrEmpty(name)) throw new ArgumentException("empty name", "name"); + if (string.IsNullOrEmpty(name)) throw new ArgumentException("empty name", nameof(name)); var result = GetInternal(name, CallInterceptors); if (result == null) result = GetInternal(name, globalInterceptors); return result; @@ -80,7 +80,7 @@ namespace ASC.Notify.Engine public void Remove(string name) { - if (string.IsNullOrEmpty(name)) throw new ArgumentException("empty name", "name"); + if (string.IsNullOrEmpty(name)) throw new ArgumentException("empty name", nameof(name)); RemoveInternal(name, CallInterceptors); RemoveInternal(name, globalInterceptors); @@ -119,7 +119,7 @@ namespace ASC.Notify.Engine private ISendInterceptor GetInternal(string name, Dictionary storage) { - ISendInterceptor interceptor = null; + ISendInterceptor interceptor; lock (syncRoot) { storage.TryGetValue(name, out interceptor); diff --git a/common/ASC.Core.Common/Notify/Engine/NotifyEngine.cs b/common/ASC.Core.Common/Notify/Engine/NotifyEngine.cs index 23c6c7fe8d..3c13771148 100644 --- a/common/ASC.Core.Common/Notify/Engine/NotifyEngine.cs +++ b/common/ASC.Core.Common/Notify/Engine/NotifyEngine.cs @@ -76,7 +76,7 @@ namespace ASC.Notify.Engine public NotifyEngine(Context context, IServiceProvider serviceProvider) { - this.context = context ?? throw new ArgumentNullException("context"); + this.context = context ?? throw new ArgumentNullException(nameof(context)); log = serviceProvider.GetService>().Get("ASC.Notify"); ServiceProvider = serviceProvider; notifyScheduler = new Thread(NotifyScheduler) { IsBackground = true, Name = "NotifyScheduler" }; @@ -102,8 +102,8 @@ namespace ASC.Notify.Engine internal void RegisterSendMethod(Action method, string cron) { - if (method == null) throw new ArgumentNullException("method"); - if (string.IsNullOrEmpty(cron)) throw new ArgumentNullException("cron"); + if (method == null) throw new ArgumentNullException(nameof(method)); + if (string.IsNullOrEmpty(cron)) throw new ArgumentNullException(nameof(cron)); var w = new SendMethodWrapper(method, cron, log); lock (sendMethods) @@ -121,7 +121,7 @@ namespace ASC.Notify.Engine internal void UnregisterSendMethod(Action method) { - if (method == null) throw new ArgumentNullException("method"); + if (method == null) throw new ArgumentNullException(nameof(method)); lock (sendMethods) { @@ -205,7 +205,7 @@ namespace ASC.Notify.Engine NotifyRequest request = null; lock (requests) { - if (requests.Any()) + if (requests.Count > 0) { request = requests.Dequeue(); } @@ -254,14 +254,14 @@ namespace ASC.Notify.Engine sendResponces.AddRange(SendGroupNotify(request, serviceScope)); } - NotifyResult result = null; - if (sendResponces == null || sendResponces.Count == 0) + NotifyResult result; + if (sendResponces.Count == 0) { result = new NotifyResult(SendResult.OK, sendResponces); } else { - result = new NotifyResult(sendResponces.Aggregate((SendResult)0, (s, r) => s |= r.Result), sendResponces); + result = new NotifyResult(sendResponces.Aggregate((SendResult)0, (s, r) => r.Result), sendResponces); } log.Debug(result); return result; @@ -346,7 +346,7 @@ namespace ASC.Notify.Engine private List SendDirectNotify(NotifyRequest request, IServiceScope serviceScope) { - if (!(request.Recipient is IDirectRecipient)) throw new ArgumentException("request.Recipient not IDirectRecipient", "request"); + if (!(request.Recipient is IDirectRecipient)) throw new ArgumentException("request.Recipient not IDirectRecipient", nameof(request)); var responses = new List(); var response = CheckPreventInterceptors(request, InterceptorPlace.DirectSend, serviceScope, null); @@ -386,7 +386,7 @@ namespace ASC.Notify.Engine } else { - response = new SendResponse(request.NotifyAction, sendertag, request.Recipient, new NotifyException(string.Format("Not registered sender \"{0}\".", sendertag))); + response = new SendResponse(request.NotifyAction, sendertag, request.Recipient, new NotifyException($"Not registered sender \"{sendertag}\".")); } responses.Add(response); } @@ -401,7 +401,7 @@ namespace ASC.Notify.Engine private SendResponse SendDirectNotify(NotifyRequest request, ISenderChannel channel, IServiceScope serviceScope) { - if (!(request.Recipient is IDirectRecipient)) throw new ArgumentException("request.Recipient not IDirectRecipient", "request"); + if (!(request.Recipient is IDirectRecipient)) throw new ArgumentException("request.Recipient not IDirectRecipient", nameof(request)); request.CurrentSender = channel.SenderName; @@ -419,13 +419,13 @@ namespace ASC.Notify.Engine private SendResponse CreateNoticeMessageFromNotifyRequest(NotifyRequest request, string sender, IServiceScope serviceScope, out NoticeMessage noticeMessage) { - if (request == null) throw new ArgumentNullException("request"); + if (request == null) throw new ArgumentNullException(nameof(request)); var recipientProvider = request.GetRecipientsProvider(serviceScope); var recipient = request.Recipient as IDirectRecipient; var addresses = recipient.Addresses; - if (addresses == null || !addresses.Any()) + if (addresses == null || addresses.Length == 0) { addresses = recipientProvider.GetRecipientAddresses(request.Recipient as IDirectRecipient, sender); recipient = new DirectRecipient(request.Recipient.ID, request.Recipient.Name, addresses); @@ -507,7 +507,7 @@ namespace ASC.Notify.Engine var subscriptionProvider = request.GetSubscriptionProvider(serviceScope); var senderNames = new List(); - senderNames.AddRange(subscriptionProvider.GetSubscriptionMethod(request.NotifyAction, request.Recipient) ?? new string[0]); + senderNames.AddRange(subscriptionProvider.GetSubscriptionMethod(request.NotifyAction, request.Recipient) ?? Array.Empty()); senderNames.AddRange(request.Arguments.OfType().Select(tag => (string)tag.Value)); request.SenderNames = senderNames.ToArray(); @@ -535,7 +535,7 @@ namespace ASC.Notify.Engine pattern = apProvider.GetPattern(request.NotifyAction, senderName); } - request.Patterns[i] = pattern ?? throw new NotifyException(string.Format("For action \"{0}\" by sender \"{1}\" no one patterns getted.", request.NotifyAction.ID, senderName)); + request.Patterns[i] = pattern ?? throw new NotifyException($"For action \"{request.NotifyAction.ID}\" by sender \"{senderName}\" no one patterns getted."); } } } @@ -554,12 +554,12 @@ namespace ASC.Notify.Engine { throw new NotifyException(string.Format("For pattern \"{0}\" formatter not instanced.", pattern), exc); } - var tags = new string[0]; + var tags = Array.Empty(); try { if (formatter != null) { - tags = formatter.GetTags(pattern) ?? new string[0]; + tags = formatter.GetTags(pattern) ?? Array.Empty(); } } catch (Exception exc) @@ -575,7 +575,7 @@ namespace ASC.Notify.Engine } - private class SendMethodWrapper + private sealed class SendMethodWrapper { private readonly object locker = new object(); private readonly CronExpression cronExpression; diff --git a/common/ASC.Core.Common/Notify/Engine/NotifyRequest.cs b/common/ASC.Core.Common/Notify/Engine/NotifyRequest.cs index 12ae7ef5c3..b1e4151d1b 100644 --- a/common/ASC.Core.Common/Notify/Engine/NotifyRequest.cs +++ b/common/ASC.Core.Common/Notify/Engine/NotifyRequest.cs @@ -75,9 +75,9 @@ namespace ASC.Notify.Engine RequaredTags = new List(); Interceptors = new List(); - NotifySource = notifySource ?? throw new ArgumentNullException("notifySource"); - Recipient = recipient ?? throw new ArgumentNullException("recipient"); - NotifyAction = action ?? throw new ArgumentNullException("action"); + NotifySource = notifySource ?? throw new ArgumentNullException(nameof(notifySource)); + Recipient = recipient ?? throw new ArgumentNullException(nameof(recipient)); + NotifyAction = action ?? throw new ArgumentNullException(nameof(action)); ObjectID = objectID; IsNeedCheckSubscriptions = true; @@ -118,14 +118,14 @@ namespace ASC.Notify.Engine var index = Array.IndexOf(SenderNames, senderName); if (index < 0) { - throw new ApplicationException(string.Format("Sender with tag {0} dnot found", senderName)); + throw new ApplicationException($"Sender with tag {senderName} dnot found"); } return Patterns[index]; } internal NotifyRequest Split(IRecipient recipient) { - if (recipient == null) throw new ArgumentNullException("recipient"); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); var newRequest = new NotifyRequest(NotifySource, NotifyAction, ObjectID, recipient) { SenderNames = SenderNames, diff --git a/common/ASC.Core.Common/Notify/Engine/SendInterceptorSkeleton.cs b/common/ASC.Core.Common/Notify/Engine/SendInterceptorSkeleton.cs index 25d6104f20..e6b56d6601 100644 --- a/common/ASC.Core.Common/Notify/Engine/SendInterceptorSkeleton.cs +++ b/common/ASC.Core.Common/Notify/Engine/SendInterceptorSkeleton.cs @@ -44,8 +44,8 @@ namespace ASC.Notify.Engine public SendInterceptorSkeleton(string name, InterceptorPlace preventPlace, InterceptorLifetime lifetime, Func sendInterceptor) { - if (string.IsNullOrEmpty(name)) throw new ArgumentException("Empty name.", "name"); - if (sendInterceptor == null) throw new ArgumentNullException("sendInterceptor"); + if (string.IsNullOrEmpty(name)) throw new ArgumentException("Empty name.", nameof(name)); + if (sendInterceptor == null) throw new ArgumentNullException(nameof(sendInterceptor)); method = sendInterceptor; Name = name; diff --git a/common/ASC.Core.Common/Notify/Jabber/JabberServiceClient.cs b/common/ASC.Core.Common/Notify/Jabber/JabberServiceClient.cs index 838cc814dd..23f176a39b 100644 --- a/common/ASC.Core.Common/Notify/Jabber/JabberServiceClient.cs +++ b/common/ASC.Core.Common/Notify/Jabber/JabberServiceClient.cs @@ -94,7 +94,7 @@ namespace ASC.Core.Notify.Jabber public int GetNewMessagesCount() { - var result = 0; + const int result = 0; if (IsServiceProbablyNotAvailable()) return result; using (var service = GetService()) diff --git a/common/ASC.Core.Common/Notify/Jabber/JabberServiceClientWcf.cs b/common/ASC.Core.Common/Notify/Jabber/JabberServiceClientWcf.cs index b0d2a2b178..5767129aad 100644 --- a/common/ASC.Core.Common/Notify/Jabber/JabberServiceClientWcf.cs +++ b/common/ASC.Core.Common/Notify/Jabber/JabberServiceClientWcf.cs @@ -24,7 +24,6 @@ */ -using System; using System.Collections.Generic; using ASC.Common.Module; @@ -32,7 +31,7 @@ using ASC.Core.Common.Notify.Jabber; namespace ASC.Core.Notify.Jabber { - public class JabberServiceClientWcf : BaseWcfClient, IJabberService, IDisposable + public class JabberServiceClientWcf : BaseWcfClient, IJabberService { public JabberServiceClientWcf() { diff --git a/common/ASC.Core.Common/Notify/JabberSenderSink.cs b/common/ASC.Core.Common/Notify/JabberSenderSink.cs index 868d9edd4a..d491898849 100644 --- a/common/ASC.Core.Common/Notify/JabberSenderSink.cs +++ b/common/ASC.Core.Common/Notify/JabberSenderSink.cs @@ -44,7 +44,7 @@ namespace ASC.Core.Notify public JabberSenderSink(INotifySender sender, IServiceProvider serviceProvider) { - this.sender = sender ?? throw new ArgumentNullException("sender"); + this.sender = sender ?? throw new ArgumentNullException(nameof(sender)); ServiceProvider = serviceProvider; } diff --git a/common/ASC.Core.Common/Notify/Messages/NoticeMessage.cs b/common/ASC.Core.Common/Notify/Messages/NoticeMessage.cs index c3b86fa401..a764d5400f 100644 --- a/common/ASC.Core.Common/Notify/Messages/NoticeMessage.cs +++ b/common/ASC.Core.Common/Notify/Messages/NoticeMessage.cs @@ -48,25 +48,25 @@ namespace ASC.Notify.Messages public NoticeMessage(IDirectRecipient recipient, INotifyAction action, string objectID) { - Recipient = recipient ?? throw new ArgumentNullException("recipient"); + Recipient = recipient ?? throw new ArgumentNullException(nameof(recipient)); Action = action; ObjectID = objectID; } public NoticeMessage(IDirectRecipient recipient, INotifyAction action, string objectID, IPattern pattern) { - Recipient = recipient ?? throw new ArgumentNullException("recipient"); + Recipient = recipient ?? throw new ArgumentNullException(nameof(recipient)); Action = action; - Pattern = pattern ?? throw new ArgumentNullException("pattern"); + Pattern = pattern ?? throw new ArgumentNullException(nameof(pattern)); ObjectID = objectID; ContentType = pattern.ContentType; } public NoticeMessage(IDirectRecipient recipient, string subject, string body, string contentType) { - Recipient = recipient ?? throw new ArgumentNullException("recipient"); + Recipient = recipient ?? throw new ArgumentNullException(nameof(recipient)); Subject = subject; - Body = body ?? throw new ArgumentNullException("body"); + Body = body ?? throw new ArgumentNullException(nameof(body)); ContentType = contentType; } @@ -89,7 +89,7 @@ namespace ASC.Notify.Messages public void AddArgument(params ITagValue[] tagValues) { - if (tagValues == null) throw new ArgumentNullException("tagValues"); + if (tagValues == null) throw new ArgumentNullException(nameof(tagValues)); Array.ForEach(tagValues, tagValue => { diff --git a/common/ASC.Core.Common/Notify/Model/ISubscriptionProvider.cs b/common/ASC.Core.Common/Notify/Model/ISubscriptionProvider.cs index cbd06ee77d..23eebf1016 100644 --- a/common/ASC.Core.Common/Notify/Model/ISubscriptionProvider.cs +++ b/common/ASC.Core.Common/Notify/Model/ISubscriptionProvider.cs @@ -69,7 +69,7 @@ namespace ASC.Notify.Model if (subscriptionRecord != null) { var properties = subscriptionRecord.GetType().GetProperties(); - if (properties.Any()) + if (properties.Length > 0) { var property = properties.Single(p => p.Name == "Subscribed"); if (property != null) diff --git a/common/ASC.Core.Common/Notify/Model/NotifyAction.cs b/common/ASC.Core.Common/Notify/Model/NotifyAction.cs index e2900b2758..b2236e84ad 100644 --- a/common/ASC.Core.Common/Notify/Model/NotifyAction.cs +++ b/common/ASC.Core.Common/Notify/Model/NotifyAction.cs @@ -43,7 +43,7 @@ namespace ASC.Notify.Model public NotifyAction(string id, string name) { - ID = id ?? throw new ArgumentNullException("id"); + ID = id ?? throw new ArgumentNullException(nameof(id)); Name = name; } @@ -69,7 +69,7 @@ namespace ASC.Notify.Model public override string ToString() { - return string.Format("action: {0}", ID); + return $"action: {ID}"; } } } \ No newline at end of file diff --git a/common/ASC.Core.Common/Notify/Model/NotifyClientImpl.cs b/common/ASC.Core.Common/Notify/Model/NotifyClientImpl.cs index 25492b9377..34de37863a 100644 --- a/common/ASC.Core.Common/Notify/Model/NotifyClientImpl.cs +++ b/common/ASC.Core.Common/Notify/Model/NotifyClientImpl.cs @@ -43,9 +43,9 @@ namespace ASC.Notify.Model public NotifyClientImpl(Context context, INotifySource notifySource, IServiceScope serviceScope) { - this.notifySource = notifySource ?? throw new ArgumentNullException("notifySource"); + this.notifySource = notifySource ?? throw new ArgumentNullException(nameof(notifySource)); ServiceScope = serviceScope; - ctx = context ?? throw new ArgumentNullException("context"); + ctx = context ?? throw new ArgumentNullException(nameof(context)); } public void SendNoticeToAsync(INotifyAction action, IRecipient[] recipients, string[] senderNames, params ITagValue[] args) @@ -108,7 +108,7 @@ namespace ASC.Notify.Model public void SendNoticeToAsync(INotifyAction action, string objectID, IRecipient[] recipients, string[] senderNames, bool checkSubsciption, params ITagValue[] args) { - if (recipients == null) throw new ArgumentNullException("recipients"); + if (recipients == null) throw new ArgumentNullException(nameof(recipients)); BeginSingleRecipientEvent("__syspreventduplicateinterceptor"); @@ -127,8 +127,8 @@ namespace ASC.Notify.Model private NotifyRequest CreateRequest(INotifyAction action, string objectID, IRecipient recipient, ITagValue[] args, string[] senders, bool checkSubsciption) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); var request = new NotifyRequest(notifySource, action, objectID, recipient) { diff --git a/common/ASC.Core.Common/Notify/NotifySource.cs b/common/ASC.Core.Common/Notify/NotifySource.cs index 4a15992042..6148488446 100644 --- a/common/ASC.Core.Common/Notify/NotifySource.cs +++ b/common/ASC.Core.Common/Notify/NotifySource.cs @@ -67,9 +67,9 @@ namespace ASC.Core.Notify private UserManager UserManager { get; } private SubscriptionManager SubscriptionManager { get; } - public NotifySource(string id, UserManager userManager, IRecipientProvider recipientsProvider, SubscriptionManager subscriptionManager) + protected NotifySource(string id, UserManager userManager, IRecipientProvider recipientsProvider, SubscriptionManager subscriptionManager) { - if (string.IsNullOrEmpty(id)) throw new ArgumentNullException("id"); + if (string.IsNullOrEmpty(id)) throw new ArgumentNullException(nameof(id)); ID = id; UserManager = userManager; @@ -77,7 +77,7 @@ namespace ASC.Core.Notify SubscriptionManager = subscriptionManager; } - public NotifySource(Guid id, UserManager userManager, IRecipientProvider recipientsProvider, SubscriptionManager subscriptionManager) + protected NotifySource(Guid id, UserManager userManager, IRecipientProvider recipientsProvider, SubscriptionManager subscriptionManager) : this(id.ToString(), userManager, recipientsProvider, subscriptionManager) { } @@ -132,12 +132,12 @@ namespace ASC.Core.Notify { var subscriptionProvider = new DirectSubscriptionProvider(ID, SubscriptionManager, RecipientsProvider); return new TopSubscriptionProvider(RecipientsProvider, subscriptionProvider, WorkContext.DefaultClientSenders) ?? - throw new NotifyException(string.Format("Provider {0} not instanced.", "ISubscriprionProvider")); + throw new NotifyException("Provider ISubscriprionProvider not instanced."); } protected virtual IRecipientProvider CreateRecipientsProvider() { - return new RecipientProviderImpl(UserManager) ?? throw new NotifyException(string.Format("Provider {0} not instanced.", "IRecipientsProvider")); + return new RecipientProviderImpl(UserManager) ?? throw new NotifyException("Provider IRecipientsProvider not instanced."); } } } \ No newline at end of file diff --git a/common/ASC.Core.Common/Notify/Patterns/NVelocityPatternFormatter.cs b/common/ASC.Core.Common/Notify/Patterns/NVelocityPatternFormatter.cs index 49f726766c..1224a50232 100644 --- a/common/ASC.Core.Common/Notify/Patterns/NVelocityPatternFormatter.cs +++ b/common/ASC.Core.Common/Notify/Patterns/NVelocityPatternFormatter.cs @@ -71,7 +71,7 @@ namespace ASC.Notify.Patterns base.AfterFormat(message); } - private static void EventCartridgeReferenceInsertion(object sender, ReferenceInsertionEventArgs e) + private void EventCartridgeReferenceInsertion(object sender, ReferenceInsertionEventArgs e) { if (!(e.OriginalValue is string originalString)) return; var lines = originalString.Split(new[] { '\n', '\r' }, StringSplitOptions.RemoveEmptyEntries); @@ -79,9 +79,9 @@ namespace ASC.Notify.Patterns e.NewValue = string.Empty; for (var i = 0; i < lines.Length - 1; i++) { - e.NewValue += string.Format("{0}{1}{2}\n", NoStylePreffix, lines[i], NoStyleSuffix); + e.NewValue += $"{NoStylePreffix}{lines[i]}{NoStyleSuffix}\n"; } - e.NewValue += string.Format("{0}{1}{2}", NoStylePreffix, lines[^1], NoStyleSuffix); + e.NewValue += $"{NoStylePreffix}{lines[^1]}{NoStyleSuffix}"; } } } \ No newline at end of file diff --git a/common/ASC.Core.Common/Notify/Patterns/Pattern.cs b/common/ASC.Core.Common/Notify/Patterns/Pattern.cs index 3c2605273c..01398d5e44 100644 --- a/common/ASC.Core.Common/Notify/Patterns/Pattern.cs +++ b/common/ASC.Core.Common/Notify/Patterns/Pattern.cs @@ -52,8 +52,8 @@ namespace ASC.Notify.Patterns { if (string.IsNullOrEmpty(id)) throw new ArgumentException("id"); ID = id; - Subject = subject ?? throw new ArgumentNullException("subject"); - Body = body ?? throw new ArgumentNullException("body"); + Subject = subject ?? throw new ArgumentNullException(nameof(subject)); + Body = body ?? throw new ArgumentNullException(nameof(body)); ContentType = string.IsNullOrEmpty(contentType) ? HTMLContentType : contentType; } diff --git a/common/ASC.Core.Common/Notify/Patterns/PatternFormatter.cs b/common/ASC.Core.Common/Notify/Patterns/PatternFormatter.cs index 7722248520..d9959ba492 100644 --- a/common/ASC.Core.Common/Notify/Patterns/PatternFormatter.cs +++ b/common/ASC.Core.Common/Notify/Patterns/PatternFormatter.cs @@ -45,16 +45,16 @@ namespace ASC.Notify.Patterns } - public PatternFormatter() + protected PatternFormatter() { } - public PatternFormatter(string tagSearchRegExp) + protected PatternFormatter(string tagSearchRegExp) : this(tagSearchRegExp, false) { } - internal PatternFormatter(string tagSearchRegExp, bool formatMessage) + protected PatternFormatter(string tagSearchRegExp, bool formatMessage) { if (string.IsNullOrEmpty(tagSearchRegExp)) throw new ArgumentException("tagSearchRegExp"); @@ -65,7 +65,7 @@ namespace ASC.Notify.Patterns public string[] GetTags(IPattern pattern) { - if (pattern == null) throw new ArgumentNullException("pattern"); + if (pattern == null) throw new ArgumentNullException(nameof(pattern)); var findedTags = new List(SearchTags(pattern.Body)); Array.ForEach(SearchTags(pattern.Subject), tag => { if (!findedTags.Contains(tag)) findedTags.Add(tag); }); @@ -74,9 +74,9 @@ namespace ASC.Notify.Patterns public void FormatMessage(INoticeMessage message, ITagValue[] tagsValues) { - if (message == null) throw new ArgumentNullException("message"); + if (message == null) throw new ArgumentNullException(nameof(message)); if (message.Pattern == null) throw new ArgumentException("message"); - if (tagsValues == null) throw new ArgumentNullException("tagsValues"); + if (tagsValues == null) throw new ArgumentNullException(nameof(tagsValues)); BeforeFormat(message, tagsValues); @@ -98,7 +98,7 @@ namespace ASC.Notify.Patterns protected virtual string[] SearchTags(string text) { - if (string.IsNullOrEmpty(text) || string.IsNullOrEmpty(tagSearchPattern)) return new string[0]; + if (string.IsNullOrEmpty(text) || string.IsNullOrEmpty(tagSearchPattern)) return Array.Empty(); var maches = RegEx.Matches(text); var findedTags = new List(maches.Count); diff --git a/common/ASC.Core.Common/Notify/Patterns/TagValue.cs b/common/ASC.Core.Common/Notify/Patterns/TagValue.cs index 77ec54dee7..b1575905a1 100644 --- a/common/ASC.Core.Common/Notify/Patterns/TagValue.cs +++ b/common/ASC.Core.Common/Notify/Patterns/TagValue.cs @@ -46,7 +46,7 @@ namespace ASC.Notify.Patterns public TagValue(string tag, object value) { - if (string.IsNullOrEmpty(tag)) throw new ArgumentNullException("tag"); + if (string.IsNullOrEmpty(tag)) throw new ArgumentNullException(nameof(tag)); Tag = tag; Value = value; diff --git a/common/ASC.Core.Common/Notify/Patterns/XmlPatternProvider2.cs b/common/ASC.Core.Common/Notify/Patterns/XmlPatternProvider2.cs index 5ab25c5837..d15a021e9f 100644 --- a/common/ASC.Core.Common/Notify/Patterns/XmlPatternProvider2.cs +++ b/common/ASC.Core.Common/Notify/Patterns/XmlPatternProvider2.cs @@ -155,13 +155,13 @@ namespace ASC.Notify.Patterns resourceManagerType.GetProperty(ToUpper(array[0]), BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Static); if (property == null) { - throw new NotifyException(string.Format("Resource {0} not found in resourceManager {1}", array[0], array[1])); + throw new NotifyException($"Resource {array[0]} not found in resourceManager {array[1]}"); } return property.GetValue(resourceManagerType, null) as string; static string ToUpper(string name) { - return name.Substring(0, 1).ToUpper() + name.Substring(1); + return name[0].ToString().ToUpper() + name.Substring(1); } } } diff --git a/common/ASC.Core.Common/Notify/RecipientProviderImpl.cs b/common/ASC.Core.Common/Notify/RecipientProviderImpl.cs index 4d2f6d4bf6..cc76fa8520 100644 --- a/common/ASC.Core.Common/Notify/RecipientProviderImpl.cs +++ b/common/ASC.Core.Common/Notify/RecipientProviderImpl.cs @@ -38,7 +38,7 @@ namespace ASC.Core.Notify private UserManager UserManager { get; } public RecipientProviderImpl(UserManager userManager) => - (UserManager) = (userManager); + UserManager = userManager; public virtual IRecipient GetRecipient(string id) { if (TryParseGuid(id, out var recID)) @@ -54,11 +54,10 @@ namespace ASC.Core.Notify public virtual IRecipient[] GetGroupEntries(IRecipientsGroup group) { - if (group == null) throw new ArgumentNullException("group"); + if (group == null) throw new ArgumentNullException(nameof(group)); var result = new List(); - var groupID = Guid.Empty; - if (TryParseGuid(group.ID, out groupID)) + if (TryParseGuid(group.ID, out var groupID)) { var coreGroup = UserManager.GetGroupInfo(groupID); if (coreGroup.ID != Constants.LostGroupInfo.ID) @@ -72,7 +71,7 @@ namespace ASC.Core.Notify public virtual IRecipientsGroup[] GetGroups(IRecipient recipient) { - if (recipient == null) throw new ArgumentNullException("recipient"); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); var result = new List(); if (TryParseGuid(recipient.ID, out var recID)) @@ -99,7 +98,7 @@ namespace ASC.Core.Notify public virtual string[] GetRecipientAddresses(IDirectRecipient recipient, string senderName) { - if (recipient == null) throw new ArgumentNullException("recipient"); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); if (TryParseGuid(recipient.ID, out var userID)) { @@ -112,7 +111,7 @@ namespace ASC.Core.Notify if (senderName == ASC.Core.Configuration.Constants.NotifyTelegramSenderSysName) return new[] { user.ID.ToString() }; } } - return new string[0]; + return Array.Empty(); } /// @@ -126,7 +125,7 @@ namespace ASC.Core.Notify if (recipient.CheckActivation) { //It's direct email - if (recipient.Addresses != null && recipient.Addresses.Any()) + if (recipient.Addresses != null && recipient.Addresses.Length > 0) { //Filtering only missing users and users who activated already var filteredAddresses = from address in recipient.Addresses diff --git a/common/ASC.Core.Common/Notify/Recipients/DirectRecipient.cs b/common/ASC.Core.Common/Notify/Recipients/DirectRecipient.cs index 17c8447f0e..39020b3bc7 100644 --- a/common/ASC.Core.Common/Notify/Recipients/DirectRecipient.cs +++ b/common/ASC.Core.Common/Notify/Recipients/DirectRecipient.cs @@ -88,7 +88,7 @@ namespace ASC.Notify.Recipients public override string ToString() { - return string.Format("{0}({1})", Name, string.Join(";", _Addresses.ToArray())); + return $"{Name}({string.Join(";", _Addresses.ToArray())})"; } } } \ No newline at end of file diff --git a/common/ASC.Core.Common/Notify/Recipients/RecipientsGroup.cs b/common/ASC.Core.Common/Notify/Recipients/RecipientsGroup.cs index bef149944a..5baddc025e 100644 --- a/common/ASC.Core.Common/Notify/Recipients/RecipientsGroup.cs +++ b/common/ASC.Core.Common/Notify/Recipients/RecipientsGroup.cs @@ -59,7 +59,7 @@ namespace ASC.Notify.Recipients public override string ToString() { - return string.Format("{0}", Name); + return Name; } } } \ No newline at end of file diff --git a/common/ASC.Core.Common/Notify/ReplyToTagProvider.cs b/common/ASC.Core.Common/Notify/ReplyToTagProvider.cs index 8a2f746cc1..f213453691 100644 --- a/common/ASC.Core.Common/Notify/ReplyToTagProvider.cs +++ b/common/ASC.Core.Common/Notify/ReplyToTagProvider.cs @@ -71,7 +71,7 @@ namespace ASC.Core.Common.Notify if (string.IsNullOrEmpty(entityId)) throw new ArgumentException(@"Entity Id is null or empty", entityId); var pId = parentId != Guid.Empty.ToString() && parentId != null ? parentId : string.Empty; - return new TagValue(TagName, string.Format("reply_{0}_{1}_{2}@{3}", entity, entityId, pId, AutoreplyDomain)); + return new TagValue(TagName, $"reply_{entity}_{entityId}_{pId}@{AutoreplyDomain}"); } /// diff --git a/common/ASC.Core.Common/Notify/Senders/AWSSender.cs b/common/ASC.Core.Common/Notify/Senders/AWSSender.cs index 2ba94163cd..bf756542cb 100644 --- a/common/ASC.Core.Common/Notify/Senders/AWSSender.cs +++ b/common/ASC.Core.Common/Notify/Senders/AWSSender.cs @@ -249,7 +249,7 @@ namespace ASC.Core.Notify.Senders } } - public class AWSSenderExtension + public static class AWSSenderExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.Core.Common/Notify/Senders/JabberSender.cs b/common/ASC.Core.Common/Notify/Senders/JabberSender.cs index 1adf0f70af..6cc3a236c0 100644 --- a/common/ASC.Core.Common/Notify/Senders/JabberSender.cs +++ b/common/ASC.Core.Common/Notify/Senders/JabberSender.cs @@ -78,7 +78,7 @@ namespace ASC.Core.Notify.Senders } } - public class JabberSenderExtension + public static class JabberSenderExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.Core.Common/Notify/Senders/SmtpSender.cs b/common/ASC.Core.Common/Notify/Senders/SmtpSender.cs index 5fd7cc11d7..3d9cfa5504 100644 --- a/common/ASC.Core.Common/Notify/Senders/SmtpSender.cs +++ b/common/ASC.Core.Common/Notify/Senders/SmtpSender.cs @@ -48,14 +48,6 @@ namespace ASC.Core.Notify.Senders [Singletone(Additional = typeof(SmtpSenderExtension))] public class SmtpSender : INotifySender { - private const string HTML_FORMAT = - @" - - - - -{0} -"; protected ILog Log { get; set; } protected IConfiguration Configuration { get; } @@ -88,11 +80,9 @@ namespace ASC.Core.Notify.Senders Host = properties["host"]; Port = properties.ContainsKey("port") ? int.Parse(properties["port"]) : 25; Ssl = properties.ContainsKey("enableSsl") && bool.Parse(properties["enableSsl"]); - if (properties.ContainsKey("userName")) + if (properties.TryGetValue("userName", out var property)) { - Credentials = new NetworkCredential( - properties["userName"], - properties["password"]); + Credentials = new NetworkCredential(property, properties["password"]); } } } @@ -276,21 +266,21 @@ namespace ASC.Core.Notify.Senders protected string GetHtmlView(string body) { - return string.Format(HTML_FORMAT, body); + return $@" + + + + +{body} +"; } private MailKit.Net.Smtp.SmtpClient GetSmtpClient() { - var sslCertificatePermit = Configuration["mail:certificate-permit"] != null && - Convert.ToBoolean(Configuration["mail:certificate-permit"]); - var smtpClient = new MailKit.Net.Smtp.SmtpClient { Timeout = NETWORK_TIMEOUT }; - - if (sslCertificatePermit) - smtpClient.ServerCertificateValidationCallback = (sender, certificate, chain, errors) => true; return smtpClient; } @@ -341,7 +331,7 @@ namespace ASC.Core.Notify.Senders } } - public class SmtpSenderExtension + public static class SmtpSenderExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.Core.Common/Notify/Signalr/SignalrServiceClient.cs b/common/ASC.Core.Common/Notify/Signalr/SignalrServiceClient.cs index b7000b5c1a..433a28cbe4 100644 --- a/common/ASC.Core.Common/Notify/Signalr/SignalrServiceClient.cs +++ b/common/ASC.Core.Common/Notify/Signalr/SignalrServiceClient.cs @@ -52,20 +52,23 @@ namespace ASC.Core.Notify.Signalr internal CoreSettings CoreSettings { get; } internal MachinePseudoKeys MachinePseudoKeys { get; } internal IConfiguration Configuration { get; } - internal IOptionsMonitor Options { get; } + internal IOptionsMonitor Options { get; } + internal IHttpClientFactory ClientFactory { get; } public ConfigureSignalrServiceClient( TenantManager tenantManager, CoreSettings coreSettings, MachinePseudoKeys machinePseudoKeys, IConfiguration configuration, - IOptionsMonitor options) + IOptionsMonitor options, + IHttpClientFactory clientFactory) { TenantManager = tenantManager; CoreSettings = coreSettings; MachinePseudoKeys = machinePseudoKeys; Configuration = configuration; - Options = options; + Options = options; + ClientFactory = clientFactory; } public void Configure(string name, SignalrServiceClient options) @@ -73,7 +76,8 @@ namespace ASC.Core.Notify.Signalr options.Log = Options.CurrentValue; options.hub = name.Trim('/'); options.TenantManager = TenantManager; - options.CoreSettings = CoreSettings; + options.CoreSettings = CoreSettings; + options.ClientFactory = ClientFactory; options.SKey = MachinePseudoKeys.GetMachineConstant(); options.Url = Configuration["web:hub:internal"]; options.EnableSignalr = !string.IsNullOrEmpty(options.Url); @@ -106,10 +110,10 @@ namespace ASC.Core.Notify.Signalr [Scope(typeof(ConfigureSignalrServiceClient))] public class SignalrServiceClient { - private static readonly TimeSpan Timeout; + private static readonly TimeSpan Timeout = TimeSpan.FromSeconds(1); internal ILog Log; private static DateTime lastErrorTime; - public bool EnableSignalr; + public bool EnableSignalr { get; set; } internal byte[] SKey; internal string Url; internal bool JabberReplaceDomain; @@ -119,12 +123,8 @@ namespace ASC.Core.Notify.Signalr internal string hub; internal TenantManager TenantManager { get; set; } - internal CoreSettings CoreSettings { get; set; } - - static SignalrServiceClient() - { - Timeout = TimeSpan.FromSeconds(1); - } + internal CoreSettings CoreSettings { get; set; } + internal IHttpClientFactory ClientFactory { get; set; } public SignalrServiceClient() { @@ -141,7 +141,7 @@ namespace ASC.Core.Notify.Signalr var tenant = tenantId == -1 ? TenantManager.GetTenant(domain) : TenantManager.GetTenant(tenantId); - var isTenantUser = callerUserName == string.Empty; + var isTenantUser = callerUserName.Length == 0; var message = new MessageClass { UserName = isTenantUser ? tenant.GetTenantDomain(CoreSettings) : callerUserName, @@ -374,7 +374,8 @@ namespace ASC.Core.Notify.Signalr request.Content = new StringContent(jsonData, Encoding.UTF8, "application/json"); - using (var httpClient = new HttpClient()) + var httpClient = ClientFactory.CreateClient(); + using (var response = httpClient.Send(request)) using (var stream = response.Content.ReadAsStream()) using (var streamReader = new StreamReader(stream)) @@ -396,7 +397,7 @@ namespace ASC.Core.Notify.Signalr private string GetMethod(string method) { - return string.Format("{0}/controller/{1}/{2}", Url.TrimEnd('/'), hub, method); + return $"{Url.TrimEnd('/')}/controller/{hub}/{method}"; } public string CreateAuthToken(string pkey = "socketio") @@ -404,7 +405,7 @@ namespace ASC.Core.Notify.Signalr using var hasher = new HMACSHA1(SKey); var now = DateTime.UtcNow.ToString("yyyyMMddHHmmss"); var hash = Convert.ToBase64String(hasher.ComputeHash(Encoding.UTF8.GetBytes(string.Join("\n", now, pkey)))); - return string.Format("ASC {0}:{1}:{2}", pkey, now, hash); + return $"ASC {pkey}:{now}:{hash}"; } } } \ No newline at end of file diff --git a/common/ASC.Core.Common/Notify/Sinks/DispatchSink.cs b/common/ASC.Core.Common/Notify/Sinks/DispatchSink.cs index 922fe8a09e..bd1fe25939 100644 --- a/common/ASC.Core.Common/Notify/Sinks/DispatchSink.cs +++ b/common/ASC.Core.Common/Notify/Sinks/DispatchSink.cs @@ -38,7 +38,7 @@ namespace ASC.Notify.Sinks public DispatchSink(string senderName, DispatchEngine dispatcher) { - this.dispatcher = dispatcher ?? throw new ArgumentNullException("dispatcher"); + this.dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); this.senderName = senderName; } diff --git a/common/ASC.Core.Common/Notify/Telegram/Dao/CachedTelegramDao.cs b/common/ASC.Core.Common/Notify/Telegram/Dao/CachedTelegramDao.cs index aba43cb9b2..d9315cac80 100644 --- a/common/ASC.Core.Common/Notify/Telegram/Dao/CachedTelegramDao.cs +++ b/common/ASC.Core.Common/Notify/Telegram/Dao/CachedTelegramDao.cs @@ -26,7 +26,6 @@ using System; using System.Collections.Generic; -using System.Linq; using ASC.Common; using ASC.Common.Caching; @@ -107,7 +106,7 @@ namespace ASC.Core.Common.Notify.Telegram if (users != null) return users; users = TgDao.GetUser(telegramId); - if (users.Any()) Cache.Insert(key, users, Expiration); + if (users.Count > 0) Cache.Insert(key, users, Expiration); return users; } diff --git a/common/ASC.Core.Common/Notify/Telegram/TelegramHelper.cs b/common/ASC.Core.Common/Notify/Telegram/TelegramHelper.cs index 4b184ebe98..295aa0f391 100644 --- a/common/ASC.Core.Common/Notify/Telegram/TelegramHelper.cs +++ b/common/ASC.Core.Common/Notify/Telegram/TelegramHelper.cs @@ -106,7 +106,7 @@ namespace ASC.Core.Common.Notify public string CurrentRegistrationLink(Guid userId, int tenantId) { var token = GetCurrentToken(userId, tenantId); - if (token == null || token == "") return ""; + if (token == null || token.Length == 0) return ""; return GetLink(token); } @@ -149,7 +149,7 @@ namespace ASC.Core.Common.Notify var botname = tgProvider == null ? default : tgProvider.TelegramBotName; if (string.IsNullOrEmpty(botname)) return null; - return string.Format("t.me/{0}?start={1}", botname, token); + return $"t.me/{botname}?start={token}"; } public bool TestingClient(TelegramBotClient telegramBotClient) diff --git a/common/ASC.Core.Common/Notify/Telegram/TelegramSenderSink.cs b/common/ASC.Core.Common/Notify/Telegram/TelegramSenderSink.cs index ffb0f0aa40..1f8aa3b886 100644 --- a/common/ASC.Core.Common/Notify/Telegram/TelegramSenderSink.cs +++ b/common/ASC.Core.Common/Notify/Telegram/TelegramSenderSink.cs @@ -43,7 +43,7 @@ namespace ASC.Core.Notify public TelegramSenderSink(INotifySender sender, IServiceProvider serviceProvider) { - this.sender = sender ?? throw new ArgumentNullException("sender"); + this.sender = sender ?? throw new ArgumentNullException(nameof(sender)); this.serviceProvider = serviceProvider; } @@ -52,7 +52,7 @@ namespace ASC.Core.Notify { try { - var result = SendResult.OK; + const SendResult result = SendResult.OK; var m = new NotifyMessage { To = message.Recipient.ID, diff --git a/common/ASC.Core.Common/Notify/TopSubscriptionProvider.cs b/common/ASC.Core.Common/Notify/TopSubscriptionProvider.cs index 1d8c92f0cb..779aacfb72 100644 --- a/common/ASC.Core.Common/Notify/TopSubscriptionProvider.cs +++ b/common/ASC.Core.Common/Notify/TopSubscriptionProvider.cs @@ -34,15 +34,15 @@ namespace ASC.Notify.Model { public class TopSubscriptionProvider : ISubscriptionProvider { - private readonly string[] defaultSenderMethods = new string[0]; + private readonly string[] defaultSenderMethods = Array.Empty(); private readonly ISubscriptionProvider subscriptionProvider; private readonly IRecipientProvider recipientProvider; public TopSubscriptionProvider(IRecipientProvider recipientProvider, ISubscriptionProvider directSubscriptionProvider) { - this.recipientProvider = recipientProvider ?? throw new ArgumentNullException("recipientProvider"); - subscriptionProvider = directSubscriptionProvider ?? throw new ArgumentNullException("directSubscriptionProvider"); + this.recipientProvider = recipientProvider ?? throw new ArgumentNullException(nameof(recipientProvider)); + subscriptionProvider = directSubscriptionProvider ?? throw new ArgumentNullException(nameof(directSubscriptionProvider)); } public TopSubscriptionProvider(IRecipientProvider recipientProvider, ISubscriptionProvider directSubscriptionProvider, string[] defaultSenderMethods) @@ -54,8 +54,8 @@ namespace ASC.Notify.Model public virtual string[] GetSubscriptionMethod(INotifyAction action, IRecipient recipient) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); var senders = subscriptionProvider.GetSubscriptionMethod(action, recipient); if (senders == null || senders.Length == 0) @@ -73,7 +73,7 @@ namespace ASC.Notify.Model public virtual IRecipient[] GetRecipients(INotifyAction action, string objectID) { - if (action == null) throw new ArgumentNullException("action"); + if (action == null) throw new ArgumentNullException(nameof(action)); var recipents = new List(5); var directRecipients = subscriptionProvider.GetRecipients(action, objectID) ?? new IRecipient[0]; @@ -83,8 +83,8 @@ namespace ASC.Notify.Model public virtual bool IsUnsubscribe(IDirectRecipient recipient, INotifyAction action, string objectID) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); return subscriptionProvider.IsUnsubscribe(recipient, action, objectID); } @@ -92,30 +92,30 @@ namespace ASC.Notify.Model public virtual void Subscribe(INotifyAction action, string objectID, IRecipient recipient) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); subscriptionProvider.Subscribe(action, objectID, recipient); } public virtual void UnSubscribe(INotifyAction action, string objectID, IRecipient recipient) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); subscriptionProvider.UnSubscribe(action, objectID, recipient); } public void UnSubscribe(INotifyAction action, string objectID) { - if (action == null) throw new ArgumentNullException("action"); + if (action == null) throw new ArgumentNullException(nameof(action)); subscriptionProvider.UnSubscribe(action, objectID); } public void UnSubscribe(INotifyAction action) { - if (action == null) throw new ArgumentNullException("action"); + if (action == null) throw new ArgumentNullException(nameof(action)); subscriptionProvider.UnSubscribe(action); } @@ -131,17 +131,17 @@ namespace ASC.Notify.Model public virtual void UpdateSubscriptionMethod(INotifyAction action, IRecipient recipient, params string[] senderNames) { - if (action == null) throw new ArgumentNullException("action"); - if (recipient == null) throw new ArgumentNullException("recipient"); - if (senderNames == null) throw new ArgumentNullException("senderNames"); + if (action == null) throw new ArgumentNullException(nameof(action)); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); + if (senderNames == null) throw new ArgumentNullException(nameof(senderNames)); subscriptionProvider.UpdateSubscriptionMethod(action, recipient, senderNames); } public virtual object GetSubscriptionRecord(INotifyAction action, IRecipient recipient, string objectID) { - if (recipient == null) throw new ArgumentNullException("recipient"); - if (action == null) throw new ArgumentNullException("action"); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); + if (action == null) throw new ArgumentNullException(nameof(action)); var subscriptionRecord = subscriptionProvider.GetSubscriptionRecord(action, recipient, objectID); @@ -161,16 +161,16 @@ namespace ASC.Notify.Model public virtual string[] GetSubscriptions(INotifyAction action, IRecipient recipient, bool checkSubscription = true) { - if (recipient == null) throw new ArgumentNullException("recipient"); - if (action == null) throw new ArgumentNullException("action"); + if (recipient == null) throw new ArgumentNullException(nameof(recipient)); + if (action == null) throw new ArgumentNullException(nameof(action)); var objects = new List(); - var direct = subscriptionProvider.GetSubscriptions(action, recipient, checkSubscription) ?? new string[0]; + var direct = subscriptionProvider.GetSubscriptions(action, recipient, checkSubscription) ?? Array.Empty(); MergeObjects(objects, direct); var parents = WalkUp(recipient); foreach (var parent in parents) { - direct = subscriptionProvider.GetSubscriptions(action, parent, checkSubscription) ?? new string[0]; + direct = subscriptionProvider.GetSubscriptions(action, parent, checkSubscription) ?? Array.Empty(); if (recipient is IDirectRecipient) { foreach (var groupsubscr in direct) diff --git a/common/ASC.Core.Common/Security/Authorizing/AzManager.cs b/common/ASC.Core.Common/Security/Authorizing/AzManager.cs index 61283bf637..4036462b18 100644 --- a/common/ASC.Core.Common/Security/Authorizing/AzManager.cs +++ b/common/ASC.Core.Common/Security/Authorizing/AzManager.cs @@ -43,8 +43,8 @@ namespace ASC.Common.Security.Authorizing public AzManager(IRoleProvider roleProvider, IPermissionProvider permissionProvider) : this() { - this.roleProvider = roleProvider ?? throw new ArgumentNullException("roleProvider"); - this.permissionProvider = permissionProvider ?? throw new ArgumentNullException("permissionProvider"); + this.roleProvider = roleProvider ?? throw new ArgumentNullException(nameof(roleProvider)); + this.permissionProvider = permissionProvider ?? throw new ArgumentNullException(nameof(permissionProvider)); } @@ -52,8 +52,8 @@ namespace ASC.Common.Security.Authorizing ISecurityObjectProvider securityObjProvider, out ISubject denySubject, out IAction denyAction) { - if (subject == null) throw new ArgumentNullException("subject"); - if (action == null) throw new ArgumentNullException("action"); + if (subject == null) throw new ArgumentNullException(nameof(subject)); + if (action == null) throw new ArgumentNullException(nameof(action)); var acl = GetAzManagerAcl(subject, action, objectId, securityObjProvider); denySubject = acl.DenySubject; @@ -76,7 +76,7 @@ namespace ASC.Common.Security.Authorizing var aceList = permissionProvider.GetAcl(s, action, objectId, securityObjProvider); foreach (var ace in aceList) { - if (ace.Reaction == AceType.Deny && !exit) + if (ace.Reaction == AceType.Deny) { acl.IsAllow = false; acl.DenySubject = s; diff --git a/common/ASC.Core.Common/Security/Authorizing/PermissionProvider.cs b/common/ASC.Core.Common/Security/Authorizing/PermissionProvider.cs index 878e65d4b8..7ffc4a8410 100644 --- a/common/ASC.Core.Common/Security/Authorizing/PermissionProvider.cs +++ b/common/ASC.Core.Common/Security/Authorizing/PermissionProvider.cs @@ -44,8 +44,8 @@ namespace ASC.Core.Security.Authorizing public IEnumerable GetAcl(ISubject subject, IAction action, ISecurityObjectId objectId, ISecurityObjectProvider secObjProvider) { - if (subject == null) throw new ArgumentNullException("subject"); - if (action == null) throw new ArgumentNullException("action"); + if (subject == null) throw new ArgumentNullException(nameof(subject)); + if (action == null) throw new ArgumentNullException(nameof(action)); return AuthorizationManager .GetAcesWithInherits(subject.ID, action.ID, objectId, secObjProvider) diff --git a/common/ASC.Core.Common/Security/Authorizing/PermissionResolver.cs b/common/ASC.Core.Common/Security/Authorizing/PermissionResolver.cs index 4d7cc57b1f..6fe753fc00 100644 --- a/common/ASC.Core.Common/Security/Authorizing/PermissionResolver.cs +++ b/common/ASC.Core.Common/Security/Authorizing/PermissionResolver.cs @@ -45,7 +45,7 @@ namespace ASC.Core.Security.Authorizing public PermissionResolver(AzManager azManager) { - this.azManager = azManager ?? throw new ArgumentNullException("azManager"); + this.azManager = azManager ?? throw new ArgumentNullException(nameof(azManager)); } diff --git a/common/ASC.Core.Common/Security/Authorizing/RoleProvider.cs b/common/ASC.Core.Common/Security/Authorizing/RoleProvider.cs index b89b13757f..72d094e6f9 100644 --- a/common/ASC.Core.Common/Security/Authorizing/RoleProvider.cs +++ b/common/ASC.Core.Common/Security/Authorizing/RoleProvider.cs @@ -43,7 +43,7 @@ namespace ASC.Core.Security.Authorizing { //circ dep private IServiceProvider ServiceProvider { get; } - public RoleProvider(IServiceProvider serviceProvider) => (ServiceProvider) = (serviceProvider); + public RoleProvider(IServiceProvider serviceProvider) => ServiceProvider = serviceProvider; public List GetRoles(ISubject account) { diff --git a/common/ASC.Core.Common/Security/Crypto.cs b/common/ASC.Core.Common/Security/Crypto.cs index 2f71b74967..8cd772396b 100644 --- a/common/ASC.Core.Common/Security/Crypto.cs +++ b/common/ASC.Core.Common/Security/Crypto.cs @@ -33,7 +33,7 @@ using ASC.Common.Security; namespace ASC.Core { - public class Crypto + public static class Crypto { private static byte[] GetSK1(bool rewrite) { diff --git a/common/ASC.Core.Common/Security/EmailValidationKeyProvider.cs b/common/ASC.Core.Common/Security/EmailValidationKeyProvider.cs index 3d62360876..820fbe17e5 100644 --- a/common/ASC.Core.Common/Security/EmailValidationKeyProvider.cs +++ b/common/ASC.Core.Common/Security/EmailValidationKeyProvider.cs @@ -85,7 +85,7 @@ namespace ASC.Security.Cryptography public string GetEmailKey(int tenantId, string email) { - if (string.IsNullOrEmpty(email)) throw new ArgumentNullException("email"); + if (string.IsNullOrEmpty(email)) throw new ArgumentNullException(nameof(email)); email = FormatEmail(tenantId, email); @@ -96,7 +96,7 @@ namespace ASC.Security.Cryptography private string FormatEmail(int tenantId, string email) { - if (email == null) throw new ArgumentNullException("email"); + if (email == null) throw new ArgumentNullException(nameof(email)); try { return string.Format("{0}|{1}|{2}", email.ToLowerInvariant(), tenantId, Encoding.UTF8.GetString(MachinePseudoKeys.GetMachineConstant())); @@ -123,8 +123,8 @@ namespace ASC.Security.Cryptography private ValidationResult ValidateEmailKeyInternal(string email, string key, TimeSpan validInterval) { - if (string.IsNullOrEmpty(email)) throw new ArgumentNullException("email"); - if (key == null) throw new ArgumentNullException("key"); + if (string.IsNullOrEmpty(email)) throw new ArgumentNullException(nameof(email)); + if (key == null) throw new ArgumentNullException(nameof(key)); email = FormatEmail(TenantManager.GetCurrentTenant().TenantId, email); var parts = key.Split(new[] { '.' }, StringSplitOptions.RemoveEmptyEntries); @@ -134,7 +134,7 @@ namespace ASC.Security.Cryptography var hash = GetMashineHashedData(BitConverter.GetBytes(ms), Encoding.ASCII.GetBytes(email)); var key2 = DoStringFromBytes(hash); - var key2_good = string.Compare(parts[1], key2, StringComparison.InvariantCultureIgnoreCase) == 0; + var key2_good = parts[1].Equals(key2, StringComparison.OrdinalIgnoreCase); if (!key2_good) return ValidationResult.Invalid; var ms_current = (long)(DateTime.UtcNow - _from).TotalMilliseconds; return validInterval >= TimeSpan.FromMilliseconds(ms_current - ms) ? ValidationResult.Ok : ValidationResult.Expired; diff --git a/common/ASC.Core.Common/Tenants/Tenant.cs b/common/ASC.Core.Common/Tenants/Tenant.cs index b074f96120..df277d6afd 100644 --- a/common/ASC.Core.Common/Tenants/Tenant.cs +++ b/common/ASC.Core.Common/Tenants/Tenant.cs @@ -181,7 +181,7 @@ namespace ASC.Core.Tenants } else { - result = string.Format("{0}.{1}", TenantAlias, baseHost).TrimEnd('.').ToLowerInvariant(); + result = $"{TenantAlias}.{baseHost}".TrimEnd('.').ToLowerInvariant(); } if (!string.IsNullOrEmpty(MappedDomain) && allowMappedDomain) { diff --git a/common/ASC.Core.Common/Tenants/TenantAuditSettings.cs b/common/ASC.Core.Common/Tenants/TenantAuditSettings.cs index c23f69ef33..0a9036e2e7 100644 --- a/common/ASC.Core.Common/Tenants/TenantAuditSettings.cs +++ b/common/ASC.Core.Common/Tenants/TenantAuditSettings.cs @@ -39,7 +39,7 @@ namespace ASC.Core.Tenants public int AuditTrailLifeTime { get; set; } - public static Guid Guid = new Guid("{8337D0FB-AD67-4552-8297-802312E7F503}"); + public static readonly Guid Guid = new Guid("{8337D0FB-AD67-4552-8297-802312E7F503}"); public Guid ID { get { return Guid; } diff --git a/common/ASC.Core.Common/Tenants/TenantCookieSettings.cs b/common/ASC.Core.Common/Tenants/TenantCookieSettings.cs index e2ce90f933..d738cdf29d 100644 --- a/common/ASC.Core.Common/Tenants/TenantCookieSettings.cs +++ b/common/ASC.Core.Common/Tenants/TenantCookieSettings.cs @@ -91,7 +91,7 @@ namespace ASC.Core.Tenants public void SetForTenant(int tenantId, TenantCookieSettings settings = null) { if (!IsVisibleSettings) return; - SettingsManager.SaveForTenant((settings ?? TenantCookieSettings.GetInstance()), tenantId); + SettingsManager.SaveForTenant(settings ?? TenantCookieSettings.GetInstance(), tenantId); } public TenantCookieSettings GetForUser(Guid userId) @@ -111,7 +111,7 @@ namespace ASC.Core.Tenants public void SetForUser(Guid userId, TenantCookieSettings settings = null) { if (!IsVisibleSettings) return; - SettingsManager.SaveForUser((settings ?? TenantCookieSettings.GetInstance()), userId); + SettingsManager.SaveForUser(settings ?? TenantCookieSettings.GetInstance(), userId); } public DateTime GetExpiresTime(int tenantId) diff --git a/common/ASC.Core.Common/Tenants/TenantExceptions.cs b/common/ASC.Core.Common/Tenants/TenantExceptions.cs index ad573ae653..278bf02b2a 100644 --- a/common/ASC.Core.Common/Tenants/TenantExceptions.cs +++ b/common/ASC.Core.Common/Tenants/TenantExceptions.cs @@ -34,8 +34,8 @@ namespace ASC.Core.Tenants [Serializable] public class TenantTooShortException : Exception { - public int MinLength = 0; - public int MaxLength = 0; + public int MinLength { get; set; } = 0; + public int MaxLength { get; set; } = 0; public TenantTooShortException(string message) : base(message) diff --git a/common/ASC.Core.Common/Tenants/TenantQuota.cs b/common/ASC.Core.Common/Tenants/TenantQuota.cs index 32b0778d96..a6b3a2070b 100644 --- a/common/ASC.Core.Common/Tenants/TenantQuota.cs +++ b/common/ASC.Core.Common/Tenants/TenantQuota.cs @@ -307,7 +307,7 @@ namespace ASC.Core.Tenants internal void SetFeature(string feature, bool set) { var features = (Features == null - ? new string[] { } + ? Array.Empty() : Features.Split(' ', ',', ';')).ToList(); if (set && !features.Contains(feature)) { diff --git a/common/ASC.Core.Common/Users/UserFormatter.cs b/common/ASC.Core.Common/Users/UserFormatter.cs index 77999e0c0c..394f3f8f9b 100644 --- a/common/ASC.Core.Common/Users/UserFormatter.cs +++ b/common/ASC.Core.Common/Users/UserFormatter.cs @@ -38,20 +38,20 @@ namespace ASC.Core.Users [Singletone] public class UserFormatter : IComparer { - private readonly DisplayUserNameFormat format; + private readonly DisplayUserNameFormat _format; private static bool forceFormatChecked; private static string forceFormat; public UserFormatter(IConfiguration configuration) { - format = DisplayUserNameFormat.Default; + _format = DisplayUserNameFormat.Default; Configuration = configuration; UserNameRegex = new Regex(Configuration["core:username:regex"] ?? ""); } public string GetUserName(UserInfo userInfo, DisplayUserNameFormat format) { - if (userInfo == null) throw new ArgumentNullException("userInfo"); + if (userInfo == null) throw new ArgumentNullException(nameof(userInfo)); return string.Format(GetUserDisplayFormat(format), userInfo.FirstName, userInfo.LastName); } @@ -69,7 +69,7 @@ namespace ASC.Core.Users int IComparer.Compare(UserInfo x, UserInfo y) { - return Compare(x, y, format); + return Compare(x, y, _format); } public static int Compare(UserInfo x, UserInfo y) @@ -135,7 +135,7 @@ namespace ASC.Core.Users return format.IndexOf("{0}") < format.IndexOf("{1}") ? DisplayUserNameFormat.FirstLast : DisplayUserNameFormat.LastFirst; } - public Regex UserNameRegex; + public Regex UserNameRegex { get; set; } private IConfiguration Configuration { get; } diff --git a/common/ASC.Core.Common/WhiteLabel/BaseWhiteLabelSettings.cs b/common/ASC.Core.Common/WhiteLabel/BaseWhiteLabelSettings.cs index a1314dd754..1775abd292 100644 --- a/common/ASC.Core.Common/WhiteLabel/BaseWhiteLabelSettings.cs +++ b/common/ASC.Core.Common/WhiteLabel/BaseWhiteLabelSettings.cs @@ -1,6 +1,6 @@ namespace ASC.Core.Common.WhiteLabel { - public class BaseWhiteLabelSettings + public static class BaseWhiteLabelSettings { public const string DefaultLogoText = "ONLYOFFICE"; } diff --git a/common/ASC.Data.Backup.Core/ActionInvoker.cs b/common/ASC.Data.Backup.Core/ActionInvoker.cs index e4ce168963..32c1be95af 100644 --- a/common/ASC.Data.Backup.Core/ActionInvoker.cs +++ b/common/ASC.Data.Backup.Core/ActionInvoker.cs @@ -52,7 +52,7 @@ namespace ASC.Data.Backup bool isSleepExponential = true) { if (action == null) - throw new ArgumentNullException("action"); + throw new ArgumentNullException(nameof(action)); var countAttempts = 0; while (countAttempts++ < maxAttempts) diff --git a/common/ASC.Data.Backup.Core/BackupAjaxHandler.cs b/common/ASC.Data.Backup.Core/BackupAjaxHandler.cs index ba1b96a747..7abb6fc548 100644 --- a/common/ASC.Data.Backup.Core/BackupAjaxHandler.cs +++ b/common/ASC.Data.Backup.Core/BackupAjaxHandler.cs @@ -233,7 +233,7 @@ namespace ASC.Data.Backup { PermissionContext.DemandPermissions(SecutiryConstants.EditPortalSettings); - if (!SetupInfo.IsVisibleSettings(ManagementType.Backup.ToString())) + if (!SetupInfo.IsVisibleSettings(nameof(ManagementType.Backup))) throw new BillingException(Resource.ErrorNotAllowedOption, "Backup"); } @@ -319,7 +319,7 @@ namespace ASC.Data.Backup PermissionContext.DemandPermissions(SecutiryConstants.EditPortalSettings); var currentUser = UserManager.GetUsers(SecurityContext.CurrentAccount.ID); - if (!SetupInfo.IsVisibleSettings(ManagementType.Migration.ToString()) + if (!SetupInfo.IsVisibleSettings(nameof(ManagementType.Migration)) || !currentUser.IsOwner(TenantManager.GetCurrentTenant()) || !SetupInfo.IsSecretEmail(currentUser.Email) && !TenantExtra.GetTenantQuota().HasMigration) throw new InvalidOperationException(Resource.ErrorNotAllowedOption); diff --git a/common/ASC.Data.Backup.Core/Core/DbBackupProvider.cs b/common/ASC.Data.Backup.Core/Core/DbBackupProvider.cs index 8b157647a2..37ede1d558 100644 --- a/common/ASC.Data.Backup.Core/Core/DbBackupProvider.cs +++ b/common/ASC.Data.Backup.Core/Core/DbBackupProvider.cs @@ -68,9 +68,9 @@ namespace ASC.Data.Backup xml.Add(node); var connectionKey = connectionString.ProviderName + connectionString.ConnectionString; - if (connectionKeys.ContainsKey(connectionKey)) + if (connectionKeys.TryGetValue(connectionKey, out var value)) { - node.Add(new XAttribute("ref", connectionKeys[connectionKey])); + node.Add(new XAttribute("ref", value)); } else { @@ -106,7 +106,7 @@ namespace ASC.Data.Backup { var map = new ExeConfigurationFileMap { - ExeConfigFilename = string.Compare(Path.GetExtension(config), ".config", true) == 0 ? config : CrossPlatform.PathCombine(config, "Web.config") + ExeConfigFilename = string.Equals(Path.GetExtension(config), ".config", StringComparison.OrdinalIgnoreCase) ? config : CrossPlatform.PathCombine(config, "Web.config") }; return ConfigurationManager.OpenMappedExeConfiguration(map, ConfigurationUserLevel.None); } @@ -160,7 +160,7 @@ namespace ASC.Data.Backup } xml.Add(new XElement(table)); - DataTable dataTable = null; + DataTable dataTable; while (true) { try @@ -183,7 +183,7 @@ namespace ASC.Data.Backup using (var file = tempStream.Create()) { dataTable.WriteXml(file, XmlWriteMode.WriteSchema); - writer.WriteEntry(string.Format("{0}\\{1}\\{2}", Name, connectionString.Name, table).ToLower(), file); + writer.WriteEntry($"{Name}\\{connectionString.Name}\\{table}".ToLower(), file); } processedTables.Add(table); @@ -194,11 +194,11 @@ namespace ASC.Data.Backup private void RestoreDatabase(ConnectionStringSettings connectionString, IEnumerable elements, IDataReadOperator reader) { var dbName = connectionString.Name; - var dbElement = elements.SingleOrDefault(e => string.Compare(e.Name.LocalName, connectionString.Name, true) == 0); + var dbElement = elements.SingleOrDefault(e => string.Equals(e.Name.LocalName, connectionString.Name, StringComparison.OrdinalIgnoreCase)); if (dbElement != null && dbElement.Attribute("ref") != null) { dbName = dbElement.Attribute("ref").Value; - dbElement = elements.Single(e => string.Compare(e.Name.LocalName, dbElement.Attribute("ref").Value, true) == 0); + dbElement = elements.Single(e => string.Equals(e.Name.LocalName, dbElement.Attribute("ref").Value, StringComparison.OrdinalIgnoreCase)); } if (dbElement == null) return; @@ -215,7 +215,7 @@ namespace ASC.Data.Backup if (dbElement.Element(table) != null) { - using (var stream = reader.GetEntry(string.Format("{0}\\{1}\\{2}", Name, dbName, table).ToLower())) + using (var stream = reader.GetEntry($"{Name}\\{dbName}\\{table}".ToLower())) { var data = new DataTable(); data.ReadXml(stream); diff --git a/common/ASC.Data.Backup.Core/Core/DbHelper.cs b/common/ASC.Data.Backup.Core/Core/DbHelper.cs index 165bc97dfc..af0f64580e 100644 --- a/common/ASC.Data.Backup.Core/Core/DbHelper.cs +++ b/common/ASC.Data.Backup.Core/Core/DbHelper.cs @@ -14,7 +14,6 @@ using ASC.Common.Logging; using ASC.Common.Utils; using ASC.Core.Common.EF; using ASC.Core.Common.EF.Context; -using ASC.Data.Backup.EF.Context; using Microsoft.EntityFrameworkCore; using Microsoft.Extensions.Options; @@ -30,15 +29,13 @@ namespace ASC.Data.Backup private readonly DataTable columns; private readonly bool mysql; private readonly IDictionary whereExceptions = new Dictionary(); - private readonly ILog log; - private readonly BackupsContext backupsContext; + private readonly ILog log; private readonly TenantDbContext tenantDbContext; private readonly CoreDbContext coreDbContext; - public DbHelper(IOptionsMonitor options, ConnectionStringSettings connectionString, BackupsContext backupsContext, TenantDbContext tenantDbContext, CoreDbContext coreDbContext) + public DbHelper(IOptionsMonitor options, ConnectionStringSettings connectionString, TenantDbContext tenantDbContext, CoreDbContext coreDbContext) { - log = options.CurrentValue; - this.backupsContext = backupsContext; + log = options.CurrentValue; this.tenantDbContext = tenantDbContext; this.coreDbContext = coreDbContext; var file = connectionString.ElementInformation.Source; @@ -54,7 +51,7 @@ namespace ASC.Data.Backup connect.ConnectionString = connectionString.ConnectionString; connect.Open(); - mysql = connectionString.ProviderName.ToLower().Contains("mysql"); + mysql = connectionString.ProviderName.Contains("mysql", StringComparison.OrdinalIgnoreCase); if (mysql) { CreateCommand("set @@session.sql_mode = concat(@@session.sql_mode, ',NO_AUTO_VALUE_ON_ZERO')").ExecuteNonQuery(); @@ -119,7 +116,7 @@ namespace ASC.Data.Backup tables = connect .GetSchema("Tables") .Select(@"TABLE_TYPE <> 'SYSTEM_TABLE'") - .Select(row => ((string)row["TABLE_NAME"])); + .Select(row => (string)row["TABLE_NAME"]); } return tables @@ -187,13 +184,13 @@ namespace ASC.Data.Backup .Intersect(table.Columns.Cast().Select(c => c.ColumnName), StringComparer.InvariantCultureIgnoreCase) .ToList(); - tableColumns.ForEach(column => sql.AppendFormat("{0}, ", Quote(column))); + tableColumns.ForEach(column => sql.Append($"{Quote(column)}, ")); sql.Replace(", ", ") values (", sql.Length - 2, 2); var insert = connect.CreateCommand(); tableColumns.ForEach(column => { - sql.AppendFormat("@{0}, ", column); + sql.Append($"@{column}, "); var p = insert.CreateParameter(); p.ParameterName = "@" + column; insert.Parameters.Add(p); @@ -257,7 +254,7 @@ namespace ASC.Data.Backup } else { - return columns.Select(string.Format("TABLE_NAME = '{0}'", table)) + return columns.Select($"TABLE_NAME = '{table}'") .Select(r => r["COLUMN_NAME"].ToString()); } } @@ -266,11 +263,11 @@ namespace ASC.Data.Backup { if (tenant == -1) return string.Empty; - if (whereExceptions.ContainsKey(tableName.ToLower())) + if (whereExceptions.TryGetValue(tableName.ToLower(), out var exc)) { - return string.Format(whereExceptions[tableName.ToLower()], tenant); + return string.Format(exc, tenant); } - var tenantColumn = GetColumnsFrom(tableName).FirstOrDefault(c => c.ToLower().StartsWith("tenant")); + var tenantColumn = GetColumnsFrom(tableName).FirstOrDefault(c => c.StartsWith("tenant", StringComparison.OrdinalIgnoreCase)); return tenantColumn != null ? " where " + Quote(tenantColumn) + " = " + tenant : " where 1 = 0"; diff --git a/common/ASC.Data.Backup.Core/Core/FileBackupProvider.cs b/common/ASC.Data.Backup.Core/Core/FileBackupProvider.cs index 5494183ad2..200731a094 100644 --- a/common/ASC.Data.Backup.Core/Core/FileBackupProvider.cs +++ b/common/ASC.Data.Backup.Core/Core/FileBackupProvider.cs @@ -132,7 +132,7 @@ namespace ASC.Data.Backup files.AddRange(store .ListFilesRelative(string.Empty, "\\", "*.*", true) - .Where(x => domainList.All(domain => x.IndexOf(string.Format("{0}/", domain)) == -1)) + .Where(x => domainList.All(domain => x.IndexOf($"{domain}/") == -1)) .Select(x => new FileBackupInfo(string.Empty, module, x))); } } diff --git a/common/ASC.Data.Backup.Core/Core/NotifyHelper.cs b/common/ASC.Data.Backup.Core/Core/NotifyHelper.cs index db8968d5c6..bce7596186 100644 --- a/common/ASC.Data.Backup.Core/Core/NotifyHelper.cs +++ b/common/ASC.Data.Backup.Core/Core/NotifyHelper.cs @@ -112,7 +112,6 @@ namespace ASC.Data.Backup var (userManager, studioNotifyHelper, studioNotifySource, displayUserSettingsHelper, authManager) = scopeClass; var client = WorkContext.NotifyContext.NotifyService.RegisterClient(studioNotifySource, scope); - var owner = userManager.GetUsers(tenant.OwnerId); var users = notifyAllUsers ? userManager.GetUsers(EmployeeStatus.Active) : new[] { userManager.GetUsers(tenantManager.GetCurrentTenant().OwnerId) }; @@ -145,7 +144,7 @@ namespace ASC.Data.Backup .Where(u => notify ? u.ActivationStatus.HasFlag(EmployeeActivationStatus.Activated) : u.IsOwner(tenant)) .ToArray(); - if (users.Any()) + if (users.Length > 0) { var args = CreateArgs(scope, region, url); if (action == Actions.MigrationPortalSuccessV115) @@ -238,7 +237,7 @@ namespace ASC.Data.Backup } } - public class NotifyHelperExtension + public static class NotifyHelperExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.Data.Backup.Core/Core/ZipOperator.cs b/common/ASC.Data.Backup.Core/Core/ZipOperator.cs index 764080ab7c..56d45d8b6e 100644 --- a/common/ASC.Data.Backup.Core/Core/ZipOperator.cs +++ b/common/ASC.Data.Backup.Core/Core/ZipOperator.cs @@ -37,16 +37,14 @@ namespace ASC.Data.Backup { public class ZipWriteOperator : IDataWriteOperator { - private readonly GZipOutputStream gZipOutputStream; private readonly TarOutputStream tarOutputStream; - private readonly Stream file; private TempStream TempStream { get; } public ZipWriteOperator(TempStream tempStream, string targetFile) { - file = new FileStream(targetFile, FileMode.Create); - gZipOutputStream = new GZipOutputStream(file); + var file = new FileStream(targetFile, FileMode.Create); + var gZipOutputStream = new GZipOutputStream(file); tarOutputStream = new TarOutputStream(gZipOutputStream, Encoding.UTF8); TempStream = tempStream; } diff --git a/common/ASC.Data.Backup.Core/Exceptions/ThrowHelper.cs b/common/ASC.Data.Backup.Core/Exceptions/ThrowHelper.cs index 94dccdcb2c..d88631c5ff 100644 --- a/common/ASC.Data.Backup.Core/Exceptions/ThrowHelper.cs +++ b/common/ASC.Data.Backup.Core/Exceptions/ThrowHelper.cs @@ -34,32 +34,32 @@ namespace ASC.Data.Backup.Exceptions { public static DbBackupException CantDetectTenant(string tableName) { - return new DbBackupException(string.Format("Can't detect tenant column for table {0}.", tableName)); + return new DbBackupException($"Can't detect tenant column for table {tableName}."); } public static DbBackupException CantOrderTables(IEnumerable conflictingTables) { - return new DbBackupException(string.Format("Can't order tables [\"{0}\"].", string.Join("\", \"", conflictingTables.ToArray()))); + return new DbBackupException($"Can't order tables [\"{string.Join("\", \"", conflictingTables.ToArray())}\"]."); } public static DbBackupException CantOrderModules(IEnumerable conflictingTypes) { - return new DbBackupException(string.Format("Can't order modules [\"{0}\"].", string.Join("\", \"", conflictingTypes.Select(x => x.Name).ToArray()))); + return new DbBackupException($"Can't order modules [\"{string.Join("\", \"", conflictingTypes.Select(x => x.Name).ToArray())}\"]."); } public static DbBackupException CantRestoreTable(string tableName, Exception reason) { - return new DbBackupException(string.Format("Can't restore table {0}.", tableName), reason); + return new DbBackupException($"Can't restore table {tableName}.", reason); } public static DbBackupException CantBackupTable(string tableName, Exception reason) { - return new DbBackupException(string.Format("Can't backup table {0}.", tableName), reason); + return new DbBackupException($"Can't backup table {tableName}.", reason); } public static DbBackupException CantDeleteTable(string tableName, Exception reason) { - return new DbBackupException(string.Format("Can't delete table {0}.", tableName), reason); + return new DbBackupException($"Can't delete table {tableName}.", reason); } } } diff --git a/common/ASC.Data.Backup.Core/Extensions/EnumerableExtensions.cs b/common/ASC.Data.Backup.Core/Extensions/EnumerableExtensions.cs index c8243c9104..6fc7aec1dd 100644 --- a/common/ASC.Data.Backup.Core/Extensions/EnumerableExtensions.cs +++ b/common/ASC.Data.Backup.Core/Extensions/EnumerableExtensions.cs @@ -56,13 +56,13 @@ namespace ASC.Data.Backup.Extensions Func parentKeySelector) { if (elements == null) - throw new ArgumentNullException("elements"); + throw new ArgumentNullException(nameof(elements)); if (keySelector == null) - throw new ArgumentNullException("keySelector"); + throw new ArgumentNullException(nameof(keySelector)); if (parentKeySelector == null) - throw new ArgumentNullException("parentKeySelector"); + throw new ArgumentNullException(nameof(parentKeySelector)); var dic = elements.ToDictionary(keySelector, x => new TreeNode(x)); foreach (var keyValue in dic) @@ -81,11 +81,16 @@ namespace ASC.Data.Backup.Extensions public static IEnumerable> MakeParts(this IEnumerable collection, int partLength) { if (collection == null) - throw new ArgumentNullException("collection"); + throw new ArgumentNullException(nameof(collection)); if (partLength <= 0) - throw new ArgumentOutOfRangeException("partLength", partLength, "Length must be positive integer"); + throw new ArgumentOutOfRangeException(nameof(partLength), partLength, "Length must be positive integer"); + return MakePartsIterator(collection, partLength); + } + + private static IEnumerable> MakePartsIterator(this IEnumerable collection, int partLength) + { var part = new List(partLength); foreach (var entry in collection) diff --git a/common/ASC.Data.Backup.Core/Service/BackupWorker.cs b/common/ASC.Data.Backup.Core/Service/BackupWorker.cs index ff32c687e0..cdb6b1a943 100644 --- a/common/ASC.Data.Backup.Core/Service/BackupWorker.cs +++ b/common/ASC.Data.Backup.Core/Service/BackupWorker.cs @@ -334,7 +334,7 @@ namespace ASC.Data.Backup.Services protected IServiceProvider ServiceProvider { get; set; } - public BaseBackupProgressItem(IOptionsMonitor options, IServiceProvider serviceProvider) + protected BaseBackupProgressItem(IOptionsMonitor options, IServiceProvider serviceProvider) { Log = options.CurrentValue; ServiceProvider = serviceProvider; @@ -405,7 +405,6 @@ namespace ASC.Data.Backup.Services var scopeClass = scope.ServiceProvider.GetService(); var (tenantManager, backupStorageFactory, notifyHelper, backupRepository, backupWorker, backupPortalTask, _, _, coreBaseSettings) = scopeClass; - var tenant = tenantManager.GetTenant(TenantId); var dateTime = coreBaseSettings.Standalone ? DateTime.Now : DateTime.UtcNow; var backupName = string.Format("{0}_{1:yyyy-MM-dd_HH-mm-ss}.{2}", tenantManager.GetTenant(TenantId).TenantAlias, dateTime, ArchiveFormat); @@ -560,14 +559,14 @@ namespace ASC.Data.Backup.Services tenantManager.SaveTenant(tenant); var columnMapper = new ColumnMapper(); - columnMapper.SetMapping("tenants_tenants", "alias", tenant.TenantAlias, (Guid.Parse(Id)).ToString("N")); + columnMapper.SetMapping("tenants_tenants", "alias", tenant.TenantAlias, Guid.Parse(Id).ToString("N")); columnMapper.Commit(); var restoreTask = restorePortalTask; restoreTask.Init(ConfigPaths[CurrentRegion], tempFile, TenantId, columnMapper, UpgradesPath); restoreTask.ProgressChanged += (sender, args) => { - Percentage = Percentage = (10d + 0.65 * args.Progress); + Percentage = Percentage = 10d + 0.65 * args.Progress; PublishChanges(); }; restoreTask.RunJob(); @@ -881,7 +880,7 @@ namespace ASC.Data.Backup.Services } } - public class BackupWorkerExtension + public static class BackupWorkerExtension { public static void Register(DIHelper services) { @@ -890,7 +889,7 @@ namespace ASC.Data.Backup.Services } } - public class FactoryProgressItemExtension + public static class FactoryProgressItemExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.Data.Backup.Core/Storage/BackupRepository.cs b/common/ASC.Data.Backup.Core/Storage/BackupRepository.cs index 28339b4e43..dd735303c9 100644 --- a/common/ASC.Data.Backup.Core/Storage/BackupRepository.cs +++ b/common/ASC.Data.Backup.Core/Storage/BackupRepository.cs @@ -26,46 +26,45 @@ using System; using System.Collections.Generic; -using System.Linq; - -using ASC.Common; -using ASC.Core.Common.EF; -using ASC.Core.Common.EF.Context; +using System.Linq; + +using ASC.Common; +using ASC.Core.Common.EF; using ASC.Core.Tenants; using ASC.Data.Backup.EF.Context; -using ASC.Data.Backup.EF.Model; - -using Microsoft.EntityFrameworkCore; - +using ASC.Data.Backup.EF.Model; + +using Microsoft.EntityFrameworkCore; + namespace ASC.Data.Backup.Storage -{ +{ [Scope] public class BackupRepository : IBackupRepository - { - private readonly Lazy _backupContext; - public BackupRepository(DbContextManager dbContactManager) - { + { + private readonly Lazy _backupContext; + public BackupRepository(DbContextManager dbContactManager) + { _backupContext = new Lazy(() => dbContactManager.Value); } public void SaveBackupRecord(BackupRecord backup) { _backupContext.Value.AddOrUpdate(r => r.Backups, backup); - _backupContext.Value.SaveChanges(); + _backupContext.Value.SaveChanges(); } public BackupRecord GetBackupRecord(Guid id) - { - return _backupContext.Value.Backups.Find(id); - } - - public BackupRecord GetBackupRecord(string hash, int tenant) - { - return _backupContext.Value.Backups.AsNoTracking().SingleOrDefault(b => b.Hash == hash && b.TenantId == tenant); - } + { + return _backupContext.Value.Backups.Find(id); + } + + public BackupRecord GetBackupRecord(string hash, int tenant) + { + return _backupContext.Value.Backups.AsNoTracking().SingleOrDefault(b => b.Hash == hash && b.TenantId == tenant); + } public List GetExpiredBackupRecords() - { + { return _backupContext.Value.Backups.AsNoTracking().Where(b => b.ExpiresOn != DateTime.MinValue && b.ExpiresOn <= DateTime.UtcNow).ToList(); } @@ -82,7 +81,7 @@ namespace ASC.Data.Backup.Storage public void DeleteBackupRecord(Guid id) { var backup = _backupContext.Value.Backups.Find(id); - + if (backup != null) { _backupContext.Value.Backups.Remove(backup); @@ -98,7 +97,7 @@ namespace ASC.Data.Backup.Storage public void DeleteBackupSchedule(int tenantId) { - var shedule = _backupContext.Value.Schedules.Where(s => s.TenantId == tenantId).ToList(); + var shedule = _backupContext.Value.Schedules.Where(s => s.TenantId == tenantId).ToList(); _backupContext.Value.Schedules.RemoveRange(shedule); _backupContext.Value.SaveChanges(); @@ -107,18 +106,18 @@ namespace ASC.Data.Backup.Storage public List GetBackupSchedules() { var query = _backupContext.Value.Schedules.Join(_backupContext.Value.Tenants, - s => s.TenantId, + s => s.TenantId, t => t.Id, - (s, t) => new { schedule = s, tenant = t }) - .Where(q => q.tenant.Status == TenantStatus.Active) - .Select(q => q.schedule); + (s, t) => new { schedule = s, tenant = t }) + .Where(q => q.tenant.Status == TenantStatus.Active) + .Select(q => q.schedule); return query.ToList(); } public BackupSchedule GetBackupSchedule(int tenantId) - { - return _backupContext.Value.Schedules.AsNoTracking().SingleOrDefault(s => s.TenantId == tenantId); - } + { + return _backupContext.Value.Schedules.AsNoTracking().SingleOrDefault(s => s.TenantId == tenantId); + } } } diff --git a/common/ASC.Data.Backup.Core/Storage/DocumentsBackupStorage.cs b/common/ASC.Data.Backup.Core/Storage/DocumentsBackupStorage.cs index 2ff9ef461c..38baee80fb 100644 --- a/common/ASC.Data.Backup.Core/Storage/DocumentsBackupStorage.cs +++ b/common/ASC.Data.Backup.Core/Storage/DocumentsBackupStorage.cs @@ -155,7 +155,7 @@ namespace ASC.Data.Backup.Storage var chunkedUploadSession = fileDao.CreateUploadSession(newFile, source.Length); chunkedUploadSession.CheckQuota = false; - var bytesRead = 0; + int bytesRead; while ((bytesRead = source.Read(buffer, 0, (int)SetupInfo.ChunkUploadSize)) > 0) { diff --git a/common/ASC.Data.Backup.Core/Tasks/BackupPortalTask.cs b/common/ASC.Data.Backup.Core/Tasks/BackupPortalTask.cs index 2d89d272a1..046e82f3fa 100644 --- a/common/ASC.Data.Backup.Core/Tasks/BackupPortalTask.cs +++ b/common/ASC.Data.Backup.Core/Tasks/BackupPortalTask.cs @@ -78,7 +78,7 @@ namespace ASC.Data.Backup.Tasks public void Init(int tenantId, string fromConfigPath, string toFilePath, int limit) { if (string.IsNullOrEmpty(toFilePath)) - throw new ArgumentNullException("toFilePath"); + throw new ArgumentNullException(nameof(toFilePath)); BackupFilePath = toFilePath; Limit = limit; Init(tenantId, fromConfigPath); @@ -209,7 +209,7 @@ namespace ASC.Data.Backup.Tasks { var files = GetFilesToProcess(tenantId).ToList(); var exclude = BackupRecordContext.Backups.Where(b => b.TenantId == tenantId && b.StorageType == 0 && b.StoragePath != null).ToList(); - files = files.Where(f => !exclude.Any(e => f.Path.Replace('\\', '/').Contains(string.Format("/file_{0}/", e.StoragePath)))).ToList(); + files = files.Where(f => !exclude.Any(e => f.Path.Replace('\\', '/').Contains($"/file_{e.StoragePath}/"))).ToList(); return files; } @@ -222,15 +222,15 @@ namespace ASC.Data.Backup.Tasks using (var connection = DbFactory.OpenConnection()) { var command = connection.CreateCommand(); - command.CommandText = string.Format("SHOW CREATE TABLE `{0}`", t); + command.CommandText = $"SHOW CREATE TABLE `{t}`"; var createScheme = ExecuteList(command); var creates = new StringBuilder(); - creates.AppendFormat("DROP TABLE IF EXISTS `{0}`;", t); + creates.Append($"DROP TABLE IF EXISTS `{t}`;"); creates.AppendLine(); creates.Append(createScheme .Select(r => Convert.ToString(r[1])) .FirstOrDefault()); - creates.Append(";"); + creates.Append(';'); var path = CrossPlatform.PathCombine(dir, t); using (var stream = File.OpenWrite(path)) @@ -284,7 +284,7 @@ namespace ASC.Data.Backup.Tasks } Logger.DebugFormat("dump table data start {0}", t); - var searchWithPrimary = false; + bool searchWithPrimary; string primaryIndex; var primaryIndexStep = 0; var primaryIndexStart = 0; @@ -293,7 +293,7 @@ namespace ASC.Data.Backup.Tasks using (var connection = DbFactory.OpenConnection()) { var command = connection.CreateCommand(); - command.CommandText = string.Format("SHOW COLUMNS FROM `{0}`", t); + command.CommandText = string.Format($"SHOW COLUMNS FROM `{t}`"); columns = ExecuteList(command).Select(r => "`" + Convert.ToString(r[0]) + "`").ToList(); if (command.CommandText.Contains("tenants_quota") || command.CommandText.Contains("webstudio_settings")) { @@ -304,14 +304,14 @@ namespace ASC.Data.Backup.Tasks using (var connection = DbFactory.OpenConnection()) { var command = connection.CreateCommand(); - command.CommandText = string.Format("select COLUMN_NAME from information_schema.`COLUMNS` where TABLE_SCHEMA = '{0}' and TABLE_NAME = '{1}' and COLUMN_KEY = 'PRI' and DATA_TYPE = 'int'", connection.Database, t); + command.CommandText = $"select COLUMN_NAME from information_schema.`COLUMNS` where TABLE_SCHEMA = '{connection.Database}' and TABLE_NAME = '{t}' and COLUMN_KEY = 'PRI' and DATA_TYPE = 'int'"; primaryIndex = ExecuteList(command).ConvertAll(r => Convert.ToString(r[0])).FirstOrDefault(); } using (var connection = DbFactory.OpenConnection()) { var command = connection.CreateCommand(); - command.CommandText = string.Format("SHOW INDEXES FROM {0} WHERE COLUMN_NAME='{1}' AND seq_in_index=1", t, primaryIndex); + command.CommandText = $"SHOW INDEXES FROM {t} WHERE COLUMN_NAME='{primaryIndex}' AND seq_in_index=1"; var isLeft = ExecuteList(command); searchWithPrimary = isLeft.Count == 1; } @@ -320,7 +320,7 @@ namespace ASC.Data.Backup.Tasks { using var connection = DbFactory.OpenConnection(); var command = connection.CreateCommand(); - command.CommandText = string.Format("select max({1}), min({1}) from {0}", t, primaryIndex); + command.CommandText = $"select max({primaryIndex}), min({primaryIndex}) from {t}"; var minMax = ExecuteList(command).ConvertAll(r => new Tuple(Convert.ToInt32(r[0]), Convert.ToInt32(r[1]))).FirstOrDefault(); primaryIndexStart = minMax.Item2; primaryIndexStep = (minMax.Item1 - minMax.Item2) / count; @@ -391,9 +391,9 @@ namespace ASC.Data.Backup.Tasks private void SaveToFile(string path, string t, IReadOnlyCollection columns, List data) { - Logger.DebugFormat("save to file {0}", t); + Logger.DebugFormat("save to file {0}", t); List portion; - while ((portion = data.Take(BatchLimit).ToList()).Any()) + while ((portion = data.Take(BatchLimit).ToList()).Count > 0) { using (var sw = new StreamWriter(path, true)) using (var writer = new JsonTextWriter(sw)) @@ -410,7 +410,8 @@ namespace ASC.Data.Backup.Tasks for (var i = 0; i < obj.Length; i++) { - if (obj[i] is byte[] byteArray) + var value = obj[i]; + if (value is byte[] byteArray) { sw.Write("0x"); foreach (var b in byteArray) @@ -419,7 +420,7 @@ namespace ASC.Data.Backup.Tasks else { var ser = new JsonSerializer(); - ser.Serialize(writer, obj[i]); + ser.Serialize(writer, value); } if (i != obj.Length - 1) { @@ -542,7 +543,7 @@ namespace ASC.Data.Backup.Tasks var files = GetFilesToProcess(TenantId).ToList(); var exclude = BackupRecordContext.Backups.Where(b => b.TenantId == TenantId && b.StorageType == 0 && b.StoragePath != null).ToList(); - files = files.Where(f => !exclude.Any(e => f.Path.Replace('\\', '/').Contains(string.Format("/file_{0}/", e.StoragePath)))).ToList(); + files = files.Where(f => !exclude.Any(e => f.Path.Replace('\\', '/').Contains($"/file_{e.StoragePath}/"))).ToList(); return files.GroupBy(file => file.Module).ToList(); } @@ -604,7 +605,7 @@ namespace ASC.Data.Backup.Tasks Logger.DebugFormat("end saving table {0}", table.Name); } - SetCurrentStepProgress((int)((++tablesProcessed * 100) / (double)tablesCount)); + SetCurrentStepProgress((int)(++tablesProcessed * 100 / (double)tablesCount)); } } Logger.DebugFormat("end saving data for module {0}", module.ModuleName); diff --git a/common/ASC.Data.Backup.Core/Tasks/ColumnMapper.cs b/common/ASC.Data.Backup.Core/Tasks/ColumnMapper.cs index e4e8829d77..7e4bb6e171 100644 --- a/common/ASC.Data.Backup.Core/Tasks/ColumnMapper.cs +++ b/common/ASC.Data.Backup.Core/Tasks/ColumnMapper.cs @@ -140,7 +140,7 @@ namespace ASC.Data.Backup.Tasks private static string GetMappingKey(string tableName, string columnName) { - return string.Format("t:{0};c:{1}", tableName, columnName).ToLowerInvariant(); + return $"t:{tableName};c:{columnName}".ToLowerInvariant(); } private static string GetMappingKey(string tableName, string columnName, object oldValue) diff --git a/common/ASC.Data.Backup.Core/Tasks/Data/DataRowInfo.cs b/common/ASC.Data.Backup.Core/Tasks/Data/DataRowInfo.cs index 445e94625f..4a8556aa1d 100644 --- a/common/ASC.Data.Backup.Core/Tasks/Data/DataRowInfo.cs +++ b/common/ASC.Data.Backup.Core/Tasks/Data/DataRowInfo.cs @@ -86,7 +86,7 @@ namespace ASC.Data.Backup.Tasks.Data while (i < _values.Count && sb.Length <= maxStrLength) { var strVal = Convert.ToString(_values[i]); - sb.AppendFormat("\"{0}\", ", strVal); + sb.Append($"\"{strVal}\", "); i++; } diff --git a/common/ASC.Data.Backup.Core/Tasks/Data/TableInfo.cs b/common/ASC.Data.Backup.Core/Tasks/Data/TableInfo.cs index 3eacb6f69f..9f3b0b9d0c 100644 --- a/common/ASC.Data.Backup.Core/Tasks/Data/TableInfo.cs +++ b/common/ASC.Data.Backup.Core/Tasks/Data/TableInfo.cs @@ -26,7 +26,6 @@ using System.Collections.Generic; using System.Diagnostics; -using System.Linq; namespace ASC.Data.Backup.Tasks.Data { @@ -63,7 +62,6 @@ namespace ASC.Data.Backup.Tasks.Data IdColumn = idColumn; IdType = idType; TenantColumn = tenantColumn; - UserIDColumns = new string[0]; DateColumns = new Dictionary(); InsertMethod = InsertMethod.Insert; } @@ -75,7 +73,7 @@ namespace ASC.Data.Backup.Tasks.Data public bool HasDateColumns() { - return DateColumns.Any(); + return DateColumns.Count > 0; } public bool HasTenantColumn() diff --git a/common/ASC.Data.Backup.Core/Tasks/DeletePortalTask.cs b/common/ASC.Data.Backup.Core/Tasks/DeletePortalTask.cs index 5cc0841441..46bcbbbaf2 100644 --- a/common/ASC.Data.Backup.Core/Tasks/DeletePortalTask.cs +++ b/common/ASC.Data.Backup.Core/Tasks/DeletePortalTask.cs @@ -75,7 +75,7 @@ namespace ASC.Data.Backup.Tasks var t = (TableInfo)state; module.CreateDeleteCommand(connection.Fix(), TenantId, t).WithTimeout(120).ExecuteNonQuery(); }, table, 5, onFailure: error => { throw ThrowHelper.CantDeleteTable(table.Name, error); }); - SetCurrentStepProgress((int)((++tablesProcessed * 100) / (double)tablesCount)); + SetCurrentStepProgress((int)(++tablesProcessed * 100 / (double)tablesCount)); } } Logger.DebugFormat("end delete data for module ({0})", module.ModuleName); @@ -89,14 +89,14 @@ namespace ASC.Data.Backup.Tasks foreach (var module in storageModules) { var storage = StorageFactory.GetStorage(ConfigPath, TenantId.ToString(), module); - var domains = StorageFactoryConfig.GetDomainList(ConfigPath, module).ToList(); + var domains = StorageFactoryConfig.GetDomainList(ConfigPath, module); foreach (var domain in domains) { ActionInvoker.Try(state => storage.DeleteFiles((string)state, "\\", "*.*", true), domain, 5, onFailure: error => Logger.WarnFormat("Can't delete files for domain {0}: \r\n{1}", domain, error)); } storage.DeleteFiles("\\", "*.*", true); - SetCurrentStepProgress((int)((++modulesProcessed * 100) / (double)storageModules.Count)); + SetCurrentStepProgress((int)(++modulesProcessed * 100 / (double)storageModules.Count)); } Logger.Debug("end delete storage"); } diff --git a/common/ASC.Data.Backup.Core/Tasks/KeyHelper.cs b/common/ASC.Data.Backup.Core/Tasks/KeyHelper.cs index e0666604c1..f9246cd14d 100644 --- a/common/ASC.Data.Backup.Core/Tasks/KeyHelper.cs +++ b/common/ASC.Data.Backup.Core/Tasks/KeyHelper.cs @@ -40,27 +40,27 @@ namespace ASC.Data.Backup.Tasks public static string GetDatabaseSchema() { - return string.Format("{0}/{1}", Databases, "scheme"); + return $"{Databases}/scheme"; } public static string GetDatabaseData() { - return string.Format("{0}/{1}", Databases, "data"); + return $"{Databases}/data"; } public static string GetDatabaseSchema(string table) { - return string.Format("{0}/{1}", GetDatabaseSchema(), table); + return $"{GetDatabaseSchema()}/{table}"; } public static string GetDatabaseData(string table) { - return string.Format("{0}/{1}", GetDatabaseData(), table); + return $"{GetDatabaseData()}/{table}"; } public static string GetTableZipKey(IModuleSpecifics module, string tableName) { - return string.Format("{0}/{1}/{2}", Databases, module.ConnectionStringName, tableName); + return $"{Databases}/{module.ConnectionStringName}/{tableName}"; } public static string GetZipKey(this BackupFileInfo file) @@ -74,7 +74,7 @@ namespace ASC.Data.Backup.Tasks } public static string GetStorageRestoreInfoZipKey() { - return string.Format("{0}/restore_info", GetStorage()); + return $"{GetStorage()}/restore_info"; } } } diff --git a/common/ASC.Data.Backup.Core/Tasks/Modules/MailModuleSpecifics.cs b/common/ASC.Data.Backup.Core/Tasks/Modules/MailModuleSpecifics.cs index d57e1ccc4e..1aaaa187fb 100644 --- a/common/ASC.Data.Backup.Core/Tasks/Modules/MailModuleSpecifics.cs +++ b/common/ASC.Data.Backup.Core/Tasks/Modules/MailModuleSpecifics.cs @@ -183,7 +183,7 @@ namespace ASC.Data.Backup.Tasks.Modules { //todo: hack: will be changed later filePath = Regex.Replace(filePath, @"^[-\w]+(?=/)", match => dump ? match.Value : columnMapper.GetUserMapping(match.Value)); - return !filePath.StartsWith("/"); + return !filePath.StartsWith('/'); } protected override bool TryPrepareRow(bool dump, DbConnection connection, ColumnMapper columnMapper, TableInfo table, DataRowInfo row, out Dictionary preparedRow) diff --git a/common/ASC.Data.Backup.Core/Tasks/Modules/ModuleProvider.cs b/common/ASC.Data.Backup.Core/Tasks/Modules/ModuleProvider.cs index 1bf2817cb7..36d25e62c4 100644 --- a/common/ASC.Data.Backup.Core/Tasks/Modules/ModuleProvider.cs +++ b/common/ASC.Data.Backup.Core/Tasks/Modules/ModuleProvider.cs @@ -38,7 +38,7 @@ namespace ASC.Data.Backup.Tasks.Modules [Scope] public class ModuleProvider { - public List AllModules; + public List AllModules { get; } public ModuleProvider(IOptionsMonitor options, Helpers helpers, CoreSettings coreSettings) { diff --git a/common/ASC.Data.Backup.Core/Tasks/Modules/ModuleSpecificsBase.cs b/common/ASC.Data.Backup.Core/Tasks/Modules/ModuleSpecificsBase.cs index b4e9165231..8cb6a321a9 100644 --- a/common/ASC.Data.Backup.Core/Tasks/Modules/ModuleSpecificsBase.cs +++ b/common/ASC.Data.Backup.Core/Tasks/Modules/ModuleSpecificsBase.cs @@ -49,7 +49,7 @@ namespace ASC.Data.Backup.Tasks.Modules public abstract IEnumerable Tables { get; } public abstract IEnumerable TableRelations { get; } private readonly Helpers helpers; - public ModuleSpecificsBase(Helpers helpers) + protected ModuleSpecificsBase(Helpers helpers) { this.helpers = helpers; } @@ -99,7 +99,7 @@ namespace ASC.Data.Backup.Tasks.Modules public DbCommand CreateDeleteCommand(DbConnection connection, int tenantId, TableInfo table) { var command = connection.CreateCommand(); - command.CommandText = string.Format("delete t.* from {0} as t {1};", table.Name, GetDeleteCommandConditionText(tenantId, table)); + command.CommandText = $"delete t.* from {table.Name} as t {GetDeleteCommandConditionText(tenantId, table)};"; return command; } @@ -112,14 +112,10 @@ namespace ASC.Data.Backup.Tasks.Modules return null; var columns = valuesForInsert.Keys.Intersect(table.Columns).ToArray(); - - var insertCommantText = string.Format("{0} into {1}({2}) values({3});", - table.InsertMethod != InsertMethod.Ignore + var insert = table.InsertMethod != InsertMethod.Ignore ? table.InsertMethod.ToString().ToLower() - : "insert ignore", - table.Name, - string.Join(",", columns), - string.Join(",", columns.Select(c => "@" + c))); + : "insert ignore"; + var insertCommantText = $"{insert} into {table.Name}({string.Join(",", columns)}) values({string.Join(",", columns.Select(c => "@" + c))});"; var command = connection.CreateCommand(); command.CommandText = insertCommantText; @@ -134,7 +130,7 @@ namespace ASC.Data.Backup.Tasks.Modules var p = command.CreateParameter(); if (!string.IsNullOrEmpty(name)) { - p.ParameterName = name.StartsWith("@") ? name : "@" + name; + p.ParameterName = name.StartsWith('@') ? name : "@" + name; } p.Value = GetParameterValue(value); diff --git a/common/ASC.Data.Backup.Core/Tasks/Modules/ProjectsModuleSpecifics.cs b/common/ASC.Data.Backup.Core/Tasks/Modules/ProjectsModuleSpecifics.cs index d3b4749aa5..afd364f37b 100644 --- a/common/ASC.Data.Backup.Core/Tasks/Modules/ProjectsModuleSpecifics.cs +++ b/common/ASC.Data.Backup.Core/Tasks/Modules/ProjectsModuleSpecifics.cs @@ -193,7 +193,7 @@ namespace ASC.Data.Backup.Tasks.Modules match => { var mappedId = Convert.ToString(columnMapper.GetMapping("projects_tasks", "id", match.Value.TrimEnd(','))); - return !string.IsNullOrEmpty(mappedId) && match.Value.EndsWith(",") ? mappedId + "," : mappedId; + return !string.IsNullOrEmpty(mappedId) && match.Value.EndsWith(',') ? mappedId + "," : mappedId; }, RegexOptions.Compiled); @@ -203,7 +203,7 @@ namespace ASC.Data.Backup.Tasks.Modules match => { var mappedId = Convert.ToString(columnMapper.GetMapping("projects_milestones", "id", match.Value.TrimEnd(','))); - return !string.IsNullOrEmpty(mappedId) && match.Value.EndsWith(",") ? mappedId + "," : mappedId; + return !string.IsNullOrEmpty(mappedId) && match.Value.EndsWith(',') ? mappedId + "," : mappedId; }, RegexOptions.Compiled); diff --git a/common/ASC.Data.Backup.Core/Tasks/PortalTaskBase.cs b/common/ASC.Data.Backup.Core/Tasks/PortalTaskBase.cs index 079bcdba69..41c67c5511 100644 --- a/common/ASC.Data.Backup.Core/Tasks/PortalTaskBase.cs +++ b/common/ASC.Data.Backup.Core/Tasks/PortalTaskBase.cs @@ -167,7 +167,7 @@ namespace ASC.Data.Backup.Tasks { if (value <= 0) { - throw new ArgumentOutOfRangeException("value"); + throw new ArgumentOutOfRangeException(nameof(value)); } stepsCount = value; Logger.Debug("Steps: " + stepsCount); @@ -191,7 +191,7 @@ namespace ASC.Data.Backup.Tasks { if (value < 0 || value > 100) { - throw new ArgumentOutOfRangeException("value"); + throw new ArgumentOutOfRangeException(nameof(value)); } if (value == 100) { @@ -207,7 +207,7 @@ namespace ASC.Data.Backup.Tasks { if (value < 0 || value > 100) { - throw new ArgumentOutOfRangeException("value"); + throw new ArgumentOutOfRangeException(nameof(value)); } if (Progress != value) { @@ -231,7 +231,7 @@ namespace ASC.Data.Backup.Tasks foreach (var p in parsed) { - if (string.IsNullOrEmpty(p.Trim())) continue; + if (string.IsNullOrWhiteSpace(p)) continue; var keyValue = p.Split('='); result.Add(keyValue[0].ToLowerInvariant(), keyValue[1]); } @@ -243,16 +243,16 @@ namespace ASC.Data.Backup.Tasks { var connectionString = ParseConnectionString(DbFactory.ConnectionStringSettings.ConnectionString); var args = new StringBuilder() - .AppendFormat("-h {0} ", connectionString["server"]) - .AppendFormat("-u {0} ", connectionString["user id"]) - .AppendFormat("-p{0} ", connectionString["password"]); + .Append($"-h {connectionString["server"]} ") + .Append($"-u {connectionString["user id"]} ") + .Append($"-p{connectionString["password"]} "); if (db) { - args.AppendFormat("-D {0} ", connectionString["database"]); + args.Append($"-D {connectionString["database"]} "); } - args.AppendFormat("-e \" source {0}\"", file); + args.Append($"-e \" source {file}\""); Logger.DebugFormat("run mysql file {0} {1}", file, args.ToString()); var startInfo = new ProcessStartInfo @@ -280,16 +280,21 @@ namespace ASC.Data.Backup.Tasks Logger.DebugFormat("complete mysql file {0}", file); } - protected async Task RunMysqlFile(Stream stream, string delimiter = ";") + protected Task RunMysqlFile(Stream stream, string delimiter = ";") { + if (stream == null) return Task.CompletedTask; - if (stream == null) return; + return InternalRunMysqlFile(stream, delimiter); + } + private async Task InternalRunMysqlFile(Stream stream, string delimiter) + { using var reader = new StreamReader(stream, Encoding.UTF8); string commandText; while ((commandText = await reader.ReadLineAsync()) != null) { + var sb = new StringBuilder(commandText); while (!commandText.EndsWith(delimiter)) { var newline = await reader.ReadLineAsync(); @@ -297,9 +302,9 @@ namespace ASC.Data.Backup.Tasks { break; } - commandText += newline; + sb.Append(newline); } - + commandText = sb.ToString(); try { diff --git a/common/ASC.Data.Backup.Core/Tasks/RestoreDbModuleTask.cs b/common/ASC.Data.Backup.Core/Tasks/RestoreDbModuleTask.cs index 419689d3cf..22ff841453 100644 --- a/common/ASC.Data.Backup.Core/Tasks/RestoreDbModuleTask.cs +++ b/common/ASC.Data.Backup.Core/Tasks/RestoreDbModuleTask.cs @@ -54,9 +54,9 @@ namespace ASC.Data.Backup.Tasks public RestoreDbModuleTask(IOptionsMonitor options, IModuleSpecifics module, IDataReadOperator reader, ColumnMapper columnMapper, DbFactory factory, bool replaceDate, bool dump, StorageFactory storageFactory, StorageFactoryConfig storageFactoryConfig, ModuleProvider moduleProvider) : base(factory, options, storageFactory, storageFactoryConfig, moduleProvider) { - Reader = reader ?? throw new ArgumentNullException("reader"); - ColumnMapper = columnMapper ?? throw new ArgumentNullException("columnMapper"); - DbFactory = factory ?? throw new ArgumentNullException("factory"); + Reader = reader ?? throw new ArgumentNullException(nameof(reader)); + ColumnMapper = columnMapper ?? throw new ArgumentNullException(nameof(columnMapper)); + DbFactory = factory ?? throw new ArgumentNullException(nameof(factory)); Module = module; ReplaceDate = replaceDate; Dump = dump; @@ -139,7 +139,7 @@ namespace ASC.Data.Backup.Tasks else if (tableInfo.IdType == IdType.Integer) { var command = connection.CreateCommand(); - command.CommandText = string.Format("select max({0}) from {1};", tableInfo.IdColumn, tableInfo.Name); + command.CommandText = $"select max({tableInfo.IdColumn}) from {tableInfo.Name};"; newIdValue = (int)command.WithTimeout(120).ExecuteScalar() + 1; } } diff --git a/common/ASC.Data.Backup.Core/Tasks/RestorePortalTask.cs b/common/ASC.Data.Backup.Core/Tasks/RestorePortalTask.cs index 95ad6c19c3..ffcafd2855 100644 --- a/common/ASC.Data.Backup.Core/Tasks/RestorePortalTask.cs +++ b/common/ASC.Data.Backup.Core/Tasks/RestorePortalTask.cs @@ -84,7 +84,7 @@ namespace ASC.Data.Backup.Tasks public void Init(string toConfigPath, string fromFilePath, int tenantId = -1, ColumnMapper columnMapper = null, string upgradesPath = null) { if (fromFilePath == null) - throw new ArgumentNullException("fromFilePath"); + throw new ArgumentNullException(nameof(fromFilePath)); if (!File.Exists(fromFilePath)) throw new FileNotFoundException("file not found at given path"); @@ -368,19 +368,21 @@ namespace ASC.Data.Backup.Tasks private void SetTenantActive(int tenantId) { - using var connection = DbFactory.OpenConnection(); - var commandText = string.Format( - "update tenants_tenants " + - "set " + - " status={0}, " + - " last_modified='{1}', " + - " statuschanged='{1}' " + - "where id = '{2}'", - (int)TenantStatus.Active, - DateTime.UtcNow.ToString("yyyy-MM-dd HH:mm:ss"), - tenantId); + using var connection = DbFactory.OpenConnection(); + var commandText = string.Format( + "update tenants_tenants " + + "set " + + " status={0}, " + + " last_modified='{1}', " + + " statuschanged='{1}' " + + "where id = '{2}'", + (int)TenantStatus.Active, + DateTime.UtcNow.ToString("yyyy-MM-dd HH:mm:ss"), + tenantId); - connection.CreateCommand().WithTimeout(120).ExecuteNonQuery(); + var command = connection.CreateCommand().WithTimeout(120); + command.CommandText = commandText; + command.ExecuteNonQuery(); } } } diff --git a/common/ASC.Data.Backup.Core/Tasks/TransferPortalTask.cs b/common/ASC.Data.Backup.Core/Tasks/TransferPortalTask.cs index bb1b900760..632af50158 100644 --- a/common/ASC.Data.Backup.Core/Tasks/TransferPortalTask.cs +++ b/common/ASC.Data.Backup.Core/Tasks/TransferPortalTask.cs @@ -83,7 +83,7 @@ namespace ASC.Data.Backup.Tasks public void Init(int tenantId, string fromConfigPath, string toConfigPath, int limit, string backupDirectory) { Limit = limit; - ToConfigPath = toConfigPath ?? throw new ArgumentNullException("toConfigPath"); + ToConfigPath = toConfigPath ?? throw new ArgumentNullException(nameof(toConfigPath)); Init(tenantId, fromConfigPath); BackupDirectory = backupDirectory; @@ -221,21 +221,16 @@ namespace ASC.Data.Backup.Tasks newAlias = GetUniqAlias(connection, newAlias); } - var commandText = string.Format( - "update tenants_tenants " + + var commandText = "update tenants_tenants " + "set " + - " status={0}, " + - " alias = '{1}', " + - " last_modified='{2}', " + - " statuschanged='{2}' " + - "where alias = '{3}'", - status.ToString("d"), - newAlias, - DateTime.UtcNow.ToString("yyyy-MM-dd HH:mm:ss"), - alias); + $" status={status.ToString("d")}, " + + $" alias = '{newAlias}', " + + $" last_modified='{DateTime.UtcNow.ToString("yyyy-MM-dd HH:mm:ss")}', " + + $" statuschanged='{DateTime.UtcNow.ToString("yyyy-MM-dd HH:mm:ss")}' " + + $"where alias = '{alias}'"; if (!string.IsNullOrEmpty(whereCondition)) - commandText += (" and " + whereCondition); + commandText += " and " + whereCondition; var command = connection.CreateCommand(); command.CommandText = commandText; command.WithTimeout(120).ExecuteNonQuery(); diff --git a/common/ASC.Data.Encryption/Crypt.cs b/common/ASC.Data.Encryption/Crypt.cs index d899667783..254888eb06 100644 --- a/common/ASC.Data.Encryption/Crypt.cs +++ b/common/ASC.Data.Encryption/Crypt.cs @@ -295,12 +295,12 @@ namespace ASC.Data.Encryption { var dir = string.IsNullOrEmpty(TempDir) ? Path.GetDirectoryName(filePath) : TempDir; var name = Path.GetFileNameWithoutExtension(filePath); - var result = CrossPlatform.PathCombine(dir, string.Format("{0}_{1}{2}", Storage, name, ext)); + var result = CrossPlatform.PathCombine(dir, $"{Storage}_{name}{ext}"); var index = 1; while (File.Exists(result)) { - result = CrossPlatform.PathCombine(dir, string.Format("{0}_{1}({2}){3}", Storage, name, index++, ext)); + result = CrossPlatform.PathCombine(dir, $"{Storage}_{name}({index++}){ext}"); } return result; diff --git a/common/ASC.Data.Encryption/Metadata.cs b/common/ASC.Data.Encryption/Metadata.cs index 5dfc16e51e..73cc75ac7a 100644 --- a/common/ASC.Data.Encryption/Metadata.cs +++ b/common/ASC.Data.Encryption/Metadata.cs @@ -242,16 +242,14 @@ namespace ASC.Data.Encryption private byte[] GenerateRandom(int length) { - var random = new byte[length]; - - random = RandomNumberGenerator.GetBytes(length); + var random = RandomNumberGenerator.GetBytes(length); return random; } private byte[] GenerateKey() { - var key = new byte[keyLength]; + byte[] key; using (var deriveBytes = new Rfc2898DeriveBytes(Password, Salt, Iterations, HashAlgorithmName.SHA256)) { @@ -263,7 +261,7 @@ namespace ASC.Data.Encryption private byte[] GenerateHmacKey() { - var hmacKey = new byte[hmacKeyLength]; + byte[] hmacKey; using (var sha512 = SHA512.Create()) { @@ -274,8 +272,8 @@ namespace ASC.Data.Encryption } private byte[] ComputeHmacHash(Stream stream) - { - var hmacHash = new byte[hmacHashLength]; + { + byte[] hmacHash; stream.Seek(metadataLength - ivLength, SeekOrigin.Begin); // Move position to (IV + encrypted data) diff --git a/common/ASC.Data.Reassigns/QueueWorker.cs b/common/ASC.Data.Reassigns/QueueWorker.cs index 4a17d0e1ee..638510b2eb 100644 --- a/common/ASC.Data.Reassigns/QueueWorker.cs +++ b/common/ASC.Data.Reassigns/QueueWorker.cs @@ -37,7 +37,7 @@ using Microsoft.Extensions.Primitives; namespace ASC.Data.Reassigns { - public class QueueWorker + public static class QueueWorker { public static IDictionary GetHttpHeaders(HttpRequest httpRequest) { @@ -52,7 +52,7 @@ namespace ASC.Data.Reassigns protected IHttpContextAccessor HttpContextAccessor { get; } protected IServiceProvider ServiceProvider { get; } - public object SynchRoot = new object(); + private readonly object _synchRoot = new object(); public QueueWorker( IHttpContextAccessor httpContextAccessor, @@ -87,7 +87,7 @@ namespace ASC.Data.Reassigns protected DistributedTaskProgress Start(int tenantId, Guid userId, Func constructor) { - lock (SynchRoot) + lock (_synchRoot) { var task = GetProgressItemStatus(tenantId, userId); diff --git a/common/ASC.Data.Reassigns/ReassignProgressItem.cs b/common/ASC.Data.Reassigns/ReassignProgressItem.cs index 6a40b23afc..ccd69d8665 100644 --- a/common/ASC.Data.Reassigns/ReassignProgressItem.cs +++ b/common/ASC.Data.Reassigns/ReassignProgressItem.cs @@ -102,7 +102,7 @@ namespace ASC.Data.Reassigns var scopeClass = scope.ServiceProvider.GetService(); var (tenantManager, coreBaseSettings, messageService, studioNotifyService, securityContext, userManager, userPhotoManager, displayUserSettingsHelper, messageTarget, options) = scopeClass; var logger = options.Get("ASC.Web"); - var tenant = tenantManager.SetCurrentTenant(_tenantId); + tenantManager.SetCurrentTenant(_tenantId); try { @@ -273,7 +273,7 @@ namespace ASC.Data.Reassigns } } - public class ReassignProgressItemExtension + public static class ReassignProgressItemExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.Data.Reassigns/RemoveProgressItem.cs b/common/ASC.Data.Reassigns/RemoveProgressItem.cs index 1bb12dafdf..f71393935e 100644 --- a/common/ASC.Data.Reassigns/RemoveProgressItem.cs +++ b/common/ASC.Data.Reassigns/RemoveProgressItem.cs @@ -97,8 +97,8 @@ namespace ASC.Data.Reassigns using var scope = ServiceProvider.CreateScope(); var scopeClass = scope.ServiceProvider.GetService(); var (tenantManager, coreBaseSettings, messageService, studioNotifyService, securityContext, userManager, messageTarget, webItemManagerSecurity, storageFactory, userFormatter, options) = scopeClass; - var logger = options.Get("ASC.Web"); - var tenant = tenantManager.SetCurrentTenant(_tenantId); + var logger = options.Get("ASC.Web"); + tenantManager.SetCurrentTenant(_tenantId); var userName = userFormatter.GetUserName(User, DisplayUserNameFormat.Default); try diff --git a/common/ASC.Data.Storage/BaseStorage.cs b/common/ASC.Data.Storage/BaseStorage.cs index 15049ae5d8..b25f4fac77 100644 --- a/common/ASC.Data.Storage/BaseStorage.cs +++ b/common/ASC.Data.Storage/BaseStorage.cs @@ -29,6 +29,7 @@ using System.Collections.Generic; using System.Globalization; using System.IO; using System.Linq; +using System.Net.Http; using System.Threading.Tasks; using System.Web; @@ -53,14 +54,16 @@ namespace ASC.Data.Storage protected EmailValidationKeyProvider EmailValidationKeyProvider { get; } protected IHttpContextAccessor HttpContextAccessor { get; } protected IOptionsMonitor Options { get; } - - public BaseStorage( + protected IHttpClientFactory ClientFactory { get; } + + protected BaseStorage( TempStream tempStream, TenantManager tenantManager, PathUtils pathUtils, EmailValidationKeyProvider emailValidationKeyProvider, IHttpContextAccessor httpContextAccessor, - IOptionsMonitor options) + IOptionsMonitor options, + IHttpClientFactory clientFactory) { TempStream = tempStream; @@ -70,6 +73,7 @@ namespace ASC.Data.Storage Options = options; Log = options.CurrentValue; HttpContextAccessor = httpContextAccessor; + ClientFactory = clientFactory; } #region IDataStore Members @@ -100,7 +104,7 @@ namespace ASC.Data.Storage { if (path == null) { - throw new ArgumentNullException("path"); + throw new ArgumentNullException(nameof(path)); } if (string.IsNullOrEmpty(_tenant) && IsSupportInternalUri) @@ -136,20 +140,12 @@ namespace ASC.Data.Storage } var auth = EmailValidationKeyProvider.GetEmailKey(currentTenantId, path.Replace('/', Path.DirectorySeparatorChar).Replace('\\', Path.DirectorySeparatorChar) + "." + headerAttr + "." + expireString); - query = string.Format("{0}{1}={2}&{3}={4}", - path.Contains("?") ? "&" : "?", - Constants.QUERY_EXPIRE, - expireString, - Constants.QUERY_AUTH, - auth); + query = $"{(path.IndexOf('?') >= 0 ? "&" : "?")}{Constants.QUERY_EXPIRE}={expireString}&{Constants.QUERY_AUTH}={auth}"; } if (!string.IsNullOrEmpty(headerAttr)) { - query += string.Format("{0}{1}={2}", - query.Contains("?") ? "&" : "?", - Constants.QUERY_HEADER, - HttpUtility.UrlEncode(headerAttr)); + query += $"{(query.IndexOf('?') >= 0 ? "&" : "?")}{Constants.QUERY_HEADER}={HttpUtility.UrlEncode(headerAttr)}"; } var tenant = _tenant.Trim('/'); diff --git a/common/ASC.Data.Storage/ChunkedUploader/CommonChunkedUploadSession.cs b/common/ASC.Data.Storage/ChunkedUploader/CommonChunkedUploadSession.cs index fd00bd4e16..ef76304537 100644 --- a/common/ASC.Data.Storage/ChunkedUploader/CommonChunkedUploadSession.cs +++ b/common/ASC.Data.Storage/ChunkedUploader/CommonChunkedUploadSession.cs @@ -111,7 +111,7 @@ namespace ASC.Core.ChunkedUploader { if (item.Value != null) { - if (item.Value.GetType() == typeof(JsonElement)) + if (item.Value is JsonElement) { var value = (JsonElement)item.Value; if (value.ValueKind == JsonValueKind.String) diff --git a/common/ASC.Data.Storage/Configuration/StorageSettings.cs b/common/ASC.Data.Storage/Configuration/StorageSettings.cs index c533a93760..5a1992cfc4 100644 --- a/common/ASC.Data.Storage/Configuration/StorageSettings.cs +++ b/common/ASC.Data.Storage/Configuration/StorageSettings.cs @@ -174,7 +174,6 @@ namespace ASC.Data.Storage.Configuration public bool Save(BaseStorageSettings baseStorageSettings) where T : class, ISettings, new() { ClearDataStoreCache(); - dataStoreConsumer = null; return SettingsManager.Save(baseStorageSettings); } @@ -195,16 +194,15 @@ namespace ASC.Data.Storage.Configuration Save(baseStorageSettings); } - private DataStoreConsumer dataStoreConsumer; public DataStoreConsumer DataStoreConsumer(BaseStorageSettings baseStorageSettings) where T : class, ISettings, new() { - if (string.IsNullOrEmpty(baseStorageSettings.Module) || baseStorageSettings.Props == null) return dataStoreConsumer = new DataStoreConsumer(); + if (string.IsNullOrEmpty(baseStorageSettings.Module) || baseStorageSettings.Props == null) return new DataStoreConsumer(); var consumer = ConsumerFactory.GetByKey(baseStorageSettings.Module); - if (!consumer.IsSet) return dataStoreConsumer = new DataStoreConsumer(); + if (!consumer.IsSet) return new DataStoreConsumer(); - dataStoreConsumer = (DataStoreConsumer)consumer.Clone(); + var dataStoreConsumer = (DataStoreConsumer)consumer.Clone(); foreach (var prop in baseStorageSettings.Props) { @@ -249,7 +247,7 @@ namespace ASC.Data.Storage.Configuration } } - public class StorageSettingsExtension + public static class StorageSettingsExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.Data.Storage/Constants.cs b/common/ASC.Data.Storage/Constants.cs index 6ec20d9cbd..a0acdb0997 100644 --- a/common/ASC.Data.Storage/Constants.cs +++ b/common/ASC.Data.Storage/Constants.cs @@ -26,7 +26,7 @@ namespace ASC.Data.Storage { - class Constants + static class Constants { public const string CONFIG_DIR = "CONFIG_DIR"; public const string STORAGE_ROOT_PARAM = "$STORAGE_ROOT"; diff --git a/common/ASC.Data.Storage/CrossModuleTransferUtility.cs b/common/ASC.Data.Storage/CrossModuleTransferUtility.cs index e8499f95c0..3bc35eb1de 100644 --- a/common/ASC.Data.Storage/CrossModuleTransferUtility.cs +++ b/common/ASC.Data.Storage/CrossModuleTransferUtility.cs @@ -57,18 +57,18 @@ namespace ASC.Data.Storage Option = option; TempStream = tempStream; TempPath = tempPath; - this.source = source ?? throw new ArgumentNullException("source"); - this.destination = destination ?? throw new ArgumentNullException("destination"); + this.source = source ?? throw new ArgumentNullException(nameof(source)); + this.destination = destination ?? throw new ArgumentNullException(nameof(destination)); maxChunkUploadSize = 10 * 1024 * 1024; chunksize = 5 * 1024 * 1024; } public void CopyFile(string srcDomain, string srcPath, string destDomain, string destPath) { - if (srcDomain == null) throw new ArgumentNullException("srcDomain"); - if (srcPath == null) throw new ArgumentNullException("srcPath"); - if (destDomain == null) throw new ArgumentNullException("destDomain"); - if (destPath == null) throw new ArgumentNullException("destPath"); + if (srcDomain == null) throw new ArgumentNullException(nameof(srcDomain)); + if (srcPath == null) throw new ArgumentNullException(nameof(srcPath)); + if (destDomain == null) throw new ArgumentNullException(nameof(destDomain)); + if (destPath == null) throw new ArgumentNullException(nameof(destPath)); using var stream = source.GetReadStream(srcDomain, srcPath); if (stream.Length < maxChunkUploadSize) @@ -90,7 +90,6 @@ namespace ASC.Data.Storage memstream.Seek(0, SeekOrigin.Begin); holder.UploadChunk(session, memstream, chunksize); memstream.Dispose(); - memstream = null; } } finally diff --git a/common/ASC.Data.Storage/DiscStorage/DiscDataStore.cs b/common/ASC.Data.Storage/DiscStorage/DiscDataStore.cs index 249551c695..1fe967da00 100644 --- a/common/ASC.Data.Storage/DiscStorage/DiscDataStore.cs +++ b/common/ASC.Data.Storage/DiscStorage/DiscDataStore.cs @@ -28,6 +28,7 @@ using System; using System.Collections.Generic; using System.IO; using System.Linq; +using System.Net.Http; using System.Threading.Tasks; using ASC.Common; @@ -85,8 +86,9 @@ namespace ASC.Data.Storage.DiscStorage IHttpContextAccessor httpContextAccessor, IOptionsMonitor options, EncryptionSettingsHelper encryptionSettingsHelper, - EncryptionFactory encryptionFactory) - : base(tempStream, tenantManager, pathUtils, emailValidationKeyProvider, httpContextAccessor, options) + EncryptionFactory encryptionFactory, + IHttpClientFactory clientFactory) + : base(tempStream, tenantManager, pathUtils, emailValidationKeyProvider, httpContextAccessor, options, clientFactory) { EncryptionSettingsHelper = encryptionSettingsHelper; EncryptionFactory = encryptionFactory; @@ -96,7 +98,7 @@ namespace ASC.Data.Storage.DiscStorage { if (path == null) { - throw new ArgumentNullException("path"); + throw new ArgumentNullException(nameof(path)); } var pathMap = GetPath(domain); @@ -116,7 +118,7 @@ namespace ASC.Data.Storage.DiscStorage public Stream GetReadStream(string domain, string path, bool withDecription) { - if (path == null) throw new ArgumentNullException("path"); + if (path == null) throw new ArgumentNullException(nameof(path)); var target = GetTarget(domain, path); if (File.Exists(target)) @@ -133,7 +135,7 @@ namespace ASC.Data.Storage.DiscStorage public override Stream GetReadStream(string domain, string path, int offset) { - if (path == null) throw new ArgumentNullException("path"); + if (path == null) throw new ArgumentNullException(nameof(path)); var target = GetTarget(domain, path); if (File.Exists(target)) @@ -170,8 +172,8 @@ namespace ASC.Data.Storage.DiscStorage QuotaController.QuotaUsedCheck(buffered.Length); } - if (path == null) throw new ArgumentNullException("path"); - if (buffered == null) throw new ArgumentNullException("stream"); + if (path == null) throw new ArgumentNullException(nameof(path)); + if (buffered == null) throw new ArgumentNullException(nameof(stream)); //Try seek to start if (buffered.CanSeek) @@ -275,7 +277,7 @@ namespace ASC.Data.Storage.DiscStorage public override void Delete(string domain, string path) { - if (path == null) throw new ArgumentNullException("path"); + if (path == null) throw new ArgumentNullException(nameof(path)); var target = GetTarget(domain, path); if (File.Exists(target)) @@ -293,7 +295,7 @@ namespace ASC.Data.Storage.DiscStorage public override void DeleteFiles(string domain, List paths) { - if (paths == null) throw new ArgumentNullException("paths"); + if (paths == null) throw new ArgumentNullException(nameof(paths)); foreach (var path in paths) { @@ -311,7 +313,7 @@ namespace ASC.Data.Storage.DiscStorage public override void DeleteFiles(string domain, string folderPath, string pattern, bool recursive) { - if (folderPath == null) throw new ArgumentNullException("folderPath"); + if (folderPath == null) throw new ArgumentNullException(nameof(folderPath)); //Return dirs var targetDir = GetTarget(domain, folderPath); @@ -327,13 +329,13 @@ namespace ASC.Data.Storage.DiscStorage } else { - throw new DirectoryNotFoundException(string.Format("Directory '{0}' not found", targetDir)); + throw new DirectoryNotFoundException($"Directory '{targetDir}' not found"); } } public override void DeleteFiles(string domain, string folderPath, DateTime fromDate, DateTime toDate) { - if (folderPath == null) throw new ArgumentNullException("folderPath"); + if (folderPath == null) throw new ArgumentNullException(nameof(folderPath)); //Return dirs var targetDir = GetTarget(domain, folderPath); @@ -353,7 +355,7 @@ namespace ASC.Data.Storage.DiscStorage } else { - throw new DirectoryNotFoundException(string.Format("Directory '{0}' not found", targetDir)); + throw new DirectoryNotFoundException($"Directory '{targetDir}' not found"); } } @@ -372,8 +374,8 @@ namespace ASC.Data.Storage.DiscStorage public override Uri Move(string srcdomain, string srcpath, string newdomain, string newpath, bool quotaCheckFileSize = true) { - if (srcpath == null) throw new ArgumentNullException("srcpath"); - if (newpath == null) throw new ArgumentNullException("srcpath"); + if (srcpath == null) throw new ArgumentNullException(nameof(srcpath)); + if (newpath == null) throw new ArgumentNullException(nameof(srcpath)); var target = GetTarget(srcdomain, srcpath); var newtarget = GetTarget(newdomain, newpath); @@ -405,7 +407,7 @@ namespace ASC.Data.Storage.DiscStorage public override bool IsDirectory(string domain, string path) { - if (path == null) throw new ArgumentNullException("path"); + if (path == null) throw new ArgumentNullException(nameof(path)); //Return dirs var targetDir = GetTarget(domain, path); @@ -418,14 +420,14 @@ namespace ASC.Data.Storage.DiscStorage public override void DeleteDirectory(string domain, string path) { - if (path == null) throw new ArgumentNullException("path"); + if (path == null) throw new ArgumentNullException(nameof(path)); //Return dirs var targetDir = GetTarget(domain, path); if (string.IsNullOrEmpty(targetDir)) throw new Exception("targetDir is null"); - if (!string.IsNullOrEmpty(targetDir) && !targetDir.EndsWith(Path.DirectorySeparatorChar.ToString())) + if (!targetDir.EndsWith(Path.DirectorySeparatorChar.ToString())) { targetDir += Path.DirectorySeparatorChar; } @@ -483,7 +485,7 @@ namespace ASC.Data.Storage.DiscStorage public override void DeleteExpired(string domain, string folderPath, TimeSpan oldThreshold) { - if (folderPath == null) throw new ArgumentNullException("folderPath"); + if (folderPath == null) throw new ArgumentNullException(nameof(folderPath)); //Return dirs var targetDir = GetTarget(domain, folderPath); @@ -529,7 +531,7 @@ namespace ASC.Data.Storage.DiscStorage public override string[] ListDirectoriesRelative(string domain, string path, bool recursive) { - if (path == null) throw new ArgumentNullException("path"); + if (path == null) throw new ArgumentNullException(nameof(path)); //Return dirs var targetDir = GetTarget(domain, path); @@ -541,12 +543,12 @@ namespace ASC.Data.Storage.DiscStorage entries, x => x.Substring(targetDir.Length)); } - return new string[0]; + return Array.Empty(); } public override string[] ListFilesRelative(string domain, string path, string pattern, bool recursive) { - if (path == null) throw new ArgumentNullException("path"); + if (path == null) throw new ArgumentNullException(nameof(path)); //Return dirs var targetDir = GetTarget(domain, path); @@ -558,12 +560,12 @@ namespace ASC.Data.Storage.DiscStorage entries, x => x.Substring(targetDir.Length)); } - return new string[0]; + return Array.Empty(); } public override bool IsFile(string domain, string path) { - if (path == null) throw new ArgumentNullException("path"); + if (path == null) throw new ArgumentNullException(nameof(path)); //Return dirs var target = GetTarget(domain, path); @@ -600,8 +602,8 @@ namespace ASC.Data.Storage.DiscStorage public override Uri Copy(string srcdomain, string srcpath, string newdomain, string newpath) { - if (srcpath == null) throw new ArgumentNullException("srcpath"); - if (newpath == null) throw new ArgumentNullException("srcpath"); + if (srcpath == null) throw new ArgumentNullException(nameof(srcpath)); + if (newpath == null) throw new ArgumentNullException(nameof(srcpath)); var target = GetTarget(srcdomain, srcpath); var newtarget = GetTarget(newdomain, newpath); @@ -664,9 +666,9 @@ namespace ASC.Data.Storage.DiscStorage private MappedPath GetPath(string domain) { if (domain != null) - if (_mappedPaths.ContainsKey(domain)) + if (_mappedPaths.TryGetValue(domain, out var value)) { - return _mappedPaths[domain]; + return value; } return _mappedPaths[string.Empty].AppendDomain(domain); } @@ -678,7 +680,7 @@ namespace ASC.Data.Storage.DiscStorage public Stream GetWriteStream(string domain, string path, FileMode fileMode) { - if (path == null) throw new ArgumentNullException("path"); + if (path == null) throw new ArgumentNullException(nameof(path)); var target = GetTarget(domain, path); CreateDirectory(target); return File.Open(target, fileMode); @@ -714,7 +716,7 @@ namespace ASC.Data.Storage.DiscStorage public void Encrypt(string domain, string path) { - if (path == null) throw new ArgumentNullException("path"); + if (path == null) throw new ArgumentNullException(nameof(path)); var target = GetTarget(domain, path); @@ -730,7 +732,7 @@ namespace ASC.Data.Storage.DiscStorage public void Decrypt(string domain, string path) { - if (path == null) throw new ArgumentNullException("path"); + if (path == null) throw new ArgumentNullException(nameof(path)); var target = GetTarget(domain, path); diff --git a/common/ASC.Data.Storage/Encryption/EncryptionOperation.cs b/common/ASC.Data.Storage/Encryption/EncryptionOperation.cs index 1da1837d52..c933dc371f 100644 --- a/common/ASC.Data.Storage/Encryption/EncryptionOperation.cs +++ b/common/ASC.Data.Storage/Encryption/EncryptionOperation.cs @@ -147,7 +147,7 @@ namespace ASC.Data.Storage.Encryption foreach (var domain in domains) { - var logParent = string.Format("Tenant: {0}, Module: {1}, Domain: {2}", tenant.TenantAlias, module, domain); + var logParent = $"Tenant: {tenant.TenantAlias}, Module: {module}, Domain: {domain}"; var files = GetFiles(domains, progress, store, domain); @@ -191,7 +191,7 @@ namespace ASC.Data.Storage.Encryption { IEnumerable files = targetStore.ListFilesRelative(targetDomain, "\\", "*.*", true); - if (progress.Any()) + if (progress.Count > 0) { files = files.Where(path => !progress.Contains(path)); } @@ -217,7 +217,7 @@ namespace ASC.Data.Storage.Encryption { foreach (var file in files) { - var logItem = string.Format("{0}, File: {1}", logParent, file); + var logItem = $"{logParent}, File: {file}"; log.Debug(logItem); @@ -378,7 +378,7 @@ namespace ASC.Data.Storage.Encryption } } - public class EncryptionOperationExtension + public static class EncryptionOperationExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.Data.Storage/Encryption/EncryptionWorker.cs b/common/ASC.Data.Storage/Encryption/EncryptionWorker.cs index 3c7c079591..618cd178f3 100644 --- a/common/ASC.Data.Storage/Encryption/EncryptionWorker.cs +++ b/common/ASC.Data.Storage/Encryption/EncryptionWorker.cs @@ -95,7 +95,7 @@ namespace ASC.Data.Storage.Encryption } } - public class FactoryOperationExtension + public static class FactoryOperationExtension { public static void Register(DIHelper dIHelper) { diff --git a/common/ASC.Data.Storage/Extensions.cs b/common/ASC.Data.Storage/Extensions.cs index f038f227a2..afc368009e 100644 --- a/common/ASC.Data.Storage/Extensions.cs +++ b/common/ASC.Data.Storage/Extensions.cs @@ -46,8 +46,8 @@ namespace ASC.Data.Storage public static void IronReadToStream(this IDataStore store, string domain, string path, int tryCount, Stream readTo) { - if (tryCount < 1) throw new ArgumentOutOfRangeException("tryCount", "Must be greater or equal 1."); - if (!readTo.CanWrite) throw new ArgumentException("stream cannot be written", "readTo"); + if (tryCount < 1) throw new ArgumentOutOfRangeException(nameof(tryCount), "Must be greater or equal 1."); + if (!readTo.CanWrite) throw new ArgumentException("stream cannot be written", nameof(readTo)); var tryCurrent = 0; var offset = 0; @@ -59,7 +59,7 @@ namespace ASC.Data.Storage tryCurrent++; using var stream = store.GetReadStream(domain, path, offset); var buffer = new byte[BufferSize]; - var readed = 0; + int readed; while ((readed = stream.Read(buffer, 0, BufferSize)) > 0) { readTo.Write(buffer, 0, readed); diff --git a/common/ASC.Data.Storage/GoogleCloud/GoogleCloudStorage.cs b/common/ASC.Data.Storage/GoogleCloud/GoogleCloudStorage.cs index 74d64519b6..1e50085105 100644 --- a/common/ASC.Data.Storage/GoogleCloud/GoogleCloudStorage.cs +++ b/common/ASC.Data.Storage/GoogleCloud/GoogleCloudStorage.cs @@ -32,6 +32,7 @@ using System.Globalization; using System.IO; using System.Linq; using System.Net.Http; +using System.Security.Cryptography; using System.Text; using System.Threading; using System.Threading.Tasks; @@ -77,7 +78,8 @@ namespace ASC.Data.Storage.GoogleCloud PathUtils pathUtils, EmailValidationKeyProvider emailValidationKeyProvider, IHttpContextAccessor httpContextAccessor, - IOptionsMonitor options) : base(tempStream, tenantManager, pathUtils, emailValidationKeyProvider, httpContextAccessor, options) + IOptionsMonitor options, + IHttpClientFactory clientFactory) : base(tempStream, tenantManager, pathUtils, emailValidationKeyProvider, httpContextAccessor, options, clientFactory) { } @@ -111,24 +113,21 @@ namespace ASC.Data.Storage.GoogleCloud _bucketRoot = props.ContainsKey("cname") && Uri.IsWellFormedUriString(props["cname"], UriKind.Absolute) ? new Uri(props["cname"], UriKind.Absolute) - : new Uri(string.Format("https://storage.googleapis.com/{0}/", _bucket), UriKind.Absolute); + : new Uri("https://storage.googleapis.com/" + _bucket + "/", UriKind.Absolute); _bucketSSlRoot = props.ContainsKey("cnamessl") && Uri.IsWellFormedUriString(props["cnamessl"], UriKind.Absolute) ? new Uri(props["cnamessl"], UriKind.Absolute) - : new Uri(string.Format("https://storage.googleapis.com/{0}/", _bucket), UriKind.Absolute); + : new Uri("https://storage.googleapis.com/" + _bucket + "/", UriKind.Absolute); - if (props.ContainsKey("lower")) + if (props.TryGetValue("lower", out var value)) { - bool.TryParse(props["lower"], out _lowerCasing); + bool.TryParse(value, out _lowerCasing); } _json = props["json"]; - if (props.ContainsKey("subdir")) - { - _subDir = props["subdir"]; - } + props.TryGetValue("subdir", out _subDir); return this; } @@ -151,14 +150,10 @@ namespace ASC.Data.Storage.GoogleCloud if (_subDir.Length == 1 && (_subDir[0] == '/' || _subDir[0] == '\\')) result = path; else - result = string.Format("{0}/{1}", _subDir, path); // Ignory all, if _subDir is not null + result = $"{_subDir}/{path}"; // Ignory all, if _subDir is not null } else//Key combined from module+domain+filename - result = string.Format("{0}/{1}/{2}/{3}", - _tenant, - _modulename, - domain, - path); + result = $"{_tenant}/{_modulename}/{domain}/{path}"; result = result.Replace("//", "/").TrimStart('/'); if (_lowerCasing) @@ -258,12 +253,10 @@ namespace ASC.Data.Storage.GoogleCloud protected override Uri SaveWithAutoAttachment(string domain, string path, System.IO.Stream stream, string attachmentFileName) { - var contentDisposition = string.Format("attachment; filename={0};", - HttpUtility.UrlPathEncode(attachmentFileName)); + var contentDisposition = $"attachment; filename={HttpUtility.UrlPathEncode(attachmentFileName)};"; if (attachmentFileName.Any(c => c >= 0 && c <= 127)) { - contentDisposition = string.Format("attachment; filename*=utf-8''{0};", - HttpUtility.UrlPathEncode(attachmentFileName)); + contentDisposition = $"attachment; filename*=utf-8''{HttpUtility.UrlPathEncode(attachmentFileName)};"; } return Save(domain, path, stream, null, contentDisposition); } @@ -352,9 +345,9 @@ namespace ASC.Data.Storage.GoogleCloud return PredefinedObjectAcl.Private; } - if (_domainsAcl.ContainsKey(domain)) + if (_domainsAcl.TryGetValue(domain, out var value)) { - return _domainsAcl[domain]; + return value; } return _moduleAcl; } @@ -394,7 +387,7 @@ namespace ASC.Data.Storage.GoogleCloud public override void DeleteFiles(string domain, List paths) { - if (!paths.Any()) return; + if (paths.Count == 0) return; var keysToDel = new List(); @@ -420,7 +413,7 @@ namespace ASC.Data.Storage.GoogleCloud } } - if (!keysToDel.Any()) return; + if (keysToDel.Count == 0) return; using var storage = GetStorage(); @@ -525,7 +518,7 @@ namespace ASC.Data.Storage.GoogleCloud var objects = storage.ListObjects(_bucket, MakePath(domain, path), null); - return objects.Count() > 0; + return objects.Any(); } public override async Task IsFileAsync(string domain, string path) @@ -534,7 +527,7 @@ namespace ASC.Data.Storage.GoogleCloud var objects = await storage.ListObjectsAsync(_bucket, MakePath(domain, path)).ReadPageAsync(1); - return objects.Count() > 0; + return objects.Any(); } public override bool IsDirectory(string domain, string path) @@ -633,9 +626,6 @@ namespace ASC.Data.Storage.GoogleCloud { using var storage = GetStorage(); - var srcKey = MakePath(srcdomain, srcpath); - var dstKey = MakePath(newdomain, newpath); - var size = GetFileSize(srcdomain, srcpath); var options = new CopyObjectOptions @@ -658,9 +648,6 @@ namespace ASC.Data.Storage.GoogleCloud using var storage = GetStorage(); - - var options = new ListObjectsOptions(); - var objects = storage.ListObjects(_bucket, srckey); foreach (var obj in objects) @@ -679,7 +666,6 @@ namespace ASC.Data.Storage.GoogleCloud { using var storage = GetStorage(); - var objectKey = MakePath(domain, path); var buffered = TempStream.GetBuffered(stream); var uploadObjectOptions = new UploadObjectOptions @@ -762,7 +748,7 @@ namespace ASC.Data.Storage.GoogleCloud if (chunkLength != defaultChunkSize) totalBytes = Convert.ToString((chunkNumber - 1) * defaultChunkSize + chunkLength); - var contentRangeHeader = string.Format("bytes {0}-{1}/{2}", bytesRangeStart, bytesRangeEnd, totalBytes); + var contentRangeHeader = $"bytes {bytesRangeStart}-{bytesRangeEnd}/{totalBytes}"; var request = new HttpRequestMessage(); request.RequestUri = new Uri(uploadUri); @@ -771,20 +757,17 @@ namespace ASC.Data.Storage.GoogleCloud request.Content = new StreamContent(stream); - long MAX_RETRIES = 100; + const int MAX_RETRIES = 100; int millisecondsTimeout; for (var i = 0; i < MAX_RETRIES; i++) { - var random = new Random(); - - millisecondsTimeout = Math.Min(Convert.ToInt32(Math.Pow(2, i)) + random.Next(0, 1000), 32 * 1000); + millisecondsTimeout = Math.Min(Convert.ToInt32(Math.Pow(2, i)) + RandomNumberGenerator.GetInt32(1000), 32 * 1000); try { - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); - var status = response.StatusCode; break; } diff --git a/common/ASC.Data.Storage/PathUtils.cs b/common/ASC.Data.Storage/PathUtils.cs index 6291a3e477..7b5683395f 100644 --- a/common/ASC.Data.Storage/PathUtils.cs +++ b/common/ASC.Data.Storage/PathUtils.cs @@ -70,9 +70,7 @@ namespace ASC.Data.Storage public string ResolveVirtualPath(string module, string domain) { - var url = string.Format("~/storage/{0}/{1}/", - module, - string.IsNullOrEmpty(domain) ? "root" : domain); + var url = $"~/storage/{module}/{(string.IsNullOrEmpty(domain) ? "root" : domain)}/"; return ResolveVirtualPath(url); } diff --git a/common/ASC.Data.Storage/ProgressStream.cs b/common/ASC.Data.Storage/ProgressStream.cs index 7d29302a6d..720d5bbc50 100644 --- a/common/ASC.Data.Storage/ProgressStream.cs +++ b/common/ASC.Data.Storage/ProgressStream.cs @@ -36,7 +36,7 @@ namespace ASC.Data.Storage public ProgressStream(Stream stream) { - this.stream = stream ?? throw new ArgumentNullException("stream"); + this.stream = stream ?? throw new ArgumentNullException(nameof(stream)); try { length = stream.Length; diff --git a/common/ASC.Data.Storage/RackspaceCloud/RackspaceCloudStorage.cs b/common/ASC.Data.Storage/RackspaceCloud/RackspaceCloudStorage.cs index 1a13e33710..9d9a026ccc 100644 --- a/common/ASC.Data.Storage/RackspaceCloud/RackspaceCloudStorage.cs +++ b/common/ASC.Data.Storage/RackspaceCloud/RackspaceCloudStorage.cs @@ -28,6 +28,7 @@ using System; using System.Collections.Generic; using System.IO; using System.Linq; +using System.Net.Http; using System.Threading.Tasks; using System.Web; @@ -72,8 +73,9 @@ namespace ASC.Data.Storage.RackspaceCloud PathUtils pathUtils, EmailValidationKeyProvider emailValidationKeyProvider, IHttpContextAccessor httpContextAccessor, - IOptionsMonitor options) - : base(tempStream, tenantManager, pathUtils, emailValidationKeyProvider, httpContextAccessor, options) + IOptionsMonitor options, + IHttpClientFactory httpClient) + : base(tempStream, tenantManager, pathUtils, emailValidationKeyProvider, httpContextAccessor, options, httpClient) { _logger = options.Get("ASC.Data.Storage.Rackspace.RackspaceCloudStorage"); TempPath = tempPath; @@ -90,14 +92,10 @@ namespace ASC.Data.Storage.RackspaceCloud if (_subDir.Length == 1 && (_subDir[0] == '/' || _subDir[0] == '\\')) result = path; else - result = string.Format("{0}/{1}", _subDir, path); // Ignory all, if _subDir is not null + result = $"{_subDir}/{path}"; // Ignory all, if _subDir is not null } else//Key combined from module+domain+filename - result = string.Format("{0}/{1}/{2}/{3}", - _tenant, - _modulename, - domain, - path); + result = $"{_tenant}/{_modulename}/{domain}/{path}"; result = result.Replace("//", "/").TrimStart('/'); if (_lowerCasing) @@ -127,7 +125,7 @@ namespace ASC.Data.Storage.RackspaceCloud { _modulename = moduleConfig.Name; _dataList = new DataList(moduleConfig); - _domains.AddRange(moduleConfig.Domain.Select(x => string.Format("{0}/", x.Name))); + _domains.AddRange(moduleConfig.Domain.Select(x => $"{x.Name}/")); _domainsExpires = moduleConfig.Domain.Where(x => x.Expires != TimeSpan.Zero).ToDictionary(x => x.Name, y => y.Expires); _domainsExpires.Add(string.Empty, moduleConfig.Expires); _domainsAcl = moduleConfig.Domain.ToDictionary(x => x.Name, y => y.Acl); @@ -148,15 +146,12 @@ namespace ASC.Data.Storage.RackspaceCloud _apiKey = props["apiKey"]; _username = props["username"]; - if (props.ContainsKey("lower")) + if (props.TryGetValue("lower", out var value)) { - bool.TryParse(props["lower"], out _lowerCasing); + bool.TryParse(value, out _lowerCasing); } - if (props.ContainsKey("subdir")) - { - _subDir = props["subdir"]; - } + props.TryGetValue("subdir", out _subDir); _public_container = props["public_container"]; @@ -195,13 +190,13 @@ namespace ASC.Data.Storage.RackspaceCloud var accounMetaData = client.GetAccountMetaData(_region); string secretKey; - if (accounMetaData.ContainsKey("Temp-Url-Key")) + if (accounMetaData.TryGetValue("Temp-Url-Key", out secretKey)) { - secretKey = accounMetaData["Temp-Url-Key"]; + } else { - secretKey = ASC.Common.Utils.RandomString.Generate(64); + secretKey = Common.Utils.RandomString.Generate(64); accounMetaData.Add("Temp-Url-Key", secretKey); client.UpdateAccountMetadata(accounMetaData, _region); } @@ -257,12 +252,10 @@ namespace ASC.Data.Storage.RackspaceCloud protected override Uri SaveWithAutoAttachment(string domain, string path, Stream stream, string attachmentFileName) { - var contentDisposition = string.Format("attachment; filename={0};", - HttpUtility.UrlPathEncode(attachmentFileName)); + var contentDisposition = $"attachment; filename={HttpUtility.UrlPathEncode(attachmentFileName)};"; if (attachmentFileName.Any(c => c >= 0 && c <= 127)) { - contentDisposition = string.Format("attachment; filename*=utf-8''{0};", - HttpUtility.UrlPathEncode(attachmentFileName)); + contentDisposition = $"attachment; filename*=utf-8''{HttpUtility.UrlPathEncode(attachmentFileName)};"; } return Save(domain, path, stream, null, contentDisposition); @@ -295,10 +288,6 @@ namespace ASC.Data.Storage.RackspaceCloud ? MimeMapping.GetMimeMapping(Path.GetFileName(path)) : contentType; - if (mime == "application/octet-stream") - { - contentDisposition = "attachment"; - } var customHeaders = new Dictionary(); @@ -337,7 +326,7 @@ namespace ASC.Data.Storage.RackspaceCloud var headers = new Dictionary { - { "X-Object-Manifest", string.Format("{0}/{1}", _private_container, MakePath(domain, path)) } + { "X-Object-Manifest", $"{_private_container}/{MakePath(domain, path)}" } }; // create symlink client.CreateObject(_public_container, @@ -384,9 +373,9 @@ namespace ASC.Data.Storage.RackspaceCloud return ACL.Auto; } - if (_domainsAcl.ContainsKey(domain)) + if (_domainsAcl.TryGetValue(domain, out var value)) { - return _domainsAcl[domain]; + return value; } return _moduleAcl; } @@ -411,8 +400,11 @@ namespace ASC.Data.Storage.RackspaceCloud .Where(x => Wildcard.IsMatch(pattern, Path.GetFileName(x.Name))); if (!files.Any()) return; - - files.ToList().ForEach(x => client.DeleteObject(_private_container, x.Name)); + + foreach(var file in files) + { + client.DeleteObject(_private_container, file.Name); + } if (QuotaController != null) { @@ -423,7 +415,7 @@ namespace ASC.Data.Storage.RackspaceCloud public override void DeleteFiles(string domain, List paths) { - if (!paths.Any()) return; + if (paths.Count == 0) return; var keysToDel = new List(); @@ -448,7 +440,7 @@ namespace ASC.Data.Storage.RackspaceCloud } } - if (!keysToDel.Any()) return; + if (keysToDel.Count == 0) return; var client = GetClient(); @@ -469,7 +461,10 @@ namespace ASC.Data.Storage.RackspaceCloud if (!files.Any()) return; - files.ToList().ForEach(x => client.DeleteObject(_private_container, x.Name)); + foreach(var file in files) + { + client.DeleteObject(_private_container, file.Name); + } if (QuotaController != null) { @@ -527,11 +522,9 @@ namespace ASC.Data.Storage.RackspaceCloud public override string[] ListFilesRelative(string domain, string path, string pattern, bool recursive) { - var paths = new List(); - var client = GetClient(); - paths = client.ListObjects(_private_container, null, null, null, MakePath(domain, path), _region).Select(x => x.Name).ToList(); + var paths = client.ListObjects(_private_container, null, null, null, MakePath(domain, path), _region).Select(x => x.Name); return paths .Where(x => Wildcard.IsMatch(pattern, Path.GetFileName(x))) @@ -543,7 +536,7 @@ namespace ASC.Data.Storage.RackspaceCloud var client = GetClient(); var objects = client.ListObjects(_private_container, null, null, null, MakePath(domain, path), _region); - return objects.Count() > 0; + return objects.Any(); } public override Task IsFileAsync(string domain, string path) @@ -566,7 +559,7 @@ namespace ASC.Data.Storage.RackspaceCloud foreach (var obj in objToDel) { client.DeleteObject(_private_container, obj.Name); - QuotaUsedDelete(domain, Convert.ToInt64(obj.Bytes)); + QuotaUsedDelete(domain, obj.Bytes); } } @@ -712,7 +705,7 @@ namespace ASC.Data.Storage.RackspaceCloud public override string UploadChunk(string domain, string path, string filePath, Stream stream, long defaultChunkSize, int chunkNumber, long chunkLength) { - var BufferSize = 4096; + const int BufferSize = 4096; var mode = chunkNumber == 0 ? FileMode.Create : FileMode.Append; diff --git a/common/ASC.Data.Storage/S3/S3Storage.cs b/common/ASC.Data.Storage/S3/S3Storage.cs index 13d8113eb2..abe306b95a 100644 --- a/common/ASC.Data.Storage/S3/S3Storage.cs +++ b/common/ASC.Data.Storage/S3/S3Storage.cs @@ -29,6 +29,7 @@ using System.Collections.Generic; using System.Globalization; using System.IO; using System.Linq; +using System.Net.Http; using System.Security.Cryptography; using System.Text; using System.Threading.Tasks; @@ -84,8 +85,9 @@ namespace ASC.Data.Storage.S3 PathUtils pathUtils, EmailValidationKeyProvider emailValidationKeyProvider, IHttpContextAccessor httpContextAccessor, - IOptionsMonitor options) - : base(tempStream, tenantManager, pathUtils, emailValidationKeyProvider, httpContextAccessor, options) + IOptionsMonitor options, + IHttpClientFactory clientFactory) + : base(tempStream, tenantManager, pathUtils, emailValidationKeyProvider, httpContextAccessor, options, clientFactory) { } @@ -96,9 +98,9 @@ namespace ASC.Data.Storage.S3 return S3CannedACL.Private; } - if (_domainsAcl.ContainsKey(domain)) + if (_domainsAcl.TryGetValue(domain, out var value)) { - return _domainsAcl[domain]; + return value; } return _moduleAcl; } @@ -149,13 +151,13 @@ namespace ASC.Data.Storage.S3 foreach (var h in headers) { - if (h.StartsWith("Content-Disposition")) headersOverrides.ContentDisposition = (h.Substring("Content-Disposition".Length + 1)); - else if (h.StartsWith("Cache-Control")) headersOverrides.CacheControl = (h.Substring("Cache-Control".Length + 1)); - else if (h.StartsWith("Content-Encoding")) headersOverrides.ContentEncoding = (h.Substring("Content-Encoding".Length + 1)); - else if (h.StartsWith("Content-Language")) headersOverrides.ContentLanguage = (h.Substring("Content-Language".Length + 1)); - else if (h.StartsWith("Content-Type")) headersOverrides.ContentType = (h.Substring("Content-Type".Length + 1)); - else if (h.StartsWith("Expires")) headersOverrides.Expires = (h.Substring("Expires".Length + 1)); - else throw new FormatException(string.Format("Invalid header: {0}", h)); + if (h.StartsWith("Content-Disposition")) headersOverrides.ContentDisposition = h.Substring("Content-Disposition".Length + 1); + else if (h.StartsWith("Cache-Control")) headersOverrides.CacheControl = h.Substring("Cache-Control".Length + 1); + else if (h.StartsWith("Content-Encoding")) headersOverrides.ContentEncoding = h.Substring("Content-Encoding".Length + 1); + else if (h.StartsWith("Content-Language")) headersOverrides.ContentLanguage = h.Substring("Content-Language".Length + 1); + else if (h.StartsWith("Content-Type")) headersOverrides.ContentType = h.Substring("Content-Type".Length + 1); + else if (h.StartsWith("Expires")) headersOverrides.Expires = h.Substring("Expires".Length + 1); + else throw new FormatException($"Invalid header: {h}"); } pUrlRequest.ResponseHeaderOverrides = headersOverrides; } @@ -230,12 +232,10 @@ namespace ASC.Data.Storage.S3 protected override Uri SaveWithAutoAttachment(string domain, string path, Stream stream, string attachmentFileName) { - var contentDisposition = string.Format("attachment; filename={0};", - HttpUtility.UrlPathEncode(attachmentFileName)); + var contentDisposition = $"attachment; filename={HttpUtility.UrlPathEncode(attachmentFileName)};"; if (attachmentFileName.Any(c => c >= 0 && c <= 127)) { - contentDisposition = string.Format("attachment; filename*=utf-8''{0};", - HttpUtility.UrlPathEncode(attachmentFileName)); + contentDisposition = $"attachment; filename*=utf-8''{HttpUtility.UrlPathEncode(attachmentFileName)};"; } return Save(domain, path, stream, null, contentDisposition); } @@ -328,7 +328,7 @@ namespace ASC.Data.Storage.S3 Paths = new Paths { Items = paths.ToList(), - Quantity = paths.Count() + Quantity = paths.Length } } }; @@ -472,7 +472,7 @@ namespace ASC.Data.Storage.S3 public override void DeleteFiles(string domain, List paths) { - if (!paths.Any()) return; + if (paths.Count == 0) return; var keysToDel = new List(); @@ -501,7 +501,7 @@ namespace ASC.Data.Storage.S3 } } - if (!keysToDel.Any()) + if (keysToDel.Count == 0) return; using (var client = GetClient()) @@ -543,7 +543,7 @@ namespace ASC.Data.Storage.S3 client.DeleteObjectAsync(deleteRequest).Wait(); - QuotaUsedDelete(domain, Convert.ToInt64(s3Object.Size)); + QuotaUsedDelete(domain, s3Object.Size); } } @@ -565,7 +565,7 @@ namespace ASC.Data.Storage.S3 client.DeleteObjectAsync(deleteRequest).Wait(); - QuotaUsedDelete(domain, Convert.ToInt64(s3Object.Size)); + QuotaUsedDelete(domain, s3Object.Size); } } @@ -727,23 +727,23 @@ namespace ASC.Data.Storage.S3 var policyBase64 = GetPolicyBase64(key, string.Empty, contentType, contentDisposition, maxUploadSize, out var sign); var postBuilder = new StringBuilder(); - postBuilder.Append("{"); - postBuilder.AppendFormat("\"key\":\"{0}${{filename}}\",", key); - postBuilder.AppendFormat("\"acl\":\"public-read\","); - postBuilder.AppendFormat("\"key\":\"{0}\",", key); - postBuilder.AppendFormat("\"success_action_status\":\"{0}\",", 201); + postBuilder.Append('{'); + postBuilder.Append("\"key\":\"").Append(key).Append("${{filename}}\","); + postBuilder.Append("\"acl\":\"public-read\","); + postBuilder.Append($"\"key\":\"{key}\","); + postBuilder.Append("\"success_action_status\":\"201\","); if (!string.IsNullOrEmpty(contentType)) - postBuilder.AppendFormat("\"Content-Type\":\"{0}\",", contentType); + postBuilder.Append($"\"Content-Type\":\"{contentType}\","); if (!string.IsNullOrEmpty(contentDisposition)) - postBuilder.AppendFormat("\"Content-Disposition\":\"{0}\",", contentDisposition); + postBuilder.Append($"\"Content-Disposition\":\"{contentDisposition}\","); - postBuilder.AppendFormat("\"AWSAccessKeyId\":\"{0}\",", _accessKeyId); - postBuilder.AppendFormat("\"Policy\":\"{0}\",", policyBase64); - postBuilder.AppendFormat("\"Signature\":\"{0}\"", sign); - postBuilder.AppendFormat("\"SignatureVersion\":\"{0}\"", 2); - postBuilder.AppendFormat("\"SignatureMethod\":\"{0}\"", "HmacSHA1"); - postBuilder.Append("}"); + postBuilder.Append($"\"AWSAccessKeyId\":\"{_accessKeyId}\","); + postBuilder.Append($"\"Policy\":\"{policyBase64}\","); + postBuilder.Append($"\"Signature\":\"{sign}\""); + postBuilder.Append("\"SignatureVersion\":\"2\""); + postBuilder.Append("\"SignatureMethod\":\"HmacSHA1\""); + postBuilder.Append('}'); return postBuilder.ToString(); } @@ -757,27 +757,25 @@ namespace ASC.Data.Storage.S3 out var sign); var formBuilder = new StringBuilder(); - formBuilder.AppendFormat("
", destBucket); - formBuilder.AppendFormat("", key); + formBuilder.Append($""); + formBuilder.Append($""); formBuilder.Append(""); if (!string.IsNullOrEmpty(redirectTo)) - formBuilder.AppendFormat("", - redirectTo); + formBuilder.Append($""); formBuilder.AppendFormat("", 201); if (!string.IsNullOrEmpty(contentType)) - formBuilder.AppendFormat("", contentType); + formBuilder.Append($""); if (!string.IsNullOrEmpty(contentDisposition)) - formBuilder.AppendFormat("", - contentDisposition); - formBuilder.AppendFormat("", _accessKeyId); - formBuilder.AppendFormat("", policyBase64); - formBuilder.AppendFormat("", sign); - formBuilder.AppendFormat("", 2); - formBuilder.AppendFormat("", "HmacSHA1"); - formBuilder.AppendFormat(""); - formBuilder.AppendFormat("
", submitLabel); + formBuilder.Append($""); + formBuilder.Append($""); + formBuilder.Append($""); + formBuilder.Append($""); + formBuilder.Append(""); + formBuilder.Append(""); + formBuilder.Append(""); + formBuilder.Append($""); return formBuilder.ToString(); } @@ -785,26 +783,28 @@ namespace ASC.Data.Storage.S3 long maxUploadSize, out string sign) { var policyBuilder = new StringBuilder(); - policyBuilder.AppendFormat("{{\"expiration\": \"{0}\",\"conditions\":[", - DateTime.UtcNow.AddMinutes(15).ToString(AWSSDKUtils.ISO8601DateFormat, - CultureInfo.InvariantCulture)); - policyBuilder.AppendFormat("{{\"bucket\": \"{0}\"}},", _bucket); - policyBuilder.AppendFormat("[\"starts-with\", \"$key\", \"{0}\"],", key); + + var minutes = DateTime.UtcNow.AddMinutes(15).ToString(AWSSDKUtils.ISO8601DateFormat, + CultureInfo.InvariantCulture); + + policyBuilder.Append($"{{\"expiration\": \"{minutes}\",\"conditions\":["); + policyBuilder.Append($"{{\"bucket\": \"{_bucket}\"}},"); + policyBuilder.Append($"[\"starts-with\", \"$key\", \"{key}\"],"); policyBuilder.Append("{\"acl\": \"public-read\"},"); if (!string.IsNullOrEmpty(redirectTo)) { - policyBuilder.AppendFormat("{{\"success_action_redirect\": \"{0}\"}},", redirectTo); + policyBuilder.Append($"{{\"success_action_redirect\": \"{redirectTo}\"}},"); } - policyBuilder.AppendFormat("{{\"success_action_status\": \"{0}\"}},", 201); + policyBuilder.Append("{{\"success_action_status\": \"201\"}},"); if (!string.IsNullOrEmpty(contentType)) { - policyBuilder.AppendFormat("[\"eq\", \"$Content-Type\", \"{0}\"],", contentType); + policyBuilder.Append($"[\"eq\", \"$Content-Type\", \"{contentType}\"],"); } if (!string.IsNullOrEmpty(contentDisposition)) { - policyBuilder.AppendFormat("[\"eq\", \"$Content-Disposition\", \"{0}\"],", contentDisposition); + policyBuilder.Append($"[\"eq\", \"$Content-Disposition\", \"{contentDisposition}\"],"); } - policyBuilder.AppendFormat("[\"content-length-range\", 0, {0}]", maxUploadSize); + policyBuilder.Append($"[\"content-length-range\", 0, {maxUploadSize}]"); policyBuilder.Append("]}"); var policyBase64 = Convert.ToBase64String(Encoding.UTF8.GetBytes(policyBuilder.ToString())); @@ -951,7 +951,7 @@ namespace ASC.Data.Storage.S3 { using (var client = GetClient()) { - var request = new ListObjectsRequest { BucketName = _bucket, Prefix = (MakePath(domain, path)) }; + var request = new ListObjectsRequest { BucketName = _bucket, Prefix = MakePath(domain, path) }; var response = client.ListObjectsAsync(request).Result; return response.S3Objects.Count > 0; } @@ -965,7 +965,7 @@ namespace ASC.Data.Storage.S3 public override long GetFileSize(string domain, string path) { using var client = GetClient(); - var request = new ListObjectsRequest { BucketName = _bucket, Prefix = (MakePath(domain, path)) }; + var request = new ListObjectsRequest { BucketName = _bucket, Prefix = MakePath(domain, path) }; var response = client.ListObjectsAsync(request).Result; if (response.S3Objects.Count > 0) { @@ -1059,7 +1059,7 @@ namespace ASC.Data.Storage.S3 { BucketName = _bucket, Prefix = path, - MaxKeys = (1000) + MaxKeys = 1000 }; var objects = new List(); @@ -1091,7 +1091,7 @@ namespace ASC.Data.Storage.S3 { _modulename = moduleConfig.Name; _dataList = new DataList(moduleConfig); - _domains.AddRange(moduleConfig.Domain.Select(x => string.Format("{0}/", x.Name))); + _domains.AddRange(moduleConfig.Domain.Select(x => $"{x.Name}/")); //Make expires _domainsExpires = moduleConfig.Domain.Where(x => x.Expires != TimeSpan.Zero).ToDictionary(x => x.Name, y => y.Expires); @@ -1116,40 +1116,37 @@ namespace ASC.Data.Storage.S3 _secretAccessKeyId = props["secretaccesskey"]; _bucket = props["bucket"]; - if (props.ContainsKey("recycleDir")) + props.TryGetValue("recycleDir", out _recycleDir); + + if (props.TryGetValue("region", out var region) && !string.IsNullOrEmpty(region)) { - _recycleDir = props["recycleDir"]; + _region = region; } - if (props.ContainsKey("region") && !string.IsNullOrEmpty(props["region"])) + if (props.TryGetValue("serviceurl", out var url) && !string.IsNullOrEmpty(url)) { - _region = props["region"]; + _serviceurl = url; } - if (props.ContainsKey("serviceurl") && !string.IsNullOrEmpty(props["serviceurl"])) + if (props.TryGetValue("forcepathstyle", out var style)) { - _serviceurl = props["serviceurl"]; - } - - if (props.ContainsKey("forcepathstyle")) - { - if (bool.TryParse(props["forcepathstyle"], out var fps)) + if (bool.TryParse(style, out var fps)) { _forcepathstyle = fps; } } - if (props.ContainsKey("usehttp")) + if (props.TryGetValue("usehttp", out var use)) { - if (bool.TryParse(props["usehttp"], out var uh)) + if (bool.TryParse(use, out var uh)) { _useHttp = uh; } } - if (props.ContainsKey("sse") && !string.IsNullOrEmpty(props["sse"])) + if (props.TryGetValue("sse", out var sse) && !string.IsNullOrEmpty(sse)) { - _sse = (props["sse"].ToLower()) switch + _sse = sse.ToLower() switch { "none" => ServerSideEncryptionMethod.None, "aes256" => ServerSideEncryptionMethod.AES256, @@ -1160,29 +1157,23 @@ namespace ASC.Data.Storage.S3 _bucketRoot = props.ContainsKey("cname") && Uri.IsWellFormedUriString(props["cname"], UriKind.Absolute) ? new Uri(props["cname"], UriKind.Absolute) - : new Uri(string.Format("http://s3.{1}.amazonaws.com/{0}/", _bucket, _region), UriKind.Absolute); + : new Uri($"http://s3.{_region}.amazonaws.com/{_bucket}/", UriKind.Absolute); _bucketSSlRoot = props.ContainsKey("cnamessl") && Uri.IsWellFormedUriString(props["cnamessl"], UriKind.Absolute) ? new Uri(props["cnamessl"], UriKind.Absolute) - : new Uri(string.Format("https://s3.{1}.amazonaws.com/{0}/", _bucket, _region), UriKind.Absolute); + : new Uri($"https://s3.{_region}.amazonaws.com/{_bucket}/", UriKind.Absolute); - if (props.ContainsKey("lower")) + if (props.TryGetValue("lower", out var lower)) { - bool.TryParse(props["lower"], out _lowerCasing); + bool.TryParse(lower, out _lowerCasing); } - if (props.ContainsKey("cloudfront")) + if (props.TryGetValue("cloudfront", out var front)) { - bool.TryParse(props["cloudfront"], out _revalidateCloudFront); - } - if (props.ContainsKey("distribution")) - { - _distributionId = props["distribution"]; + bool.TryParse(front, out _revalidateCloudFront); } - if (props.ContainsKey("subdir")) - { - _subDir = props["subdir"]; - } + props.TryGetValue("distribution", out _distributionId); + props.TryGetValue("subdir", out _subDir); return this; } @@ -1198,14 +1189,10 @@ namespace ASC.Data.Storage.S3 if (_subDir.Length == 1 && (_subDir[0] == '/' || _subDir[0] == '\\')) result = path; else - result = string.Format("{0}/{1}", _subDir, path); // Ignory all, if _subDir is not null + result = $"{_subDir}/{path}"; // Ignory all, if _subDir is not null } else//Key combined from module+domain+filename - result = string.Format("{0}/{1}/{2}/{3}", - _tenant, - _modulename, - domain, - path); + result = $"{_tenant}/{_modulename}/{domain}/{path}"; result = result.Replace("//", "/").TrimStart('/').TrimEnd('/'); if (_lowerCasing) @@ -1218,7 +1205,7 @@ namespace ASC.Data.Storage.S3 private string GetRecyclePath(string path) { - return string.IsNullOrEmpty(_recycleDir) ? "" : string.Format("{0}/{1}", _recycleDir, path.TrimStart('/')); + return string.IsNullOrEmpty(_recycleDir) ? "" : $"{_recycleDir}/{path.TrimStart('/')}"; } private void Recycle(IAmazonS3 client, string domain, string key) @@ -1275,7 +1262,7 @@ namespace ASC.Data.Storage.S3 public ResponseStreamWrapper(GetObjectResponse response) { - _response = response ?? throw new ArgumentNullException("response"); + _response = response ?? throw new ArgumentNullException(nameof(response)); } diff --git a/common/ASC.Data.Storage/StaticUploader.cs b/common/ASC.Data.Storage/StaticUploader.cs index 39d4cdc39b..f65539a372 100644 --- a/common/ASC.Data.Storage/StaticUploader.cs +++ b/common/ASC.Data.Storage/StaticUploader.cs @@ -255,7 +255,7 @@ namespace ASC.Data.Storage this.relativePath = relativePath; this.mappedPath = mappedPath; - var extensions = ".png|.jpeg|.jpg|.gif|.ico|.swf|.mp3|.ogg|.eot|.svg|.ttf|.woff|.woff2|.css|.less|.js"; + const string extensions = ".png|.jpeg|.jpg|.gif|.ico|.swf|.mp3|.ogg|.eot|.svg|.ttf|.woff|.woff2|.css|.less|.js"; var extensionsArray = extensions.Split('|'); directoryFiles = Directory.GetFiles(mappedPath, "*", SearchOption.AllDirectories) diff --git a/common/ASC.Data.Storage/StorageFactory.cs b/common/ASC.Data.Storage/StorageFactory.cs index d19bc45af1..40a45f1151 100644 --- a/common/ASC.Data.Storage/StorageFactory.cs +++ b/common/ASC.Data.Storage/StorageFactory.cs @@ -56,8 +56,7 @@ namespace ASC.Data.Storage public IEnumerable GetModuleList(string configpath, bool exceptDisabledMigration = false) { return Section.Module - .Where(x => x.Visible) - .Where(x => !exceptDisabledMigration || !x.DisableMigrate) + .Where(x => x.Visible && (!exceptDisabledMigration || !x.DisableMigrate)) .Select(x => x.Name); } @@ -252,7 +251,7 @@ namespace ASC.Data.Storage props = handler.Property.ToDictionary(r => r.Name, r => r.Value); } - ; + return ((IDataStore)ActivatorUtilities.CreateInstance(ServiceProvider, instanceType)) .Configure(tenant, handler, moduleElement, props) .SetQuotaController(moduleElement.Count ? controller : null @@ -260,7 +259,7 @@ namespace ASC.Data.Storage } } - public class StorageFactoryExtension + public static class StorageFactoryExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.Data.Storage/StorageHandler.cs b/common/ASC.Data.Storage/StorageHandler.cs index b36f22aba8..280e6597f4 100644 --- a/common/ASC.Data.Storage/StorageHandler.cs +++ b/common/ASC.Data.Storage/StorageHandler.cs @@ -63,9 +63,9 @@ namespace ASC.Data.Storage.DiscStorage } private IServiceProvider ServiceProvider { get; } - - public async Task Invoke(HttpContext context) - { + + public Task Invoke(HttpContext context) + { using var scope = ServiceProvider.CreateScope(); var scopeClass = scope.ServiceProvider.GetService(); var (tenantManager, securityContext, storageFactory, emailValidationKeyProvider) = scopeClass; @@ -73,11 +73,11 @@ namespace ASC.Data.Storage.DiscStorage if (_checkAuth && !securityContext.IsAuthenticated) { context.Response.StatusCode = (int)HttpStatusCode.Forbidden; - return; + return Task.CompletedTask; } var storage = storageFactory.GetStorage(tenantManager.GetCurrentTenant().TenantId.ToString(CultureInfo.InvariantCulture), _module); - var path = CrossPlatform.PathCombine(_path, GetRouteValue("pathInfo").Replace('/', Path.DirectorySeparatorChar)); + var path = CrossPlatform.PathCombine(_path, GetRouteValue("pathInfo", context).Replace('/', Path.DirectorySeparatorChar)); var header = context.Request.Query[Constants.QUERY_HEADER].FirstOrDefault() ?? ""; var auth = context.Request.Query[Constants.QUERY_AUTH].FirstOrDefault() ?? ""; @@ -92,17 +92,17 @@ namespace ASC.Data.Storage.DiscStorage if (validateResult != EmailValidationKeyProvider.ValidationResult.Ok) { context.Response.StatusCode = (int)HttpStatusCode.Forbidden; - return; + return Task.CompletedTask; } } if (!storage.IsFile(_domain, path)) { context.Response.StatusCode = (int)HttpStatusCode.NotFound; - return; + return Task.CompletedTask; } - var headers = header.Length > 0 ? header.Split('&').Select(HttpUtility.UrlDecode) : new string[] { }; + var headers = header.Length > 0 ? header.Split('&').Select(HttpUtility.UrlDecode) : Array.Empty(); if (storage.IsSupportInternalUri) { @@ -113,9 +113,9 @@ namespace ASC.Data.Storage.DiscStorage //context.Response.Cache.SetCacheability(HttpCacheability.NoCache); context.Response.Redirect(uri.ToString()); - return; - } - + return Task.CompletedTask; + } + string encoding = null; if (storage is DiscDataStore && storage.IsFile(_domain, path + ".gz")) { @@ -143,18 +143,23 @@ namespace ASC.Data.Storage.DiscStorage if (encoding != null) context.Response.Headers["Content-Encoding"] = encoding; + return InternalInvoke(context, storage, path); + } + + private async Task InternalInvoke(HttpContext context, IDataStore storage, string path) + { using (var stream = storage.GetReadStream(_domain, path)) { await stream.CopyToAsync(context.Response.Body); } await context.Response.Body.FlushAsync(); - await context.Response.CompleteAsync(); - - string GetRouteValue(string name) - { - return (context.GetRouteValue(name) ?? "").ToString(); - } + await context.Response.CompleteAsync(); + } + + private string GetRouteValue(string name, HttpContext context) + { + return (context.GetRouteValue(name) ?? "").ToString(); } } diff --git a/common/ASC.Data.Storage/TenantPath.cs b/common/ASC.Data.Storage/TenantPath.cs index 1f49776515..0f604fda12 100644 --- a/common/ASC.Data.Storage/TenantPath.cs +++ b/common/ASC.Data.Storage/TenantPath.cs @@ -29,13 +29,13 @@ using System.Globalization; namespace ASC.Data.Storage { - public class TenantPath + public static class TenantPath { public static string CreatePath(string tenant) { if (tenant == null) { - throw new ArgumentNullException("tenant"); + throw new ArgumentNullException(nameof(tenant)); } if (long.TryParse(tenant, NumberStyles.Integer, CultureInfo.InvariantCulture, out var tenantId)) diff --git a/common/ASC.Data.Storage/TenantQuotaController.cs b/common/ASC.Data.Storage/TenantQuotaController.cs index 0f34fd4843..12d8b43c8f 100644 --- a/common/ASC.Data.Storage/TenantQuotaController.cs +++ b/common/ASC.Data.Storage/TenantQuotaController.cs @@ -129,7 +129,7 @@ namespace ASC.Data.Storage private void SetTenantQuotaRow(string module, string domain, long size, string dataTag, bool exchange) { TenantManager.SetTenantQuotaRow( - new TenantQuotaRow { Tenant = tenant, Path = string.Format("/{0}/{1}", module, domain), Counter = size, Tag = dataTag }, + new TenantQuotaRow { Tenant = tenant, Path = $"/{module}/{domain}", Counter = size, Tag = dataTag }, exchange); } diff --git a/common/ASC.Data.Storage/WebPath.cs b/common/ASC.Data.Storage/WebPath.cs index 4c89ff377f..0752ac206e 100644 --- a/common/ASC.Data.Storage/WebPath.cs +++ b/common/ASC.Data.Storage/WebPath.cs @@ -65,7 +65,7 @@ namespace ASC.Data.Storage { if (!Uri.IsWellFormedUriString(absolutePath, UriKind.Absolute)) { - throw new ArgumentException(string.Format("bad path format {0} is not absolute", absolutePath)); + throw new ArgumentException($"bad path format {absolutePath} is not absolute"); } var appender = Appenders.FirstOrDefault(x => absolutePath.Contains(x.Append) || (absolutePath.Contains(x.AppendSecure) && !string.IsNullOrEmpty(x.AppendSecure))); @@ -82,7 +82,7 @@ namespace ASC.Data.Storage { if (!string.IsNullOrEmpty(relativePath) && relativePath.IndexOf('~') == 0) { - throw new ArgumentException(string.Format("bad path format {0} remove '~'", relativePath), "relativePath"); + throw new ArgumentException($"bad path format {relativePath} remove '~'", nameof(relativePath)); } var result = relativePath; @@ -91,12 +91,12 @@ namespace ASC.Data.Storage if (Appenders.Any()) { var avaliableAppenders = Appenders.Where(x => x.Extensions != null && x.Extensions.Split('|').Contains(ext) || string.IsNullOrEmpty(ext)).ToList(); - var avaliableAppendersCount = avaliableAppenders.LongCount(); + var avaliableAppendersCount = avaliableAppenders.Count; Appender appender; if (avaliableAppendersCount > 1) { - appender = avaliableAppenders[(int)(relativePath.Length % avaliableAppendersCount)]; + appender = avaliableAppenders[relativePath.Length % avaliableAppendersCount]; } else if (avaliableAppendersCount == 1) { @@ -123,7 +123,7 @@ namespace ASC.Data.Storage //} //else //{ - result = string.Format("{0}/{1}{2}", appender.Append.TrimEnd('/').TrimStart('~'), relativePath.TrimStart('/'), query); + result = $"{appender.Append.TrimEnd('/').TrimStart('~')}/{relativePath.TrimStart('/')}{query}"; //} } else @@ -131,12 +131,12 @@ namespace ASC.Data.Storage //TODO HostingEnvironment.IsHosted if (SecureHelper.IsSecure(httpContext, options) && !string.IsNullOrEmpty(appender.AppendSecure)) { - result = string.Format("{0}/{1}", appender.AppendSecure.TrimEnd('/'), relativePath.TrimStart('/')); + result = $"{appender.AppendSecure.TrimEnd('/')}/{relativePath.TrimStart('/')}"; } else { //Append directly - result = string.Format("{0}/{1}", appender.Append.TrimEnd('/'), relativePath.TrimStart('/')); + result = $"{appender.Append.TrimEnd('/')}/{relativePath.TrimStart('/')}"; } } } @@ -158,6 +158,7 @@ namespace ASC.Data.Storage public IHostEnvironment HostEnvironment { get; } private CoreBaseSettings CoreBaseSettings { get; } private IOptionsMonitor Options { get; } + private IHttpClientFactory ClientFactory { get; } public WebPath( WebPathSettings webPathSettings, @@ -166,7 +167,8 @@ namespace ASC.Data.Storage StorageSettingsHelper storageSettingsHelper, IHostEnvironment hostEnvironment, CoreBaseSettings coreBaseSettings, - IOptionsMonitor options) + IOptionsMonitor options, + IHttpClientFactory clientFactory) { WebPathSettings = webPathSettings; ServiceProvider = serviceProvider; @@ -175,6 +177,7 @@ namespace ASC.Data.Storage HostEnvironment = hostEnvironment; CoreBaseSettings = coreBaseSettings; Options = options; + ClientFactory = clientFactory; } public WebPath( @@ -186,8 +189,9 @@ namespace ASC.Data.Storage IHttpContextAccessor httpContextAccessor, IHostEnvironment hostEnvironment, CoreBaseSettings coreBaseSettings, - IOptionsMonitor options) - : this(webPathSettings, serviceProvider, settingsManager, storageSettingsHelper, hostEnvironment, coreBaseSettings, options) + IOptionsMonitor options, + IHttpClientFactory clientFactory) + : this(webPathSettings, serviceProvider, settingsManager, storageSettingsHelper, hostEnvironment, coreBaseSettings, options, clientFactory) { HttpContextAccessor = httpContextAccessor; } @@ -196,7 +200,7 @@ namespace ASC.Data.Storage { if (!string.IsNullOrEmpty(relativePath) && relativePath.IndexOf('~') == 0) { - throw new ArgumentException(string.Format("bad path format {0} remove '~'", relativePath), "relativePath"); + throw new ArgumentException($"bad path format {relativePath} remove '~'", nameof(relativePath)); } if (CoreBaseSettings.Standalone && ServiceProvider.GetService().CanUpload()) //hack for skip resolve DistributedTaskQueueOptionsManager @@ -241,7 +245,7 @@ namespace ASC.Data.Storage var request = new HttpRequestMessage(); request.RequestUri = new Uri(path); request.Method = HttpMethod.Head; - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); return response.StatusCode == HttpStatusCode.OK; diff --git a/common/ASC.Data.Storage/Wildcard.cs b/common/ASC.Data.Storage/Wildcard.cs index 7fec130992..235c47a8b5 100644 --- a/common/ASC.Data.Storage/Wildcard.cs +++ b/common/ASC.Data.Storage/Wildcard.cs @@ -26,7 +26,7 @@ namespace ASC.Data.Storage { - public class Wildcard + public static class Wildcard { public static bool IsMatch(string pattern, string input) { @@ -38,8 +38,8 @@ namespace ASC.Data.Storage var offsetInput = 0; var isAsterix = false; - int i; - for (i = 0; i < pattern.Length;) + int i = 0; + while (i < pattern.Length) { switch (pattern[i]) { @@ -90,7 +90,7 @@ namespace ASC.Data.Storage } // final evaluation. The index should be pointing at the // end of the string. - return (offsetInput == input.Length); + return offsetInput == input.Length; } } } \ No newline at end of file diff --git a/common/ASC.FederatedLogin/AccountLinker.cs b/common/ASC.FederatedLogin/AccountLinker.cs index 946609794d..4cee029002 100644 --- a/common/ASC.FederatedLogin/AccountLinker.cs +++ b/common/ASC.FederatedLogin/AccountLinker.cs @@ -65,7 +65,8 @@ namespace ASC.FederatedLogin var profiles = cache.Get>(obj); if (profiles == null) { - cache.Insert(obj, profiles = fromDb(obj), DateTime.UtcNow + TimeSpan.FromMinutes(10)); + profiles = fromDb(obj); + cache.Insert(obj, profiles, DateTime.UtcNow + TimeSpan.FromMinutes(10)); } return profiles; } diff --git a/common/ASC.FederatedLogin/Helpers/HashHelper.cs b/common/ASC.FederatedLogin/Helpers/HashHelper.cs index 1c9f6024a9..d4cf589bc3 100644 --- a/common/ASC.FederatedLogin/Helpers/HashHelper.cs +++ b/common/ASC.FederatedLogin/Helpers/HashHelper.cs @@ -28,13 +28,13 @@ using System.Text; namespace ASC.FederatedLogin.Helpers { - public class HashHelper + public static class HashHelper { public static int CombineHashCodes(int hash1, int hash2) { if (hash2 == 0) return hash1; - return (((hash1 << 5) + hash1) ^ hash2); + return ((hash1 << 5) + hash1) ^ hash2; } //Use this luke!!! diff --git a/common/ASC.FederatedLogin/Helpers/JsCallbackHelper.cs b/common/ASC.FederatedLogin/Helpers/JsCallbackHelper.cs index 17bdc13f3f..5e610c6d23 100644 --- a/common/ASC.FederatedLogin/Helpers/JsCallbackHelper.cs +++ b/common/ASC.FederatedLogin/Helpers/JsCallbackHelper.cs @@ -29,7 +29,7 @@ using System.Reflection; namespace ASC.FederatedLogin.Helpers { - public class JsCallbackHelper + public static class JsCallbackHelper { public static string GetCallbackPage() { diff --git a/common/ASC.FederatedLogin/Helpers/OAuth20TokenHelper.cs b/common/ASC.FederatedLogin/Helpers/OAuth20TokenHelper.cs index 1f2ec7bfa4..5ed17df780 100644 --- a/common/ASC.FederatedLogin/Helpers/OAuth20TokenHelper.cs +++ b/common/ASC.FederatedLogin/Helpers/OAuth20TokenHelper.cs @@ -70,7 +70,7 @@ namespace ASC.FederatedLogin.Helpers var stateUriBuilder = new UriBuilder(u.Scheme, u.Host, u.Port, $"thirdparty/{loginProvider.Name.ToLower()}/code"); - if (additionalStateArgs != null && additionalStateArgs.Any()) + if (additionalStateArgs != null && additionalStateArgs.Count > 0) { var stateQuery = ""; stateQuery = additionalStateArgs.Keys @@ -88,8 +88,8 @@ namespace ASC.FederatedLogin.Helpers query = additionalArgs.Keys.Where(additionalArg => additionalArg != null) .Aggregate(query, (current, additionalArg) => additionalArg != null ? current - + ("&" + HttpUtility.UrlEncode((additionalArg).Trim()) - + "=" + HttpUtility.UrlEncode((additionalArgs[additionalArg] ?? "").Trim())) : null); + + "&" + HttpUtility.UrlEncode(additionalArg.Trim()) + + "=" + HttpUtility.UrlEncode((additionalArgs[additionalArg] ?? "").Trim()) : null); } return uriBuilder.Uri + "?" + query; @@ -103,14 +103,11 @@ namespace ASC.FederatedLogin.Helpers var clientSecret = loginProvider.ClientSecret; var redirectUri = loginProvider.RedirectUri; - if (string.IsNullOrEmpty(authCode)) throw new ArgumentNullException("authCode"); + if (string.IsNullOrEmpty(authCode)) throw new ArgumentNullException(nameof(authCode)); if (string.IsNullOrEmpty(clientID)) throw new ArgumentNullException("clientID"); if (string.IsNullOrEmpty(clientSecret)) throw new ArgumentNullException("clientSecret"); - var data = string.Format("code={0}&client_id={1}&client_secret={2}", - HttpUtility.UrlEncode(authCode), - HttpUtility.UrlEncode(clientID), - HttpUtility.UrlEncode(clientSecret)); + var data = $"code={HttpUtility.UrlEncode(authCode)}&client_id={HttpUtility.UrlEncode(clientID)}&client_secret={HttpUtility.UrlEncode(clientSecret)}"; if (!string.IsNullOrEmpty(redirectUri)) data += "&redirect_uri=" + HttpUtility.UrlEncode(redirectUri); @@ -120,7 +117,7 @@ namespace ASC.FederatedLogin.Helpers var json = RequestHelper.PerformRequest(requestUrl, "application/x-www-form-urlencoded", "POST", data); if (json != null) { - if (!json.StartsWith("{")) + if (!json.StartsWith('{')) { json = "{\"" + json.Replace("=", "\":\"").Replace("&", "\",\"") + "\"}"; } @@ -145,12 +142,9 @@ namespace ASC.FederatedLogin.Helpers public static OAuth20Token RefreshToken(string requestUrl, OAuth20Token token) { - if (token == null || !CanRefresh(token)) throw new ArgumentException("Can not refresh given token", "token"); + if (token == null || !CanRefresh(token)) throw new ArgumentException("Can not refresh given token", nameof(token)); - var data = string.Format("client_id={0}&client_secret={1}&refresh_token={2}&grant_type=refresh_token", - HttpUtility.UrlEncode(token.ClientID), - HttpUtility.UrlEncode(token.ClientSecret), - HttpUtility.UrlEncode(token.RefreshToken)); + var data = $"client_id={HttpUtility.UrlEncode(token.ClientID)}&client_secret={HttpUtility.UrlEncode(token.ClientSecret)}&refresh_token={HttpUtility.UrlEncode(token.RefreshToken)}&grant_type=refresh_token"; var json = RequestHelper.PerformRequest(requestUrl, "application/x-www-form-urlencoded", "POST", data); if (json != null) diff --git a/common/ASC.FederatedLogin/Helpers/RequestHelper.cs b/common/ASC.FederatedLogin/Helpers/RequestHelper.cs index e4d86a8d0f..f4caddc46d 100644 --- a/common/ASC.FederatedLogin/Helpers/RequestHelper.cs +++ b/common/ASC.FederatedLogin/Helpers/RequestHelper.cs @@ -33,18 +33,19 @@ using System.Text; namespace ASC.FederatedLogin.Helpers { - public class RequestHelper + public static class RequestHelper { + private static HttpClient HttpClient { get; } = new HttpClient(); + public static string PerformRequest(string uri, string contentType = "", string method = "GET", string body = "", Dictionary headers = null, int timeout = 30000) { - if (string.IsNullOrEmpty(uri)) throw new ArgumentNullException("uri"); + if (string.IsNullOrEmpty(uri)) throw new ArgumentNullException(nameof(uri)); var request = new HttpRequestMessage(); request.RequestUri = new Uri(uri); request.Method = new HttpMethod(method); - using var httpClient = new HttpClient(); - httpClient.Timeout = TimeSpan.FromMilliseconds(timeout); + HttpClient.Timeout = TimeSpan.FromMilliseconds(timeout); if (headers != null) { @@ -64,7 +65,7 @@ namespace ASC.FederatedLogin.Helpers } } - using var response = httpClient.Send(request); + using var response = HttpClient.Send(request); using var stream = response.Content.ReadAsStream(); if (stream == null) return null; using var readStream = new StreamReader(stream); diff --git a/common/ASC.FederatedLogin/Helpers/XrdsHelper.cs b/common/ASC.FederatedLogin/Helpers/XrdsHelper.cs index 767691a740..8011ad223a 100644 --- a/common/ASC.FederatedLogin/Helpers/XrdsHelper.cs +++ b/common/ASC.FederatedLogin/Helpers/XrdsHelper.cs @@ -30,19 +30,18 @@ using Microsoft.AspNetCore.Http; namespace ASC.FederatedLogin.Helpers { - public class XrdsHelper + public static class XrdsHelper { - private const string Xrds = + internal static async Task RenderXrds(HttpResponse responce, string location, string iconlink) + { + var xrds = @"http://specs.openid.net/auth/2.0/return_to{0}http://specs.openid.net/extensions/ui/icon{1}"; + $@"priority=""1"">{location}http://specs.openid.net/extensions/ui/icon{iconlink}"; - - internal static async Task RenderXrds(HttpResponse responce, string location, string iconlink) - { - await responce.WriteAsync(string.Format(Xrds, location, iconlink)); + await responce.WriteAsync(xrds); } //TODO diff --git a/common/ASC.FederatedLogin/LoginProviders/BaseLoginProvider.cs b/common/ASC.FederatedLogin/LoginProviders/BaseLoginProvider.cs index 89cefcaaed..d00ae65afa 100644 --- a/common/ASC.FederatedLogin/LoginProviders/BaseLoginProvider.cs +++ b/common/ASC.FederatedLogin/LoginProviders/BaseLoginProvider.cs @@ -113,7 +113,7 @@ namespace ASC.FederatedLogin.LoginProviders InstanceCrypto = instanceCrypto; } - public virtual LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs = null) + public virtual LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs) { try { @@ -163,7 +163,7 @@ namespace ASC.FederatedLogin.LoginProviders public abstract LoginProfile GetLoginProfile(string accessToken); } - public class BaseLoginProviderExtension + public static class BaseLoginProviderExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.FederatedLogin/LoginProviders/DocuSignLoginProvider.cs b/common/ASC.FederatedLogin/LoginProviders/DocuSignLoginProvider.cs index a5822378a3..42fe66347d 100644 --- a/common/ASC.FederatedLogin/LoginProviders/DocuSignLoginProvider.cs +++ b/common/ASC.FederatedLogin/LoginProviders/DocuSignLoginProvider.cs @@ -79,7 +79,7 @@ namespace ASC.FederatedLogin.LoginProviders { get { - var codeAuth = string.Format("{0}:{1}", ClientID, ClientSecret); + var codeAuth = $"{ClientID}:{ClientSecret}"; var codeAuthBytes = Encoding.UTF8.GetBytes(codeAuth); var codeAuthBase64 = Convert.ToBase64String(codeAuthBytes); return "Basic " + codeAuthBase64; @@ -88,17 +88,17 @@ namespace ASC.FederatedLogin.LoginProviders public OAuth20Token GetAccessToken(string authCode) { - if (string.IsNullOrEmpty(authCode)) throw new ArgumentNullException("authCode"); + if (string.IsNullOrEmpty(authCode)) throw new ArgumentNullException(nameof(authCode)); if (string.IsNullOrEmpty(ClientID)) throw new ArgumentException("clientID"); if (string.IsNullOrEmpty(ClientSecret)) throw new ArgumentException("clientSecret"); - var data = string.Format("grant_type=authorization_code&code={0}", authCode); + var data = $"grant_type=authorization_code&code={authCode}"; var headers = new Dictionary { { "Authorization", AuthHeader } }; var json = RequestHelper.PerformRequest(AccessTokenUrl, "application/x-www-form-urlencoded", "POST", data, headers); if (json == null) throw new Exception("Can not get token"); - if (!json.StartsWith("{")) + if (!json.StartsWith('{')) { json = "{\"" + json.Replace("=", "\":\"").Replace("&", "\",\"") + "\"}"; } @@ -117,7 +117,7 @@ namespace ASC.FederatedLogin.LoginProviders if (string.IsNullOrEmpty(refreshToken) || string.IsNullOrEmpty(ClientID) || string.IsNullOrEmpty(ClientSecret)) throw new ArgumentException("Can not refresh given token"); - var data = string.Format("grant_type=refresh_token&refresh_token={0}", refreshToken); + var data = $"grant_type=refresh_token&refresh_token={refreshToken}"; var headers = new Dictionary { { "Authorization", AuthHeader } }; var json = RequestHelper.PerformRequest(AccessTokenUrl, "application/x-www-form-urlencoded", "POST", data, headers); diff --git a/common/ASC.FederatedLogin/LoginProviders/FacebookLoginProvider.cs b/common/ASC.FederatedLogin/LoginProviders/FacebookLoginProvider.cs index 8586df0b38..30d7d5590f 100644 --- a/common/ASC.FederatedLogin/LoginProviders/FacebookLoginProvider.cs +++ b/common/ASC.FederatedLogin/LoginProviders/FacebookLoginProvider.cs @@ -100,7 +100,7 @@ namespace ASC.FederatedLogin.LoginProviders TimeZone = jProfile.Value("timezone"), Locale = jProfile.Value("locale"), Provider = ProviderConstants.Facebook, - Avatar = string.Format("http://graph.facebook.com/{0}/picture?type=large", jProfile.Value("id")) + Avatar = "http://graph.facebook.com/" + jProfile.Value("id") + "/picture?type=large" }; return profile; diff --git a/common/ASC.FederatedLogin/LoginProviders/GoogleLoginProvider.cs b/common/ASC.FederatedLogin/LoginProviders/GoogleLoginProvider.cs index d52237aaaf..4447af379a 100644 --- a/common/ASC.FederatedLogin/LoginProviders/GoogleLoginProvider.cs +++ b/common/ASC.FederatedLogin/LoginProviders/GoogleLoginProvider.cs @@ -58,9 +58,9 @@ namespace ASC.FederatedLogin.LoginProviders public const string GoogleUrlProfile = "https://people.googleapis.com/v1/people/me"; public static readonly string[] GoogleDriveExt = new[] { ".gdoc", ".gsheet", ".gslides", ".gdraw" }; - public static string GoogleDriveMimeTypeFolder = "application/vnd.google-apps.folder"; - public static string FilesFields = "id,name,mimeType,parents,createdTime,modifiedTime,owners/displayName,lastModifyingUser/displayName,capabilities/canEdit,size"; - public static string ProfileFields = "emailAddresses,genders,names"; + public static readonly string GoogleDriveMimeTypeFolder = "application/vnd.google-apps.folder"; + public static readonly string FilesFields = "id,name,mimeType,parents,createdTime,modifiedTime,owners/displayName,lastModifyingUser/displayName,capabilities/canEdit,size"; + public static readonly string ProfileFields = "emailAddresses,genders,names"; public override string AccessTokenUrl { get { return "https://www.googleapis.com/oauth2/v4/token"; } } public override string CodeUrl { get { return "https://accounts.google.com/o/oauth2/v2/auth"; } } diff --git a/common/ASC.FederatedLogin/LoginProviders/GosUslugiLoginProvider.cs b/common/ASC.FederatedLogin/LoginProviders/GosUslugiLoginProvider.cs index a9e477a798..505932ddda 100644 --- a/common/ASC.FederatedLogin/LoginProviders/GosUslugiLoginProvider.cs +++ b/common/ASC.FederatedLogin/LoginProviders/GosUslugiLoginProvider.cs @@ -114,7 +114,7 @@ namespace ASC.FederatedLogin.LoginProviders } - public override LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs = null) + public override LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs) { try { diff --git a/common/ASC.FederatedLogin/LoginProviders/MailRuLoginProvider.cs b/common/ASC.FederatedLogin/LoginProviders/MailRuLoginProvider.cs index 6f73b71e5d..70678a26bc 100644 --- a/common/ASC.FederatedLogin/LoginProviders/MailRuLoginProvider.cs +++ b/common/ASC.FederatedLogin/LoginProviders/MailRuLoginProvider.cs @@ -97,7 +97,7 @@ namespace ASC.FederatedLogin.LoginProviders { } - public override LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs = null) + public override LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs) { try { diff --git a/common/ASC.FederatedLogin/LoginProviders/OpenIdLoginProvider.cs b/common/ASC.FederatedLogin/LoginProviders/OpenIdLoginProvider.cs index 285710cfdb..40edb0b444 100644 --- a/common/ASC.FederatedLogin/LoginProviders/OpenIdLoginProvider.cs +++ b/common/ASC.FederatedLogin/LoginProviders/OpenIdLoginProvider.cs @@ -53,7 +53,7 @@ namespace ASC.FederatedLogin.LoginProviders ConsumerFactory = consumerFactory; } - public LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs = null) + public LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs) { var response = Openid.GetResponse(); if (response == null) @@ -66,8 +66,7 @@ namespace ASC.FederatedLogin.LoginProviders var realmUrlString = string.Empty; - if (@params.ContainsKey("realmUrl")) - realmUrlString = @params["realmUrl"]; + @params.TryGetValue("realmUrl", out realmUrlString); if (!string.IsNullOrEmpty(realmUrlString)) request = Openid.CreateRequest(id, new Realm(realmUrlString)); @@ -123,8 +122,7 @@ namespace ASC.FederatedLogin.LoginProviders var fetchprofile = response.GetExtension(); var realmUrlString = string.Empty; - if (@params.ContainsKey("realmUrl")) - realmUrlString = @params["realmUrl"]; + @params.TryGetValue("realmUrl", out realmUrlString); var profile = ProfileFromOpenId(spprofile, fetchprofile, response.ClaimedIdentifier.ToString(), realmUrlString); return profile; diff --git a/common/ASC.FederatedLogin/LoginProviders/ProviderManager.cs b/common/ASC.FederatedLogin/LoginProviders/ProviderManager.cs index 97953837bc..3d1deb91ee 100644 --- a/common/ASC.FederatedLogin/LoginProviders/ProviderManager.cs +++ b/common/ASC.FederatedLogin/LoginProviders/ProviderManager.cs @@ -41,7 +41,7 @@ namespace ASC.FederatedLogin.LoginProviders [Scope] public class ProviderManager { - public static List AuthProviders = new List + public static readonly List AuthProviders = new List { ProviderConstants.Google, ProviderConstants.Facebook, @@ -79,7 +79,7 @@ namespace ASC.FederatedLogin.LoginProviders public LoginProfile GetLoginProfile(string providerType, string accessToken) { var consumer = GetLoginProvider(providerType); - if (consumer == null) throw new ArgumentException("Unknown provider type", "providerType"); + if (consumer == null) throw new ArgumentException("Unknown provider type", nameof(providerType)); try { diff --git a/common/ASC.FederatedLogin/LoginProviders/TelegramLoginProvider.cs b/common/ASC.FederatedLogin/LoginProviders/TelegramLoginProvider.cs index 3a86305340..a918e26014 100644 --- a/common/ASC.FederatedLogin/LoginProviders/TelegramLoginProvider.cs +++ b/common/ASC.FederatedLogin/LoginProviders/TelegramLoginProvider.cs @@ -83,7 +83,7 @@ namespace ASC.FederatedLogin.LoginProviders public bool ValidateKeys() { - if (TelegramBotToken == "") + if (TelegramBotToken.Length == 0) { TelegramHelper.DisableClient(TenantManager.GetCurrentTenant().TenantId); return true; diff --git a/common/ASC.FederatedLogin/LoginProviders/VKLoginProvider.cs b/common/ASC.FederatedLogin/LoginProviders/VKLoginProvider.cs index 1a4f6b9516..15450112c6 100644 --- a/common/ASC.FederatedLogin/LoginProviders/VKLoginProvider.cs +++ b/common/ASC.FederatedLogin/LoginProviders/VKLoginProvider.cs @@ -102,7 +102,7 @@ namespace ASC.FederatedLogin.LoginProviders } - public override LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs = null) + public override LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs) { try { diff --git a/common/ASC.FederatedLogin/LoginProviders/YandexLoginProvider.cs b/common/ASC.FederatedLogin/LoginProviders/YandexLoginProvider.cs index 96a96c4840..d803e38c5b 100644 --- a/common/ASC.FederatedLogin/LoginProviders/YandexLoginProvider.cs +++ b/common/ASC.FederatedLogin/LoginProviders/YandexLoginProvider.cs @@ -94,7 +94,7 @@ namespace ASC.FederatedLogin.LoginProviders { } - public override LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs = null) + public override LoginProfile ProcessAuthoriztion(HttpContext context, IDictionary @params, IDictionary additionalStateArgs) { try { diff --git a/common/ASC.FederatedLogin/MultiRegionAccountLinker.cs b/common/ASC.FederatedLogin/MultiRegionAccountLinker.cs index a689447b59..2a38655e77 100644 --- a/common/ASC.FederatedLogin/MultiRegionAccountLinker.cs +++ b/common/ASC.FederatedLogin/MultiRegionAccountLinker.cs @@ -48,7 +48,7 @@ namespace ASC.FederatedLogin databaseId = string.Join(".", new[] { _baseDatabaseId, hostedRegion.Trim() }); if (!_accountLinkers.ContainsKey(databaseId)) - throw new ArgumentException(string.Format("Region {0} is not defined", databaseId), "hostedRegion"); + throw new ArgumentException($"Region {databaseId} is not defined", nameof(hostedRegion)); return databaseId; } diff --git a/common/ASC.FederatedLogin/Profile/LoginProfile.cs b/common/ASC.FederatedLogin/Profile/LoginProfile.cs index 9a1f6911f8..af7b337aee 100644 --- a/common/ASC.FederatedLogin/Profile/LoginProfile.cs +++ b/common/ASC.FederatedLogin/Profile/LoginProfile.cs @@ -163,7 +163,7 @@ namespace ASC.FederatedLogin.Profile public string UniqueId { - get { return string.Format("{0}/{1}", Provider, Id); } + get { return $"{Provider}/{Id}"; } } public string HashId @@ -233,7 +233,7 @@ namespace ASC.FederatedLogin.Profile internal void SetField(string name, string value) { - if (name == null) throw new ArgumentNullException("name"); + if (name == null) throw new ArgumentNullException(nameof(name)); if (!string.IsNullOrEmpty(value)) { if (_fields.ContainsKey(name)) @@ -276,7 +276,7 @@ namespace ASC.FederatedLogin.Profile public static bool HasProfile(HttpRequest request) { - if (request == null) throw new ArgumentNullException("request"); + if (request == null) throw new ArgumentNullException(nameof(request)); return new Uri(request.GetDisplayUrl()).HasProfile(); } @@ -306,8 +306,7 @@ namespace ASC.FederatedLogin.Profile var query = new StringBuilder(); foreach (var key in queryString.AllKeys) { - query.AppendFormat("{0}={1}&", key, - queryString[key]); + query.Append($"{key}={queryString[key]}&"); } var builder = new UriBuilder(uri) { Query = query.ToString().TrimEnd('&') }; return builder.Uri; @@ -362,7 +361,7 @@ namespace ASC.FederatedLogin.Profile internal void FromSerializedString(string serialized) { - if (serialized == null) throw new ArgumentNullException("serialized"); + if (serialized == null) throw new ArgumentNullException(nameof(serialized)); _fields = serialized.Split(PairSeparator).ToDictionary(x => x.Split(KeyValueSeparator)[0], y => y.Split(KeyValueSeparator)[1]); } @@ -387,7 +386,7 @@ namespace ASC.FederatedLogin.Profile protected LoginProfile(Signature signature, InstanceCrypto instanceCrypto, SerializationInfo info) : this(signature, instanceCrypto) { if (info == null) - throw new ArgumentNullException("info"); + throw new ArgumentNullException(nameof(info)); var transformed = (string)info.GetValue(QueryParamName, typeof(string)); FromTransport(transformed); } diff --git a/common/ASC.FederatedLogin/Profile/WellKnownFields.cs b/common/ASC.FederatedLogin/Profile/WellKnownFields.cs index acce11684e..595cdaf358 100644 --- a/common/ASC.FederatedLogin/Profile/WellKnownFields.cs +++ b/common/ASC.FederatedLogin/Profile/WellKnownFields.cs @@ -26,7 +26,7 @@ namespace ASC.FederatedLogin.Profile { - public class WellKnownFields + public static class WellKnownFields { //Constants public const string Id = "Id"; diff --git a/common/ASC.Feed/Core/Constants.cs b/common/ASC.Feed/Core/Constants.cs index 11d9b1c529..eecbac306e 100644 --- a/common/ASC.Feed/Core/Constants.cs +++ b/common/ASC.Feed/Core/Constants.cs @@ -26,7 +26,7 @@ namespace ASC.Feed { - public class Constants + public static class Constants { public const string FeedDbId = "core"; public const string ProjectsDbId = "projects"; diff --git a/common/ASC.Feed/Core/Feed.cs b/common/ASC.Feed/Core/Feed.cs index 45e9a5aee2..9ee3ee7af7 100644 --- a/common/ASC.Feed/Core/Feed.cs +++ b/common/ASC.Feed/Core/Feed.cs @@ -53,7 +53,7 @@ namespace ASC.Feed.Aggregator public string Id { - get { return string.Format("{0}_{1}", Item, ItemId); } + get { return $"{Item}_{ItemId}"; } } public Guid AuthorId { get; private set; } diff --git a/common/ASC.Feed/Data/FeedAggregateDataProvider.cs b/common/ASC.Feed/Data/FeedAggregateDataProvider.cs index 5336453e10..134c1cc2cd 100644 --- a/common/ASC.Feed/Data/FeedAggregateDataProvider.cs +++ b/common/ASC.Feed/Data/FeedAggregateDataProvider.cs @@ -94,7 +94,7 @@ namespace ASC.Feed.Data SaveFeedsPortion(feedsPortion, aggregatedDate); feedsPortion.Clear(); } - if (feedsPortion.Any()) + if (feedsPortion.Count > 0) { SaveFeedsPortion(feedsPortion, aggregatedDate); } @@ -179,9 +179,9 @@ namespace ASC.Feed.Data feedsIteration = GetFeedsInternal(filter); foreach (var feed in feedsIteration) { - if (feeds.ContainsKey(feed.GroupId)) + if (feeds.TryGetValue(feed.GroupId, out var value)) { - feeds[feed.GroupId].Add(feed); + value.Add(feed); } else { diff --git a/common/ASC.IPSecurity/IPAddressRange.cs b/common/ASC.IPSecurity/IPAddressRange.cs index a9fa0caf1a..c98dbc9295 100644 --- a/common/ASC.IPSecurity/IPAddressRange.cs +++ b/common/ASC.IPSecurity/IPAddressRange.cs @@ -56,13 +56,18 @@ namespace ASC.IPSecurity for (var i = 0; i < lowerBytes.Length && (lowerBoundary || upperBoundary); i++) { - if ((lowerBoundary && addressBytes[i] < lowerBytes[i]) || (upperBoundary && addressBytes[i] > upperBytes[i])) + var addressByte = addressBytes[i]; + var upperByte = upperBytes[i]; + var lowerByte = lowerBytes[i]; + + + if ((lowerBoundary && addressByte < lowerByte) || (upperBoundary && addressByte > upperByte)) { return false; } - lowerBoundary &= (addressBytes[i] == lowerBytes[i]); - upperBoundary &= (addressBytes[i] == upperBytes[i]); + lowerBoundary &= addressByte == lowerByte; + upperBoundary &= addressByte == upperByte; } return true; diff --git a/common/ASC.IPSecurity/IPRestrictionsService.cs b/common/ASC.IPSecurity/IPRestrictionsService.cs index aa4d5483d1..3f459bf4df 100644 --- a/common/ASC.IPSecurity/IPRestrictionsService.cs +++ b/common/ASC.IPSecurity/IPRestrictionsService.cs @@ -77,7 +77,8 @@ namespace ASC.IPSecurity var restrictions = cache.Get>(key); if (restrictions == null) { - cache.Insert(key, restrictions = IPRestrictionsRepository.Get(tenant), timeout); + restrictions = IPRestrictionsRepository.Get(tenant); + cache.Insert(key, restrictions, timeout); } return restrictions; } diff --git a/common/ASC.IPSecurity/IPSecurity.cs b/common/ASC.IPSecurity/IPSecurity.cs index a9c2cea17c..0153b97949 100644 --- a/common/ASC.IPSecurity/IPSecurity.cs +++ b/common/ASC.IPSecurity/IPSecurity.cs @@ -79,7 +79,6 @@ namespace ASC.IPSecurity public bool Verify() { var tenant = TenantManager.GetCurrentTenant(); - var settings = SettingsManager.Load(); if (!IpSecurityEnabled) return true; @@ -92,16 +91,18 @@ namespace ASC.IPSecurity { var restrictions = IPRestrictionsService.Get(tenant.TenantId).ToList(); - if (!restrictions.Any()) return true; + if (restrictions.Count == 0) return true; - if (string.IsNullOrWhiteSpace(requestIps = CurrentIpForTest)) + requestIps = CurrentIpForTest; + + if (string.IsNullOrWhiteSpace(requestIps)) { var request = HttpContextAccessor.HttpContext.Request; requestIps = request.Headers["X-Forwarded-For"].FirstOrDefault() ?? request.GetUserHostAddress(); } var ips = string.IsNullOrWhiteSpace(requestIps) - ? new string[] { } + ? Array.Empty() : requestIps.Split(new[] { ",", " " }, StringSplitOptions.RemoveEmptyEntries); if (ips.Any(requestIp => restrictions.Any(restriction => MatchIPs(GetIpWithoutPort(requestIp), restriction.Ip)))) @@ -122,7 +123,7 @@ namespace ASC.IPSecurity private static bool MatchIPs(string requestIp, string restrictionIp) { var dividerIdx = restrictionIp.IndexOf('-'); - if (restrictionIp.IndexOf('-') > 0) + if (dividerIdx > -1) { var lower = IPAddress.Parse(restrictionIp.Substring(0, dividerIdx).Trim()); var upper = IPAddress.Parse(restrictionIp.Substring(dividerIdx + 1).Trim()); diff --git a/common/ASC.MessagingSystem/DbSender/MessagesRepository.cs b/common/ASC.MessagingSystem/DbSender/MessagesRepository.cs index 32bf2ca09b..1436632d11 100644 --- a/common/ASC.MessagingSystem/DbSender/MessagesRepository.cs +++ b/common/ASC.MessagingSystem/DbSender/MessagesRepository.cs @@ -50,7 +50,7 @@ namespace ASC.MessagingSystem.DbSender [Singletone(Additional = typeof(MessagesRepositoryExtension))] public class MessagesRepository: IDisposable { - private static DateTime lastSave = DateTime.UtcNow; + private DateTime lastSave = DateTime.UtcNow; private readonly TimeSpan CacheTime; private readonly IDictionary Cache; private Parser Parser { get; set; } @@ -133,9 +133,9 @@ namespace ASC.MessagingSystem.DbSender ClientInfo clientInfo; - if (dict.ContainsKey(message.UAHeader)) + if (dict.TryGetValue(message.UAHeader, out clientInfo)) { - clientInfo = dict[message.UAHeader]; + } else { @@ -181,7 +181,7 @@ namespace ASC.MessagingSystem.DbSender Action = (int)message.Action }; - if (message.Description != null && message.Description.Any()) + if (message.Description != null && message.Description.Count > 0) { le.Description = JsonConvert.SerializeObject(message.Description, new JsonSerializerSettings @@ -210,7 +210,7 @@ namespace ASC.MessagingSystem.DbSender Target = message.Target?.ToString() }; - if (message.Description != null && message.Description.Any()) + if (message.Description != null && message.Description.Count > 0) { ae.Description = JsonConvert.SerializeObject(GetSafeDescription(message.Description), new JsonSerializerSettings @@ -251,14 +251,14 @@ namespace ASC.MessagingSystem.DbSender { return clientInfo == null ? null - : string.Format("{0} {1}", clientInfo.UA.Family, clientInfo.UA.Major); + : $"{clientInfo.UA.Family} {clientInfo.UA.Major}"; } private static string GetPlatform(ClientInfo clientInfo) { return clientInfo == null ? null - : string.Format("{0} {1}", clientInfo.OS.Family, clientInfo.OS.Major); + : $"{clientInfo.OS.Family} {clientInfo.OS.Major}"; } public void Dispose() @@ -276,7 +276,7 @@ namespace ASC.MessagingSystem.DbSender public DbSet Tenants { get; set; } public DbSet WebstudioSettings { get; set; } } - public class MessagesRepositoryExtension + public static class MessagesRepositoryExtension { public static void Register(DIHelper services) { diff --git a/common/ASC.MessagingSystem/MessageFactory.cs b/common/ASC.MessagingSystem/MessageFactory.cs index 2bf1429307..4c54aa06a2 100644 --- a/common/ASC.MessagingSystem/MessageFactory.cs +++ b/common/ASC.MessagingSystem/MessageFactory.cs @@ -73,7 +73,7 @@ namespace ASC.MessagingSystem Action = action, Description = description, Target = target, - UAHeader = request.Headers[userAgentHeader].FirstOrDefault() + UAHeader = request?.Headers[userAgentHeader].FirstOrDefault() }; } catch (Exception ex) diff --git a/common/ASC.MessagingSystem/MessagePolicy.cs b/common/ASC.MessagingSystem/MessagePolicy.cs index 5ea1803eeb..8637aa30aa 100644 --- a/common/ASC.MessagingSystem/MessagePolicy.cs +++ b/common/ASC.MessagingSystem/MessagePolicy.cs @@ -43,7 +43,7 @@ namespace ASC.MessagingSystem { secretIps = configuration["messaging.secret-ips"] == null - ? new string[] { } + ? Array.Empty() : configuration["messaging.secret-ips"].Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries); } diff --git a/common/ASC.MessagingSystem/MessageTarget.cs b/common/ASC.MessagingSystem/MessageTarget.cs index c27d472045..ab8359fab2 100644 --- a/common/ASC.MessagingSystem/MessageTarget.cs +++ b/common/ASC.MessagingSystem/MessageTarget.cs @@ -99,7 +99,7 @@ namespace ASC.MessagingSystem var items = value.Split(','); - if (!items.Any()) return null; + if (items.Length == 0) return null; return new MessageTarget(Option) { diff --git a/common/ASC.Notify.Textile/JabberStyler.cs b/common/ASC.Notify.Textile/JabberStyler.cs index 5a4265e0d5..5ea7a7547e 100644 --- a/common/ASC.Notify.Textile/JabberStyler.cs +++ b/common/ASC.Notify.Textile/JabberStyler.cs @@ -25,6 +25,7 @@ using System; +using System.Text; using System.Text.RegularExpressions; using System.Web; @@ -48,22 +49,27 @@ namespace ASC.Notify.Textile public void ApplyFormating(NoticeMessage message) { - var body = string.Empty; + var sb = new StringBuilder(); if (!string.IsNullOrEmpty(message.Subject)) { - body += VelocityArguments.Replace(message.Subject, ArgMatchReplace) + Environment.NewLine; + sb.AppendLine(VelocityArguments.Replace(message.Subject, ArgMatchReplace)); message.Subject = string.Empty; } if (string.IsNullOrEmpty(message.Body)) return; var lines = message.Body.Split(new[] { Environment.NewLine, "\n" }, StringSplitOptions.None); + for (var i = 0; i < lines.Length - 1; i++) { - if (string.IsNullOrEmpty(lines[i])) { body += Environment.NewLine; continue; } - lines[i] = VelocityArguments.Replace(lines[i], ArgMatchReplace); - body += LinkReplacer.Replace(lines[i], EvalLink) + Environment.NewLine; + ref var line = ref lines[i]; + if (string.IsNullOrEmpty(line)) { sb.AppendLine(); continue; } + line = VelocityArguments.Replace(line, ArgMatchReplace); + sb.AppendLine(LinkReplacer.Replace(line, EvalLink)); } - lines[^1] = VelocityArguments.Replace(lines[^1], ArgMatchReplace); - body += LinkReplacer.Replace(lines[^1], EvalLink); + + ref var lastLine = ref lines[^1]; + lastLine = VelocityArguments.Replace(lastLine, ArgMatchReplace); + sb.Append(LinkReplacer.Replace(lastLine, EvalLink)); + var body = sb.ToString(); body = TextileReplacer.Replace(HttpUtility.HtmlDecode(body), ""); //Kill textile markup body = BrReplacer.Replace(body, Environment.NewLine); body = ClosedTagsReplacer.Replace(body, Environment.NewLine); @@ -72,7 +78,7 @@ namespace ASC.Notify.Textile message.Body = body; } - private static string EvalLink(Match match) + private string EvalLink(Match match) { if (match.Success) { @@ -82,13 +88,13 @@ namespace ASC.Notify.Textile { return " " + match.Groups["text"].Value + " "; } - return match.Groups["text"].Value + string.Format(" ( {0} )", match.Groups["link"].Value); + return match.Groups["text"].Value + $" ( {match.Groups["link"].Value} )"; } } return match.Value; } - private static string ArgMatchReplace(Match match) + private string ArgMatchReplace(Match match) { return match.Result("${arg}"); } diff --git a/common/ASC.Notify.Textile/TextileStyler.cs b/common/ASC.Notify.Textile/TextileStyler.cs index 1ba89b2610..baefd5ea3a 100644 --- a/common/ASC.Notify.Textile/TextileStyler.cs +++ b/common/ASC.Notify.Textile/TextileStyler.cs @@ -152,7 +152,7 @@ namespace ASC.Notify.Textile if (string.IsNullOrEmpty(logoImg)) { var logo = message.GetArgument("LetterLogo"); - if (logo != null && (string)logo.Value != "") + if (logo != null && ((string)logo.Value).Length != 0) { logoImg = (string)logo.Value; } @@ -173,7 +173,7 @@ namespace ASC.Notify.Textile if (string.IsNullOrEmpty(logoText)) { var llt = message.GetArgument("LetterLogoText"); - if (llt != null && (string)llt.Value != "") + if (llt != null && ((string)llt.Value).Length != 0) { logoText = (string)llt.Value; } @@ -299,7 +299,7 @@ namespace ASC.Notify.Textile private string GetSiteUnsubscribeLink(NoticeMessage message, MailWhiteLabelSettings settings) { - var mail = message.Recipient.Addresses.FirstOrDefault(r => r.Contains("@")); + var mail = message.Recipient.Addresses.FirstOrDefault(r => r.Contains('@')); if (string.IsNullOrEmpty(mail)) return string.Empty; diff --git a/common/ASC.Textile/Blocks/BlockAttributesParser.cs b/common/ASC.Textile/Blocks/BlockAttributesParser.cs index 56a2237a97..e0b5e11abf 100644 --- a/common/ASC.Textile/Blocks/BlockAttributesParser.cs +++ b/common/ASC.Textile/Blocks/BlockAttributesParser.cs @@ -17,7 +17,7 @@ using System.Text.RegularExpressions; namespace Textile.Blocks { - public class BlockAttributesParser + public static class BlockAttributesParser { public static StyleReader Styler { get; set; } @@ -45,7 +45,6 @@ namespace Textile.Blocks var colspan = string.Empty; var rowspan = string.Empty; var id = string.Empty; - var atts = string.Empty; if (Styler != null) { @@ -53,7 +52,7 @@ namespace Textile.Blocks } if (input.Length == 0) - return (style.Length > 0 ? " style=\"" + style + "\"" : ""); + return style.Length > 0 ? " style=\"" + style + "\"" : ""; Match m; @@ -134,14 +133,14 @@ namespace Textile.Blocks - return ( + return (style.Length > 0 ? " style=\"" + style + "\"" : "") + (cssClass.Length > 0 ? " class=\"" + cssClass + "\"" : "") + (lang.Length > 0 ? " lang=\"" + lang + "\"" : "") + (id.Length > 0 ? " id=\"" + id + "\"" : "") + (colspan.Length > 0 ? " colspan=\"" + colspan + "\"" : "") + (rowspan.Length > 0 ? " rowspan=\"" + rowspan + "\"" : "") - ); + ; } private static string GetStyle(string element, string style) diff --git a/common/ASC.Textile/Blocks/CapitalsBlockModifier.cs b/common/ASC.Textile/Blocks/CapitalsBlockModifier.cs index 546621a5bd..800d52cc0a 100644 --- a/common/ASC.Textile/Blocks/CapitalsBlockModifier.cs +++ b/common/ASC.Textile/Blocks/CapitalsBlockModifier.cs @@ -11,7 +11,7 @@ namespace Textile.Blocks return line; } - static private string CapitalsFormatMatchEvaluator(Match m) + private string CapitalsFormatMatchEvaluator(Match m) { return @"" + m.Groups["caps"].Value + @""; } diff --git a/common/ASC.Textile/Blocks/CodeBlockModifier.cs b/common/ASC.Textile/Blocks/CodeBlockModifier.cs index 476404a986..efb6e635ee 100644 --- a/common/ASC.Textile/Blocks/CodeBlockModifier.cs +++ b/common/ASC.Textile/Blocks/CodeBlockModifier.cs @@ -49,7 +49,7 @@ namespace Textile.Blocks return line; } - static public string CodeFormatMatchEvaluator(Match m) + public string CodeFormatMatchEvaluator(Match m) { var res = m.Groups["before"].Value + " 0) diff --git a/common/ASC.Textile/Blocks/GlyphBlockModifier.cs b/common/ASC.Textile/Blocks/GlyphBlockModifier.cs index 716707a299..24a9f2e408 100644 --- a/common/ASC.Textile/Blocks/GlyphBlockModifier.cs +++ b/common/ASC.Textile/Blocks/GlyphBlockModifier.cs @@ -11,6 +11,7 @@ #endregion #region Using Statements +using System.Text; using System.Text.RegularExpressions; #endregion @@ -39,7 +40,7 @@ namespace Textile.Blocks { @"\b ?[([](C|c)[])]", "©" } // copyright }; - var output = ""; + var sb = new StringBuilder(); if (!Regex.IsMatch(line, "<.*>")) { @@ -48,13 +49,14 @@ namespace Textile.Blocks { line = Regex.Replace(line, glyphs[i, 0], glyphs[i, 1]); } - output = line; + sb.Append(line); } else { var splits = Regex.Split(line, "(<.*?>)"); var offtags = "code|pre|notextile"; var codepre = false; + foreach (var split in splits) { var modifiedSplit = split; @@ -75,18 +77,18 @@ namespace Textile.Blocks } // do htmlspecial if between - if (codepre == true) + if (codepre) { //TODO: htmlspecialchars(line) //line = Regex.Replace(line, @"<(\/?" + offtags + ")>", "<$1>"); //line = line.Replace("&#", "&#"); } - output += modifiedSplit; + sb.Append(modifiedSplit); } } - return output; + return sb.ToString(); } } } diff --git a/common/ASC.Textile/Blocks/HyperLinkBlockModifier.cs b/common/ASC.Textile/Blocks/HyperLinkBlockModifier.cs index a44dbe5d35..dab812c2ac 100644 --- a/common/ASC.Textile/Blocks/HyperLinkBlockModifier.cs +++ b/common/ASC.Textile/Blocks/HyperLinkBlockModifier.cs @@ -33,7 +33,7 @@ namespace Textile.Blocks @"\s?" + @"(?:\((?[^)]+)\)(?=""))?" + // title "\":" + - string.Format(@"""(?<url>\S+[^""]+)""", Regex.Escape(@"a-zA-Z:/.-{}?&_%#+=@")) + // url + @"""(?<url>\S+[^""]+)""" + // url @"(?<slash>\/)?" + // slash @"(?<post>[^\w\/;]*)" + // post @"(?=\s|$)", diff --git a/common/ASC.Textile/Blocks/ImageBlockModifier.cs b/common/ASC.Textile/Blocks/ImageBlockModifier.cs index a000ef4f76..b5ea663f66 100644 --- a/common/ASC.Textile/Blocks/ImageBlockModifier.cs +++ b/common/ASC.Textile/Blocks/ImageBlockModifier.cs @@ -36,7 +36,7 @@ namespace Textile.Blocks return line; } - static string ImageFormatMatchEvaluator(Match m) + string ImageFormatMatchEvaluator(Match m) { var atts = BlockAttributesParser.ParseBlockAttributes(m.Groups["atts"].Value, "img"); if (m.Groups["algn"].Length > 0) diff --git a/common/ASC.Textile/Blocks/NoTextileEncoder.cs b/common/ASC.Textile/Blocks/NoTextileEncoder.cs index 0da996cb69..7f717ee980 100644 --- a/common/ASC.Textile/Blocks/NoTextileEncoder.cs +++ b/common/ASC.Textile/Blocks/NoTextileEncoder.cs @@ -39,7 +39,7 @@ namespace Textile.Blocks string evaluator(Match m) { var toEncode = m.Groups["notex"].Value; - if (toEncode == string.Empty) + if (toEncode.Length == 0) { return string.Empty; } @@ -52,7 +52,7 @@ namespace Textile.Blocks } return patternPrefix + toEncode + patternSuffix; } - tmp = Regex.Replace(tmp, string.Format("({0}(?<notex>.+?){1})*", patternPrefix, patternSuffix), new MatchEvaluator(evaluator)); + tmp = Regex.Replace(tmp, "("+ patternPrefix + "(?<notex>.+?)" + patternSuffix + ")*", new MatchEvaluator(evaluator)); return tmp; } @@ -75,7 +75,7 @@ namespace Textile.Blocks } return toEncode; } - tmp = Regex.Replace(tmp, string.Format("({0}(?<notex>.+?){1})*", patternPrefix, patternSuffix), new MatchEvaluator(evaluator)); + tmp = Regex.Replace(tmp, "(" + patternPrefix + "(?<notex>.+?)" + patternSuffix + ")*", new MatchEvaluator(evaluator)); return tmp; } } diff --git a/common/ASC.Textile/Blocks/PhraseBlockModifier.cs b/common/ASC.Textile/Blocks/PhraseBlockModifier.cs index b789f9fb30..d77e9993f8 100644 --- a/common/ASC.Textile/Blocks/PhraseBlockModifier.cs +++ b/common/ASC.Textile/Blocks/PhraseBlockModifier.cs @@ -35,7 +35,7 @@ namespace Textile.Blocks else if (modifier.Length == 2) { if (modifier[0] != '\\') - compressedModifier = modifier.Substring(0, 1); + compressedModifier = modifier[0].ToString(); //else: compressedModifier = modifier; } //else: compressedModifier = modifier; @@ -61,7 +61,7 @@ namespace Textile.Blocks return res; } - private class PhraseModifierMatchEvaluator + private sealed class PhraseModifierMatchEvaluator { readonly string m_tag; diff --git a/common/ASC.Textile/FormatterState.cs b/common/ASC.Textile/FormatterState.cs index c51cdb3f7c..b65085b095 100644 --- a/common/ASC.Textile/FormatterState.cs +++ b/common/ASC.Textile/FormatterState.cs @@ -36,7 +36,7 @@ namespace Textile /// Public constructor. /// </summary> /// <param name="f">The parent formatter.</param> - public FormatterState(TextileFormatter formatter) + protected FormatterState(TextileFormatter formatter) { Formatter = formatter; } diff --git a/common/ASC.Textile/Globals.cs b/common/ASC.Textile/Globals.cs index 89dc5eca1c..34dfea0f2d 100644 --- a/common/ASC.Textile/Globals.cs +++ b/common/ASC.Textile/Globals.cs @@ -20,7 +20,7 @@ namespace Textile /// <summary> /// A utility class for global things used by the TextileFormatter. /// </summary> - class Globals + static class Globals { #region Global Regex Patterns @@ -44,44 +44,29 @@ namespace Textile #endregion - private static Dictionary<string, string> m_imageAlign; /// <summary> /// Image alignment tags, mapped to their HTML meanings. /// </summary> - public static Dictionary<string, string> ImageAlign - { - get { return Globals.m_imageAlign; } - set { Globals.m_imageAlign = value; } - } - private static Dictionary<string, string> m_horizontalAlign; + public static Dictionary<string, string> ImageAlign { get; set; } /// <summary> /// Horizontal text alignment tags, mapped to their HTML meanings. /// </summary> - public static Dictionary<string, string> HorizontalAlign - { - get { return Globals.m_horizontalAlign; } - set { Globals.m_horizontalAlign = value; } - } - private static Dictionary<string, string> m_verticalAlign; + public static Dictionary<string, string> HorizontalAlign { get; set; } /// <summary> /// Vertical text alignment tags, mapped to their HTML meanings. /// </summary> - public static Dictionary<string, string> VerticalAlign - { - get { return Globals.m_verticalAlign; } - set { Globals.m_verticalAlign = value; } - } + public static Dictionary<string, string> VerticalAlign { get; set;} static Globals() { - m_imageAlign = new Dictionary<string, string> + ImageAlign = new Dictionary<string, string> { ["<"] = "left", ["="] = "center", [">"] = "right" }; - m_horizontalAlign = new Dictionary<string, string> + HorizontalAlign = new Dictionary<string, string> { ["<"] = "left", ["="] = "center", @@ -89,7 +74,7 @@ namespace Textile ["<>"] = "justify" }; - m_verticalAlign = new Dictionary<string, string> + VerticalAlign = new Dictionary<string, string> { ["^"] = "top", ["-"] = "middle", diff --git a/common/ASC.Textile/States/HeaderFormatterState.cs b/common/ASC.Textile/States/HeaderFormatterState.cs index debabe18c7..0f091116b1 100644 --- a/common/ASC.Textile/States/HeaderFormatterState.cs +++ b/common/ASC.Textile/States/HeaderFormatterState.cs @@ -32,7 +32,7 @@ namespace Textile.States { for (var i = 0; i < HeaderLevel; i++) { - Formatter.Output.Write(string.Format("<br {0}/>", FormattedStylesAndAlignment("br"))); + Formatter.Output.Write($"<br {FormattedStylesAndAlignment("br")}/>"); } } @@ -77,12 +77,12 @@ namespace Textile.States public override void Enter() { - Formatter.Output.Write(string.Format("<h{0}{1}>", HeaderLevel, FormattedStylesAndAlignment(string.Format("h{0}", HeaderLevel)))); + Formatter.Output.Write("<h" + HeaderLevel + FormattedStylesAndAlignment("h" + HeaderLevel) + ">"); } public override void Exit() { - Formatter.Output.WriteLine(string.Format("</h{0}>", HeaderLevel.ToString())); + Formatter.Output.WriteLine("</h" + HeaderLevel + ">"); } protected override void OnContextAcquired() diff --git a/common/ASC.Textile/States/ListFormatterState.cs b/common/ASC.Textile/States/ListFormatterState.cs index fba026681b..fbeaef8518 100644 --- a/common/ASC.Textile/States/ListFormatterState.cs +++ b/common/ASC.Textile/States/ListFormatterState.cs @@ -36,7 +36,7 @@ namespace Textile.States get { return m_tag.Length; } } - public ListFormatterState(TextileFormatter formatter) + protected ListFormatterState(TextileFormatter formatter) : base(formatter) { } @@ -72,7 +72,7 @@ namespace Textile.States { if (!m_firstItem) Formatter.Output.WriteLine("</li>"); - Formatter.Output.Write(string.Format("<li {0}>", FormattedStylesAndAlignment("li"))); + Formatter.Output.Write("<li " + FormattedStylesAndAlignment("li") + ">"); m_firstItemLine = false; } else @@ -86,7 +86,7 @@ namespace Textile.States public sealed override bool ShouldNestState(FormatterState other) { var listState = (ListFormatterState)other; - return (listState.NestingDepth > NestingDepth); + return listState.NestingDepth > NestingDepth; } public sealed override bool ShouldExit(string input) diff --git a/common/ASC.Textile/States/SimpleBlockFormatterState.cs b/common/ASC.Textile/States/SimpleBlockFormatterState.cs index 2a494b36e0..b1a0a84905 100644 --- a/common/ASC.Textile/States/SimpleBlockFormatterState.cs +++ b/common/ASC.Textile/States/SimpleBlockFormatterState.cs @@ -35,9 +35,9 @@ namespace Textile.States public override bool ShouldNestState(FormatterState other) { var blockFormatterState = (SimpleBlockFormatterState)other; - return (blockFormatterState.Tag != Tag || + return blockFormatterState.Tag != Tag || blockFormatterState.AlignInfo != AlignInfo || - blockFormatterState.AttInfo != AttInfo); + blockFormatterState.AttInfo != AttInfo; } protected virtual void OnContextAcquired() diff --git a/common/ASC.Textile/States/TableFormatterState.cs b/common/ASC.Textile/States/TableFormatterState.cs index e60dd91b58..ca6aafed00 100644 --- a/common/ASC.Textile/States/TableFormatterState.cs +++ b/common/ASC.Textile/States/TableFormatterState.cs @@ -58,7 +58,7 @@ namespace Textile.States @"(\.\s?)?(?<tag>\|)" + @"(?<content>.*)(?=\|)" ); - return (m.Success == false); + return !m.Success; } protected string FormattedStylesAndAlignment() diff --git a/common/ASC.Textile/States/TableRowFormatterState.cs b/common/ASC.Textile/States/TableRowFormatterState.cs index d2628dddc7..247b08dcf8 100644 --- a/common/ASC.Textile/States/TableRowFormatterState.cs +++ b/common/ASC.Textile/States/TableRowFormatterState.cs @@ -1,3 +1,4 @@ +using System.Text; using System.Text.RegularExpressions; namespace Textile.States @@ -18,7 +19,7 @@ namespace Textile.States { m_alignInfo = m.Groups["align"].Value; m_attsInfo = m.Groups["atts"].Value; - input = string.Format("|{0}|", m.Groups["content"].Value); + input = "|" + m.Groups["content"].Value + "|"; if (!(this.Formatter.CurrentState is TableFormatterState)) { @@ -50,17 +51,16 @@ namespace Textile.States { // can get: Align & Classes - var formattedLine = ""; - + var sb = new StringBuilder(); var cellsInput = input.Split('|'); for (var i = 1; i < cellsInput.Length - 1; i++) { var cellInput = cellsInput[i]; var tcp = new TableCellParser(cellInput); - formattedLine += tcp.GetLineFragmentFormatting(); + sb.Append(tcp.GetLineFragmentFormatting()); } - Formatter.Output.WriteLine(formattedLine); + Formatter.Output.WriteLine(sb.ToString()); } public override bool ShouldExit(string input) diff --git a/common/ASC.VoipService/Dao/AbstractDao.cs b/common/ASC.VoipService/Dao/AbstractDao.cs index 61b3602ff4..a051f4fb6a 100644 --- a/common/ASC.VoipService/Dao/AbstractDao.cs +++ b/common/ASC.VoipService/Dao/AbstractDao.cs @@ -54,7 +54,7 @@ namespace ASC.VoipService.Dao protected string GetTenantColumnName(string table) { const string tenant = "tenant_id"; - if (!table.Contains(" ")) return tenant; + if (!table.Contains(' ')) return tenant; return table.Substring(table.IndexOf(" ", StringComparison.Ordinal)).Trim() + "." + tenant; } diff --git a/common/ASC.VoipService/Dao/CachedVoipDao.cs b/common/ASC.VoipService/Dao/CachedVoipDao.cs index 0a39bf0031..47b4f8566f 100644 --- a/common/ASC.VoipService/Dao/CachedVoipDao.cs +++ b/common/ASC.VoipService/Dao/CachedVoipDao.cs @@ -104,7 +104,7 @@ namespace ASC.VoipService.Dao cache.Insert(GetCacheKey(TenantID), numbers, DateTime.UtcNow.Add(timeout)); } - return ids.Any() ? numbers.Where(r => ids.Contains(r.Id) || ids.Contains(r.Number)).ToList() : numbers; + return ids.Length > 0 ? numbers.Where(r => ids.Contains(r.Id) || ids.Contains(r.Number)).ToList() : numbers; } public static string GetCacheKey(int tenant) diff --git a/common/ASC.VoipService/Dao/VoIPCallFilter.cs b/common/ASC.VoipService/Dao/VoIPCallFilter.cs index efd8e8a9d7..96947f5e27 100644 --- a/common/ASC.VoipService/Dao/VoIPCallFilter.cs +++ b/common/ASC.VoipService/Dao/VoIPCallFilter.cs @@ -62,7 +62,7 @@ namespace ASC.VoipService.Dao get { if (string.IsNullOrWhiteSpace(Type)) return null; - if (TypeStatuses.ContainsKey(Type)) return TypeStatuses[Type]; + if (TypeStatuses.TryGetValue(Type, out var status)) return status; return null; } diff --git a/common/ASC.VoipService/Dao/VoipDao.cs b/common/ASC.VoipService/Dao/VoipDao.cs index f28f7792b6..bb025abcaa 100644 --- a/common/ASC.VoipService/Dao/VoipDao.cs +++ b/common/ASC.VoipService/Dao/VoipDao.cs @@ -101,7 +101,7 @@ namespace ASC.VoipService.Dao { var numbers = VoipDbContext.VoipNumbers.Where(r => r.TenantId == TenantID); - if (ids.Any()) + if (ids.Length > 0) { numbers = numbers.Where(r => ids.Any(a => a == r.Number || a == r.Id)); } @@ -343,7 +343,7 @@ namespace ASC.VoipService.Dao { call.ContactTitle = call.ContactIsCompany ? dbVoipCall.CrmContact.CompanyName - : dbVoipCall.CrmContact.FirstName == null || dbVoipCall.CrmContact.LastName == null ? null : string.Format("{0} {1}", dbVoipCall.CrmContact.FirstName, dbVoipCall.CrmContact.LastName); + : dbVoipCall.CrmContact.FirstName == null || dbVoipCall.CrmContact.LastName == null ? null : $"{dbVoipCall.CrmContact.FirstName} {dbVoipCall.CrmContact.LastName}"; } return call; diff --git a/common/ASC.VoipService/Twilio/TwilioProvider.cs b/common/ASC.VoipService/Twilio/TwilioProvider.cs index d2ee57c930..533e698b57 100644 --- a/common/ASC.VoipService/Twilio/TwilioProvider.cs +++ b/common/ASC.VoipService/Twilio/TwilioProvider.cs @@ -60,8 +60,8 @@ namespace ASC.VoipService.Twilio public TwilioProvider(string accountSid, string authToken, AuthContext authContext, TenantUtil tenantUtil, SecurityContext securityContext, BaseCommonLinkUtility baseCommonLinkUtility) { - if (string.IsNullOrEmpty(accountSid)) throw new ArgumentNullException("accountSid"); - if (string.IsNullOrEmpty(authToken)) throw new ArgumentNullException("authToken"); + if (string.IsNullOrEmpty(accountSid)) throw new ArgumentNullException(nameof(accountSid)); + if (string.IsNullOrEmpty(authToken)) throw new ArgumentNullException(nameof(authToken)); this.authToken = authToken; AuthContext = authContext; diff --git a/common/ASC.VoipService/VoipModel.cs b/common/ASC.VoipService/VoipModel.cs index 035cc31388..13c4b5498a 100644 --- a/common/ASC.VoipService/VoipModel.cs +++ b/common/ASC.VoipService/VoipModel.cs @@ -90,7 +90,7 @@ namespace ASC.VoipService } } - public class WorkingHours + public sealed class WorkingHours { public bool Enabled { get; set; } public TimeSpan? From { get; set; } @@ -105,7 +105,7 @@ namespace ASC.VoipService } - protected bool Equals(WorkingHours other) + private bool Equals(WorkingHours other) { return Enabled.Equals(other.Enabled) && From.Equals(other.From) && To.Equals(other.To); } diff --git a/common/ASC.Webhooks.Core/ASC.Webhooks.Core.csproj b/common/ASC.Webhooks.Core/ASC.Webhooks.Core.csproj index fae7e9e936..5aa604c97e 100644 --- a/common/ASC.Webhooks.Core/ASC.Webhooks.Core.csproj +++ b/common/ASC.Webhooks.Core/ASC.Webhooks.Core.csproj @@ -1,12 +1,7 @@ -<Project Sdk="Microsoft.NET.Sdk.Web"> +<Project Sdk="Microsoft.NET.Sdk"> <PropertyGroup> <TargetFramework>net6.0</TargetFramework> - <IsPackable>false</IsPackable> - <DefaultItemExcludes>$(DefaultItemExcludes);</DefaultItemExcludes> - <RazorCompileOnBuild>false</RazorCompileOnBuild> - <GenerateMvcApplicationPartsAssemblyAttributes>false</GenerateMvcApplicationPartsAssemblyAttributes> - <OutputType>Library</OutputType> </PropertyGroup> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|AnyCPU'"> @@ -33,4 +28,8 @@ <Protobuf Include="proto\webhook_request.proto" /> </ItemGroup> + <ItemGroup> + <Folder Include="Properties\" /> + </ItemGroup> + </Project> diff --git a/common/services/ASC.ApiSystem/Classes/AuthHandler.cs b/common/services/ASC.ApiSystem/Classes/AuthHandler.cs index d3119f2701..e1763c18cb 100644 --- a/common/services/ASC.ApiSystem/Classes/AuthHandler.cs +++ b/common/services/ASC.ApiSystem/Classes/AuthHandler.cs @@ -105,7 +105,7 @@ namespace ASC.ApiSystem.Classes { Log.Debug("Auth header is NULL"); - return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(HttpStatusCode.Unauthorized.ToString()))); + return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(nameof(HttpStatusCode.Unauthorized)))); } var substring = "ASC"; @@ -118,7 +118,7 @@ namespace ASC.ApiSystem.Classes { Log.DebugFormat("Auth failed: invalid token {0}.", header); - return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(HttpStatusCode.Unauthorized.ToString()))); + return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(nameof(HttpStatusCode.Unauthorized)))); } var pkey = splitted[0]; @@ -137,7 +137,7 @@ namespace ASC.ApiSystem.Classes { Log.DebugFormat("Auth failed: invalid timesatmp {0}, now {1}.", timestamp, DateTime.UtcNow); - return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(HttpStatusCode.Forbidden.ToString()))); + return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(nameof(HttpStatusCode.Forbidden)))); } } @@ -150,21 +150,21 @@ namespace ASC.ApiSystem.Classes { Log.DebugFormat("Auth failed: invalid token {0}, expect {1} or {2}.", orighash, WebEncoders.Base64UrlEncode(hash), Convert.ToBase64String(hash)); - return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(HttpStatusCode.Forbidden.ToString()))); + return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(nameof(HttpStatusCode.Forbidden)))); } } else { Log.DebugFormat("Auth failed: invalid auth header. Sheme: {0}, parameter: {1}.", Scheme.Name, header); - return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(HttpStatusCode.Forbidden.ToString()))); + return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(nameof(HttpStatusCode.Forbidden)))); } } catch (Exception ex) { Log.Error(ex); - return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(HttpStatusCode.InternalServerError.ToString()))); + return Task.FromResult(AuthenticateResult.Fail(new AuthenticationException(nameof(HttpStatusCode.InternalServerError)))); } var identity = new ClaimsIdentity( Scheme.Name); diff --git a/common/services/ASC.ApiSystem/Classes/CommonConstants.cs b/common/services/ASC.ApiSystem/Classes/CommonConstants.cs index 66abd3d46a..2ffa9c4f3b 100644 --- a/common/services/ASC.ApiSystem/Classes/CommonConstants.cs +++ b/common/services/ASC.ApiSystem/Classes/CommonConstants.cs @@ -61,9 +61,9 @@ namespace ASC.ApiSystem.Classes MaxAttemptsCount = Convert.ToInt32(configuration["max-attempts-count"] ?? "10"); - MaxAttemptsTimeInterval = TimeSpan.Parse(Convert.ToString(configuration["max-attempts-interval"] ?? "00:05:00")); + MaxAttemptsTimeInterval = TimeSpan.Parse(configuration["max-attempts-interval"] ?? "00:05:00"); - WebApiBaseUrl = Convert.ToString(configuration["api:url"] ?? "/api/2.0/"); + WebApiBaseUrl = configuration["api:url"] ?? "/api/2.0/"; } diff --git a/common/services/ASC.ApiSystem/Classes/CommonMethods.cs b/common/services/ASC.ApiSystem/Classes/CommonMethods.cs index 19b38fe1f8..5e25c014fe 100644 --- a/common/services/ASC.ApiSystem/Classes/CommonMethods.cs +++ b/common/services/ASC.ApiSystem/Classes/CommonMethods.cs @@ -28,32 +28,32 @@ using System; using System.Collections.Generic; using System.Diagnostics; using System.IO; -using System.Net.Http; -using System.Net.Http.Headers; +using System.Net.Http; +using System.Net.Http.Headers; using System.Text; using System.Text.RegularExpressions; - + using ASC.ApiSystem.Classes; using ASC.ApiSystem.Interfaces; using ASC.ApiSystem.Models; -using ASC.Common; +using ASC.Common; using ASC.Common.Logging; using ASC.Common.Utils; using ASC.Core; using ASC.Core.Tenants; using ASC.Security.Cryptography; using ASC.Web.Studio.Utility; - + using Microsoft.AspNetCore.Http; using Microsoft.Extensions.Caching.Memory; using Microsoft.Extensions.Configuration; using Microsoft.Extensions.Options; - + using Newtonsoft.Json.Linq; namespace ASC.ApiSystem.Controllers -{ +{ [Scope] public class CommonMethods { @@ -75,24 +75,27 @@ namespace ASC.ApiSystem.Controllers private HostedSolution HostedSolution { get; } - private IMemoryCache MemoryCache { get; } - - private CoreBaseSettings CoreBaseSettings { get; } - - private TenantManager TenantManager { get; } - - public CommonMethods( - IHttpContextAccessor httpContextAccessor, - IConfiguration configuration, - IOptionsMonitor<ILog> option, - CoreSettings coreSettings, - CommonLinkUtility commonLinkUtility, - EmailValidationKeyProvider emailValidationKeyProvider, - TimeZoneConverter timeZoneConverter, CommonConstants commonConstants, - IMemoryCache memoryCache, - IOptionsSnapshot<HostedSolution> hostedSolutionOptions, - CoreBaseSettings coreBaseSettings, - TenantManager tenantManager) + private IMemoryCache MemoryCache { get; } + + private CoreBaseSettings CoreBaseSettings { get; } + + private TenantManager TenantManager { get; } + + private IHttpClientFactory ClientFactory { get; } + + public CommonMethods( + IHttpContextAccessor httpContextAccessor, + IConfiguration configuration, + IOptionsMonitor<ILog> option, + CoreSettings coreSettings, + CommonLinkUtility commonLinkUtility, + EmailValidationKeyProvider emailValidationKeyProvider, + TimeZoneConverter timeZoneConverter, CommonConstants commonConstants, + IMemoryCache memoryCache, + IOptionsSnapshot<HostedSolution> hostedSolutionOptions, + CoreBaseSettings coreBaseSettings, + TenantManager tenantManager, + IHttpClientFactory clientFactory) { HttpContextAccessor = httpContextAccessor; @@ -110,9 +113,14 @@ namespace ASC.ApiSystem.Controllers CommonConstants = commonConstants; - MemoryCache = memoryCache; - CoreBaseSettings = coreBaseSettings; - TenantManager = tenantManager; + MemoryCache = memoryCache; + + CoreBaseSettings = coreBaseSettings; + + TenantManager = tenantManager; + + ClientFactory = clientFactory; + HostedSolution = hostedSolutionOptions.Get(CommonConstants.BaseDbConnKeyString); } @@ -139,16 +147,8 @@ namespace ASC.ApiSystem.Controllers public string CreateReference(string requestUriScheme, string tenantDomain, string email, bool first = false, string module = "", bool sms = false) { - return string.Format("{0}{1}{2}/{3}{4}{5}{6}", - requestUriScheme, - Uri.SchemeDelimiter, - tenantDomain, - CommonLinkUtility.GetConfirmationUrlRelative(email, ConfirmType.Auth, (first ? "true" : "") + module + (sms ? "true" : "")), - first ? "&first=true" : "", - string.IsNullOrEmpty(module) ? "" : "&module=" + module, - sms ? "&sms=true" : "" - - ); + var url = CommonLinkUtility.GetConfirmationUrlRelative(email, ConfirmType.Auth, (first ? "true" : "") + module + (sms ? "true" : "")); + return $"{requestUriScheme}{Uri.SchemeDelimiter}{tenantDomain}/{url}{(first ? "&first=true" : "")}{(string.IsNullOrEmpty(module) ? "" : "&module=" + module)}{(sms ? "&sms=true" : "")}"; } public bool SendCongratulations(string requestUriScheme, Tenant tenant, bool skipWelcome, out string url) @@ -169,15 +169,15 @@ namespace ASC.ApiSystem.Controllers Log.DebugFormat("congratulations skiped"); return false; } - - var request = new HttpRequestMessage(); - request.Method = HttpMethod.Post; + + var request = new HttpRequestMessage(); + request.Method = HttpMethod.Post; request.Headers.Accept.Add(MediaTypeWithQualityHeaderValue.Parse("application/x-www-form-urlencoded")); try - { - using var httpClient = new HttpClient(); - using var response = httpClient.Send(request); + { + var httpClient = ClientFactory.CreateClient(); + using var response = httpClient.Send(request); using var stream = response.Content.ReadAsStream(); using var reader = new StreamReader(stream, Encoding.UTF8); @@ -203,12 +203,12 @@ namespace ASC.ApiSystem.Controllers } public bool GetTenant(IModel model, out Tenant tenant) - { - if (CoreBaseSettings.Standalone && model != null && !string.IsNullOrEmpty((model.PortalName ?? "").Trim())) - { - tenant = TenantManager.GetTenant((model.PortalName ?? "").Trim()); - return true; - } + { + if (CoreBaseSettings.Standalone && model != null && !string.IsNullOrWhiteSpace((model.PortalName ?? ""))) + { + tenant = TenantManager.GetTenant((model.PortalName ?? "").Trim()); + return true; + } if (model != null && model.TenantId.HasValue) { @@ -216,7 +216,7 @@ namespace ASC.ApiSystem.Controllers return true; } - if (model != null && !string.IsNullOrEmpty((model.PortalName ?? "").Trim())) + if (model != null && !string.IsNullOrWhiteSpace((model.PortalName ?? ""))) { tenant = HostedSolution.GetTenant((model.PortalName ?? "").Trim()); return true; @@ -227,13 +227,13 @@ namespace ASC.ApiSystem.Controllers } public bool IsTestEmail(string email) - { - //the point is not needed in gmail.com - email = Regex.Replace(email ?? "", "\\.*(?=\\S*(@gmail.com$))", "").ToLower(); - if (string.IsNullOrEmpty(email) || string.IsNullOrEmpty(CommonConstants.AutotestSecretEmails)) - return false; - - var regex = new Regex(CommonConstants.AutotestSecretEmails, RegexOptions.IgnoreCase | RegexOptions.Singleline | RegexOptions.Compiled); + { + //the point is not needed in gmail.com + email = Regex.Replace(email ?? "", "\\.*(?=\\S*(@gmail.com$))", "").ToLower(); + if (string.IsNullOrEmpty(email) || string.IsNullOrEmpty(CommonConstants.AutotestSecretEmails)) + return false; + + var regex = new Regex(CommonConstants.AutotestSecretEmails, RegexOptions.IgnoreCase | RegexOptions.Singleline | RegexOptions.Compiled); return regex.IsMatch(email); } @@ -252,11 +252,11 @@ namespace ASC.ApiSystem.Controllers ipAttemptsCount++; - MemoryCache.Set( - // String that represents the name of the cache item, - // could be any string - cacheKey, - // Something to store in the cache + MemoryCache.Set( + // String that represents the name of the cache item, + // could be any string + cacheKey, + // Something to store in the cache ipAttemptsCount, new MemoryCacheEntryOptions { @@ -301,33 +301,33 @@ namespace ASC.ApiSystem.Controllers public bool ValidateRecaptcha(string response, RecaptchaType recaptchaType, string ip) { try - { - string privateKey; - switch (recaptchaType) - { - case RecaptchaType.AndroidV2: - privateKey = Configuration["recaptcha:private-key:android"]; - break; - case RecaptchaType.iOSV2: - privateKey = Configuration["recaptcha:private-key:ios"]; - break; - default: - privateKey = Configuration["recaptcha:private-key"]; - break; - } - - var data = string.Format("secret={0}&remoteip={1}&response={2}", privateKey, ip, response); + { + string privateKey; + switch (recaptchaType) + { + case RecaptchaType.AndroidV2: + privateKey = Configuration["recaptcha:private-key:android"]; + break; + case RecaptchaType.iOSV2: + privateKey = Configuration["recaptcha:private-key:ios"]; + break; + default: + privateKey = Configuration["recaptcha:private-key"]; + break; + } + + var data = $"secret={privateKey}&remoteip={ip}&response={response}"; var url = Configuration["recaptcha:verify-url"] ?? "https://www.recaptcha.net/recaptcha/api/siteverify"; - - var request = new HttpRequestMessage(); - request.RequestUri = new Uri(url); - request.Method = HttpMethod.Post; + + var request = new HttpRequestMessage(); + request.RequestUri = new Uri(url); + request.Method = HttpMethod.Post; request.Content = new StringContent(data, Encoding.UTF8, "application/x-www-form-urlencoded"); - - using var httpClient = new HttpClient(); - using var httpClientResponse = httpClient.Send(request); + + var httpClient = ClientFactory.CreateClient(); + using var httpClientResponse = httpClient.Send(request); using var stream = httpClientResponse.Content.ReadAsStream(); - using var reader = new StreamReader(stream); + using var reader = new StreamReader(stream); var resp = reader.ReadToEnd(); var resObj = JObject.Parse(resp); diff --git a/common/services/ASC.ApiSystem/Controllers/CalDavController.cs b/common/services/ASC.ApiSystem/Controllers/CalDavController.cs index 0bd087230b..35b1e90784 100644 --- a/common/services/ASC.ApiSystem/Controllers/CalDavController.cs +++ b/common/services/ASC.ApiSystem/Controllers/CalDavController.cs @@ -60,6 +60,7 @@ namespace ASC.ApiSystem.Controllers private CommonConstants CommonConstants { get; } public InstanceCrypto InstanceCrypto { get; } private ILog Log { get; } + private IHttpClientFactory ClientFactory { get; } public CalDavController( CommonMethods commonMethods, @@ -184,10 +185,7 @@ namespace ASC.ApiSystem.Controllers var validationKey = EmailValidationKeyProvider.GetEmailKey(tenant.TenantId, email + userPassword.Password + ConfirmType.Auth); - var authData = string.Format("userName={0}&password={1}&key={2}", - HttpUtility.UrlEncode(email), - HttpUtility.UrlEncode(userPassword.Password), - HttpUtility.UrlEncode(validationKey)); + var authData = $"userName={HttpUtility.UrlEncode(email)}&password={HttpUtility.UrlEncode(userPassword.Password)}&key={HttpUtility.UrlEncode(validationKey)}"; SendToApi(Request.Scheme, tenant, "authentication/login", null, WebRequestMethods.Http.Post, authData); @@ -230,7 +228,7 @@ namespace ASC.ApiSystem.Controllers return false; } - Log.Info(string.Format("CalDav calendarParam: {0}", calendarParam)); + Log.Info($"CalDav calendarParam: {calendarParam}"); var userParam = calendarParam.Split('/')[0]; return GetUserData(userParam, out _, out tenant, out error); @@ -260,7 +258,7 @@ namespace ASC.ApiSystem.Controllers if (userData.Length < 3) { - Log.Error(string.Format("Error Caldav username: {0}", userParam)); + Log.Error($"Error Caldav username: {userParam}"); error = new { @@ -283,7 +281,7 @@ namespace ASC.ApiSystem.Controllers tenantName = tenantName.Replace("." + baseUrl, ""); } - Log.Info(string.Format("CalDav: user:{0} tenantName:{1}", userParam, tenantName)); + Log.Info($"CalDav: user:{userParam} tenantName:{tenantName}"); var tenantModel = new TenantModel { PortalName = tenantName }; @@ -329,22 +327,16 @@ namespace ASC.ApiSystem.Controllers ? null : string.Join("&", args.Select(arg => HttpUtility.UrlEncode(arg.Key) + "=" + HttpUtility.UrlEncode(arg.Value)).ToArray()); - var url = string.Format("{0}{1}{2}{3}{4}{5}", - requestUriScheme, - Uri.SchemeDelimiter, - tenant.GetTenantDomain(CoreSettings), - CommonConstants.WebApiBaseUrl, - path, - string.IsNullOrEmpty(query) ? "" : "?" + query); + var url = $"{requestUriScheme}{Uri.SchemeDelimiter}{tenant.GetTenantDomain(CoreSettings)}{CommonConstants.WebApiBaseUrl}{path}{(string.IsNullOrEmpty(query) ? "" : "?" + query)}"; - Log.Info(string.Format("CalDav: SendToApi: {0}", url)); + Log.Info($"CalDav: SendToApi: {url}"); var request = new HttpRequestMessage(); request.RequestUri = new Uri(url); request.Method = new HttpMethod(httpMethod); request.Headers.Accept.Add(MediaTypeWithQualityHeaderValue.Parse("application/json")); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); if (data != null) { diff --git a/common/services/ASC.ApiSystem/Controllers/PortalController.cs b/common/services/ASC.ApiSystem/Controllers/PortalController.cs index 2f895237a6..014164f6dc 100644 --- a/common/services/ASC.ApiSystem/Controllers/PortalController.cs +++ b/common/services/ASC.ApiSystem/Controllers/PortalController.cs @@ -28,90 +28,90 @@ using System; using System.Collections.Generic; using System.Diagnostics; using System.Linq; -using System.Security; - +using System.Security; + using ASC.ApiSystem.Classes; using ASC.ApiSystem.Models; -using ASC.Common; -using ASC.Common.Logging; -using ASC.Common.Utils; -using ASC.Core; -using ASC.Core.Billing; -using ASC.Core.Common.Settings; +using ASC.Common; +using ASC.Common.Logging; +using ASC.Common.Utils; +using ASC.Core; +using ASC.Core.Billing; +using ASC.Core.Common.Settings; using ASC.Core.Tenants; -using ASC.Core.Users; -using ASC.Security.Cryptography; -using ASC.Web.Core.Helpers; -using ASC.Web.Core.Users; +using ASC.Core.Users; +using ASC.Security.Cryptography; +using ASC.Web.Core.Helpers; +using ASC.Web.Core.Users; using ASC.Web.Core.Utility; using ASC.Web.Core.Utility.Settings; - + using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc; -using Microsoft.Extensions.Configuration; -using Microsoft.Extensions.Options; - +using Microsoft.Extensions.Configuration; +using Microsoft.Extensions.Options; + using Newtonsoft.Json.Linq; namespace ASC.ApiSystem.Controllers -{ +{ [Scope] [ApiController] [Route("[controller]")] public class PortalController : ControllerBase - { - private IConfiguration Configuration { get; } - private Core.SecurityContext SecurityContext { get; } - private TenantManager TenantManager { get; } - private SettingsManager SettingsManager { get; } - private ApiSystemHelper ApiSystemHelper { get; } - private CommonMethods CommonMethods { get; } - private HostedSolution HostedSolution { get; } - private CoreSettings CoreSettings { get; } - private TenantDomainValidator TenantDomainValidator { get; } - private UserFormatter UserFormatter { get; } - private UserManagerWrapper UserManagerWrapper { get; } - private CommonConstants CommonConstants { get; } - private TimeZonesProvider TimeZonesProvider { get; } - private TimeZoneConverter TimeZoneConverter { get; } - public PasswordHasher PasswordHasher { get; } - private ILog Log { get; } + { + private IConfiguration Configuration { get; } + private Core.SecurityContext SecurityContext { get; } + private TenantManager TenantManager { get; } + private SettingsManager SettingsManager { get; } + private ApiSystemHelper ApiSystemHelper { get; } + private CommonMethods CommonMethods { get; } + private HostedSolution HostedSolution { get; } + private CoreSettings CoreSettings { get; } + private TenantDomainValidator TenantDomainValidator { get; } + private UserFormatter UserFormatter { get; } + private UserManagerWrapper UserManagerWrapper { get; } + private CommonConstants CommonConstants { get; } + private TimeZonesProvider TimeZonesProvider { get; } + private TimeZoneConverter TimeZoneConverter { get; } + public PasswordHasher PasswordHasher { get; } + private ILog Log { get; } - public PortalController( - IConfiguration configuration, - Core.SecurityContext securityContext, - TenantManager tenantManager, - SettingsManager settingsManager, - ApiSystemHelper apiSystemHelper, - CommonMethods commonMethods, - IOptionsSnapshot<HostedSolution> hostedSolutionOptions, - CoreSettings coreSettings, - TenantDomainValidator tenantDomainValidator, - UserFormatter userFormatter, - UserManagerWrapper userManagerWrapper, - CommonConstants commonConstants, - IOptionsMonitor<ILog> option, - TimeZonesProvider timeZonesProvider, - TimeZoneConverter timeZoneConverter, + public PortalController( + IConfiguration configuration, + Core.SecurityContext securityContext, + TenantManager tenantManager, + SettingsManager settingsManager, + ApiSystemHelper apiSystemHelper, + CommonMethods commonMethods, + IOptionsSnapshot<HostedSolution> hostedSolutionOptions, + CoreSettings coreSettings, + TenantDomainValidator tenantDomainValidator, + UserFormatter userFormatter, + UserManagerWrapper userManagerWrapper, + CommonConstants commonConstants, + IOptionsMonitor<ILog> option, + TimeZonesProvider timeZonesProvider, + TimeZoneConverter timeZoneConverter, PasswordHasher passwordHasher) - { - Configuration = configuration; - SecurityContext = securityContext; - TenantManager = tenantManager; - SettingsManager = settingsManager; - ApiSystemHelper = apiSystemHelper; - CommonMethods = commonMethods; - HostedSolution = hostedSolutionOptions.Value; - CoreSettings = coreSettings; - TenantDomainValidator = tenantDomainValidator; - UserFormatter = userFormatter; - UserManagerWrapper = userManagerWrapper; - CommonConstants = commonConstants; - TimeZonesProvider = timeZonesProvider; - TimeZoneConverter = timeZoneConverter; - PasswordHasher = passwordHasher; + { + Configuration = configuration; + SecurityContext = securityContext; + TenantManager = tenantManager; + SettingsManager = settingsManager; + ApiSystemHelper = apiSystemHelper; + CommonMethods = commonMethods; + HostedSolution = hostedSolutionOptions.Value; + CoreSettings = coreSettings; + TenantDomainValidator = tenantDomainValidator; + UserFormatter = userFormatter; + UserManagerWrapper = userManagerWrapper; + CommonConstants = commonConstants; + TimeZonesProvider = timeZonesProvider; + TimeZoneConverter = timeZoneConverter; + PasswordHasher = passwordHasher; Log = option.Get("ASC.ApiSystem"); } @@ -161,20 +161,20 @@ namespace ASC.ApiSystem.Controllers } var sw = Stopwatch.StartNew(); - - if (string.IsNullOrEmpty(model.PasswordHash)) - { - if (!CheckPasswordPolicy(model.Password, out var error1)) - { - sw.Stop(); - return BadRequest(error1); - } - - if (!string.IsNullOrEmpty(model.Password)) - { - model.PasswordHash = PasswordHasher.GetClientPassword(model.Password); - } - + + if (string.IsNullOrEmpty(model.PasswordHash)) + { + if (!CheckPasswordPolicy(model.Password, out var error1)) + { + sw.Stop(); + return BadRequest(error1); + } + + if (!string.IsNullOrEmpty(model.Password)) + { + model.PasswordHash = PasswordHasher.GetClientPassword(model.Password); + } + } model.FirstName = (model.FirstName ?? "").Trim(); model.LastName = (model.LastName ?? "").Trim(); @@ -248,7 +248,7 @@ namespace ASC.ApiSystem.Controllers MobilePhone = string.IsNullOrEmpty(model.Phone) ? null : model.Phone.Trim(), Industry = (TenantIndustry)model.Industry, Spam = model.Spam, - Calls = model.Calls, + Calls = model.Calls, LimitedControlPanel = model.LimitedControlPanel }; @@ -301,31 +301,31 @@ namespace ASC.ApiSystem.Controllers message = e.Message, stacktrace = e.StackTrace }); - } - - var trialQuota = Configuration["trial-quota"]; - if (!string.IsNullOrEmpty(trialQuota)) - { - if (int.TryParse(trialQuota, out var trialQuotaId)) - { - var dueDate = DateTime.MaxValue; - if (int.TryParse(Configuration["trial-due"], out var dueTrial)) - { - dueDate = DateTime.UtcNow.AddDays(dueTrial); - } - - var tariff = new Tariff - { - QuotaId = trialQuotaId, - DueDate = dueDate - }; - HostedSolution.SetTariff(t.TenantId, tariff); - } - } - - - var isFirst = true; - string sendCongratulationsAddress = null; + } + + var trialQuota = Configuration["trial-quota"]; + if (!string.IsNullOrEmpty(trialQuota)) + { + if (int.TryParse(trialQuota, out var trialQuotaId)) + { + var dueDate = DateTime.MaxValue; + if (int.TryParse(Configuration["trial-due"], out var dueTrial)) + { + dueDate = DateTime.UtcNow.AddDays(dueTrial); + } + + var tariff = new Tariff + { + QuotaId = trialQuotaId, + DueDate = dueDate + }; + HostedSolution.SetTariff(t.TenantId, tariff); + } + } + + + var isFirst = true; + string sendCongratulationsAddress = null; if (!string.IsNullOrEmpty(model.PasswordHash)) { @@ -349,7 +349,7 @@ namespace ASC.ApiSystem.Controllers Log.Error(e); } } - + var reference = CommonMethods.CreateReference(Request.Scheme, t.GetTenantDomain(CoreSettings), info.Email, isFirst); Log.DebugFormat("PortalName = {0}; Elapsed ms. CreateReferenceByCookie...: {1}", model.PortalName, sw.ElapsedMilliseconds); @@ -360,7 +360,7 @@ namespace ASC.ApiSystem.Controllers { reference, tenant = CommonMethods.ToTenantWrapper(t), - referenceWelcome = sendCongratulationsAddress + referenceWelcome = sendCongratulationsAddress }); } @@ -477,13 +477,13 @@ namespace ASC.ApiSystem.Controllers var tenants = new List<Tenant>(); var empty = true; - if (!string.IsNullOrEmpty((model.Email ?? "").Trim())) + if (!string.IsNullOrWhiteSpace((model.Email ?? ""))) { empty = false; tenants.AddRange(HostedSolution.FindTenants((model.Email ?? "").Trim())); } - if (!string.IsNullOrEmpty((model.PortalName ?? "").Trim())) + if (!string.IsNullOrWhiteSpace((model.PortalName ?? ""))) { empty = false; var tenant = HostedSolution.GetTenant((model.PortalName ?? "").Trim()); @@ -671,9 +671,9 @@ namespace ASC.ApiSystem.Controllers { Log.DebugFormat("PortalName = {0}; Elapsed ms. ValidateRecaptcha via app key: {1}. {2}", model.PortalName, model.AppKey, sw.ElapsedMilliseconds); return true; - } - - var data = string.Format("{0} {1} {2} {3} {4} {5}", model.PortalName, model.FirstName, model.LastName, model.Email, model.Phone, model.RecaptchaType); + } + + var data = $"{model.PortalName} {model.FirstName} {model.LastName} {model.Email} {model.Phone} {model.RecaptchaType}"; /*** validate recaptcha ***/ if (!CommonMethods.ValidateRecaptcha(model.RecaptchaResponse, model.RecaptchaType, clientIP)) @@ -695,5 +695,5 @@ namespace ASC.ApiSystem.Controllers #endregion #endregion - } + } } \ No newline at end of file diff --git a/common/services/ASC.AuditTrail/AuditEventsRepository.cs b/common/services/ASC.AuditTrail/AuditEventsRepository.cs index 5ea5616469..cf8850ec6e 100644 --- a/common/services/ASC.AuditTrail/AuditEventsRepository.cs +++ b/common/services/ASC.AuditTrail/AuditEventsRepository.cs @@ -66,7 +66,7 @@ namespace ASC.AuditTrail return Get(tenant, from, to, null); } - private class Query + private sealed class Query { public Core.Common.EF.Model.AuditEvent AuditEvent { get; set; } public User User { get; set; } @@ -83,7 +83,7 @@ namespace ASC.AuditTrail if (fromDate.HasValue && to.HasValue) { - query = query.Where(q => q.AuditEvent.Date >= fromDate & q.AuditEvent.Date <= to); + query = query.Where(q => q.AuditEvent.Date >= fromDate && q.AuditEvent.Date <= to); } if (limit.HasValue) @@ -102,7 +102,7 @@ namespace ASC.AuditTrail if (from.HasValue && to.HasValue) { - query = query.Where(a => a.Date >= from & a.Date <= to); + query = query.Where(a => a.Date >= from && a.Date <= to); } return query.Count(); @@ -129,7 +129,7 @@ namespace ASC.AuditTrail if (query.AuditEvent.Description != null) { evt.Description = JsonConvert.DeserializeObject<IList<string>>( - Convert.ToString(query.AuditEvent.Description), + query.AuditEvent.Description, new JsonSerializerSettings { DateTimeZoneHandling = DateTimeZoneHandling.Utc }); } diff --git a/common/services/ASC.AuditTrail/LoginEventsRepository.cs b/common/services/ASC.AuditTrail/LoginEventsRepository.cs index fa829e8688..e0bb249078 100644 --- a/common/services/ASC.AuditTrail/LoginEventsRepository.cs +++ b/common/services/ASC.AuditTrail/LoginEventsRepository.cs @@ -55,7 +55,7 @@ namespace ASC.AuditTrail.Data LazyMessagesContext = new Lazy<MessagesContext>(() => dbMessagesContext.Value); } - private class Query + private sealed class Query { public LoginEvents LoginEvents { get; set; } public User User { get; set; } @@ -95,7 +95,7 @@ namespace ASC.AuditTrail.Data if (from.HasValue && to.HasValue) { - query = query.Where(l => l.Date >= from & l.Date <= to); + query = query.Where(l => l.Date >= from && l.Date <= to); } return query.Count(); diff --git a/common/services/ASC.AuditTrail/Mappers/AuditActionMapper.cs b/common/services/ASC.AuditTrail/Mappers/AuditActionMapper.cs index d6d6be2612..039a3c54e4 100644 --- a/common/services/ASC.AuditTrail/Mappers/AuditActionMapper.cs +++ b/common/services/ASC.AuditTrail/Mappers/AuditActionMapper.cs @@ -71,7 +71,7 @@ namespace ASC.AuditTrail.Mappers { var actionText = Actions[(MessageAction)evt.Action].GetActionText(); - if (evt.Description == null || !evt.Description.Any()) return actionText; + if (evt.Description == null || evt.Description.Count == 0) return actionText; var description = evt.Description .Select(t => t.Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries)) @@ -100,7 +100,7 @@ namespace ASC.AuditTrail.Mappers { var actionText = Actions[(MessageAction)evt.Action].GetActionText(); - if (evt.Description == null || !evt.Description.Any()) return actionText; + if (evt.Description == null || evt.Description.Count == 0) return actionText; var description = evt.Description .Select(t => t.Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries)) @@ -142,7 +142,7 @@ namespace ASC.AuditTrail.Mappers private string ToLimitedText(string text) { if (text == null) return null; - return text.Length < 50 ? text : string.Format("{0}...", text.Substring(0, 47)); + return text.Length < 50 ? text : $"{text.Substring(0, 47)}..."; } } } \ No newline at end of file diff --git a/common/services/ASC.AuditTrail/Mappers/CrmActionMapper.cs b/common/services/ASC.AuditTrail/Mappers/CrmActionMapper.cs index 6f0a9170fe..a311eef439 100644 --- a/common/services/ASC.AuditTrail/Mappers/CrmActionMapper.cs +++ b/common/services/ASC.AuditTrail/Mappers/CrmActionMapper.cs @@ -32,7 +32,7 @@ using ASC.MessagingSystem; namespace ASC.AuditTrail.Mappers { - internal class CrmActionMapper + internal static class CrmActionMapper { public static Dictionary<MessageAction, MessageMaps> GetMaps() { diff --git a/common/services/ASC.AuditTrail/Mappers/DocumentsActionMapper.cs b/common/services/ASC.AuditTrail/Mappers/DocumentsActionMapper.cs index 0189838e04..9e46f41daa 100644 --- a/common/services/ASC.AuditTrail/Mappers/DocumentsActionMapper.cs +++ b/common/services/ASC.AuditTrail/Mappers/DocumentsActionMapper.cs @@ -31,7 +31,7 @@ using ASC.MessagingSystem; namespace ASC.AuditTrail.Mappers { - internal class DocumentsActionMapper + internal static class DocumentsActionMapper { public static Dictionary<MessageAction, MessageMaps> GetMaps() { diff --git a/common/services/ASC.AuditTrail/Mappers/LoginActionMapper.cs b/common/services/ASC.AuditTrail/Mappers/LoginActionMapper.cs index 0ad37f1fd2..bffafbc2a4 100644 --- a/common/services/ASC.AuditTrail/Mappers/LoginActionMapper.cs +++ b/common/services/ASC.AuditTrail/Mappers/LoginActionMapper.cs @@ -32,7 +32,7 @@ using ASC.MessagingSystem; namespace ASC.AuditTrail.Mappers { - internal class LoginActionsMapper + internal static class LoginActionsMapper { public static Dictionary<MessageAction, MessageMaps> GetMaps() { diff --git a/common/services/ASC.AuditTrail/Mappers/OthersActionMapper.cs b/common/services/ASC.AuditTrail/Mappers/OthersActionMapper.cs index 572e0644a1..f0bf259b4b 100644 --- a/common/services/ASC.AuditTrail/Mappers/OthersActionMapper.cs +++ b/common/services/ASC.AuditTrail/Mappers/OthersActionMapper.cs @@ -32,7 +32,7 @@ using ASC.MessagingSystem; namespace ASC.AuditTrail.Mappers { - internal class OthersActionsMapper + internal static class OthersActionsMapper { public static Dictionary<MessageAction, MessageMaps> GetMaps() { diff --git a/common/services/ASC.AuditTrail/Mappers/PeopleActionMapper.cs b/common/services/ASC.AuditTrail/Mappers/PeopleActionMapper.cs index a67feacb0d..5aa563afeb 100644 --- a/common/services/ASC.AuditTrail/Mappers/PeopleActionMapper.cs +++ b/common/services/ASC.AuditTrail/Mappers/PeopleActionMapper.cs @@ -32,7 +32,7 @@ using ASC.MessagingSystem; namespace ASC.AuditTrail.Mappers { - internal class PeopleActionMapper + internal static class PeopleActionMapper { public static Dictionary<MessageAction, MessageMaps> GetMaps() { diff --git a/common/services/ASC.AuditTrail/Mappers/ProjectsActionMapper.cs b/common/services/ASC.AuditTrail/Mappers/ProjectsActionMapper.cs index ac3de67f0f..00135f8c7d 100644 --- a/common/services/ASC.AuditTrail/Mappers/ProjectsActionMapper.cs +++ b/common/services/ASC.AuditTrail/Mappers/ProjectsActionMapper.cs @@ -31,7 +31,7 @@ using ASC.MessagingSystem; namespace ASC.AuditTrail.Mappers { - internal class ProjectsActionsMapper + internal static class ProjectsActionsMapper { public static Dictionary<MessageAction, MessageMaps> GetMaps() { diff --git a/common/services/ASC.AuditTrail/Mappers/SettingsActionMapper.cs b/common/services/ASC.AuditTrail/Mappers/SettingsActionMapper.cs index 74904ef51f..8298a4b2f3 100644 --- a/common/services/ASC.AuditTrail/Mappers/SettingsActionMapper.cs +++ b/common/services/ASC.AuditTrail/Mappers/SettingsActionMapper.cs @@ -31,7 +31,7 @@ using ASC.MessagingSystem; namespace ASC.AuditTrail.Mappers { - internal class SettingsActionsMapper + internal static class SettingsActionsMapper { public static Dictionary<MessageAction, MessageMaps> GetMaps() { diff --git a/common/services/ASC.ClearEvents/ClearEventsServiceLauncher.cs b/common/services/ASC.ClearEvents/ClearEventsServiceLauncher.cs index b006aeafe9..c3d92d8732 100644 --- a/common/services/ASC.ClearEvents/ClearEventsServiceLauncher.cs +++ b/common/services/ASC.ClearEvents/ClearEventsServiceLauncher.cs @@ -115,12 +115,12 @@ namespace ASC.Thumbnails.Svc ids = ae.Select(r => r.ef).ToList(); - if (!ids.Any()) return; + if (ids.Count == 0) return; table.RemoveRange(ids); ef.SaveChanges(); - } while (ids.Any()); + } while (ids.Count > 0); } } @@ -131,7 +131,7 @@ namespace ASC.Thumbnails.Svc public DbSet<DbWebstudioSettings> WebstudioSettings { get; } } -public class MessagesRepositoryExtension + public static class MessagesRepositoryExtension { public static void Register(DIHelper services) { diff --git a/common/services/ASC.ClearEvents/Program.cs b/common/services/ASC.ClearEvents/Program.cs index 8110acd843..3d3dd959f0 100644 --- a/common/services/ASC.ClearEvents/Program.cs +++ b/common/services/ASC.ClearEvents/Program.cs @@ -26,8 +26,8 @@ using System.Collections.Generic; using System.IO; -using System.Threading.Tasks; - +using System.Threading.Tasks; + using ASC.Api.Core; using ASC.Common; using ASC.Common.Caching; @@ -39,13 +39,13 @@ using Autofac.Extensions.DependencyInjection; using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; -using Microsoft.Extensions.Hosting; - -using StackExchange.Redis.Extensions.Core.Configuration; - +using Microsoft.Extensions.Hosting; + +using StackExchange.Redis.Extensions.Core.Configuration; + namespace ASC.Thumbnails.Svc -{ -public class Program +{ + public static class Program { public async static Task Main(string[] args) { @@ -68,7 +68,7 @@ public class Program path = Path.GetFullPath(CrossPlatform.PathCombine(hostContext.HostingEnvironment.ContentRootPath, path)); } config.SetBasePath(path); - var env = hostContext.Configuration.GetValue("ENVIRONMENT", "Production"); + config .AddJsonFile("appsettings.json") .AddEnvironmentVariables() @@ -82,23 +82,23 @@ public class Program .ConfigureServices((hostContext, services) => { services.AddMemoryCache(); - var diHelper = new DIHelper(services); - - var redisConfiguration = hostContext.Configuration.GetSection("Redis").Get<RedisConfiguration>(); - var kafkaConfiguration = hostContext.Configuration.GetSection("kafka").Get<KafkaSettings>(); - - if (kafkaConfiguration != null) - { - diHelper.TryAdd(typeof(ICacheNotify<>), typeof(KafkaCache<>)); - } - else if (redisConfiguration != null) - { - diHelper.TryAdd(typeof(ICacheNotify<>), typeof(RedisCache<>)); - } - else - { - diHelper.TryAdd(typeof(ICacheNotify<>), typeof(MemoryCacheNotify<>)); - } + var diHelper = new DIHelper(services); + + var redisConfiguration = hostContext.Configuration.GetSection("Redis").Get<RedisConfiguration>(); + var kafkaConfiguration = hostContext.Configuration.GetSection("kafka").Get<KafkaSettings>(); + + if (kafkaConfiguration != null) + { + diHelper.TryAdd(typeof(ICacheNotify<>), typeof(KafkaCache<>)); + } + else if (redisConfiguration != null) + { + diHelper.TryAdd(typeof(ICacheNotify<>), typeof(RedisCache<>)); + } + else + { + diHelper.TryAdd(typeof(ICacheNotify<>), typeof(MemoryCacheNotify<>)); + } services.AddHostedService<ClearEventsServiceLauncher>(); diHelper.TryAdd<ClearEventsServiceLauncher>(); diff --git a/common/services/ASC.Data.Backup/GlobalUsings.cs b/common/services/ASC.Data.Backup/GlobalUsings.cs index bc8c334827..45e32aa25b 100644 --- a/common/services/ASC.Data.Backup/GlobalUsings.cs +++ b/common/services/ASC.Data.Backup/GlobalUsings.cs @@ -37,7 +37,4 @@ global using Microsoft.Extensions.DependencyInjection; global using Microsoft.Extensions.Hosting; global using Microsoft.Extensions.Options; -global using StackExchange.Redis.Extensions.Core.Configuration; -global using StackExchange.Redis.Extensions.Newtonsoft; - global using static ASC.Data.Backup.BackupAjaxHandler; diff --git a/common/services/ASC.Data.Backup/Program.cs b/common/services/ASC.Data.Backup/Program.cs index 87f896009f..54b8b33250 100644 --- a/common/services/ASC.Data.Backup/Program.cs +++ b/common/services/ASC.Data.Backup/Program.cs @@ -1,83 +1,83 @@ -using Microsoft.Extensions.Hosting.WindowsServices; - -var options = new WebApplicationOptions -{ - Args = args, - ContentRootPath = WindowsServiceHelpers.IsWindowsService() ? AppContext.BaseDirectory : default -}; - -var builder = WebApplication.CreateBuilder(options); - -builder.Host.UseWindowsService(); -builder.Host.UseSystemd(); -builder.Host.UseServiceProviderFactory(new AutofacServiceProviderFactory()); - -builder.WebHost.ConfigureKestrel((hostingContext, serverOptions) => -{ - var kestrelConfig = hostingContext.Configuration.GetSection("Kestrel"); - - if (!kestrelConfig.Exists()) return; - - var unixSocket = kestrelConfig.GetValue<string>("ListenUnixSocket"); - - if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) - { - if (!string.IsNullOrWhiteSpace(unixSocket)) - { - unixSocket = string.Format(unixSocket, hostingContext.HostingEnvironment.ApplicationName.Replace("ASC.", "").Replace(".", "")); - - serverOptions.ListenUnixSocket(unixSocket); - } - } -}); - -builder.Host.ConfigureAppConfiguration((hostContext, config) => -{ - var buided = config.Build(); - - var path = buided["pathToConf"]; - - if (!Path.IsPathRooted(path)) - { - path = Path.GetFullPath(CrossPlatform.PathCombine(hostContext.HostingEnvironment.ContentRootPath, path)); - } - - config.SetBasePath(path); - - var env = hostContext.Configuration.GetValue("ENVIRONMENT", "Production"); - config - .AddJsonFile("appsettings.json") - .AddJsonFile($"appsettings.{env}.json", true) - .AddJsonFile("storage.json") - .AddJsonFile("notify.json") - .AddJsonFile($"notify.{env}.json", true) - .AddJsonFile("backup.json") - .AddJsonFile("kafka.json") - .AddJsonFile($"kafka.{env}.json", true) - .AddJsonFile("redis.json") - .AddJsonFile($"redis.{env}.json", true) - .AddEnvironmentVariables() - .AddCommandLine(args) - .AddInMemoryCollection(new Dictionary<string, string> - { - {"pathToConf", path } - } - ); -}); - -builder.Host.ConfigureNLogLogging(); - -var startup = new Startup(builder.Configuration, builder.Environment); - -startup.ConfigureServices(builder.Services); - -builder.Host.ConfigureContainer<ContainerBuilder>(containerBuilder => -{ - startup.ConfigureContainer(containerBuilder); -}); - -var app = builder.Build(); - -startup.Configure(app, app.Environment); - -app.Run(); \ No newline at end of file +using Microsoft.Extensions.Hosting.WindowsServices; + +var options = new WebApplicationOptions +{ + Args = args, + ContentRootPath = WindowsServiceHelpers.IsWindowsService() ? AppContext.BaseDirectory : default +}; + +var builder = WebApplication.CreateBuilder(options); + +builder.Host.UseWindowsService(); +builder.Host.UseSystemd(); +builder.Host.UseServiceProviderFactory(new AutofacServiceProviderFactory()); + +builder.WebHost.ConfigureKestrel((hostingContext, serverOptions) => +{ + var kestrelConfig = hostingContext.Configuration.GetSection("Kestrel"); + + if (!kestrelConfig.Exists()) return; + + var unixSocket = kestrelConfig.GetValue<string>("ListenUnixSocket"); + + if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) + { + if (!string.IsNullOrWhiteSpace(unixSocket)) + { + unixSocket = string.Format(unixSocket, hostingContext.HostingEnvironment.ApplicationName.Replace("ASC.", "").Replace(".", "")); + + serverOptions.ListenUnixSocket(unixSocket); + } + } +}); + +builder.Host.ConfigureAppConfiguration((hostContext, config) => +{ + var buided = config.Build(); + + var path = buided["pathToConf"]; + + if (!Path.IsPathRooted(path)) + { + path = Path.GetFullPath(CrossPlatform.PathCombine(hostContext.HostingEnvironment.ContentRootPath, path)); + } + + config.SetBasePath(path); + + var env = hostContext.Configuration.GetValue("ENVIRONMENT", "Production"); + config + .AddJsonFile("appsettings.json") + .AddJsonFile($"appsettings.{env}.json", true) + .AddJsonFile("storage.json") + .AddJsonFile("notify.json") + .AddJsonFile($"notify.{env}.json", true) + .AddJsonFile("backup.json") + .AddJsonFile("kafka.json") + .AddJsonFile($"kafka.{env}.json", true) + .AddJsonFile("redis.json") + .AddJsonFile($"redis.{env}.json", true) + .AddEnvironmentVariables() + .AddCommandLine(args) + .AddInMemoryCollection(new Dictionary<string, string> + { + {"pathToConf", path } + } + ); +}); + +builder.Host.ConfigureNLogLogging(); + +var startup = new Startup(builder.Configuration, builder.Environment); + +startup.ConfigureServices(builder.Services); + +builder.Host.ConfigureContainer<ContainerBuilder>(containerBuilder => +{ + startup.ConfigureContainer(containerBuilder); +}); + +var app = builder.Build(); + +startup.Configure(app, app.Environment); + +app.Run(); diff --git a/common/services/ASC.ElasticSearch/Core/SearchSettings.cs b/common/services/ASC.ElasticSearch/Core/SearchSettings.cs index cc049827d4..9d9a111d1a 100644 --- a/common/services/ASC.ElasticSearch/Core/SearchSettings.cs +++ b/common/services/ASC.ElasticSearch/Core/SearchSettings.cs @@ -120,12 +120,12 @@ namespace ASC.ElasticSearch.Core }).ToList(); } - private List<IFactoryIndexer> allItems; - internal List<IFactoryIndexer> AllItems + private IEnumerable<IFactoryIndexer> allItems; + internal IEnumerable<IFactoryIndexer> AllItems { get { - return allItems ??= ServiceProvider.GetService<IEnumerable<IFactoryIndexer>>().ToList(); + return allItems ??= ServiceProvider.GetService<IEnumerable<IFactoryIndexer>>(); } } @@ -136,7 +136,7 @@ namespace ASC.ElasticSearch.Core var settings = SettingsManager.Load<SearchSettings>(); var settingsItems = settings.Items; - var toReIndex = !settingsItems.Any() ? items.Where(r => r.Enabled).ToList() : items.Where(item => settingsItems.Any(r => r.ID == item.ID && r.Enabled != item.Enabled)).ToList(); + var toReIndex = settingsItems.Count == 0 ? items.Where(r => r.Enabled).ToList() : items.Where(item => settingsItems.Any(r => r.ID == item.ID && r.Enabled != item.Enabled)).ToList(); settings.Items = items; settings.Data = JsonConvert.SerializeObject(items); diff --git a/common/services/ASC.ElasticSearch/Core/Selector.cs b/common/services/ASC.ElasticSearch/Core/Selector.cs index bdd8d0f133..74dfb147ab 100644 --- a/common/services/ASC.ElasticSearch/Core/Selector.cs +++ b/common/services/ASC.ElasticSearch/Core/Selector.cs @@ -207,7 +207,7 @@ namespace ASC.ElasticSearch { var t = ServiceProvider.GetService<T>(); var searchSettingsHelper = ServiceProvider.GetService<SearchSettingsHelper>(); - return ((NewArrayExpression)(t.GetSearchContentFields(searchSettingsHelper)).Body).Expressions.ToArray(); + return ((NewArrayExpression)t.GetSearchContentFields(searchSettingsHelper).Body).Expressions.ToArray(); }, value); @@ -341,7 +341,7 @@ namespace ASC.ElasticSearch if (string.IsNullOrEmpty(path) && !string.IsNullOrEmpty(fieldSelector.Name) && - fieldSelector.Name.IndexOf(".", StringComparison.InvariantCulture) > 0) + fieldSelector.Name.IndexOf('.') > -1) { var splitted = fieldSelector.Name.Split(':')[1]; path = splitted.Split('.')[0]; @@ -372,7 +372,7 @@ namespace ASC.ElasticSearch private bool IsPhrase(string searchText) { - return searchText.Contains(" ") || searchText.Contains("\r\n") || searchText.Contains("\n"); + return searchText.Contains(' ') || searchText.Contains("\r\n") || searchText.Contains('\n'); } private bool IsExactlyPhrase(string searchText) @@ -382,7 +382,7 @@ namespace ASC.ElasticSearch private bool IsExactly(string searchText) { - return searchText.StartsWith("\"") && searchText.EndsWith("\""); + return searchText.StartsWith('\"') && searchText.EndsWith('\"'); } private QueryContainer MultiMatch(Fields fields, string value) @@ -440,7 +440,7 @@ namespace ASC.ElasticSearch { var result = value; - if (!value.Contains("*") && !value.Contains("?")) + if (!value.Contains('*') && !value.Contains('?')) { result = "*" + result + "*"; } diff --git a/common/services/ASC.ElasticSearch/Engine/BaseIndexer.cs b/common/services/ASC.ElasticSearch/Engine/BaseIndexer.cs index 2cff58569f..b07b2e50e2 100644 --- a/common/services/ASC.ElasticSearch/Engine/BaseIndexer.cs +++ b/common/services/ASC.ElasticSearch/Engine/BaseIndexer.cs @@ -122,7 +122,7 @@ namespace ASC.ElasticSearch internal void Index(List<T> data, bool immediately = true) { - if (!data.Any()) return; + if (data.Count == 0) return; CreateIfNotExist(data[0]); @@ -258,7 +258,6 @@ namespace ASC.ElasticSearch { wwd.Document.Data = null; wwd.Document = null; - wwd = null; GC.Collect(); } continue; @@ -288,7 +287,6 @@ namespace ASC.ElasticSearch doc.Document.Data = null; doc.Document = null; } - doc = null; } portionStart = i; @@ -357,8 +355,6 @@ namespace ASC.ElasticSearch lock (Locker) { - if (isExist) return true; - isExist = Client.Instance.Indices.Exists(data.IndexName).Exists; BaseIndexerHelper.IsExist.TryUpdate(data.IndexName, IsExist, false); @@ -428,33 +424,33 @@ namespace ASC.ElasticSearch foreach (var c in Enum.GetNames(typeof(Analyzer))) { var c1 = c; - b.Custom(c1 + "custom", ca => ca.Tokenizer(c1).Filters(Filter.lowercase.ToString()).CharFilters(CharFilter.io.ToString())); + b.Custom(c1 + "custom", ca => ca.Tokenizer(c1).Filters(nameof(Filter.lowercase)).CharFilters(nameof(CharFilter.io))); } foreach (var c in Enum.GetNames(typeof(CharFilter))) { - if (c == CharFilter.io.ToString()) continue; + if (c == nameof(CharFilter.io)) continue; - var charFilters = new List<string>() { CharFilter.io.ToString(), c }; + var charFilters = new List<string>() { nameof(CharFilter.io), c }; var c1 = c; - b.Custom(c1 + "custom", ca => ca.Tokenizer(Analyzer.whitespace.ToString()).Filters(Filter.lowercase.ToString()).CharFilters(charFilters)); + b.Custom(c1 + "custom", ca => ca.Tokenizer(nameof(Analyzer.whitespace)).Filters(nameof(Filter.lowercase)).CharFilters(charFilters)); } if (data is ISearchItemDocument) { - b.Custom("document", ca => ca.Tokenizer(Analyzer.whitespace.ToString()).Filters(Filter.lowercase.ToString()).CharFilters(CharFilter.io.ToString())); + b.Custom("document", ca => ca.Tokenizer(nameof(Analyzer.whitespace)).Filters(nameof(Filter.lowercase)).CharFilters(nameof(CharFilter.io))); } return b; } - var createIndexResponse = Client.Instance.Indices.Create(data.IndexName, - c => - c.Map<T>(m => m.AutoMap()) - .Settings(r => r.Analysis(a => - a.Analyzers(analyzers) - .CharFilters(d => d.HtmlStrip(CharFilter.html.ToString()) - .Mapping(CharFilter.io.ToString(), m => m.Mappings("ё => е", "Ё => Е")))))); + Client.Instance.Indices.Create(data.IndexName, + c => + c.Map<T>(m => m.AutoMap()) + .Settings(r => r.Analysis(a => + a.Analyzers(analyzers) + .CharFilters(d => d.HtmlStrip(CharFilter.html.ToString()) + .Mapping(CharFilter.io.ToString(), m => m.Mappings("ё => е", "Ё => Е")))))); IsExist = true; } @@ -497,7 +493,7 @@ namespace ASC.ElasticSearch { var result = request.Index(IndexName); - if (fields.Any()) + if (fields.Length > 0) { result.Script(GetScriptUpdateByQuery(data, fields)); } @@ -520,21 +516,21 @@ namespace ASC.ElasticSearch var parameters = new Dictionary<string, object>(); for (var i = 0; i < fields.Length; i++) - { - var func = fields[i].Compile(); + { + var field = fields[i]; + var func = field.Compile(); var newValue = func(data); string name; - var expression = fields[i].Body; + var expression = field.Body; var isList = expression.Type.IsGenericType && expression.Type.GetGenericTypeDefinition() == typeof(List<>); var sourceExprText = ""; - + while (!string.IsNullOrEmpty(name = TryGetName(expression, out var member))) { sourceExprText = "." + name + sourceExprText; - expression = member.Expression; } if (isList) @@ -545,12 +541,12 @@ namespace ASC.ElasticSearch { if (newValue == default(T)) { - source.AppendFormat("ctx._source.remove('{0}');", sourceExprText.Substring(1)); + source.Append($"ctx._source.remove('{sourceExprText.Substring(1)}');"); } else { var pkey = "p" + sourceExprText.Replace(".", ""); - source.AppendFormat("ctx._source{0} = params.{1};", sourceExprText, pkey); + source.Append($"ctx._source{sourceExprText} = params.{pkey};"); parameters.Add(pkey, newValue); } } @@ -584,10 +580,10 @@ namespace ASC.ElasticSearch var expression = fields.Body; var sourceExprText = ""; - + while (!string.IsNullOrEmpty(name = TryGetName(expression, out var member))) { - sourceExprText = "." + name + sourceExprText; + sourceExprText = "." + name + sourceExprText; expression = member.Expression; } @@ -607,22 +603,22 @@ namespace ASC.ElasticSearch for (var i = 0; i < newValue.Count; i++) { parameters.Add(paramKey + i, newValue[i]); - source.AppendFormat("if (!ctx._source{0}.contains(params.{1})){{ctx._source{0}.add(params.{1})}}", key, paramKey + i); + source.Append($"if (!ctx._source{key}.contains(params.{paramKey + i})){{ctx._source{key}.add(params.{paramKey + i})}}"); } break; case UpdateAction.Replace: parameters.Add(paramKey, newValue); - source.AppendFormat("ctx._source{0} = params.{1};", key, paramKey); + source.Append($"ctx._source{key} = params.{paramKey};"); break; case UpdateAction.Remove: for (var i = 0; i < newValue.Count; i++) { parameters.Add(paramKey + i, newValue[i]); - source.AppendFormat("ctx._source{0}.removeIf(item -> item.id == params.{1}.id)", key, paramKey + i); + source.Append($"ctx._source{key}.removeIf(item -> item.id == params.{paramKey + i}.id)"); } break; default: - throw new ArgumentOutOfRangeException("action", action, null); + throw new ArgumentOutOfRangeException(nameof(action), action, null); } } diff --git a/common/services/ASC.ElasticSearch/Engine/FactoryIndexer.cs b/common/services/ASC.ElasticSearch/Engine/FactoryIndexer.cs index 2c79d0b214..9dc52bb2c9 100644 --- a/common/services/ASC.ElasticSearch/Engine/FactoryIndexer.cs +++ b/common/services/ASC.ElasticSearch/Engine/FactoryIndexer.cs @@ -207,7 +207,7 @@ namespace ASC.ElasticSearch public void Index(List<T> data, bool immediately = true, int retry = 0) { var t = ServiceProvider.GetService<T>(); - if (!Support(t) || !data.Any()) return; + if (!Support(t) || data.Count == 0) return; try { @@ -230,7 +230,7 @@ namespace ASC.ElasticSearch Thread.Sleep(60000); if (retry < 5) { - Index(data, immediately, retry++); + Index(data, immediately, retry + 1); return; } @@ -259,7 +259,7 @@ namespace ASC.ElasticSearch Thread.Sleep(60000); if (retry < 5) { - Index(data, immediately, retry++); + Index(data, immediately, retry + 1); return; } @@ -271,13 +271,18 @@ namespace ASC.ElasticSearch throw; } } - } + } - public async Task IndexAsync(List<T> data, bool immediately = true, int retry = 0) + public Task IndexAsync(List<T> data, bool immediately = true, int retry = 0) { var t = ServiceProvider.GetService<T>(); - if (!Support(t) || !data.Any()) return; + if (!Support(t) || data.Count == 0) return Task.CompletedTask; + return InternalIndexAsync(data, immediately, retry); + } + + private async Task InternalIndexAsync(List<T> data, bool immediately, int retry) + { try { await Indexer.IndexAsync(data, immediately).ConfigureAwait(false); @@ -299,7 +304,7 @@ namespace ASC.ElasticSearch await Task.Delay(60000); if (retry < 5) { - await IndexAsync(data, immediately, retry++); + await IndexAsync(data, immediately, retry + 1); return; } @@ -328,7 +333,7 @@ namespace ASC.ElasticSearch await Task.Delay(60000); if (retry < 5) { - await IndexAsync(data, immediately, retry++); + await IndexAsync(data, immediately, retry + 1); return; } @@ -546,9 +551,9 @@ namespace ASC.ElasticSearch } } - public async Task<bool> SupportAsync(T t) + public Task<bool> SupportAsync(T t) { - return await FactoryIndexerCommon.CheckStateAsync(); + return FactoryIndexerCommon.CheckStateAsync(); } } @@ -623,9 +628,9 @@ namespace ASC.ElasticSearch return false; } } - - public async Task<bool> CheckStateAsync(bool cacheState = true) - { + + public Task<bool> CheckStateAsync(bool cacheState = true) + { const string key = "elasticsearch"; if (cacheState) @@ -633,10 +638,15 @@ namespace ASC.ElasticSearch var cacheValue = cache.Get<string>(key); if (!string.IsNullOrEmpty(cacheValue)) { - return Convert.ToBoolean(cacheValue); + return Task.FromResult(Convert.ToBoolean(cacheValue)); } - } + } + + return InternalCheckStateAsync(cacheState, key); + } + private async Task<bool> InternalCheckStateAsync(bool cacheState, string key) + { var cacheTime = DateTime.UtcNow.AddMinutes(15); try diff --git a/common/services/ASC.ElasticSearch/Service/Launcher.cs b/common/services/ASC.ElasticSearch/Service/Launcher.cs index d8d5f61b8f..6ab671c876 100644 --- a/common/services/ASC.ElasticSearch/Service/Launcher.cs +++ b/common/services/ASC.ElasticSearch/Service/Launcher.cs @@ -210,7 +210,7 @@ namespace ASC.ElasticSearch } } - public class ServiceLauncherExtension + public static class ServiceLauncherExtension { public static void Register(DIHelper services) { diff --git a/common/services/ASC.ElasticSearch/Service/Service.cs b/common/services/ASC.ElasticSearch/Service/Service.cs index 12a2b4462e..ba619f2c9e 100644 --- a/common/services/ASC.ElasticSearch/Service/Service.cs +++ b/common/services/ASC.ElasticSearch/Service/Service.cs @@ -79,7 +79,7 @@ namespace ASC.ElasticSearch.Service tasks.Add(instance.ReIndex()); } - if (!tasks.Any()) return; + if (tasks.Count == 0) return; Task.WhenAll(tasks).ContinueWith(r => { @@ -120,7 +120,7 @@ namespace ASC.ElasticSearch.Service } } - internal class ServiceExtension + internal static class ServiceExtension { public static void Register(DIHelper services) { diff --git a/common/services/ASC.Feed.Aggregator/Modules/FeedModule.cs b/common/services/ASC.Feed.Aggregator/Modules/FeedModule.cs index c676c283ee..84964b39c1 100644 --- a/common/services/ASC.Feed.Aggregator/Modules/FeedModule.cs +++ b/common/services/ASC.Feed.Aggregator/Modules/FeedModule.cs @@ -49,7 +49,7 @@ namespace ASC.Feed.Aggregator.Modules protected TenantManager TenantManager { get; } protected WebItemSecurity WebItemSecurity { get; } - public FeedModule(TenantManager tenantManager, WebItemSecurity webItemSecurity) + protected FeedModule(TenantManager tenantManager, WebItemSecurity webItemSecurity) { TenantManager = tenantManager; WebItemSecurity = webItemSecurity; diff --git a/common/services/ASC.Feed.Aggregator/Service/FeedAggregatorService.cs b/common/services/ASC.Feed.Aggregator/Service/FeedAggregatorService.cs index 112b38fd20..325417599e 100644 --- a/common/services/ASC.Feed.Aggregator/Service/FeedAggregatorService.cs +++ b/common/services/ASC.Feed.Aggregator/Service/FeedAggregatorService.cs @@ -135,7 +135,7 @@ namespace ASC.Feed.Aggregator var toTime = DateTime.UtcNow; var tenants = Attempt(10, () => module.GetTenantsWithFeeds(fromTime)).ToList(); - Log.DebugFormat("Find {1} tenants for module {0}.", module.GetType().Name, tenants.Count()); + Log.DebugFormat("Find {1} tenants for module {0}.", module.GetType().Name, tenants.Count); foreach (var tenant in tenants) { @@ -336,7 +336,7 @@ namespace ASC.Feed.Aggregator } } - public class FeedAggregatorServiceExtension + public static class FeedAggregatorServiceExtension { public static void Register(DIHelper services) { diff --git a/common/services/ASC.Notify/DbWorker.cs b/common/services/ASC.Notify/DbWorker.cs index 17f92e59aa..b726ca5325 100644 --- a/common/services/ASC.Notify/DbWorker.cs +++ b/common/services/ASC.Notify/DbWorker.cs @@ -224,7 +224,7 @@ namespace ASC.Notify } } - public class DbWorkerExtension + public static class DbWorkerExtension { public static void Register(DIHelper services) { diff --git a/common/services/ASC.Notify/NotifyService.cs b/common/services/ASC.Notify/NotifyService.cs index 7507390e16..970d37f296 100644 --- a/common/services/ASC.Notify/NotifyService.cs +++ b/common/services/ASC.Notify/NotifyService.cs @@ -142,7 +142,7 @@ namespace ASC.Notify } } - public class NotifyServiceExtension + public static class NotifyServiceExtension { public static void Register(DIHelper services) { diff --git a/common/services/ASC.Notify/Program.cs b/common/services/ASC.Notify/Program.cs index 9adc227e03..bfbf492d47 100644 --- a/common/services/ASC.Notify/Program.cs +++ b/common/services/ASC.Notify/Program.cs @@ -23,7 +23,7 @@ using StackExchange.Redis.Extensions.Newtonsoft; namespace ASC.Notify { - public class Program + public static class Program { public async static Task Main(string[] args) { diff --git a/common/services/ASC.Socket.IO.Svc/SocketServiceLauncher.cs b/common/services/ASC.Socket.IO.Svc/SocketServiceLauncher.cs index fc2a6bfddb..018fc52e3f 100644 --- a/common/services/ASC.Socket.IO.Svc/SocketServiceLauncher.cs +++ b/common/services/ASC.Socket.IO.Svc/SocketServiceLauncher.cs @@ -90,7 +90,7 @@ namespace ASC.Socket.IO.Svc UseShellExecute = false, FileName = "node", WindowStyle = ProcessWindowStyle.Hidden, - Arguments = string.Format("\"{0}\"", Path.GetFullPath(CrossPlatform.PathCombine(HostEnvironment.ContentRootPath, settings.Path, "app.js"))), + Arguments = $"\"{Path.GetFullPath(CrossPlatform.PathCombine(HostEnvironment.ContentRootPath, settings.Path, "app.js"))}\"", WorkingDirectory = AppDomain.CurrentDomain.BaseDirectory }; StartInfo.EnvironmentVariables.Add("core.machinekey", Configuration["core:machinekey"]); @@ -161,7 +161,7 @@ namespace ASC.Socket.IO.Svc Thread.Sleep(PingInterval); var error = false; - WebSocket = new WebSocket(string.Format("ws://127.0.0.1:{0}/socket.io/?EIO=3&transport=websocket", StartInfo.EnvironmentVariables["port"])); + WebSocket = new WebSocket($"ws://127.0.0.1:{StartInfo.EnvironmentVariables["port"]}/socket.io/?EIO=3&transport=websocket"); WebSocket.SetCookie(new WebSocketSharp.Net.Cookie("authorization", SignalrServiceClient.CreateAuthToken())); WebSocket.EmitOnPing = true; diff --git a/common/services/ASC.SsoAuth.Svc/Launcher.cs b/common/services/ASC.SsoAuth.Svc/Launcher.cs index d195957760..ca8d2e93c9 100644 --- a/common/services/ASC.SsoAuth.Svc/Launcher.cs +++ b/common/services/ASC.SsoAuth.Svc/Launcher.cs @@ -69,7 +69,7 @@ namespace ASC.SsoAuth.Svc UseShellExecute = false, FileName = "node", WindowStyle = ProcessWindowStyle.Hidden, - Arguments = string.Format("\"{0}\"", Path.GetFullPath(CrossPlatform.PathCombine(HostEnvironment.ContentRootPath, cfg.Path, "app.js"))), + Arguments = $"\"{Path.GetFullPath(CrossPlatform.PathCombine(HostEnvironment.ContentRootPath, cfg.Path, "app.js"))}\"", WorkingDirectory = AppDomain.CurrentDomain.BaseDirectory }; diff --git a/common/services/ASC.Studio.Notify/Program.cs b/common/services/ASC.Studio.Notify/Program.cs index b3810aa522..875fb5124d 100644 --- a/common/services/ASC.Studio.Notify/Program.cs +++ b/common/services/ASC.Studio.Notify/Program.cs @@ -24,7 +24,7 @@ using StackExchange.Redis.Extensions.Newtonsoft; namespace ASC.Studio.Notify { - public class Program + public static class Program { public async static Task Main(string[] args) { diff --git a/common/services/ASC.TelegramService/Commands/UserCommands.cs b/common/services/ASC.TelegramService/Commands/UserCommands.cs index c1ee72a456..1cd072b2f6 100644 --- a/common/services/ASC.TelegramService/Commands/UserCommands.cs +++ b/common/services/ASC.TelegramService/Commands/UserCommands.cs @@ -45,11 +45,16 @@ namespace ASC.TelegramService.Commands CachedTelegramDao = cachedTelegramDao.Value; } - [Command("start")] - public async Task StartCommand(string token) - { - if (string.IsNullOrEmpty(token)) return; + [Command("start")] + public Task StartCommand(string token) + { + if (string.IsNullOrEmpty(token)) return Task.CompletedTask; + + return InternalStartCommand(token); + } + private async Task InternalStartCommand(string token) + { var user = MemoryCache.Default.Get(token); if (user != null) { diff --git a/common/services/ASC.TelegramService/Core/Core.cs b/common/services/ASC.TelegramService/Core/Core.cs index 6e581a8079..387a2e1a2f 100644 --- a/common/services/ASC.TelegramService/Core/Core.cs +++ b/common/services/ASC.TelegramService/Core/Core.cs @@ -107,7 +107,7 @@ namespace ASC.TelegramService.Core var reg = cmdReg.Match(msg.Text); var args = argsReg.Matches(reg.Groups[2].Value); - return new TelegramCommand(msg, reg.Groups[1].Value.ToLowerInvariant(), args.Count > 0 ? args.Cast<Match>().Select(a => a.Value).ToArray() : null); + return new TelegramCommand(msg, reg.Groups[1].Value.ToLowerInvariant(), args.Count > 0 ? args.Select(a => a.Value).ToArray() : null); } private object[] ParseParams(MethodInfo cmd, string[] args) @@ -116,20 +116,20 @@ namespace ASC.TelegramService.Core var cmdArgs = cmd.GetParameters(); - if (cmdArgs.Any() && args == null || cmdArgs.Count() != args.Count()) throw new Exception("Wrong parameters count"); - for (var i = 0; i < cmdArgs.Count(); i++) + if (cmdArgs.Length > 0 && args == null || cmdArgs.Length != args.Length) throw new Exception("Wrong parameters count"); + for (var i = 0; i < cmdArgs.Length; i++) { var type = cmdArgs[i].ParameterType; - + var arg = args[i]; if (type == typeof(string)) { - parsedParams.Add(args[i]); + parsedParams.Add(arg); continue; } if (!parsers.ContainsKey(type)) throw new Exception(string.Format("No parser found for type '{0}'", type)); - parsedParams.Add(parsers[cmdArgs[i].ParameterType].FromString(args[i])); + parsedParams.Add(parsers[type].FromString(arg)); } return parsedParams.ToArray(); @@ -141,7 +141,7 @@ namespace ASC.TelegramService.Core { var cmd = ParseCommand(msg); - if (!commands.ContainsKey(cmd.CommandName)) throw new Exception(string.Format("No handler found for command '{0}'", cmd.CommandName)); + if (!commands.ContainsKey(cmd.CommandName)) throw new Exception($"No handler found for command '{cmd.CommandName}'"); var command = commands[cmd.CommandName]; var context = (CommandContext)ServiceProvider.CreateScope().ServiceProvider.GetService(contexts[cmd.CommandName]); @@ -186,7 +186,7 @@ namespace ASC.TelegramService.Core public abstract class ParamParser<T> : ParamParser { - public ParamParser() : base(typeof(T)) { } + protected ParamParser() : base(typeof(T)) { } public override abstract object FromString(string arg); public override abstract string ToString(object arg); diff --git a/common/services/ASC.TelegramService/Program.cs b/common/services/ASC.TelegramService/Program.cs index 8d75d54535..a1f4a5c900 100644 --- a/common/services/ASC.TelegramService/Program.cs +++ b/common/services/ASC.TelegramService/Program.cs @@ -39,7 +39,7 @@ using Microsoft.Extensions.Hosting; namespace ASC.TelegramService { - public class Program + public static class Program { public async static Task Main(string[] args) { diff --git a/common/services/ASC.TelegramService/Startup.cs b/common/services/ASC.TelegramService/Startup.cs index fbe9944c0b..38ed2fc431 100644 --- a/common/services/ASC.TelegramService/Startup.cs +++ b/common/services/ASC.TelegramService/Startup.cs @@ -30,9 +30,6 @@ using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Hosting; -using StackExchange.Redis.Extensions.Core.Configuration; -using StackExchange.Redis.Extensions.Newtonsoft; - namespace ASC.TelegramService { public class Startup : BaseStartup diff --git a/common/services/ASC.TelegramService/TelegramHandler.cs b/common/services/ASC.TelegramService/TelegramHandler.cs index 0bddd8cf86..9035834a2d 100644 --- a/common/services/ASC.TelegramService/TelegramHandler.cs +++ b/common/services/ASC.TelegramService/TelegramHandler.cs @@ -61,13 +61,19 @@ namespace ASC.TelegramService Clients = new Dictionary<int, TenantTgClient>(); ServicePointManager.SecurityProtocol |= SecurityProtocolType.Tls12 | SecurityProtocolType.Tls13; } + + public Task SendMessage(NotifyMessage msg) + { + if (string.IsNullOrEmpty(msg.To)) return Task.CompletedTask; + if (!Clients.ContainsKey(msg.Tenant)) return Task.CompletedTask; + + return InternalSendMessage(msg); + } - public async Task SendMessage(NotifyMessage msg) + private async Task InternalSendMessage(NotifyMessage msg) { var scope = ServiceProvider.CreateScope(); - var cachedTelegramDao = scope.ServiceProvider.GetService<IOptionsSnapshot<CachedTelegramDao>>().Value; - if (string.IsNullOrEmpty(msg.To)) return; - if (!Clients.ContainsKey(msg.Tenant)) return; + var cachedTelegramDao = scope.ServiceProvider.GetService<IOptionsSnapshot<CachedTelegramDao>>().Value; var client = Clients[msg.Tenant].Client; @@ -106,9 +112,8 @@ namespace ASC.TelegramService var telegramHelper = scope.ServiceProvider.GetService<TelegramHelper>(); var newClient = telegramHelper.InitClient(token, proxy); - if (Clients.ContainsKey(tenantId)) + if (Clients.TryGetValue(tenantId, out var client)) { - var client = Clients[tenantId]; client.TokenLifeSpan = tokenLifespan; if (token != client.Token || proxy != client.Proxy) @@ -156,10 +161,14 @@ namespace ASC.TelegramService MemoryCache.Default.Set(token, userKey, dateExpires); } + private Task OnMessage(object sender, MessageEventArgs e, TelegramBotClient client, int tenantId) + { + if (string.IsNullOrEmpty(e.Message.Text) || e.Message.Text[0] != '/') return Task.CompletedTask; + return InternalOnMessage(sender, e, client, tenantId); + } - private async Task OnMessage(object sender, MessageEventArgs e, TelegramBotClient client, int tenantId) + private async Task InternalOnMessage(object sender, MessageEventArgs e, TelegramBotClient client, int tenantId) { - if (string.IsNullOrEmpty(e.Message.Text) || e.Message.Text[0] != '/') return; await Command.HandleCommand(e.Message, client, tenantId); } @@ -176,7 +185,7 @@ namespace ASC.TelegramService } } - public class TelegramHandlerExtension + public static class TelegramHandlerExtension { public static void Register(DIHelper services) { diff --git a/common/services/ASC.TelegramService/TelegramLauncher.cs b/common/services/ASC.TelegramService/TelegramLauncher.cs index 0f022e809a..c46a10ac12 100644 --- a/common/services/ASC.TelegramService/TelegramLauncher.cs +++ b/common/services/ASC.TelegramService/TelegramLauncher.cs @@ -100,7 +100,7 @@ namespace ASC.TelegramService } } - public class TelegramLauncherExtension + public static class TelegramLauncherExtension { public static void Register(DIHelper services) { diff --git a/common/services/ASC.Thumbnails.Svc/ThumbnailsServiceLauncher.cs b/common/services/ASC.Thumbnails.Svc/ThumbnailsServiceLauncher.cs index 3a2742a4ea..572159d9fd 100644 --- a/common/services/ASC.Thumbnails.Svc/ThumbnailsServiceLauncher.cs +++ b/common/services/ASC.Thumbnails.Svc/ThumbnailsServiceLauncher.cs @@ -67,7 +67,7 @@ namespace ASC.Thumbnails.Svc UseShellExecute = false, FileName = "node", WindowStyle = ProcessWindowStyle.Hidden, - Arguments = string.Format("\"{0}\"", Path.GetFullPath(CrossPlatform.PathCombine(HostEnvironment.ContentRootPath, settings.Path, "index.js"))), + Arguments = $"\"{Path.GetFullPath(CrossPlatform.PathCombine(HostEnvironment.ContentRootPath, settings.Path, "index.js"))}\"", WorkingDirectory = AppDomain.CurrentDomain.BaseDirectory }; diff --git a/common/services/ASC.UrlShortener.Svc/Program.cs b/common/services/ASC.UrlShortener.Svc/Program.cs index 0a5dc6868d..f05d2b4c6b 100644 --- a/common/services/ASC.UrlShortener.Svc/Program.cs +++ b/common/services/ASC.UrlShortener.Svc/Program.cs @@ -26,87 +26,87 @@ using System.Collections.Generic; using System.IO; -using System.Threading.Tasks; - +using System.Threading.Tasks; + using ASC.Api.Core; using ASC.Common; using ASC.Common.DependencyInjection; -using ASC.Common.Utils; - -using Autofac; -using Autofac.Extensions.DependencyInjection; - -using Microsoft.AspNetCore.Hosting; +using ASC.Common.Utils; + +using Autofac; +using Autofac.Extensions.DependencyInjection; + +using Microsoft.AspNetCore.Hosting; using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; -using Microsoft.Extensions.Hosting; - -using StackExchange.Redis.Extensions.Core.Configuration; -using StackExchange.Redis.Extensions.Newtonsoft; - +using Microsoft.Extensions.Hosting; + +using StackExchange.Redis.Extensions.Core.Configuration; +using StackExchange.Redis.Extensions.Newtonsoft; + namespace ASC.UrlShortener.Svc -{ -public class Program -{ -public async static Task Main(string[] args) -{ - var host = CreateHostBuilder(args).Build(); - - await host.RunAsync(); - } - - public static IHostBuilder CreateHostBuilder(string[] args) => - Host.CreateDefaultBuilder(args) - .UseSystemd() +{ + public static class Program + { + public async static Task Main(string[] args) + { + var host = CreateHostBuilder(args).Build(); + + await host.RunAsync(); + } + + public static IHostBuilder CreateHostBuilder(string[] args) => + Host.CreateDefaultBuilder(args) + .UseSystemd() .UseWindowsService() - .UseServiceProviderFactory(new AutofacServiceProviderFactory()) + .UseServiceProviderFactory(new AutofacServiceProviderFactory()) .ConfigureWebHostDefaults(webBuilder => webBuilder.UseStartup<BaseWorkerStartup>()) .ConfigureAppConfiguration((hostContext, config) => { var buided = config.Build(); var path = buided["pathToConf"]; - + if (!Path.IsPathRooted(path)) { path = Path.GetFullPath(CrossPlatform.PathCombine(hostContext.HostingEnvironment.ContentRootPath, path)); } - + config.SetBasePath(path); - - var env = hostContext.Configuration.GetValue("ENVIRONMENT", "Production"); - + + var env = hostContext.Configuration.GetValue("ENVIRONMENT", "Production"); + config.AddJsonFile("appsettings.json") - .AddJsonFile($"appsettings.{env}.json", true) - .AddJsonFile($"urlshortener.{env}.json", true) - .AddJsonFile("storage.json") - .AddJsonFile("kafka.json") - .AddJsonFile($"kafka.{env}.json", true) + .AddJsonFile($"appsettings.{env}.json", true) + .AddJsonFile($"urlshortener.{env}.json", true) + .AddJsonFile("storage.json") + .AddJsonFile("kafka.json") + .AddJsonFile($"kafka.{env}.json", true) .AddJsonFile("redis.json") - .AddJsonFile($"redis.{env}.json", true) - .AddEnvironmentVariables() - .AddCommandLine(args) - .AddInMemoryCollection(new Dictionary<string, string> - { - {"pathToConf", path } - } + .AddJsonFile($"redis.{env}.json", true) + .AddEnvironmentVariables() + .AddCommandLine(args) + .AddInMemoryCollection(new Dictionary<string, string> + { + {"pathToConf", path } + } ); }) .ConfigureServices((hostContext, services) => - { + { services.AddMemoryCache(); - - var diHelper = new DIHelper(services); + + var diHelper = new DIHelper(services); services.AddHostedService<UrlShortenerServiceLauncher>(); - diHelper.TryAdd<UrlShortenerServiceLauncher>(); - + diHelper.TryAdd<UrlShortenerServiceLauncher>(); + services.AddStackExchangeRedisExtensions<NewtonsoftSerializer>(hostContext.Configuration.GetSection("Redis").Get<RedisConfiguration>()); }) - .ConfigureContainer<ContainerBuilder>((context, builder) => - { - builder.Register(context.Configuration, false, false); - }) + .ConfigureContainer<ContainerBuilder>((context, builder) => + { + builder.Register(context.Configuration, false, false); + }) .ConfigureNLogLogging(); } } diff --git a/common/services/ASC.UrlShortener.Svc/UrlShortenerService.cs b/common/services/ASC.UrlShortener.Svc/UrlShortenerService.cs index deb3c76561..7e189d8bf5 100644 --- a/common/services/ASC.UrlShortener.Svc/UrlShortenerService.cs +++ b/common/services/ASC.UrlShortener.Svc/UrlShortenerService.cs @@ -50,7 +50,6 @@ namespace ASC.UrlShortener.Svc private readonly IHostEnvironment hostEnvironment; private readonly ConfigurationExtension configurationExtension; - private ProcessStartInfo processStartInfo; private Process process; @@ -74,7 +73,7 @@ namespace ASC.UrlShortener.Svc { Stop(); - processStartInfo = GetProcessStartInfo(); + var processStartInfo = GetProcessStartInfo(); process = Process.Start(processStartInfo); } catch (Exception e) @@ -116,7 +115,7 @@ namespace ASC.UrlShortener.Svc UseShellExecute = false, FileName = "node", WindowStyle = ProcessWindowStyle.Hidden, - Arguments = string.Format("\"{0}\"", Path.GetFullPath(CrossPlatform.PathCombine(hostEnvironment.ContentRootPath, path))), + Arguments = $"\"{Path.GetFullPath(CrossPlatform.PathCombine(hostEnvironment.ContentRootPath, path))}\"", WorkingDirectory = AppDomain.CurrentDomain.BaseDirectory }; @@ -140,9 +139,9 @@ namespace ASC.UrlShortener.Svc if (splited.Length < 2) continue; - if (dict.ContainsKey(splited[0])) + if (dict.TryGetValue(splited[0], out var value)) { - startInfo.EnvironmentVariables.Add("sql:" + dict[splited[0]], splited[1]); + startInfo.EnvironmentVariables.Add("sql:" + dict[value], splited[1]); } } diff --git a/common/services/ASC.Webhooks.Service/Program.cs b/common/services/ASC.Webhooks.Service/Program.cs index 931170ee42..17c2da953a 100644 --- a/common/services/ASC.Webhooks.Service/Program.cs +++ b/common/services/ASC.Webhooks.Service/Program.cs @@ -22,7 +22,7 @@ using StackExchange.Redis.Extensions.Newtonsoft; namespace ASC.Webhooks.Service { - public class Program + public static class Program { public async static Task Main(string[] args) { diff --git a/common/services/ASC.Webhooks.Service/WebhookSender.cs b/common/services/ASC.Webhooks.Service/WebhookSender.cs index 929d49bc8d..0055177d9c 100644 --- a/common/services/ASC.Webhooks.Service/WebhookSender.cs +++ b/common/services/ASC.Webhooks.Service/WebhookSender.cs @@ -111,7 +111,7 @@ namespace ASC.Webhooks.Service { var responseContent = streamReader.ReadToEnd(); responsePayload = JsonSerializer.Serialize(responseContent); - }; + } dbWorker.UpdateWebhookJournal(id, status, responsePayload, responseHeaders, requestHeaders); } diff --git a/common/services/ASC.Webhooks.Service/WorkerService.cs b/common/services/ASC.Webhooks.Service/WorkerService.cs index 402cdab757..3b4c0173f3 100644 --- a/common/services/ASC.Webhooks.Service/WorkerService.cs +++ b/common/services/ASC.Webhooks.Service/WorkerService.cs @@ -13,7 +13,7 @@ namespace ASC.Webhooks.Service [Singletone] public class WorkerService { - private readonly int? threadCount = 10; + private readonly int? threadCount; private readonly WebhookSender webhookSender; private readonly ConcurrentQueue<WebhookRequest> queue; private CancellationToken cancellationToken; diff --git a/products/ASC.CRM/Server/Api/ContactInfosController.cs b/products/ASC.CRM/Server/Api/ContactInfosController.cs index bdefcc5b85..8ac80bf1e2 100644 --- a/products/ASC.CRM/Server/Api/ContactInfosController.cs +++ b/products/ASC.CRM/Server/Api/ContactInfosController.cs @@ -537,7 +537,7 @@ namespace ASC.CRM.Api return wrapper; } - private static ContactInfo FromContactInfoDto(ContactInfoDto contactInfoDto) + private ContactInfo FromContactInfoDto(ContactInfoDto contactInfoDto) { return new ContactInfo { diff --git a/products/ASC.CRM/Server/Api/InvoicesController.cs b/products/ASC.CRM/Server/Api/InvoicesController.cs index 801bae651b..80168ce318 100644 --- a/products/ASC.CRM/Server/Api/InvoicesController.cs +++ b/products/ASC.CRM/Server/Api/InvoicesController.cs @@ -192,9 +192,9 @@ namespace ASC.CRM.Api ) { if (!String.IsNullOrEmpty(entityType) && !( - String.Compare(entityType, "contact", true) == 0 || - String.Compare(entityType, "opportunity", true) == 0 || - String.Compare(entityType, "case", true) == 0)) + string.Equals(entityType, "contact", StringComparison.CurrentCultureIgnoreCase) || + string.Equals(entityType, "opportunity", StringComparison.CurrentCultureIgnoreCase) || + string.Equals(entityType, "case", StringComparison.CurrentCultureIgnoreCase))) throw new ArgumentException(); IEnumerable<InvoiceBaseDto> result; diff --git a/products/ASC.CRM/Server/Api/RelationshipEventsController.cs b/products/ASC.CRM/Server/Api/RelationshipEventsController.cs index 945a90d51d..0194c26a64 100644 --- a/products/ASC.CRM/Server/Api/RelationshipEventsController.cs +++ b/products/ASC.CRM/Server/Api/RelationshipEventsController.cs @@ -387,8 +387,8 @@ namespace ASC.CRM.Api if (!string.IsNullOrEmpty(entityType) && !( - string.Compare(entityType, "opportunity", StringComparison.OrdinalIgnoreCase) == 0 || - string.Compare(entityType, "case", StringComparison.OrdinalIgnoreCase) == 0) + string.Equals(entityType, "opportunity", StringComparison.OrdinalIgnoreCase) || + string.Equals(entityType, "case", StringComparison.OrdinalIgnoreCase)) ) throw new ArgumentException(); @@ -458,14 +458,14 @@ namespace ASC.CRM.Api var extension = Path.GetExtension(file.Title); if (extension == null) continue; - var fileInfo = string.Format("{0} ({1})", file.Title, extension.ToUpper()); + var fileInfo = $"{file.Title} ({extension.ToUpper()})"; if (!fileListInfoHashtable.ContainsKey(fileInfo)) { fileListInfoHashtable.Add(fileInfo, file.DownloadUrl); } else { - fileInfo = string.Format("{0} ({1}, {2})", file.Title, extension.ToUpper(), file.UniqID); + fileInfo = $"{file.Title} ({extension.ToUpper()}, {file.UniqID})"; fileListInfoHashtable.Add(fileInfo, file.DownloadUrl); } } diff --git a/products/ASC.CRM/Server/Api/TasksController.cs b/products/ASC.CRM/Server/Api/TasksController.cs index 7c4775c80d..170ae0720d 100644 --- a/products/ASC.CRM/Server/Api/TasksController.cs +++ b/products/ASC.CRM/Server/Api/TasksController.cs @@ -103,9 +103,9 @@ namespace ASC.CRM.Api if (!string.IsNullOrEmpty(entityType) && !( - string.Compare(entityType, "contact", StringComparison.OrdinalIgnoreCase) == 0 || - string.Compare(entityType, "opportunity", StringComparison.OrdinalIgnoreCase) == 0 || - string.Compare(entityType, "case", StringComparison.OrdinalIgnoreCase) == 0) + string.Equals(entityType, "contact", StringComparison.OrdinalIgnoreCase)|| + string.Equals(entityType, "opportunity", StringComparison.OrdinalIgnoreCase)|| + string.Equals(entityType, "case", StringComparison.OrdinalIgnoreCase)) ) throw new ArgumentException(); @@ -303,8 +303,8 @@ namespace ASC.CRM.Api if (!string.IsNullOrEmpty(entityType) && !( - string.Compare(entityType, "opportunity", StringComparison.OrdinalIgnoreCase) == 0 || - string.Compare(entityType, "case", StringComparison.OrdinalIgnoreCase) == 0 + string.Equals(entityType, "opportunity", StringComparison.OrdinalIgnoreCase)|| + string.Equals(entityType, "case", StringComparison.OrdinalIgnoreCase) ) || categoryId <= 0) throw new ArgumentException(); @@ -398,8 +398,8 @@ namespace ASC.CRM.Api if ( !string.IsNullOrEmpty(entityType) && - !(string.Compare(entityType, "opportunity", StringComparison.OrdinalIgnoreCase) == 0 || - string.Compare(entityType, "case", StringComparison.OrdinalIgnoreCase) == 0) + !(string.Equals(entityType, "opportunity", StringComparison.OrdinalIgnoreCase) || + string.Equals(entityType, "case", StringComparison.OrdinalIgnoreCase)) ) throw new ArgumentException(); @@ -508,8 +508,8 @@ namespace ASC.CRM.Api var isNotify = inDto.isNotify; if (!string.IsNullOrEmpty(entityType) && - !(string.Compare(entityType, "opportunity", StringComparison.OrdinalIgnoreCase) == 0 || - string.Compare(entityType, "case", StringComparison.OrdinalIgnoreCase) == 0 + !(string.Equals(entityType, "opportunity", StringComparison.OrdinalIgnoreCase) || + string.Equals(entityType, "case", StringComparison.OrdinalIgnoreCase) ) || categoryid <= 0) throw new ArgumentException(); diff --git a/products/ASC.CRM/Server/Api/UtilsController.cs b/products/ASC.CRM/Server/Api/UtilsController.cs index cb8a780de1..63027453bd 100644 --- a/products/ASC.CRM/Server/Api/UtilsController.cs +++ b/products/ASC.CRM/Server/Api/UtilsController.cs @@ -304,7 +304,7 @@ namespace ASC.CRM.Api var companyAddress = JsonSerializer.Serialize(new { - type = AddressCategory.Billing.ToString(), + type = nameof(AddressCategory.Billing), street, city, state, diff --git a/products/ASC.CRM/Server/Api/VoipController.cs b/products/ASC.CRM/Server/Api/VoipController.cs index 0e2dd31590..8272fb092f 100644 --- a/products/ASC.CRM/Server/Api/VoipController.cs +++ b/products/ASC.CRM/Server/Api/VoipController.cs @@ -390,7 +390,7 @@ namespace ASC.CRM.Api return new { queue = number.Settings.Queue, pause = number.Settings.Pause }; } - var files = _storageFactory.GetStorage("", "crm").ListFiles("voip", "default/" + AudioType.Queue.ToString().ToLower(), "*.*", true); + var files = _storageFactory.GetStorage("", "crm").ListFiles("voip", "default/" + nameof(AudioType.Queue).ToLower(), "*.*", true); var file = files.FirstOrDefault(); return new { queue = new Queue(null, "Default", 5, file != null ? _commonLinkUtility.GetFullAbsolutePath(file.ToString()) : "", 5), pause = false }; } diff --git a/products/ASC.CRM/Server/Classes/CRMSettings.cs b/products/ASC.CRM/Server/Classes/CRMSettings.cs index e88f7d54a6..15b2a2ca19 100644 --- a/products/ASC.CRM/Server/Classes/CRMSettings.cs +++ b/products/ASC.CRM/Server/Classes/CRMSettings.cs @@ -162,7 +162,7 @@ namespace ASC.Web.CRM.Classes var languageName = System.Threading.Thread.CurrentThread.CurrentCulture.TwoLetterISOLanguageName; - var findedCurrency = currencyProvider.GetAll().Find(item => String.Compare(item.CultureName, languageName, true) == 0); + var findedCurrency = currencyProvider.GetAll().Find(item => string.Equals(item.CultureName, languageName, StringComparison.OrdinalIgnoreCase)); return new CrmSettings() { diff --git a/products/ASC.CRM/Server/Classes/CSVReader.cs b/products/ASC.CRM/Server/Classes/CSVReader.cs index 739d2a14f5..f1e71f2a0a 100644 --- a/products/ASC.CRM/Server/Classes/CSVReader.cs +++ b/products/ASC.CRM/Server/Classes/CSVReader.cs @@ -157,7 +157,7 @@ namespace ASC.Web.CRM.Classes // Build the list of objects in the line List<object> objects = new List<object>(); - while (currentLine != "") + while (currentLine.Length != 0) objects.Add(ReadNextObject()); return objects; } @@ -177,7 +177,7 @@ namespace ASC.Web.CRM.Classes quoted = true; // Find the end of the next value - string nextObjectString = ""; + string nextObjectString; int i = 0; int len = currentLine.Length; bool foundEnd = false; @@ -185,17 +185,17 @@ namespace ASC.Web.CRM.Classes { // Check if we've hit the end of the string if ((!quoted && i == len) // non-quoted strings end with a comma or end of line - || (!quoted && currentLine.Substring(i, 1) == FieldSep) + || (!quoted && string.CompareOrdinal(currentLine, i, FieldSep, 0, 1) == 0) // quoted strings end with a quote followed by a comma or end of line || (quoted && i == len - 1 && currentLine.EndsWith("\"")) - || (quoted && currentLine.Substring(i, 2) == "\"" + FieldSep)) + || (quoted && string.CompareOrdinal(currentLine, i, "\"" + FieldSep, 0, 2) == 0)) foundEnd = true; else i++; } if (quoted) { - if (i > len || !currentLine.Substring(i, 1).StartsWith("\"")) + if (i > len || currentLine[i] != '\"') throw new FormatException("Invalid CSV format: " + currentLine.Substring(0, i)); i++; } @@ -231,7 +231,7 @@ namespace ASC.Web.CRM.Classes { // Read the CSV data into rows List<List<object>> rows = new List<List<object>>(); - List<object> readRow = null; + List<object> readRow; while ((readRow = ReadRow()) != null) rows.Add(readRow); diff --git a/products/ASC.CRM/Server/Classes/ContactPhotoManager.cs b/products/ASC.CRM/Server/Classes/ContactPhotoManager.cs index 4d3264e78f..1e5f55a955 100644 --- a/products/ASC.CRM/Server/Classes/ContactPhotoManager.cs +++ b/products/ASC.CRM/Server/Classes/ContactPhotoManager.cs @@ -84,7 +84,8 @@ namespace ASC.Web.CRM.Classes public readonly WebImageSupplier _webImageSupplier; private readonly DistributedTaskQueue _resizeQueue; private readonly ICacheNotify<ContactPhotoManagerCacheItem> _cacheNotify; - private readonly ICache _cache; + private readonly ICache _cache; + private readonly IHttpClientFactory _clientFactory; private const string PhotosBaseDirName = "photos"; private const string PhotosDefaultTmpDirName = "temp"; @@ -103,14 +104,16 @@ namespace ASC.Web.CRM.Classes IOptionsMonitor<ILog> logger, ICache cache, ICacheNotify<ContactPhotoManagerCacheItem> cacheNotify, - DistributedTaskQueueOptionsManager optionsQueue) + DistributedTaskQueueOptionsManager optionsQueue, + IHttpClientFactory clientFactory) { _global = global; _webImageSupplier = webImageSupplier; _cacheNotify = cacheNotify; _cache = cache; _resizeQueue = optionsQueue.Get<ResizeWorkerItem>(); - _logger = logger.Get("ASC.CRM"); + _logger = logger.Get("ASC.CRM"); + _clientFactory = clientFactory; _cacheNotify.Subscribe((x) => { @@ -349,14 +352,11 @@ namespace ASC.Web.CRM.Classes lock (locker) { - _resizeQueue.GetTasks<ResizeWorkerItem>().Where(item => item.ContactID == contactID) - .All(item => - { - _resizeQueue.RemoveTask(item.Id); - - return true; - }); - + foreach(var item in _resizeQueue.GetTasks<ResizeWorkerItem>().Where(item => item.ContactID == contactID)) + { + _resizeQueue.RemoveTask(item.Id); + } + var photoDirectory = !isTmpDir ? BuildFileDirectory(contactID) : (String.IsNullOrEmpty(tmpDirName) ? BuildFileTmpDirectory(contactID) : BuildFileTmpDirectory(tmpDirName)); @@ -544,7 +544,7 @@ namespace ASC.Web.CRM.Classes var request = new HttpRequestMessage(); request.RequestUri = new Uri(imageUrl); - using var httpClient = new HttpClient(); + var httpClient = _clientFactory.CreateClient(); using var response = httpClient.Send(request); using (var inputStream = response.Content.ReadAsStream()) { @@ -580,7 +580,7 @@ namespace ASC.Web.CRM.Classes var request = new HttpRequestMessage(); request.RequestUri = new Uri(imageUrl); - using var httpClient = new HttpClient(); + var httpClient = _clientFactory.CreateClient(); using var response = httpClient.Send(request); using (var inputStream = response.Content.ReadAsStream()) { diff --git a/products/ASC.CRM/Server/Classes/Global.cs b/products/ASC.CRM/Server/Classes/Global.cs index 5bc7022eb3..bc3eea5866 100644 --- a/products/ASC.CRM/Server/Classes/Global.cs +++ b/products/ASC.CRM/Server/Classes/Global.cs @@ -206,7 +206,7 @@ namespace ASC.Web.CRM.Classes { var br = new MemoryStream(); var data = new byte[1024]; - var readed = 0; + int readed; while ((readed = inputStream.Read(data, 0, data.Length)) > 0) { diff --git a/products/ASC.CRM/Server/Classes/InvoiceFormattedData.cs b/products/ASC.CRM/Server/Classes/InvoiceFormattedData.cs index 8fee0d4dc9..be51671ae1 100644 --- a/products/ASC.CRM/Server/Classes/InvoiceFormattedData.cs +++ b/products/ASC.CRM/Server/Classes/InvoiceFormattedData.cs @@ -341,9 +341,7 @@ namespace ASC.Web.CRM.Classes //data.TableFooterRows.Add(new Tuple<string, string>(CRMInvoiceResource.ResourceManager.GetString("Discount", cultureInfo), "-" + discount.ToString(CultureInfo.InvariantCulture))); data.TableTotalRow = - new Tuple<string, string>( - string.Format("{0} ({1})", CRMInvoiceResource.ResourceManager.GetString("Total", cultureInfo), - invoice.Currency), amount.ToString(CultureInfo.InvariantCulture)); + new Tuple<string, string>($"{CRMInvoiceResource.ResourceManager.GetString("Total", cultureInfo)} ({invoice.Currency})", amount.ToString(CultureInfo.InvariantCulture)); #endregion @@ -671,9 +669,7 @@ namespace ASC.Web.CRM.Classes //data.TableFooterRows.Add(new Tuple<string, string>(CRMInvoiceResource.ResourceManager.GetString("Discount", cultureInfo), "-" + discount.ToString(CultureInfo.InvariantCulture))); data.TableTotalRow = - new Tuple<string, string>( - string.Format("{0} ({1})", CRMInvoiceResource.ResourceManager.GetString("Total", cultureInfo), - invoice.Currency), amount.ToString(CultureInfo.InvariantCulture)); + new Tuple<string, string>($"{CRMInvoiceResource.ResourceManager.GetString("Total", cultureInfo)} ({invoice.Currency})", amount.ToString(CultureInfo.InvariantCulture)); #endregion diff --git a/products/ASC.CRM/Server/Classes/LocalizedEnumConverter.cs b/products/ASC.CRM/Server/Classes/LocalizedEnumConverter.cs index 24875c55e5..91d5a78297 100644 --- a/products/ASC.CRM/Server/Classes/LocalizedEnumConverter.cs +++ b/products/ASC.CRM/Server/Classes/LocalizedEnumConverter.cs @@ -87,7 +87,7 @@ namespace ASC.CRM.Classes /// <returns></returns> private LookupTable GetLookupTable(CultureInfo culture) { - LookupTable result = null; + LookupTable result; if (culture == null) culture = CultureInfo.CurrentCulture; @@ -116,7 +116,7 @@ namespace ASC.CRM.Classes private string GetValueText(CultureInfo culture, object value) { Type type = value.GetType(); - string resourceName = string.Format("{0}_{1}", type.Name, value.ToString()); + string resourceName = $"{type.Name}_{value}"; string result = _resourceManager.GetString(resourceName, culture); if (result == null) result = resourceName; @@ -174,7 +174,7 @@ namespace ASC.CRM.Classes } else { - result = string.Format("{0}, {1}", result, valueText); + result = $"{result}, {valueText}"; } } } @@ -191,7 +191,7 @@ namespace ASC.CRM.Classes private object GetValue(CultureInfo culture, string text) { LookupTable lookupTable = GetLookupTable(culture); - object result = null; + object result; lookupTable.TryGetValue(text, out result); return result; } @@ -203,7 +203,7 @@ namespace ASC.CRM.Classes ulong result = 0; foreach (string textValue in textValues) { - object value = null; + object value; string trimmedTextValue = textValue.Trim(); if (!lookupTable.TryGetValue(trimmedTextValue, out value)) { diff --git a/products/ASC.CRM/Server/Core/Dao/AbstractDao.cs b/products/ASC.CRM/Server/Core/Dao/AbstractDao.cs index fade236b46..74c47ce810 100644 --- a/products/ASC.CRM/Server/Core/Dao/AbstractDao.cs +++ b/products/ASC.CRM/Server/Core/Dao/AbstractDao.cs @@ -296,9 +296,9 @@ namespace ASC.CRM.Core.Dao { var tenant = "tenant_id"; - if (!table.Contains(" ")) return tenant; + if (!table.Contains(' ')) return tenant; - return table.Substring(table.IndexOf(" ")).Trim() + "." + tenant; + return table.Substring(table.IndexOf(' ')).Trim() + "." + tenant; } protected static Guid ToGuid(object guid) diff --git a/products/ASC.CRM/Server/Core/Dao/ContactDao.cs b/products/ASC.CRM/Server/Core/Dao/ContactDao.cs index 102ecfc8d2..b23799af54 100644 --- a/products/ASC.CRM/Server/Core/Dao/ContactDao.cs +++ b/products/ASC.CRM/Server/Core/Dao/ContactDao.cs @@ -927,7 +927,7 @@ namespace ASC.CRM.Core.Dao } } - return GetContacts(title, null, -1, -1, isCompany ? ContactListViewType.Company : ContactListViewType.Person, DateTime.MinValue, DateTime.MinValue, 0, 0, null); + return GetContacts(title, null, -1, -1, ContactListViewType.Person, DateTime.MinValue, DateTime.MinValue, 0, 0, null); } public void RemoveMember(int[] peopleID) @@ -1136,7 +1136,7 @@ namespace ASC.CRM.Core.Dao String title; int companyID; - var displayName = String.Empty; + string displayName; if (contact is Company) { @@ -1344,7 +1344,7 @@ namespace ASC.CRM.Core.Dao String title; int companyID; - var displayName = String.Empty; + string displayName; if (contact is Company) { diff --git a/products/ASC.CRM/Server/Core/Dao/CustomFieldDao.cs b/products/ASC.CRM/Server/Core/Dao/CustomFieldDao.cs index 501a4ae520..893d1d2199 100644 --- a/products/ASC.CRM/Server/Core/Dao/CustomFieldDao.cs +++ b/products/ASC.CRM/Server/Core/Dao/CustomFieldDao.cs @@ -347,7 +347,7 @@ namespace ASC.CRM.Core.Dao if (fieldType == CustomFieldType.SelectBox) { - if (oldMask == customField.Mask || customField.Mask == "") + if (oldMask == customField.Mask || customField.Mask.Length == 0) { resultMask = oldMask; } diff --git a/products/ASC.CRM/Server/Core/Dao/DealMilestoneDao.cs b/products/ASC.CRM/Server/Core/Dao/DealMilestoneDao.cs index 2912d25878..abe9964464 100644 --- a/products/ASC.CRM/Server/Core/Dao/DealMilestoneDao.cs +++ b/products/ASC.CRM/Server/Core/Dao/DealMilestoneDao.cs @@ -156,7 +156,7 @@ namespace ASC.CRM.Core.Dao public void Edit(DealMilestone item) { if (HaveContactLink(item.ID)) - throw new ArgumentException(String.Format("{0}. {1}.", CRMErrorsResource.BasicCannotBeEdited, CRMErrorsResource.DealMilestoneHasRelatedDeals)); + throw new ArgumentException($"{CRMErrorsResource.BasicCannotBeEdited}. {CRMErrorsResource.DealMilestoneHasRelatedDeals}."); var dbEntity = CrmDbContext.DealMilestones.Find(item.ID); @@ -181,7 +181,7 @@ namespace ASC.CRM.Core.Dao public void Delete(int id) { if (HaveContactLink(id)) - throw new ArgumentException(String.Format("{0}. {1}.", CRMErrorsResource.BasicCannotBeDeleted, CRMErrorsResource.DealMilestoneHasRelatedDeals)); + throw new ArgumentException($"{CRMErrorsResource.BasicCannotBeDeleted}. {CRMErrorsResource.DealMilestoneHasRelatedDeals}."); var dbEntity = CrmDbContext.DealMilestones.Find(id); diff --git a/products/ASC.CRM/Server/Core/Dao/ListItemDao.cs b/products/ASC.CRM/Server/Core/Dao/ListItemDao.cs index c1b1a883ca..b513071245 100644 --- a/products/ASC.CRM/Server/Core/Dao/ListItemDao.cs +++ b/products/ASC.CRM/Server/Core/Dao/ListItemDao.cs @@ -216,7 +216,7 @@ namespace ASC.CRM.Core.Dao .Where(x => x.ListType == listType) .Select(x => new { x.Id, x.Color }) .ToList() - .ForEach(x => result.Add(x.Id.ToString(), x.Color.ToString())); + .ForEach(x => result.Add(x.Id.ToString(), x.Color)); return result; @@ -379,13 +379,13 @@ namespace ASC.CRM.Core.Dao { case ListType.ContactStatus: case ListType.ContactType: - throw new ArgumentException(string.Format("{0}. {1}.", CRMErrorsResource.BasicCannotBeEdited, CRMErrorsResource.HasRelatedContacts)); + throw new ArgumentException($"{CRMErrorsResource.BasicCannotBeEdited}. {CRMErrorsResource.HasRelatedContacts}."); case ListType.TaskCategory: - throw new ArgumentException(string.Format("{0}. {1}.", CRMErrorsResource.BasicCannotBeEdited, CRMErrorsResource.TaskCategoryHasRelatedTasks)); + throw new ArgumentException($"{CRMErrorsResource.BasicCannotBeEdited}. {CRMErrorsResource.TaskCategoryHasRelatedTasks}."); case ListType.HistoryCategory: - throw new ArgumentException(string.Format("{0}. {1}.", CRMErrorsResource.BasicCannotBeEdited, CRMErrorsResource.HistoryCategoryHasRelatedEvents)); + throw new ArgumentException($"{CRMErrorsResource.BasicCannotBeEdited}. {CRMErrorsResource.HistoryCategoryHasRelatedEvents}."); default: - throw new ArgumentException(string.Format("{0}.", CRMErrorsResource.BasicCannotBeEdited)); + throw new ArgumentException($"{CRMErrorsResource.BasicCannotBeEdited}."); } } @@ -496,16 +496,16 @@ namespace ASC.CRM.Core.Dao { case ListType.ContactStatus: case ListType.ContactType: - throw new ArgumentException(string.Format("{0}. {1}.", CRMErrorsResource.BasicCannotBeDeleted, CRMErrorsResource.HasRelatedContacts)); + throw new ArgumentException($"{CRMErrorsResource.BasicCannotBeDeleted}. {CRMErrorsResource.HasRelatedContacts}."); case ListType.TaskCategory: - var exMsg = string.Format("{0}. {1}.", CRMErrorsResource.BasicCannotBeDeleted, CRMErrorsResource.TaskCategoryHasRelatedTasks); + var exMsg = $"{CRMErrorsResource.BasicCannotBeDeleted}. {CRMErrorsResource.TaskCategoryHasRelatedTasks}."; if (itemID == toItemID) throw new ArgumentException(exMsg); ChangeRelativeItemsLink(listType, itemID, toItemID); break; case ListType.HistoryCategory: - throw new ArgumentException(string.Format("{0}. {1}.", CRMErrorsResource.BasicCannotBeDeleted, CRMErrorsResource.HistoryCategoryHasRelatedEvents)); + throw new ArgumentException($"{CRMErrorsResource.BasicCannotBeDeleted}. {CRMErrorsResource.HistoryCategoryHasRelatedEvents}."); default: - throw new ArgumentException(string.Format("{0}.", CRMErrorsResource.BasicCannotBeDeleted)); + throw new ArgumentException($"{CRMErrorsResource.BasicCannotBeDeleted}."); } } diff --git a/products/ASC.CRM/Server/Core/Dao/RelationshipEventDao.cs b/products/ASC.CRM/Server/Core/Dao/RelationshipEventDao.cs index 400cf59c69..b315b17a25 100644 --- a/products/ASC.CRM/Server/Core/Dao/RelationshipEventDao.cs +++ b/products/ASC.CRM/Server/Core/Dao/RelationshipEventDao.cs @@ -257,7 +257,7 @@ namespace ASC.CRM.Core.Dao } } - var itemToUpdate = Query(CrmDbContext.Invoices).FirstOrDefault(x => x.FileId == Convert.ToInt32(file.ID)); + var itemToUpdate = Query(CrmDbContext.Invoices).FirstOrDefault(x => x.FileId == file.ID); itemToUpdate.FileId = 0; diff --git a/products/ASC.CRM/Server/Core/Dao/ReportDao.cs b/products/ASC.CRM/Server/Core/Dao/ReportDao.cs index 50a7bbfd5d..8c92a67f0d 100644 --- a/products/ASC.CRM/Server/Core/Dao/ReportDao.cs +++ b/products/ASC.CRM/Server/Core/Dao/ReportDao.cs @@ -239,7 +239,7 @@ namespace ASC.CRM.Core.Dao case ReportTimePeriod.CurrentWeek: case ReportTimePeriod.PreviousWeek: case ReportTimePeriod.NextWeek: - return string.Format("{0}-{1}", fromDate.ToShortDateString(), toDate.ToShortDateString()); + return $"{fromDate.ToShortDateString()}-{toDate.ToShortDateString()}"; case ReportTimePeriod.CurrentMonth: case ReportTimePeriod.PreviousMonth: case ReportTimePeriod.NextMonth: @@ -247,7 +247,7 @@ namespace ASC.CRM.Core.Dao case ReportTimePeriod.CurrentQuarter: case ReportTimePeriod.PreviousQuarter: case ReportTimePeriod.NextQuarter: - return string.Format("{0}-{1}", fromDate.ToString("Y"), toDate.ToString("Y")); + return $"{fromDate.ToString("Y")}-{toDate.ToString("Y")}"; case ReportTimePeriod.CurrentYear: case ReportTimePeriod.PreviousYear: case ReportTimePeriod.NextYear: @@ -1753,10 +1753,7 @@ namespace ASC.CRM.Core.Dao { var timeSpan = TimeSpan.FromSeconds(duration); - return string.Format("{0}:{1}:{2}", - ((timeSpan.TotalHours < 10 ? "0" : "") + (int)timeSpan.TotalHours), - ((timeSpan.Minutes < 10 ? "0" : "") + timeSpan.Minutes), - ((timeSpan.Seconds < 10 ? "0" : "") + timeSpan.Seconds)); + return $"{(timeSpan.TotalHours < 10 ? "0" : "") + (int)timeSpan.TotalHours}:{(timeSpan.Minutes < 10 ? "0" : "") + timeSpan.Minutes}:{(timeSpan.Seconds < 10 ? "0" : "") + timeSpan.Seconds}"; } #endregion diff --git a/products/ASC.CRM/Server/Core/Dao/SearchDao.cs b/products/ASC.CRM/Server/Core/Dao/SearchDao.cs index fb602f6e28..7042a3f3ac 100644 --- a/products/ASC.CRM/Server/Core/Dao/SearchDao.cs +++ b/products/ASC.CRM/Server/Core/Dao/SearchDao.cs @@ -343,7 +343,7 @@ namespace ASC.CRM.Core.Dao result.Add(new SearchResultItem { - Name = x.IsCompany ? x.CompanyName : String.Format("{0} {1}", x.FirstName, x.LastName), + Name = x.IsCompany ? x.CompanyName : $"{x.FirstName} {x.LastName}", Description = HtmlUtil.GetText(x.Notes, 120), URL = String.Concat(_pathProvider.BaseAbsolutePath, String.Format("default.aspx?id={0}", x.Id)), Date = _tenantUtil.DateTimeFromUtc(x.CreateOn), diff --git a/products/ASC.CRM/Server/Core/Dao/TagDao.cs b/products/ASC.CRM/Server/Core/Dao/TagDao.cs index 0484c046d8..bfb1f3cabe 100644 --- a/products/ASC.CRM/Server/Core/Dao/TagDao.cs +++ b/products/ASC.CRM/Server/Core/Dao/TagDao.cs @@ -428,7 +428,7 @@ namespace ASC.CRM.Core.Dao tx.Commit(); } - private static string CorrectTag(string tag) + private string CorrectTag(string tag) { return tag == null ? null diff --git a/products/ASC.CRM/Server/Core/Dao/TaskDao.cs b/products/ASC.CRM/Server/Core/Dao/TaskDao.cs index 2f18ee40ed..0bbd770861 100644 --- a/products/ASC.CRM/Server/Core/Dao/TaskDao.cs +++ b/products/ASC.CRM/Server/Core/Dao/TaskDao.cs @@ -331,7 +331,7 @@ namespace ASC.CRM.Core.Dao int entityId) { - int result = 0; + int result; _logger.DebugFormat("Starting GetTasksCount: {0}", DateTime.Now.ToString()); diff --git a/products/ASC.CRM/Server/Core/Entities/Contact.cs b/products/ASC.CRM/Server/Core/Entities/Contact.cs index 6f03c0fc4e..7b27ef3b34 100644 --- a/products/ASC.CRM/Server/Core/Entities/Contact.cs +++ b/products/ASC.CRM/Server/Core/Entities/Contact.cs @@ -75,7 +75,7 @@ namespace ASC.CRM.Core.Entities var people = (Person)contact; - return String.Format("{0} {1}", people.FirstName, people.LastName); + return $"{people.FirstName} {people.LastName}"; } //public static String RenderLinkForCard(this Contact contact) diff --git a/products/ASC.CRM/Server/Core/Entities/CurrencyInfo.cs b/products/ASC.CRM/Server/Core/Entities/CurrencyInfo.cs index 6337582852..48a7a9d93a 100644 --- a/products/ASC.CRM/Server/Core/Entities/CurrencyInfo.cs +++ b/products/ASC.CRM/Server/Core/Entities/CurrencyInfo.cs @@ -73,7 +73,7 @@ namespace ASC.CRM.Core public override bool Equals(object obj) { var ci = obj as CurrencyInfo; - return ci != null && string.Compare(Title, ci.Title, true) == 0; + return ci != null && string.Equals(Title, ci.Title, StringComparison.OrdinalIgnoreCase); } public override int GetHashCode() diff --git a/products/ASC.CRM/Server/Core/Search/FactoryIndexerCase.cs b/products/ASC.CRM/Server/Core/Search/FactoryIndexerCase.cs index 8e6a83fbae..039847b799 100644 --- a/products/ASC.CRM/Server/Core/Search/FactoryIndexerCase.cs +++ b/products/ASC.CRM/Server/Core/Search/FactoryIndexerCase.cs @@ -68,7 +68,7 @@ namespace ASC.Web.CRM.Core.Search IQueryable<DbCase> GetBaseQuery(DateTime lastIndexed) => entityDao.CrmDbContext.Cases .Where(r => r.LastModifedOn >= lastIndexed) - .Join(entityDao.TenantDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) + .Join(entityDao.CrmDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) .Where(r => r.DbTenant.Status == ASC.Core.Tenants.TenantStatus.Active) .Select(r => r.DbEntity); diff --git a/products/ASC.CRM/Server/Core/Search/FactoryIndexerContact.cs b/products/ASC.CRM/Server/Core/Search/FactoryIndexerContact.cs index 4beed3b7c4..d906c5726f 100644 --- a/products/ASC.CRM/Server/Core/Search/FactoryIndexerContact.cs +++ b/products/ASC.CRM/Server/Core/Search/FactoryIndexerContact.cs @@ -68,7 +68,7 @@ namespace ASC.Web.CRM.Core.Search IQueryable<DbContact> GetBaseQuery(DateTime lastIndexed) => entityDao.CrmDbContext.Contacts .Where(r => r.LastModifedOn >= lastIndexed) - .Join(entityDao.TenantDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) + .Join(entityDao.CrmDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) .Where(r => r.DbTenant.Status == ASC.Core.Tenants.TenantStatus.Active) .Select(r => r.DbEntity); diff --git a/products/ASC.CRM/Server/Core/Search/FactoryIndexerContactInfo.cs b/products/ASC.CRM/Server/Core/Search/FactoryIndexerContactInfo.cs index cac8d01298..569494840e 100644 --- a/products/ASC.CRM/Server/Core/Search/FactoryIndexerContactInfo.cs +++ b/products/ASC.CRM/Server/Core/Search/FactoryIndexerContactInfo.cs @@ -68,7 +68,7 @@ namespace ASC.Web.CRM.Core.Search IQueryable<DbContactInfo> GetBaseQuery(DateTime lastIndexed) => entityDao.CrmDbContext.ContactsInfo .Where(r => r.LastModifedOn >= lastIndexed) - .Join(entityDao.TenantDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) + .Join(entityDao.CrmDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) .Where(r => r.DbTenant.Status == ASC.Core.Tenants.TenantStatus.Active) .Select(r => r.DbEntity); diff --git a/products/ASC.CRM/Server/Core/Search/FactoryIndexerDeal.cs b/products/ASC.CRM/Server/Core/Search/FactoryIndexerDeal.cs index bfc8d194bf..a891a61665 100644 --- a/products/ASC.CRM/Server/Core/Search/FactoryIndexerDeal.cs +++ b/products/ASC.CRM/Server/Core/Search/FactoryIndexerDeal.cs @@ -42,7 +42,7 @@ namespace ASC.Web.CRM.Core.Search IQueryable<DbDeal> GetBaseQuery(DateTime lastIndexed) => entityDao.CrmDbContext.Deals .Where(r => r.LastModifedOn >= lastIndexed) - .Join(entityDao.TenantDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) + .Join(entityDao.CrmDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) .Where(r => r.DbTenant.Status == ASC.Core.Tenants.TenantStatus.Active) .Select(r => r.DbEntity); diff --git a/products/ASC.CRM/Server/Core/Search/FactoryIndexerEvents.cs b/products/ASC.CRM/Server/Core/Search/FactoryIndexerEvents.cs index 64c79f11c5..3a3352a4ff 100644 --- a/products/ASC.CRM/Server/Core/Search/FactoryIndexerEvents.cs +++ b/products/ASC.CRM/Server/Core/Search/FactoryIndexerEvents.cs @@ -67,7 +67,7 @@ namespace ASC.Web.CRM.Core.Search IQueryable<DbRelationshipEvent> GetBaseQuery(DateTime lastIndexed) => entityDao.CrmDbContext.RelationshipEvent .Where(r => r.LastModifedOn >= lastIndexed) - .Join(entityDao.TenantDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) + .Join(entityDao.CrmDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) .Where(r => r.DbTenant.Status == ASC.Core.Tenants.TenantStatus.Active) .Select(r => r.DbEntity); diff --git a/products/ASC.CRM/Server/Core/Search/FactoryIndexerFieldValue.cs b/products/ASC.CRM/Server/Core/Search/FactoryIndexerFieldValue.cs index 294e1c0632..abab074969 100644 --- a/products/ASC.CRM/Server/Core/Search/FactoryIndexerFieldValue.cs +++ b/products/ASC.CRM/Server/Core/Search/FactoryIndexerFieldValue.cs @@ -68,7 +68,7 @@ namespace ASC.Web.CRM.Core.Search IQueryable<DbFieldValue> GetBaseQuery(DateTime lastIndexed) => entityDao.CrmDbContext.FieldValue .Where(r => r.LastModifedOn >= lastIndexed) - .Join(entityDao.TenantDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) + .Join(entityDao.CrmDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) .Where(r => r.DbTenant.Status == ASC.Core.Tenants.TenantStatus.Active) .Select(r => r.DbEntity); diff --git a/products/ASC.CRM/Server/Core/Search/FactoryIndexerInvoice.cs b/products/ASC.CRM/Server/Core/Search/FactoryIndexerInvoice.cs index 24d40cc93a..0170f1848f 100644 --- a/products/ASC.CRM/Server/Core/Search/FactoryIndexerInvoice.cs +++ b/products/ASC.CRM/Server/Core/Search/FactoryIndexerInvoice.cs @@ -68,7 +68,7 @@ namespace ASC.Web.CRM.Core.Search IQueryable<DbInvoice> GetBaseQuery(DateTime lastIndexed) => entityDao.CrmDbContext.Invoices .Where(r => r.LastModifedOn >= lastIndexed) - .Join(entityDao.TenantDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) + .Join(entityDao.CrmDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) .Where(r => r.DbTenant.Status == ASC.Core.Tenants.TenantStatus.Active) .Select(r => r.DbEntity); diff --git a/products/ASC.CRM/Server/Core/Search/FactoryIndexerTask.cs b/products/ASC.CRM/Server/Core/Search/FactoryIndexerTask.cs index 75802f80f1..f9ccb64981 100644 --- a/products/ASC.CRM/Server/Core/Search/FactoryIndexerTask.cs +++ b/products/ASC.CRM/Server/Core/Search/FactoryIndexerTask.cs @@ -68,7 +68,7 @@ namespace ASC.Web.CRM.Core.Search IQueryable<DbTask> GetBaseQuery(DateTime lastIndexed) => entityDao.CrmDbContext.Tasks .Where(r => r.LastModifedOn >= lastIndexed) - .Join(entityDao.TenantDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) + .Join(entityDao.CrmDbContext.Tenants, r => r.TenantId, r => r.Id, (f, t) => new { DbEntity = f, DbTenant = t }) .Where(r => r.DbTenant.Status == ASC.Core.Tenants.TenantStatus.Active) .Select(r => r.DbEntity); diff --git a/products/ASC.CRM/Server/Mapping/TypeConverter/ContactDtoTypeConverter.cs b/products/ASC.CRM/Server/Mapping/TypeConverter/ContactDtoTypeConverter.cs index f1a6ef2262..9ceaee8d81 100644 --- a/products/ASC.CRM/Server/Mapping/TypeConverter/ContactDtoTypeConverter.cs +++ b/products/ASC.CRM/Server/Mapping/TypeConverter/ContactDtoTypeConverter.cs @@ -219,8 +219,6 @@ namespace ASC.CRM.Mapping { if (source == null) return null; - if (source == null) return null; - var contactBaseDto = context.Mapper.Map<ContactBaseDto>(source); var result = new ContactBaseWithPhoneDto diff --git a/products/ASC.CRM/Server/Middlewares/ContactPhotoHandlerMiddleware.cs b/products/ASC.CRM/Server/Middlewares/ContactPhotoHandlerMiddleware.cs index 5afce5d56c..450e5b2316 100644 --- a/products/ASC.CRM/Server/Middlewares/ContactPhotoHandlerMiddleware.cs +++ b/products/ASC.CRM/Server/Middlewares/ContactPhotoHandlerMiddleware.cs @@ -54,7 +54,7 @@ namespace ASC.Web.CRM.HttpHandlers private readonly RequestDelegate _next; - public async System.Threading.Tasks.Task Invoke(HttpContext context, + public System.Threading.Tasks.Task Invoke(HttpContext context, SetupInfo setupInfo, CrmSecurity crmSecurity, FileSizeComment fileSizeComment, @@ -62,8 +62,7 @@ namespace ASC.Web.CRM.HttpHandlers MessageTarget messageTarget, MessageService messageService, DaoFactory daoFactory, - ContactPhotoManager contactPhotoManager) - { + ContactPhotoManager contactPhotoManager){ if (!webItemSecurity.IsAvailableForMe(ProductEntryPoint.ID)) throw crmSecurity.CreateSecurityException(); @@ -82,6 +81,18 @@ namespace ASC.Web.CRM.HttpHandlers throw crmSecurity.CreateSecurityException(); } + return InternalInvoke(context, setupInfo, fileSizeComment, messageTarget, messageService, contactPhotoManager, contact, contactId); + } + + private async System.Threading.Tasks.Task InternalInvoke(HttpContext context, + SetupInfo setupInfo, + FileSizeComment fileSizeComment, + MessageTarget messageTarget, + MessageService messageService, + ContactPhotoManager contactPhotoManager, + Contact contact, + int contactId) + { var fileUploadResult = new FileUploadResult(); if (context.Request.Form.Files.Count == 0) @@ -112,7 +123,7 @@ namespace ASC.Web.CRM.HttpHandlers } var uploadOnly = Convert.ToBoolean(context.Request.Form["uploadOnly"]); - var tmpDirName = Convert.ToString(context.Request.Form["tmpDirName"]); + var tmpDirName = context.Request.Form["tmpDirName"]; try { diff --git a/products/ASC.CRM/Server/Middlewares/FileHandlerMiddleware.cs b/products/ASC.CRM/Server/Middlewares/FileHandlerMiddleware.cs index 23433df7bd..0238032732 100644 --- a/products/ASC.CRM/Server/Middlewares/FileHandlerMiddleware.cs +++ b/products/ASC.CRM/Server/Middlewares/FileHandlerMiddleware.cs @@ -89,7 +89,7 @@ namespace ASC.Web.CRM.HttpHandlers var filePath = String.Format("folder_{0}/message_{1}.html", (messageId / 1000 + 1) * 1000, messageId); - string messageContent = string.Empty; + string messageContent; using (var streamReader = new StreamReader(global.GetStore().GetReadStream("mail_messages", filePath))) { diff --git a/products/ASC.CRM/Server/Middlewares/ImportFileHandlerMiddleware.cs b/products/ASC.CRM/Server/Middlewares/ImportFileHandlerMiddleware.cs index 1e495a831b..cdc1d25219 100644 --- a/products/ASC.CRM/Server/Middlewares/ImportFileHandlerMiddleware.cs +++ b/products/ASC.CRM/Server/Middlewares/ImportFileHandlerMiddleware.cs @@ -50,7 +50,7 @@ namespace ASC.Web.CRM.HttpHandlers _next = next; } - public async Task Invoke(HttpContext context, + public Task Invoke(HttpContext context, WebItemSecurity webItemSecurity, CrmSecurity crmSecurity, Global global, @@ -59,6 +59,15 @@ namespace ASC.Web.CRM.HttpHandlers if (!webItemSecurity.IsAvailableForMe(ProductEntryPoint.ID)) throw crmSecurity.CreateSecurityException(); + return InternalInvoke(context, webItemSecurity, crmSecurity, global, importFromCSV); + } + + private async Task InternalInvoke(HttpContext context, + WebItemSecurity webItemSecurity, + CrmSecurity crmSecurity, + Global global, + ImportFromCSV importFromCSV) + { var fileUploadResult = new FileUploadResult(); if (context.Request.Form.Files.Count == 0) diff --git a/products/ASC.CRM/Server/Middlewares/OrganisationLogoHandlerMiddleware.cs b/products/ASC.CRM/Server/Middlewares/OrganisationLogoHandlerMiddleware.cs index 7891665425..8e8a1e8d75 100644 --- a/products/ASC.CRM/Server/Middlewares/OrganisationLogoHandlerMiddleware.cs +++ b/products/ASC.CRM/Server/Middlewares/OrganisationLogoHandlerMiddleware.cs @@ -50,7 +50,7 @@ namespace ASC.Web.CRM.HttpHandlers _next = next; } - public async System.Threading.Tasks.Task Invoke(HttpContext context, + public System.Threading.Tasks.Task Invoke(HttpContext context, CrmSecurity crmSecurity, SetupInfo setupInfo, FileSizeComment fileSizeComment, @@ -62,6 +62,16 @@ namespace ASC.Web.CRM.HttpHandlers if (!crmSecurity.IsAdmin) throw crmSecurity.CreateSecurityException(); + return InternalInvoke(context, crmSecurity, setupInfo, fileSizeComment, contactPhotoManager, organisationLogoManager); + } + + private async System.Threading.Tasks.Task InternalInvoke(HttpContext context, + CrmSecurity crmSecurity, + SetupInfo setupInfo, + FileSizeComment fileSizeComment, + ContactPhotoManager contactPhotoManager, + OrganisationLogoManager organisationLogoManager) + { var fileUploadResult = new FileUploadResult(); if (context.Request.Form.Files.Count == 0) diff --git a/products/ASC.CRM/Server/Middlewares/WebToLeadFromHandlerMiddleware.cs b/products/ASC.CRM/Server/Middlewares/WebToLeadFromHandlerMiddleware.cs index 1da79cc7e0..9ae99dabb9 100644 --- a/products/ASC.CRM/Server/Middlewares/WebToLeadFromHandlerMiddleware.cs +++ b/products/ASC.CRM/Server/Middlewares/WebToLeadFromHandlerMiddleware.cs @@ -152,7 +152,7 @@ namespace ASC.Web.CRM.HttpHandlers var addressTemplateStr = JsonSerializer.Serialize(addressTemplate); - var isCompany = false; + bool isCompany; var isCompanyString = GetValue("is_company"); var firstName = GetValue("firstName"); @@ -267,7 +267,7 @@ namespace ASC.Web.CRM.HttpHandlers .Cast<object>() .Any(categoryEnum => (int)categoryEnum == category); if (!categoryIsExists) - throw new ArgumentException(String.Format("Category for {0} not found", nameParts[0])); + throw new ArgumentException($"Category for {nameParts[0]} not found"); if (contactInfoType == ContactInfoType.Address) { @@ -313,7 +313,7 @@ namespace ASC.Web.CRM.HttpHandlers IsPrimary = true }); } - else if (String.Compare(key, "tag", true) == 0) + else if (string.Equals(key, "tag", StringComparison.OrdinalIgnoreCase)) { var tags = _context.Request.Form["tag"]; @@ -355,8 +355,8 @@ namespace ASC.Web.CRM.HttpHandlers context.Response.Headers.Add("Location", newURL); await context.Response.WriteAsync("<HTML><Head>"); - await context.Response.WriteAsync(String.Format("<META HTTP-EQUIV=Refresh CONTENT=\"0;URL={0}\">", newURL)); - await context.Response.WriteAsync(String.Format("<Script>window.location='{0}';</Script>", newURL)); + await context.Response.WriteAsync($"<META HTTP-EQUIV=Refresh CONTENT=\"0;URL={newURL}\">"); + await context.Response.WriteAsync($"<Script>window.location='{newURL}';</Script>"); await context.Response.WriteAsync("</Head>"); await context.Response.WriteAsync("</HTML>"); } diff --git a/products/ASC.CRM/Server/Services/NotifyService/NotifyClient.cs b/products/ASC.CRM/Server/Services/NotifyService/NotifyClient.cs index 7cee5ecc14..bc933ca311 100644 --- a/products/ASC.CRM/Server/Services/NotifyService/NotifyClient.cs +++ b/products/ASC.CRM/Server/Services/NotifyService/NotifyClient.cs @@ -246,8 +246,8 @@ namespace ASC.Web.CRM.Services.NotifyService var recipient = notifySource.GetRecipientsProvider().GetRecipient(recipientID.ToString()); - var entitiyListTitle = ""; - var entitiyListRelativeURL = ""; + string entitiyListTitle; + string entitiyListRelativeURL; switch (entityType) { diff --git a/products/ASC.CRM/Server/Startup.cs b/products/ASC.CRM/Server/Startup.cs index e38fad6353..4867f36f21 100644 --- a/products/ASC.CRM/Server/Startup.cs +++ b/products/ASC.CRM/Server/Startup.cs @@ -1,4 +1,5 @@ using System.Collections.Generic; +using System.Net.Http; using System.Text; using System.Text.Json.Serialization; @@ -33,6 +34,16 @@ namespace ASC.CRM base.ConfigureServices(services); + services.AddHttpClient("DownloadCurrencyPage").ConfigurePrimaryHttpMessageHandler(() => + { + return new HttpClientHandler() + { + AllowAutoRedirect = true, + MaxAutomaticRedirections = 2, + UseDefaultCredentials = true + }; + }); + DIHelper.TryAdd<EntryPointApiController>(); DIHelper.TryAdd<CasesController>(); DIHelper.TryAdd<ContactInfosController>(); diff --git a/products/ASC.CRM/Server/Utils/CurrencyProvider.cs b/products/ASC.CRM/Server/Utils/CurrencyProvider.cs index 6018f24f58..273d14ce5e 100644 --- a/products/ASC.CRM/Server/Utils/CurrencyProvider.cs +++ b/products/ASC.CRM/Server/Utils/CurrencyProvider.cs @@ -30,11 +30,11 @@ using System.Globalization; using System.IO; using System.Linq; using System.Net.Http; -using System.Text.RegularExpressions; - -using ASC.Common; -using ASC.Common.Logging; -using ASC.Core.Common.Settings; +using System.Text.RegularExpressions; + +using ASC.Common; +using ASC.Common.Logging; +using ASC.Core.Common.Settings; using ASC.CRM.Core; using ASC.CRM.Core.Dao; @@ -46,48 +46,51 @@ namespace ASC.Web.CRM.Classes [Scope] public class CurrencyProvider { - private readonly ILog _logger; + private readonly ILog _log; + private readonly IHttpClientFactory _clientFactory; private readonly object _syncRoot = new object(); private readonly IConfiguration _configuration; private readonly SettingsManager _settingsManager; - private Dictionary<string, decimal> _exchangeRates; + private Dictionary<string, decimal> _exchangeRates; private DateTime _publisherDate; private const String _formatDate = "yyyy-MM-ddTHH:mm:ss.fffffffK"; - private Dictionary<String, CurrencyInfo> _currencies; - private readonly DaoFactory _daoFactory; + private Dictionary<String, CurrencyInfo> _currencies; + private readonly DaoFactory _daoFactory; public CurrencyProvider(IOptionsMonitor<ILog> logger, - IConfiguration configuration, + IConfiguration configuration, DaoFactory daoFactory, - SettingsManager settingsManager) + SettingsManager settingsManager, + IHttpClientFactory httpClientFactory) { - _logger = logger.Get("ASC"); + _log = logger.Get("ASC"); _daoFactory = daoFactory; _configuration = configuration; _settingsManager = settingsManager; - } - - public Dictionary<String, CurrencyInfo> Currencies - { - get - { - if (_currencies != null) return _currencies; - - var currencies = _daoFactory.GetCurrencyInfoDao().GetAll(); - - if (currencies == null || currencies.Count == 0) - { - currencies = new List<CurrencyInfo> - { - new CurrencyInfo("Currency_UnitedStatesDollar", "USD", "$", "US", true, true) - }; - } - - _currencies = currencies.ToDictionary(c => c.Abbreviation); - - return _currencies; - } - } + _clientFactory = httpClientFactory; + } + + public Dictionary<String, CurrencyInfo> Currencies + { + get + { + if (_currencies != null) return _currencies; + + var currencies = _daoFactory.GetCurrencyInfoDao().GetAll(); + + if (currencies == null || currencies.Count == 0) + { + currencies = new List<CurrencyInfo> + { + new CurrencyInfo("Currency_UnitedStatesDollar", "USD", "$", "US", true, true) + }; + } + + _currencies = currencies.ToDictionary(c => c.Abbreviation); + + return _currencies; + } + } public DateTime GetPublisherDate { @@ -138,7 +141,7 @@ namespace ASC.Web.CRM.Classes continue; } - var key = String.Format("{1}/{0}", baseCurrency.Abbreviation, ci.Abbreviation); + var key = $"{ci.Abbreviation}/{baseCurrency.Abbreviation}"; if (!rates.ContainsKey(key)) continue; @@ -151,7 +154,7 @@ namespace ASC.Web.CRM.Classes public bool IsConvertable(String abbreviation) { - var findedItem = Currencies.Keys.ToList().Find(item => String.Compare(abbreviation, item) == 0); + var findedItem = _currencies.Keys.ToList().Find(item => string.Equals(abbreviation, item)); if (findedItem == null) throw new ArgumentException(abbreviation); @@ -161,13 +164,13 @@ namespace ASC.Web.CRM.Classes public Decimal MoneyConvert(decimal amount, string from, string to) { - if (string.IsNullOrEmpty(from) || string.IsNullOrEmpty(to) || string.Compare(from, to, true) == 0) return amount; + if (string.IsNullOrEmpty(from) || string.IsNullOrEmpty(to) || string.Equals(from, to, StringComparison.OrdinalIgnoreCase)) return amount; var rates = GetExchangeRates(); if (from.Contains('-')) from = new RegionInfo(from).ISOCurrencySymbol; if (to.Contains('-')) to = new RegionInfo(to).ISOCurrencySymbol; - var key = string.Format("{0}/{1}", to, from); + var key = $"{to}/{from}"; return Math.Round(rates[key] * amount, 4, MidpointRounding.AwayFromZero); } @@ -251,7 +254,7 @@ namespace ASC.Web.CRM.Classes } catch (Exception error) { - _logger.Error(error); + _log.Error(error); _publisherDate = DateTime.UtcNow; } } @@ -277,8 +280,7 @@ namespace ASC.Web.CRM.Classes { foreach (var curInfo in currencyInfos) { - _exchangeRates.Add( - String.Format("{0}/{1}", (curInfo as Match).Groups["Currency"].Value.Trim(), curCI.Abbreviation), + _exchangeRates.Add($"{(curInfo as Match).Groups["Currency"].Value.Trim()}/{curCI.Abbreviation}", Convert.ToDecimal((curInfo as Match).Groups["Rate"].Value.Trim(), CultureInfo.InvariantCulture.NumberFormat)); success = true; @@ -306,7 +308,7 @@ namespace ASC.Web.CRM.Classes } catch (Exception err) { - _logger.Error(err); + _log.Error(err); } } } @@ -320,7 +322,7 @@ namespace ASC.Web.CRM.Classes } catch (Exception err) { - _logger.Error(err); + _log.Error(err); } } @@ -336,7 +338,7 @@ namespace ASC.Web.CRM.Classes Directory.CreateDirectory(dir); } - var destinationURI = new Uri(String.Format("https://themoneyconverter.com/{0}/{0}.aspx", currency)); + var destinationURI = new Uri("https://themoneyconverter.com/" + currency + "/" + currency + ".aspx"); var request = new HttpRequestMessage(); request.RequestUri = destinationURI; @@ -348,7 +350,8 @@ namespace ASC.Web.CRM.Classes handler.MaxAutomaticRedirections = 2; handler.UseDefaultCredentials = true; - var httpClient = new HttpClient(handler); + var httpClient = _clientFactory.CreateClient("DownloadCurrencyPage"); + _clientFactory.CreateClient(); using var response = httpClient.Send(request); using (var responseStream = new StreamReader(response.Content.ReadAsStream())) { @@ -359,7 +362,7 @@ namespace ASC.Web.CRM.Classes } catch (Exception error) { - _logger.Error(error); + _log.Error(error); } } diff --git a/products/ASC.CRM/Server/Utils/ExportToCSV.cs b/products/ASC.CRM/Server/Utils/ExportToCSV.cs index ad2fd70f9b..0b09d02de0 100644 --- a/products/ASC.CRM/Server/Utils/ExportToCSV.cs +++ b/products/ASC.CRM/Server/Utils/ExportToCSV.cs @@ -473,7 +473,7 @@ namespace ASC.Web.CRM.Classes foreach (ContactInfoType infoTypeEnum in Enum.GetValues(typeof(ContactInfoType))) foreach (Enum categoryEnum in Enum.GetValues(ContactInfo.GetCategory(infoTypeEnum))) { - var localTitle = String.Format("{1} ({0})", categoryEnum.ToLocalizedString().ToLower(), infoTypeEnum.ToLocalizedString()); + var localTitle = $"{infoTypeEnum.ToLocalizedString()} ({categoryEnum.ToLocalizedString().ToLower()})"; if (infoTypeEnum == ContactInfoType.Address) dataTable.Columns.AddRange((from AddressPart addressPartEnum in Enum.GetValues(typeof(AddressPart)) @@ -942,15 +942,13 @@ namespace ASC.Web.CRM.Classes var casesObj = casesDao.GetByID(item.EntityID); if (casesObj != null) - entityTitle = String.Format("{0}: {1}", CRMCasesResource.Case, - casesObj.Title); + entityTitle = $"{CRMCasesResource.Case}: {casesObj.Title}"; break; case EntityType.Opportunity: var dealObj = dealDao.GetByID(item.EntityID); if (dealObj != null) - entityTitle = String.Format("{0}: {1}", CRMDealResource.Deal, - dealObj.Title); + entityTitle = $"{CRMDealResource.Deal}: {dealObj.Title}"; break; } @@ -1069,13 +1067,13 @@ namespace ASC.Web.CRM.Classes var caseObj = casesDao.GetByID(item.EntityID); if (caseObj != null) - entityTitle = String.Format("{0}: {1}", CRMCasesResource.Case, caseObj.Title); + entityTitle = $"{CRMCasesResource.Case}: {caseObj.Title}"; break; case EntityType.Opportunity: var dealObj = dealDao.GetByID(item.EntityID); if (dealObj != null) - entityTitle = String.Format("{0}: {1}", CRMDealResource.Deal, dealObj.Title); + entityTitle = $"{CRMDealResource.Deal}: {dealObj.Title}"; break; } diff --git a/products/ASC.CRM/Server/Utils/Import/CSV/ImportDataOperation.cs b/products/ASC.CRM/Server/Utils/Import/CSV/ImportDataOperation.cs index 9cbf155a79..51a194bc21 100644 --- a/products/ASC.CRM/Server/Utils/Import/CSV/ImportDataOperation.cs +++ b/products/ASC.CRM/Server/Utils/Import/CSV/ImportDataOperation.cs @@ -148,7 +148,7 @@ namespace ASC.Web.CRM.Classes var values = jsonElement.EnumerateArray().Select(x => x.GetInt32()).ToList().ConvertAll(columnIndex => _columns[columnIndex]); - values.RemoveAll(item => item == String.Empty); + values.RemoveAll(item => item.Length == 0); return String.Join(",", values.ToArray()); } diff --git a/products/ASC.CRM/Server/Utils/Import/CSV/ImportDeals.cs b/products/ASC.CRM/Server/Utils/Import/CSV/ImportDeals.cs index 92fe4b6a69..4f21010437 100644 --- a/products/ASC.CRM/Server/Utils/Import/CSV/ImportDeals.cs +++ b/products/ASC.CRM/Server/Utils/Import/CSV/ImportDeals.cs @@ -125,17 +125,17 @@ namespace ASC.Web.CRM.Classes if (!string.IsNullOrEmpty(bidTypeStr)) { - if (String.Compare(CRMDealResource.BidType_FixedBid, bidTypeStr, true) == 0) + if (string.Equals(CRMDealResource.BidType_FixedBid, bidTypeStr, StringComparison.OrdinalIgnoreCase)) bidType = BidType.FixedBid; - else if (String.Compare(CRMDealResource.BidType_PerDay, bidTypeStr, true) == 0) + else if (string.Equals(CRMDealResource.BidType_PerDay, bidTypeStr, StringComparison.OrdinalIgnoreCase)) bidType = BidType.PerDay; - else if (String.Compare(CRMDealResource.BidType_PerHour, bidTypeStr, true) == 0) + else if (string.Equals(CRMDealResource.BidType_PerHour, bidTypeStr, StringComparison.OrdinalIgnoreCase)) bidType = BidType.PerHour; - else if (String.Compare(CRMDealResource.BidType_PerMonth, bidTypeStr, true) == 0) + else if (string.Equals(CRMDealResource.BidType_PerMonth, bidTypeStr, StringComparison.OrdinalIgnoreCase)) bidType = BidType.PerMonth; - else if (String.Compare(CRMDealResource.BidType_PerWeek, bidTypeStr, true) == 0) + else if (string.Equals(CRMDealResource.BidType_PerWeek, bidTypeStr, StringComparison.OrdinalIgnoreCase)) bidType = BidType.PerWeek; - else if (String.Compare(CRMDealResource.BidType_PerYear, bidTypeStr, true) == 0) + else if (string.Equals(CRMDealResource.BidType_PerYear, bidTypeStr, StringComparison.OrdinalIgnoreCase)) bidType = BidType.PerYear; } @@ -176,7 +176,7 @@ namespace ASC.Web.CRM.Classes obj.DealMilestoneID = dealMilestones[0].ID; else { - var dealMilestone = dealMilestones.Find(item => String.Compare(item.Title, dealMilestoneTitle, true) == 0); + var dealMilestone = dealMilestones.Find(item => string.Equals(item.Title, dealMilestoneTitle, StringComparison.OrdinalIgnoreCase)); if (dealMilestone == null) obj.DealMilestoneID = dealMilestones[0].ID; diff --git a/products/ASC.CRM/Server/Utils/Import/CSV/ImportTasks.cs b/products/ASC.CRM/Server/Utils/Import/CSV/ImportTasks.cs index 524482846b..bc60a84bbc 100644 --- a/products/ASC.CRM/Server/Utils/Import/CSV/ImportTasks.cs +++ b/products/ASC.CRM/Server/Utils/Import/CSV/ImportTasks.cs @@ -108,7 +108,7 @@ namespace ASC.Web.CRM.Classes if (!String.IsNullOrEmpty(categoryTitle)) { - var findedCategory = taskCategories.Find(item => String.Compare(item.Title, categoryTitle) == 0); + var findedCategory = taskCategories.Find(item => string.Equals(item.Title, categoryTitle)); if (findedCategory == null) { @@ -144,17 +144,16 @@ namespace ASC.Web.CRM.Classes var taskStatus = GetPropertyValue("status"); - if (!String.IsNullOrEmpty(taskStatus)) + if (!string.IsNullOrEmpty(taskStatus)) { - if (String.Compare(taskStatus, CRMTaskResource.TaskStatus_Closed, true) == 0) + if (string.Equals(taskStatus, CRMTaskResource.TaskStatus_Closed, StringComparison.OrdinalIgnoreCase)) obj.IsClosed = true; } var alertValue = GetPropertyValue("alertValue"); - int alertIntVal = 0; - if (Int32.TryParse(alertValue, out alertIntVal)) + if (Int32.TryParse(alertValue, out var alertIntVal)) obj.AlertValue = alertIntVal; else obj.AlertValue = 0; diff --git a/products/ASC.CRM/Server/Utils/MailSender.cs b/products/ASC.CRM/Server/Utils/MailSender.cs index b120ca72a3..b2408b241b 100644 --- a/products/ASC.CRM/Server/Utils/MailSender.cs +++ b/products/ASC.CRM/Server/Utils/MailSender.cs @@ -51,9 +51,8 @@ using ASC.CRM.Core.Dao; using ASC.CRM.Core.Entities; using ASC.CRM.Core.Enums; using ASC.CRM.Resources; -using ASC.Web.Files.Api; - -using MailKit; +using ASC.Web.Files.Api; + using MailKit.Net.Smtp; using MailKit.Security; @@ -275,7 +274,7 @@ namespace ASC.Web.CRM.Classes continue; } - var to = new MailboxAddress(recipientEmail); + var to = MailboxAddress.Parse(recipientEmail); var mimeMessage = new MimeMessage { @@ -431,8 +430,6 @@ namespace ASC.Web.CRM.Classes { var client = new SmtpClient { - ServerCertificateValidationCallback = (sender, certificate, chain, errors) => - WorkContext.IsMono || MailKit.MailService.DefaultServerCertificateValidationCallback(sender, certificate, chain, errors), Timeout = (int)TimeSpan.FromSeconds(30).TotalMilliseconds }; @@ -563,7 +560,6 @@ namespace ASC.Web.CRM.Classes { var client = new SmtpClient { - ServerCertificateValidationCallback = (sender, certificate, chain, errors) => MailService.DefaultServerCertificateValidationCallback(sender, certificate, chain, errors), Timeout = (int)TimeSpan.FromSeconds(30).TotalMilliseconds }; @@ -594,7 +590,7 @@ namespace ASC.Web.CRM.Classes { try { - var toAddress = new MailboxAddress(recipientEmail); + var toAddress = MailboxAddress.Parse(recipientEmail); var fromAddress = new MailboxAddress(smtpSetting.SenderDisplayName, smtpSetting.SenderEmailAddress); var mimeMessage = new MimeMessage @@ -693,7 +689,7 @@ namespace ASC.Web.CRM.Classes foreach (Match match in _regex.Matches(template)) { - var findedTag = tags.Find(item => String.Compare(item.Name, match.Value) == 0); + var findedTag = tags.Find(item => string.Equals(item.Name, match.Value)); if (findedTag == null) continue; @@ -827,7 +823,7 @@ namespace ASC.Web.CRM.Classes private String ToTagName(String value, bool isCompany) { - return String.Format("$({0}.{1})", isCompany ? "Company" : "Person", value); + return $"$({(isCompany ? "Company" : "Person")}.{value})"; } private List<MailTemplateTag> GetAllTags() @@ -907,7 +903,7 @@ namespace ASC.Web.CRM.Classes DisplayName = String.Format(localTitle + " {0}", addressPartEnum.ToLocalizedString()), Category = CRMContactResource.GeneralInformation, isCompany = isCompany, - Name = ToTagName(String.Format("{0} {1}", infoTypeEnum.ToString(), addressPartEnum.ToString()), isCompany) + Name = ToTagName($"{infoTypeEnum} {addressPartEnum}", isCompany) }); else result.Add(new MailTemplateTag diff --git a/products/ASC.CRM/Server/Utils/PdfCreator.cs b/products/ASC.CRM/Server/Utils/PdfCreator.cs index d45abb0c69..86ce4a0666 100644 --- a/products/ASC.CRM/Server/Utils/PdfCreator.cs +++ b/products/ASC.CRM/Server/Utils/PdfCreator.cs @@ -57,7 +57,8 @@ namespace ASC.Web.CRM.Classes private DocumentServiceConnector _documentServiceConnector; private OrganisationLogoManager _organisationLogoManager; private Files.Classes.PathProvider _filesPathProvider; - private ILog _logger; + private ILog _logger; + private IHttpClientFactory _clientFactory; public PdfCreator(IOptionsMonitor<ILog> logger, @@ -66,7 +67,8 @@ namespace ASC.Web.CRM.Classes IServiceProvider serviceProvider, OrganisationLogoManager organisationLogoManager, DaoFactory daoFactory, - InvoiceFormattedData invoiceFormattedData) + InvoiceFormattedData invoiceFormattedData, + IHttpClientFactory clientFactory) { _filesPathProvider = filesPathProvider; @@ -76,7 +78,8 @@ namespace ASC.Web.CRM.Classes _serviceProvider = serviceProvider; _organisationLogoManager = organisationLogoManager; _daoFactory = daoFactory; - _invoiceFormattedData = invoiceFormattedData; + _invoiceFormattedData = invoiceFormattedData; + _clientFactory = clientFactory; } @@ -124,13 +127,13 @@ namespace ASC.Web.CRM.Classes var file = _serviceProvider.GetService<File<int>>(); - file.Title = string.Format("{0}{1}", invoice.Number, FormatPdf); + file.Title = $"{invoice.Number}{FormatPdf}"; file.FolderID = _daoFactory.GetFileDao().GetRoot(); var request = new HttpRequestMessage(); request.RequestUri = new Uri(urlToFile); - using (var httpClient = new HttpClient()) + var httpClient = _clientFactory.CreateClient(); using (var response = httpClient.Send(request)) using (var stream = response.Content.ReadAsStream()) { @@ -249,7 +252,7 @@ namespace ASC.Web.CRM.Classes var request = new HttpRequestMessage(); request.RequestUri = new Uri(url); - using var httpClient = new HttpClient(); + var httpClient = _clientFactory.CreateClient(); using (var stream = httpClient.Send(request).Content.ReadAsStream()) { @@ -257,7 +260,7 @@ namespace ASC.Web.CRM.Classes { var document = _serviceProvider.GetService<File<int>>(); - document.Title = string.Format("{0}{1}", data.Number, FormatPdf); + document.Title = $"{data.Number}{FormatPdf}"; document.FolderID = _daoFactory.GetFileDao().GetRoot(); document.ContentLength = stream.Length; diff --git a/products/ASC.CRM/Server/Utils/ReportHelper.cs b/products/ASC.CRM/Server/Utils/ReportHelper.cs index 6cf7eed67d..a728e7e659 100644 --- a/products/ASC.CRM/Server/Utils/ReportHelper.cs +++ b/products/ASC.CRM/Server/Utils/ReportHelper.cs @@ -28,6 +28,7 @@ using System; using System.Collections.Generic; using System.Net.Http; using System.Text.Json; +using System.Threading.Tasks; using ASC.Common; using ASC.Core; @@ -57,6 +58,7 @@ namespace ASC.Web.CRM.Classes private SettingsManager _settingsManager; private TenantUtil _tenantUtil; private TenantManager _tenantManager; + private IHttpClientFactory _clientFactory; public ReportHelper(TenantManager tenantManager, TenantUtil tenantUtil, @@ -67,7 +69,8 @@ namespace ASC.Web.CRM.Classes SecurityContext securityContext, IServiceProvider serviceProvider, IHttpContextAccessor httpContextAccessor, - CurrencyProvider currencyProvider + CurrencyProvider currencyProvider, + IHttpClientFactory clientFactory ) { _tenantManager = tenantManager; @@ -80,6 +83,7 @@ namespace ASC.Web.CRM.Classes _securityContext = securityContext; _httpContext = httpContextAccessor; _currencyProvider = currencyProvider; + _clientFactory = clientFactory; } private string GetFileName(ReportType reportType) @@ -123,10 +127,7 @@ namespace ASC.Web.CRM.Classes break; } - return string.Format("{0} ({1} {2}).xlsx", - reportName, - _tenantUtil.DateTimeNow().ToShortDateString(), - _tenantUtil.DateTimeNow().ToShortTimeString()); + return $"{reportName} ({_tenantUtil.DateTimeNow().ToShortDateString()} {_tenantUtil.DateTimeNow().ToShortTimeString()}).xlsx"; } public bool CheckReportData(ReportType reportType, ReportTimePeriod timePeriod, Guid[] managers) @@ -221,9 +222,9 @@ namespace ASC.Web.CRM.Classes .Replace("${reportData}", JsonSerializer.Serialize(data)); } - private async void SaveReportFile(ReportState state, string url) + private async Task SaveReportFile(ReportState state, string url) { - using var httpClient = new HttpClient(); + var httpClient = _clientFactory.CreateClient(); var responseData = await httpClient.GetByteArrayAsync(url); using (var stream = new System.IO.MemoryStream(responseData)) diff --git a/products/ASC.Calendar/Server/BusinessObjects/Calendar.cs b/products/ASC.Calendar/Server/BusinessObjects/Calendar.cs index 1075f46948..716b996328 100644 --- a/products/ASC.Calendar/Server/BusinessObjects/Calendar.cs +++ b/products/ASC.Calendar/Server/BusinessObjects/Calendar.cs @@ -81,7 +81,7 @@ namespace ASC.Calendar.BusinessObjects } public static List<EventWrapper> GetEventWrappers(this BaseCalendar calendar, Guid userId, ApiDateTime startDate, ApiDateTime endDate, EventWrapperHelper eventWrapperHelper) - {new List<EventWrapper>(); + { var result = new List<EventWrapper>(); if (calendar != null) { diff --git a/products/ASC.Calendar/Server/BusinessObjects/DataProvider.cs b/products/ASC.Calendar/Server/BusinessObjects/DataProvider.cs index 42af0cc6e3..946b365b3c 100644 --- a/products/ASC.Calendar/Server/BusinessObjects/DataProvider.cs +++ b/products/ASC.Calendar/Server/BusinessObjects/DataProvider.cs @@ -28,7 +28,7 @@ using System; using System.Collections.Generic; using System.Linq; using System.Net.Http; -using System.Net.Http.Headers; +using System.Net.Http.Headers; using System.Text; using System.Web; @@ -82,6 +82,7 @@ namespace ASC.Calendar.BusinessObjects protected DDayICalParser DDayICalParser { get; } public ILog Log { get; } public InstanceCrypto InstanceCrypto { get; } + public IHttpClientFactory ClientFactory { get; } public DataProvider(DbContextManager<CalendarDbContext> calendarDbContext, AuthManager authentication, @@ -94,7 +95,8 @@ namespace ASC.Calendar.BusinessObjects UserManager userManager, DDayICalParser dDayICalParser, IOptionsMonitor<ILog> option, - InstanceCrypto instanceCrypto) + InstanceCrypto instanceCrypto, + IHttpClientFactory clientFactory) { Authentication = authentication; CalendarDb = calendarDbContext.Get("calendar"); @@ -108,7 +110,7 @@ namespace ASC.Calendar.BusinessObjects DDayICalParser = dDayICalParser; Log = option.Get("ASC.CalendarDataProvider"); InstanceCrypto = instanceCrypto; - + ClientFactory = clientFactory; } public List<UserViewSettings> GetUserViewSettings(Guid userId, List<string> calendarIds) @@ -125,8 +127,8 @@ namespace ASC.Calendar.BusinessObjects options.Add(new UserViewSettings() { CalendarId = - Convert.ToInt32(r.CalendarId) == 0 - ? Convert.ToString(r.ExtCalendarId) + r.CalendarId == 0 + ? r.ExtCalendarId : Convert.ToString(r.CalendarId), UserId = r.UserId, IsHideEvents = Convert.ToBoolean(r.HideEvents), @@ -206,9 +208,9 @@ namespace ASC.Calendar.BusinessObjects public List<Calendar> LoadiCalStreamsForUser(Guid userId) { - var calIds = CalendarDb.CalendarCalendars.Where(p => - p.Tenant == TenantManager.GetCurrentTenant().TenantId && - p.OwnerId == userId.ToString() && + var calIds = CalendarDb.CalendarCalendars.Where(p => + p.Tenant == TenantManager.GetCurrentTenant().TenantId && + p.OwnerId == userId.ToString() && p.IcalUrl != null) .Select(s => s.Id).ToArray(); var calendars = GetCalendarsByIds(calIds.ToArray()); @@ -257,30 +259,30 @@ namespace ASC.Calendar.BusinessObjects return data.FirstOrDefault().calUsrTimeZone == null ? TimeZoneConverter.GetTimeZone(data.FirstOrDefault().calTimeZone) : TimeZoneConverter.GetTimeZone(data.FirstOrDefault().calUsrTimeZone); - } - - public List<object[]> GetCalendarIdByCaldavGuid(string caldavGuid) + } + + public List<object[]> GetCalendarIdByCaldavGuid(string caldavGuid) { var data = CalendarDb.CalendarCalendars .Where(p => p.CaldavGuid == caldavGuid) - .Select(s => new object[]{ + .Select(s => new object[]{ s.Id, s.OwnerId, s.Tenant - }).ToList(); - - return data; - } - public Event GetEventIdByUid(string uid, int calendarId) + }).ToList(); + + return data; + } + public Event GetEventIdByUid(string uid, int calendarId) { var eventId = CalendarDb.CalendarEvents - .Where(p => + .Where(p => uid.Contains(p.Uid) && p.CalendarId == calendarId ) - .Select(s => s.Id).FirstOrDefault(); - - return eventId == 0 ? null : GetEventById(eventId); + .Select(s => s.Id).FirstOrDefault(); + + return eventId == 0 ? null : GetEventById(eventId); } public Event GetEventIdOnlyByUid(string uid) @@ -336,7 +338,7 @@ namespace ASC.Calendar.BusinessObjects string.Equals(c.Id, r.calId.ToString(), StringComparison.InvariantCultureIgnoreCase)); if (calendar == null) { - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); calendar = new Calendar(AuthContext, TimeZoneConverter, icalendar, this) { Id = r.calId.ToString(), @@ -483,8 +485,8 @@ namespace ASC.Calendar.BusinessObjects { var dataCaldavGuid = CalendarDb.CalendarCalendars.Where(p => p.Id.ToString() == id).Select(s => s.CaldavGuid).FirstOrDefault(); - return dataCaldavGuid; - + return dataCaldavGuid; + } public Calendar UpdateCalendar(int calendarId, string name, string description, List<SharingOptions.PublicItem> publicItems, List<UserViewSettings> viewSettings) { @@ -751,8 +753,8 @@ namespace ASC.Calendar.BusinessObjects { var dataCaldavGuid = CalendarDb.CalendarCalendars.Where(p => p.Id == calendarId).Select(s => s.CaldavGuid).ToArray(); - if (dataCaldavGuid[0] != null) - caldavGuid = Guid.Parse(dataCaldavGuid[0].ToString()); + if (dataCaldavGuid[0] != null) + caldavGuid = Guid.Parse(dataCaldavGuid[0]); } catch (Exception ex) { @@ -795,7 +797,7 @@ namespace ASC.Calendar.BusinessObjects public void RemoveCaldavCalendar(string currentUserName, string email, string calDavGuid, Uri myUri, bool isShared = false) { - var calDavServerUrl = myUri.Scheme + "://" + myUri.Host + "/caldav"; + var calDavServerUrl = myUri.Scheme + "://" + myUri.Host + "/caldav"; var requestUrl = calDavServerUrl + "/" + HttpUtility.UrlEncode(currentUserName) + "/" + (isShared ? calDavGuid + "-shared" : calDavGuid); try @@ -806,13 +808,13 @@ namespace ASC.Calendar.BusinessObjects var authorization = isShared ? GetSystemAuthorization() : GetUserAuthorization(email); - request.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(Encoding.UTF8.GetBytes(authorization))); - request.Content.Headers.ContentType = new MediaTypeHeaderValue("text/xml") - { - CharSet = Encoding.UTF8.WebName + request.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(Encoding.UTF8.GetBytes(authorization))); + request.Content.Headers.ContentType = new MediaTypeHeaderValue("text/xml") + { + CharSet = Encoding.UTF8.WebName }; - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); httpClient.Send(request); } catch (Exception ex) @@ -822,8 +824,8 @@ namespace ASC.Calendar.BusinessObjects } public void RemoveExternalCalendarData(string calendarId) { - using var tx = CalendarDb.Database.BeginTransaction(); - + using var tx = CalendarDb.Database.BeginTransaction(); + var ccu = CalendarDb.CalendarCalendarUser.Where(r => r.ExtCalendarId == calendarId).SingleOrDefault(); if (ccu != null) @@ -948,14 +950,14 @@ namespace ASC.Calendar.BusinessObjects Uid = s.Uid }) .ToList(); - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); todoList = data.ConvertAll(r => new Todo(AuthContext, TimeZoneConverter, icalendar, this) { - Id = r.Id.ToString(), + Id = r.Id, Name = r.Name, Description = r.Description, TenantId = r.TenantId, - CalendarId = r.CalendarId.ToString(), + CalendarId = r.CalendarId, UtcStartDate = r.UtcStartDate ?? DateTime.MinValue, Completed = r.Completed ?? DateTime.MinValue, OwnerId = r.OwnerId, @@ -980,14 +982,14 @@ namespace ASC.Calendar.BusinessObjects Uid = s.Uid }) .ToList(); - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); todoList = data.ConvertAll(r => new Todo(AuthContext, TimeZoneConverter, icalendar, this) { - Id = r.Id.ToString(), + Id = r.Id, Name = r.Name, Description = r.Description, TenantId = r.TenantId, - CalendarId = r.CalendarId.ToString(), + CalendarId = r.CalendarId, UtcStartDate = r.UtcStartDate ?? DateTime.MinValue, Completed = r.Completed ?? DateTime.MinValue, OwnerId = r.OwnerId, @@ -1025,19 +1027,19 @@ namespace ASC.Calendar.BusinessObjects var groups = UserManager.GetUserGroups(userId).Select(g => g.ID).ToList(); groups.AddRange(UserManager.GetUserGroups(userId, Constants.SysGroupCategoryId).Select(g => g.ID)); - var evIds = from events in CalendarDb.CalendarEvents - join eventItem in CalendarDb.CalendarEventItem on events.Id equals eventItem.EventId - where - events.Tenant == tenantId && - ( - eventItem.ItemId == userId || (groups.Contains(eventItem.ItemId) && eventItem.IsGroup == 1) && - events.Tenant == tenantId && - ((events.StartDate >= utcStartDate && events.StartDate <= utcEndDate && events.Rrule == "") || events.Rrule != "") && - events.OwnerId != userId && - !(from calEventUser in CalendarDb.CalendarEventUser - where calEventUser.EventId == events.Id && calEventUser.UserId == userId && calEventUser.IsUnsubscribe == 1 - select calEventUser.EventId).Any() - ) + var evIds = from events in CalendarDb.CalendarEvents + join eventItem in CalendarDb.CalendarEventItem on events.Id equals eventItem.EventId + where + events.Tenant == tenantId && + ( + eventItem.ItemId == userId || (groups.Contains(eventItem.ItemId) && eventItem.IsGroup == 1) && + events.Tenant == tenantId && + ((events.StartDate >= utcStartDate && events.StartDate <= utcEndDate && events.Rrule == "") || events.Rrule != "") && + events.OwnerId != userId && + !(from calEventUser in CalendarDb.CalendarEventUser + where calEventUser.EventId == events.Id && calEventUser.UserId == userId && calEventUser.IsUnsubscribe == 1 + select calEventUser.EventId).Any() + ) select events.Id; return GetEventsByIds(evIds.ToArray(), userId, tenantId); } @@ -1062,8 +1064,8 @@ namespace ASC.Calendar.BusinessObjects ) ) ) - .Select(s => s.Id).ToList(); - + .Select(s => s.Id).ToList(); + return GetEventsByIds(evIds.ToArray(), userId, tenantId); } @@ -1132,7 +1134,7 @@ namespace ASC.Calendar.BusinessObjects e => String.Equals(e.Id, r.Id, StringComparison.InvariantCultureIgnoreCase)); if (ev == null) { - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); ev = new Event(AuthContext, TimeZoneConverter, icalendar, this) { Id = r.Id, @@ -1198,7 +1200,7 @@ namespace ASC.Calendar.BusinessObjects e => String.Equals(e.Id, r.Id, StringComparison.InvariantCultureIgnoreCase)); if (ev == null) { - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); ev = new Event(AuthContext, TimeZoneConverter, icalendar, this) { Id = r.Id, @@ -1457,8 +1459,8 @@ namespace ASC.Calendar.BusinessObjects } CalendarDb.SaveChanges(); - tx.Commit(); - + tx.Commit(); + return GetEventById(eventId); } @@ -1610,14 +1612,14 @@ namespace ASC.Calendar.BusinessObjects CalendarDb.SaveChanges(); tx.Commit(); - } - + } + public static string GetEventUid(string uid, string id = null) { if (!string.IsNullOrEmpty(uid)) return uid; - return string.Format("{0}@onlyoffice.com", string.IsNullOrEmpty(id) ? Guid.NewGuid().ToString() : id); + return $"{(string.IsNullOrEmpty(id) ? Guid.NewGuid().ToString() : id)}@onlyoffice.com"; } @@ -1707,7 +1709,7 @@ namespace ASC.Calendar.BusinessObjects }; var calendarAlertType = (EventAlertType)calendarData.FirstOrDefault().alertType; - var calendarOwner = Convert.ToString(calendarData.FirstOrDefault().ownerId); + var calendarOwner = calendarData.FirstOrDefault().ownerId; var calendarTimeZone = TimeZoneConverter.GetTimeZone(calendarData.FirstOrDefault().timeZone); var eventUsers = new List<UserAlertType>(); @@ -1786,7 +1788,7 @@ namespace ASC.Calendar.BusinessObjects u.TimeZone = r.timeZone == null ? calendarTimeZone : TimeZoneConverter.GetTimeZone(Convert.ToString(r.isAccepted)); if (u.AlertType == EventAlertType.Default && u.UserId.Equals(r.userId)) - u.AlertType = (EventAlertType)Convert.ToInt32(r.alertType); + u.AlertType = (EventAlertType)r.alertType; }); } @@ -1841,7 +1843,7 @@ namespace ASC.Calendar.BusinessObjects eventUsers.ForEach(u => { if (u.UserId.Equals(r.userIdCol)) - u.AlertType = (EventAlertType)(Convert.ToInt32(r.alertTypeCol)); + u.AlertType = (EventAlertType)r.alertTypeCol; }); } @@ -1873,7 +1875,7 @@ namespace ASC.Calendar.BusinessObjects u.TimeZone = r.timeZone == null ? calendarTimeZone : TimeZoneConverter.GetTimeZone(r.timeZone); if (u.AlertType == EventAlertType.Default && u.UserId.Equals(r.userId)) - u.AlertType = (EventAlertType)Convert.ToInt32(r.alertType); + u.AlertType = (EventAlertType)r.alertType; }); } diff --git a/products/ASC.Calendar/Server/Controllers/CalendarController.cs b/products/ASC.Calendar/Server/Controllers/CalendarController.cs index 4e9d6bcd02..6f45e586ff 100644 --- a/products/ASC.Calendar/Server/Controllers/CalendarController.cs +++ b/products/ASC.Calendar/Server/Controllers/CalendarController.cs @@ -30,8 +30,8 @@ using System.Globalization; using System.IO; using System.Linq; using System.Net; -using System.Net.Http; -using System.Net.Http.Headers; +using System.Net.Http; +using System.Net.Http.Headers; using System.Security; using System.Text; using System.Text.Json; @@ -39,7 +39,7 @@ using System.Text.RegularExpressions; using System.Threading; using System.Threading.Tasks; using System.Web; - + using ASC.Api.Core; using ASC.Calendar.BusinessObjects; using ASC.Calendar.Configuration; @@ -48,28 +48,28 @@ using ASC.Calendar.ExternalCalendars; using ASC.Calendar.iCalParser; using ASC.Calendar.Models; using ASC.Calendar.Notification; -using ASC.Common; -using ASC.Common.Logging; -using ASC.Common.Security; -using ASC.Common.Utils; -using ASC.Common.Web; -using ASC.Core; -using ASC.Core.Tenants; -using ASC.Core.Users; -using ASC.Security.Cryptography; +using ASC.Common; +using ASC.Common.Logging; +using ASC.Common.Security; +using ASC.Common.Utils; +using ASC.Common.Web; +using ASC.Core; +using ASC.Core.Tenants; +using ASC.Core.Users; +using ASC.Security.Cryptography; using ASC.Web.Api.Routing; using ASC.Web.Core.Calendars; -using ASC.Web.Core.Users; -using ASC.Web.Studio.Core; -using ASC.Web.Studio.Utility; - -using Ical.Net.CalendarComponents; -using Ical.Net.DataTypes; - +using ASC.Web.Core.Users; +using ASC.Web.Studio.Core; +using ASC.Web.Studio.Utility; + +using Ical.Net.CalendarComponents; +using Ical.Net.DataTypes; + using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc; using Microsoft.Extensions.Options; - + using HttpContext = Microsoft.AspNetCore.Http.HttpContext; using SecurityContext = ASC.Core.SecurityContext; @@ -113,6 +113,7 @@ namespace ASC.Calendar.Controllers private SetupInfo SetupInfo { get; } private InstanceCrypto InstanceCrypto { get; } private CalendarManager CalendarManager { get; } + private IHttpClientFactory ClientFactory { get; } public CalendarController( @@ -144,7 +145,8 @@ namespace ASC.Calendar.Controllers SetupInfo setupInfo, InstanceCrypto instanceCrypto, CalendarManager calendarManager, - ProductEntryPoint productEntryPoint) + ProductEntryPoint productEntryPoint, + IHttpClientFactory clientFactory) { AuthContext = authContext; Authentication = authentication; @@ -174,6 +176,7 @@ namespace ASC.Calendar.Controllers InstanceCrypto = instanceCrypto; CalendarManager = calendarManager; ProductEntryPoint = productEntryPoint; + ClientFactory = clientFactory; CalendarManager.RegistryCalendar(new SharedEventsCalendar(AuthContext, TimeZoneConverter, TenantManager, DataProvider)); var birthdayReminderCalendar = new BirthdayReminderCalendar(AuthContext, TimeZoneConverter, UserManager, DisplayUserSettingsHelper); @@ -314,10 +317,10 @@ namespace ASC.Calendar.Controllers //internal var calendars = DataProvider.LoadCalendarsForUser(SecurityContext.CurrentAccount.ID, out newCalendarsCount); - result.AddRange(calendars.ConvertAll(c => CalendarWrapperHelper.Get(c))); - - - //external + result.AddRange(calendars.ConvertAll(c => CalendarWrapperHelper.Get(c))); + + + //external var extCalendars = CalendarManager.GetCalendarsForUser(SecurityContext.CurrentAccount.ID, UserManager); var viewSettings = DataProvider.GetUserViewSettings(SecurityContext.CurrentAccount.ID, extCalendars.ConvertAll(c => c.Id)); @@ -340,16 +343,16 @@ namespace ASC.Calendar.Controllers else result.ForEach(c => c.Events = c.UserCalendar.GetEventWrappers(SecurityContext.CurrentAccount.ID, startDate, endDate, EventWrapperHelper)); - result.AddRange(extCalendarsWrappers); - - //TODO for personal + result.AddRange(extCalendarsWrappers); + + //TODO for personal /* //remove all subscription except ical streams result.RemoveAll(c => c.IsSubscription && !c.IsiCalStream); result.ForEach(c => c.Events = c.UserCalendar.GetEventWrappers(SecurityContext.CurrentAccount.ID, startDate, endDate)); - */ - + */ + var days = new List<ApiDateTime>(); foreach (var cal in result) { @@ -399,7 +402,7 @@ namespace ASC.Calendar.Controllers .FindAll(c => c.IsAcceptedSubscription); - extCalendarsWrappers.ForEach(c => + extCalendarsWrappers.ForEach(c => { c.Events = c.UserCalendar.GetEventWrappers(SecurityContext.CurrentAccount.ID, startDate, endDate, EventWrapperHelper); c.Todos = c.UserCalendar.GetTodoWrappers(SecurityContext.CurrentAccount.ID, startDate, endDate, TodoWrapperHelper); @@ -475,8 +478,8 @@ namespace ASC.Calendar.Controllers // var path = UrlPath.ResolveUrl(() => new CalendarApi().GetCalendariCalStream(calendarId, sig)); - var path = "api/2.0/calendar/" + calendarId + "/ical/" + sig; - + var path = "api/2.0/calendar/" + calendarId + "/ical/" + sig; + var result = new Uri(HttpContext.Request.GetUrlRewriter(), VirtualPathUtility.ToAbsolute("~/" + path)).ToString(); return new { result }; @@ -510,7 +513,7 @@ namespace ASC.Calendar.Controllers var todoCalendars = DataProvider.LoadTodoCalendarsForUser(SecurityContext.CurrentAccount.ID); var userTimeZone = TenantManager.GetCurrentTenant().TimeZone; - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); var newCalendar = new BusinessObjects.Calendar(AuthContext, TimeZoneConverter, icalendar, DataProvider); var todoCal = CalendarWrapperHelper.Get(newCalendar); @@ -522,7 +525,7 @@ namespace ASC.Calendar.Controllers Description = "", TextColor = BusinessObjects.Calendar.DefaultTextColor, BackgroundColor = BusinessObjects.Calendar.DefaultTodoBackgroundColor, - TimeZone = userTimeZone.ToString(), + TimeZone = userTimeZone, AlertType = EventAlertType.FifteenMinutes, SharingOptions = null, ICalUrl = null, @@ -531,7 +534,7 @@ namespace ASC.Calendar.Controllers todoCal = CreateCalendar(todoCalModel); if (todoCal != null) - { + { try { var dataCaldavGuid = DataProvider.GetCalDavGuid(todoCal.Id); @@ -542,7 +545,7 @@ namespace ASC.Calendar.Controllers var sharedCalUrl = new Uri(new Uri(calDavServerUrl), "/caldav/" + curCaldavUserName + "/" + caldavGuid).ToString(); var calendar = GetUserCaldavCalendar(sharedCalUrl, userName); - if (calendar != "") + if (calendar.Length != 0) { if (calendar == "NotFound") { @@ -579,7 +582,7 @@ namespace ASC.Calendar.Controllers { var sharedCalUrl = new Uri(new Uri(calDavServerUrl), "/caldav/" + curCaldavUserName + "/" + todoCalendars[0].calDavGuid).ToString(); var calendar = GetUserCaldavCalendar(sharedCalUrl, userName); - if (calendar != "") + if (calendar.Length != 0) { if (calendar == "NotFound") { @@ -587,10 +590,10 @@ namespace ASC.Calendar.Controllers "Todo_calendar", "", BusinessObjects.Calendar.DefaultTodoBackgroundColor, - todoCalendars[0].calDavGuid.ToString(), + todoCalendars[0].calDavGuid, myUri, curCaldavUserName, - userName + userName ); } return sharedCalUrl; @@ -610,14 +613,14 @@ namespace ASC.Calendar.Controllers if (SecurityContext.IsAuthenticated) { - var sharedCalendar = GetCalendarById(calendarId); - + var sharedCalendar = GetCalendarById(calendarId); + var currentCaldavUserName = userName + "@" + caldavHost; var sharedCalUrl = new Uri(new Uri(calDavServerUrl), "/caldav/" + currentCaldavUserName + "/" + calendarId + "-shared").ToString(); var calendar = GetUserCaldavCalendar(sharedCalUrl, userName); - if (calendar != "") + if (calendar.Length != 0) { if (calendar == "NotFound") { @@ -632,7 +635,7 @@ namespace ASC.Calendar.Controllers true ); } - if (sharedCalUrl != "") + if (sharedCalUrl.Length != 0) { var calendarIcs = GetCalendariCalString(calendarId, true); @@ -654,7 +657,7 @@ namespace ASC.Calendar.Controllers var isShared = ownerId != SecurityContext.CurrentAccount.ID; var calDavGuid = cal.calDavGuid; - if (calDavGuid == "" || calDavGuid == Guid.Empty.ToString()) + if (calDavGuid.Length == 0 || calDavGuid == Guid.Empty.ToString()) { calDavGuid = Guid.NewGuid().ToString(); DataProvider.UpdateCalendarGuid(Convert.ToInt32(cal.Id), Guid.Parse(calDavGuid)); @@ -666,7 +669,7 @@ namespace ASC.Calendar.Controllers var caldavCalendar = GetUserCaldavCalendar(calUrl, userName); - if (caldavCalendar != "") + if (caldavCalendar.Length != 0) { if (caldavCalendar == "NotFound") { @@ -721,7 +724,7 @@ namespace ASC.Calendar.Controllers var team = caldavCalendarModel.Team; try - { + { var myUri = HttpContext.Request.GetUrlRewriter(); var caldavHost = myUri.Host; @@ -745,7 +748,7 @@ namespace ASC.Calendar.Controllers } catch (Exception ex) { - Log.Error(String.Format("Delete project caldav calendar: {0}", ex.Message)); + Log.Error($"Delete project caldav calendar: {ex.Message}"); } } @@ -802,7 +805,7 @@ namespace ASC.Calendar.Controllers } catch (Exception ex) { - Log.Error(String.Format("Delete CRM caldav event: {0}", ex.Message)); + Log.Error($"Delete CRM caldav event: {ex.Message}"); } } @@ -895,7 +898,7 @@ namespace ASC.Calendar.Controllers } catch (Exception ex) { - Log.Error(String.Format("Error: {0}", ex.Message)); + Log.Error($"Error: {ex.Message}"); } finally { @@ -904,12 +907,12 @@ namespace ASC.Calendar.Controllers { SecurityContext.AuthenticateMeWithoutCookie(currentUserId); } - } + } } } catch (Exception ex) { - Log.Error(String.Format("Create/update CRM caldav event: {0}", ex.Message)); + Log.Error($"Create/update CRM caldav event: {ex.Message}"); } } @@ -924,7 +927,7 @@ namespace ASC.Calendar.Controllers { evt.End = new CalDateTime(evt.End.AddDays(1)); } - evt.Status = EventStatus.Confirmed.ToString(); + evt.Status = nameof(EventStatus.Confirmed); if (alert > 0) { evt.Alarms.Add( @@ -1013,7 +1016,7 @@ namespace ASC.Calendar.Controllers var calendarIcs = GetCalendariCalString(icalendar.Id, true); var tenant = TenantManager.GetCurrentTenant(); - var caldavTask = isShared + var caldavTask = isShared ? new Task(() => CreateCaldavSharedEvents(calDavGuid.ToString(), calendarIcs, myUri, email, icalendar, SecurityContext.CurrentAccount, tenant.TenantId)) : new Task(() => CreateCaldavEvents(calDavGuid.ToString(), myUri, email, icalendar, calendarIcs, tenant.TenantId)); caldavTask.Start(); @@ -1027,19 +1030,19 @@ namespace ASC.Calendar.Controllers private string GetUserCaldavCalendar(string calUrl, string encoded) { var authorization = DataProvider.GetUserAuthorization(encoded); - - var request = new HttpRequestMessage(); - request.Method = HttpMethod.Get; - request.RequestUri = new Uri(calUrl); - request.Content.Headers.ContentType = new MediaTypeHeaderValue("text/xml") - { - CharSet = Encoding.UTF8.WebName - }; - request.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(Encoding.UTF8.GetBytes(authorization))); + + var request = new HttpRequestMessage(); + request.Method = HttpMethod.Get; + request.RequestUri = new Uri(calUrl); + request.Content.Headers.ContentType = new MediaTypeHeaderValue("text/xml") + { + CharSet = Encoding.UTF8.WebName + }; + request.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(Encoding.UTF8.GetBytes(authorization))); try - { - using var httpClient = new HttpClient(); + { + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using (var reader = new StreamReader(response.Content.ReadAsStream())) { @@ -1085,23 +1088,23 @@ namespace ASC.Calendar.Controllers "<C:supported-calendar-component-set><C:comp name=\"VEVENT\" /><C:comp name=\"VJOURNAL\" /><C:comp name=\"VTODO\" />" + "</C:supported-calendar-component-set><displayname>" + name + "</displayname>" + "<I:calendar-color>" + color + "</I:calendar-color>" + - "<C:calendar-description>" + description + "</C:calendar-description></prop></set></mkcol>"; - + "<C:calendar-description>" + description + "</C:calendar-description></prop></set></mkcol>"; + var requestUrl = calDavServerUrl + "/" + HttpUtility.UrlEncode(currentUserName) + "/" + calDavGuid + (isSharedCalendar ? "-shared" : ""); try - { - var request = new HttpRequestMessage(); - request.RequestUri = new Uri(requestUrl); - request.Method = new HttpMethod("MKCOL"); + { + var request = new HttpRequestMessage(); + request.RequestUri = new Uri(requestUrl); + request.Method = new HttpMethod("MKCOL"); var authorization = isSharedCalendar ? DataProvider.GetSystemAuthorization() : DataProvider.GetUserAuthorization(email); request.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(Encoding.UTF8.GetBytes(authorization))); - request.Content = new StringContent(data, Encoding.UTF8, "text/xml"); - - using var httpClient = new HttpClient(); - using var response = httpClient.Send(request); + request.Content = new StringContent(data, Encoding.UTF8, "text/xml"); + + var httpClient = ClientFactory.CreateClient(); + using var response = httpClient.Send(request); using (var reader = new StreamReader(response.Content.ReadAsStream())) { @@ -1175,10 +1178,10 @@ namespace ASC.Calendar.Controllers { SecurityContext.AuthenticateMeWithoutCookie(userId); var icalFormat = GetCalendariCalString(calendarId); - if (icalFormat != null) - { - resp = new FileStreamResult(new MemoryStream(Encoding.UTF8.GetBytes(icalFormat)), "text/calendar"); - resp.FileDownloadName = calendarId + ".ics"; + if (icalFormat != null) + { + resp = new FileStreamResult(new MemoryStream(Encoding.UTF8.GetBytes(icalFormat)), "text/calendar"); + resp.FileDownloadName = calendarId + ".ics"; } } finally @@ -1268,12 +1271,12 @@ namespace ASC.Calendar.Controllers if (!string.IsNullOrEmpty(calendar.ICalUrl)) { try - { - var request = new HttpRequestMessage(); - request.RequestUri = new Uri(calendar.ICalUrl); - using var httpClient = new HttpClient(); - using var response = httpClient.Send(request); - + { + var request = new HttpRequestMessage(); + request.RequestUri = new Uri(calendar.ICalUrl); + var httpClient = ClientFactory.CreateClient(); + using var response = httpClient.Send(request); + using (var stream = response.Content.ReadAsStream()) { var ms = new MemoryStream(); @@ -1290,7 +1293,7 @@ namespace ASC.Calendar.Controllers } catch (Exception ex) { - Log.Info(String.Format("Error import events to new calendar by ical url: {0}", ex.Message)); + Log.Info($"Error import events to new calendar by ical url: {ex.Message}"); } } @@ -1333,11 +1336,11 @@ namespace ASC.Calendar.Controllers if (!string.IsNullOrEmpty(iCalUrl)) { try - { - var request = new HttpRequestMessage(); - request.RequestUri = new Uri(iCalUrl); - - using var httpClient = new HttpClient(); + { + var request = new HttpRequestMessage(); + request.RequestUri = new Uri(iCalUrl); + + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using (var stream = response.Content.ReadAsStream()) { @@ -1355,7 +1358,7 @@ namespace ASC.Calendar.Controllers } catch (Exception ex) { - Log.Info(String.Format("Error import events to calendar by ical url: {0}", ex.Message)); + Log.Info($"Error import events to calendar by ical url: {ex.Message}"); } } @@ -1467,8 +1470,8 @@ namespace ASC.Calendar.Controllers var replaceSharingEventThread = new Thread(() => { - TenantManager.SetCurrentTenant(currentTenantId); - + TenantManager.SetCurrentTenant(currentTenantId); + foreach (var sharingOption in oldSharingList) { if (!sharingOption.IsGroup) @@ -1632,8 +1635,8 @@ namespace ASC.Calendar.Controllers var replaceSharingEventThread = new Thread(() => { - TenantManager.SetCurrentTenant(currentTenantId); - + TenantManager.SetCurrentTenant(currentTenantId); + foreach (var sharingOption in sharingList) { if (!sharingOption.IsGroup) @@ -1723,7 +1726,7 @@ namespace ASC.Calendar.Controllers { string[] split = evt.Uid.Split(new Char[] { '@' }); var myUri = HttpContext.Request.GetUrlRewriter(); - var email = UserManager.GetUsers(SecurityContext.CurrentAccount.ID).Email; + var email = UserManager.GetUsers(SecurityContext.CurrentAccount.ID).Email; var fullAccess = CheckPermissions(evt, CalendarAccessRights.FullAccessAction, true); deleteEvent(fullAccess ? split[0] + "_write" : split[0], SharedEventsCalendar.CalendarId, email, myUri, SecurityContext.CurrentAccount.ID != evt.OwnerId); @@ -1733,8 +1736,8 @@ namespace ASC.Calendar.Controllers } private void deleteEvent(string uid, string calendarId, string email, Uri myUri, bool isShared = false) - { - + { + try { var сaldavGuid = ""; @@ -1750,7 +1753,7 @@ namespace ASC.Calendar.Controllers сaldavGuid = calendarId; } - if (сaldavGuid != "") + if (сaldavGuid.Length != 0) { var calDavServerUrl = myUri.Scheme + "://" + myUri.Host + "/caldav"; @@ -1761,15 +1764,15 @@ namespace ASC.Calendar.Controllers var requestUrl = calDavServerUrl + "/" + HttpUtility.UrlEncode(currentUserName) + "/" + (isShared ? сaldavGuid + "-shared" : сaldavGuid) + "/" + uid + ".ics"; try - { - var request = new HttpRequestMessage(); - request.RequestUri = new Uri(requestUrl); - request.Method = HttpMethod.Delete; - + { + var request = new HttpRequestMessage(); + request.RequestUri = new Uri(requestUrl); + request.Method = HttpMethod.Delete; + var authorization = isShared ? DataProvider.GetSystemAuthorization() : DataProvider.GetUserAuthorization(email); request.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(Encoding.UTF8.GetBytes(authorization))); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); httpClient.Send(request); } catch (HttpRequestException ex) @@ -1860,7 +1863,7 @@ namespace ASC.Calendar.Controllers return AddEvent(calendarId, eventModel); } - throw new Exception(string.Format("Can't parse {0} to int", calendar.Id)); + throw new Exception($"Can't parse {calendar.Id} to int"); } /// <summary> @@ -1944,7 +1947,7 @@ namespace ASC.Calendar.Controllers { var defaultCalendar = LoadInternalCalendars().First(x => (!x.IsSubscription && x.IsTodo != 1)); if (!int.TryParse(defaultCalendar.Id, out calId)) - throw new Exception(string.Format("Can't parse {0} to int", defaultCalendar.Id)); + throw new Exception($"Can't parse {defaultCalendar.Id} to int"); } var calendars = DDayICalParser.DeserializeCalendar(ics); @@ -1973,7 +1976,7 @@ namespace ASC.Calendar.Controllers if (eventObj.IsAllDay && utcStartDate.Date < utcEndDate.Date) utcEndDate = utcEndDate.AddDays(-1); - eventUid = eventUid == null ? null : string.Format("{0}@onlyoffice.com", eventUid); + eventUid = eventUid == null ? null : $"{eventUid}@onlyoffice.com"; var result = CreateEvent(calId, eventObj.Summary, @@ -2122,7 +2125,7 @@ namespace ASC.Calendar.Controllers } }); - updateCaldavThread.Start(); + updateCaldavThread.Start(); } catch (Exception e) { @@ -2263,8 +2266,8 @@ namespace ASC.Calendar.Controllers var calDavGuid = calendarObj != null ? calendarObj.calDavGuid : ""; var myUri = HttpContext.Request.GetUrlRewriter(); - var currentUserEmail = UserManager.GetUsers(AuthContext.CurrentAccount.ID).Email.ToLower(); - + var currentUserEmail = UserManager.GetUsers(AuthContext.CurrentAccount.ID).Email.ToLower(); + var isFullAccess = PermissionContext.PermissionResolver.Check(AuthContext.CurrentAccount, evt, null, CalendarAccessRights.FullAccessAction); var isShared = false; @@ -2576,8 +2579,8 @@ namespace ASC.Calendar.Controllers try { var calDavGuid = cal != null ? cal.calDavGuid : ""; - var currentUserEmail = UserManager.GetUsers(AuthContext.CurrentAccount.ID).Email.ToLower(); - + var currentUserEmail = UserManager.GetUsers(AuthContext.CurrentAccount.ID).Email.ToLower(); + var calendarObj = DataProvider.GetCalendarById(Convert.ToInt32(cal.Id)); var calendarObjViewSettings = calendarObj != null && calendarObj.ViewSettings != null ? calendarObj.ViewSettings.FirstOrDefault() : null; var targetCalendar = DDayICalParser.ConvertCalendar(calendarObj != null ? calendarObj.GetUserCalendar(calendarObjViewSettings) : null); @@ -2686,7 +2689,7 @@ namespace ASC.Calendar.Controllers var todoCalendars = DataProvider.LoadTodoCalendarsForUser(AuthContext.CurrentAccount.ID); var userTimeZone = TenantManager.GetCurrentTenant().TimeZone; - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); var newCalendar = new BusinessObjects.Calendar(AuthContext, TimeZoneConverter, icalendar, DataProvider); var todoCal = CalendarWrapperHelper.Get(newCalendar); @@ -2698,7 +2701,7 @@ namespace ASC.Calendar.Controllers Description = "", TextColor = BusinessObjects.Calendar.DefaultTextColor, BackgroundColor = BusinessObjects.Calendar.DefaultTodoBackgroundColor, - TimeZone = userTimeZone.ToString(), + TimeZone = userTimeZone, AlertType = EventAlertType.FifteenMinutes, SharingOptions = null, ICalUrl = null, @@ -2712,7 +2715,7 @@ namespace ASC.Calendar.Controllers { var defaultCalendar = LoadInternalCalendars().First(x => (!x.IsSubscription && x.IsTodo != 1)); if (!int.TryParse(defaultCalendar.Id, out calendarId)) - throw new Exception(string.Format("Can't parse {0} to int", defaultCalendar.Id)); + throw new Exception($"Can't parse {defaultCalendar.Id} to int"); } var calendars = DDayICalParser.DeserializeCalendar(ics); @@ -2735,7 +2738,7 @@ namespace ASC.Calendar.Controllers var utcStartDate = todoObj.Start != null ? DDayICalParser.ToUtc(todoObj.Start) : DateTime.MinValue; - todoUid = todoUid == null ? null : string.Format("{0}@onlyoffice.com", todoUid); + todoUid = todoUid == null ? null : $"{todoUid}@onlyoffice.com"; var result = CreateTodo(calendarId, @@ -2844,8 +2847,8 @@ namespace ASC.Calendar.Controllers var calDavGuid = calendarObj != null ? calendarObj.calDavGuid : ""; var myUri = HttpContext.Request.GetUrlRewriter(); - var currentUserEmail = UserManager.GetUsers(AuthContext.CurrentAccount.ID).Email.ToLower(); - + var currentUserEmail = UserManager.GetUsers(AuthContext.CurrentAccount.ID).Email.ToLower(); + var updateCaldavThread = new Thread(() => updateCaldavEvent(old_ics, split[0], true, calDavGuid, myUri, currentUserEmail)); updateCaldavThread.Start(); } @@ -3070,7 +3073,7 @@ namespace ASC.Calendar.Controllers if (int.TryParse(calendar.Id, out calendarId)) return ImportEvents(calendarId, uploadModel); - throw new Exception(string.Format("Can't parse {0} to int", calendar.Id)); + throw new Exception($"Can't parse {calendar.Id} to int"); } /// <summary> @@ -3140,7 +3143,7 @@ namespace ASC.Calendar.Controllers } - throw new Exception(string.Format("Can't parse {0} to int", calendar.Id)); + throw new Exception($"Can't parse {calendar.Id} to int"); } /// <summary> @@ -3162,7 +3165,7 @@ namespace ASC.Calendar.Controllers var textColor = сalendarUrl.TextColor; var backgroundColor = сalendarUrl.BackgroundColor; - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); var cal = icalendar.GetFromUrl(iCalUrl); if (cal.isEmptyName) cal.Name = iCalUrl; @@ -3285,8 +3288,8 @@ namespace ASC.Calendar.Controllers return EventHistoryWrapperHelper.Get(history, canEdit, canNotify, cal, fullHistory); } private bool CheckIsOrganizer(EventHistory history) - { - + { + var canNotify = false; //TODO @@ -3440,79 +3443,79 @@ namespace ASC.Calendar.Controllers } else { - if (EventHistoryHelper.Contains(tmpCalendar, eventHistory)) continue; - - eventHistory = DataProvider.AddEventHistory(eventHistory.CalendarId, eventHistory.EventUid, - eventHistory.EventId, ics); - - var mergedCalendar = EventHistoryHelper.GetMerged(eventHistory); - - if (mergedCalendar == null || mergedCalendar.Events == null || !mergedCalendar.Events.Any()) continue; - - var mergedEvent = mergedCalendar.Events.First(); - - rrule = GetRRuleString(mergedEvent); - - var utcStartDate = mergedEvent.IsAllDay ? mergedEvent.Start.Value : DDayICalParser.ToUtc(mergedEvent.Start); - var utcEndDate = mergedEvent.IsAllDay ? mergedEvent.End.Value : DDayICalParser.ToUtc(mergedEvent.End); - - var existCalendar = DataProvider.GetCalendarById(calendarId); - if (!eventObj.IsAllDay && eventObj.Created != null && !eventObj.Start.IsUtc) - { - var offset = existCalendar.TimeZone.GetUtcOffset(eventObj.Created.Value); - - var _utcStartDate = eventObj.Start.Subtract(offset).Value; - var _utcEndDate = eventObj.End.Subtract(offset).Value; - - utcStartDate = _utcStartDate; - utcEndDate = _utcEndDate; - } - - if (mergedEvent.IsAllDay && utcStartDate.Date < utcEndDate.Date) - utcEndDate = utcEndDate.AddDays(-1); - - var targetEvent = DataProvider.GetEventById(eventHistory.EventId); - var permissions = PublicItemCollectionHelper.GetForEvent(targetEvent); - var sharingOptions = permissions.Items - .Where(x => x.SharingOption.Id != AccessOption.OwnerOption.Id) - .Select(x => new SharingParam - { - Id = x.Id, - actionId = x.SharingOption.Id, - isGroup = x.IsGroup - }).ToList(); - - try - { - var uid = eventObj.Uid; - string[] split = uid.Split(new Char[] { '@' }); - - var calDavGuid = existCalendar != null ? existCalendar.calDavGuid : ""; - var myUri = HttpContext.Request.GetUrlRewriter(); ; - var currentUserEmail = UserManager.GetUsers(SecurityContext.CurrentAccount.ID).Email.ToLower(); - - var updateCaldavThread = new Thread(() => updateCaldavEvent(ics, split[0], true, calDavGuid, myUri, currentUserEmail, DateTime.Now, tmpCalendar.TimeZones[0], existCalendar.TimeZone)); - updateCaldavThread.Start(); - } - catch (Exception e) - { - Log.Error(e.Message); - } - - //updateEvent(ics, split[0], calendarId.ToString(), true, DateTime.Now, tmpCalendar.TimeZones[0], existCalendar.TimeZone); - - CreateEvent(eventHistory.CalendarId, - mergedEvent.Summary, - mergedEvent.Description, - utcStartDate, - utcEndDate, - RecurrenceRule.Parse(rrule), - EventAlertType.Default, - mergedEvent.IsAllDay, - sharingOptions, - mergedEvent.Uid, - DDayICalParser.ConvertEventStatus(mergedEvent.Status), eventObj.Created != null ? eventObj.Created.Value : DateTime.Now); - + if (EventHistoryHelper.Contains(tmpCalendar, eventHistory)) continue; + + eventHistory = DataProvider.AddEventHistory(eventHistory.CalendarId, eventHistory.EventUid, + eventHistory.EventId, ics); + + var mergedCalendar = EventHistoryHelper.GetMerged(eventHistory); + + if (mergedCalendar == null || mergedCalendar.Events == null || !mergedCalendar.Events.Any()) continue; + + var mergedEvent = mergedCalendar.Events.First(); + + rrule = GetRRuleString(mergedEvent); + + var utcStartDate = mergedEvent.IsAllDay ? mergedEvent.Start.Value : DDayICalParser.ToUtc(mergedEvent.Start); + var utcEndDate = mergedEvent.IsAllDay ? mergedEvent.End.Value : DDayICalParser.ToUtc(mergedEvent.End); + + var existCalendar = DataProvider.GetCalendarById(calendarId); + if (!eventObj.IsAllDay && eventObj.Created != null && !eventObj.Start.IsUtc) + { + var offset = existCalendar.TimeZone.GetUtcOffset(eventObj.Created.Value); + + var _utcStartDate = eventObj.Start.Subtract(offset).Value; + var _utcEndDate = eventObj.End.Subtract(offset).Value; + + utcStartDate = _utcStartDate; + utcEndDate = _utcEndDate; + } + + if (mergedEvent.IsAllDay && utcStartDate.Date < utcEndDate.Date) + utcEndDate = utcEndDate.AddDays(-1); + + var targetEvent = DataProvider.GetEventById(eventHistory.EventId); + var permissions = PublicItemCollectionHelper.GetForEvent(targetEvent); + var sharingOptions = permissions.Items + .Where(x => x.SharingOption.Id != AccessOption.OwnerOption.Id) + .Select(x => new SharingParam + { + Id = x.Id, + actionId = x.SharingOption.Id, + isGroup = x.IsGroup + }).ToList(); + + try + { + var uid = eventObj.Uid; + string[] split = uid.Split(new Char[] { '@' }); + + var calDavGuid = existCalendar != null ? existCalendar.calDavGuid : ""; + var myUri = HttpContext.Request.GetUrlRewriter(); ; + var currentUserEmail = UserManager.GetUsers(SecurityContext.CurrentAccount.ID).Email.ToLower(); + + var updateCaldavThread = new Thread(() => updateCaldavEvent(ics, split[0], true, calDavGuid, myUri, currentUserEmail, DateTime.Now, tmpCalendar.TimeZones[0], existCalendar.TimeZone)); + updateCaldavThread.Start(); + } + catch (Exception e) + { + Log.Error(e.Message); + } + + //updateEvent(ics, split[0], calendarId.ToString(), true, DateTime.Now, tmpCalendar.TimeZones[0], existCalendar.TimeZone); + + CreateEvent(eventHistory.CalendarId, + mergedEvent.Summary, + mergedEvent.Description, + utcStartDate, + utcEndDate, + RecurrenceRule.Parse(rrule), + EventAlertType.Default, + mergedEvent.IsAllDay, + sharingOptions, + mergedEvent.Uid, + DDayICalParser.ConvertEventStatus(mergedEvent.Status), eventObj.Created != null ? eventObj.Created.Value : DateTime.Now); + counter++; } } @@ -3558,10 +3561,10 @@ namespace ASC.Calendar.Controllers var date = periodList.ToString(); //has time - if (date.ToLowerInvariant().IndexOf('t') >= 0) + if (date.IndexOf('t', StringComparison.OrdinalIgnoreCase) >= 0) { //is utc time - if (date.ToLowerInvariant().IndexOf('z') >= 0) + if (date.IndexOf('z', StringComparison.OrdinalIgnoreCase) >= 0) { rrule += date; } @@ -3585,7 +3588,7 @@ namespace ASC.Calendar.Controllers } } //for yyyyMMdd/P1D date. Bug in the ical.net - else if (date.ToLowerInvariant().IndexOf("/p") >= 0) + else if (date.IndexOf("/p", StringComparison.OrdinalIgnoreCase) >= 0) { try { @@ -3902,12 +3905,12 @@ namespace ASC.Calendar.Controllers } private void CreateCaldavSharedEvents( - string calendarId, - string calendarIcs, - Uri myUri, - string currentUserEmail, - BaseCalendar icalendar, - Common.Security.Authentication.IAccount currentUser, + string calendarId, + string calendarIcs, + Uri myUri, + string currentUserEmail, + BaseCalendar icalendar, + Common.Security.Authentication.IAccount currentUser, int tenantId ) { @@ -3934,9 +3937,9 @@ namespace ASC.Calendar.Controllers foreach (var e in events) { Event evt = null; - evt = DataProvider.GetEventOnlyByUid(e.Uid); - - + evt = DataProvider.GetEventOnlyByUid(e.Uid); + + isFullAccess = calendarId != BirthdayReminderCalendar.CalendarId && calendarId != "crm_calendar" ? evt != null ? PermissionContext.PermissionResolver.Check(currentUser, evt, null, CalendarAccessRights.FullAccessAction) : isFullAccess : isFullAccess; @@ -3959,7 +3962,7 @@ namespace ASC.Calendar.Controllers else if (calendarId == "crm_calendar" || calendarId.Contains("Project_")) { e.Created = null; - e.Status = EventStatus.Confirmed.ToString(); + e.Status = nameof(EventStatus.Confirmed); } calendar.Events.Clear(); @@ -3997,7 +4000,7 @@ namespace ASC.Calendar.Controllers { try { - if (guid != null && guid != "") + if (guid != null && guid.Length != 0) { var calDavServerUrl = myUri.Scheme + "://" + myUri.Host + "/caldav"; @@ -4013,7 +4016,7 @@ namespace ASC.Calendar.Controllers if (indexOfChar != -1) { ics = ics.Remove(indexOfChar, indexOfCharEND + 14 - indexOfChar); - if (ics.IndexOf("BEGIN:VTIMEZONE") > -1) + if (ics.IndexOf("BEGIN:VTIMEZONE") > -1) updateCaldavEvent(ics, uid, true, guid, myUri, userEmail); } @@ -4062,17 +4065,17 @@ namespace ASC.Calendar.Controllers try - { - var request = new HttpRequestMessage(); - request.RequestUri = new Uri(requestUrl); - request.Method = HttpMethod.Put; + { + var request = new HttpRequestMessage(); + request.RequestUri = new Uri(requestUrl); + request.Method = HttpMethod.Put; var authorization = isShared ? DataProvider.GetSystemAuthorization() : DataProvider.GetUserAuthorization(userEmail); request.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(Encoding.UTF8.GetBytes(authorization))); request.Content = new StringContent(ics, Encoding.UTF8, "text/calendar"); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); httpClient.Send(request); } catch (HttpRequestException ex) @@ -4185,189 +4188,190 @@ namespace ASC.Calendar.Controllers try { SecurityContext.AuthenticateMeWithoutCookie(ownerId); - var request = new HttpRequestMessage(); - request.RequestUri = new Uri(eventURl); - request.Method = HttpMethod.Get; - - var _email = UserManager.GetUsers(ownerId).Email; + var request = new HttpRequestMessage(); + request.RequestUri = new Uri(eventURl); + request.Method = HttpMethod.Get; + + var _email = UserManager.GetUsers(ownerId).Email; var authorization = sharedPostfixIndex != -1 ? DataProvider.GetSystemAuthorization() : DataProvider.GetUserAuthorization(_email); - request.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(Encoding.UTF8.GetBytes(authorization))); - request.Content.Headers.ContentType = new MediaTypeHeaderValue("text/calendar") - { - CharSet = Encoding.UTF8.WebName - }; - - Log.Info(String.Format("UpdateCalDavEvent eventURl: {0}", eventURl)); - - string ics = ""; - - using (var httpClient = new HttpClient()) + request.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(Encoding.UTF8.GetBytes(authorization))); + request.Content.Headers.ContentType = new MediaTypeHeaderValue("text/calendar") + { + CharSet = Encoding.UTF8.WebName + }; + + Log.Info($"UpdateCalDavEvent eventURl: {eventURl}"); + + string ics = ""; + + var httpClient = ClientFactory.CreateClient(); + using (var response = httpClient.Send(request)) using (var reader = new StreamReader(response.Content.ReadAsStream())) { - ics = reader.ReadToEnd(); - } - Log.Info(String.Format("UpdateCalDavEvent: {0}", ics)); - var existEvent = DataProvider.GetEventIdByUid(eventGuid + "%", calendarId); - var existCalendar = DataProvider.GetCalendarById(calendarId); - - var calendars = DDayICalParser.DeserializeCalendar(ics); - var _calendar = calendars == null ? null : calendars.FirstOrDefault(); - var eventObj = _calendar == null || _calendar.Events == null ? null : _calendar.Events.FirstOrDefault(); - if (eventObj != null && existCalendar.IsTodo == 0) - { - var name = eventObj.Summary; - var description = eventObj.Description ?? " "; - - var alarm = eventObj.Alarms == null ? null : eventObj.Alarms.FirstOrDefault(); - var alertType = EventAlertType.Default; - if (alarm != null) - { - if (alarm.Trigger.Duration != null) - { - var alarmMinutes = alarm.Trigger.Duration.Value.Minutes; - var alarmHours = alarm.Trigger.Duration.Value.Hours; - var alarmDays = alarm.Trigger.Duration.Value.Days; - switch (alarmMinutes) - { - case -5: - alertType = EventAlertType.FiveMinutes; - break; - case -15: - alertType = EventAlertType.FifteenMinutes; - break; - case -30: - alertType = EventAlertType.HalfHour; - break; - } - switch (alarmHours) - { - case -1: - alertType = EventAlertType.Hour; - break; - case -2: - alertType = EventAlertType.TwoHours; - break; - } - if (alarmDays == -1) - alertType = EventAlertType.Day; - } - } - - var utcStartDate = eventObj.IsAllDay ? eventObj.Start.Value : DDayICalParser.ToUtc(eventObj.Start); - var utcEndDate = eventObj.IsAllDay ? eventObj.End.Value : DDayICalParser.ToUtc(eventObj.End); - - if (existEvent != null && existCalendar != null && !eventObj.IsAllDay) - { - var offset = existCalendar.TimeZone.GetUtcOffset(existEvent.UtcUpdateDate); - if (!eventObj.End.IsUtc && !eventObj.Start.IsUtc) - { - utcStartDate = eventObj.Start.Subtract(offset).Value; - utcEndDate = eventObj.End.Subtract(offset).Value; - } - else - { - var createOffset = existCalendar.TimeZone.GetUtcOffset(eventObj.Created.Value); - var startOffset = existCalendar.TimeZone.GetUtcOffset(eventObj.Start.Value); - var endOffset = existCalendar.TimeZone.GetUtcOffset(eventObj.End.Value); - - if (createOffset != startOffset) - { - var _utcStartDate = eventObj.Start.Subtract(createOffset).Add(startOffset).Value; - utcStartDate = _utcStartDate; - } - if (createOffset != endOffset) - { - var _utcEndDate = eventObj.End.Subtract(createOffset).Add(endOffset).Value; - utcEndDate = _utcEndDate; - } - } - } - - - bool isAllDayLong = eventObj.IsAllDay; - - var rrule = RecurrenceRule.Parse(GetRRuleString(eventObj)); - var status = DDayICalParser.ConvertEventStatus(eventObj.Status); - - if (existEvent != null) - { - var eventId = int.Parse(existEvent.Id); - - var cal = new Ical.Net.Calendar(); - - var permissions = PublicItemCollectionHelper.GetForEvent(existEvent); - var sharingOptions = permissions.Items - .Where(x => x.SharingOption.Id != AccessOption.OwnerOption.Id) - .Select(x => new SharingParam - { - Id = x.Id, - actionId = x.SharingOption.Id, - isGroup = x.IsGroup - }).ToList(); - eventObj.Start = new CalDateTime(DateTime.SpecifyKind(utcStartDate, DateTimeKind.Utc), TimeZoneInfo.Utc.Id); - eventObj.End = new CalDateTime(DateTime.SpecifyKind(utcEndDate, DateTimeKind.Utc), TimeZoneInfo.Utc.Id); - eventObj.Created = new CalDateTime(DateTime.SpecifyKind(eventObj.Created != null ? eventObj.Created.Value : DateTime.Now, DateTimeKind.Utc), TimeZoneInfo.Utc.Id); - - - cal.Events.Add(eventObj); - var eventModel = new EventModel - { - EventId = eventId, - CalendarId = calendarId.ToString(), - Ics = DDayICalParser.SerializeCalendar(cal), - AlertType = alertType, - SharingOptions = sharingOptions, - FromCalDavServer = true, - OwnerId = ownerId.ToString() - }; - UpdateEvent(eventModel); - } - else - { - var eventModel = new EventModel - { - Ics = ics, - AlertType = alertType, - SharingOptions = null, - EventUid = null - }; - AddEvent(calendarId, eventModel); - } - } - var todoObj = _calendar == null || _calendar.Todos == null ? null : _calendar.Todos.FirstOrDefault(); - if (todoObj != null && existCalendar.IsTodo == 1) - { - var todoName = todoObj.Summary; - var todoDescription = todoObj.Description ?? " "; - var todoUtcStartDate = todoObj.Start != null ? DDayICalParser.ToUtc(todoObj.Start) : DateTime.MinValue; - var todoCompleted = todoObj.Completed != null ? DDayICalParser.ToUtc(todoObj.Completed) : DateTime.MinValue; - - var existTodo = DataProvider.GetTodoIdByUid(eventGuid + "%", calendarId); - - if (existTodo != null) - { - var todoId = int.Parse(existTodo.Id); - - - UpdateTodo( - calendarId, - todoName, - todoDescription, - todoUtcStartDate, - existTodo.Uid, - todoCompleted); - } - else - { - CreateTodo(calendarId, - todoName, - todoDescription, - todoUtcStartDate, - eventGuid, - todoCompleted); - } - } + ics = reader.ReadToEnd(); + } + Log.Info($"UpdateCalDavEvent: {ics}"); + var existEvent = DataProvider.GetEventIdByUid(eventGuid + "%", calendarId); + var existCalendar = DataProvider.GetCalendarById(calendarId); + + var calendars = DDayICalParser.DeserializeCalendar(ics); + var _calendar = calendars == null ? null : calendars.FirstOrDefault(); + var eventObj = _calendar == null || _calendar.Events == null ? null : _calendar.Events.FirstOrDefault(); + if (eventObj != null && existCalendar.IsTodo == 0) + { + var name = eventObj.Summary; + var description = eventObj.Description ?? " "; + + var alarm = eventObj.Alarms == null ? null : eventObj.Alarms.FirstOrDefault(); + var alertType = EventAlertType.Default; + if (alarm != null) + { + if (alarm.Trigger.Duration != null) + { + var alarmMinutes = alarm.Trigger.Duration.Value.Minutes; + var alarmHours = alarm.Trigger.Duration.Value.Hours; + var alarmDays = alarm.Trigger.Duration.Value.Days; + switch (alarmMinutes) + { + case -5: + alertType = EventAlertType.FiveMinutes; + break; + case -15: + alertType = EventAlertType.FifteenMinutes; + break; + case -30: + alertType = EventAlertType.HalfHour; + break; + } + switch (alarmHours) + { + case -1: + alertType = EventAlertType.Hour; + break; + case -2: + alertType = EventAlertType.TwoHours; + break; + } + if (alarmDays == -1) + alertType = EventAlertType.Day; + } + } + + var utcStartDate = eventObj.IsAllDay ? eventObj.Start.Value : DDayICalParser.ToUtc(eventObj.Start); + var utcEndDate = eventObj.IsAllDay ? eventObj.End.Value : DDayICalParser.ToUtc(eventObj.End); + + if (existEvent != null && existCalendar != null && !eventObj.IsAllDay) + { + var offset = existCalendar.TimeZone.GetUtcOffset(existEvent.UtcUpdateDate); + if (!eventObj.End.IsUtc && !eventObj.Start.IsUtc) + { + utcStartDate = eventObj.Start.Subtract(offset).Value; + utcEndDate = eventObj.End.Subtract(offset).Value; + } + else + { + var createOffset = existCalendar.TimeZone.GetUtcOffset(eventObj.Created.Value); + var startOffset = existCalendar.TimeZone.GetUtcOffset(eventObj.Start.Value); + var endOffset = existCalendar.TimeZone.GetUtcOffset(eventObj.End.Value); + + if (createOffset != startOffset) + { + var _utcStartDate = eventObj.Start.Subtract(createOffset).Add(startOffset).Value; + utcStartDate = _utcStartDate; + } + if (createOffset != endOffset) + { + var _utcEndDate = eventObj.End.Subtract(createOffset).Add(endOffset).Value; + utcEndDate = _utcEndDate; + } + } + } + + + bool isAllDayLong = eventObj.IsAllDay; + + var rrule = RecurrenceRule.Parse(GetRRuleString(eventObj)); + var status = DDayICalParser.ConvertEventStatus(eventObj.Status); + + if (existEvent != null) + { + var eventId = int.Parse(existEvent.Id); + + var cal = new Ical.Net.Calendar(); + + var permissions = PublicItemCollectionHelper.GetForEvent(existEvent); + var sharingOptions = permissions.Items + .Where(x => x.SharingOption.Id != AccessOption.OwnerOption.Id) + .Select(x => new SharingParam + { + Id = x.Id, + actionId = x.SharingOption.Id, + isGroup = x.IsGroup + }).ToList(); + eventObj.Start = new CalDateTime(DateTime.SpecifyKind(utcStartDate, DateTimeKind.Utc), TimeZoneInfo.Utc.Id); + eventObj.End = new CalDateTime(DateTime.SpecifyKind(utcEndDate, DateTimeKind.Utc), TimeZoneInfo.Utc.Id); + eventObj.Created = new CalDateTime(DateTime.SpecifyKind(eventObj.Created != null ? eventObj.Created.Value : DateTime.Now, DateTimeKind.Utc), TimeZoneInfo.Utc.Id); + + + cal.Events.Add(eventObj); + var eventModel = new EventModel + { + EventId = eventId, + CalendarId = calendarId.ToString(), + Ics = DDayICalParser.SerializeCalendar(cal), + AlertType = alertType, + SharingOptions = sharingOptions, + FromCalDavServer = true, + OwnerId = ownerId.ToString() + }; + UpdateEvent(eventModel); + } + else + { + var eventModel = new EventModel + { + Ics = ics, + AlertType = alertType, + SharingOptions = null, + EventUid = null + }; + AddEvent(calendarId, eventModel); + } + } + var todoObj = _calendar == null || _calendar.Todos == null ? null : _calendar.Todos.FirstOrDefault(); + if (todoObj != null && existCalendar.IsTodo == 1) + { + var todoName = todoObj.Summary; + var todoDescription = todoObj.Description ?? " "; + var todoUtcStartDate = todoObj.Start != null ? DDayICalParser.ToUtc(todoObj.Start) : DateTime.MinValue; + var todoCompleted = todoObj.Completed != null ? DDayICalParser.ToUtc(todoObj.Completed) : DateTime.MinValue; + + var existTodo = DataProvider.GetTodoIdByUid(eventGuid + "%", calendarId); + + if (existTodo != null) + { + var todoId = int.Parse(existTodo.Id); + + + UpdateTodo( + calendarId, + todoName, + todoDescription, + todoUtcStartDate, + existTodo.Uid, + todoCompleted); + } + else + { + CreateTodo(calendarId, + todoName, + todoDescription, + todoUtcStartDate, + eventGuid, + todoCompleted); + } + } } finally { @@ -4452,10 +4456,10 @@ namespace ASC.Calendar.Controllers } } private void CreateCaldavEvents( - string calDavGuid, - Uri myUri, - string currentUserEmail, - BaseCalendar icalendar, + string calDavGuid, + Uri myUri, + string currentUserEmail, + BaseCalendar icalendar, string calendarIcs, int tenantId ) @@ -4547,16 +4551,16 @@ namespace ASC.Calendar.Controllers "<INF:addressbook-color /><CR:addressbook-description /></prop></remove></propertyupdate>"; try - { - var request = new HttpRequestMessage(); - request.RequestUri = new Uri(requestUrl); - request.Method = new HttpMethod("PROPPATCH"); + { + var request = new HttpRequestMessage(); + request.RequestUri = new Uri(requestUrl); + request.Method = new HttpMethod("PROPPATCH"); var authorization = isSharedCalendar ? DataProvider.GetSystemAuthorization() : DataProvider.GetUserAuthorization(email); request.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(Encoding.UTF8.GetBytes(authorization))); request.Content = new StringContent(data, Encoding.UTF8, "text/calendar"); - - using var httpClient = new HttpClient(); + + var httpClient = ClientFactory.CreateClient(); var response = httpClient.Send(request); using (var reader = new StreamReader(response.Content.ReadAsStream())) @@ -4654,7 +4658,7 @@ namespace ASC.Calendar.Controllers TimeZoneInfo calendarTimeZone = null, string calGuid = null) { - if (calGuid != "" && myUri != null && user != null) + if (calGuid.Length != 0 && myUri != null && user != null) { string eventUid = guid, oldEventUid = guid; @@ -4686,13 +4690,13 @@ namespace ASC.Calendar.Controllers ".ics"; try - { - var request = new HttpRequestMessage(); - request.RequestUri = new Uri(requestDeleteUrl); - request.Method = HttpMethod.Delete; - request.Headers.Add("Authorization", "Basic " + encoded); - - using var httpClient = new HttpClient(); + { + var request = new HttpRequestMessage(); + request.RequestUri = new Uri(requestDeleteUrl); + request.Method = HttpMethod.Delete; + request.Headers.Add("Authorization", "Basic " + encoded); + + var httpClient = ClientFactory.CreateClient(); httpClient.Send(request); } catch (HttpRequestException ex) @@ -4751,13 +4755,13 @@ namespace ASC.Calendar.Controllers updatedEvents.Add(guid); try - { - var request = new HttpRequestMessage(); - request.RequestUri = new Uri(requestDeleteUrl); - request.Method = HttpMethod.Delete; - request.Headers.Add("Authorization", "Basic " + encoded); - - using var httpClient = new HttpClient(); + { + var request = new HttpRequestMessage(); + request.RequestUri = new Uri(requestDeleteUrl); + request.Method = HttpMethod.Delete; + request.Headers.Add("Authorization", "Basic " + encoded); + + var httpClient = ClientFactory.CreateClient(); httpClient.Send(request); } catch (HttpRequestException ex) @@ -4776,6 +4780,6 @@ namespace ASC.Calendar.Controllers updateCaldavEvent(oldIcs, eventUid, true, calendarId, myUri, userSharingInfo.Email, updateDate, calendarVTimeZone, calendarTimeZone, false, true); } - } - } + } + } } \ No newline at end of file diff --git a/products/ASC.Calendar/Server/Models/EventWrapper.cs b/products/ASC.Calendar/Server/Models/EventWrapper.cs index 96a942a087..2be4acbead 100644 --- a/products/ASC.Calendar/Server/Models/EventWrapper.cs +++ b/products/ASC.Calendar/Server/Models/EventWrapper.cs @@ -38,6 +38,7 @@ using ASC.Common.Utils; using ASC.Common; using ASC.Calendar.iCalParser; using ASC.Calendar.BusinessObjects; +using System.Net.Http; namespace ASC.Calendar.Models { @@ -140,6 +141,7 @@ namespace ASC.Calendar.Models private AuthContext AuthContext { get; } private TimeZoneConverter TimeZoneConverter { get; } private DataProvider DataProvider { get; } + private IHttpClientFactory ClientFactory { get; } public EventWrapperHelper( UserManager userManager, @@ -150,7 +152,8 @@ namespace ASC.Calendar.Models PublicItemCollectionHelper publicItemCollectionHelper, AuthContext context, TimeZoneConverter timeZoneConverter, - DataProvider dataProvider) + DataProvider dataProvider, + IHttpClientFactory clientFactory) { Authentication = authentication; TenantManager = tenantManager; @@ -161,6 +164,7 @@ namespace ASC.Calendar.Models AuthContext = context; TimeZoneConverter = timeZoneConverter; DataProvider = dataProvider; + ClientFactory = clientFactory; } public EventWrapper Get(IEvent baseEvent, Guid userId, TimeZoneInfo timeZone, DateTime utcStartDate, DateTime utcEndDate, DateTime utcUpdateDate) { @@ -184,7 +188,7 @@ namespace ASC.Calendar.Models eventWraper.Description = _baseEvent.Description; eventWraper.AllDayLong = _baseEvent.AllDayLong; ; - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); //--- var startD = _utcStartDate != DateTime.MinValue ? _utcStartDate : _baseEvent.UtcStartDate; startD = new DateTime(startD.Ticks, DateTimeKind.Utc); diff --git a/products/ASC.Calendar/Server/Models/PublicItemCollection.cs b/products/ASC.Calendar/Server/Models/PublicItemCollection.cs index 3d04903da2..94dc39872f 100644 --- a/products/ASC.Calendar/Server/Models/PublicItemCollection.cs +++ b/products/ASC.Calendar/Server/Models/PublicItemCollection.cs @@ -86,10 +86,10 @@ namespace ASC.Calendar.Models Id = calendar.OwnerId, IsGroup = false }, - calendar.Id.ToString(), calendar.OwnerId)); + calendar.Id, calendar.OwnerId)); foreach (var item in calendar.SharingOptions.PublicItems) - sharingOptions.Items.Add(PublicItemWrapperHelper.Get(item, calendar.Id.ToString(), calendar.OwnerId)); + sharingOptions.Items.Add(PublicItemWrapperHelper.Get(item, calendar.Id, calendar.OwnerId)); return sharingOptions; } diff --git a/products/ASC.Calendar/Server/Models/PublicItemWrapper.cs b/products/ASC.Calendar/Server/Models/PublicItemWrapper.cs index 7da6fef1a6..c0744159c1 100644 --- a/products/ASC.Calendar/Server/Models/PublicItemWrapper.cs +++ b/products/ASC.Calendar/Server/Models/PublicItemWrapper.cs @@ -35,6 +35,7 @@ using ASC.Common; using ASC.Calendar.iCalParser; using ASC.Calendar.BusinessObjects; using System.Text.Json.Serialization; +using System.Net.Http; namespace ASC.Calendar.Models { @@ -84,6 +85,7 @@ namespace ASC.Calendar.Models private TenantManager TenantManager { get; } private TimeZoneConverter TimeZoneConverter { get; } private PermissionContext PermissionContext { get; } + private IHttpClientFactory ClientFactory { get; } public DisplayUserSettingsHelper DisplayUserSettingsHelper { get; } public DataProvider DataProvider { get; } @@ -96,7 +98,8 @@ namespace ASC.Calendar.Models TimeZoneConverter timeZoneConverter, PermissionContext permissionContext, DisplayUserSettingsHelper displayUserSettingsHelper, - DataProvider dataProvider) + DataProvider dataProvider, + IHttpClientFactory clientFactory) { UserManager = userManager; Authentication = authentication; @@ -106,6 +109,7 @@ namespace ASC.Calendar.Models PermissionContext = permissionContext; DisplayUserSettingsHelper = displayUserSettingsHelper; DataProvider = dataProvider; + ClientFactory = clientFactory; } public PublicItemWrapper Get(ASC.Web.Core.Calendars.SharingOptions.PublicItem publicItem, string calendartId, Guid owner) @@ -164,7 +168,7 @@ namespace ASC.Calendar.Models int calId; if (_isCalendar && int.TryParse(_calendarId, out calId)) { - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); var obj = new BusinessObjects.Calendar(AuthContext, TimeZoneConverter, icalendar, DataProvider) { Id = _calendarId }; if (PermissionContext.PermissionResolver.Check(subject, obj, null, CalendarAccessRights.FullAccessAction)) result.SharingOption = AccessOption.FullAccessOption; @@ -173,7 +177,7 @@ namespace ASC.Calendar.Models } else if (!_isCalendar) { - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); var obj = new BusinessObjects.Event(AuthContext, TimeZoneConverter, icalendar, DataProvider) { Id = _eventId, CalendarId = _calendarId }; if (PermissionContext.PermissionResolver.Check(subject, obj, null, CalendarAccessRights.FullAccessAction)) result.SharingOption = AccessOption.FullAccessOption; diff --git a/products/ASC.Calendar/Server/iCalParser/Parser.cs b/products/ASC.Calendar/Server/iCalParser/Parser.cs index 9130e13efc..d8c6b36cb3 100644 --- a/products/ASC.Calendar/Server/iCalParser/Parser.cs +++ b/products/ASC.Calendar/Server/iCalParser/Parser.cs @@ -44,6 +44,7 @@ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ +using System; using System.Collections; using System.IO; using System.Text; @@ -490,7 +491,7 @@ namespace ASC.Calendar.iCalParser } else if (iprop != null && id.TokenVal != TokenValue.Xtension) { - if (iprop.TokenText.ToLowerInvariant() == "uri") + if (iprop.TokenText.Equals("uri", StringComparison.OrdinalIgnoreCase)) { // special case emitter.doURIResource(val); diff --git a/products/ASC.Calendar/Server/iCalParser/Token.cs b/products/ASC.Calendar/Server/iCalParser/Token.cs index d448f30de3..4c09103c10 100644 --- a/products/ASC.Calendar/Server/iCalParser/Token.cs +++ b/products/ASC.Calendar/Server/iCalParser/Token.cs @@ -123,7 +123,7 @@ namespace ASC.Calendar.iCalParser { if (str.Length > 0) { - return CamelCase(str.Substring(0, 1).ToUpper() + str.Substring(1)); + return CamelCase(str[0].ToString().ToUpper() + str.Substring(1)); } else { @@ -139,7 +139,9 @@ namespace ASC.Calendar.iCalParser for (int i = 0; i < lstr.Length; ++i) { - if (lstr[i] == '-') + var c = lstr[i]; + + if (c == '-') { upper = true; } @@ -147,12 +149,12 @@ namespace ASC.Calendar.iCalParser { if (upper) { - buff.Append(Char.ToUpper(lstr[i])); + buff.Append(Char.ToUpper(c)); upper = false; } else { - buff.Append(lstr[i]); + buff.Append(c); } } } @@ -179,8 +181,8 @@ namespace ASC.Calendar.iCalParser - isUTC= icalDate.ToLowerInvariant().EndsWith("z"); - isDate = !icalDate.ToLowerInvariant().Contains("t"); + isUTC= icalDate.EndsWith("z", StringComparison.OrdinalIgnoreCase); + isDate = icalDate.IndexOf("t", StringComparison.OrdinalIgnoreCase) == -1; DateTime dateTime ; diff --git a/products/ASC.Calendar/Server/iCalParser/iCalendar.cs b/products/ASC.Calendar/Server/iCalParser/iCalendar.cs index d15296ce43..c2e429b103 100644 --- a/products/ASC.Calendar/Server/iCalParser/iCalendar.cs +++ b/products/ASC.Calendar/Server/iCalParser/iCalendar.cs @@ -41,10 +41,11 @@ namespace ASC.Calendar.iCalParser public class iCalendar : BaseCalendar { private TenantManager TenantManager { get; } + private IHttpClientFactory ClientFactory { get; } public iCalendar GetFromStream(TextReader reader) { - var emitter = new iCalendarEmitter(AuthContext, TimeZoneConverter, TenantManager); + var emitter = new iCalendarEmitter(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); var parser = new Parser(reader, emitter); parser.Parse(); return emitter.GetCalendar(); @@ -57,7 +58,7 @@ namespace ASC.Calendar.iCalParser public iCalendar GetFromUrl(string url, string calendarId) { - var cache = new iCalendarCache(AuthContext, TimeZoneConverter, TenantManager); + var cache = new iCalendarCache(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); iCalendar calendar = null; if (calendarId != null) calendar = cache.GetCalendarFromCache(calendarId); @@ -72,7 +73,7 @@ namespace ASC.Calendar.iCalParser var request = new HttpRequestMessage(); request.RequestUri = new Uri(url); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using (var response = httpClient.Send(request)) using (var stream = response.Content.ReadAsStream()) { @@ -107,10 +108,12 @@ namespace ASC.Calendar.iCalParser public iCalendar( AuthContext authContext, TimeZoneConverter timeZoneConverter, - TenantManager tenantManager) + TenantManager tenantManager, + IHttpClientFactory clientFactory) : base(authContext, timeZoneConverter) { - TenantManager = tenantManager; + TenantManager = tenantManager; + ClientFactory = clientFactory; this.Context.CanChangeAlertType = false; this.Context.CanChangeTimeZone = false; this.Context.GetGroupMethod = delegate () { return Resources.CalendarApiResource.iCalCalendarsGroup; }; diff --git a/products/ASC.Calendar/Server/iCalParser/iCalendarCache.cs b/products/ASC.Calendar/Server/iCalParser/iCalendarCache.cs index 94f8b9bbc3..9e1bbd389c 100644 --- a/products/ASC.Calendar/Server/iCalParser/iCalendarCache.cs +++ b/products/ASC.Calendar/Server/iCalParser/iCalendarCache.cs @@ -28,6 +28,7 @@ using System; using System.IO; using ASC.Core; using ASC.Common.Utils; +using System.Net.Http; namespace ASC.Calendar.iCalParser { @@ -58,21 +59,25 @@ namespace ASC.Calendar.iCalParser public AuthContext AuthContext { get; } public TimeZoneConverter TimeZoneConverter { get; } public TenantManager TenantManager { get; } + public IHttpClientFactory ClientFactory { get; } public iCalendarCache( AuthContext authContext, TimeZoneConverter timeZoneConverter, - TenantManager tenantManager - ) : this(authContext, timeZoneConverter, tenantManager, iCalendarCacheParams.Default){} + TenantManager tenantManager, + IHttpClientFactory clientFactory + ) : this(authContext, timeZoneConverter, tenantManager, clientFactory, iCalendarCacheParams.Default){} public iCalendarCache( AuthContext authContext, TimeZoneConverter timeZoneConverter, TenantManager tenantManager, + IHttpClientFactory clientFactory, iCalendarCacheParams cacheParams) { AuthContext = authContext; TimeZoneConverter = timeZoneConverter; TenantManager = tenantManager; + ClientFactory = clientFactory; _cacheParams = cacheParams; } @@ -120,7 +125,7 @@ namespace ASC.Calendar.iCalParser using (var tr = new StreamReader(File.OpenRead(filePath))) { - var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + var icalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); return icalendar.GetFromStream(tr); } } diff --git a/products/ASC.Calendar/Server/iCalParser/iCalendarEmitter.cs b/products/ASC.Calendar/Server/iCalParser/iCalendarEmitter.cs index b16d11f30b..bb5fe3bcb7 100644 --- a/products/ASC.Calendar/Server/iCalParser/iCalendarEmitter.cs +++ b/products/ASC.Calendar/Server/iCalParser/iCalendarEmitter.cs @@ -27,9 +27,11 @@ using System; using System.Collections.Generic; using System.Linq; +using System.Net.Http; + using ASC.Common.Utils; -using ASC.Web.Core.Calendars; using ASC.Core; +using ASC.Web.Core.Calendars; namespace ASC.Calendar.iCalParser { @@ -38,7 +40,7 @@ namespace ASC.Calendar.iCalParser private iCalendar _curCalendar; private iCalEvent _curEvent; - private Stack<Token> _component= new Stack<Token>(); + private Stack<Token> _component = new Stack<Token>(); private Token _curPropToken = null; public Parser VParser { get; set; } @@ -46,14 +48,17 @@ namespace ASC.Calendar.iCalParser private AuthContext AuthContext { get; } private TimeZoneConverter TimeZoneConverter { get; } private TenantManager TenantManager { get; } + private IHttpClientFactory ClientFactory { get; } public iCalendarEmitter( AuthContext authContext, TimeZoneConverter timeZoneConverter, - TenantManager tenantManager) + TenantManager tenantManager, + IHttpClientFactory clientFactory) { AuthContext = authContext; TimeZoneConverter = timeZoneConverter; TenantManager = tenantManager; + ClientFactory = clientFactory; } public iCalendar GetCalendar() { @@ -61,12 +66,12 @@ namespace ASC.Calendar.iCalParser } - public void doIntro(){} + public void doIntro() { } public void doOutro() { } - public void doComponent() { } - + public void doComponent() { } + public void doResource(Token t) { } public void emit(string val) { } @@ -81,44 +86,44 @@ namespace ASC.Calendar.iCalParser } public void doBegin(Token t) - { + { } - public void doEndComponent() + public void doEndComponent() { _component.Pop(); } public void doComponentBegin(Token t) - { + { _component.Push(t); switch (t.TokenVal) { - case TokenValue.Tvcalendar: - _curCalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager); + case TokenValue.Tvcalendar: + _curCalendar = new iCalendar(AuthContext, TimeZoneConverter, TenantManager, ClientFactory); break; case TokenValue.Tvevent: - case TokenValue.Tvjournal: + case TokenValue.Tvjournal: _curEvent = new iCalEvent(); _curCalendar.Events.Add(_curEvent); _curEvent.CalendarId = _curCalendar.Id; break; } - } - + } + public void doID(Token t) { - _curPropToken = t; + _curPropToken = t; } public void doSymbolic(Token t) - { + { } public void doURIResource(Token t) - { + { } public void doMailto(Token t) @@ -131,12 +136,12 @@ namespace ASC.Calendar.iCalParser bool isAllDay = true; bool isUTC = true; - if (_curPropToken.TokenVal == TokenValue.Tdtstart + if (_curPropToken.TokenVal == TokenValue.Tdtstart || _curPropToken.TokenVal == TokenValue.Tdtend || _curPropToken.TokenVal == TokenValue.Texdate) { - if (iprop != null && iprop.TokenText.ToLowerInvariant() == "date") + if (iprop != null && iprop.TokenText.Equals("date", StringComparison.OrdinalIgnoreCase)) dateTime = Token.ParseDate(t.TokenText); else @@ -182,7 +187,7 @@ namespace ASC.Calendar.iCalParser } public void doIprop(Token t, Token iprop) - { + { } public void doRest(Token t, Token id) @@ -204,8 +209,8 @@ namespace ASC.Calendar.iCalParser case "x:wrtimezone": _curCalendar.xTimeZone = t.TokenText; - break; - + break; + case "x:wrcalname": _curCalendar.Name = t.TokenText; break; @@ -262,7 +267,7 @@ namespace ASC.Calendar.iCalParser //event rrule if (_curPropToken.TokenVal == TokenValue.Trrule && _component.Peek().TokenVal == TokenValue.Tvevent) { - switch(key.TokenText.ToLowerInvariant()) + switch (key.TokenText.ToLowerInvariant()) { case "freq": _curEvent.RecurrenceRule.Freq = RecurrenceRule.ParseFrequency(val.TokenText); @@ -286,7 +291,7 @@ namespace ASC.Calendar.iCalParser break; case "byminute": - _curEvent.RecurrenceRule.ByMinute= val.TokenText.Split(',').Select(v => Convert.ToInt32(v)).ToArray(); + _curEvent.RecurrenceRule.ByMinute = val.TokenText.Split(',').Select(v => Convert.ToInt32(v)).ToArray(); break; case "byhour": @@ -294,7 +299,7 @@ namespace ASC.Calendar.iCalParser break; case "byday": - _curEvent.RecurrenceRule.ByDay = val.TokenText.Split(',').Select(v => RecurrenceRule.WeekDay.Parse(v)).ToArray(); + _curEvent.RecurrenceRule.ByDay = val.TokenText.Split(',').Select(v => RecurrenceRule.WeekDay.ParseWeekDay(v)).ToArray(); break; case "bymonthday": @@ -314,11 +319,11 @@ namespace ASC.Calendar.iCalParser break; case "bysetpos": - _curEvent.RecurrenceRule.BySetPos= val.TokenText.Split(',').Select(v => Convert.ToInt32(v)).ToArray(); + _curEvent.RecurrenceRule.BySetPos = val.TokenText.Split(',').Select(v => Convert.ToInt32(v)).ToArray(); break; case "wkst": - _curEvent.RecurrenceRule.WKST = RecurrenceRule.WeekDay.Parse(val.TokenText); + _curEvent.RecurrenceRule.WKST = RecurrenceRule.WeekDay.ParseWeekDay(val.TokenText); break; } } diff --git a/products/ASC.Files/Core/Configuration/FilesSpaceUsageStatManager.cs b/products/ASC.Files/Core/Configuration/FilesSpaceUsageStatManager.cs index 8a357e95d5..ef33da3615 100644 --- a/products/ASC.Files/Core/Configuration/FilesSpaceUsageStatManager.cs +++ b/products/ASC.Files/Core/Configuration/FilesSpaceUsageStatManager.cs @@ -83,7 +83,7 @@ namespace ASC.Web.Files .Join(FilesDbContext.BunchObjects, a => a.tree.ParentId.ToString(), b => b.LeftNode, (fileTree, bunch) => new { fileTree.file, fileTree.tree, bunch }) .Where(r => r.file.TenantId == r.bunch.TenantId) .Where(r => r.file.TenantId == TenantManager.GetCurrentTenant().TenantId) - .Where(r => r.bunch.RightNode.StartsWith("files/my/") | r.bunch.RightNode.StartsWith("files/trash/")) + .Where(r => r.bunch.RightNode.StartsWith("files/my/") || r.bunch.RightNode.StartsWith("files/trash/")) .GroupBy(r => r.file.CreateBy) .Select(r => new { CreateBy = r.Key, Size = r.Sum(a => a.file.ContentLength) }); diff --git a/products/ASC.Files/Core/Core/Compress/CompressToArchive.cs b/products/ASC.Files/Core/Core/Compress/CompressToArchive.cs index 9627dc9c8f..942f4b3015 100644 --- a/products/ASC.Files/Core/Core/Compress/CompressToArchive.cs +++ b/products/ASC.Files/Core/Core/Compress/CompressToArchive.cs @@ -33,8 +33,8 @@ namespace ASC.Web.Files.Core.Compress { private readonly ICompress compress; - internal static string TarExt = ".tar.gz"; - internal static string ZipExt = ".zip"; + internal static readonly string TarExt = ".tar.gz"; + internal static readonly string ZipExt = ".zip"; private static List<string> Exts = new List<string>(2) { TarExt, ZipExt }; public CompressToArchive(FilesSettingsHelper filesSettings, CompressToTarGz compressToTarGz, CompressToZip compressToZip) diff --git a/products/ASC.Files/Core/Core/Dao/TeamlabDao/AbstractDao.cs b/products/ASC.Files/Core/Core/Dao/TeamlabDao/AbstractDao.cs index b23cac0dbf..00da0da380 100644 --- a/products/ASC.Files/Core/Core/Dao/TeamlabDao/AbstractDao.cs +++ b/products/ASC.Files/Core/Core/Dao/TeamlabDao/AbstractDao.cs @@ -53,7 +53,13 @@ namespace ASC.Files.Core.Data private Lazy<EF.FilesDbContext> LazyFilesDbContext { get; } public EF.FilesDbContext FilesDbContext { get => LazyFilesDbContext.Value; } private int tenantID; - protected internal int TenantID { get => tenantID != 0 ? tenantID : (tenantID = TenantManager.GetCurrentTenant().TenantId); } + protected internal int TenantID { + get + { + if (tenantID == 0) tenantID = TenantManager.GetCurrentTenant().TenantId; + return tenantID; + } + } protected UserManager UserManager { get; } protected TenantManager TenantManager { get; } protected TenantUtil TenantUtil { get; } diff --git a/products/ASC.Files/Core/Core/Dao/TeamlabDao/DaoFactory.cs b/products/ASC.Files/Core/Core/Dao/TeamlabDao/DaoFactory.cs index b89b74b5b7..d68b9557fa 100644 --- a/products/ASC.Files/Core/Core/Dao/TeamlabDao/DaoFactory.cs +++ b/products/ASC.Files/Core/Core/Dao/TeamlabDao/DaoFactory.cs @@ -72,7 +72,7 @@ namespace ASC.Files.Core.Data } } - public class DaoFactoryExtension + public static class DaoFactoryExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Core/Dao/TeamlabDao/FileDao.cs b/products/ASC.Files/Core/Core/Dao/TeamlabDao/FileDao.cs index 7c98500d73..96730f23db 100644 --- a/products/ASC.Files/Core/Core/Dao/TeamlabDao/FileDao.cs +++ b/products/ASC.Files/Core/Core/Dao/TeamlabDao/FileDao.cs @@ -149,7 +149,7 @@ namespace ASC.Files.Core.Data { if (string.IsNullOrEmpty(title)) throw new ArgumentNullException(title); - var query = GetFileQuery(r => r.Title == title && r.CurrentVersion == true && r.FolderId == parentId) + var query = GetFileQuery(r => r.Title == title && r.CurrentVersion && r.FolderId == parentId) .AsNoTracking() .OrderBy(r => r.CreateOn); @@ -352,9 +352,9 @@ namespace ASC.Files.Core.Data { return GetFileStream(file, 0); } - public async Task<Stream> GetFileStreamAsync(File<int> file) + public Task<Stream> GetFileStreamAsync(File<int> file) { - return await GlobalStore.GetStore().GetReadStreamAsync(string.Empty, GetUniqFilePath(file), 0); + return GlobalStore.GetStore().GetReadStreamAsync(string.Empty, GetUniqFilePath(file), 0); } public File<int> SaveFile(File<int> file, Stream fileStream) @@ -366,7 +366,7 @@ namespace ASC.Files.Core.Data { if (file == null) { - throw new ArgumentNullException("file"); + throw new ArgumentNullException(nameof(file)); } var maxChunkedUploadSize = SetupInfo.MaxChunkedUploadSize(TenantExtra, TenantStatisticProvider); @@ -455,7 +455,7 @@ namespace ASC.Files.Core.Data parentFoldersIds = parentFolders.Select(r => r.ParentId).ToList(); - if (parentFoldersIds.Any()) + if (parentFoldersIds.Count > 0) { var folderToUpdate = FilesDbContext.Folders .Where(r => parentFoldersIds.Contains(r.Id)); @@ -512,7 +512,7 @@ namespace ASC.Files.Core.Data public File<int> ReplaceFileVersion(File<int> file, Stream fileStream) { - if (file == null) throw new ArgumentNullException("file"); + if (file == null) throw new ArgumentNullException(nameof(file)); if (file.ID == default) throw new ArgumentException("No file id or folder id toFolderId determine provider"); var maxChunkedUploadSize = SetupInfo.MaxChunkedUploadSize(TenantExtra, TenantStatisticProvider); @@ -579,7 +579,7 @@ namespace ASC.Files.Core.Data parentFoldersIds = parentFolders.Select(r => r.ParentId).ToList(); - if (parentFoldersIds.Any()) + if (parentFoldersIds.Count > 0) { var folderToUpdate = FilesDbContext.Folders .Where(r => parentFoldersIds.Contains(r.Id)); @@ -666,6 +666,9 @@ namespace ASC.Files.Core.Data .Distinct() .ToList(); + var toDeleteLinks = Query(FilesDbContext.TagLink).Where(r => r.EntryId == fileId.ToString() && r.EntryType == FileEntryType.File); + FilesDbContext.RemoveRange(toDeleteLinks); + var toDeleteFiles = Query(FilesDbContext.Files).Where(r => r.Id == fileId); FilesDbContext.RemoveRange(toDeleteFiles); @@ -674,7 +677,6 @@ namespace ASC.Files.Core.Data FactoryIndexer.DeleteAsync(d); } - var toDeleteLinks = Query(FilesDbContext.TagLink).Where(r => r.EntryId == fileId.ToString() && r.EntryType == FileEntryType.File); FilesDbContext.RemoveRange(toDeleteFiles); var tagsToRemove = Query(FilesDbContext.Tag) @@ -691,7 +693,10 @@ namespace ASC.Files.Core.Data tx.Commit(); - fromFolders.ForEach(folderId => RecalculateFilesCount(folderId)); + foreach (var folderId in fromFolders) + { + RecalculateFilesCount(folderId); + } if (deleteFolder) DeleteFolder(fileId); @@ -768,7 +773,10 @@ namespace ASC.Files.Core.Data FilesDbContext.SaveChanges(); tx.Commit(); - fromFolders.ForEach(folderId => RecalculateFilesCount(folderId)); + foreach (var folderId in fromFolders) + { + RecalculateFilesCount(folderId); + } RecalculateFilesCount(toFolderId); } @@ -945,7 +953,7 @@ namespace ASC.Files.Core.Data public string GetUniqFileDirectory(int fileId) { if (fileId == 0) throw new ArgumentNullException("fileIdObject"); - return string.Format("folder_{0}/file_{1}", (Convert.ToInt32(fileId) / 1000 + 1) * 1000, fileId); + return string.Format("folder_{0}/file_{1}", (fileId / 1000 + 1) * 1000, fileId); } public string GetUniqFilePath(File<int> file) @@ -958,7 +966,7 @@ namespace ASC.Files.Core.Data public string GetUniqFilePath(File<int> file, string fileTitle) { return file != null - ? string.Format("{0}/{1}", GetUniqFileVersionPath(file.ID, file.Version), fileTitle) + ? $"{GetUniqFileVersionPath(file.ID, file.Version)}/{fileTitle}" : null; } @@ -1120,7 +1128,7 @@ namespace ASC.Files.Core.Data return FromQueryWithShared(q).Select(ToFile).ToList(); } - public IEnumerable<File<int>> Search(string searchText, bool bunch) + public IEnumerable<File<int>> Search(string searchText, bool bunch = false) { if (FactoryIndexer.TrySelectIds(s => s.MatchAll(searchText), out var ids)) { @@ -1155,18 +1163,18 @@ namespace ASC.Files.Core.Data return GlobalStore.GetStore().IsFile(GetUniqFilePath(file)); } - public async Task<bool> IsExistOnStorageAsync(File<int> file) + public Task<bool> IsExistOnStorageAsync(File<int> file) { - return await GlobalStore.GetStore().IsFileAsync(string.Empty, GetUniqFilePath(file)); + return GlobalStore.GetStore().IsFileAsync(string.Empty, GetUniqFilePath(file)); } private const string DiffTitle = "diff.zip"; public void SaveEditHistory(File<int> file, string changes, Stream differenceStream) { - if (file == null) throw new ArgumentNullException("file"); - if (string.IsNullOrEmpty(changes)) throw new ArgumentNullException("changes"); - if (differenceStream == null) throw new ArgumentNullException("differenceStream"); + if (file == null) throw new ArgumentNullException(nameof(file)); + if (string.IsNullOrEmpty(changes)) throw new ArgumentNullException(nameof(changes)); + if (differenceStream == null) throw new ArgumentNullException(nameof(differenceStream)); changes = changes.Trim(); @@ -1258,14 +1266,14 @@ namespace ASC.Files.Core.Data var q1 = FilesDbContext.Files .Where(r => r.ModifiedOn > fromTime) .GroupBy(r => r.TenantId) - .Where(r => r.Count() > 0) + .Where(r => r.Any()) .Select(r => r.Key) .ToList(); var q2 = FilesDbContext.Security .Where(r => r.TimeStamp > fromTime) .GroupBy(r => r.TenantId) - .Where(r => r.Count() > 0) + .Where(r => r.Any()) .Select(r => r.Key) .ToList(); @@ -1276,7 +1284,7 @@ namespace ASC.Files.Core.Data public void SaveThumbnail(File<int> file, Stream thumbnail) { - if (file == null) throw new ArgumentNullException("file"); + if (file == null) throw new ArgumentNullException(nameof(file)); var toUpdate = FilesDbContext.Files .FirstOrDefault(r => r.Id == file.ID && r.Version == file.Version && r.TenantId == TenantID); @@ -1514,7 +1522,7 @@ namespace ASC.Files.Core.Data return dbFile; } - internal protected async Task<DbFile> InitDocumentAsync(DbFile dbFile) + internal protected Task<DbFile> InitDocumentAsync(DbFile dbFile) { if (!FactoryIndexer.CanIndexByContent(dbFile)) { @@ -1522,9 +1530,14 @@ namespace ASC.Files.Core.Data { Data = Convert.ToBase64String(Encoding.UTF8.GetBytes("")) }; - return dbFile; + return Task.FromResult(dbFile); } + return InernalInitDocumentAsync(dbFile); + } + + private async Task<DbFile> InernalInitDocumentAsync(DbFile dbFile) + { var file = ServiceProvider.GetService<File<int>>(); file.ID = dbFile.Id; file.Title = dbFile.Title; diff --git a/products/ASC.Files/Core/Core/Dao/TeamlabDao/FolderDao.cs b/products/ASC.Files/Core/Core/Dao/TeamlabDao/FolderDao.cs index b09e471904..21ed0070a4 100644 --- a/products/ASC.Files/Core/Core/Dao/TeamlabDao/FolderDao.cs +++ b/products/ASC.Files/Core/Core/Dao/TeamlabDao/FolderDao.cs @@ -295,7 +295,7 @@ namespace ASC.Files.Core.Data public int SaveFolder(Folder<int> folder, IDbContextTransaction transaction) { - if (folder == null) throw new ArgumentNullException("folder"); + if (folder == null) throw new ArgumentNullException(nameof(folder)); folder.Title = Global.ReplaceInvalidCharsAndTruncate(folder.Title); @@ -484,7 +484,7 @@ namespace ASC.Files.Core.Data var folder = GetFolder(folderId); if (folder.FolderType != FolderType.DEFAULT) - throw new ArgumentException("It is forbidden to move the System folder.", "folderId"); + throw new ArgumentException("It is forbidden to move the System folder.", nameof(folderId)); var recalcFolders = new List<int> { toFolderId }; var parent = FilesDbContext.Folders @@ -655,14 +655,17 @@ namespace ASC.Files.Core.Data if (conflict != 0) { - FilesDbContext.Files + var files = FilesDbContext.Files .AsNoTracking() .Join(FilesDbContext.Files, f1 => f1.Title.ToLower(), f2 => f2.Title.ToLower(), (f1, f2) => new { f1, f2 }) .Where(r => r.f1.TenantId == TenantID && r.f1.CurrentVersion && r.f1.FolderId == folderId) .Where(r => r.f2.TenantId == TenantID && r.f2.CurrentVersion && r.f2.FolderId == conflict) - .Select(r => r.f1) - .ToList() - .ForEach(r => result[r.Id] = r.Title); + .Select(r => r.f1); + + foreach (var file in files) + { + result[file.Id] = file.Title; + } var childs = Query(FilesDbContext.Folders) .AsNoTracking() @@ -753,7 +756,7 @@ namespace ASC.Files.Core.Data return true; } - public long GetMaxUploadSize(int folderId, bool chunkedUpload) + public long GetMaxUploadSize(int folderId, bool chunkedUpload = false) { var tmp = long.MaxValue; @@ -796,7 +799,7 @@ namespace ASC.Files.Core.Data } - public IEnumerable<Folder<int>> SearchFolders(string text, bool bunch) + public IEnumerable<Folder<int>> SearchFolders(string text, bool bunch = false) { return Search(text).Where(f => bunch ? f.RootFolderType == FolderType.BUNCH @@ -819,10 +822,10 @@ namespace ASC.Files.Core.Data public IEnumerable<int> GetFolderIDs(string module, string bunch, IEnumerable<string> data, bool createIfNotExists) { - if (string.IsNullOrEmpty(module)) throw new ArgumentNullException("module"); - if (string.IsNullOrEmpty(bunch)) throw new ArgumentNullException("bunch"); + if (string.IsNullOrEmpty(module)) throw new ArgumentNullException(nameof(module)); + if (string.IsNullOrEmpty(bunch)) throw new ArgumentNullException(nameof(bunch)); - var keys = data.Select(id => string.Format("{0}/{1}/{2}", module, bunch, id)).ToArray(); + var keys = data.Select(id => $"{module}/{bunch}/{id}").ToArray(); var folderIdsDictionary = Query(FilesDbContext.BunchObjects) .AsNoTracking() @@ -903,10 +906,10 @@ namespace ASC.Files.Core.Data public int GetFolderID(string module, string bunch, string data, bool createIfNotExists) { - if (string.IsNullOrEmpty(module)) throw new ArgumentNullException("module"); - if (string.IsNullOrEmpty(bunch)) throw new ArgumentNullException("bunch"); + if (string.IsNullOrEmpty(module)) throw new ArgumentNullException(nameof(module)); + if (string.IsNullOrEmpty(bunch)) throw new ArgumentNullException(nameof(bunch)); - var key = string.Format("{0}/{1}/{2}", module, bunch, data); + var key = $"{module}/{bunch}/{data}"; var folderId = Query(FilesDbContext.BunchObjects) .Where(r => r.RightNode == key) .Select(r => r.LeftNode) @@ -927,7 +930,7 @@ namespace ASC.Files.Core.Data case my: folder.FolderType = FolderType.USER; folder.Title = my; - folder.CreateBy = new Guid(data.ToString()); + folder.CreateBy = new Guid(data); break; case common: folder.FolderType = FolderType.COMMON; @@ -936,7 +939,7 @@ namespace ASC.Files.Core.Data case trash: folder.FolderType = FolderType.TRASH; folder.Title = trash; - folder.CreateBy = new Guid(data.ToString()); + folder.CreateBy = new Guid(data); break; case share: folder.FolderType = FolderType.SHARE; @@ -1171,7 +1174,7 @@ namespace ASC.Files.Core.Data public string GetBunchObjectID(int folderID) { return Query(FilesDbContext.BunchObjects) - .Where(r => r.LeftNode == (folderID).ToString()) + .Where(r => r.LeftNode == folderID.ToString()) .Select(r => r.RightNode) .FirstOrDefault(); } @@ -1214,14 +1217,14 @@ namespace ASC.Files.Core.Data var q1 = FilesDbContext.Files .Where(r => r.ModifiedOn > fromTime) .GroupBy(r => r.TenantId) - .Where(r => r.Count() > 0) + .Where(r => r.Any()) .Select(r => r.Key) .ToList(); var q2 = FilesDbContext.Security .Where(r => r.TimeStamp > fromTime) .GroupBy(r => r.TenantId) - .Where(r => r.Count() > 0) + .Where(r => r.Any()) .Select(r => r.Key) .ToList(); diff --git a/products/ASC.Files/Core/Core/Dao/TeamlabDao/SecurityDao.cs b/products/ASC.Files/Core/Core/Dao/TeamlabDao/SecurityDao.cs index 91df0f2dd1..2945cf4f03 100644 --- a/products/ASC.Files/Core/Core/Dao/TeamlabDao/SecurityDao.cs +++ b/products/ASC.Files/Core/Core/Dao/TeamlabDao/SecurityDao.cs @@ -215,7 +215,7 @@ namespace ASC.Files.Core.Data var q = GetQuery(r => folders.Contains(r.EntryId) && r.EntryType == FileEntryType.Folder); - if (files.Any()) + if (files.Count > 0) { q = q.Union(GetQuery(r => files.Contains(r.EntryId) && r.EntryType == FileEntryType.File)); } diff --git a/products/ASC.Files/Core/Core/Dao/TeamlabDao/TagDao.cs b/products/ASC.Files/Core/Core/Dao/TeamlabDao/TagDao.cs index cdc6eaea1c..c3f0b963b6 100644 --- a/products/ASC.Files/Core/Core/Dao/TeamlabDao/TagDao.cs +++ b/products/ASC.Files/Core/Core/Dao/TeamlabDao/TagDao.cs @@ -175,7 +175,7 @@ namespace ASC.Files.Core.Data public IEnumerable<Tag> GetTags(string[] names, TagType tagType) { - if (names == null) throw new ArgumentNullException("names"); + if (names == null) throw new ArgumentNullException(nameof(names)); var q = Query(FilesDbContext.Tag) .Join(FilesDbContext.TagLink, r => r.Id, l => l.TagId, (tag, link) => new TagLinkData { Tag = tag, Link = link }) @@ -189,7 +189,7 @@ namespace ASC.Files.Core.Data public IEnumerable<Tag> GetTags(string name, TagType tagType) { - if (string.IsNullOrEmpty(name)) throw new ArgumentNullException("name"); + if (string.IsNullOrEmpty(name)) throw new ArgumentNullException(nameof(name)); return GetTags(new[] { name }, tagType); } @@ -441,8 +441,8 @@ namespace ASC.Files.Core.Data FilesDbContext.TagLink.RemoveRange(toDelete); FilesDbContext.SaveChanges(); - var count = Query(FilesDbContext.TagLink).Count(r => r.TagId == id); - if (count == 0) + var any = Query(FilesDbContext.TagLink).Any(r => r.TagId == id); + if (!any) { var tagToDelete = Query(FilesDbContext.Tag).Where(r => r.Id == id); FilesDbContext.Tag.RemoveRange(tagToDelete); @@ -479,7 +479,7 @@ namespace ASC.Files.Core.Data entryTypes.Add((int)entryType); } - if (entryIds.Any()) + if (entryIds.Count > 0) { var sqlQuery = Query(FilesDbContext.Tag) .Join(FilesDbContext.TagLink, r => r.Id, l => l.TagId, (tag, link) => new TagLinkData { Tag = tag, Link = link }) @@ -751,7 +751,7 @@ namespace ASC.Files.Core.Data .Concat(folderIds.ConvertAll(r => $"onedrive-{r}")) .ToList(); - if (thirdpartyFolderIds.Any()) + if (thirdpartyFolderIds.Count > 0) { result.AddRange(FromQuery(newTagsForSBoxQuery(FilesDbContext, tenantId, subject, thirdpartyFolderIds))); } diff --git a/products/ASC.Files/Core/Core/Entries/ChunkedUploadSession.cs b/products/ASC.Files/Core/Core/Entries/ChunkedUploadSession.cs index 12d60adc64..dbf971f48f 100644 --- a/products/ASC.Files/Core/Core/Entries/ChunkedUploadSession.cs +++ b/products/ASC.Files/Core/Core/Entries/ChunkedUploadSession.cs @@ -76,7 +76,7 @@ namespace ASC.Files.Core public static ChunkedUploadSession<T> Deserialize(Stream stream, FileHelper fileHelper) { - var chunkedUploadSession = JsonSerializer.DeserializeAsync<ChunkedUploadSession<T>>(stream).Result; + var chunkedUploadSession = JsonSerializer.Deserialize<ChunkedUploadSession<T>>(stream); chunkedUploadSession.File.FileHelper = fileHelper; chunkedUploadSession.TransformItems(); return chunkedUploadSession; diff --git a/products/ASC.Files/Core/Core/Entries/EncryptionKeyPair.cs b/products/ASC.Files/Core/Core/Entries/EncryptionKeyPair.cs index 3cf65ce08e..70aefb7bf8 100644 --- a/products/ASC.Files/Core/Core/Entries/EncryptionKeyPair.cs +++ b/products/ASC.Files/Core/Core/Entries/EncryptionKeyPair.cs @@ -72,8 +72,8 @@ namespace ASC.Web.Files.Core.Entries public void SetKeyPair(string publicKey, string privateKeyEnc) { - if (string.IsNullOrEmpty(publicKey)) throw new ArgumentNullException("publicKey"); - if (string.IsNullOrEmpty(privateKeyEnc)) throw new ArgumentNullException("privateKeyEnc"); + if (string.IsNullOrEmpty(publicKey)) throw new ArgumentNullException(nameof(publicKey)); + if (string.IsNullOrEmpty(privateKeyEnc)) throw new ArgumentNullException(nameof(privateKeyEnc)); var user = UserManager.GetUsers(AuthContext.CurrentAccount.ID); if (!AuthContext.IsAuthenticated || user.IsVisitor(UserManager)) throw new System.Security.SecurityException(); diff --git a/products/ASC.Files/Core/Core/Entries/File.cs b/products/ASC.Files/Core/Core/Entries/File.cs index 8a8584ff7a..a6ad9fb6e1 100644 --- a/products/ASC.Files/Core/Core/Entries/File.cs +++ b/products/ASC.Files/Core/Core/Entries/File.cs @@ -26,10 +26,11 @@ using System; using System.Diagnostics; -using System.Text.Json.Serialization; - +using System.Text.Json.Serialization; + using ASC.Common; using ASC.Web.Core.Files; +using ASC.Web.Files.Classes; using ASC.Web.Studio.Core; namespace ASC.Files.Core @@ -51,28 +52,29 @@ namespace ASC.Files.Core IsFavorite = 0x20, - IsTemplate = 0x40, - + IsTemplate = 0x40, + IsFillFormDraft = 0x80 } - + [Transient] [Serializable] [DebuggerDisplay("{Title} ({ID} v{Version})")] public class File<T> : FileEntry<T>, IFileEntry<T> - { - private FileStatus _status; - - public File() - { - Version = 1; - VersionGroup = 1; - FileEntryType = FileEntryType.File; - } - - public File(FileHelper fileHelper) : this() - { - FileHelper = fileHelper; + { + private FileStatus _status; + + public File() + { + Version = 1; + VersionGroup = 1; + FileEntryType = FileEntryType.File; + } + + public File(FileHelper fileHelper, Global global): this() + { + FileHelper = fileHelper; + Global = global; } public int Version { get; set; } @@ -88,13 +90,13 @@ namespace ASC.Files.Core } public long ContentLength { get; set; } - + [JsonIgnore] public string ContentLengthString { get { return FileSizeComment.FilesSizeToString(ContentLength); } } - + [JsonIgnore] public FilterType FilterType { @@ -119,30 +121,30 @@ namespace ASC.Files.Core return FilterType.None; } - } - + } + public FileStatus FileStatus { get => FileHelper.GetFileStatus(this, ref _status); - set => _status = value; - } - + set => _status = value; + } + public override string UniqID { get { return $"file_{ID}"; } - } - - [JsonIgnore] - public override string Title { get => FileHelper.GetTitle(this); } - + } [JsonIgnore] - public string DownloadUrl { get => FileHelper.GetDownloadUrl(this); } + public override string Title { get => FileHelper.GetTitle(this); } + + + [JsonIgnore] + public string DownloadUrl { get => FileHelper.GetDownloadUrl(this); } public bool Locked { get; set; } public string LockedBy { get; set; } - + [JsonIgnore] public override bool IsNew { @@ -154,54 +156,54 @@ namespace ASC.Files.Core else _status &= ~FileStatus.IsNew; } - } - - [JsonIgnore] - public bool IsFavorite - { - get { return (_status & FileStatus.IsFavorite) == FileStatus.IsFavorite; } - set - { - if (value) - _status |= FileStatus.IsFavorite; - else - _status &= ~FileStatus.IsFavorite; - } - } - - [JsonIgnore] - public bool IsTemplate - { - get { return (_status & FileStatus.IsTemplate) == FileStatus.IsTemplate; } - set - { - if (value) - _status |= FileStatus.IsTemplate; - else - _status &= ~FileStatus.IsTemplate; - } - } - - [JsonIgnore] - public bool IsFillFormDraft - { - get { return (_status & FileStatus.IsFillFormDraft) == FileStatus.IsFillFormDraft; } - set - { - if (value) - _status |= FileStatus.IsFillFormDraft; - else - _status &= ~FileStatus.IsFillFormDraft; - } } - public bool Encrypted { get; set; } - - public Thumbnail ThumbnailStatus { get; set; } + + [JsonIgnore] + public bool IsFavorite + { + get { return (_status & FileStatus.IsFavorite) == FileStatus.IsFavorite; } + set + { + if (value) + _status |= FileStatus.IsFavorite; + else + _status &= ~FileStatus.IsFavorite; + } + } + + [JsonIgnore] + public bool IsTemplate + { + get { return (_status & FileStatus.IsTemplate) == FileStatus.IsTemplate; } + set + { + if (value) + _status |= FileStatus.IsTemplate; + else + _status &= ~FileStatus.IsTemplate; + } + } + + [JsonIgnore] + public bool IsFillFormDraft + { + get { return (_status & FileStatus.IsFillFormDraft) == FileStatus.IsFillFormDraft; } + set + { + if (value) + _status |= FileStatus.IsFillFormDraft; + else + _status &= ~FileStatus.IsFillFormDraft; + } + } + public bool Encrypted { get; set; } + + public Thumbnail ThumbnailStatus { get; set; } public ForcesaveType Forcesave { get; set; } public string ConvertedType { get; set; } - + [JsonIgnore] public string ConvertedExtension { @@ -210,17 +212,17 @@ namespace ASC.Files.Core if (string.IsNullOrEmpty(ConvertedType)) return FileUtility.GetFileExtension(Title); var curFileType = FileUtility.GetFileTypeByFileName(Title); - return curFileType switch - { - FileType.Image => ConvertedType.Trim('.') == "zip" ? ".pptt" : ConvertedType, - FileType.Spreadsheet => ConvertedType.Trim('.') != "xlsx" ? ".xlst" : ConvertedType, - FileType.Document => ConvertedType.Trim('.') == "zip" ? ".doct" : ConvertedType, - _ => ConvertedType, - }; + return curFileType switch + { + FileType.Image => ConvertedType.Trim('.') == "zip" ? ".pptt" : ConvertedType, + FileType.Spreadsheet => ConvertedType.Trim('.') != "xlsx" ? ".xlst" : ConvertedType, + FileType.Document => ConvertedType.Trim('.') == "zip" ? ".doct" : ConvertedType, + _ => ConvertedType, + }; } } - public object NativeAccessor { get; set; } + public object NativeAccessor { get; set; } } } \ No newline at end of file diff --git a/products/ASC.Files/Core/Core/Entries/FileEntry.cs b/products/ASC.Files/Core/Core/Entries/FileEntry.cs index 501b358acc..f532d90ea1 100644 --- a/products/ASC.Files/Core/Core/Entries/FileEntry.cs +++ b/products/ASC.Files/Core/Core/Entries/FileEntry.cs @@ -25,46 +25,59 @@ using System; -using System.Text.Json.Serialization; - -using ASC.Files.Core.Security; - +using System.Text.Json.Serialization; + +using ASC.Files.Core.Security; +using ASC.Web.Files.Classes; + namespace ASC.Files.Core { [Serializable] public abstract class FileEntry : ICloneable - { - [JsonIgnore] - public FileHelper FileHelper { get; set; } - - protected FileEntry() - { - - } - - public FileEntry(FileHelper fileHelper) - { - FileHelper = fileHelper; - } + { + [JsonIgnore] + public FileHelper FileHelper { get; set; } + + [JsonIgnore] + public Global Global { get; set; } + + protected FileEntry() + { + + } + + protected FileEntry(FileHelper fileHelper, Global global) + { + FileHelper = fileHelper; + Global = global; + } public virtual string Title { get; set; } - public Guid CreateBy { get; set; } - - [JsonIgnore] - public string CreateByString { get => FileHelper.GetCreateByString(this); } - - public Guid ModifiedBy { get; set; } - - [JsonIgnore] - public string ModifiedByString { get => FileHelper.GetModifiedByString(this); } - + public Guid CreateBy { get; set; } + + [JsonIgnore] + public string CreateByString + { + get => !CreateBy.Equals(Guid.Empty) ? Global.GetUserName(CreateBy) : _createByString; + set => _createByString = value; + } + + public Guid ModifiedBy { get; set; } + + [JsonIgnore] + public string ModifiedByString + { + get => !ModifiedBy.Equals(Guid.Empty) ? Global.GetUserName(ModifiedBy) : _modifiedByString; + set => _modifiedByString = value; + } + [JsonIgnore] public string CreateOnString { get { return CreateOn.Equals(default) ? null : CreateOn.ToString("g"); } } - + [JsonIgnore] public string ModifiedOnString { @@ -79,8 +92,8 @@ namespace ASC.Files.Core public int ProviderId { get; set; } - public string ProviderKey { get; set; } - + public string ProviderKey { get; set; } + [JsonIgnore] public bool ProviderEntry { @@ -97,10 +110,10 @@ namespace ASC.Files.Core public abstract bool IsNew { get; set; } - public FileEntryType FileEntryType; + public FileEntryType FileEntryType { get; set; } - public string _modifiedByString; - public string _createByString; + private string _modifiedByString; + private string _createByString; public override string ToString() { @@ -114,30 +127,30 @@ namespace ASC.Files.Core } - public interface IFileEntry<in T> - { - string UniqID { get; } - } - - - [Serializable] + public interface IFileEntry<in T> + { + string UniqID { get; } + } + + + [Serializable] public abstract class FileEntry<T> : FileEntry, ICloneable, IFileEntry<T> { - public T ID { get; set; } - + public T ID { get; set; } + public T FolderID { get; set; } - private T _folderIdDisplay; - - protected FileEntry() - { - - } - - protected FileEntry(FileHelper fileHelper) : base(fileHelper) - { - } - + private T _folderIdDisplay; + + protected FileEntry() + { + + } + + protected FileEntry(FileHelper fileHelper, Global global) : base(fileHelper, global) + { + } + public T FolderIdDisplay { get @@ -149,8 +162,8 @@ namespace ASC.Files.Core set { _folderIdDisplay = value; } } - public T RootFolderId { get; set; } - + public T RootFolderId { get; set; } + [JsonIgnore] public virtual string UniqID { @@ -162,7 +175,7 @@ namespace ASC.Files.Core return obj is FileEntry<T> f && Equals(f.ID, ID); } - public bool Equals(FileEntry<T> obj) + public virtual bool Equals(FileEntry<T> obj) { return Equals(obj.ID, ID); } diff --git a/products/ASC.Files/Core/Core/Entries/FileHelper.cs b/products/ASC.Files/Core/Core/Entries/FileHelper.cs index 07700232a1..7564bfb884 100644 --- a/products/ASC.Files/Core/Core/Entries/FileHelper.cs +++ b/products/ASC.Files/Core/Core/Entries/FileHelper.cs @@ -23,11 +23,8 @@ * */ -using System; - using ASC.Common; using ASC.Web.Core.Files; -using ASC.Web.Files.Classes; using ASC.Web.Files.Utils; namespace ASC.Files.Core @@ -43,26 +40,13 @@ namespace ASC.Files.Core private FileConverter FileConverter { get; set; } - private Global Global { get; set; } - - public FileHelper(FileTrackerHelper fileTracker, FilesLinkUtility filesLinkUtility, FileUtility fileUtility, FileConverter fileConverter, Global global) + public FileHelper(FileTrackerHelper fileTracker, FilesLinkUtility filesLinkUtility, FileUtility fileUtility, FileConverter fileConverter) { FileTracker = fileTracker; FilesLinkUtility = filesLinkUtility; FileUtility = fileUtility; FileConverter = fileConverter; - Global = global; - } - - internal string GetCreateByString(FileEntry fileEntry) - { - return !fileEntry.CreateBy.Equals(Guid.Empty) ? Global.GetUserName(fileEntry.CreateBy) : fileEntry._createByString; - } - - internal string GetModifiedByString(FileEntry fileEntry) - { - return !fileEntry.ModifiedBy.Equals(Guid.Empty) ? Global.GetUserName(fileEntry.ModifiedBy) : fileEntry._modifiedByString; - } + } internal string GetTitle<T>(File<T> file) { diff --git a/products/ASC.Files/Core/Core/Entries/Folder.cs b/products/ASC.Files/Core/Core/Entries/Folder.cs index 2040de017b..6a68c1b62d 100644 --- a/products/ASC.Files/Core/Core/Entries/Folder.cs +++ b/products/ASC.Files/Core/Core/Entries/Folder.cs @@ -28,6 +28,7 @@ using System; using System.Diagnostics; using ASC.Common; +using ASC.Web.Files.Classes; namespace ASC.Files.Core { @@ -89,9 +90,10 @@ namespace ASC.Files.Core FileEntryType = FileEntryType.Folder; } - public Folder(FileHelper fileHelper) : this() + public Folder(FileHelper fileHelper, Global global) : this() { FileHelper = fileHelper; + Global = global; } public override string UniqID diff --git a/products/ASC.Files/Core/Core/Entries/Tag.cs b/products/ASC.Files/Core/Core/Entries/Tag.cs index 8f4f8668e3..246c824594 100644 --- a/products/ASC.Files/Core/Core/Entries/Tag.cs +++ b/products/ASC.Files/Core/Core/Entries/Tag.cs @@ -42,7 +42,7 @@ namespace ASC.Files.Core [Serializable] [DebuggerDisplay("{TagName} ({Id}) entry {EntryType} ({EntryId})")] - public class Tag + public sealed class Tag { public string TagName { get; set; } diff --git a/products/ASC.Files/Core/Core/FileStorageService.cs b/products/ASC.Files/Core/Core/FileStorageService.cs index d97c7b02dc..79d57f77b5 100644 --- a/products/ASC.Files/Core/Core/FileStorageService.cs +++ b/products/ASC.Files/Core/Core/FileStorageService.cs @@ -45,7 +45,6 @@ using ASC.Core.Common.Configuration; using ASC.Core.Common.Settings; using ASC.Core.Users; using ASC.Data.Storage; -using ASC.ElasticSearch; using ASC.FederatedLogin.LoginProviders; using ASC.Files.Core; using ASC.Files.Core.Resources; @@ -260,7 +259,6 @@ namespace ASC.Web.Files.Services.WCFService var subjectId = string.IsNullOrEmpty(ssubject) ? Guid.Empty : new Guid(ssubject); var folderDao = GetFolderDao(); - var fileDao = GetFileDao(); Folder<T> parent = null; try @@ -310,7 +308,7 @@ namespace ASC.Web.Files.Services.WCFService var breadCrumbs = EntryManager.GetBreadCrumbs(parentId, folderDao); - var prevVisible = breadCrumbs.ElementAtOrDefault(breadCrumbs.Count() - 2); + var prevVisible = breadCrumbs.ElementAtOrDefault(breadCrumbs.Count - 2); if (prevVisible != null) { if (prevVisible is Folder<string> f1) parent.FolderID = (T)Convert.ChangeType(f1.ID, typeof(T)); @@ -322,8 +320,8 @@ namespace ASC.Web.Files.Services.WCFService || parent.RootFolderType == FolderType.Privacy; entries = entries.Where(x => x.FileEntryType == FileEntryType.Folder || - (x is File<string> f1 && !FileConverter.IsConverting(f1) || - x is File<int> f2 && !FileConverter.IsConverting(f2))); + x is File<string> f1 && !FileConverter.IsConverting(f1) || + x is File<int> f2 && !FileConverter.IsConverting(f2)); var result = new DataWrapper<T> { @@ -437,7 +435,7 @@ namespace ASC.Web.Files.Services.WCFService var folderAccess = folder.Access; - if (string.Compare(folder.Title, title, false) != 0) + if (!string.Equals(folder.Title, title, StringComparison.OrdinalIgnoreCase)) { var newFolderID = folderDao.RenameFolder(folder, title); folder = folderDao.GetFolder(newFolderID); @@ -990,7 +988,7 @@ namespace ASC.Web.Files.Services.WCFService } var usersDrop = FileTracker.GetEditingBy(file.ID).Where(uid => uid != AuthContext.CurrentAccount.ID).Select(u => u.ToString()).ToArray(); - if (usersDrop.Any()) + if (usersDrop.Length > 0) { var fileStable = file.Forcesave == ForcesaveType.None ? file : fileDao.GetFileStable(file.ID, file.Version); var docKey = DocumentServiceHelper.GetDocKey(fileStable); @@ -1180,7 +1178,7 @@ namespace ASC.Web.Files.Services.WCFService result = new List<FileEntry>(EntryManager.SortEntries<T>(result, new OrderBy(SortedByType.DateAndTime, false))); - if (!result.Any()) + if (result.Count == 0) { MarkAsRead(new List<JsonElement>() { JsonDocument.Parse(JsonSerializer.Serialize(folderId)).RootElement }, new List<JsonElement>() { }); //TODO } @@ -1196,7 +1194,7 @@ namespace ASC.Web.Files.Services.WCFService public List<FileOperationResult> MarkAsRead(List<JsonElement> foldersId, List<JsonElement> filesId) { - if (!foldersId.Any() && !filesId.Any()) return GetTasksStatuses(); + if (foldersId.Count == 0 && filesId.Count == 0) return GetTasksStatuses(); return FileOperationsManager.MarkAsRead(AuthContext.CurrentAccount.ID, TenantManager.GetCurrentTenant(), foldersId, filesId); } @@ -1231,7 +1229,7 @@ namespace ASC.Web.Files.Services.WCFService var folders = providersInfo.Select(providerInfo => { - var folder = EntryManager.GetFakeThirdpartyFolder<T>(providerInfo); + var folder = EntryManager.GetFakeThirdpartyFolder(providerInfo); folder.NewForMe = folder.RootFolderType == FolderType.COMMON ? 1 : 0; return folder; }); @@ -1326,7 +1324,7 @@ namespace ASC.Web.Files.Services.WCFService var curProviderId = Convert.ToInt32(providerId); var providerInfo = providerDao.GetProviderInfo(curProviderId); - var folder = EntryManager.GetFakeThirdpartyFolder<T>(providerInfo); + var folder = EntryManager.GetFakeThirdpartyFolder(providerInfo); ErrorIf(!FileSecurity.CanDelete(folder), FilesCommonResource.ErrorMassage_SecurityException_DeleteFolder); if (providerInfo.RootFolderType == FolderType.COMMON) @@ -1335,7 +1333,7 @@ namespace ASC.Web.Files.Services.WCFService } providerDao.RemoveProviderInfo(folder.ProviderId); - FilesMessageService.Send(folder, GetHttpHeaders(), MessageAction.ThirdPartyDeleted, folder.ID.ToString(), providerInfo.ProviderKey); + FilesMessageService.Send(folder, GetHttpHeaders(), MessageAction.ThirdPartyDeleted, folder.ID, providerInfo.ProviderKey); return folder.ID; } @@ -1401,7 +1399,7 @@ namespace ASC.Web.Files.Services.WCFService public List<FileOperationResult> BulkDownload(Dictionary<JsonElement, string> folders, Dictionary<JsonElement, string> files) { - ErrorIf(!folders.Any() && !files.Any(), FilesCommonResource.ErrorMassage_BadRequest); + ErrorIf(folders.Count == 0 && files.Count == 0, FilesCommonResource.ErrorMassage_BadRequest); return FileOperationsManager.Download(AuthContext.CurrentAccount.ID, TenantManager.GetCurrentTenant(), folders, files, GetHttpHeaders()); } @@ -1468,7 +1466,7 @@ namespace ASC.Web.Files.Services.WCFService var folders = folderDao.GetFolders(foldersId); var foldersProject = folders.Where(folder => folder.FolderType == FolderType.BUNCH).ToList(); - if (foldersProject.Any()) + if (foldersProject.Count > 0) { var toSubfolders = destFolderDao.GetFolders(toFolder.ID); @@ -1503,7 +1501,7 @@ namespace ASC.Web.Files.Services.WCFService public List<FileOperationResult> MoveOrCopyItems(List<JsonElement> foldersId, List<JsonElement> filesId, JsonElement destFolderId, FileConflictResolveType resolve, bool ic, bool deleteAfter = false) { List<FileOperationResult> result; - if (foldersId.Any() || filesId.Any()) + if (foldersId.Count > 0 || filesId.Count > 0) { result = FileOperationsManager.MoveOrCopy(AuthContext.CurrentAccount.ID, TenantManager.GetCurrentTenant(), foldersId, filesId, destFolderId, ic, resolve, !deleteAfter, GetHttpHeaders()); } @@ -1666,7 +1664,7 @@ namespace ASC.Web.Files.Services.WCFService if (providerDao != null) { var providersInfo = providerDao.GetProvidersInfo(userFrom.ID); - var commonProvidersInfo = providersInfo.Where(provider => provider.RootFolderType == FolderType.COMMON).ToList(); + var commonProvidersInfo = providersInfo.Where(provider => provider.RootFolderType == FolderType.COMMON); //move common thirdparty storage userFrom foreach (var commonProviderInfo in commonProvidersInfo) diff --git a/products/ASC.Files/Core/Core/FilesIntegration.cs b/products/ASC.Files/Core/Core/FilesIntegration.cs index 63c88b4de4..8ce27d11e9 100644 --- a/products/ASC.Files/Core/Core/FilesIntegration.cs +++ b/products/ASC.Files/Core/Core/FilesIntegration.cs @@ -55,7 +55,7 @@ namespace ASC.Web.Files.Api public IEnumerable<T> RegisterBunchFolders<T>(string module, string bunch, IEnumerable<string> data) { if (data == null) - throw new ArgumentNullException("data"); + throw new ArgumentNullException(nameof(data)); data = data.ToList(); if (!data.Any()) @@ -126,7 +126,11 @@ namespace ASC.Web.Files.Api if (provider == null) continue; var data = provider.GetFileSecurity(grouping.ToDictionary(r => r.Key, r => r.Value)); - data.ToList().ForEach(x => result.Add(x.Key, x.Value)); + + foreach(var d in data) + { + result.Add(d.Key, d.Value); + } } return result; diff --git a/products/ASC.Files/Core/Core/Search/FactoryIndexerFile.cs b/products/ASC.Files/Core/Core/Search/FactoryIndexerFile.cs index a018bdba1b..2cb68d06c3 100644 --- a/products/ASC.Files/Core/Core/Search/FactoryIndexerFile.cs +++ b/products/ASC.Files/Core/Core/Search/FactoryIndexerFile.cs @@ -171,7 +171,7 @@ namespace ASC.Web.Files.Core.Search } } - if (tasks.Any()) + if (tasks.Count > 0) { Task.WaitAll(tasks.ToArray()); } @@ -196,7 +196,7 @@ namespace ASC.Web.Files.Core.Search public DbFile DbFile { get; set; } } - public class FactoryIndexerFileExtension + public static class FactoryIndexerFileExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Core/Search/FactoryIndexerFolder.cs b/products/ASC.Files/Core/Core/Search/FactoryIndexerFolder.cs index 361cd9df0c..ac411dcb98 100644 --- a/products/ASC.Files/Core/Core/Search/FactoryIndexerFolder.cs +++ b/products/ASC.Files/Core/Core/Search/FactoryIndexerFolder.cs @@ -155,7 +155,7 @@ namespace ASC.Web.Files.Core.Search } } - if (tasks.Any()) + if (tasks.Count > 0) { Task.WaitAll(tasks.ToArray()); } @@ -174,7 +174,7 @@ namespace ASC.Web.Files.Core.Search public DbFolder DbFolder { get; set; } } - public class FactoryIndexerFolderExtension + public static class FactoryIndexerFolderExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Core/Security/FileSecurity.cs b/products/ASC.Files/Core/Core/Security/FileSecurity.cs index 2b9346e6ef..fb423abab3 100644 --- a/products/ASC.Files/Core/Core/Security/FileSecurity.cs +++ b/products/ASC.Files/Core/Core/Security/FileSecurity.cs @@ -732,8 +732,8 @@ namespace ASC.Files.Core.Security var records = securityDao.GetShares(subjects); var result = new List<FileEntry>(); - result.AddRange(GetSharesForMe<int>(records.Where(r => r.EntryId.GetType() == typeof(int)), subjects, filterType, subjectGroup, subjectID, searchText, searchInContent, withSubfolders)); - result.AddRange(GetSharesForMe<string>(records.Where(r => r.EntryId.GetType() == typeof(string)), subjects, filterType, subjectGroup, subjectID, searchText, searchInContent, withSubfolders)); + result.AddRange(GetSharesForMe<int>(records.Where(r => r.EntryId is int), subjects, filterType, subjectGroup, subjectID, searchText, searchInContent, withSubfolders)); + result.AddRange(GetSharesForMe<string>(records.Where(r => r.EntryId is string), subjects, filterType, subjectGroup, subjectID, searchText, searchInContent, withSubfolders)); return result; } @@ -775,9 +775,9 @@ namespace ASC.Files.Core.Security files.ForEach(x => { - if (fileIds.ContainsKey(x.ID)) + if (fileIds.TryGetValue(x.ID, out var access)) { - x.Access = fileIds[x.ID]; + x.Access = access; x.FolderIdDisplay = GlobalFolder.GetFolderShare<T>(daoFactory); } }); @@ -795,9 +795,9 @@ namespace ASC.Files.Core.Security } folders.ForEach(x => { - if (folderIds.ContainsKey(x.ID)) + if (folderIds.TryGetValue(x.ID, out var access)) { - x.Access = folderIds[x.ID]; + x.Access = access; x.FolderIdDisplay = GlobalFolder.GetFolderShare<T>(daoFactory); } }); @@ -837,7 +837,7 @@ namespace ASC.Files.Core.Security failedRecords.Add(failedRecord); } - if (failedRecords.Any()) + if (failedRecords.Count > 0) { securityDao.DeleteShareRecords(failedRecords); } @@ -852,8 +852,8 @@ namespace ASC.Files.Core.Security var records = securityDao.GetShares(subjects); var result = new List<FileEntry>(); - result.AddRange(GetPrivacyForMe<int>(records.Where(r => r.EntryId.GetType() == typeof(int)), subjects, filterType, subjectGroup, subjectID, searchText, searchInContent, withSubfolders)); - result.AddRange(GetPrivacyForMe<string>(records.Where(r => r.EntryId.GetType() == typeof(string)), subjects, filterType, subjectGroup, subjectID, searchText, searchInContent, withSubfolders)); + result.AddRange(GetPrivacyForMe<int>(records.Where(r => r.EntryId is int), subjects, filterType, subjectGroup, subjectID, searchText, searchInContent, withSubfolders)); + result.AddRange(GetPrivacyForMe<string>(records.Where(r => r.EntryId is string), subjects, filterType, subjectGroup, subjectID, searchText, searchInContent, withSubfolders)); return result; } @@ -894,9 +894,9 @@ namespace ASC.Files.Core.Security files.ForEach(x => { - if (fileIds.ContainsKey(x.ID)) + if (fileIds.TryGetValue(x.ID, out var access)) { - x.Access = fileIds[x.ID]; + x.Access = access; x.FolderIdDisplay = GlobalFolder.GetFolderPrivacy<T>(daoFactory); } }); @@ -914,9 +914,9 @@ namespace ASC.Files.Core.Security } folders.ForEach(x => { - if (folderIds.ContainsKey(x.ID)) + if (folderIds.TryGetValue(x.ID, out var access)) { - x.Access = folderIds[x.ID]; + x.Access = access; x.FolderIdDisplay = GlobalFolder.GetFolderPrivacy<T>(daoFactory); } }); @@ -962,7 +962,7 @@ namespace ASC.Files.Core.Security return result; } - private class SubjectComparer : IComparer<FileShareRecord> + private sealed class SubjectComparer : IComparer<FileShareRecord> { private readonly List<Guid> _subjects; diff --git a/products/ASC.Files/Core/Core/Thirdparty/Box/BoxDaoBase.cs b/products/ASC.Files/Core/Core/Thirdparty/Box/BoxDaoBase.cs index 3a0346f7cf..be2793b2e0 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Box/BoxDaoBase.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Box/BoxDaoBase.cs @@ -51,7 +51,7 @@ namespace ASC.Files.Thirdparty.Box { protected override string Id { get => "box"; } - public BoxDaoBase( + protected BoxDaoBase( IServiceProvider serviceProvider, UserManager userManager, TenantManager tenantManager, @@ -92,8 +92,9 @@ namespace ASC.Files.Thirdparty.Box } protected override string MakeId(string path = null) - { - return string.Format("{0}{1}", PathPrefix, string.IsNullOrEmpty(path) || path == "0" ? "" : ("-|" + path.TrimStart('/'))); + { + var p = string.IsNullOrEmpty(path) || path == "0" ? "" : ("-|" + path.TrimStart('/')); + return $"{PathPrefix}{p}"; } protected string MakeFolderTitle(BoxFolder boxFolder) @@ -297,9 +298,9 @@ namespace ASC.Files.Thirdparty.Box if (!match.Success) { var insertIndex = requestTitle.Length; - if (requestTitle.LastIndexOf(".", StringComparison.InvariantCulture) != -1) + if (requestTitle.LastIndexOf('.') != -1) { - insertIndex = requestTitle.LastIndexOf(".", StringComparison.InvariantCulture); + insertIndex = requestTitle.LastIndexOf('.'); } requestTitle = requestTitle.Insert(insertIndex, " (1)"); } @@ -311,7 +312,7 @@ namespace ASC.Files.Thirdparty.Box return requestTitle; } - private static string MatchEvaluator(Match match) + private string MatchEvaluator(Match match) { var index = Convert.ToInt32(match.Groups[2].Value); var staticText = match.Value.Substring(string.Format(" ({0})", index).Length); diff --git a/products/ASC.Files/Core/Core/Thirdparty/Box/BoxDaoSelector.cs b/products/ASC.Files/Core/Core/Thirdparty/Box/BoxDaoSelector.cs index 897ef9e01e..99ec198360 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Box/BoxDaoSelector.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Box/BoxDaoSelector.cs @@ -63,7 +63,7 @@ namespace ASC.Files.Thirdparty.Box return base.GetSecurityDao<BoxSecurityDao>(id); } } - public class BoxDaoSelectorExtension + public static class BoxDaoSelectorExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Core/Thirdparty/Box/BoxFileDao.cs b/products/ASC.Files/Core/Core/Thirdparty/Box/BoxFileDao.cs index 1953d967ab..060127c5b0 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Box/BoxFileDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Box/BoxFileDao.cs @@ -99,7 +99,7 @@ namespace ASC.Files.Thirdparty.Box .FirstOrDefault(item => item.Name.Equals(title, StringComparison.InvariantCultureIgnoreCase)) as BoxFile); } - public File<string> GetFileStable(string fileId, int fileVersion) + public File<string> GetFileStable(string fileId, int fileVersion = -1) { return ToFile(GetBoxFile(fileId)); } @@ -151,8 +151,8 @@ namespace ASC.Files.Thirdparty.Box case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -212,8 +212,8 @@ namespace ASC.Files.Thirdparty.Box case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -252,7 +252,7 @@ namespace ASC.Files.Thirdparty.Box ProviderInfo.CacheReset(boxFileId, true); var boxFile = GetBoxFile(file.ID); - if (boxFile == null) throw new ArgumentNullException("file", FilesCommonResource.ErrorMassage_FileNotFound); + if (boxFile == null) throw new ArgumentNullException(nameof(file), FilesCommonResource.ErrorMassage_FileNotFound); if (boxFile is ErrorFile errorFile) throw new Exception(errorFile.Error); var fileStream = ProviderInfo.Storage.DownloadStream(boxFile, (int)offset); @@ -272,8 +272,8 @@ namespace ASC.Files.Thirdparty.Box public File<string> SaveFile(File<string> file, Stream fileStream) { - if (file == null) throw new ArgumentNullException("file"); - if (fileStream == null) throw new ArgumentNullException("fileStream"); + if (file == null) throw new ArgumentNullException(nameof(file)); + if (fileStream == null) throw new ArgumentNullException(nameof(fileStream)); BoxFile newBoxFile = null; diff --git a/products/ASC.Files/Core/Core/Thirdparty/Box/BoxFolderDao.cs b/products/ASC.Files/Core/Core/Thirdparty/Box/BoxFolderDao.cs index b7c9b9635c..959a1b5c1c 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Box/BoxFolderDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Box/BoxFolderDao.cs @@ -180,7 +180,7 @@ namespace ASC.Files.Thirdparty.Box public string SaveFolder(Folder<string> folder) { - if (folder == null) throw new ArgumentNullException("folder"); + if (folder == null) throw new ArgumentNullException(nameof(folder)); if (folder.ID != null) { return RenameFolder(folder, folder.Title); @@ -435,7 +435,7 @@ namespace ASC.Files.Thirdparty.Box return false; } - public long GetMaxUploadSize(string folderId, bool chunkedUpload) + public long GetMaxUploadSize(string folderId, bool chunkedUpload = false) { var storageMaxUploadSize = ProviderInfo.Storage.GetMaxUploadSize(); diff --git a/products/ASC.Files/Core/Core/Thirdparty/Box/BoxStorage.cs b/products/ASC.Files/Core/Core/Thirdparty/Box/BoxStorage.cs index a8ea44b03e..66a1959fbe 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Box/BoxStorage.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Box/BoxStorage.cs @@ -43,8 +43,6 @@ namespace ASC.Files.Thirdparty.Box { internal class BoxStorage { - private OAuth20Token _token; - private BoxClient _boxClient; private readonly List<string> _boxFields = new List<string> { "created_at", "modified_at", "name", "parent", "size" }; @@ -64,10 +62,8 @@ namespace ASC.Files.Thirdparty.Box if (IsOpened) return; - _token = token; - - var config = new BoxConfig(_token.ClientID, _token.ClientSecret, new Uri(_token.RedirectUri)); - var session = new OAuthSession(_token.AccessToken, _token.RefreshToken, (int)_token.ExpiresIn, "bearer"); + var config = new BoxConfig(token.ClientID, token.ClientSecret, new Uri(token.RedirectUri)); + var session = new OAuthSession(token.AccessToken, token.RefreshToken, (int)token.ExpiresIn, "bearer"); _boxClient = new BoxClient(config, session); IsOpened = true; @@ -125,7 +121,7 @@ namespace ASC.Files.Thirdparty.Box public Stream DownloadStream(BoxFile file, int offset = 0) { - if (file == null) throw new ArgumentNullException("file"); + if (file == null) throw new ArgumentNullException(nameof(file)); if (offset > 0 && file.Size.HasValue) { diff --git a/products/ASC.Files/Core/Core/Thirdparty/CrossDao.cs b/products/ASC.Files/Core/Core/Thirdparty/CrossDao.cs index f6a4a4cd89..8ffc3b05fd 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/CrossDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/CrossDao.cs @@ -86,19 +86,21 @@ namespace ASC.Files.Core.Thirdparty if (deleteSourceFile) { - if (fromFileShareRecords.Any()) - fromFileShareRecords.ToList().ForEach(x => - { - x.EntryId = toFile.ID; - securityDao.SetShare(x); - }); + if (fromFileShareRecords.Any()) + { + foreach (var record in fromFileShareRecords) + { + record.EntryId = toFile.ID; + securityDao.SetShare(record); + } + } var fromFileTags = fromFileNewTags; if (fromFileLockTag != null) fromFileTags.Add(fromFileLockTag); if (fromFileFavoriteTag != null) fromFileTags.AddRange(fromFileFavoriteTag); if (fromFileTemplateTag != null) fromFileTags.AddRange(fromFileTemplateTag); - if (fromFileTags.Any()) + if (fromFileTags.Count > 0) { fromFileTags.ForEach(x => x.EntryId = toFile.ID); @@ -167,18 +169,17 @@ namespace ASC.Files.Core.Thirdparty .Where(x => x.EntryType == FileEntryType.Folder); if (fromFileShareRecords.Any()) - { - fromFileShareRecords.ToList().ForEach(x => - { - x.EntryId = toFolderId; - securityDao.SetShare(x); - }); + { + foreach(var record in fromFileShareRecords){ + record.EntryId = toFolderId; + securityDao.SetShare(record); + } } var tagDao = ServiceProvider.GetService<ITagDao<TFrom>>(); var fromFileNewTags = tagDao.GetNewTags(Guid.Empty, fromFolder).ToList(); - if (fromFileNewTags.Any()) + if (fromFileNewTags.Count > 0) { fromFileNewTags.ForEach(x => x.EntryId = toFolderId); @@ -195,7 +196,7 @@ namespace ASC.Files.Core.Thirdparty } } - public class CrossDaoExtension + public static class CrossDaoExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxDaoBase.cs b/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxDaoBase.cs index cae4a21698..07bc5d5017 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxDaoBase.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxDaoBase.cs @@ -51,7 +51,7 @@ namespace ASC.Files.Thirdparty.Dropbox { protected override string Id { get => "dropbox"; } - public DropboxDaoBase(IServiceProvider serviceProvider, UserManager userManager, TenantManager tenantManager, TenantUtil tenantUtil, DbContextManager<FilesDbContext> dbContextManager, SetupInfo setupInfo, IOptionsMonitor<ILog> monitor, FileUtility fileUtility, TempPath tempPath) + protected DropboxDaoBase(IServiceProvider serviceProvider, UserManager userManager, TenantManager tenantManager, TenantUtil tenantUtil, DbContextManager<FilesDbContext> dbContextManager, SetupInfo setupInfo, IOptionsMonitor<ILog> monitor, FileUtility fileUtility, TempPath tempPath) : base(serviceProvider, userManager, tenantManager, tenantUtil, dbContextManager, setupInfo, monitor, fileUtility, tempPath) { } @@ -87,8 +87,9 @@ namespace ASC.Files.Thirdparty.Dropbox } protected override string MakeId(string path = null) - { - return string.Format("{0}{1}", PathPrefix, string.IsNullOrEmpty(path) || path == "/" ? "" : ("-" + path.Replace('/', '|'))); + { + var p = string.IsNullOrEmpty(path) || path == "/" ? "" : ("-" + path.Replace('/', '|')); + return $"{PathPrefix}{p}"; } protected string MakeFolderTitle(FolderMetadata dropboxFolder) @@ -289,9 +290,9 @@ namespace ASC.Files.Thirdparty.Dropbox if (!match.Success) { var insertIndex = requestTitle.Length; - if (requestTitle.LastIndexOf(".", StringComparison.InvariantCulture) != -1) + if (requestTitle.LastIndexOf('.') != -1) { - insertIndex = requestTitle.LastIndexOf(".", StringComparison.InvariantCulture); + insertIndex = requestTitle.LastIndexOf('.'); } requestTitle = requestTitle.Insert(insertIndex, " (1)"); } @@ -303,7 +304,7 @@ namespace ASC.Files.Thirdparty.Dropbox return requestTitle; } - private static string MatchEvaluator(Match match) + private string MatchEvaluator(Match match) { var index = Convert.ToInt32(match.Groups[2].Value); var staticText = match.Value.Substring(string.Format(" ({0})", index).Length); diff --git a/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxDaoSelector.cs b/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxDaoSelector.cs index 937bb13f2c..529a392475 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxDaoSelector.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxDaoSelector.cs @@ -64,7 +64,7 @@ namespace ASC.Files.Thirdparty.Dropbox } } - public class DropboxDaoSelectorExtension + public static class DropboxDaoSelectorExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxFileDao.cs b/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxFileDao.cs index 4f38ff3c86..d1af6c3cd3 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxFileDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxFileDao.cs @@ -103,7 +103,7 @@ namespace ASC.Files.Thirdparty.Dropbox : ToFile(metadata.AsFile); } - public File<string> GetFileStable(string fileId, int fileVersion) + public File<string> GetFileStable(string fileId, int fileVersion = -1) { return ToFile(GetDropboxFile(fileId)); } @@ -155,8 +155,8 @@ namespace ASC.Files.Thirdparty.Dropbox case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -216,8 +216,8 @@ namespace ASC.Files.Thirdparty.Dropbox case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -256,7 +256,7 @@ namespace ASC.Files.Thirdparty.Dropbox ProviderInfo.CacheReset(dropboxFilePath, true); var dropboxFile = GetDropboxFile(file.ID); - if (dropboxFile == null) throw new ArgumentNullException("file", FilesCommonResource.ErrorMassage_FileNotFound); + if (dropboxFile == null) throw new ArgumentNullException(nameof(file), FilesCommonResource.ErrorMassage_FileNotFound); if (dropboxFile is ErrorFile errorFile) throw new Exception(errorFile.Error); var fileStream = ProviderInfo.Storage.DownloadStream(MakeDropboxPath(dropboxFile), (int)offset); @@ -276,8 +276,8 @@ namespace ASC.Files.Thirdparty.Dropbox public File<string> SaveFile(File<string> file, Stream fileStream) { - if (file == null) throw new ArgumentNullException("file"); - if (fileStream == null) throw new ArgumentNullException("fileStream"); + if (file == null) throw new ArgumentNullException(nameof(file)); + if (fileStream == null) throw new ArgumentNullException(nameof(fileStream)); FileMetadata newDropboxFile = null; @@ -494,10 +494,10 @@ namespace ASC.Files.Thirdparty.Dropbox if (file == null) return null; if (file.ID != null) - file.ID = MakeId(file.ID.ToString()); + file.ID = MakeId(file.ID); if (file.FolderID != null) - file.FolderID = MakeId(file.FolderID.ToString()); + file.FolderID = MakeId(file.FolderID); return file; } diff --git a/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxFolderDao.cs b/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxFolderDao.cs index 90d6f113fd..4f42b3cf0d 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxFolderDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxFolderDao.cs @@ -181,7 +181,7 @@ namespace ASC.Files.Thirdparty.Dropbox public string SaveFolder(Folder<string> folder) { - if (folder == null) throw new ArgumentNullException("folder"); + if (folder == null) throw new ArgumentNullException(nameof(folder)); if (folder.ID != null) { return RenameFolder(folder, folder.Title); @@ -432,7 +432,7 @@ namespace ASC.Files.Thirdparty.Dropbox return false; } - public long GetMaxUploadSize(string folderId, bool chunkedUpload) + public long GetMaxUploadSize(string folderId, bool chunkedUpload = false) { var storageMaxUploadSize = ProviderInfo.Storage.MaxChunkedUploadFileSize; diff --git a/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxStorage.cs b/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxStorage.cs index 0e94297ab2..d5807a398a 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxStorage.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Dropbox/DropboxStorage.cs @@ -38,8 +38,6 @@ namespace ASC.Files.Thirdparty.Dropbox { internal class DropboxStorage : IDisposable { - private OAuth20Token _token; - private DropboxClient dropboxClient; public bool IsOpened { get; private set; } @@ -57,9 +55,7 @@ namespace ASC.Files.Thirdparty.Dropbox if (IsOpened) return; - _token = token; - - dropboxClient = new DropboxClient(_token.AccessToken); + dropboxClient = new DropboxClient(token.AccessToken); IsOpened = true; } diff --git a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveDaoBase.cs b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveDaoBase.cs index c1a4d7235e..566c03555f 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveDaoBase.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveDaoBase.cs @@ -52,7 +52,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive { protected override string Id { get => "drive"; } - public GoogleDriveDaoBase(IServiceProvider serviceProvider, UserManager userManager, TenantManager tenantManager, TenantUtil tenantUtil, DbContextManager<FilesDbContext> dbContextManager, SetupInfo setupInfo, IOptionsMonitor<ILog> monitor, FileUtility fileUtility, TempPath tempPath) + protected GoogleDriveDaoBase(IServiceProvider serviceProvider, UserManager userManager, TenantManager tenantManager, TenantUtil tenantUtil, DbContextManager<FilesDbContext> dbContextManager, SetupInfo setupInfo, IOptionsMonitor<ILog> monitor, FileUtility fileUtility, TempPath tempPath) : base(serviceProvider, userManager, tenantManager, tenantUtil, dbContextManager, setupInfo, monitor, fileUtility, tempPath) { } @@ -84,8 +84,9 @@ namespace ASC.Files.Thirdparty.GoogleDrive } protected override string MakeId(string path = null) - { - return string.Format("{0}{1}", PathPrefix, string.IsNullOrEmpty(path) || path == "root" || path == ProviderInfo.DriveRootId ? "" : ("-|" + path.TrimStart('/'))); + { + var p = string.IsNullOrEmpty(path) || path == "root" || path == ProviderInfo.DriveRootId ? "" : ("-|" + path.TrimStart('/')); + return $"{PathPrefix}{p}"; } protected string MakeFolderTitle(DriveFile driveFolder) diff --git a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveDaoSelector.cs b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveDaoSelector.cs index 6eebee8067..f3f9ab73b5 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveDaoSelector.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveDaoSelector.cs @@ -63,7 +63,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive } } - public class GoogleDriveDaoSelectorExtension + public static class GoogleDriveDaoSelectorExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveFileDao.cs b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveFileDao.cs index 72a0e6a537..2672617976 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveFileDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveFileDao.cs @@ -100,7 +100,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive .FirstOrDefault(file => file.Name.Equals(title, StringComparison.InvariantCultureIgnoreCase))); } - public File<string> GetFileStable(string fileId, int fileVersion) + public File<string> GetFileStable(string fileId, int fileVersion = -1) { return ToFile(GetDriveEntry(fileId)); } @@ -152,8 +152,8 @@ namespace ASC.Files.Thirdparty.GoogleDrive case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -213,8 +213,8 @@ namespace ASC.Files.Thirdparty.GoogleDrive case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -252,7 +252,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive var driveId = MakeDriveId(file.ID); ProviderInfo.CacheReset(driveId, true); var driveFile = GetDriveEntry(file.ID); - if (driveFile == null) throw new ArgumentNullException("file", FilesCommonResource.ErrorMassage_FileNotFound); + if (driveFile == null) throw new ArgumentNullException(nameof(file), FilesCommonResource.ErrorMassage_FileNotFound); if (driveFile is ErrorDriveEntry errorDriveEntry) throw new Exception(errorDriveEntry.Error); var fileStream = ProviderInfo.Storage.DownloadStream(driveFile, (int)offset); @@ -277,8 +277,8 @@ namespace ASC.Files.Thirdparty.GoogleDrive public File<string> SaveFile(File<string> file, Stream fileStream) { - if (file == null) throw new ArgumentNullException("file"); - if (fileStream == null) throw new ArgumentNullException("fileStream"); + if (file == null) throw new ArgumentNullException(nameof(file)); + if (fileStream == null) throw new ArgumentNullException(nameof(fileStream)); DriveFile newDriveFile = null; diff --git a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveFolderDao.cs b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveFolderDao.cs index d45c02abd9..433af01ca2 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveFolderDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveFolderDao.cs @@ -177,7 +177,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive public string SaveFolder(Folder<string> folder) { - if (folder == null) throw new ArgumentNullException("folder"); + if (folder == null) throw new ArgumentNullException(nameof(folder)); if (folder.ID != null) { return RenameFolder(folder, folder.Title); @@ -424,7 +424,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive return false; } - public long GetMaxUploadSize(string folderId, bool chunkedUpload) + public long GetMaxUploadSize(string folderId, bool chunkedUpload = false) { var storageMaxUploadSize = ProviderInfo.Storage.GetMaxUploadSize(); diff --git a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveProviderInfo.cs b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveProviderInfo.cs index fce1658a43..fefce56444 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveProviderInfo.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveProviderInfo.cs @@ -366,7 +366,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive } } - public class GoogleDriveProviderInfoExtention + public static class GoogleDriveProviderInfoExtention { public static void Register(DIHelper dIHelper) { diff --git a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveStorage.cs b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveStorage.cs index 7608b25a9a..036b2659ac 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveStorage.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/GoogleDrive/GoogleDriveStorage.cs @@ -62,19 +62,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive { [Scope] internal class GoogleDriveStorage : IDisposable - { - public GoogleDriveStorage( - ConsumerFactory consumerFactory, - FileUtility fileUtility, - IOptionsMonitor<ILog> monitor, - TempStream tempStream) - { - ConsumerFactory = consumerFactory; - FileUtility = fileUtility; - Log = monitor.Get("ASC.Files"); - TempStream = tempStream; - } - + { private OAuth20Token _token; private string AccessToken @@ -94,9 +82,24 @@ namespace ASC.Files.Thirdparty.GoogleDrive private FileUtility FileUtility { get; } public ILog Log { get; } private TempStream TempStream { get; } + private IHttpClientFactory ClientFactory { get; } public const long MaxChunkedUploadFileSize = 2L * 1024L * 1024L * 1024L; + public GoogleDriveStorage( + ConsumerFactory consumerFactory, + FileUtility fileUtility, + IOptionsMonitor<ILog> monitor, + TempStream tempStream, + IHttpClientFactory clientFactory) + { + ConsumerFactory = consumerFactory; + FileUtility = fileUtility; + Log = monitor.Get("ASC.Files"); + TempStream = tempStream; + ClientFactory = clientFactory; + } + public void Open(OAuth20Token token) { if (IsOpened) @@ -202,9 +205,9 @@ namespace ASC.Files.Thirdparty.GoogleDrive public Stream DownloadStream(DriveFile file, int offset = 0) { - if (file == null) throw new ArgumentNullException("file"); + if (file == null) throw new ArgumentNullException(nameof(file)); - var downloadArg = string.Format("{0}?alt=media", file.Id); + var downloadArg = $"{file.Id}?alt=media"; var ext = MimeMapping.GetExtention(file.MimeType); if (GoogleLoginProvider.GoogleDriveExt.Contains(ext)) @@ -212,9 +215,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive var internalExt = FileUtility.GetGoogleDownloadableExtension(ext); var requiredMimeType = MimeMapping.GetMimeMapping(internalExt); - downloadArg = string.Format("{0}/export?mimeType={1}", - file.Id, - HttpUtility.UrlEncode(requiredMimeType)); + downloadArg = $"{file.Id}/export?mimeType={HttpUtility.UrlEncode(requiredMimeType)}"; } var request = new HttpRequestMessage(); @@ -222,7 +223,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive request.Method = HttpMethod.Get; request.Headers.Add("Authorization", "Bearer " + AccessToken); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); if (offset == 0 && file.Size.HasValue && file.Size > 0) @@ -346,7 +347,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive public ResumableUploadSession CreateResumableSession(DriveFile driveFile, long contentLength) { - if (driveFile == null) throw new ArgumentNullException("driveFile"); + if (driveFile == null) throw new ArgumentNullException(nameof(driveFile)); var fileId = string.Empty; var method = "POST"; @@ -360,10 +361,10 @@ namespace ASC.Files.Thirdparty.GoogleDrive } else { - var titleData = !string.IsNullOrEmpty(driveFile.Name) ? string.Format("\"name\":\"{0}\"", driveFile.Name) : ""; - var parentData = !string.IsNullOrEmpty(folderId) ? string.Format(",\"parents\":[\"{0}\"]", folderId) : ""; + var titleData = !string.IsNullOrEmpty(driveFile.Name) ? $"\"name\":\"{driveFile.Name}\"" : ""; + var parentData = !string.IsNullOrEmpty(folderId) ? $",\"parents\":[\"{folderId}\"]" : ""; - body = !string.IsNullOrEmpty(titleData + parentData) ? string.Format("{{{0}{1}}}", titleData, parentData) : ""; + body = !string.IsNullOrEmpty(titleData + parentData) ? "{{" + titleData + parentData + "}}" : ""; } var request = new HttpRequestMessage(); @@ -374,7 +375,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive request.Headers.Add("Authorization", "Bearer " + AccessToken); request.Content = new StringContent(body, Encoding.UTF8, "application/json"); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); var uploadSession = new ResumableUploadSession(driveFile.Id, folderId, contentLength); @@ -388,7 +389,7 @@ namespace ASC.Files.Thirdparty.GoogleDrive public void Transfer(ResumableUploadSession googleDriveSession, Stream stream, long chunkLength) { if (stream == null) - throw new ArgumentNullException("stream"); + throw new ArgumentNullException(nameof(stream)); if (googleDriveSession.Status != ResumableUploadSessionStatus.Started) throw new InvalidOperationException("Can't upload chunk for given upload session."); @@ -402,8 +403,8 @@ namespace ASC.Files.Thirdparty.GoogleDrive googleDriveSession.BytesTransfered + chunkLength - 1, googleDriveSession.BytesToTransfer)); request.Content = new StreamContent(stream); - using var httpClient = new HttpClient(); - HttpResponseMessage response = null; + var httpClient = ClientFactory.CreateClient(); + HttpResponseMessage response; try { diff --git a/products/ASC.Files/Core/Core/Thirdparty/IThirdPartyProviderDao.cs b/products/ASC.Files/Core/Core/Thirdparty/IThirdPartyProviderDao.cs index 36aea72403..40f14f0aa7 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/IThirdPartyProviderDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/IThirdPartyProviderDao.cs @@ -82,7 +82,7 @@ namespace ASC.Files.Thirdparty public Task<Stream> GetThumbnailAsync(File<string> file) { - return null; + return Task.FromResult<Stream>(null); } public virtual Stream GetFileStream(File<string> file) @@ -229,7 +229,7 @@ namespace ASC.Files.Thirdparty protected abstract string Id { get; } - public ThirdPartyProviderDao( + protected ThirdPartyProviderDao( IServiceProvider serviceProvider, UserManager userManager, TenantManager tenantManager, @@ -270,7 +270,7 @@ namespace ASC.Files.Thirdparty string result; if (id.StartsWith(Id)) { - result = Regex.Replace(BitConverter.ToString(Hasher.Hash(id.ToString(), HashAlg.MD5)), "-", "").ToLower(); + result = Regex.Replace(BitConverter.ToString(Hasher.Hash(id, HashAlg.MD5)), "-", "").ToLower(); } else { @@ -495,7 +495,7 @@ namespace ASC.Files.Thirdparty .Select(r => r.HashId) .ToList(); - if (!entryIDs.Any()) return new List<Tag>(); + if (entryIDs.Count == 0) return new List<Tag>(); var q = from r in FilesDbContext.Tag from l in FilesDbContext.TagLink.Where(a => a.TenantId == r.TenantId && a.TagId == r.Id).DefaultIfEmpty() diff --git a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveDaoBase.cs b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveDaoBase.cs index 6d8c1ea275..399540137f 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveDaoBase.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveDaoBase.cs @@ -49,7 +49,7 @@ namespace ASC.Files.Thirdparty.OneDrive { protected override string Id { get => "onedrive"; } - public OneDriveDaoBase(IServiceProvider serviceProvider, UserManager userManager, TenantManager tenantManager, TenantUtil tenantUtil, DbContextManager<FilesDbContext> dbContextManager, SetupInfo setupInfo, IOptionsMonitor<ILog> monitor, FileUtility fileUtility, TempPath tempPath) + protected OneDriveDaoBase(IServiceProvider serviceProvider, UserManager userManager, TenantManager tenantManager, TenantUtil tenantUtil, DbContextManager<FilesDbContext> dbContextManager, SetupInfo setupInfo, IOptionsMonitor<ILog> monitor, FileUtility fileUtility, TempPath tempPath) : base(serviceProvider, userManager, tenantManager, tenantUtil, dbContextManager, setupInfo, monitor, fileUtility, tempPath) { } @@ -83,19 +83,18 @@ namespace ASC.Files.Thirdparty.OneDrive } protected override string MakeId(string id = null) - { - return string.Format("{0}{1}", PathPrefix, - string.IsNullOrEmpty(id) || id == "" - ? "" : ("-|" + id.TrimStart('/'))); + { + var i = string.IsNullOrEmpty(id) ? "" : ("-|" + id.TrimStart('/')); + return $"{PathPrefix}{i}"; } public string MakeOneDrivePath(Item onedriveItem) { return onedriveItem == null || IsRoot(onedriveItem) ? string.Empty - : (OneDriveStorage.MakeOneDrivePath( + : OneDriveStorage.MakeOneDrivePath( new Regex("^" + OneDriveStorage.RootPath).Replace(onedriveItem.ParentReference.Path, ""), - onedriveItem.Name)); + onedriveItem.Name); } protected string MakeItemTitle(Item onedriveItem) @@ -254,9 +253,9 @@ namespace ASC.Files.Thirdparty.OneDrive if (!match.Success) { var insertIndex = requestTitle.Length; - if (requestTitle.LastIndexOf(".", StringComparison.InvariantCulture) != -1) + if (requestTitle.LastIndexOf('.') != -1) { - insertIndex = requestTitle.LastIndexOf(".", StringComparison.InvariantCulture); + insertIndex = requestTitle.LastIndexOf('.'); } requestTitle = requestTitle.Insert(insertIndex, " (1)"); } @@ -268,7 +267,7 @@ namespace ASC.Files.Thirdparty.OneDrive return requestTitle; } - private static string MatchEvaluator(Match match) + private string MatchEvaluator(Match match) { var index = Convert.ToInt32(match.Groups[2].Value); var staticText = match.Value.Substring(string.Format(" ({0})", index).Length); diff --git a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveDaoSelector.cs b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveDaoSelector.cs index f5d1510da5..57d36beb93 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveDaoSelector.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveDaoSelector.cs @@ -64,7 +64,7 @@ namespace ASC.Files.Thirdparty.OneDrive } } - public class OneDriveDaoSelectorExtension + public static class OneDriveDaoSelectorExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveFileDao.cs b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveFileDao.cs index 1c11359457..9f1ab45b7b 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveFileDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveFileDao.cs @@ -99,7 +99,7 @@ namespace ASC.Files.Thirdparty.OneDrive .FirstOrDefault(item => item.Name.Equals(title, StringComparison.InvariantCultureIgnoreCase) && item.File != null)); } - public File<string> GetFileStable(string fileId, int fileVersion) + public File<string> GetFileStable(string fileId, int fileVersion = -1) { return ToFile(GetOneDriveItem(fileId)); } @@ -151,8 +151,8 @@ namespace ASC.Files.Thirdparty.OneDrive case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -212,8 +212,8 @@ namespace ASC.Files.Thirdparty.OneDrive case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -252,7 +252,7 @@ namespace ASC.Files.Thirdparty.OneDrive ProviderInfo.CacheReset(onedriveFileId); var onedriveFile = GetOneDriveItem(file.ID); - if (onedriveFile == null) throw new ArgumentNullException("file", FilesCommonResource.ErrorMassage_FileNotFound); + if (onedriveFile == null) throw new ArgumentNullException(nameof(file), FilesCommonResource.ErrorMassage_FileNotFound); if (onedriveFile is ErrorItem errorItem) throw new Exception(errorItem.Error); var fileStream = ProviderInfo.Storage.DownloadStream(onedriveFile, (int)offset); @@ -272,8 +272,8 @@ namespace ASC.Files.Thirdparty.OneDrive public File<string> SaveFile(File<string> file, Stream fileStream) { - if (file == null) throw new ArgumentNullException("file"); - if (fileStream == null) throw new ArgumentNullException("fileStream"); + if (file == null) throw new ArgumentNullException(nameof(file)); + if (fileStream == null) throw new ArgumentNullException(nameof(fileStream)); Item newOneDriveFile = null; @@ -488,10 +488,10 @@ namespace ASC.Files.Thirdparty.OneDrive if (file == null) return null; if (file.ID != null) - file.ID = MakeId(file.ID.ToString()); + file.ID = MakeId(file.ID); if (file.FolderID != null) - file.FolderID = MakeId(file.FolderID.ToString()); + file.FolderID = MakeId(file.FolderID); return file; } diff --git a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveFolderDao.cs b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveFolderDao.cs index faa3e485e0..93eb12d384 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveFolderDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveFolderDao.cs @@ -177,7 +177,7 @@ namespace ASC.Files.Thirdparty.OneDrive public string SaveFolder(Folder<string> folder) { - if (folder == null) throw new ArgumentNullException("folder"); + if (folder == null) throw new ArgumentNullException(nameof(folder)); if (folder.ID != null) { return RenameFolder(folder, folder.Title); @@ -435,7 +435,7 @@ namespace ASC.Files.Thirdparty.OneDrive return true; } - public long GetMaxUploadSize(string folderId, bool chunkedUpload) + public long GetMaxUploadSize(string folderId, bool chunkedUpload = false) { var storageMaxUploadSize = ProviderInfo.Storage.MaxChunkedUploadFileSize; diff --git a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveProviderInfo.cs b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveProviderInfo.cs index 475e472427..bc3c5e4562 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveProviderInfo.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveProviderInfo.cs @@ -258,7 +258,7 @@ namespace ASC.Files.Thirdparty.OneDrive } } } - public class OneDriveProviderInfoExtention + public static class OneDriveProviderInfoExtention { public static void Register(DIHelper dIHelper) { diff --git a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveStorage.cs b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveStorage.cs index fb1e9d3beb..f0cd96680a 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveStorage.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/OneDrive/OneDriveStorage.cs @@ -50,11 +50,6 @@ namespace ASC.Files.Thirdparty.OneDrive [Scope] internal class OneDriveStorage { - public OneDriveStorage(ConsumerFactory consumerFactory) - { - ConsumerFactory = consumerFactory; - } - private OAuth20Token _token; private string AccessToken @@ -79,9 +74,16 @@ namespace ASC.Files.Thirdparty.OneDrive } public bool IsOpened { get; private set; } - private ConsumerFactory ConsumerFactory { get; } + private ConsumerFactory ConsumerFactory { get; } + private IHttpClientFactory ClientFactory { get; } - public long MaxChunkedUploadFileSize = 10L * 1024L * 1024L * 1024L; + public long MaxChunkedUploadFileSize = 10L * 1024L * 1024L * 1024L; + + public OneDriveStorage(ConsumerFactory consumerFactory, IHttpClientFactory clientFactory) + { + ConsumerFactory = consumerFactory; + ClientFactory = clientFactory; + } public void Open(OAuth20Token token) { @@ -108,8 +110,8 @@ namespace ASC.Files.Thirdparty.OneDrive } - public static string RootPath = "/drive/root:"; - public static string ApiVersion = "v1.0"; + public static readonly string RootPath = "/drive/root:"; + public static readonly string ApiVersion = "v1.0"; public static string MakeOneDrivePath(string parentPath, string name) { @@ -140,7 +142,7 @@ namespace ASC.Files.Thirdparty.OneDrive public Stream DownloadStream(Item file, int offset = 0) { - if (file == null || file.File == null) throw new ArgumentNullException("file"); + if (file == null || file.File == null) throw new ArgumentNullException(nameof(file)); var fileStream = OnedriveClient .Drive @@ -249,7 +251,7 @@ namespace ASC.Files.Thirdparty.OneDrive public ResumableUploadSession CreateResumableSession(Item onedriveFile, long contentLength) { - if (onedriveFile == null) throw new ArgumentNullException("onedriveFile"); + if (onedriveFile == null) throw new ArgumentNullException(nameof(onedriveFile)); var folderId = onedriveFile.ParentReference.Id; var fileName = onedriveFile.Name; @@ -270,7 +272,7 @@ namespace ASC.Files.Thirdparty.OneDrive var uploadSession = new ResumableUploadSession(onedriveFile.Id, folderId, contentLength); - using (var httpClient = new HttpClient()) + var httpClient = ClientFactory.CreateClient(); using (var response = httpClient.Send(request)) using (var responseStream = response.Content.ReadAsStream()) { @@ -291,7 +293,7 @@ namespace ASC.Files.Thirdparty.OneDrive public void Transfer(ResumableUploadSession oneDriveSession, Stream stream, long chunkLength) { if (stream == null) - throw new ArgumentNullException("stream"); + throw new ArgumentNullException(nameof(stream)); if (oneDriveSession.Status != ResumableUploadSessionStatus.Started) throw new InvalidOperationException("Can't upload chunk for given upload session."); @@ -306,7 +308,7 @@ namespace ASC.Files.Thirdparty.OneDrive oneDriveSession.BytesToTransfer)); request.Content = new StreamContent(stream); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); if (response.StatusCode != HttpStatusCode.Created && response.StatusCode != HttpStatusCode.OK) @@ -333,7 +335,7 @@ namespace ASC.Files.Thirdparty.OneDrive request.RequestUri = new Uri(oneDriveSession.Location); request.Method = HttpMethod.Delete; - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); } } diff --git a/products/ASC.Files/Core/Core/Thirdparty/ProviderAccountDao.cs b/products/ASC.Files/Core/Core/Thirdparty/ProviderAccountDao.cs index f1cdd5ba5e..8bc41e0058 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/ProviderAccountDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/ProviderAccountDao.cs @@ -81,7 +81,14 @@ namespace ASC.Files.Thirdparty internal class ProviderAccountDao : IProviderDao { private int tenantID; - protected int TenantID { get => tenantID != 0 ? tenantID : (tenantID = TenantManager.GetCurrentTenant().TenantId); } + protected int TenantID + { + get + { + if (tenantID == 0) tenantID = TenantManager.GetCurrentTenant().TenantId; + return tenantID; + } + } private Lazy<FilesDbContext> LazyFilesDbContext { get; } private FilesDbContext FilesDbContext { get => LazyFilesDbContext.Value; } public ILog Logger { get; } @@ -318,7 +325,7 @@ namespace ASC.Files.Thirdparty public virtual void RemoveProviderInfo(int linkId) { using var tx = FilesDbContext.Database.BeginTransaction(); - var folderId = GetProviderInfo(linkId).RootFolderId.ToString(); + var folderId = GetProviderInfo(linkId).RootFolderId; var entryIDs = FilesDbContext.ThirdpartyIdMapping .Where(r => r.TenantId == TenantID) @@ -593,7 +600,7 @@ namespace ASC.Files.Thirdparty } } - public class ProviderAccountDaoExtension + public static class ProviderAccountDaoExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderDaoBase.cs b/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderDaoBase.cs index 7f4fefae9d..6cd316fd24 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderDaoBase.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderDaoBase.cs @@ -27,8 +27,8 @@ using System; using System.Collections.Generic; using System.Linq; -using System.Threading; - +using System.Threading; + using ASC.Core; using ASC.Files.Core; using ASC.Files.Core.Data; @@ -46,9 +46,9 @@ namespace ASC.Files.Thirdparty.ProviderDao { internal class ProviderDaoBase : ThirdPartyProviderDao, IDisposable { - private List<IDaoSelector> selectors; - private List<IDaoSelector> Selectors - { + private List<IDaoSelector> selectors; + private List<IDaoSelector> Selectors + { get => selectors ??= new List<IDaoSelector> { //Fill in selectors @@ -58,11 +58,18 @@ namespace ASC.Files.Thirdparty.ProviderDao ServiceProvider.GetService<BoxDaoSelector>(), ServiceProvider.GetService<DropboxDaoSelector>(), ServiceProvider.GetService<OneDriveDaoSelector>() - }; + }; } private int tenantID; - private int TenantID { get => tenantID != 0 ? tenantID : (tenantID = TenantManager.GetCurrentTenant().TenantId); } + private int TenantID + { + get + { + if (tenantID == 0) tenantID = TenantManager.GetCurrentTenant().TenantId; + return tenantID; + } + } public ProviderDaoBase( IServiceProvider serviceProvider, @@ -98,16 +105,17 @@ namespace ASC.Files.Thirdparty.ProviderDao protected void SetSharedProperty(IEnumerable<FileEntry<string>> entries) { - SecurityDao.GetPureShareRecords(entries) - //.Where(x => x.Owner == SecurityContext.CurrentAccount.ID) - .Select(x => x.EntryId).Distinct().ToList() - .ForEach(id => - { - var firstEntry = entries.FirstOrDefault(y => y.ID.Equals(id)); + var ids = SecurityDao.GetPureShareRecords(entries) + //.Where(x => x.Owner == SecurityContext.CurrentAccount.ID) + .Select(x => x.EntryId).Distinct(); - if (firstEntry != null) - firstEntry.Shared = true; - }); + foreach(var id in ids) + { + var firstEntry = entries.FirstOrDefault(y => y.ID.Equals(id)); + + if (firstEntry != null) + firstEntry.Shared = true; + } } protected IEnumerable<IDaoSelector> GetSelectors() @@ -125,12 +133,12 @@ namespace ASC.Files.Thirdparty.ProviderDao fromFileId, fromSelector.GetFileDao(fromFileId), fromSelector.ConvertId, toFolderId, toSelector.GetFileDao(toFolderId), toSelector.ConvertId, deleteSourceFile); - } - + } + protected File<int> PerformCrossDaoFileCopy(string fromFileId, int toFolderId, bool deleteSourceFile) { var fromSelector = GetSelector(fromFileId); - using var scope = ServiceProvider.CreateScope(); + using var scope = ServiceProvider.CreateScope(); var tenantManager = scope.ServiceProvider.GetService<TenantManager>(); tenantManager.SetCurrentTenant(TenantID); @@ -153,7 +161,7 @@ namespace ASC.Files.Thirdparty.ProviderDao protected Folder<int> PerformCrossDaoFolderCopy(string fromFolderId, int toRootFolderId, bool deleteSourceFolder, CancellationToken? cancellationToken) { - var fromSelector = GetSelector(fromFolderId); + var fromSelector = GetSelector(fromFolderId); return CrossDao.PerformCrossDaoFolderCopy( fromFolderId, fromSelector.GetFolderDao(fromFolderId), fromSelector.GetFileDao(fromFolderId), fromSelector.ConvertId, @@ -162,10 +170,10 @@ namespace ASC.Files.Thirdparty.ProviderDao } public void Dispose() - { - if (selectors != null) - { - selectors.ForEach(r => r.Dispose()); + { + if (selectors != null) + { + selectors.ForEach(r => r.Dispose()); } } } diff --git a/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderFileDao.cs b/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderFileDao.cs index fb81dd414d..64202e8a5f 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderFileDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderFileDao.cs @@ -188,7 +188,7 @@ namespace ASC.Files.Thirdparty.ProviderDao .GetFiles(selector.ConvertId(parentId), orderBy, filterType, subjectGroup, subjectID, searchText, searchInContent, withSubfolders) .Where(r => r != null).ToList(); - if (!result.Any()) return new List<File<string>>(); + if (result.Count > 0) return new List<File<string>>(); SetSharedProperty(result); @@ -208,7 +208,7 @@ namespace ASC.Files.Thirdparty.ProviderDao /// <returns>Stream</returns> public Stream GetFileStream(File<string> file, long offset) { - if (file == null) throw new ArgumentNullException("file"); + if (file == null) throw new ArgumentNullException(nameof(file)); var fileId = file.ID; var selector = GetSelector(fileId); file.ID = selector.ConvertId(fileId); @@ -221,7 +221,7 @@ namespace ASC.Files.Thirdparty.ProviderDao public bool IsSupportedPreSignedUri(File<string> file) { - if (file == null) throw new ArgumentNullException("file"); + if (file == null) throw new ArgumentNullException(nameof(file)); var fileId = file.ID; var selector = GetSelector(fileId); file.ID = selector.ConvertId(fileId); @@ -234,7 +234,7 @@ namespace ASC.Files.Thirdparty.ProviderDao public Uri GetPreSignedUri(File<string> file, TimeSpan expires) { - if (file == null) throw new ArgumentNullException("file"); + if (file == null) throw new ArgumentNullException(nameof(file)); var fileId = file.ID; var selector = GetSelector(fileId); file.ID = selector.ConvertId(fileId); @@ -247,7 +247,7 @@ namespace ASC.Files.Thirdparty.ProviderDao public File<string> SaveFile(File<string> file, Stream fileStream) { - if (file == null) throw new ArgumentNullException("file"); + if (file == null) throw new ArgumentNullException(nameof(file)); var fileId = file.ID; var folderId = file.FolderID; @@ -281,7 +281,7 @@ namespace ASC.Files.Thirdparty.ProviderDao public File<string> ReplaceFileVersion(File<string> file, Stream fileStream) { - if (file == null) throw new ArgumentNullException("file"); + if (file == null) throw new ArgumentNullException(nameof(file)); if (file.ID == null) throw new ArgumentException("No file id or folder id toFolderId determine provider"); var fileId = file.ID; @@ -446,7 +446,7 @@ namespace ASC.Files.Thirdparty.ProviderDao if (file.FolderID != null) return GetSelector(file.FolderID).GetFileDao(file.FolderID); - throw new ArgumentException("Can't create instance of dao for given file.", "file"); + throw new ArgumentException("Can't create instance of dao for given file.", nameof(file)); } private string ConvertId(string id) diff --git a/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderFolderDao.cs b/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderFolderDao.cs index 0e6a04e9da..9ed97f9094 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderFolderDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderFolderDao.cs @@ -103,7 +103,7 @@ namespace ASC.Files.Thirdparty.ProviderDao var result = folderDao.GetFolders(selector.ConvertId(parentId), orderBy, filterType, subjectGroup, subjectID, searchText, withSubfolders) .Where(r => r != null).ToList(); - if (!result.Any()) return new List<Folder<string>>(); + if (result.Count > 0) return new List<Folder<string>>(); SetSharedProperty(result); @@ -119,7 +119,7 @@ namespace ASC.Files.Thirdparty.ProviderDao var selectorLocal = selector; var matchedIds = folderIds.Where(selectorLocal.IsMatch).ToList(); - if (!matchedIds.Any()) continue; + if (matchedIds.Count > 0) continue; result = result.Concat(matchedIds.GroupBy(selectorLocal.GetIdCode) .SelectMany(matchedId => @@ -144,7 +144,7 @@ filterType, subjectGroup, subjectID, searchText, searchSubfolders, checkShare); public string SaveFolder(Folder<string> folder) { - if (folder == null) throw new ArgumentNullException("folder"); + if (folder == null) throw new ArgumentNullException(nameof(folder)); if (folder.ID != null) { @@ -261,12 +261,12 @@ filterType, subjectGroup, subjectID, searchText, searchSubfolders, checkShare); public IDictionary<string, string> CanMoveOrCopy(string[] folderIds, string to) { - if (!folderIds.Any()) return new Dictionary<string, string>(); + if (folderIds.Length > 0) return new Dictionary<string, string>(); var selector = GetSelector(to); var matchedIds = folderIds.Where(selector.IsMatch).ToArray(); - if (!matchedIds.Any()) return new Dictionary<string, string>(); + if (matchedIds.Length > 0) return new Dictionary<string, string>(); var folderDao = selector.GetFolderDao(matchedIds.FirstOrDefault()); return folderDao.CanMoveOrCopy(matchedIds, to); @@ -338,7 +338,7 @@ filterType, subjectGroup, subjectID, searchText, searchSubfolders, checkShare); return folderDao.CanCalculateSubitems(entryId); } - public long GetMaxUploadSize(string folderId, bool chunkedUpload) + public long GetMaxUploadSize(string folderId, bool chunkedUpload = false) { var selector = GetSelector(folderId); var folderDao = selector.GetFolderDao(folderId); diff --git a/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderSecutiryDao.cs b/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderSecutiryDao.cs index 4ba1a889dd..b377ffce77 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderSecutiryDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/ProviderDao/ProviderSecutiryDao.cs @@ -64,7 +64,7 @@ namespace ASC.Files.Thirdparty.ProviderDao var files = entries.Where(x => x.FileEntryType == FileEntryType.File).ToArray(); var folders = entries.Where(x => x.FileEntryType == FileEntryType.Folder).ToList(); - if (files.Any()) + if (files.Length > 0) { var folderIds = files.Select(x => ((File<string>)x).FolderID).Distinct(); foreach (var folderId in folderIds) @@ -135,7 +135,7 @@ namespace ASC.Files.Thirdparty.ProviderDao private List<FileShareRecord> GetShareForFolders(IReadOnlyCollection<FileEntry<string>> folders) { - if (!folders.Any()) return new List<FileShareRecord>(); + if (folders.Count > 0) return new List<FileShareRecord>(); var result = new List<FileShareRecord>(); @@ -146,7 +146,7 @@ namespace ASC.Files.Thirdparty.ProviderDao if (folderDao == null) continue; var parentFolders = folderDao.GetParentFolders(selector.ConvertId(folder.ID)); - if (parentFolders == null || !parentFolders.Any()) continue; + if (parentFolders == null || parentFolders.Count > 0) continue; parentFolders.Reverse(); var pureShareRecords = GetPureShareRecords(parentFolders); diff --git a/products/ASC.Files/Core/Core/Thirdparty/RegexDaoSelectorBase.cs b/products/ASC.Files/Core/Core/Thirdparty/RegexDaoSelectorBase.cs index b4f42ceee2..2e825eb568 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/RegexDaoSelectorBase.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/RegexDaoSelectorBase.cs @@ -116,7 +116,7 @@ namespace ASC.Files.Thirdparty private T1 GetDao<T1>(string id) where T1 : ThirdPartyProviderDao<T> { var providerKey = $"{id}{typeof(T1)}"; - if (Providers.ContainsKey(providerKey)) return (T1)Providers[providerKey]; + if (Providers.TryGetValue(providerKey, out var provider)) return (T1)provider; var res = ServiceProvider.GetService<T1>(); @@ -130,7 +130,7 @@ namespace ASC.Files.Thirdparty internal BaseProviderInfo<T> GetInfo(string objectId) { - if (objectId == null) throw new ArgumentNullException("objectId"); + if (objectId == null) throw new ArgumentNullException(nameof(objectId)); var id = objectId; var match = Selector.Match(id); if (match.Success) diff --git a/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointDaoBase.cs b/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointDaoBase.cs index e495a3ed55..002d6bedba 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointDaoBase.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointDaoBase.cs @@ -63,9 +63,9 @@ namespace ASC.Files.Thirdparty.SharePoint if (!match.Success) { var insertIndex = requestTitle.Length; - if (requestTitle.LastIndexOf(".", StringComparison.Ordinal) != -1) + if (requestTitle.LastIndexOf('.') != -1) { - insertIndex = requestTitle.LastIndexOf(".", StringComparison.Ordinal); + insertIndex = requestTitle.LastIndexOf('.'); } requestTitle = requestTitle.Insert(insertIndex, " (1)"); } @@ -77,7 +77,7 @@ namespace ASC.Files.Thirdparty.SharePoint return requestTitle; } - private static string MatchEvaluator(Match match) + private string MatchEvaluator(Match match) { var index = Convert.ToInt32(match.Groups[2].Value); var staticText = match.Value.Substring(string.Format(" ({0})", index).Length); diff --git a/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointDaoSelector.cs b/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointDaoSelector.cs index 618b3bfb60..4159c99fb1 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointDaoSelector.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointDaoSelector.cs @@ -77,7 +77,7 @@ namespace ASC.Files.Thirdparty.SharePoint } } - public class SharePointDaoSelectorExtension + public static class SharePointDaoSelectorExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointFileDao.cs b/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointFileDao.cs index 16f2b2f623..4d84687ad8 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointFileDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointFileDao.cs @@ -92,7 +92,7 @@ namespace ASC.Files.Thirdparty.SharePoint return ProviderInfo.ToFile(ProviderInfo.GetFolderFiles(parentId).FirstOrDefault(item => item.Name.Equals(title, StringComparison.InvariantCultureIgnoreCase))); } - public File<string> GetFileStable(string fileId, int fileVersion) + public File<string> GetFileStable(string fileId, int fileVersion = -1) { return ProviderInfo.ToFile(ProviderInfo.GetFileById(fileId)); } @@ -143,8 +143,8 @@ namespace ASC.Files.Thirdparty.SharePoint case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -204,8 +204,8 @@ namespace ASC.Files.Thirdparty.SharePoint case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -242,7 +242,7 @@ namespace ASC.Files.Thirdparty.SharePoint { var fileToDownload = ProviderInfo.GetFileById(file.ID); if (fileToDownload == null) - throw new ArgumentNullException("file", FilesCommonResource.ErrorMassage_FileNotFound); + throw new ArgumentNullException(nameof(file), FilesCommonResource.ErrorMassage_FileNotFound); var fileStream = ProviderInfo.GetFileStream(fileToDownload.ServerRelativeUrl, (int)offset); @@ -261,7 +261,7 @@ namespace ASC.Files.Thirdparty.SharePoint public File<string> SaveFile(File<string> file, Stream fileStream) { - if (fileStream == null) throw new ArgumentNullException("fileStream"); + if (fileStream == null) throw new ArgumentNullException(nameof(fileStream)); if (file.ID != null) { @@ -273,7 +273,7 @@ namespace ASC.Files.Thirdparty.SharePoint var folder = ProviderInfo.GetFolderById(file.FolderID); file.Title = GetAvailableTitle(file.Title, folder, IsExist); - var id = ProviderInfo.RenameFile(DaoSelector.ConvertId(resultFile.ID).ToString(), file.Title); + var id = ProviderInfo.RenameFile(DaoSelector.ConvertId(resultFile.ID), file.Title); return GetFile(DaoSelector.ConvertId(id)); } return resultFile; diff --git a/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointProviderInfo.cs b/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointProviderInfo.cs index 9c57234b6c..bcdb7d7323 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointProviderInfo.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/SharePoint/SharePointProviderInfo.cs @@ -60,8 +60,7 @@ namespace ASC.Files.Thirdparty.SharePoint public DateTime CreateOn { get; set; } public string CustomerTitle { get; set; } public string RootFolderId { get { return "spoint-" + ID; } } - - public string SpRootFolderId = "/Shared Documents"; + public string SpRootFolderId { get; set; } = "/Shared Documents"; public SharePointProviderInfo( IOptionsMonitor<ILog> options, @@ -114,7 +113,7 @@ namespace ASC.Files.Thirdparty.SharePoint if (authData.Login.EndsWith("onmicrosoft.com")) { - var personalPath = string.Concat("/personal/", authData.Login.Replace("@", "_").Replace(".", "_").ToLower()); + var personalPath = string.Concat("/personal/", authData.Login.Replace('@', '_').Replace('.', '_').ToLower()); SpRootFolderId = string.Concat(personalPath, "/Documents"); var ss = new SecureString(); @@ -166,7 +165,7 @@ namespace ASC.Files.Thirdparty.SharePoint { SharePointProviderInfoHelper.PublishFolder(MakeId(GetParentFolderId(id))); var serverException = (ServerException)ex; - if (serverException.ServerErrorTypeName == (typeof(FileNotFoundException)).ToString()) + if (serverException.ServerErrorTypeName == typeof(FileNotFoundException).ToString()) { return null; } @@ -375,7 +374,7 @@ namespace ASC.Files.Thirdparty.SharePoint private Folder GetFolder(object id) { - if ((string)id == "") id = SpRootFolderId; + if (((string)id).Length == 0) id = SpRootFolderId; var folder = clientContext.Web.GetFolderByServerRelativeUrl((string)id); clientContext.Load(folder); clientContext.Load(folder.Files, collection => collection.IncludeWithDefaultProperties(r => r.ListItemAllFields)); @@ -389,7 +388,7 @@ namespace ASC.Files.Thirdparty.SharePoint { SharePointProviderInfoHelper.PublishFolder(MakeId(GetParentFolderId(id))); var serverException = (ServerException)ex; - if (serverException.ServerErrorTypeName == (typeof(FileNotFoundException)).ToString()) + if (serverException.ServerErrorTypeName == typeof(FileNotFoundException).ToString()) { return null; } @@ -455,17 +454,31 @@ namespace ASC.Files.Thirdparty.SharePoint var newFolder = CreateFolder(newUrl); if (delete) - { - folder.Folders.ToList().ForEach(r => MoveFolder(r.ServerRelativeUrl, newUrl)); - folder.Files.ToList().ForEach(r => MoveFile(r.ServerRelativeUrl, newUrl)); + { + foreach (var f in folder.Folders) + { + MoveFolder(f.ServerRelativeUrl, newUrl); + } + + foreach (var f in folder.Files) + { + MoveFile(f.ServerRelativeUrl, newUrl); + } folder.DeleteObject(); clientContext.ExecuteQuery(); } else - { - folder.Folders.ToList().ForEach(r => CopyFolder(r.ServerRelativeUrl, newUrl)); - folder.Files.ToList().ForEach(r => CopyFile(r.ServerRelativeUrl, newUrl)); + { + foreach (var f in folder.Folders) + { + CopyFolder(f.ServerRelativeUrl, newUrl); + } + + foreach(var f in folder.Files) + { + CopyFile(f.ServerRelativeUrl, newUrl); + } } return newFolder; @@ -548,8 +561,9 @@ namespace ASC.Files.Thirdparty.SharePoint public string MakeId(string path = "") { - path = path.Replace(SpRootFolderId, ""); - return string.Format("{0}{1}", "spoint-" + ID, string.IsNullOrEmpty(path) || path == "/" || path == SpRootFolderId ? "" : ("-" + path.Replace('/', '|'))); + path = path.Replace(SpRootFolderId, ""); + var p = string.IsNullOrEmpty(path) || path == "/" || path == SpRootFolderId ? "" : ("-" + path.Replace('/', '|')); + return $"{ID}{p}"; } private string MakeId(object path) diff --git a/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxDaoBase.cs b/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxDaoBase.cs index 3cdc336b54..a6a4f51077 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxDaoBase.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxDaoBase.cs @@ -53,7 +53,7 @@ namespace ASC.Files.Thirdparty.Sharpbox { protected override string Id { get => "sbox"; } - public SharpBoxDaoBase(IServiceProvider serviceProvider, UserManager userManager, TenantManager tenantManager, TenantUtil tenantUtil, DbContextManager<FilesDbContext> dbContextManager, SetupInfo setupInfo, IOptionsMonitor<ILog> monitor, FileUtility fileUtility, TempPath tempPath) + protected SharpBoxDaoBase(IServiceProvider serviceProvider, UserManager userManager, TenantManager tenantManager, TenantUtil tenantUtil, DbContextManager<FilesDbContext> dbContextManager, SetupInfo setupInfo, IOptionsMonitor<ILog> monitor, FileUtility fileUtility, TempPath tempPath) : base(serviceProvider, userManager, tenantManager, tenantUtil, dbContextManager, setupInfo, monitor, fileUtility, tempPath) { } @@ -214,7 +214,7 @@ namespace ASC.Files.Thirdparty.Sharpbox protected string MakePath(object entryId) { - return string.Format("/{0}", Convert.ToString(entryId, CultureInfo.InvariantCulture).Trim('/')); + return $"/{Convert.ToString(entryId, CultureInfo.InvariantCulture).Trim('/')}"; } protected override string MakeId(string path = null) @@ -240,8 +240,8 @@ namespace ASC.Files.Thirdparty.Sharpbox { path = entry.Id; } - - return string.Format("{0}{1}", PathPrefix, string.IsNullOrEmpty(path) || path == "/" ? "" : ("-" + path.Replace('/', '|'))); + var p = string.IsNullOrEmpty(path) || path == "/" ? "" : ("-" + path.Replace('/', '|')); + return $"{PathPrefix}{p}"; } protected string MakeTitle(ICloudFileSystemEntry fsEntry) @@ -433,7 +433,7 @@ namespace ASC.Files.Thirdparty.Sharpbox protected IEnumerable<ICloudFileSystemEntry> GetFolderSubfolders(ICloudDirectoryEntry folder) { - return folder.Where(x => (x is ICloudDirectoryEntry)); + return folder.Where(x => x is ICloudDirectoryEntry); } protected string GetAvailableTitle(string requestTitle, ICloudDirectoryEntry parentFolder, Func<string, ICloudDirectoryEntry, bool> isExist) @@ -446,9 +446,9 @@ namespace ASC.Files.Thirdparty.Sharpbox if (!match.Success) { var insertIndex = requestTitle.Length; - if (requestTitle.LastIndexOf(".", StringComparison.InvariantCulture) != -1) + if (requestTitle.LastIndexOf('.') != -1) { - insertIndex = requestTitle.LastIndexOf(".", StringComparison.InvariantCulture); + insertIndex = requestTitle.LastIndexOf('.'); } requestTitle = requestTitle.Insert(insertIndex, " (1)"); } @@ -467,7 +467,7 @@ namespace ASC.Files.Thirdparty.Sharpbox return subFolders.Concat(files); } - private static string MatchEvaluator(Match match) + private string MatchEvaluator(Match match) { var index = Convert.ToInt32(match.Groups[2].Value); var staticText = match.Value.Substring(string.Format(" ({0})", index).Length); diff --git a/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxDaoSelector.cs b/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxDaoSelector.cs index 7caba01af8..b9ab818ed1 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxDaoSelector.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxDaoSelector.cs @@ -64,7 +64,7 @@ namespace ASC.Files.Thirdparty.Sharpbox } } - public class SharpBoxDaoSelectorExtension + public static class SharpBoxDaoSelectorExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxFileDao.cs b/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxFileDao.cs index e3b4ee12e7..1fc3734fb3 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxFileDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxFileDao.cs @@ -100,7 +100,7 @@ namespace ASC.Files.Thirdparty.Sharpbox return ToFile(GetFolderFiles(parentId).FirstOrDefault(item => item.Name.Equals(title, StringComparison.InvariantCultureIgnoreCase))); } - public File<string> GetFileStable(string fileId, int fileVersion) + public File<string> GetFileStable(string fileId, int fileVersion = -1) { return ToFile(GetFileById(fileId)); } @@ -151,8 +151,8 @@ namespace ASC.Files.Thirdparty.Sharpbox case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -216,8 +216,8 @@ namespace ASC.Files.Thirdparty.Sharpbox case FilterType.MediaOnly: files = files.Where(x => { - FileType fileType; - return (fileType = FileUtility.GetFileTypeByFileName(x.Title)) == FileType.Audio || fileType == FileType.Video; + FileType fileType = FileUtility.GetFileTypeByFileName(x.Title); + return fileType == FileType.Audio || fileType == FileType.Video; }); break; case FilterType.ByExtension: @@ -250,7 +250,7 @@ namespace ASC.Files.Thirdparty.Sharpbox var fileToDownload = GetFileById(file.ID); if (fileToDownload == null) - throw new ArgumentNullException("file", FilesCommonResource.ErrorMassage_FileNotFound); + throw new ArgumentNullException(nameof(file), FilesCommonResource.ErrorMassage_FileNotFound); if (fileToDownload is ErrorEntry errorEntry) throw new Exception(errorEntry.Error); @@ -293,7 +293,7 @@ namespace ASC.Files.Thirdparty.Sharpbox public File<string> SaveFile(File<string> file, Stream fileStream) { - if (fileStream == null) throw new ArgumentNullException("fileStream"); + if (fileStream == null) throw new ArgumentNullException(nameof(fileStream)); ICloudFileSystemEntry entry = null; if (file.ID != null) { @@ -320,7 +320,7 @@ namespace ASC.Files.Thirdparty.Sharpbox var webException = (WebException)e.InnerException; if (webException != null) { - var response = ((HttpWebResponse)webException.Response); + var response = (HttpWebResponse)webException.Response; if (response != null) { if (response.StatusCode == HttpStatusCode.Unauthorized || response.StatusCode == HttpStatusCode.Forbidden) @@ -494,7 +494,7 @@ namespace ASC.Files.Thirdparty.Sharpbox var entry = GetFileById(file.ID); if (entry == null) - throw new ArgumentNullException("file", FilesCommonResource.ErrorMassage_FileNotFound); + throw new ArgumentNullException(nameof(file), FilesCommonResource.ErrorMassage_FileNotFound); var oldFileId = MakeId(entry); var newFileId = oldFileId; diff --git a/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxFolderDao.cs b/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxFolderDao.cs index b398dbcdb9..bc027d786f 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxFolderDao.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxFolderDao.cs @@ -205,7 +205,7 @@ namespace ASC.Files.Thirdparty.Sharpbox var webException = (WebException)e.InnerException; if (webException != null) { - var response = ((HttpWebResponse)webException.Response); + var response = (HttpWebResponse)webException.Response; if (response != null) { if (response.StatusCode == HttpStatusCode.Unauthorized || response.StatusCode == HttpStatusCode.Forbidden) @@ -450,7 +450,7 @@ namespace ASC.Files.Thirdparty.Sharpbox return false; } - public long GetMaxUploadSize(string folderId, bool chunkedUpload) + public long GetMaxUploadSize(string folderId, bool chunkedUpload = false) { var storageMaxUploadSize = chunkedUpload diff --git a/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxProviderInfo.cs b/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxProviderInfo.cs index b8f1a4b192..6234ca6a48 100644 --- a/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxProviderInfo.cs +++ b/products/ASC.Files/Core/Core/Thirdparty/Sharpbox/SharpBoxProviderInfo.cs @@ -141,7 +141,7 @@ namespace ASC.Files.Thirdparty.Sharpbox internal CloudStorage CreateStorage(AuthData _authData, nSupportedCloudConfigurations _providerKey) { - var prms = new object[] { }; + var prms = Array.Empty<object>(); if (!string.IsNullOrEmpty(_authData.Url)) { var uri = _authData.Url; diff --git a/products/ASC.Files/Core/Helpers/DocuSignHelper.cs b/products/ASC.Files/Core/Helpers/DocuSignHelper.cs index 2246221241..a54f8ca466 100644 --- a/products/ASC.Files/Core/Helpers/DocuSignHelper.cs +++ b/products/ASC.Files/Core/Helpers/DocuSignHelper.cs @@ -99,7 +99,7 @@ namespace ASC.Web.Files.Helpers public void SaveToken(OAuth20Token token) { - if (token == null) throw new ArgumentNullException("token"); + if (token == null) throw new ArgumentNullException(nameof(token)); TokenHelper.SaveToken(new Token(token, AppAttr)); } @@ -149,9 +149,9 @@ namespace ASC.Web.Files.Helpers ".csv", ".et", ".ett", ".xls", ".xlsm", ".xlsx", ".xlt" }; - public static long MaxFileSize = 25L * 1024L * 1024L; + public static readonly long MaxFileSize = 25L * 1024L * 1024L; - public static int MaxEmailLength = 10000; + public static readonly int MaxEmailLength = 10000; private DocuSignToken DocuSignToken { get; } private FileSecurity FileSecurity { get; } @@ -207,7 +207,7 @@ namespace ASC.Web.Files.Helpers public string SendDocuSign<T>(T fileId, DocuSignData docuSignData, IDictionary<string, StringValues> requestHeaders) { - if (docuSignData == null) throw new ArgumentNullException("docuSignData"); + if (docuSignData == null) throw new ArgumentNullException(nameof(docuSignData)); var token = DocuSignToken.GetToken(); var account = GetDocuSignAccount(token); @@ -223,7 +223,7 @@ namespace ASC.Web.Files.Helpers private DocuSignAccount GetDocuSignAccount(OAuth20Token token) { - if (token == null) throw new ArgumentNullException("token"); + if (token == null) throw new ArgumentNullException(nameof(token)); var userInfoString = RequestHelper.PerformRequest(ConsumerFactory.Get<DocuSignLoginProvider>().DocuSignHost + "/oauth/userinfo", headers: new Dictionary<string, string> { { "Authorization", "Bearer " + DocuSignToken.GetRefreshedToken(token) } }); @@ -240,8 +240,8 @@ namespace ASC.Web.Files.Helpers private DocuSign.eSign.Client.Configuration GetConfiguration(DocuSignAccount account, OAuth20Token token) { - if (account == null) throw new ArgumentNullException("account"); - if (token == null) throw new ArgumentNullException("token"); + if (account == null) throw new ArgumentNullException(nameof(account)); + if (token == null) throw new ArgumentNullException(nameof(token)); var apiClient = new ApiClient(account.BaseUri + "/restapi"); @@ -302,9 +302,9 @@ namespace ASC.Web.Files.Helpers { //new EnvelopeEvent {EnvelopeEventStatusCode = DocuSignStatus.Sent.ToString()}, //new EnvelopeEvent {EnvelopeEventStatusCode = DocuSignStatus.Delivered.ToString()}, - new EnvelopeEvent {EnvelopeEventStatusCode = DocuSignStatus.Completed.ToString()}, - new EnvelopeEvent {EnvelopeEventStatusCode = DocuSignStatus.Declined.ToString()}, - new EnvelopeEvent {EnvelopeEventStatusCode = DocuSignStatus.Voided.ToString()}, + new EnvelopeEvent {EnvelopeEventStatusCode = nameof(DocuSignStatus.Completed)}, + new EnvelopeEvent {EnvelopeEventStatusCode = nameof(DocuSignStatus.Declined)}, + new EnvelopeEvent {EnvelopeEventStatusCode = nameof(DocuSignStatus.Voided)}, }, IncludeDocumentFields = "true", //RecipientEvents = new List<RecipientEvent> @@ -377,8 +377,8 @@ namespace ASC.Web.Files.Helpers public File<T> SaveDocument<T>(string envelopeId, string documentId, string documentName, T folderId) { - if (string.IsNullOrEmpty(envelopeId)) throw new ArgumentNullException("envelopeId"); - if (string.IsNullOrEmpty(documentId)) throw new ArgumentNullException("documentId"); + if (string.IsNullOrEmpty(envelopeId)) throw new ArgumentNullException(nameof(envelopeId)); + if (string.IsNullOrEmpty(documentId)) throw new ArgumentNullException(nameof(documentId)); var token = DocuSignToken.GetToken(); var account = GetDocuSignAccount(token); diff --git a/products/ASC.Files/Core/Helpers/EasyBibHelper.cs b/products/ASC.Files/Core/Helpers/EasyBibHelper.cs index 8a2bbd69eb..c722e4d8c9 100644 --- a/products/ASC.Files/Core/Helpers/EasyBibHelper.cs +++ b/products/ASC.Files/Core/Helpers/EasyBibHelper.cs @@ -141,7 +141,7 @@ namespace ASC.Web.Files.Helpers jsonBlogInfo.Add("key", easyBibappkey); var citationData = jsonBlogInfo.ToString(); - var uri = "https://api.citation-api.com/2.0/rest/cite"; + const string uri = "https://api.citation-api.com/2.0/rest/cite"; const string contentType = "application/json"; const string method = "POST"; var body = citationData; diff --git a/products/ASC.Files/Core/Helpers/Global.cs b/products/ASC.Files/Core/Helpers/Global.cs index f2a0fb6577..d3d6786b1d 100644 --- a/products/ASC.Files/Core/Helpers/Global.cs +++ b/products/ASC.Files/Core/Helpers/Global.cs @@ -135,7 +135,7 @@ namespace ASC.Web.Files.Classes #region Property - public string ThumbnailExtension; + public string ThumbnailExtension { get; set; } public const int MaxTitle = 170; diff --git a/products/ASC.Files/Core/Helpers/PathProvider.cs b/products/ASC.Files/Core/Helpers/PathProvider.cs index 9ea4dbaf0a..4d1559b971 100644 --- a/products/ASC.Files/Core/Helpers/PathProvider.cs +++ b/products/ASC.Files/Core/Helpers/PathProvider.cs @@ -107,7 +107,7 @@ namespace ASC.Web.Files.Classes public string GetFolderUrl<T>(Folder<T> folder, int projectID = 0) { - if (folder == null) throw new ArgumentNullException("folder", FilesCommonResource.ErrorMassage_FolderNotFound); + if (folder == null) throw new ArgumentNullException(nameof(folder), FilesCommonResource.ErrorMassage_FolderNotFound); var folderDao = DaoFactory.GetFolderDao<T>(); @@ -139,7 +139,7 @@ namespace ASC.Web.Files.Classes public string GetFileStreamUrl<T>(File<T> file, string doc = null, bool lastVersion = false) { - if (file == null) throw new ArgumentNullException("file", FilesCommonResource.ErrorMassage_FileNotFound); + if (file == null) throw new ArgumentNullException(nameof(file), FilesCommonResource.ErrorMassage_FileNotFound); //NOTE: Always build path to handler! var uriBuilder = new UriBuilder(CommonLinkUtility.GetFullAbsolutePath(FilesLinkUtility.FileHandlerPath)); @@ -163,7 +163,7 @@ namespace ASC.Web.Files.Classes public string GetFileChangesUrl<T>(File<T> file, string doc = null) { - if (file == null) throw new ArgumentNullException("file", FilesCommonResource.ErrorMassage_FileNotFound); + if (file == null) throw new ArgumentNullException(nameof(file), FilesCommonResource.ErrorMassage_FileNotFound); var uriBuilder = new UriBuilder(CommonLinkUtility.GetFullAbsolutePath(FilesLinkUtility.FileHandlerPath)); var query = uriBuilder.Query; @@ -181,7 +181,7 @@ namespace ASC.Web.Files.Classes public string GetTempUrl(Stream stream, string ext) { - if (stream == null) throw new ArgumentNullException("stream"); + if (stream == null) throw new ArgumentNullException(nameof(stream)); var store = GlobalStore.GetStore(); var fileName = string.Format("{0}{1}", Guid.NewGuid(), ext); diff --git a/products/ASC.Files/Core/Helpers/ThirdpartyConfiguration.cs b/products/ASC.Files/Core/Helpers/ThirdpartyConfiguration.cs index 201f663950..32f1fbaa4a 100644 --- a/products/ASC.Files/Core/Helpers/ThirdpartyConfiguration.cs +++ b/products/ASC.Files/Core/Helpers/ThirdpartyConfiguration.cs @@ -26,7 +26,6 @@ using System; using System.Collections.Generic; -using System.Linq; using ASC.Common; using ASC.Core.Common.Configuration; @@ -47,7 +46,7 @@ namespace ASC.Web.Files.Helpers { get { - return thirdPartyProviders ??= (Configuration.GetSection("files:thirdparty:enable").Get<string[]>() ?? new string[] { }).ToList(); + return thirdPartyProviders ??= Configuration.GetSection("files:thirdparty:enable").Get<List<string>>() ?? new List<string>(); } } public ThirdpartyConfigurationData(IConfiguration configuration) diff --git a/products/ASC.Files/Core/Helpers/WordpressHelper.cs b/products/ASC.Files/Core/Helpers/WordpressHelper.cs index b0908e05ff..21e1881891 100644 --- a/products/ASC.Files/Core/Helpers/WordpressHelper.cs +++ b/products/ASC.Files/Core/Helpers/WordpressHelper.cs @@ -61,7 +61,7 @@ namespace ASC.Web.Files.Helpers public void SaveToken(OAuth20Token token) { - if (token == null) throw new ArgumentNullException("token"); + if (token == null) throw new ArgumentNullException(nameof(token)); TokenHelper.SaveToken(new Token(token, AppAttr)); } @@ -75,7 +75,7 @@ namespace ASC.Web.Files.Helpers public void DeleteToken(OAuth20Token token) { - if (token == null) throw new ArgumentNullException("token"); + if (token == null) throw new ArgumentNullException(nameof(token)); TokenHelper.DeleteToken(AppAttr); } diff --git a/products/ASC.Files/Core/HttpHandlers/ChunkedUploaderHandler.cs b/products/ASC.Files/Core/HttpHandlers/ChunkedUploaderHandler.cs index 4e4b65d019..e507a814cd 100644 --- a/products/ASC.Files/Core/HttpHandlers/ChunkedUploaderHandler.cs +++ b/products/ASC.Files/Core/HttpHandlers/ChunkedUploaderHandler.cs @@ -385,7 +385,7 @@ namespace ASC.Web.Files.HttpHandlers public ChunkedRequestHelper(HttpRequest request) { - _request = request ?? throw new ArgumentNullException("request"); + _request = request ?? throw new ArgumentNullException(nameof(request)); } private bool IsAuthDataSet(InstanceCrypto instanceCrypto) diff --git a/products/ASC.Files/Core/HttpHandlers/FileHandler.ashx.cs b/products/ASC.Files/Core/HttpHandlers/FileHandler.ashx.cs index 51a139dc6b..618161336a 100644 --- a/products/ASC.Files/Core/HttpHandlers/FileHandler.ashx.cs +++ b/products/ASC.Files/Core/HttpHandlers/FileHandler.ashx.cs @@ -41,6 +41,7 @@ using ASC.Common.Logging; using ASC.Common.Utils; using ASC.Common.Web; using ASC.Core; +using ASC.Data.Storage; using ASC.Files.Core; using ASC.Files.Core.Resources; using ASC.Files.Core.Security; @@ -120,6 +121,7 @@ namespace ASC.Web.Files public TempStream TempStream { get; } private UserManager UserManager { get; } private ILog Logger { get; } + private IHttpClientFactory ClientFactory { get; } public FileHandlerService( FilesLinkUtility filesLinkUtility, @@ -146,7 +148,8 @@ namespace ASC.Web.Files FileConverter fileConverter, FFmpegService fFmpegService, IServiceProvider serviceProvider, - TempStream tempStream) + TempStream tempStream, + IHttpClientFactory clientFactory) { FilesLinkUtility = filesLinkUtility; TenantExtra = tenantExtra; @@ -172,17 +175,23 @@ namespace ASC.Web.Files TempStream = tempStream; UserManager = userManager; Logger = optionsMonitor.CurrentValue; + ClientFactory = clientFactory; } - public async Task Invoke(HttpContext context) + public Task Invoke(HttpContext context) { if (TenantExtra.IsNotPaid()) { context.Response.StatusCode = (int)HttpStatusCode.PaymentRequired; //context.Response.StatusDescription = "Payment Required."; - return; + return Task.CompletedTask; } + return InternalInvoke(context); + } + + private async Task InternalInvoke(HttpContext context) + { try { switch ((context.Request.Query[FilesLinkUtility.Action].FirstOrDefault() ?? "").ToLower()) @@ -229,12 +238,12 @@ namespace ASC.Web.Files } } - private async Task BulkDownloadFile(HttpContext context) + private Task BulkDownloadFile(HttpContext context) { if (!SecurityContext.IsAuthenticated) { context.Response.StatusCode = (int)HttpStatusCode.Forbidden; - return; + return Task.CompletedTask; } var ext = CompressToArchive.GetExt(ServiceProvider, context.Request.Query["ext"]); @@ -245,32 +254,36 @@ namespace ASC.Web.Files { Logger.ErrorFormat("BulkDownload file error. File is not exist on storage. UserId: {0}.", AuthContext.CurrentAccount.ID); context.Response.StatusCode = (int)HttpStatusCode.NotFound; - return; + return Task.CompletedTask; } if (store.IsSupportedPreSignedUri) { var url = store.GetPreSignedUri(FileConstant.StorageDomainTmp, path, TimeSpan.FromHours(1), null).ToString(); context.Response.Redirect(url); - return; + return Task.CompletedTask; } context.Response.Clear(); + return InternalBulkDownloadFile(context, store, path, ext); + } + private async Task InternalBulkDownloadFile(HttpContext context, IDataStore store, string path, string ext) + { try - { + { var flushed = false; using (var readStream = store.GetReadStream(FileConstant.StorageDomainTmp, path)) { - long offset = 0; + long offset = 0; var length = readStream.Length; if (readStream.CanSeek) - { + { length = ProcessRangeHeader(context, readStream.Length, ref offset); readStream.Seek(offset, SeekOrigin.Begin); - } - - flushed = await SendStreamByChunksAsync(context, length, FileConstant.DownloadTitle + ext, readStream, flushed); + } + + await SendStreamByChunksAsync(context, length, FileConstant.DownloadTitle + ext, readStream, flushed); } await context.Response.Body.FlushAsync(); @@ -522,7 +535,7 @@ namespace ASC.Web.Files var range = context.Request.Headers["Range"].FirstOrDefault().Split(new[] { '=', '-' }); offset = Convert.ToInt64(range[1]); - if (range.Count() > 2 && !string.IsNullOrEmpty(range[2])) + if (range.Length > 2 && !string.IsNullOrEmpty(range[2])) { endOffset = Convert.ToInt64(range[2]); } @@ -1005,7 +1018,7 @@ namespace ASC.Web.Files context.Response.Headers.Add("Content-Disposition", ContentDispositionUtil.GetHeaderValue("." + Global.ThumbnailExtension)); context.Response.ContentType = MimeMapping.GetMimeMapping("." + Global.ThumbnailExtension); - using (var stream = await fileDao.GetThumbnailAsync(file)) + using (var stream = await fileDao.GetThumbnailAsync(file)) { context.Response.Headers.Add("Content-Length", stream.Length.ToString(CultureInfo.InvariantCulture)); await stream.CopyToAsync(context.Response.Body); @@ -1042,18 +1055,23 @@ namespace ASC.Web.Files return file.ID + ":" + file.Version + ":" + file.Title.GetHashCode() + ":" + file.ContentLength; } - private async Task CreateFile(HttpContext context) + private Task CreateFile(HttpContext context) { if (!SecurityContext.IsAuthenticated) { //var refererURL = context.Request.GetUrlRewriter().AbsoluteUri; //context.Session["refererURL"] = refererURL; - var authUrl = "~/Auth.aspx"; + const string authUrl = "~/Auth.aspx"; context.Response.Redirect(authUrl, true); - return; + return Task.CompletedTask; } + return InternalCreateFile(context); + } + + private async Task InternalCreateFile(HttpContext context) + { var folderId = context.Request.Query[FilesLinkUtility.FolderId].FirstOrDefault(); if (string.IsNullOrEmpty(folderId)) { @@ -1072,9 +1090,10 @@ namespace ASC.Web.Files } } - private async Task CreateFile<T>(HttpContext context, T folderId) + private Task CreateFile<T>(HttpContext context, T folderId) { var responseMessage = context.Request.Query["response"] == "message"; + Folder<T> folder; var folderDao = DaoFactory.GetFolderDao<T>(); @@ -1100,32 +1119,44 @@ namespace ASC.Web.Files } catch (Exception ex) { - Logger.Error(ex); - if (responseMessage) - { - await context.Response.WriteAsync("error: " + ex.Message); - return; - } - context.Response.Redirect(PathProvider.StartURL + "#error/" + HttpUtility.UrlEncode(ex.Message), true); - return; + return InternalWriteError(context, ex, responseMessage); } FileMarker.MarkAsNew(file); if (responseMessage) { - var message = string.Format(FilesCommonResource.MessageFileCreated, folder.Title); - if (FileUtility.CanWebRestrictedEditing(file.Title)) - message = string.Format(FilesCommonResource.MessageFileCreatedForm, folder.Title); - - await context.Response.WriteAsync("ok: " + message); - return; + return InternalWriteOk(context, folder, file); } context.Response.Redirect( (context.Request.Query["openfolder"].FirstOrDefault() ?? "").Equals("true") ? PathProvider.GetFolderUrlById(file.FolderID) : (FilesLinkUtility.GetFileWebEditorUrl(file.ID) + "#message/" + HttpUtility.UrlEncode(string.Format(FilesCommonResource.MessageFileCreated, folder.Title)))); + + return Task.CompletedTask; + } + + private async Task InternalWriteError(HttpContext context, Exception ex, bool responseMessage) + { + Logger.Error(ex); + + if (responseMessage) + { + await context.Response.WriteAsync("error: " + ex.Message); + return; + } + context.Response.Redirect(PathProvider.StartURL + "#error/" + HttpUtility.UrlEncode(ex.Message), true); + return; + } + + private async Task InternalWriteOk<T>(HttpContext context, Folder<T> folder, File<T> file) + { + var message = string.Format(FilesCommonResource.MessageFileCreated, folder.Title); + if (FileUtility.CanWebRestrictedEditing(file.Title)) + message = string.Format(FilesCommonResource.MessageFileCreatedForm, folder.Title); + + await context.Response.WriteAsync("ok: " + message); } private File<T> CreateFileFromTemplate<T>(Folder<T> folder, string fileTitle, string docType) @@ -1183,17 +1214,9 @@ namespace ASC.Web.Files var request = new HttpRequestMessage(); request.RequestUri = new Uri(fileUri); - // hack. http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono) - { - ServicePointManager.ServerCertificateValidationCallback += (s, ce, ca, p) => true; - } - - - - var fileDao = DaoFactory.GetFileDao<T>(); - using var httpClient = new HttpClient(); - using var response = httpClient.Send(request); + var fileDao = DaoFactory.GetFileDao<T>(); + var httpClient = ClientFactory.CreateClient(); + using var response = httpClient.Send(request); using var fileStream = httpClient.Send(request).Content.ReadAsStream(); if (fileStream.CanSeek) @@ -1278,7 +1301,7 @@ namespace ASC.Web.Files } } - private async Task TrackFile<T>(HttpContext context, T fileId) + private Task TrackFile<T>(HttpContext context, T fileId) { var auth = context.Request.Query[FilesLinkUtility.AuthKey].FirstOrDefault(); Logger.Debug("DocService track fileid: " + fileId); @@ -1291,6 +1314,11 @@ namespace ASC.Web.Files throw new HttpException((int)HttpStatusCode.Forbidden, FilesCommonResource.ErrorMassage_SecurityException); } + return InternalTrackFile(context, fileId); + } + + private async Task InternalTrackFile<T>(HttpContext context, T fileId) + { DocumentServiceTracker.TrackerData fileData; try { diff --git a/products/ASC.Files/Core/HttpHandlers/SearchHandler.cs b/products/ASC.Files/Core/HttpHandlers/SearchHandler.cs index 072cb6a981..7ff59c49aa 100644 --- a/products/ASC.Files/Core/HttpHandlers/SearchHandler.cs +++ b/products/ASC.Files/Core/HttpHandlers/SearchHandler.cs @@ -115,12 +115,12 @@ namespace ASC.Web.Files.Configuration var id = GlobalFolderHelper.FolderMy; if (!Equals(id, 0)) { - var folderMy = folderDao.GetFolder(id); + //var folderMy = folderDao.GetFolder(id); //result = result.Concat(EntryManager.GetThirpartyFolders(folderMy, text)); } - id = GlobalFolderHelper.FolderCommon; - var folderCommon = folderDao.GetFolder(id); + //id = GlobalFolderHelper.FolderCommon; + //var folderCommon = folderDao.GetFolder(id); //result = result.Concat(EntryManager.GetThirpartyFolders(folderCommon, text)); } @@ -143,7 +143,7 @@ namespace ASC.Web.Files.Configuration Additional = new Dictionary<string, object> { { "Author", file.CreateByString.HtmlEncode() }, - { "Path", FolderPathBuilder<int>(EntryManager.GetBreadCrumbs(file.FolderID, folderDao)) }, + { "Path", FolderPathBuilder(EntryManager.GetBreadCrumbs(file.FolderID, folderDao)) }, { "Size", FileSizeComment.FilesSizeToString(file.ContentLength) } } }; @@ -162,7 +162,7 @@ namespace ASC.Web.Files.Configuration Additional = new Dictionary<string, object> { { "Author", folder.CreateByString.HtmlEncode() }, - { "Path", FolderPathBuilder<int>(EntryManager.GetBreadCrumbs(folder.ID, folderDao)) }, + { "Path", FolderPathBuilder(EntryManager.GetBreadCrumbs(folder.ID, folderDao)) }, { "IsFolder", true } } }; @@ -172,7 +172,7 @@ namespace ASC.Web.Files.Configuration return list.ToArray(); } - private static string FolderPathBuilder<T>(IEnumerable<FileEntry> folders) + private static string FolderPathBuilder(IEnumerable<FileEntry> folders) { var titles = folders.Select(f => f.Title).ToList(); const string separator = " \\ "; diff --git a/products/ASC.Files/Core/HttpHandlers/ThirdPartyAppHandler.ashx.cs b/products/ASC.Files/Core/HttpHandlers/ThirdPartyAppHandler.ashx.cs index 129d7e1c0e..d16a341629 100644 --- a/products/ASC.Files/Core/HttpHandlers/ThirdPartyAppHandler.ashx.cs +++ b/products/ASC.Files/Core/HttpHandlers/ThirdPartyAppHandler.ashx.cs @@ -115,7 +115,7 @@ namespace ASC.Web.Files.HttpHandlers if (string.IsNullOrEmpty(message)) { - if ((context.Request.Query["error"].FirstOrDefault() ?? "").ToLower() == "access_denied") + if ((context.Request.Query["error"].FirstOrDefault() ?? "").Equals("access_denied", StringComparison.InvariantCultureIgnoreCase)) { message = context.Request.Query["error_description"].FirstOrDefault() ?? FilesCommonResource.AppAccessDenied; } diff --git a/products/ASC.Files/Core/Model/Binders.cs b/products/ASC.Files/Core/Model/Binders.cs index 98caa72046..291a7b29fc 100644 --- a/products/ASC.Files/Core/Model/Binders.cs +++ b/products/ASC.Files/Core/Model/Binders.cs @@ -57,7 +57,7 @@ namespace ASC.Files.Model return valueProviderResult.Select(ParseQueryParam).ToList(); } - if (modelName.EndsWith("[]")) + if (modelName.EndsWith("[]", StringComparison.Ordinal)) { return new List<JsonElement>(); } @@ -197,7 +197,7 @@ namespace ASC.Files.Model var defaultBindingContext = bindingContext as DefaultModelBindingContext; var composite = bindingContext.ValueProvider as CompositeValueProvider; - if (defaultBindingContext != null && composite != null && !composite.Any()) + if (defaultBindingContext != null && composite != null && composite.Count == 0) { bindingContext.ValueProvider = defaultBindingContext.OriginalValueProvider; } @@ -245,7 +245,7 @@ namespace ASC.Files.Model var defaultBindingContext = bindingContext as DefaultModelBindingContext; var composite = bindingContext.ValueProvider as CompositeValueProvider; - if (defaultBindingContext != null && composite != null && !composite.Any()) + if (defaultBindingContext != null && composite != null && composite.Count == 0) { bindingContext.ValueProvider = defaultBindingContext.OriginalValueProvider; } diff --git a/products/ASC.Files/Core/Model/FileWrapper.cs b/products/ASC.Files/Core/Model/FileWrapper.cs index 01188a16d7..f8dd184f96 100644 --- a/products/ASC.Files/Core/Model/FileWrapper.cs +++ b/products/ASC.Files/Core/Model/FileWrapper.cs @@ -135,7 +135,7 @@ namespace ASC.Api.Documents //Updated = ApiDateTime.GetSample(), //Created = ApiDateTime.GetSample(), //CreatedBy = EmployeeWraper.GetSample(), - Id = new Random().Next(), + Id = 10, RootFolderType = FolderType.BUNCH, Shared = false, Title = "Some titile.txt", diff --git a/products/ASC.Files/Core/Model/FolderWrapper.cs b/products/ASC.Files/Core/Model/FolderWrapper.cs index 55519827df..6d5738bde6 100644 --- a/products/ASC.Files/Core/Model/FolderWrapper.cs +++ b/products/ASC.Files/Core/Model/FolderWrapper.cs @@ -80,14 +80,14 @@ namespace ASC.Api.Documents //Updated = ApiDateTime.GetSample(), //Created = ApiDateTime.GetSample(), //CreatedBy = EmployeeWraper.GetSample(), - Id = new Random().Next(), + Id = 10, RootFolderType = FolderType.BUNCH, Shared = false, Title = "Some titile", //UpdatedBy = EmployeeWraper.GetSample(), - FilesCount = new Random().Next(), - FoldersCount = new Random().Next(), - ParentId = new Random().Next(), + FilesCount = 5, + FoldersCount = 7, + ParentId = 10, IsShareable = null }; } diff --git a/products/ASC.Files/Core/Services/DocumentService/Configuration.cs b/products/ASC.Files/Core/Services/DocumentService/Configuration.cs index bf5cea1755..2cb3ce3379 100644 --- a/products/ASC.Files/Core/Services/DocumentService/Configuration.cs +++ b/products/ASC.Files/Core/Services/DocumentService/Configuration.cs @@ -1,216 +1,213 @@ -/* - * - * (c) Copyright Ascensio System Limited 2010-2018 - * - * This program is freeware. You can redistribute it and/or modify it under the terms of the GNU - * General Public License (GPL) version 3 as published by the Free Software Foundation (https://www.gnu.org/copyleft/gpl.html). - * In accordance with Section 7(a) of the GNU GPL its Section 15 shall be amended to the effect that - * Ascensio System SIA expressly excludes the warranty of non-infringement of any third-party rights. - * - * THIS PROGRAM IS DISTRIBUTED WITHOUT ANY WARRANTY; WITHOUT EVEN THE IMPLIED WARRANTY OF MERCHANTABILITY OR - * FITNESS FOR A PARTICULAR PURPOSE. For more details, see GNU GPL at https://www.gnu.org/copyleft/gpl.html - * - * You can contact Ascensio System SIA by email at sales@onlyoffice.com - * - * The interactive user interfaces in modified source and object code versions of ONLYOFFICE must display - * Appropriate Legal Notices, as required under Section 5 of the GNU GPL version 3. - * - * Pursuant to Section 7 § 3(b) of the GNU GPL you must retain the original ONLYOFFICE logo which contains - * relevant author attributions when distributing the software. If the display of the logo in its graphic - * form is not reasonably feasible for technical reasons, you must include the words "Powered by ONLYOFFICE" - * in every copy of the program you distribute. - * Pursuant to Section 7 § 3(e) we decline to grant you any rights under trademark law for use of our trademarks. - * -*/ - - -using System; -using System.Collections.Generic; -using System.Globalization; -using System.IO; -using System.Linq; -using System.Text.Json; -using System.Text.Json.Serialization; -using System.Web; +/* + * + * (c) Copyright Ascensio System Limited 2010-2018 + * + * This program is freeware. You can redistribute it and/or modify it under the terms of the GNU + * General Public License (GPL) version 3 as published by the Free Software Foundation (https://www.gnu.org/copyleft/gpl.html). + * In accordance with Section 7(a) of the GNU GPL its Section 15 shall be amended to the effect that + * Ascensio System SIA expressly excludes the warranty of non-infringement of any third-party rights. + * + * THIS PROGRAM IS DISTRIBUTED WITHOUT ANY WARRANTY; WITHOUT EVEN THE IMPLIED WARRANTY OF MERCHANTABILITY OR + * FITNESS FOR A PARTICULAR PURPOSE. For more details, see GNU GPL at https://www.gnu.org/copyleft/gpl.html + * + * You can contact Ascensio System SIA by email at sales@onlyoffice.com + * + * The interactive user interfaces in modified source and object code versions of ONLYOFFICE must display + * Appropriate Legal Notices, as required under Section 5 of the GNU GPL version 3. + * + * Pursuant to Section 7 § 3(b) of the GNU GPL you must retain the original ONLYOFFICE logo which contains + * relevant author attributions when distributing the software. If the display of the logo in its graphic + * form is not reasonably feasible for technical reasons, you must include the words "Powered by ONLYOFFICE" + * in every copy of the program you distribute. + * Pursuant to Section 7 § 3(e) we decline to grant you any rights under trademark law for use of our trademarks. + * +*/ -using ASC.Common; -using ASC.Core; -using ASC.Core.Common; -using ASC.Core.Common.Configuration; -using ASC.Core.Common.Settings; -using ASC.Core.Users; -using ASC.FederatedLogin.LoginProviders; -using ASC.Files.Core; -using ASC.Files.Core.Resources; -using ASC.Files.Core.Security; -using ASC.Web.Core.Files; -using ASC.Web.Core.Users; -using ASC.Web.Core.WhiteLabel; -using ASC.Web.Files.Classes; -using ASC.Web.Files.Helpers; -using ASC.Web.Files.Services.WCFService; -using ASC.Web.Files.ThirdPartyApp; -using ASC.Web.Files.Utils; -using ASC.Web.Studio.Utility; -using Microsoft.Extensions.DependencyInjection; - -namespace ASC.Web.Files.Services.DocumentService -{ - public enum EditorType - { - Desktop, - Mobile, - Embedded, - External, - } - - public class Configuration<T> - { - internal static Dictionary<FileType, string> DocType = new Dictionary<FileType, string> - { - { FileType.Document, "text" }, - { FileType.Spreadsheet, "spreadsheet" }, - { FileType.Presentation, "presentation" } - }; - - private FileType _fileTypeCache = FileType.Unknown; - - public Configuration( - File<T> file, - IServiceProvider serviceProvider - ) - { - Document = serviceProvider.GetService<DocumentConfig<T>>(); - Document.Info.SetFile(file); - EditorConfig = serviceProvider.GetService<EditorConfiguration<T>>(); - EditorConfig.SetConfiguration(this); - } - - public EditorType EditorType - { - set { Document.Info.Type = value; } - get { return Document.Info.Type; } - } - - #region Property - - public DocumentConfig<T> Document { get; set; } - - public string DocumentType - { - set { } - get - { - DocType.TryGetValue(GetFileType, out var documentType); - return documentType; - } - } - - public EditorConfiguration<T> EditorConfig { get; set; } - - public string Token { get; set; } - - public string Type - { - set { EditorType = (EditorType)Enum.Parse(typeof(EditorType), value, true); } - get { return EditorType.ToString().ToLower(); } - } - - internal FileType GetFileType - { - set { } - get - { - if (_fileTypeCache == FileType.Unknown) - _fileTypeCache = FileUtility.GetFileTypeByFileName(Document.Info.GetFile().Title); - return _fileTypeCache; - } - } - - [JsonPropertyName("Error")] - public string ErrorMessage { get; set; } - - #endregion - - public static string Serialize(Configuration<T> configuration) - { - return JsonSerializer.Serialize(configuration); - } - } - #region Nested Classes +using System; +using System.Collections.Generic; +using System.Globalization; +using System.IO; +using System.Linq; +using System.Text.Json; +using System.Text.Json.Serialization; +using System.Web; - [Transient] - public class DocumentConfig<T> - { - public string SharedLinkKey; - - public DocumentConfig(DocumentServiceConnector documentServiceConnector, PathProvider pathProvider, InfoConfig<T> infoConfig) - { - Info = infoConfig; - Permissions = new PermissionsConfig(); - DocumentServiceConnector = documentServiceConnector; - PathProvider = pathProvider; - } - - private string _key = string.Empty; - private string _fileUri; - private string _title = null; - - - public string FileType - { - set { } - get { return Info.GetFile().ConvertedExtension.Trim('.'); } - } - - public InfoConfig<T> Info { get; set; } - - public string Key - { - set { _key = value; } - get { return DocumentServiceConnector.GenerateRevisionId(_key); } - } - - public PermissionsConfig Permissions { get; set; } - - public string Title - { - set { _title = value; } - get { return _title ?? Info.GetFile().Title; } - } - - public string Url - { - set { _fileUri = DocumentServiceConnector.ReplaceCommunityAdress(value); } - get - { - if (!string.IsNullOrEmpty(_fileUri)) - return _fileUri; - var last = Permissions.Edit || Permissions.Review || Permissions.Comment; - _fileUri = DocumentServiceConnector.ReplaceCommunityAdress(PathProvider.GetFileStreamUrl(Info.GetFile(), SharedLinkKey, last)); - return _fileUri; - } - } - - private DocumentServiceConnector DocumentServiceConnector { get; } - private PathProvider PathProvider { get; } - } +using ASC.Common; +using ASC.Core; +using ASC.Core.Common; +using ASC.Core.Common.Configuration; +using ASC.Core.Common.Settings; +using ASC.Core.Users; +using ASC.FederatedLogin.LoginProviders; +using ASC.Files.Core; +using ASC.Files.Core.Resources; +using ASC.Files.Core.Security; +using ASC.Web.Core.Files; +using ASC.Web.Core.Users; +using ASC.Web.Core.WhiteLabel; +using ASC.Web.Files.Classes; +using ASC.Web.Files.Helpers; +using ASC.Web.Files.Services.WCFService; +using ASC.Web.Files.ThirdPartyApp; +using ASC.Web.Files.Utils; +using ASC.Web.Studio.Utility; - [Transient] - public class InfoConfig<T> - { - private File<T> File; +using Microsoft.Extensions.DependencyInjection; + +namespace ASC.Web.Files.Services.DocumentService +{ + public enum EditorType + { + Desktop, + Mobile, + Embedded, + External, + } + + public class Configuration<T> + { + internal static readonly Dictionary<FileType, string> DocType = new Dictionary<FileType, string> + { + { FileType.Document, "text" }, + { FileType.Spreadsheet, "spreadsheet" }, + { FileType.Presentation, "presentation" } + }; + + private FileType _fileTypeCache = FileType.Unknown; + + public Configuration( + File<T> file, + IServiceProvider serviceProvider + ) + { + Document = serviceProvider.GetService<DocumentConfig<T>>(); + Document.Info.SetFile(file); + EditorConfig = serviceProvider.GetService<EditorConfiguration<T>>(); + EditorConfig.SetConfiguration(this); + } + + public EditorType EditorType + { + set { Document.Info.Type = value; } + get { return Document.Info.Type; } + } + + #region Property + + public DocumentConfig<T> Document { get; set; } + + public string DocumentType + { + get + { + DocType.TryGetValue(GetFileType, out var documentType); + return documentType; + } + } + + public EditorConfiguration<T> EditorConfig { get; set; } + + public string Token { get; set; } + + public string Type + { + set { EditorType = (EditorType)Enum.Parse(typeof(EditorType), value, true); } + get { return EditorType.ToString().ToLower(); } + } + + internal FileType GetFileType + { + get + { + if (_fileTypeCache == FileType.Unknown) + _fileTypeCache = FileUtility.GetFileTypeByFileName(Document.Info.GetFile().Title); + return _fileTypeCache; + } + } + + [JsonPropertyName("Error")] + public string ErrorMessage { get; set; } + + #endregion + + public static string Serialize(Configuration<T> configuration) + { + return JsonSerializer.Serialize(configuration); + } + } + #region Nested Classes + + [Transient] + public class DocumentConfig<T> + { + public string SharedLinkKey; + + public DocumentConfig(DocumentServiceConnector documentServiceConnector, PathProvider pathProvider, InfoConfig<T> infoConfig) + { + Info = infoConfig; + Permissions = new PermissionsConfig(); + DocumentServiceConnector = documentServiceConnector; + PathProvider = pathProvider; + } + + private string _key = string.Empty; + private string _fileUri; + private string _title = null; + + + public string FileType + { + get { return Info.GetFile().ConvertedExtension.Trim('.'); } + } + + public InfoConfig<T> Info { get; set; } + + public string Key + { + set { _key = value; } + get { return DocumentServiceConnector.GenerateRevisionId(_key); } + } + + public PermissionsConfig Permissions { get; set; } + + public string Title + { + set { _title = value; } + get { return _title ?? Info.GetFile().Title; } + } + + public string Url + { + set { _fileUri = DocumentServiceConnector.ReplaceCommunityAdress(value); } + get + { + if (!string.IsNullOrEmpty(_fileUri)) + return _fileUri; + var last = Permissions.Edit || Permissions.Review || Permissions.Comment; + _fileUri = DocumentServiceConnector.ReplaceCommunityAdress(PathProvider.GetFileStreamUrl(Info.GetFile(), SharedLinkKey, last)); + return _fileUri; + } + } + + private DocumentServiceConnector DocumentServiceConnector { get; } + private PathProvider PathProvider { get; } + } + + [Transient] + public class InfoConfig<T> + { + private File<T> File; public File<T> GetFile() => File; public void SetFile(File<T> file) => File = file; - - public EditorType Type = EditorType.Desktop; - private string _breadCrumbs; - - public InfoConfig(BreadCrumbsManager breadCrumbsManager, FileSharing fileSharing, SecurityContext securityContext, UserManager userManager) - { - BreadCrumbsManager = breadCrumbsManager; + + public EditorType Type { get; set; } = EditorType.Desktop; + private string _breadCrumbs; + + public InfoConfig(BreadCrumbsManager breadCrumbsManager, FileSharing fileSharing, SecurityContext securityContext, UserManager userManager) + { + BreadCrumbsManager = breadCrumbsManager; FileSharing = fileSharing; SecurityContext = securityContext; UserManager = userManager; @@ -218,122 +215,117 @@ namespace ASC.Web.Files.Services.DocumentService public bool? Favorite { - set { } get { if (!SecurityContext.IsAuthenticated || UserManager.GetUsers(SecurityContext.CurrentAccount.ID).IsVisitor(UserManager)) return null; if (File.Encrypted) return null; return File.IsFavorite; } - } - - public string Folder - { - set { } - get - { - if (Type == EditorType.Embedded || Type == EditorType.External) return null; - if (string.IsNullOrEmpty(_breadCrumbs)) - { - const string crumbsSeporator = " \\ "; - - var breadCrumbsList = BreadCrumbsManager.GetBreadCrumbs(File.FolderID); - _breadCrumbs = string.Join(crumbsSeporator, breadCrumbsList.Select(folder => folder.Title).ToArray()); - } - - return _breadCrumbs; - } - } - - public string Owner - { - set { } - get { return File.CreateByString; } - } - - public string Uploaded - { - set { } - get { return File.CreateOnString; } - } - - public List<AceShortWrapper> SharingSettings - { - set { } - get - { - if (Type == EditorType.Embedded - || Type == EditorType.External - || !FileSharing.CanSetAccess(File)) return null; - - try - { - return FileSharing.GetSharedInfoShortFile(File.ID); - } - catch - { - return null; - } - } - } - - private BreadCrumbsManager BreadCrumbsManager { get; } + } + + public string Folder + { + get + { + if (Type == EditorType.Embedded || Type == EditorType.External) return null; + if (string.IsNullOrEmpty(_breadCrumbs)) + { + const string crumbsSeporator = " \\ "; + + var breadCrumbsList = BreadCrumbsManager.GetBreadCrumbs(File.FolderID); + _breadCrumbs = string.Join(crumbsSeporator, breadCrumbsList.Select(folder => folder.Title).ToArray()); + } + + return _breadCrumbs; + } + } + + public string Owner + { + get { return File.CreateByString; } + } + + public string Uploaded + { + get { return File.CreateOnString; } + } + + public List<AceShortWrapper> SharingSettings + { + get + { + if (Type == EditorType.Embedded + || Type == EditorType.External + || !FileSharing.CanSetAccess(File)) return null; + + try + { + return FileSharing.GetSharedInfoShortFile(File.ID); + } + catch + { + return null; + } + } + } + + private BreadCrumbsManager BreadCrumbsManager { get; } private FileSharing FileSharing { get; } private SecurityContext SecurityContext { get; } private UserManager UserManager { get; } - } - - public class PermissionsConfig - { - //todo: obsolete since DS v5.5 - public bool ChangeHistory { get; set; } = false; - - public bool Comment { get; set; } = true; - - public bool Download { get; set; } = true; - - public bool Edit { get; set; } = true; - - public bool FillForms { get; set; } = true; - + } + + public class PermissionsConfig + { + //todo: obsolete since DS v5.5 + public bool ChangeHistory { get; set; } = false; + + public bool Comment { get; set; } = true; + + public bool Download { get; set; } = true; + + public bool Edit { get; set; } = true; + + public bool FillForms { get; set; } = true; + public bool Print { get; set; } = true; public bool ModifyFilter { get; set; } = true; //todo: obsolete since DS v6.0 - public bool Rename { get; set; } = false; - - public bool Review { get; set; } = true; - } + public bool Rename { get; set; } = false; - [Transient] - public class EditorConfiguration<T> - { - public EditorConfiguration( - UserManager userManager, - AuthContext authContext, - DisplayUserSettingsHelper displayUserSettingsHelper, + public bool Review { get; set; } = true; + } + + [Transient] + public class EditorConfiguration<T> + { + public EditorConfiguration( + UserManager userManager, + AuthContext authContext, + DisplayUserSettingsHelper displayUserSettingsHelper, FilesLinkUtility filesLinkUtility, - FileUtility fileUtility, - BaseCommonLinkUtility baseCommonLinkUtility, - PluginsConfig pluginsConfig, - EmbeddedConfig embeddedConfig, + FileUtility fileUtility, + BaseCommonLinkUtility baseCommonLinkUtility, + PluginsConfig pluginsConfig, + EmbeddedConfig embeddedConfig, CustomizationConfig<T> customizationConfig, FilesSettingsHelper filesSettingsHelper, IDaoFactory daoFactory, - EntryManager entryManager) - { - UserManager = userManager; - AuthContext = authContext; + EntryManager entryManager) + { + UserManager = userManager; + AuthContext = authContext; FilesLinkUtility = filesLinkUtility; FileUtility = fileUtility; - BaseCommonLinkUtility = baseCommonLinkUtility; + BaseCommonLinkUtility = baseCommonLinkUtility; Customization = customizationConfig; FilesSettingsHelper = filesSettingsHelper; DaoFactory = daoFactory; EntryManager = entryManager; - Plugins = pluginsConfig; - Embedded = embeddedConfig; + Plugins = pluginsConfig; + Embedded = embeddedConfig; _userInfo = userManager.GetUsers(authContext.CurrentAccount.ID); if (!_userInfo.ID.Equals(ASC.Core.Configuration.Constants.Guest.ID)) @@ -343,43 +335,43 @@ namespace ASC.Web.Files.Services.DocumentService Id = _userInfo.ID.ToString(), Name = _userInfo.DisplayUserName(false, displayUserSettingsHelper), }; - } - } - - public bool ModeWrite = false; - - private Configuration<T> _configuration; - - internal void SetConfiguration(Configuration<T> configuration) - { - _configuration = configuration; - Customization.SetConfiguration(_configuration); - } - - private readonly UserInfo _userInfo; - private EmbeddedConfig _embeddedConfig; - - public ActionLinkConfig ActionLink { get; set; } - - public string ActionLinkString - { - get { return null; } - set - { - try + } + } + + public bool ModeWrite { get; set; } = false; + + private Configuration<T> _configuration; + + internal void SetConfiguration(Configuration<T> configuration) + { + _configuration = configuration; + Customization.SetConfiguration(_configuration); + } + + private readonly UserInfo _userInfo; + private EmbeddedConfig _embeddedConfig; + + public ActionLinkConfig ActionLink { get; set; } + + public string ActionLinkString + { + get { return null; } + set + { + try { var options = new JsonSerializerOptions { AllowTrailingCommas = true, PropertyNameCaseInsensitive = true - }; - JsonSerializer.Deserialize<ActionLinkConfig>(value, options); - } - catch (Exception) - { - ActionLink = null; - } - } + }; + JsonSerializer.Deserialize<ActionLinkConfig>(value, options); + } + catch (Exception) + { + ActionLink = null; + } + } } @@ -421,56 +413,53 @@ namespace ASC.Web.Files.Services.DocumentService return listTemplates.ToList(); } } - - public string CallbackUrl { get; set; } - - public string CreateUrl - { - set { } - get - { - if (_configuration.Document.Info.Type != EditorType.Desktop) return null; - if (!AuthContext.IsAuthenticated || UserManager.GetUsers(AuthContext.CurrentAccount.ID).IsVisitor(UserManager)) return null; - - return GetCreateUrl(_configuration.GetFileType); - } - } - - public PluginsConfig Plugins { get; set; } - + + public string CallbackUrl { get; set; } + + public string CreateUrl + { + get + { + if (_configuration.Document.Info.Type != EditorType.Desktop) return null; + if (!AuthContext.IsAuthenticated || UserManager.GetUsers(AuthContext.CurrentAccount.ID).IsVisitor(UserManager)) return null; + + return GetCreateUrl(_configuration.GetFileType); + } + } + + public PluginsConfig Plugins { get; set; } + public CustomizationConfig<T> Customization { get; set; } private FilesSettingsHelper FilesSettingsHelper { get; } private IDaoFactory DaoFactory { get; } private EntryManager EntryManager { get; } - public EmbeddedConfig Embedded - { - set { _embeddedConfig = value; } - get { return _configuration.Document.Info.Type == EditorType.Embedded ? _embeddedConfig : null; } + public EmbeddedConfig Embedded + { + set { _embeddedConfig = value; } + get { return _configuration.Document.Info.Type == EditorType.Embedded ? _embeddedConfig : null; } } public EncryptionKeysConfig EncryptionKeys { get; set; } - - public string FileChoiceUrl { get; set; } - - public string Lang - { - set { } - get { return _userInfo.GetCulture().Name; } - } - - public string Mode - { - set { } - get { return ModeWrite ? "edit" : "view"; } - } - - private UserManager UserManager { get; } - private AuthContext AuthContext { get; } + + public string FileChoiceUrl { get; set; } + + public string Lang + { + get { return _userInfo.GetCulture().Name; } + } + + public string Mode + { + get { return ModeWrite ? "edit" : "view"; } + } + + private UserManager UserManager { get; } + private AuthContext AuthContext { get; } private FilesLinkUtility FilesLinkUtility { get; } private FileUtility FileUtility { get; } - private BaseCommonLinkUtility BaseCommonLinkUtility { get; } - + private BaseCommonLinkUtility BaseCommonLinkUtility { get; } + public string SaveAsUrl { get; set; } public List<RecentConfig> Recent { @@ -508,92 +497,89 @@ namespace ASC.Web.Files.Services.DocumentService return listRecent.ToList(); } } - - public string SharingSettingsUrl { get; set; } - - public UserConfig User { get; set; } - - private string GetCreateUrl(FileType fileType) - { - string title; - switch (fileType) - { - case FileType.Document: - title = FilesJSResource.TitleNewFileText; - break; - case FileType.Spreadsheet: - title = FilesJSResource.TitleNewFileSpreadsheet; - break; - case FileType.Presentation: - title = FilesJSResource.TitleNewFilePresentation; - break; - default: - return null; - } - - Configuration<T>.DocType.TryGetValue(fileType, out var documentType); - - return BaseCommonLinkUtility.GetFullAbsolutePath(FilesLinkUtility.FileHandlerPath) - + "?" + FilesLinkUtility.Action + "=create" - + "&doctype=" + documentType - + "&" + FilesLinkUtility.FileTitle + "=" + HttpUtility.UrlEncode(title); - } - } - - #endregion - - public class ActionLinkConfig - { - public ActionConfig Action { get; set; } - - - public class ActionConfig - { - public string Type { get; set; } - - public string Data { get; set; } - } - - - public static string Serialize(ActionLinkConfig actionLinkConfig) - { - return JsonSerializer.Serialize(actionLinkConfig); - } - } - [Transient] - public class EmbeddedConfig - { - public string ShareLinkParam { get; set; } - - public string EmbedUrl - { - set { } - get { return BaseCommonLinkUtility.GetFullAbsolutePath(FilesLinkUtility.FilesBaseAbsolutePath + FilesLinkUtility.EditorPage + "?" + FilesLinkUtility.Action + "=embedded" + ShareLinkParam); } - } - - public string SaveUrl - { - set { } - get { return BaseCommonLinkUtility.GetFullAbsolutePath(FilesLinkUtility.FileHandlerPath + "?" + FilesLinkUtility.Action + "=download" + ShareLinkParam); } - } - - public string ShareUrl - { - set { } - get { return BaseCommonLinkUtility.GetFullAbsolutePath(FilesLinkUtility.FilesBaseAbsolutePath + FilesLinkUtility.EditorPage + "?" + FilesLinkUtility.Action + "=view" + ShareLinkParam); } - } - - private BaseCommonLinkUtility BaseCommonLinkUtility { get; } - private FilesLinkUtility FilesLinkUtility { get; } - - public string ToolbarDocked { get => "top"; } - - public EmbeddedConfig(BaseCommonLinkUtility baseCommonLinkUtility, FilesLinkUtility filesLinkUtility) - { - BaseCommonLinkUtility = baseCommonLinkUtility; - FilesLinkUtility = filesLinkUtility; - } + public string SharingSettingsUrl { get; set; } + + public UserConfig User { get; set; } + + private string GetCreateUrl(FileType fileType) + { + string title; + switch (fileType) + { + case FileType.Document: + title = FilesJSResource.TitleNewFileText; + break; + case FileType.Spreadsheet: + title = FilesJSResource.TitleNewFileSpreadsheet; + break; + case FileType.Presentation: + title = FilesJSResource.TitleNewFilePresentation; + break; + default: + return null; + } + + Configuration<T>.DocType.TryGetValue(fileType, out var documentType); + + return BaseCommonLinkUtility.GetFullAbsolutePath(FilesLinkUtility.FileHandlerPath) + + "?" + FilesLinkUtility.Action + "=create" + + "&doctype=" + documentType + + "&" + FilesLinkUtility.FileTitle + "=" + HttpUtility.UrlEncode(title); + } + } + + #endregion + + public class ActionLinkConfig + { + public ActionConfig Action { get; set; } + + + public class ActionConfig + { + public string Type { get; set; } + + public string Data { get; set; } + } + + + public static string Serialize(ActionLinkConfig actionLinkConfig) + { + return JsonSerializer.Serialize(actionLinkConfig); + } + } + + [Transient] + public class EmbeddedConfig + { + public string ShareLinkParam { get; set; } + + public string EmbedUrl + { + get { return BaseCommonLinkUtility.GetFullAbsolutePath(FilesLinkUtility.FilesBaseAbsolutePath + FilesLinkUtility.EditorPage + "?" + FilesLinkUtility.Action + "=embedded" + ShareLinkParam); } + } + + public string SaveUrl + { + get { return BaseCommonLinkUtility.GetFullAbsolutePath(FilesLinkUtility.FileHandlerPath + "?" + FilesLinkUtility.Action + "=download" + ShareLinkParam); } + } + + public string ShareUrl + { + get { return BaseCommonLinkUtility.GetFullAbsolutePath(FilesLinkUtility.FilesBaseAbsolutePath + FilesLinkUtility.EditorPage + "?" + FilesLinkUtility.Action + "=view" + ShareLinkParam); } + } + + private BaseCommonLinkUtility BaseCommonLinkUtility { get; } + private FilesLinkUtility FilesLinkUtility { get; } + + public string ToolbarDocked { get => "top"; } + + public EmbeddedConfig(BaseCommonLinkUtility baseCommonLinkUtility, FilesLinkUtility filesLinkUtility) + { + BaseCommonLinkUtility = baseCommonLinkUtility; + FilesLinkUtility = filesLinkUtility; + } } public class EncryptionKeysConfig @@ -611,7 +597,6 @@ namespace ASC.Web.Files.Services.DocumentService { public string[] PluginsData { - set { } get { var plugins = new List<string>(); @@ -696,13 +681,12 @@ namespace ASC.Web.Files.Services.DocumentService Logo.SetConfiguration(_configuration); } - public string GobackUrl; - public bool IsRetina = false; + //private string _gobackUrl; + public bool IsRetina { get; set; } = false; public bool About { - set { } get { return !CoreBaseSettings.Standalone && !CoreBaseSettings.CustomMode; } } @@ -710,7 +694,6 @@ namespace ASC.Web.Files.Services.DocumentService public FeedbackConfig Feedback { - set { } get { if (CoreBaseSettings.Standalone) return null; @@ -728,7 +711,6 @@ namespace ASC.Web.Files.Services.DocumentService public bool? Forcesave { - set { } get { return FileUtility.CanForcesave @@ -740,18 +722,17 @@ namespace ASC.Web.Files.Services.DocumentService public GobackConfig Goback { - set { } get { if (_configuration.EditorType == EditorType.Embedded || _configuration.EditorType == EditorType.External) return null; if (!AuthContext.IsAuthenticated) return null; - if (GobackUrl != null) - { - return new GobackConfig - { - Url = GobackUrl, - }; - } + //if (_gobackUrl != null) + //{ + // return new GobackConfig + // { + // Url = _gobackUrl, + // }; + //} var folderDao = DaoFactory.GetFolderDao<T>(); try @@ -796,7 +777,6 @@ namespace ASC.Web.Files.Services.DocumentService public bool MentionShare { - set { } get { return AuthContext.IsAuthenticated @@ -807,7 +787,6 @@ namespace ASC.Web.Files.Services.DocumentService public string ReviewDisplay { - set { } get { return _configuration.EditorConfig.ModeWrite ? null : "markup"; } } @@ -844,13 +823,11 @@ namespace ASC.Web.Files.Services.DocumentService public string Logo { - set { } get { return BaseCommonLinkUtility.GetFullAbsolutePath(TenantLogoHelper.GetLogo(WhiteLabelLogoTypeEnum.Dark, !_configuration.EditorConfig.Customization.IsRetina)); } } public string Name { - set { } get { return (SettingsManager.Load<TenantWhiteLabelSettings>().GetLogoText(SettingsManager) ?? "") @@ -896,7 +873,6 @@ namespace ASC.Web.Files.Services.DocumentService public string Image { - set { } get { var fillingForm = FileUtility.CanWebRestrictedEditing(_configuration.Document.Title); @@ -920,7 +896,6 @@ namespace ASC.Web.Files.Services.DocumentService public string ImageEmbedded { - set { } get { return @@ -995,5 +970,5 @@ namespace ASC.Web.Files.Services.DocumentService services.TryAdd<LogoConfig<int>>(); } - } + } } \ No newline at end of file diff --git a/products/ASC.Files/Core/Services/DocumentService/DocbuilderReportsUtility.cs b/products/ASC.Files/Core/Services/DocumentService/DocbuilderReportsUtility.cs index 3f62330780..f7c2bc687d 100644 --- a/products/ASC.Files/Core/Services/DocumentService/DocbuilderReportsUtility.cs +++ b/products/ASC.Files/Core/Services/DocumentService/DocbuilderReportsUtility.cs @@ -63,13 +63,13 @@ namespace ASC.Web.Files.Services.DocumentService public string Script { get; } public int ReportType { get; } public ReportOrigin Origin { get; } - public Action<ReportState, string> SaveFileAction { get; } + public Func<ReportState, string, Task> SaveFileAction { get; } public object Obj { get; } public int TenantId { get; } public Guid UserId { get; } public ReportStateData(string fileName, string tmpFileName, string script, int reportType, ReportOrigin origin, - Action<ReportState, string> saveFileAction, object obj, + Func<ReportState, string, Task> saveFileAction, object obj, int tenantId, Guid userId) { FileName = fileName; @@ -98,7 +98,7 @@ namespace ASC.Web.Files.Services.DocumentService internal string BuilderKey { get; set; } internal string Script { get; set; } internal string TmpFileName { get; set; } - internal Action<ReportState, string> SaveFileAction { get; set; } + internal Func<ReportState, string, Task> SaveFileAction { get; set; } internal int TenantId { get; set; } internal Guid UserId { get; set; } @@ -189,7 +189,7 @@ namespace ASC.Web.Files.Services.DocumentService if (builderKey == null) throw new NullReferenceException(); - if (urls != null && !urls.Any()) throw new Exception("Empty response"); + if (urls != null && urls.Count == 0) throw new Exception("Empty response"); if (urls != null && urls.ContainsKey(TmpFileName)) break; @@ -301,7 +301,6 @@ namespace ASC.Web.Files.Services.DocumentService var result = ReportState.FromTask(task, httpContextAccessor, tenantId, userId); var status = task.GetProperty<ReportStatus>("status"); - var id = task.GetProperty<ReportStatus>("status"); if ((int)status > 1) { diff --git a/products/ASC.Files/Core/Services/DocumentService/DocumentServiceConnector.cs b/products/ASC.Files/Core/Services/DocumentService/DocumentServiceConnector.cs index 28cd9475d7..733d1aacfc 100644 --- a/products/ASC.Files/Core/Services/DocumentService/DocumentServiceConnector.cs +++ b/products/ASC.Files/Core/Services/DocumentService/DocumentServiceConnector.cs @@ -29,7 +29,7 @@ using System.Collections.Generic; using System.Globalization; using System.IO; using System.Net; -using System.Net.Http; +using System.Net.Http; using System.Web; using ASC.Common; @@ -44,20 +44,21 @@ using ASC.Web.Studio.Utility; using Microsoft.Extensions.Options; -using Newtonsoft.Json; - -using static ASC.Web.Core.Files.DocumentService; - +using Newtonsoft.Json; + +using static ASC.Web.Core.Files.DocumentService; + using CommandMethod = ASC.Web.Core.Files.DocumentService.CommandMethod; namespace ASC.Web.Files.Services.DocumentService -{ +{ [Scope] public class DocumentServiceConnector { public ILog Logger { get; } private FilesLinkUtility FilesLinkUtility { get; } private FileUtility FileUtility { get; } + private IHttpClientFactory ClientFactory { get; } private GlobalStore GlobalStore { get; } private BaseCommonLinkUtility BaseCommonLinkUtility { get; } private TenantManager TenantManager { get; } @@ -74,7 +75,8 @@ namespace ASC.Web.Files.Services.DocumentService BaseCommonLinkUtility baseCommonLinkUtility, TenantManager tenantManager, TenantExtra tenantExtra, - CoreSettings coreSettings) + CoreSettings coreSettings, + IHttpClientFactory clientFactory) { Logger = optionsMonitor.CurrentValue; FilesLinkUtility = filesLinkUtility; @@ -85,6 +87,7 @@ namespace ASC.Web.Files.Services.DocumentService TenantExtra = tenantExtra; CoreSettings = coreSettings; PathProvider = pathProvider; + ClientFactory = clientFactory; } public static string GenerateRevisionId(string expectedKey) @@ -96,8 +99,8 @@ namespace ASC.Web.Files.Services.DocumentService string fromExtension, string toExtension, string documentRevisionId, - string password, - ThumbnailData thumbnail, + string password, + ThumbnailData thumbnail, SpreadsheetLayout spreadsheetLayout, bool isAsync, out string convertedDocumentUri) @@ -112,11 +115,12 @@ namespace ASC.Web.Files.Services.DocumentService fromExtension, toExtension, GenerateRevisionId(documentRevisionId), - password, - thumbnail, + password, + thumbnail, spreadsheetLayout, isAsync, FileUtility.SignatureSecret, + ClientFactory, out convertedDocumentUri); } catch (Exception ex) @@ -143,8 +147,9 @@ namespace ASC.Web.Files.Services.DocumentService callbackUrl, users, meta, - FileUtility.SignatureSecret); - + FileUtility.SignatureSecret, + ClientFactory); + if (commandResponse.Error == CommandResponse.ErrorTypes.NoError) { return true; @@ -189,6 +194,7 @@ namespace ASC.Web.Files.Services.DocumentService scriptUrl, isAsync, FileUtility.SignatureSecret, + ClientFactory, out urls); } catch (Exception ex) @@ -210,19 +216,20 @@ namespace ASC.Web.Files.Services.DocumentService null, null, null, - FileUtility.SignatureSecret); - - var version = commandResponse.Version; - if (string.IsNullOrEmpty(version)) - { - version = "0"; - } - - if (commandResponse.Error == CommandResponse.ErrorTypes.NoError) - { - return version; - } - + FileUtility.SignatureSecret, + ClientFactory); + + var version = commandResponse.Version; + if (string.IsNullOrEmpty(version)) + { + version = "0"; + } + + if (commandResponse.Error == CommandResponse.ErrorTypes.NoError) + { + return version; + } + Logger.ErrorFormat("DocService command response: '{0}' {1}", commandResponse.Error, commandResponse.ErrorString); } catch (Exception e) @@ -238,7 +245,7 @@ namespace ASC.Web.Files.Services.DocumentService { try { - if (!HealthcheckRequest(FilesLinkUtility.DocServiceHealthcheckUrl)) + if (!HealthcheckRequest(FilesLinkUtility.DocServiceHealthcheckUrl, ClientFactory)) { throw new Exception("bad status"); } @@ -262,7 +269,7 @@ namespace ASC.Web.Files.Services.DocumentService var fileUri = ReplaceCommunityAdress(url); var key = GenerateRevisionId(Guid.NewGuid().ToString()); - Web.Core.Files.DocumentService.GetConvertedUri(FileUtility, FilesLinkUtility.DocServiceConverterUrl, fileUri, fileExtension, toExtension, key, null, null, null, false, FileUtility.SignatureSecret, out convertedFileUri); + Web.Core.Files.DocumentService.GetConvertedUri(FileUtility, FilesLinkUtility.DocServiceConverterUrl, fileUri, fileExtension, toExtension, key, null, null, null, false, FileUtility.SignatureSecret, ClientFactory, out convertedFileUri); } catch (Exception ex) { @@ -271,12 +278,12 @@ namespace ASC.Web.Files.Services.DocumentService } try - { - var request1 = new HttpRequestMessage(); - request1.RequestUri = new Uri(convertedFileUri); - - using var httpClient = new HttpClient(); - using var response = httpClient.Send(request1); + { + var request1 = new HttpRequestMessage(); + request1.RequestUri = new Uri(convertedFileUri); + + using var httpClient = ClientFactory.CreateClient(); + using var response = httpClient.Send(request1); if (response.StatusCode != HttpStatusCode.OK) { @@ -295,7 +302,7 @@ namespace ASC.Web.Files.Services.DocumentService try { var key = GenerateRevisionId(Guid.NewGuid().ToString()); - CommandRequest(FileUtility, FilesLinkUtility.DocServiceCommandUrl, CommandMethod.Version, key, null, null, null, FileUtility.SignatureSecret); + CommandRequest(FileUtility, FilesLinkUtility.DocServiceCommandUrl, CommandMethod.Version, key, null, null, null, FileUtility.SignatureSecret, ClientFactory); } catch (Exception ex) { @@ -313,7 +320,7 @@ namespace ASC.Web.Files.Services.DocumentService var scriptUrl = BaseCommonLinkUtility.GetFullAbsolutePath(scriptUri.ToString()); scriptUrl = ReplaceCommunityAdress(scriptUrl); - Web.Core.Files.DocumentService.DocbuilderRequest(FileUtility, FilesLinkUtility.DocServiceDocbuilderUrl, null, scriptUrl, false, FileUtility.SignatureSecret, out var urls); + Web.Core.Files.DocumentService.DocbuilderRequest(FileUtility, FilesLinkUtility.DocServiceDocbuilderUrl, null, scriptUrl, false, FileUtility.SignatureSecret, ClientFactory, out var urls); } catch (Exception ex) { @@ -334,9 +341,9 @@ namespace ASC.Web.Files.Services.DocumentService if (string.IsNullOrEmpty(docServicePortalUrl)) { - Tenant tenant; + Tenant tenant = TenantManager.GetCurrentTenant(); if (!TenantExtra.Saas - || string.IsNullOrEmpty((tenant = TenantManager.GetCurrentTenant()).MappedDomain) + || string.IsNullOrEmpty(tenant.MappedDomain) || !url.StartsWith("https://" + tenant.MappedDomain)) { return url; @@ -388,7 +395,7 @@ namespace ASC.Web.Files.Services.DocumentService { var error = FilesCommonResource.ErrorMassage_DocServiceException; if (!string.IsNullOrEmpty(ex.Message)) - error += string.Format(" ({0})", ex.Message); + error += $" ({ex.Message})"; Logger.Error("DocService error", ex); return new Exception(error, ex); diff --git a/products/ASC.Files/Core/Services/DocumentService/DocumentServiceHelper.cs b/products/ASC.Files/Core/Services/DocumentService/DocumentServiceHelper.cs index 9948023f53..9d3baf7539 100644 --- a/products/ASC.Files/Core/Services/DocumentService/DocumentServiceHelper.cs +++ b/products/ASC.Files/Core/Services/DocumentService/DocumentServiceHelper.cs @@ -225,7 +225,7 @@ namespace ASC.Web.Files.Services.DocumentService } - if (!editPossible && !FileUtility.CanWebView(file.Title)) throw new Exception(string.Format("{0} ({1})", FilesCommonResource.ErrorMassage_NotSupportedFormat, FileUtility.GetFileExtension(file.Title))); + if (!editPossible && !FileUtility.CanWebView(file.Title)) throw new Exception($"{FilesCommonResource.ErrorMassage_NotSupportedFormat} ({FileUtility.GetFileExtension(file.Title)})"); if (reviewPossible && !FileUtility.CanWebReview(file.Title)) @@ -308,7 +308,7 @@ namespace ASC.Web.Files.Services.DocumentService if (!lastVersion) { - configuration.Document.Title += string.Format(" ({0})", file.CreateOnString); + configuration.Document.Title += $" ({file.CreateOnString})"; } return file; @@ -371,7 +371,7 @@ namespace ASC.Web.Files.Services.DocumentService }) .Select(u => u.ToString()).ToArray(); - if (!usersDrop.Any()) return; + if (usersDrop.Length == 0) return; var fileStable = file; if (file.Forcesave != ForcesaveType.None) diff --git a/products/ASC.Files/Core/Services/DocumentService/DocumentServiceTracker.cs b/products/ASC.Files/Core/Services/DocumentService/DocumentServiceTracker.cs index 04e35868de..4c4ff24621 100644 --- a/products/ASC.Files/Core/Services/DocumentService/DocumentServiceTracker.cs +++ b/products/ASC.Files/Core/Services/DocumentService/DocumentServiceTracker.cs @@ -30,7 +30,6 @@ using System.Diagnostics; using System.Globalization; using System.IO; using System.Linq; -using System.Net; using System.Net.Http; using System.Text; using System.Text.Json; @@ -98,8 +97,8 @@ namespace ASC.Web.Files.Services.DocumentService [DebuggerDisplay("{Type} - {UserId}")] public class Action { - public string Type; - public string UserId; + public string Type { get; set; } + public string UserId { get; set; } } public enum ForceSaveInitiator @@ -138,7 +137,6 @@ namespace ASC.Web.Files.Services.DocumentService { public int Error { - set { } get { return string.IsNullOrEmpty(Message) @@ -184,7 +182,8 @@ namespace ASC.Web.Files.Services.DocumentService private NotifyClient NotifyClient { get; } private MailMergeTaskRunner MailMergeTaskRunner { get; } private FileTrackerHelper FileTracker { get; } - public ILog Logger { get; } + public ILog Logger { get; } + public IHttpClientFactory ClientFactory { get; } public DocumentServiceTrackerHelper( SecurityContext securityContext, @@ -205,7 +204,8 @@ namespace ASC.Web.Files.Services.DocumentService DocumentServiceConnector documentServiceConnector, NotifyClient notifyClient, MailMergeTaskRunner mailMergeTaskRunner, - FileTrackerHelper fileTracker) + FileTrackerHelper fileTracker, + IHttpClientFactory clientFactory) { SecurityContext = securityContext; UserManager = userManager; @@ -225,7 +225,8 @@ namespace ASC.Web.Files.Services.DocumentService NotifyClient = notifyClient; MailMergeTaskRunner = mailMergeTaskRunner; FileTracker = fileTracker; - Logger = options.CurrentValue; + Logger = options.CurrentValue; + ClientFactory = clientFactory; } public string GetCallbackUrl<T>(T fileId) @@ -323,7 +324,7 @@ namespace ASC.Web.Files.Services.DocumentService } } - if (usersDrop.Any()) + if (usersDrop.Count > 0) { if (!DocumentServiceHelper.DropUser(fileData.Key, usersDrop.ToArray(), fileId)) { @@ -491,19 +492,13 @@ namespace ASC.Web.Files.Services.DocumentService var message = fileData.MailMerge.Message; Stream attach = null; - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); switch (fileData.MailMerge.Type) { case MailMergeType.AttachDocx: case MailMergeType.AttachPdf: var requestDownload = new HttpRequestMessage(); requestDownload.RequestUri = new Uri(DocumentServiceConnector.ReplaceDocumentAdress(fileData.Url)); - - // hack. http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono) - { - ServicePointManager.ServerCertificateValidationCallback += (s, ce, ca, p) => true; - } using (var responseDownload = httpClient.Send(requestDownload)) using (var streamDownload = responseDownload.Content.ReadAsStream()) @@ -536,14 +531,7 @@ namespace ASC.Web.Files.Services.DocumentService case MailMergeType.Html: var httpRequest = new HttpRequestMessage(); - httpRequest.RequestUri = new Uri(DocumentServiceConnector.ReplaceDocumentAdress(fileData.Url)); - - // hack. http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono) - { - ServicePointManager.ServerCertificateValidationCallback += (s, ce, ca, p) => true; - } - + httpRequest.RequestUri = new Uri(DocumentServiceConnector.ReplaceDocumentAdress(fileData.Url)); using (var httpResponse = httpClient.Send(httpRequest)) using (var stream = httpResponse.Content.ReadAsStream()) @@ -566,7 +554,7 @@ namespace ASC.Web.Files.Services.DocumentService Attach = attach }) { - var response = MailMergeTaskRunner.Run(mailMergeTask); + var response = MailMergeTaskRunner.Run(mailMergeTask, ClientFactory); Logger.InfoFormat("DocService mailMerge {0}/{1} send: {2}", fileData.MailMerge.RecordIndex + 1, fileData.MailMerge.RecordCount, response); } @@ -576,7 +564,7 @@ namespace ASC.Web.Files.Services.DocumentService { Logger.Error( string.Format("DocService mailMerge{0} error: userId - {1}, url - {2}", - (fileData.MailMerge == null ? "" : " " + fileData.MailMerge.RecordIndex + "/" + fileData.MailMerge.RecordCount), + fileData.MailMerge == null ? "" : " " + fileData.MailMerge.RecordIndex + "/" + fileData.MailMerge.RecordCount, userId, fileData.Url), ex); saveMessage = ex.Message; @@ -602,22 +590,13 @@ namespace ASC.Web.Files.Services.DocumentService try { var fileName = Global.ReplaceInvalidCharsAndTruncate(fileId + FileUtility.GetFileExtension(downloadUri)); - var path = string.Format(@"save_crash\{0}\{1}_{2}", - DateTime.UtcNow.ToString("yyyy_MM_dd"), - userId, - fileName); + var path = $@"save_crash\{DateTime.UtcNow.ToString("yyyy_MM_dd")}\{userId}_{fileName}"; var store = GlobalStore.GetStore(); var request = new HttpRequestMessage(); - request.RequestUri = new Uri(downloadUri); - - // hack. http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono) - { - ServicePointManager.ServerCertificateValidationCallback += (s, ce, ca, p) => true; - } + request.RequestUri = new Uri(downloadUri); - using (var httpClient = new HttpClient()) + var httpClient = ClientFactory.CreateClient(); using (var response = httpClient.Send(request)) using (var stream = response.Content.ReadAsStream()) using (var fileStream = new ResponseStream(stream, stream.Length)) @@ -642,15 +621,9 @@ namespace ASC.Web.Files.Services.DocumentService { var fileDao = DaoFactory.GetFileDao<T>(); var request = new HttpRequestMessage(); - request.RequestUri = new Uri(differenceUrl); - - // hack. http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono) - { - ServicePointManager.ServerCertificateValidationCallback += (s, ce, ca, p) => true; - } + request.RequestUri = new Uri(differenceUrl); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using var stream = response.Content.ReadAsStream(); diff --git a/products/ASC.Files/Core/Services/FFmpegService/FFmpeg.cs b/products/ASC.Files/Core/Services/FFmpegService/FFmpeg.cs index 63e2a93e70..0d1c715a44 100644 --- a/products/ASC.Files/Core/Services/FFmpegService/FFmpeg.cs +++ b/products/ASC.Files/Core/Services/FFmpegService/FFmpeg.cs @@ -24,7 +24,7 @@ namespace ASC.Web.Files.Services.FFmpegService get { if (string.IsNullOrEmpty(FFmpegPath)) return new List<string>(); - return ConvertableMedia.ToList(); + return ConvertableMedia; } } @@ -33,11 +33,16 @@ namespace ASC.Web.Files.Services.FFmpegService return MustConvertable.Contains(extension.TrimStart('.')); } - public async Task<Stream> Convert(Stream inputStream, string inputFormat) + public Task<Stream> Convert(Stream inputStream, string inputFormat) { if (inputStream == null) throw new ArgumentException(); if (string.IsNullOrEmpty(inputFormat)) throw new ArgumentException(); + return ConvertInternal(inputStream, inputFormat); + } + + private async Task<Stream> ConvertInternal(Stream inputStream, string inputFormat) + { var startInfo = PrepareFFmpeg(inputFormat); Process process; @@ -50,7 +55,7 @@ namespace ASC.Web.Files.Services.FFmpegService await ProcessLog(process.StandardError.BaseStream); return process.StandardOutput.BaseStream; - } + } } public FFmpegService(IOptionsMonitor<ILog> optionsMonitor, IConfiguration configuration) @@ -59,7 +64,7 @@ namespace ASC.Web.Files.Services.FFmpegService FFmpegPath = configuration["files:ffmpeg:value"]; FFmpegArgs = configuration["files:ffmpeg:args"] ?? "-i - -preset ultrafast -movflags frag_keyframe+empty_moov -f {0} -"; - ConvertableMedia = (configuration.GetSection("files:ffmpeg:exts").Get<string[]>() ?? new string[] { }).ToList(); + ConvertableMedia = (configuration.GetSection("files:ffmpeg:exts").Get<string[]>() ?? Array.Empty<string>()).ToList(); if (string.IsNullOrEmpty(FFmpegPath)) { @@ -116,13 +121,18 @@ namespace ASC.Web.Files.Services.FFmpegService return startInfo; } - private static async Task<int> StreamCopyToAsync(Stream srcStream, Stream dstStream, bool closeSrc = false, bool closeDst = false) + private static Task<int> StreamCopyToAsync(Stream srcStream, Stream dstStream, bool closeSrc = false, bool closeDst = false) { - const int bufs = 2048 * 4; - - if (srcStream == null) throw new ArgumentNullException("srcStream"); - if (dstStream == null) throw new ArgumentNullException("dstStream"); + if (srcStream == null) throw new ArgumentNullException(nameof(srcStream)); + if (dstStream == null) throw new ArgumentNullException(nameof(dstStream)); + return StreamCopyToAsyncInternal(srcStream, dstStream, closeSrc, closeDst); + } + + private static async Task<int> StreamCopyToAsyncInternal(Stream srcStream, Stream dstStream, bool closeSrc, bool closeDst) + { + const int bufs = 2048 * 4; + var buffer = new byte[bufs]; int readed; var total = 0; @@ -146,7 +156,7 @@ namespace ASC.Web.Files.Services.FFmpegService dstStream.Close(); } - return total; + return total; } private async Task ProcessLog(Stream stream) diff --git a/products/ASC.Files/Core/Services/NotifyService/NotifyClient.cs b/products/ASC.Files/Core/Services/NotifyService/NotifyClient.cs index e2c13b3938..3cb2a3b6a1 100644 --- a/products/ASC.Files/Core/Services/NotifyService/NotifyClient.cs +++ b/products/ASC.Files/Core/Services/NotifyService/NotifyClient.cs @@ -258,7 +258,7 @@ namespace ASC.Files.Core.Services.NotifyService } } - public class NotifyClientExtension + public static class NotifyClientExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Services/WCFService/FileOperations/FileDownloadOperation.cs b/products/ASC.Files/Core/Services/WCFService/FileOperations/FileDownloadOperation.cs index d38c6f4e74..e4f74fe9a5 100644 --- a/products/ASC.Files/Core/Services/WCFService/FileOperations/FileDownloadOperation.cs +++ b/products/ASC.Files/Core/Services/WCFService/FileOperations/FileDownloadOperation.cs @@ -36,7 +36,6 @@ using ASC.Common.Threading; using ASC.Common.Web; using ASC.Core.Tenants; using ASC.Files.Core; -using ASC.Files.Core.EF; using ASC.Files.Core.Resources; using ASC.MessagingSystem; using ASC.Web.Core.Files; @@ -87,16 +86,16 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations using var scope = ThirdPartyOperation.CreateScope(); var scopeClass = scope.ServiceProvider.GetService<FileDownloadOperationScope>(); var (globalStore, filesLinkUtility, _, _, _) = scopeClass; - var stream = TempStream.Create(); + using var stream = TempStream.Create(); (ThirdPartyOperation as FileDownloadOperation<string>).CompressToZip(stream, scope); (DaoOperation as FileDownloadOperation<int>).CompressToZip(stream, scope); if (stream != null) { - var archiveExtension = ""; + string archiveExtension; - using(var zip = scope.ServiceProvider.GetService<CompressToArchive>()) + using (var zip = scope.ServiceProvider.GetService<CompressToArchive>()) { archiveExtension = zip.ArchiveExtension; } @@ -117,7 +116,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations stream, MimeMapping.GetMimeMapping(path), "attachment; filename=\"" + fileName + "\""); - Result = string.Format("{0}?{1}=bulk&ext={2}", filesLinkUtility.FileHandlerPath, FilesLinkUtility.Action, archiveExtension); + Result = $"{filesLinkUtility.FileHandlerPath}?{FilesLinkUtility.Action}=bulk&ext={archiveExtension}"; TaskInfo.SetProperty(PROGRESS, 100); TaskInfo.SetProperty(RESULT, Result); @@ -153,16 +152,16 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations base.FillDistributedTask(); - TaskInfo.SetProperty(PROGRESS, progress < 100 ? progress : progress); + TaskInfo.SetProperty(PROGRESS, progress); TaskInfo.PublishChanges(); } } class FileDownloadOperation<T> : FileOperation<FileDownloadOperationData<T>, T> { - private readonly Dictionary<T, string> files; + private readonly Dictionary<T, string> _files; private readonly IDictionary<string, StringValues> headers; - ItemNameValueCollection<T> entriesPathId; + private ItemNameValueCollection<T> _entriesPathId; public override FileOperationType OperationType { get { return FileOperationType.Download; } @@ -171,17 +170,17 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations public FileDownloadOperation(IServiceProvider serviceProvider, FileDownloadOperationData<T> fileDownloadOperationData) : base(serviceProvider, fileDownloadOperationData) { - files = fileDownloadOperationData.FilesDownload; + _files = fileDownloadOperationData.FilesDownload; headers = fileDownloadOperationData.Headers; } protected override void Do(IServiceScope scope) { - if (!Files.Any() && !Folders.Any()) return; + if (Files.Count == 0 && Folders.Count == 0) return; - entriesPathId = GetEntriesPathId(scope); + _entriesPathId = GetEntriesPathId(scope); - if (entriesPathId == null || entriesPathId.Count == 0) + if (_entriesPathId == null || _entriesPathId.Count == 0) { if (Files.Count > 0) { @@ -191,9 +190,9 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations throw new DirectoryNotFoundException(FilesCommonResource.ErrorMassage_FolderNotFound); } - ReplaceLongPath(entriesPathId); + ReplaceLongPath(_entriesPathId); - Total = entriesPathId.Count; + Total = _entriesPathId.Count; TaskInfo.PublishChanges(); } @@ -205,10 +204,8 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations var title = file.Title; - if (files.ContainsKey(file.ID)) + if (_files.TryGetValue(file.ID, out var convertToExt)) { - var convertToExt = files[file.ID]; - if (!string.IsNullOrEmpty(convertToExt)) { title = FileUtility.ReplaceFileExtension(title, convertToExt); @@ -233,8 +230,12 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations } if (0 < Folders.Count) { - FilesSecurity.FilterRead(FolderDao.GetFolders(Files)).Cast<FileEntry<T>>().ToList() - .ForEach(folder => fileMarker.RemoveMarkAsNew(folder)); + var folders = FilesSecurity.FilterRead(FolderDao.GetFolders(Files)); + + foreach (var folder in folders) + { + fileMarker.RemoveMarkAsNew(folder); + } var filesInFolder = GetFilesInFolders(scope, Folders, string.Empty); entriesPathId.Add(filesInFolder); @@ -274,11 +275,11 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations entriesPathId.Add(filesInFolder); } return entriesPathId; - } - + } + internal void CompressToZip(Stream stream, IServiceScope scope) { - if (entriesPathId == null) return; + if (_entriesPathId == null) return; var scopeClass = scope.ServiceProvider.GetService<FileDownloadOperationScope>(); var (_, _, _, fileConverter, filesMessageService) = scopeClass; var FileDao = scope.ServiceProvider.GetService<IFileDao<T>>(); @@ -287,15 +288,13 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations { compressTo.SetStream(stream); - foreach (var path in entriesPathId.AllKeys) + foreach (var path in _entriesPathId.AllKeys) { var counter = 0; - foreach (var entryId in entriesPathId[path]) + foreach (var entryId in _entriesPathId[path]) { if (CancellationToken.IsCancellationRequested) { - compressTo.Dispose(); - stream.Dispose(); CancellationToken.ThrowIfCancellationRequested(); } @@ -315,9 +314,8 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations continue; } - if (files.ContainsKey(file.ID)) + if (_files.TryGetValue(file.ID, out convertToExt)) { - convertToExt = files[file.ID]; if (!string.IsNullOrEmpty(convertToExt)) { newtitle = FileUtility.ReplaceFileExtension(path, convertToExt); @@ -331,7 +329,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations if (!Equals(entryId, default(T))) { - newtitle = 0 < newtitle.IndexOf('.') ? newtitle.Insert(newtitle.LastIndexOf('.'), suffix) : newtitle + suffix; + newtitle = newtitle.IndexOf('.') > 0 ? newtitle.Insert(newtitle.LastIndexOf('.'), suffix) : newtitle + suffix; } else { diff --git a/products/ASC.Files/Core/Services/WCFService/FileOperations/FileMarkAsReadOperation.cs b/products/ASC.Files/Core/Services/WCFService/FileOperations/FileMarkAsReadOperation.cs index b69b4e5595..92314b7e83 100644 --- a/products/ASC.Files/Core/Services/WCFService/FileOperations/FileMarkAsReadOperation.cs +++ b/products/ASC.Files/Core/Services/WCFService/FileOperations/FileMarkAsReadOperation.cs @@ -91,11 +91,11 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations var scopeClass = scope.ServiceProvider.GetService<FileMarkAsReadOperationScope>(); var (fileMarker, globalFolder, daoFactory, settingsManager) = scopeClass; var entries = new List<FileEntry<T>>(); - if (Folders.Any()) + if (Folders.Count > 0) { entries.AddRange(FolderDao.GetFolders(Folders)); } - if (Files.Any()) + if (Files.Count > 0) { entries.AddRange(FileDao.GetFiles(Files)); } diff --git a/products/ASC.Files/Core/Services/WCFService/FileOperations/FileMoveCopyOperation.cs b/products/ASC.Files/Core/Services/WCFService/FileOperations/FileMoveCopyOperation.cs index be3f0ce6f7..783a853541 100644 --- a/products/ASC.Files/Core/Services/WCFService/FileOperations/FileMoveCopyOperation.cs +++ b/products/ASC.Files/Core/Services/WCFService/FileOperations/FileMoveCopyOperation.cs @@ -27,6 +27,7 @@ using System; using System.Collections.Generic; using System.Linq; +using System.Text; using System.Text.Json; using ASC.Common; @@ -174,7 +175,12 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations needToMark.AddRange(MoveOrCopyFolders(scope, Folders, toFolder, _copy)); needToMark.AddRange(MoveOrCopyFiles(scope, Files, toFolder, _copy)); - needToMark.Distinct().ToList().ForEach(x => fileMarker.MarkAsNew(x)); + var ntm = needToMark.Distinct(); + + foreach(var n in ntm) + { + fileMarker.MarkAsNew(n); + } } private List<FileEntry<TTo>> MoveOrCopyFolders<TTo>(IServiceScope scope, List<T> folderIds, Folder<TTo> toFolder, bool copy) @@ -190,7 +196,8 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations var toFolderId = toFolder.ID; var isToFolder = Equals(toFolderId, DaoFolderId); - + var sb = new StringBuilder(); + sb.Append(Result); foreach (var folderId in folderIds) { CancellationToken.ThrowIfCancellationRequested(); @@ -238,7 +245,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations if (ProcessedFolder(folderId)) { - Result += string.Format("folder_{0}{1}", newFolder.ID, SPLIT_CHAR); + sb.Append($"folder_{newFolder.ID}{SPLIT_CHAR}"); } } @@ -259,7 +266,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations FolderDao.DeleteFolder(folder.ID); if (ProcessedFolder(folderId)) { - Result += string.Format("folder_{0}{1}", newFolder.ID, SPLIT_CHAR); + sb.Append($"folder_{newFolder.ID}{SPLIT_CHAR}"); } } } @@ -280,7 +287,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations if (ProcessedFolder(folderId)) { - Result += string.Format("folder_{0}{1}", newFolderId, SPLIT_CHAR); + sb.Append($"folder_{newFolderId}{SPLIT_CHAR}"); } } else if (!FilesSecurity.CanDelete(folder)) @@ -312,7 +319,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations if (ProcessedFolder(folderId)) { - Result += string.Format("folder_{0}{1}", newFolderId, SPLIT_CHAR); + sb.Append($"folder_{newFolderId}{SPLIT_CHAR}"); } } } @@ -349,10 +356,11 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations if (ProcessedFolder(folderId)) { - Result += string.Format("folder_{0}{1}", newFolderId, SPLIT_CHAR); + sb.Append($"folder_{newFolderId}{SPLIT_CHAR}"); } } - } + } + Result = sb.ToString(); } catch (Exception ex) { @@ -378,7 +386,8 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations var fileDao = scope.ServiceProvider.GetService<IFileDao<TTo>>(); var fileTracker = scope.ServiceProvider.GetService<FileTrackerHelper>(); - var toFolderId = toFolder.ID; + var toFolderId = toFolder.ID; + var sb = new StringBuilder(); foreach (var fileId in fileIds) { CancellationToken.ThrowIfCancellationRequested(); @@ -428,7 +437,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations if (ProcessedFile(fileId)) { - Result += string.Format("file_{0}{1}", newFile.ID, SPLIT_CHAR); + sb.Append($"file_{newFile.ID}{SPLIT_CHAR}"); } } catch @@ -480,7 +489,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations if (ProcessedFile(fileId)) { - Result += string.Format("file_{0}{1}", newFileId, SPLIT_CHAR); + sb.Append($"file_{newFileId}{SPLIT_CHAR}"); } } } @@ -537,7 +546,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations filesMessageService.Send(newFile, toFolder, _headers, MessageAction.FileCopiedWithOverwriting, newFile.Title, parentFolder.Title, toFolder.Title); if (ProcessedFile(fileId)) { - Result += string.Format("file_{0}{1}", newFile.ID, SPLIT_CHAR); + sb.Append($"file_{newFile.ID}{SPLIT_CHAR}"); } } else @@ -546,7 +555,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations { if (ProcessedFile(fileId)) { - Result += string.Format("file_{0}{1}", newFile.ID, SPLIT_CHAR); + sb.Append($"file_{newFile.ID}{SPLIT_CHAR}"); } } else @@ -572,7 +581,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations if (ProcessedFile(fileId)) { - Result += string.Format("file_{0}{1}", newFile.ID, SPLIT_CHAR); + sb.Append($"file_{newFile.ID}{SPLIT_CHAR}"); } } } @@ -593,7 +602,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations } ProgressStep(fileId: FolderDao.CanCalculateSubitems(fileId) ? default : fileId); } - + Result = sb.ToString(); return needToMark; } diff --git a/products/ASC.Files/Core/Services/WCFService/FileOperations/FileOperation.cs b/products/ASC.Files/Core/Services/WCFService/FileOperations/FileOperation.cs index 8fb2f09096..cdcb7dd99e 100644 --- a/products/ASC.Files/Core/Services/WCFService/FileOperations/FileOperation.cs +++ b/products/ASC.Files/Core/Services/WCFService/FileOperations/FileOperation.cs @@ -79,7 +79,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations protected DistributedTask TaskInfo { get; set; } - public FileOperation(IServiceProvider serviceProvider) + protected FileOperation(IServiceProvider serviceProvider) { principal = serviceProvider.GetService<Microsoft.AspNetCore.Http.IHttpContextAccessor>()?.HttpContext?.User ?? Thread.CurrentPrincipal; culture = Thread.CurrentThread.CurrentCulture.Name; diff --git a/products/ASC.Files/Core/Services/WCFService/FileOperations/FileOperationsManager.cs b/products/ASC.Files/Core/Services/WCFService/FileOperations/FileOperationsManager.cs index ea9d56e9eb..3242aac74d 100644 --- a/products/ASC.Files/Core/Services/WCFService/FileOperations/FileOperationsManager.cs +++ b/products/ASC.Files/Core/Services/WCFService/FileOperations/FileOperationsManager.cs @@ -61,7 +61,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations var processlist = Process.GetProcesses(); //TODO: replace with distributed cache - if (processlist.Any()) + if (processlist.Length > 0) { foreach (var o in operations.Where(o => processlist.All(p => p.Id != o.InstanceId))) { @@ -254,7 +254,7 @@ namespace ASC.Web.Files.Services.WCFService.FileOperations } } - public class FileOperationsManagerHelperExtention + public static class FileOperationsManagerHelperExtention { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Services/WCFService/Wrappers/MentionWrapper.cs b/products/ASC.Files/Core/Services/WCFService/Wrappers/MentionWrapper.cs index eac97faedc..3b3efb88c3 100644 --- a/products/ASC.Files/Core/Services/WCFService/Wrappers/MentionWrapper.cs +++ b/products/ASC.Files/Core/Services/WCFService/Wrappers/MentionWrapper.cs @@ -37,13 +37,11 @@ namespace ASC.Web.Files.Services.WCFService public string Email { get { return User.Email; } - set { } } public string Id { get { return User.ID.ToString(); } - set { } } public bool HasAccess { get; set; } @@ -51,12 +49,11 @@ namespace ASC.Web.Files.Services.WCFService public string Name { get { return User.DisplayUserName(false, DisplayUserSettingsHelper); } - set { } } private DisplayUserSettingsHelper DisplayUserSettingsHelper { get; } - public UserInfo User; + public UserInfo User { get; set; } public MentionWrapper(UserInfo user, DisplayUserSettingsHelper displayUserSettingsHelper) { diff --git a/products/ASC.Files/Core/ThirdPartyApp/BoxApp.cs b/products/ASC.Files/Core/ThirdPartyApp/BoxApp.cs index 09295480fb..79098f10af 100644 --- a/products/ASC.Files/Core/ThirdPartyApp/BoxApp.cs +++ b/products/ASC.Files/Core/ThirdPartyApp/BoxApp.cs @@ -113,7 +113,8 @@ namespace ASC.Web.Files.ThirdPartyApp private DocumentServiceConnector DocumentServiceConnector { get; } private ThirdPartyAppHandlerService ThirdPartyAppHandlerService { get; } private IServiceProvider ServiceProvider { get; } - public ILog Logger { get; } + public ILog Logger { get; } + public IHttpClientFactory ClientFactory { get; } public BoxApp() { @@ -146,7 +147,8 @@ namespace ASC.Web.Files.ThirdPartyApp CoreSettings coreSettings, IConfiguration configuration, ICacheNotify<ConsumerCacheItem> cache, - ConsumerFactory consumerFactory, + ConsumerFactory consumerFactory, + IHttpClientFactory clientFactory, string name, int order, Dictionary<string, string> additional) : base(tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, name, order, additional) { @@ -170,7 +172,8 @@ namespace ASC.Web.Files.ThirdPartyApp DocumentServiceConnector = documentServiceConnector; ThirdPartyAppHandlerService = thirdPartyAppHandlerService; ServiceProvider = serviceProvider; - Logger = option.CurrentValue; + Logger = option.CurrentValue; + ClientFactory = clientFactory; } public bool Request(HttpContext context) @@ -198,11 +201,11 @@ namespace ASC.Web.Files.ThirdPartyApp public File<string> GetFile(string fileId, out bool editable) { Logger.Debug("BoxApp: get file " + fileId); - fileId = ThirdPartySelector.GetFileId(fileId.ToString()); + fileId = ThirdPartySelector.GetFileId(fileId); var token = TokenHelper.GetToken(AppAttr); - var boxFile = GetBoxFile(fileId.ToString(), token); + var boxFile = GetBoxFile(fileId, token); editable = true; if (boxFile == null) return null; @@ -220,13 +223,13 @@ namespace ASC.Web.Files.ThirdPartyApp var modifiedBy = jsonFile.Value<JObject>("modified_by"); if (modifiedBy != null) { - file._modifiedByString = modifiedBy.Value<string>("name"); + file.ModifiedByString = modifiedBy.Value<string>("name"); } var createdBy = jsonFile.Value<JObject>("created_by"); if (createdBy != null) { - file._createByString = createdBy.Value<string>("name"); + file.CreateByString = createdBy.Value<string>("name"); } @@ -275,11 +278,11 @@ namespace ASC.Web.Files.ThirdPartyApp (stream == null ? " from - " + downloadUrl : " from stream")); - fileId = ThirdPartySelector.GetFileId(fileId.ToString()); + fileId = ThirdPartySelector.GetFileId(fileId); var token = TokenHelper.GetToken(AppAttr); - var boxFile = GetBoxFile(fileId.ToString(), token); + var boxFile = GetBoxFile(fileId, token); if (boxFile == null) { Logger.Error("BoxApp: file is null"); @@ -311,7 +314,7 @@ namespace ASC.Web.Files.ThirdPartyApp } } - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); var request = new HttpRequestMessage(); request.RequestUri = new Uri(BoxUrlUpload.Replace("{fileId}", fileId)); @@ -320,8 +323,8 @@ namespace ASC.Web.Files.ThirdPartyApp { var boundary = DateTime.UtcNow.Ticks.ToString("x"); - var metadata = string.Format("Content-Disposition: form-data; name=\"filename\"; filename=\"{0}\"\r\nContent-Type: application/octet-stream\r\n\r\n", title); - var metadataPart = string.Format("--{0}\r\n{1}", boundary, metadata); + var metadata = $"Content-Disposition: form-data; name=\"filename\"; filename=\"{title}\"\r\nContent-Type: application/octet-stream\r\n\r\n"; + var metadataPart = $"--{boundary}\r\n{metadata}"; var bytes = Encoding.UTF8.GetBytes(metadataPart); tmpStream.Write(bytes, 0, bytes.Length); @@ -338,7 +341,7 @@ namespace ASC.Web.Files.ThirdPartyApp downloadStream.CopyTo(tmpStream); } - var mediaPartEnd = string.Format("\r\n--{0}--\r\n", boundary); + var mediaPartEnd = $"\r\n--{boundary}--\r\n"; bytes = Encoding.UTF8.GetBytes(mediaPartEnd); tmpStream.Write(bytes, 0, bytes.Length); @@ -472,7 +475,7 @@ namespace ASC.Web.Files.ThirdPartyApp request.Method = HttpMethod.Get; request.Headers.Add("Authorization", "Bearer " + token); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using var stream = new ResponseStream(response); stream.CopyTo(context.Response.Body); @@ -500,7 +503,7 @@ namespace ASC.Web.Files.ThirdPartyApp private bool CurrentUser(string boxUserId) { var linkedProfiles = Snapshot.Get("webstudio") - .GetLinkedObjectsByHashId(HashHelper.MD5(string.Format("{0}/{1}", ProviderConstants.Box, boxUserId))); + .GetLinkedObjectsByHashId(HashHelper.MD5($"{ProviderConstants.Box}/{boxUserId}")); return linkedProfiles.Any(profileId => Guid.TryParse(profileId, out var tmp) && tmp == AuthContext.CurrentAccount.ID); } diff --git a/products/ASC.Files/Core/ThirdPartyApp/GoogleDriveApp.cs b/products/ASC.Files/Core/ThirdPartyApp/GoogleDriveApp.cs index fbcac00041..d0b46d092c 100644 --- a/products/ASC.Files/Core/ThirdPartyApp/GoogleDriveApp.cs +++ b/products/ASC.Files/Core/ThirdPartyApp/GoogleDriveApp.cs @@ -119,7 +119,8 @@ namespace ASC.Web.Files.ThirdPartyApp private TokenHelper TokenHelper { get; } private DocumentServiceConnector DocumentServiceConnector { get; } private ThirdPartyAppHandlerService ThirdPartyAppHandlerService { get; } - private IServiceProvider ServiceProvider { get; } + private IServiceProvider ServiceProvider { get; } + private IHttpClientFactory ClientFactory { get; } public GoogleDriveApp() { @@ -156,7 +157,8 @@ namespace ASC.Web.Files.ThirdPartyApp CoreSettings coreSettings, IConfiguration configuration, ICacheNotify<ConsumerCacheItem> cache, - ConsumerFactory consumerFactory, + ConsumerFactory consumerFactory, + IHttpClientFactory clientFactory, string name, int order, Dictionary<string, string> additional) : base(tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, name, order, additional) { @@ -184,7 +186,8 @@ namespace ASC.Web.Files.ThirdPartyApp TokenHelper = tokenHelper; DocumentServiceConnector = documentServiceConnector; ThirdPartyAppHandlerService = thirdPartyAppHandlerService; - ServiceProvider = serviceProvider; + ServiceProvider = serviceProvider; + ClientFactory = clientFactory; } public bool Request(HttpContext context) @@ -235,13 +238,13 @@ namespace ASC.Web.Files.ThirdPartyApp file.CreateOn = TenantUtil.DateTimeFromUtc(jsonFile.Value<DateTime>("createdTime")); file.ModifiedOn = TenantUtil.DateTimeFromUtc(jsonFile.Value<DateTime>("modifiedTime")); file.ContentLength = Convert.ToInt64(jsonFile.Value<string>("size")); - file._modifiedByString = jsonFile["lastModifyingUser"]["displayName"].Value<string>(); + file.ModifiedByString = jsonFile["lastModifyingUser"]["displayName"].Value<string>(); file.ProviderKey = "Google"; var owners = jsonFile["owners"]; if (owners != null) { - file._createByString = owners[0]["displayName"].Value<string>(); + file.CreateByString = owners[0]["displayName"].Value<string>(); } editable = jsonFile["capabilities"]["canEdit"].Value<bool>(); @@ -252,7 +255,7 @@ namespace ASC.Web.Files.ThirdPartyApp { if (file == null) return string.Empty; - var fileId = ThirdPartySelector.GetFileId(file.ID.ToString()); + var fileId = ThirdPartySelector.GetFileId(file.ID); return GetFileStreamUrl(fileId); } @@ -316,7 +319,7 @@ namespace ASC.Web.Files.ThirdPartyApp } } - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); var request = new HttpRequestMessage(); request.RequestUri = new Uri(GoogleLoginProvider.GoogleUrlFileUpload + "/{fileId}?uploadType=media".Replace("{fileId}", fileId)); @@ -330,7 +333,6 @@ namespace ASC.Web.Files.ThirdPartyApp } else { - var downloadRequest = new HttpRequestMessage(); using var response = httpClient.Send(request); using var downloadStream = new ResponseStream(response); @@ -523,7 +525,7 @@ namespace ASC.Web.Files.ThirdPartyApp request.Method = HttpMethod.Get; request.Headers.Add("Authorization", "Bearer " + token); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using var stream = new ResponseStream(response); stream.CopyTo(context.Response.Body); @@ -625,8 +627,8 @@ namespace ASC.Web.Files.ThirdPartyApp private bool CurrentUser(string googleId) { var linker = Snapshot.Get("webstudio"); - var linkedProfiles = linker.GetLinkedObjectsByHashId(HashHelper.MD5(string.Format("{0}/{1}", ProviderConstants.Google, googleId))); - linkedProfiles = linkedProfiles.Concat(linker.GetLinkedObjectsByHashId(HashHelper.MD5(string.Format("{0}/{1}", ProviderConstants.OpenId, googleId)))); + var linkedProfiles = linker.GetLinkedObjectsByHashId(HashHelper.MD5($"{ProviderConstants.Google}/{googleId}")); + linkedProfiles = linkedProfiles.Concat(linker.GetLinkedObjectsByHashId(HashHelper.MD5($"{ProviderConstants.OpenId}/{googleId}"))); return linkedProfiles.Any(profileId => Guid.TryParse(profileId, out var tmp) && tmp == AuthContext.CurrentAccount.ID); } @@ -733,7 +735,7 @@ namespace ASC.Web.Files.ThirdPartyApp var request = new HttpRequestMessage(); request.RequestUri = new Uri(contentUrl); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using var content = new ResponseStream(response); return CreateFile(content, fileName, folderId, token); @@ -743,7 +745,7 @@ namespace ASC.Web.Files.ThirdPartyApp { Logger.Debug("GoogleDriveApp: create file"); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); var request = new HttpRequestMessage(); request.RequestUri = new Uri(GoogleLoginProvider.GoogleUrlFileUpload + "?uploadType=multipart"); @@ -752,19 +754,19 @@ namespace ASC.Web.Files.ThirdPartyApp { var boundary = DateTime.UtcNow.Ticks.ToString("x"); - var folderdata = string.IsNullOrEmpty(folderId) ? "" : string.Format(",\"parents\":[\"{0}\"]", folderId); - var metadata = string.Format("{{\"name\":\"{0}\"{1}}}", fileName, folderdata); - var metadataPart = string.Format("\r\n--{0}\r\nContent-Type: application/json; charset=UTF-8\r\n\r\n{1}", boundary, metadata); + var folderdata = string.IsNullOrEmpty(folderId) ? "" : $",\"parents\":[\"{folderId}\"]"; + var metadata = "{{\"name\":\"" + fileName + "\"" + folderdata + "}}"; + var metadataPart = $"\r\n--{boundary}\r\nContent-Type: application/json; charset=UTF-8\r\n\r\n{metadata}"; var bytes = Encoding.UTF8.GetBytes(metadataPart); tmpStream.Write(bytes, 0, bytes.Length); - var mediaPartStart = string.Format("\r\n--{0}\r\nContent-Type: {1}\r\n\r\n", boundary, MimeMapping.GetMimeMapping(fileName)); + var mediaPartStart = $"\r\n--{boundary}\r\nContent-Type: {MimeMapping.GetMimeMapping(fileName)}\r\n\r\n"; bytes = Encoding.UTF8.GetBytes(mediaPartStart); tmpStream.Write(bytes, 0, bytes.Length); content.CopyTo(tmpStream); - var mediaPartEnd = string.Format("\r\n--{0}--\r\n", boundary); + var mediaPartEnd = $"\r\n--{boundary}--\r\n"; bytes = Encoding.UTF8.GetBytes(mediaPartEnd); tmpStream.Write(bytes, 0, bytes.Length); @@ -843,12 +845,9 @@ namespace ASC.Web.Files.ThirdPartyApp fileName = FileUtility.ReplaceFileExtension(fileName, internalExt); var requiredMimeType = MimeMapping.GetMimeMapping(internalExt); - var downloadUrl = GoogleLoginProvider.GoogleUrlFile - + string.Format("{0}/export?mimeType={1}", - fileId, - HttpUtility.UrlEncode(requiredMimeType)); + var downloadUrl = GoogleLoginProvider.GoogleUrlFile + $"{fileId}/export?mimeType={HttpUtility.UrlEncode(requiredMimeType)}"; - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); var request = new HttpRequestMessage(); request.RequestUri = new Uri(downloadUrl); diff --git a/products/ASC.Files/Core/ThirdPartyApp/IThirdPartyApp.cs b/products/ASC.Files/Core/ThirdPartyApp/IThirdPartyApp.cs index fec6bb4e06..2d9df9b6a8 100644 --- a/products/ASC.Files/Core/ThirdPartyApp/IThirdPartyApp.cs +++ b/products/ASC.Files/Core/ThirdPartyApp/IThirdPartyApp.cs @@ -46,7 +46,7 @@ namespace ASC.Web.Files.ThirdPartyApp void SaveFile(string fileId, string fileType, string downloadUrl, Stream stream); } - public class ThirdPartySelector + public static class ThirdPartySelector { public const string AppAttr = "app"; public static readonly Regex AppRegex = new Regex("^" + AppAttr + @"-(\S+)\|(\S+)$", RegexOptions.Singleline | RegexOptions.Compiled); diff --git a/products/ASC.Files/Core/Utils/EntryManager.cs b/products/ASC.Files/Core/Utils/EntryManager.cs index d02de154d6..7b3b69b09f 100644 --- a/products/ASC.Files/Core/Utils/EntryManager.cs +++ b/products/ASC.Files/Core/Utils/EntryManager.cs @@ -28,10 +28,8 @@ using System; using System.Collections.Generic; using System.IO; using System.Linq; -using System.Net; using System.Net.Http; using System.Security; -using System.Text; using System.Threading; using ASC.Common; @@ -55,8 +53,6 @@ using ASC.Web.Studio.Core; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Options; -using Newtonsoft.Json.Linq; - using FileShare = ASC.Files.Core.Security.FileShare; namespace ASC.Web.Files.Utils @@ -253,7 +249,6 @@ namespace ASC.Web.Files.Utils private FilesIntegration FilesIntegration { get; } private FileMarker FileMarker { get; } private FileUtility FileUtility { get; } - private Global Global { get; } private GlobalStore GlobalStore { get; } private CoreBaseSettings CoreBaseSettings { get; } private FilesSettingsHelper FilesSettingsHelper { get; } @@ -267,7 +262,8 @@ namespace ASC.Web.Files.Utils private TenantManager TenantManager { get; } private SettingsManager SettingsManager { get; } private IServiceProvider ServiceProvider { get; } - private ILog Logger { get; } + private ILog Logger { get; } + private IHttpClientFactory ClientFactory { get; } public EntryManager( IDaoFactory daoFactory, @@ -278,7 +274,6 @@ namespace ASC.Web.Files.Utils FilesIntegration filesIntegration, FileMarker fileMarker, FileUtility fileUtility, - Global global, GlobalStore globalStore, CoreBaseSettings coreBaseSettings, FilesSettingsHelper filesSettingsHelper, @@ -295,7 +290,8 @@ namespace ASC.Web.Files.Utils IServiceProvider serviceProvider, ICache cache, FileTrackerHelper fileTracker, - EntryStatusManager entryStatusManager) + EntryStatusManager entryStatusManager, + IHttpClientFactory clientFactory) { DaoFactory = daoFactory; FileSecurity = fileSecurity; @@ -305,7 +301,6 @@ namespace ASC.Web.Files.Utils FilesIntegration = filesIntegration; FileMarker = fileMarker; FileUtility = fileUtility; - Global = global; GlobalStore = globalStore; CoreBaseSettings = coreBaseSettings; FilesSettingsHelper = filesSettingsHelper; @@ -323,13 +318,14 @@ namespace ASC.Web.Files.Utils Cache = cache; FileTracker = fileTracker; EntryStatusManager = entryStatusManager; + ClientFactory = clientFactory; } public IEnumerable<FileEntry> GetEntries<T>(Folder<T> parent, int from, int count, FilterType filter, bool subjectGroup, Guid subjectId, string searchText, bool searchInContent, bool withSubfolders, OrderBy orderBy, out int total) { total = 0; - if (parent == null) throw new ArgumentNullException("parent", FilesCommonResource.ErrorMassage_FolderNotFound); + if (parent == null) throw new ArgumentNullException(nameof(parent), FilesCommonResource.ErrorMassage_FolderNotFound); if (parent.ProviderEntry && !FilesSettingsHelper.EnableThirdParty) throw new SecurityException(FilesCommonResource.ErrorMassage_SecurityException_ReadFolder); if (parent.RootFolderType == FolderType.Privacy && (!PrivacyRoomSettings.IsAvailable(TenantManager) || !PrivacyRoomSettings.GetEnabled(SettingsManager))) throw new SecurityException(FilesCommonResource.ErrorMassage_SecurityException_ReadFolder); @@ -344,101 +340,99 @@ namespace ASC.Web.Files.Utils //var apiServer = new ASC.Api.ApiServer(); //var apiUrl = string.Format("{0}project/maxlastmodified.json", SetupInfo.WebApiBaseUrl); - string responseBody = null;// apiServer.GetApiResponse(apiUrl, "GET"); - if (responseBody != null) - { - var responseApi = JObject.Parse(Encoding.UTF8.GetString(Convert.FromBase64String(responseBody))); + //const string responseBody = null;// apiServer.GetApiResponse(apiUrl, "GET"); + //if (responseBody != null) + //{ + // JObject responseApi; - var projectLastModified = responseApi["response"].Value<string>(); - var projectListCacheKey = string.Format("documents/projectFolders/{0}", AuthContext.CurrentAccount.ID); - Dictionary<int, KeyValuePair<int, string>> folderIDProjectTitle = null; + // Dictionary<int, KeyValuePair<int, string>> folderIDProjectTitle = null; - if (folderIDProjectTitle == null) - { - //apiUrl = string.Format("{0}project/filter.json?sortBy=title&sortOrder=ascending&status=open&fields=id,title,security,projectFolder", SetupInfo.WebApiBaseUrl); + // if (folderIDProjectTitle == null) + // { + // //apiUrl = string.Format("{0}project/filter.json?sortBy=title&sortOrder=ascending&status=open&fields=id,title,security,projectFolder", SetupInfo.WebApiBaseUrl); - responseApi = JObject.Parse(""); //Encoding.UTF8.GetString(Convert.FromBase64String(apiServer.GetApiResponse(apiUrl, "GET")))); + // responseApi = JObject.Parse(""); //Encoding.UTF8.GetString(Convert.FromBase64String(apiServer.GetApiResponse(apiUrl, "GET")))); - var responseData = responseApi["response"]; + // var responseData = responseApi["response"]; - if (!(responseData is JArray)) return entries.ToList(); + // if (!(responseData is JArray)) return entries.ToList(); - folderIDProjectTitle = new Dictionary<int, KeyValuePair<int, string>>(); - foreach (JObject projectInfo in responseData.Children()) - { - var projectID = projectInfo["id"].Value<int>(); - var projectTitle = Global.ReplaceInvalidCharsAndTruncate(projectInfo["title"].Value<string>()); + // folderIDProjectTitle = new Dictionary<int, KeyValuePair<int, string>>(); + // foreach (JObject projectInfo in responseData.Children().OfType<JObject>()) + // { + // var projectID = projectInfo["id"].Value<int>(); + // var projectTitle = Global.ReplaceInvalidCharsAndTruncate(projectInfo["title"].Value<string>()); - if (projectInfo.TryGetValue("security", out var projectSecurityJToken)) - { - var projectSecurity = projectInfo["security"].Value<JObject>(); - if (projectSecurity.TryGetValue("canReadFiles", out var projectCanFileReadJToken)) - { - if (!projectSecurity["canReadFiles"].Value<bool>()) - { - continue; - } - } - } + // if (projectInfo.TryGetValue("security", out var projectSecurityJToken)) + // { + // var projectSecurity = projectInfo["security"].Value<JObject>(); + // if (projectSecurity.TryGetValue("canReadFiles", out var projectCanFileReadJToken)) + // { + // if (!projectSecurity["canReadFiles"].Value<bool>()) + // { + // continue; + // } + // } + // } - int projectFolderID; - if (projectInfo.TryGetValue("projectFolder", out var projectFolderIDjToken)) - projectFolderID = projectFolderIDjToken.Value<int>(); - else - projectFolderID = FilesIntegration.RegisterBunch<int>("projects", "project", projectID.ToString()); + // int projectFolderID; + // if (projectInfo.TryGetValue("projectFolder", out var projectFolderIDjToken)) + // projectFolderID = projectFolderIDjToken.Value<int>(); + // else + // projectFolderID = FilesIntegration.RegisterBunch<int>("projects", "project", projectID.ToString()); - if (!folderIDProjectTitle.ContainsKey(projectFolderID)) - folderIDProjectTitle.Add(projectFolderID, new KeyValuePair<int, string>(projectID, projectTitle)); + // if (!folderIDProjectTitle.ContainsKey(projectFolderID)) + // folderIDProjectTitle.Add(projectFolderID, new KeyValuePair<int, string>(projectID, projectTitle)); - Cache.Remove("documents/folders/" + projectFolderID); - Cache.Insert("documents/folders/" + projectFolderID, projectTitle, TimeSpan.FromMinutes(30)); - } - } + // Cache.Remove("documents/folders/" + projectFolderID); + // Cache.Insert("documents/folders/" + projectFolderID, projectTitle, TimeSpan.FromMinutes(30)); + // } + // } - var rootKeys = folderIDProjectTitle.Keys.ToArray(); - if (filter == FilterType.None || filter == FilterType.FoldersOnly) - { - var folders = DaoFactory.GetFolderDao<int>().GetFolders(rootKeys, filter, subjectGroup, subjectId, searchText, withSubfolders, false); + // var rootKeys = folderIDProjectTitle.Keys.ToArray(); + // if (filter == FilterType.None || filter == FilterType.FoldersOnly) + // { + // var folders = DaoFactory.GetFolderDao<int>().GetFolders(rootKeys, filter, subjectGroup, subjectId, searchText, withSubfolders, false); - var emptyFilter = string.IsNullOrEmpty(searchText) && filter == FilterType.None && subjectId == Guid.Empty; - if (!emptyFilter) - { - var projectFolderIds = - folderIDProjectTitle - .Where(projectFolder => string.IsNullOrEmpty(searchText) - || (projectFolder.Value.Value ?? "").ToLower().Trim().Contains(searchText.ToLower().Trim())) - .Select(projectFolder => projectFolder.Key); + // var emptyFilter = string.IsNullOrEmpty(searchText) && filter == FilterType.None && subjectId == Guid.Empty; + // if (!emptyFilter) + // { + // var projectFolderIds = + // folderIDProjectTitle + // .Where(projectFolder => string.IsNullOrEmpty(searchText) + // || (projectFolder.Value.Value ?? "").ToLower().Trim().Contains(searchText.ToLower().Trim())) + // .Select(projectFolder => projectFolder.Key); - folders.RemoveAll(folder => rootKeys.Contains(folder.ID)); + // folders.RemoveAll(folder => rootKeys.Contains(folder.ID)); - var projectFolders = DaoFactory.GetFolderDao<int>().GetFolders(projectFolderIds.ToList(), filter, subjectGroup, subjectId, null, false, false); - folders.AddRange(projectFolders); - } + // var projectFolders = DaoFactory.GetFolderDao<int>().GetFolders(projectFolderIds.ToList(), filter, subjectGroup, subjectId, null, false, false); + // folders.AddRange(projectFolders); + // } - folders.ForEach(x => - { - x.Title = folderIDProjectTitle.ContainsKey(x.ID) ? folderIDProjectTitle[x.ID].Value : x.Title; - x.FolderUrl = folderIDProjectTitle.ContainsKey(x.ID) ? PathProvider.GetFolderUrl(x, folderIDProjectTitle[x.ID].Key) : string.Empty; - }); + // folders.ForEach(x => + // { + // x.Title = folderIDProjectTitle.ContainsKey(x.ID) ? folderIDProjectTitle[x.ID].Value : x.Title; + // x.FolderUrl = folderIDProjectTitle.ContainsKey(x.ID) ? PathProvider.GetFolderUrl(x, folderIDProjectTitle[x.ID].Key) : string.Empty; + // }); - if (withSubfolders) - { - entries = entries.Concat(fileSecurity.FilterRead(folders)); - } - else - { - entries = entries.Concat(folders); - } - } + // if (withSubfolders) + // { + // entries = entries.Concat(fileSecurity.FilterRead(folders)); + // } + // else + // { + // entries = entries.Concat(folders); + // } + // } - if (filter != FilterType.FoldersOnly && withSubfolders) - { - var files = DaoFactory.GetFileDao<int>().GetFiles(rootKeys, filter, subjectGroup, subjectId, searchText, searchInContent); - entries = entries.Concat(fileSecurity.FilterRead(files)); - } - } + // if (filter != FilterType.FoldersOnly && withSubfolders) + // { + // var files = DaoFactory.GetFileDao<int>().GetFiles(rootKeys, filter, subjectGroup, subjectId, searchText, searchInContent); + // entries = entries.Concat(fileSecurity.FilterRead(files)); + // } + //} - CalculateTotal(); + //CalculateTotal(); } else if (parent.FolderType == FolderType.SHARE) { @@ -458,9 +452,6 @@ namespace ASC.Web.Files.Utils } else if (parent.FolderType == FolderType.Favorites) { - var fileDao = DaoFactory.GetFileDao<T>(); - var folderDao = DaoFactory.GetFolderDao<T>(); - var (files, folders) = GetFavorites(filter, subjectGroup, subjectId, searchText, searchInContent); entries = entries.Concat(folders); @@ -591,19 +582,20 @@ namespace ASC.Web.Files.Utils var providers = providerDao.GetProvidersInfo(parent.RootFolderType, searchText); folderList = providers - .Select(providerInfo => GetFakeThirdpartyFolder<T>(providerInfo, parent.ID.ToString())) + .Select(providerInfo => GetFakeThirdpartyFolder(providerInfo, parent.ID.ToString())) .Where(r => fileSecurity.CanRead(r)).ToList(); - if (folderList.Any()) + if (folderList.Count > 0) { var securityDao = DaoFactory.GetSecurityDao<string>(); - securityDao.GetPureShareRecords(folderList) + var ids = securityDao.GetPureShareRecords(folderList) //.Where(x => x.Owner == SecurityContext.CurrentAccount.ID) - .Select(x => x.EntryId).Distinct().ToList() - .ForEach(id => - { - folderList.First(y => y.ID.Equals(id)).Shared = true; - }); + .Select(x => x.EntryId).Distinct(); + + foreach (var id in ids) + { + folderList.First(y => y.ID.Equals(id)).Shared = true; + } } } @@ -656,7 +648,6 @@ namespace ASC.Web.Files.Utils public (IEnumerable<FileEntry>, IEnumerable<FileEntry>) GetFavorites(FilterType filter, bool subjectGroup, Guid subjectId, string searchText, bool searchInContent) { - var fileSecurity = FileSecurity; var tagDao = DaoFactory.GetTagDao<int>(); var tags = tagDao.GetTags(AuthContext.CurrentAccount.ID, TagType.Favorite); @@ -748,10 +739,12 @@ namespace ASC.Web.Files.Utils { entries = entries.Where(where).ToList(); } + + searchText = (searchText ?? string.Empty).ToLower().Trim(); - if ((!searchInContent || filter == FilterType.ByExtension) && !string.IsNullOrEmpty(searchText = (searchText ?? string.Empty).ToLower().Trim())) + if ((!searchInContent || filter == FilterType.ByExtension) && !string.IsNullOrEmpty(searchText)) { - entries = entries.Where(f => f.Title.ToLower().Contains(searchText)).ToList(); + entries = entries.Where(f => f.Title.Contains(searchText, StringComparison.InvariantCultureIgnoreCase)).ToList(); } return entries; } @@ -772,7 +765,7 @@ namespace ASC.Web.Files.Utils { var cmp = 0; if (x.FileEntryType == FileEntryType.File && y.FileEntryType == FileEntryType.File) - cmp = c * (FileUtility.GetFileExtension((x.Title)).CompareTo(FileUtility.GetFileExtension(y.Title))); + cmp = c * FileUtility.GetFileExtension(x.Title).CompareTo(FileUtility.GetFileExtension(y.Title)); return cmp == 0 ? x.Title.EnumerableComparer(y.Title) : cmp; } , @@ -829,7 +822,7 @@ namespace ASC.Web.Files.Utils return result; } - public Folder<string> GetFakeThirdpartyFolder<T>(IProviderInfo providerInfo, string parentFolderId = null) + public Folder<string> GetFakeThirdpartyFolder(IProviderInfo providerInfo, string parentFolderId = null) { //Fake folder. Don't send request to third party var folder = ServiceProvider.GetService<Folder<string>>(); @@ -1096,15 +1089,10 @@ namespace ASC.Web.Files.Utils } else { - // hack. http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono) - { - ServicePointManager.ServerCertificateValidationCallback += (s, ce, ca, p) => true; - } var request = new HttpRequestMessage(); request.RequestUri = new Uri(downloadUri); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using var editedFileStream = new ResponseStream(response); editedFileStream.CopyTo(tmpStream); @@ -1175,7 +1163,7 @@ namespace ASC.Web.Files.Utils public File<T> UpdateToVersionFile<T>(T fileId, int version, string doc = null, bool checkRight = true) { var fileDao = DaoFactory.GetFileDao<T>(); - if (version < 1) throw new ArgumentNullException("version"); + if (version < 1) throw new ArgumentNullException(nameof(version)); var editLink = FileShareLink.Check(doc, false, fileDao, out var fromFile); @@ -1326,7 +1314,7 @@ namespace ASC.Web.Files.Utils title = Global.ReplaceInvalidCharsAndTruncate(title); var ext = FileUtility.GetFileExtension(file.Title); - if (string.Compare(ext, FileUtility.GetFileExtension(title), true) != 0) + if (!string.Equals(ext, FileUtility.GetFileExtension(title), StringComparison.InvariantCultureIgnoreCase)) { title += ext; } @@ -1334,7 +1322,7 @@ namespace ASC.Web.Files.Utils var fileAccess = file.Access; var renamed = false; - if (string.Compare(file.Title, title, false) != 0) + if (!string.Equals(file.Title, title)) { var newFileID = fileDao.FileRename(file, title); diff --git a/products/ASC.Files/Core/Utils/FileConverter.cs b/products/ASC.Files/Core/Utils/FileConverter.cs index 27ae2aac45..8728933fa6 100644 --- a/products/ASC.Files/Core/Utils/FileConverter.cs +++ b/products/ASC.Files/Core/Utils/FileConverter.cs @@ -170,15 +170,16 @@ namespace ASC.Web.Files.Utils { timer.Change(Timeout.Infinite, Timeout.Infinite); - conversionQueue.Where(x => !string.IsNullOrEmpty(x.Value.Processed) + var queues = conversionQueue.Where(x => !string.IsNullOrEmpty(x.Value.Processed) && (x.Value.Progress == 100 && DateTime.UtcNow - x.Value.StopDateTime > TimeSpan.FromMinutes(1) || - DateTime.UtcNow - x.Value.StopDateTime > TimeSpan.FromMinutes(10))) - .ToList() - .ForEach(x => - { - conversionQueue.Remove(x); - cache.Remove(GetKey(x.Key)); - }); + DateTime.UtcNow - x.Value.StopDateTime > TimeSpan.FromMinutes(10))) + .ToList(); + + foreach (var q in queues) + { + conversionQueue.Remove(q); + cache.Remove(GetKey(q.Key)); + } logger.DebugFormat("Run CheckConvertFilesStatus: count {0}", conversionQueue.Count); @@ -265,16 +266,14 @@ namespace ASC.Web.Files.Utils } catch (Exception exception) { - var password = exception.InnerException != null - && (exception.InnerException is DocumentService.DocumentServiceException documentServiceException) + var password = exception.InnerException is DocumentService.DocumentServiceException documentServiceException && documentServiceException.Code == DocumentService.DocumentServiceException.ErrorCode.ConvertPassword; logger.Error(string.Format("Error convert {0} with url {1}", file.ID, fileUri), exception); lock (locker) { - if (conversionQueue.Keys.Contains(file)) + if (conversionQueue.TryGetValue(file, out var operationResult)) { - var operationResult = conversionQueue[file]; if (operationResult.Delete) { conversionQueue.Remove(file); @@ -298,10 +297,8 @@ namespace ASC.Web.Files.Utils { lock (locker) { - if (conversionQueue.Keys.Contains(file)) + if (conversionQueue.TryGetValue(file, out var operationResult)) { - var operationResult = conversionQueue[file]; - if (DateTime.Now - operationResult.StartDateTime > TimeSpan.FromMinutes(10)) { operationResult.StopDateTime = DateTime.UtcNow; @@ -339,9 +336,8 @@ namespace ASC.Web.Files.Utils { lock (locker) { - if (conversionQueue.Keys.Contains(file)) + if (conversionQueue.TryGetValue(file, out var operationResult)) { - var operationResult = conversionQueue[file]; if (operationResult.Delete) { conversionQueue.Remove(file); @@ -543,7 +539,8 @@ namespace ASC.Web.Files.Utils private BaseCommonLinkUtility BaseCommonLinkUtility { get; } private EntryStatusManager EntryStatusManager { get; } private IServiceProvider ServiceProvider { get; } - private IHttpContextAccessor HttpContextAccesor { get; } + private IHttpContextAccessor HttpContextAccesor { get; } + private IHttpClientFactory ClientFactory { get; } public FileConverter( FileUtility fileUtility, @@ -565,7 +562,8 @@ namespace ASC.Web.Files.Utils FileTrackerHelper fileTracker, BaseCommonLinkUtility baseCommonLinkUtility, EntryStatusManager entryStatusManager, - IServiceProvider serviceProvider) + IServiceProvider serviceProvider, + IHttpClientFactory clientFactory) { FileUtility = fileUtility; FilesLinkUtility = filesLinkUtility; @@ -586,7 +584,8 @@ namespace ASC.Web.Files.Utils FileTracker = fileTracker; BaseCommonLinkUtility = baseCommonLinkUtility; EntryStatusManager = entryStatusManager; - ServiceProvider = serviceProvider; + ServiceProvider = serviceProvider; + ClientFactory = clientFactory; } public FileConverter( FileUtility fileUtility, @@ -609,18 +608,19 @@ namespace ASC.Web.Files.Utils BaseCommonLinkUtility baseCommonLinkUtility, EntryStatusManager entryStatusManager, IServiceProvider serviceProvider, - IHttpContextAccessor httpContextAccesor) + IHttpContextAccessor httpContextAccesor, + IHttpClientFactory clientFactory) : this(fileUtility, filesLinkUtility, daoFactory, setupInfo, pathProvider, fileSecurity, fileMarker, tenantManager, authContext, entryManager, filesSettingsHelper, globalFolderHelper, filesMessageService, fileShareLink, documentServiceHelper, documentServiceConnector, fileTracker, - baseCommonLinkUtility, entryStatusManager, serviceProvider) + baseCommonLinkUtility, entryStatusManager, serviceProvider, clientFactory) { HttpContextAccesor = httpContextAccesor; } public bool EnableAsUploaded { - get { return FileUtility.ExtsMustConvert.Any() && !string.IsNullOrEmpty(FilesLinkUtility.DocServiceConverterUrl); } + get { return FileUtility.ExtsMustConvert.Count > 0 && !string.IsNullOrEmpty(FilesLinkUtility.DocServiceConverterUrl); } } public bool MustConvert<T>(File<T> file) @@ -680,15 +680,11 @@ namespace ASC.Web.Files.Utils var docKey = DocumentServiceHelper.GetDocKey(file); fileUri = DocumentServiceConnector.ReplaceCommunityAdress(fileUri); DocumentServiceConnector.GetConvertedUri(fileUri, file.ConvertedExtension, toExtension, docKey, null, null, null, false, out var convertUri); - - if (WorkContext.IsMono && ServicePointManager.ServerCertificateValidationCallback == null) - { - ServicePointManager.ServerCertificateValidationCallback += (s, c, n, p) => true; //HACK: http://ubuntuforums.org/showthread.php?t=1841740 - } + var request = new HttpRequestMessage(); request.RequestUri = new Uri(convertUri); - using var httpClient = new HttpClient(); + using var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); return new ResponseStream(response); } @@ -702,7 +698,7 @@ namespace ASC.Web.Files.Utils var readLink = FileShareLink.Check(doc, true, fileDao, out file); if (file == null) { - throw new ArgumentNullException("file", FilesCommonResource.ErrorMassage_FileNotFound); + throw new ArgumentNullException(nameof(file), FilesCommonResource.ErrorMassage_FileNotFound); } if (!readLink) { @@ -856,12 +852,7 @@ namespace ASC.Web.Files.Utils var request = new HttpRequestMessage(); request.RequestUri = new Uri(convertedFileUrl); - using var httpClient = new HttpClient(); - - if (WorkContext.IsMono && ServicePointManager.ServerCertificateValidationCallback == null) - { - ServicePointManager.ServerCertificateValidationCallback += (s, c, n, p) => true; //HACK: http://ubuntuforums.org/showthread.php?t=1841740 - } + var httpClient = ClientFactory.CreateClient(); try { @@ -872,13 +863,13 @@ namespace ASC.Web.Files.Utils } catch (HttpRequestException e) { - var errorString = string.Format("HttpRequestException: {0}", e.StatusCode); + var errorString = $"HttpRequestException: {e.StatusCode}"; if (e.StatusCode != HttpStatusCode.NotFound) { if (e.Message != null) { - errorString += string.Format(" Error message: {0}", e.Message); + errorString += $" Error message: {e.Message}"; } } @@ -894,7 +885,7 @@ namespace ASC.Web.Files.Utils var tagDao = DaoFactory.GetTagDao<T>(); var tags = tagDao.GetTags(file.ID, FileEntryType.File, TagType.System).ToList(); - if (tags.Any()) + if (tags.Count > 0) { tags.ForEach(r => r.EntryId = newFile.ID); tagDao.SaveTags(tags); @@ -941,7 +932,7 @@ namespace ASC.Web.Files.Utils public string ServerRootPath { get; set; } } - public class FileConverterQueueExtension + public static class FileConverterQueueExtension { public static void Register(DIHelper services) { @@ -949,7 +940,7 @@ namespace ASC.Web.Files.Utils } } - public class FileConverterExtension + public static class FileConverterExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Utils/FileMarker.cs b/products/ASC.Files/Core/Utils/FileMarker.cs index facfb661f5..696b110726 100644 --- a/products/ASC.Files/Core/Utils/FileMarker.cs +++ b/products/ASC.Files/Core/Utils/FileMarker.cs @@ -126,7 +126,7 @@ namespace ASC.Web.Files.Utils internal void ExecMarkFileAsNew<T>(AsyncTaskData<T> obj) { - TenantManager.SetCurrentTenant(Convert.ToInt32(obj.TenantID)); + TenantManager.SetCurrentTenant(obj.TenantID); var folderDao = DaoFactory.GetFolderDao<T>(); T parentFolderId; @@ -144,7 +144,7 @@ namespace ASC.Web.Files.Utils if (obj.FileEntry.RootFolderType == FolderType.BUNCH) { - if (!userIDs.Any()) return; + if (userIDs.Count == 0) return; parentFolders.Add(folderDao.GetFolder(GlobalFolder.GetFolderProjects<T>(DaoFactory))); @@ -153,8 +153,8 @@ namespace ASC.Web.Files.Utils userIDs.ForEach(userID => { - if (userEntriesData.ContainsKey(userID)) - userEntriesData[userID].AddRange(entries); + if (userEntriesData.TryGetValue(userID, out var value)) + value.AddRange(entries); else userEntriesData.Add(userID, entries); @@ -165,30 +165,29 @@ namespace ASC.Web.Files.Utils { var filesSecurity = FileSecurity; - if (!userIDs.Any()) + if (userIDs.Count == 0) { userIDs = filesSecurity.WhoCanRead(obj.FileEntry).Where(x => x != obj.CurrentAccountId).ToList(); } if (obj.FileEntry.ProviderEntry) { userIDs = userIDs.Where(u => !UserManager.GetUsers(u).IsVisitor(UserManager)).ToList(); + } + + foreach(var parentFolder in parentFolders) + { + var ids = filesSecurity + .WhoCanRead(parentFolder) + .Where(userID => userIDs.Contains(userID) && userID != obj.CurrentAccountId); + foreach (var id in ids) + { + if (userEntriesData.TryGetValue(id, out var value)) + value.Add(parentFolder); + else + userEntriesData.Add(id, new List<FileEntry> { parentFolder }); + } } - parentFolders.ForEach(parentFolder => - filesSecurity - .WhoCanRead(parentFolder) - .Where(userID => userIDs.Contains(userID) && userID != obj.CurrentAccountId) - .ToList() - .ForEach(userID => - { - if (userEntriesData.ContainsKey(userID)) - userEntriesData[userID].Add(parentFolder); - else - userEntriesData.Add(userID, new List<FileEntry> { parentFolder }); - }) - ); - - if (obj.FileEntry.RootFolderType == FolderType.USER) { @@ -218,8 +217,8 @@ namespace ASC.Web.Files.Utils if (rootFolder == null) continue; - if (userEntriesData.ContainsKey(userID)) - userEntriesData[userID].Add(rootFolder); + if (userEntriesData.TryGetValue(userID, out var value)) + value.Add(rootFolder); else userEntriesData.Add(userID, new List<FileEntry> { rootFolder }); @@ -235,8 +234,8 @@ namespace ASC.Web.Files.Utils var commonFolder = folderDao.GetFolder(GlobalFolder.GetFolderCommon<T>(this, DaoFactory)); userIDs.ForEach(userID => { - if (userEntriesData.ContainsKey(userID)) - userEntriesData[userID].Add(commonFolder); + if (userEntriesData.TryGetValue(userID, out var value)) + value.Add(commonFolder); else userEntriesData.Add(userID, new List<FileEntry> { commonFolder }); @@ -254,8 +253,8 @@ namespace ASC.Web.Files.Utils var rootFolder = folderDao.GetFolder(privacyFolderId); if (rootFolder == null) continue; - if (userEntriesData.ContainsKey(userID)) - userEntriesData[userID].Add(rootFolder); + if (userEntriesData.TryGetValue(userID, out var value)) + value.Add(rootFolder); else userEntriesData.Add(userID, new List<FileEntry> { rootFolder }); @@ -265,8 +264,8 @@ namespace ASC.Web.Files.Utils userIDs.ForEach(userID => { - if (userEntriesData.ContainsKey(userID)) - userEntriesData[userID].Add(obj.FileEntry); + if (userEntriesData.TryGetValue(userID, out var value)) + value.Add(obj.FileEntry); else userEntriesData.Add(userID, new List<FileEntry> { obj.FileEntry }); }); @@ -287,9 +286,9 @@ namespace ASC.Web.Files.Utils GetNewTags(userID, entries.OfType<FileEntry<string>>().ToList()); } - if (updateTags.Any()) + if (updateTags.Count > 0) tagDao.UpdateNewTags(updateTags); - if (newTags.Any()) + if (newTags.Count > 0) tagDao.SaveTags(newTags); void GetNewTags<T1>(Guid userID, List<FileEntry<T1>> entries) @@ -321,7 +320,7 @@ namespace ASC.Web.Files.Utils taskData.FileEntry = (FileEntry<T>)fileEntry.Clone(); taskData.UserIDs = userIDs; - if (fileEntry.RootFolderType == FolderType.BUNCH && !userIDs.Any()) + if (fileEntry.RootFolderType == FolderType.BUNCH && userIDs.Count == 0) { var folderDao = DaoFactory.GetFolderDao<T>(); var path = folderDao.GetBunchObjectID(fileEntry.RootFolderId); @@ -332,7 +331,7 @@ namespace ASC.Web.Files.Utils var projectTeam = FileSecurity.WhoCanRead(fileEntry) .Where(x => x != AuthContext.CurrentAccount.ID).ToList(); - if (!projectTeam.Any()) return; + if (projectTeam.Count == 0) return; taskData.UserIDs = projectTeam; } @@ -379,7 +378,7 @@ namespace ASC.Web.Files.Utils var folderTags = listTags.Where(tag => tag.EntryType == FileEntryType.Folder); var providerFolderTags = folderTags.Select(tag => new KeyValuePair<Tag, Folder<T>>(tag, folderDao.GetFolder((T)tag.EntryId))) - .Where(pair => pair.Value != null && pair.Value.ProviderEntry).ToList(); + .Where(pair => pair.Value != null && pair.Value.ProviderEntry); foreach (var providerFolderTag in providerFolderTags) { @@ -450,9 +449,9 @@ namespace ASC.Web.Files.Utils UpdateRemoveTags(parentFolder); } - if (updateTags.Any()) + if (updateTags.Count > 0) tagDao.UpdateNewTags(updateTags); - if (removeTags.Any()) + if (removeTags.Count > 0) tagDao.RemoveTags(removeTags); void UpdateRemoveTags<TFolder>(Folder<TFolder> folder) @@ -514,24 +513,22 @@ namespace ASC.Web.Files.Utils public List<FileEntry> MarkedItems<T>(Folder<T> folder) { - if (folder == null) throw new ArgumentNullException("folder", FilesCommonResource.ErrorMassage_FolderNotFound); + if (folder == null) throw new ArgumentNullException(nameof(folder), FilesCommonResource.ErrorMassage_FolderNotFound); if (!FileSecurity.CanRead(folder)) throw new SecurityException(FilesCommonResource.ErrorMassage_SecurityException_ViewFolder); if (folder.RootFolderType == FolderType.TRASH && !Equals(folder.ID, GlobalFolder.GetFolderTrash<T>(DaoFactory))) throw new SecurityException(FilesCommonResource.ErrorMassage_ViewTrashItem); var tagDao = DaoFactory.GetTagDao<T>(); - var fileDao = DaoFactory.GetFileDao<T>(); - var folderDao = DaoFactory.GetFolderDao<T>(); var providerFolderDao = DaoFactory.GetFolderDao<string>(); var providerTagDao = DaoFactory.GetTagDao<string>(); var tags = (tagDao.GetNewTags(AuthContext.CurrentAccount.ID, folder, true) ?? new List<Tag>()).ToList(); - if (!tags.Any()) return new List<FileEntry>(); + if (tags.Count == 0) return new List<FileEntry>(); if (Equals(folder.ID, GlobalFolder.GetFolderMy(this, DaoFactory)) || Equals(folder.ID, GlobalFolder.GetFolderCommon(this, DaoFactory)) || Equals(folder.ID, GlobalFolder.GetFolderShare(DaoFactory))) { - var folderTags = tags.Where(tag => tag.EntryType == FileEntryType.Folder && tag.EntryId.GetType() == typeof(string)); + var folderTags = tags.Where(tag => tag.EntryType == FileEntryType.Folder && (tag.EntryId is string)); var providerFolderTags = folderTags .Select(tag => new KeyValuePair<Tag, Folder<string>>(tag, providerFolderDao.GetFolder(tag.EntryId.ToString()))) @@ -552,8 +549,8 @@ namespace ASC.Web.Files.Utils .ToList(); //TODO: refactoring - var entryTagsProvider = GetEntryTags<string>(tags.Where(r=> r.EntryId.GetType() == typeof(string))); - var entryTagsInternal = GetEntryTags<int>(tags.Where(r=> r.EntryId.GetType() == typeof(int))); + var entryTagsProvider = GetEntryTags<string>(tags.Where(r=> r.EntryId is string)); + var entryTagsInternal = GetEntryTags<int>(tags.Where(r=> r.EntryId is int)); foreach (var entryTag in entryTagsInternal) { @@ -646,7 +643,7 @@ namespace ASC.Web.Files.Utils var folderDao = DaoFactory.GetFolderDao<T>(); var totalTags = tagDao.GetNewTags(AuthContext.CurrentAccount.ID, parent, false).ToList(); - if (totalTags.Any()) + if (totalTags.Count > 0) { var parentFolderTag = Equals(GlobalFolder.GetFolderShare<T>(DaoFactory), parent.ID) ? tagDao.GetNewTags(AuthContext.CurrentAccount.ID, folderDao.GetFolder(GlobalFolder.GetFolderShare<T>(DaoFactory))).FirstOrDefault() @@ -683,7 +680,7 @@ namespace ASC.Web.Files.Utils parentsList.Reverse(); parentsList.Remove(parent); - if (parentsList.Any()) + if (parentsList.Count > 0) { var rootFolder = parentsList.Last(); T rootFolderId = default; @@ -799,7 +796,7 @@ namespace ASC.Web.Files.Utils public Guid CurrentAccountId { get; set; } } - public class FileMarkerExtention + public static class FileMarkerExtention { public static void Register(DIHelper services) { diff --git a/products/ASC.Files/Core/Utils/FileSharing.cs b/products/ASC.Files/Core/Utils/FileSharing.cs index 4b4c118961..fa34b85c61 100644 --- a/products/ASC.Files/Core/Utils/FileSharing.cs +++ b/products/ASC.Files/Core/Utils/FileSharing.cs @@ -167,7 +167,7 @@ namespace ASC.Web.Files.Utils DocumentServiceHelper.CheckUsersForDrop((File<T>)entry); } - if (recipients.Any()) + if (recipients.Count > 0) { if (entryType == FileEntryType.File || ((Folder<T>)entry).TotalSubFolders + ((Folder<T>)entry).TotalFiles > 0 @@ -299,7 +299,7 @@ namespace ASC.Web.Files.Utils if (entry == null) throw new ArgumentNullException(FilesCommonResource.ErrorMassage_BadRequest); if (!CanSetAccess(entry)) { - Logger.ErrorFormat("User {0} can't get shared info for {1} {2}", AuthContext.CurrentAccount.ID, (entry.FileEntryType == FileEntryType.File ? "file" : "folder"), entry.ID); + Logger.ErrorFormat("User {0} can't get shared info for {1} {2}", AuthContext.CurrentAccount.ID, entry.FileEntryType == FileEntryType.File ? "file" : "folder", entry.ID); throw new SecurityException(FilesCommonResource.ErrorMassage_SecurityException); } @@ -467,7 +467,7 @@ namespace ASC.Web.Files.Utils var duplicate = result.FirstOrDefault(ace => ace.SubjectId == aceForObject.SubjectId); if (duplicate == null) { - if (result.Any()) + if (result.Count > 0) { aceForObject.Owner = false; aceForObject.Share = FileShare.Varies; diff --git a/products/ASC.Files/Core/Utils/FileTracker.cs b/products/ASC.Files/Core/Utils/FileTracker.cs index 159766f5e4..0e066dcdf4 100644 --- a/products/ASC.Files/Core/Utils/FileTracker.cs +++ b/products/ASC.Files/Core/Utils/FileTracker.cs @@ -63,10 +63,10 @@ namespace ASC.Web.Files.Utils var tracker = GetTracker(fileId); if (tracker != null && IsEditing(fileId)) { - if (tracker.EditingBy.Keys.Contains(tabId)) + if (tracker.EditingBy.TryGetValue(tabId, out var trackInfo)) { - tracker.EditingBy[tabId].TrackTime = DateTime.UtcNow; - checkRight = (DateTime.UtcNow - tracker.EditingBy[tabId].CheckRightTime > CheckRightTimeout); + trackInfo.TrackTime = DateTime.UtcNow; + checkRight = DateTime.UtcNow - tracker.EditingBy[tabId].CheckRightTime > CheckRightTimeout; } else { @@ -97,8 +97,8 @@ namespace ASC.Web.Files.Utils if (userId != default) { var listForRemove = tracker.EditingBy - .Where(b => tracker.EditingBy[b.Key].UserId == userId) - .ToList(); + .Where(b => tracker.EditingBy[b.Key].UserId == userId); + foreach (var editTab in listForRemove) { tracker.EditingBy.Remove(editTab.Key); @@ -117,8 +117,8 @@ namespace ASC.Web.Files.Utils if (tracker != null) { var listForRemove = tracker.EditingBy - .Where(b => b.Value.UserId != userId) - .ToList(); + .Where(b => b.Value.UserId != userId); + if (listForRemove.Count() != tracker.EditingBy.Count) { foreach (var forRemove in listForRemove) @@ -138,8 +138,8 @@ namespace ASC.Web.Files.Utils if (tracker != null) { var listForRemove = tracker.EditingBy - .Where(e => !e.Value.NewScheme && (DateTime.UtcNow - e.Value.TrackTime).Duration() > TrackTimeout) - .ToList(); + .Where(e => !e.Value.NewScheme && (DateTime.UtcNow - e.Value.TrackTime).Duration() > TrackTimeout); + foreach (var editTab in listForRemove) { tracker.EditingBy.Remove(editTab.Key); @@ -168,17 +168,14 @@ namespace ASC.Web.Files.Utils { var tracker = GetTracker(fileId); if (tracker != null) - { - - tracker.EditingBy.Values - .ToList() - .ForEach(i => - { - if (i.UserId == userId || userId == Guid.Empty) - { - i.CheckRightTime = check ? DateTime.MinValue : DateTime.UtcNow; - } - }); + { + foreach(var value in tracker.EditingBy.Values) + { + if (value.UserId == userId || userId == Guid.Empty) + { + value.CheckRightTime = check ? DateTime.MinValue : DateTime.UtcNow; + } + } SetTracker(fileId, tracker); } else diff --git a/products/ASC.Files/Core/Utils/FileUploader.cs b/products/ASC.Files/Core/Utils/FileUploader.cs index b42ae898d6..83d16940be 100644 --- a/products/ASC.Files/Core/Utils/FileUploader.cs +++ b/products/ASC.Files/Core/Utils/FileUploader.cs @@ -208,7 +208,7 @@ namespace ASC.Web.Files.Utils if (!FileSecurity.CanCreate(folder)) throw new SecurityException(FilesCommonResource.ErrorMassage_SecurityException_Create); - if (relativePath != null && relativePath.Any()) + if (relativePath != null && relativePath.Count > 0) { var subFolderTitle = Global.ReplaceInvalidCharsAndTruncate(relativePath.FirstOrDefault()); diff --git a/products/ASC.Files/Core/Utils/MailMergeTask.cs b/products/ASC.Files/Core/Utils/MailMergeTask.cs index 0be0f4e3b6..88e78d3dae 100644 --- a/products/ASC.Files/Core/Utils/MailMergeTask.cs +++ b/products/ASC.Files/Core/Utils/MailMergeTask.cs @@ -44,14 +44,14 @@ namespace ASC.Web.Files.Utils { internal const string MessageBodyFormat = "id={0}&from={1}&subject={2}&to%5B%5D={3}&body={4}&mimeReplyToId="; - public string From; - public string Subject; - public string To; - public string Message; - public string AttachTitle; - public Stream Attach; - public int MessageId; - public string StreamId; + public string From { get; set; } + public string Subject { get; set; } + public string To { get; set; } + public string Message { get; set; } + public string AttachTitle { get; set; } + public Stream Attach { get; set; } + public int MessageId { get; set; } + public string StreamId { get; set; } public MailMergeTask() { @@ -86,31 +86,30 @@ namespace ASC.Web.Files.Utils BaseCommonLinkUtility = baseCommonLinkUtility; } - public string Run(MailMergeTask mailMergeTask) + public string Run(MailMergeTask mailMergeTask, IHttpClientFactory clientFactory) { if (string.IsNullOrEmpty(mailMergeTask.From)) throw new ArgumentException("From is null"); if (string.IsNullOrEmpty(mailMergeTask.To)) throw new ArgumentException("To is null"); CreateDraftMail(mailMergeTask); - var bodySendAttach = AttachToMail(mailMergeTask); + var bodySendAttach = AttachToMail(mailMergeTask, clientFactory); return SendMail(mailMergeTask, bodySendAttach); } private void CreateDraftMail(MailMergeTask mailMergeTask) - { - var apiUrlCreate = string.Format("{0}mail/drafts/save.json", SetupInfo.WebApiBaseUrl); - var bodyCreate = - string.Format( - MailMergeTask.MessageBodyFormat, - mailMergeTask.MessageId, - HttpUtility.UrlEncode(mailMergeTask.From), - HttpUtility.UrlEncode(mailMergeTask.Subject), - HttpUtility.UrlEncode(mailMergeTask.To), - HttpUtility.UrlEncode(mailMergeTask.Message)); - - string responseCreateString = null; //TODO: Encoding.UTF8.GetString(Convert.FromBase64String(Api.GetApiResponse(apiUrlCreate, "PUT", bodyCreate))); + { + //var apiUrlCreate = $"{SetupInfo.WebApiBaseUrl}mail/drafts/save.json"; + //var bodyCreate = + // string.Format( + // MailMergeTask.MessageBodyFormat, + // mailMergeTask.MessageId, + // HttpUtility.UrlEncode(mailMergeTask.From), + // HttpUtility.UrlEncode(mailMergeTask.Subject), + // HttpUtility.UrlEncode(mailMergeTask.To), + // HttpUtility.UrlEncode(mailMergeTask.Message)); + const string responseCreateString = null; //TODO: Encoding.UTF8.GetString(Convert.FromBase64String(Api.GetApiResponse(apiUrlCreate, "PUT", bodyCreate))); var responseCreate = JObject.Parse(responseCreateString); if (responseCreate["statusCode"].Value<int>() != (int)HttpStatusCode.OK) @@ -122,7 +121,7 @@ namespace ASC.Web.Files.Utils mailMergeTask.StreamId = responseCreate["response"]["streamId"].Value<string>(); } - private string AttachToMail(MailMergeTask mailMergeTask) + private string AttachToMail(MailMergeTask mailMergeTask, IHttpClientFactory clientFactory) { if (mailMergeTask.Attach == null) return string.Empty; @@ -140,14 +139,8 @@ namespace ASC.Web.Files.Utils request.Content.Headers.ContentType = new MediaTypeHeaderValue(mailMergeTask.AttachTitle); request.Content = new StreamContent(mailMergeTask.Attach); - // hack. http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono) - { - ServicePointManager.ServerCertificateValidationCallback += (s, ce, ca, p) => true; - } - string responseAttachString; - using var httpClient = new HttpClient(); + var httpClient = clientFactory.CreateClient(); using var response = httpClient.Send(request); using (var stream = response.Content.ReadAsStream()) { @@ -177,21 +170,20 @@ namespace ASC.Web.Files.Utils } private string SendMail(MailMergeTask mailMergeTask, string bodySendAttach) - { - var apiUrlSend = string.Format("{0}mail/messages/send.json", SetupInfo.WebApiBaseUrl); - - var bodySend = - string.Format( - MailMergeTask.MessageBodyFormat, - mailMergeTask.MessageId, - HttpUtility.UrlEncode(mailMergeTask.From), - HttpUtility.UrlEncode(mailMergeTask.Subject), - HttpUtility.UrlEncode(mailMergeTask.To), - HttpUtility.UrlEncode(mailMergeTask.Message)); - - bodySend += bodySendAttach; - - string responseSendString = null;//TODO: Encoding.UTF8.GetString(Convert.FromBase64String(Api.GetApiResponse(apiUrlSend, "PUT", bodySend))); + { + //var apiUrlSend = $"{SetupInfo.WebApiBaseUrl}mail/messages/send.json"; + + //var bodySend = + // string.Format( + // MailMergeTask.MessageBodyFormat, + // mailMergeTask.MessageId, + // HttpUtility.UrlEncode(mailMergeTask.From), + // HttpUtility.UrlEncode(mailMergeTask.Subject), + // HttpUtility.UrlEncode(mailMergeTask.To), + // HttpUtility.UrlEncode(mailMergeTask.Message)); + + //bodySend += bodySendAttach; + const string responseSendString = null;//TODO: Encoding.UTF8.GetString(Convert.FromBase64String(Api.GetApiResponse(apiUrlSend, "PUT", bodySend))); var responseSend = JObject.Parse(responseSendString); if (responseSend["statusCode"].Value<int>() != (int)HttpStatusCode.OK) diff --git a/products/ASC.Files/Server/Controllers/FilesController.cs b/products/ASC.Files/Server/Controllers/FilesController.cs index fd6248b416..a03f1d088c 100644 --- a/products/ASC.Files/Server/Controllers/FilesController.cs +++ b/products/ASC.Files/Server/Controllers/FilesController.cs @@ -211,7 +211,7 @@ namespace ASC.Api.Documents if (!IsVisitor && !withoutAdditionalFolder - && FileUtility.ExtsWebTemplate.Any() + && FileUtility.ExtsWebTemplate.Count > 0 && FilesSettingsHelper.TemplatesSection) { result.Add(GlobalFolderHelper.FolderTemplates); @@ -2441,7 +2441,7 @@ namespace ASC.Api.Documents private object WordpressSave(WordpressSaveModel model) { - if (model.Code == "") + if (model.Code.Length == 0) { return new { diff --git a/products/ASC.Files/Server/Helpers/FilesControllerHelper.cs b/products/ASC.Files/Server/Helpers/FilesControllerHelper.cs index e03c2fe2f3..52bd9db9ad 100644 --- a/products/ASC.Files/Server/Helpers/FilesControllerHelper.cs +++ b/products/ASC.Files/Server/Helpers/FilesControllerHelper.cs @@ -2,7 +2,6 @@ using System.Collections.Generic; using System.IO; using System.Linq; -using System.Net; using System.Net.Http; using System.Text; using System.Text.Json; @@ -72,6 +71,7 @@ namespace ASC.Files.Helpers private UserManager UserManager { get; } private DisplayUserSettingsHelper DisplayUserSettingsHelper { get; } private ILog Logger { get; set; } + private IHttpClientFactory ClientFactory { get; set; } /// <summary> /// </summary> @@ -102,7 +102,8 @@ namespace ASC.Files.Helpers FileConverter fileConverter, ApiDateTimeHelper apiDateTimeHelper, UserManager userManager, - DisplayUserSettingsHelper displayUserSettingsHelper) + DisplayUserSettingsHelper displayUserSettingsHelper, + IHttpClientFactory clientFactory) { ApiContext = context; FileStorageService = fileStorageService; @@ -129,6 +130,7 @@ namespace ASC.Files.Helpers HttpContextAccessor = httpContextAccessor; FileConverter = fileConverter; Logger = optionMonitor.Get("ASC.Files"); + ClientFactory = clientFactory; } public FolderContentWrapper<T> GetFolder(T folderId, Guid userIdOrGroupId, FilterType filterType, bool withSubFolders) @@ -258,7 +260,7 @@ namespace ASC.Files.Helpers if (FilesLinkUtility.IsLocalFileUploader) { - var session = FileUploader.InitiateUpload(file.FolderID, (file.ID ?? default), file.Title, file.ContentLength, encrypted); + var session = FileUploader.InitiateUpload(file.FolderID, file.ID ?? default, file.Title, file.ContentLength, encrypted); var responseObject = ChunkedUploadSessionHelper.ToResponseObject(session, true); return new @@ -270,7 +272,7 @@ namespace ASC.Files.Helpers var createSessionUrl = FilesLinkUtility.GetInitiateUploadSessionUrl(TenantManager.GetCurrentTenant().TenantId, file.FolderID, file.ID, file.Title, file.ContentLength, encrypted, SecurityContext); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); var request = new HttpRequestMessage(); request.RequestUri = new Uri(createSessionUrl); @@ -283,12 +285,6 @@ namespace ASC.Files.Helpers request.Headers.Add(HttpRequestExtensions.UrlRewriterHeader, rewriterHeader.ToString()); } - // hack. http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono) - { - ServicePointManager.ServerCertificateValidationCallback += (s, ce, ca, p) => true; - } - using var response = httpClient.Send(request); using var responseStream = response.Content.ReadAsStream(); using var streamReader = new StreamReader(responseStream); @@ -297,7 +293,7 @@ namespace ASC.Files.Helpers public FileWrapper<T> CreateTextFile(T folderId, string title, string content) { - if (title == null) throw new ArgumentNullException("title"); + if (title == null) throw new ArgumentNullException(nameof(title)); //Try detect content var extension = ".txt"; if (!string.IsNullOrEmpty(content)) @@ -321,7 +317,7 @@ namespace ASC.Files.Helpers public FileWrapper<T> CreateHtmlFile(T folderId, string title, string content) { - if (title == null) throw new ArgumentNullException("title"); + if (title == null) throw new ArgumentNullException(nameof(title)); return CreateFile(folderId, title, content, ".html"); } @@ -486,8 +482,8 @@ namespace ASC.Files.Helpers public IEnumerable<FileEntryWrapper> MoveOrCopyBatchCheck(BatchModel batchModel) { - var checkedFiles = new List<object>(); - var checkedFolders = new List<object>(); + List<object> checkedFiles; + List<object> checkedFolders; if (batchModel.DestFolderId.ValueKind == JsonValueKind.Number) { @@ -667,8 +663,6 @@ namespace ASC.Files.Helpers public string GenerateSharedLink(T fileId, FileShare share) { - var file = GetFileInfo(fileId); - var sharedInfo = FileStorageService.GetSharedInfo(new List<T> { fileId }, new List<T> { }).Find(r => r.SubjectId == FileConstant.ShareLinkId); if (sharedInfo == null || sharedInfo.Share != share) { diff --git a/products/ASC.Files/Server/Program.cs b/products/ASC.Files/Server/Program.cs index ec928e616c..115c4728c8 100644 --- a/products/ASC.Files/Server/Program.cs +++ b/products/ASC.Files/Server/Program.cs @@ -15,7 +15,7 @@ using Microsoft.Extensions.Hosting; namespace ASC.Files { - public class Program + public static class Program { public async static Task Main(string[] args) { diff --git a/products/ASC.Files/Server/Startup.cs b/products/ASC.Files/Server/Startup.cs index 57bd7c9b16..e6b321652a 100644 --- a/products/ASC.Files/Server/Startup.cs +++ b/products/ASC.Files/Server/Startup.cs @@ -13,9 +13,6 @@ using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Hosting; -using StackExchange.Redis.Extensions.Core.Configuration; -using StackExchange.Redis.Extensions.Newtonsoft; - namespace ASC.Files { public class Startup : BaseStartup diff --git a/products/ASC.Files/Service/Core/FilesModule.cs b/products/ASC.Files/Service/Core/FilesModule.cs index f3bd00f7dc..5cbd9e9822 100644 --- a/products/ASC.Files/Service/Core/FilesModule.cs +++ b/products/ASC.Files/Service/Core/FilesModule.cs @@ -65,7 +65,7 @@ namespace ASC.Files.Service.Core var owner = (Guid)feed.Target; var groupUsers = UserManager.GetUsersByGroup(owner).Select(x => x.ID).ToList(); - if (!groupUsers.Any()) + if (groupUsers.Count == 0) { groupUsers.Add(owner); } @@ -147,7 +147,7 @@ namespace ASC.Files.Service.Core ExtraLocation = rootFolder.FolderType == FolderType.DEFAULT ? rootFolder.Title : string.Empty, ExtraLocationUrl = rootFolder.FolderType == FolderType.DEFAULT ? FilesLinkUtility.GetFileRedirectPreviewUrl(file.FolderID, false) : string.Empty, AdditionalInfo = file.ContentLengthString, - Keywords = string.Format("{0}", file.Title), + Keywords = file.Title, HasPreview = false, CanComment = false, Target = shareRecord.ShareTo, @@ -170,7 +170,7 @@ namespace ASC.Files.Service.Core ExtraLocation = rootFolder.FolderType == FolderType.DEFAULT ? rootFolder.Title : string.Empty, ExtraLocationUrl = rootFolder.FolderType == FolderType.DEFAULT ? FilesLinkUtility.GetFileRedirectPreviewUrl(file.FolderID, false) : string.Empty, AdditionalInfo = file.ContentLengthString, - Keywords = string.Format("{0}", file.Title), + Keywords = file.Title, HasPreview = false, CanComment = false, Target = null, @@ -183,7 +183,7 @@ namespace ASC.Files.Service.Core if (target == null) return true; var owner = (Guid)target; var groupUsers = UserManager.GetUsersByGroup(owner).Select(x => x.ID).ToList(); - if (!groupUsers.Any()) + if (groupUsers.Count == 0) { groupUsers.Add(owner); } diff --git a/products/ASC.Files/Service/Core/FoldersModule.cs b/products/ASC.Files/Service/Core/FoldersModule.cs index f22db52a5e..ee7150c264 100644 --- a/products/ASC.Files/Service/Core/FoldersModule.cs +++ b/products/ASC.Files/Service/Core/FoldersModule.cs @@ -62,7 +62,7 @@ namespace ASC.Files.Service.Core var owner = (Guid)feed.Target; var groupUsers = UserManager.GetUsersByGroup(owner).Select(x => x.ID).ToList(); - if (!groupUsers.Any()) + if (groupUsers.Count == 0) { groupUsers.Add(owner); } @@ -110,7 +110,7 @@ namespace ASC.Files.Service.Core Title = folder.Title, ExtraLocation = rootFolder.FolderType == FolderType.DEFAULT ? rootFolder.Title : string.Empty, ExtraLocationUrl = rootFolder.FolderType == FolderType.DEFAULT ? FilesLinkUtility.GetFileRedirectPreviewUrl(folder.FolderID, false) : string.Empty, - Keywords = string.Format("{0}", folder.Title), + Keywords = folder.Title, HasPreview = false, CanComment = false, Target = shareRecord.ShareTo, @@ -130,7 +130,7 @@ namespace ASC.Files.Service.Core Title = folder.Title, ExtraLocation = rootFolder.FolderType == FolderType.DEFAULT ? rootFolder.Title : string.Empty, ExtraLocationUrl = rootFolder.FolderType == FolderType.DEFAULT ? FilesLinkUtility.GetFileRedirectPreviewUrl(folder.FolderID, false) : string.Empty, - Keywords = string.Format("{0}", folder.Title), + Keywords = folder.Title, HasPreview = false, CanComment = false, Target = null, diff --git a/products/ASC.Files/Service/Program.cs b/products/ASC.Files/Service/Program.cs index d0fa6bbf9d..d60442addd 100644 --- a/products/ASC.Files/Service/Program.cs +++ b/products/ASC.Files/Service/Program.cs @@ -25,7 +25,7 @@ using StackExchange.Redis.Extensions.Newtonsoft; namespace ASC.Files.Service { - public class Program + public static class Program { public async static Task Main(string[] args) { diff --git a/products/ASC.Files/Service/Thumbnail/Builder.cs b/products/ASC.Files/Service/Thumbnail/Builder.cs index 6f4f0753c6..4d901c9782 100644 --- a/products/ASC.Files/Service/Thumbnail/Builder.cs +++ b/products/ASC.Files/Service/Thumbnail/Builder.cs @@ -19,42 +19,41 @@ using System; using System.Collections.Generic; using System.IO; using System.Linq; -using System.Net; -using System.Net.Http; +using System.Net.Http; using System.Threading; -using System.Threading.Tasks; - +using System.Threading.Tasks; + using ASC.Common; using ASC.Common.Logging; using ASC.Core; -using ASC.Core.Common; +using ASC.Core.Common; using ASC.Files.Core; using ASC.Web.Core.Files; using ASC.Web.Core.Users; using ASC.Web.Files.Classes; using ASC.Web.Files.Core; -using ASC.Web.Files.Services.DocumentService; - -using Microsoft.Extensions.DependencyInjection; -using Microsoft.Extensions.Options; - -using SixLabors.ImageSharp; -using SixLabors.ImageSharp.Formats.Png; - +using ASC.Web.Files.Services.DocumentService; + +using Microsoft.Extensions.DependencyInjection; +using Microsoft.Extensions.Options; + +using SixLabors.ImageSharp; +using SixLabors.ImageSharp.Formats.Png; + namespace ASC.Files.ThumbnailBuilder -{ +{ [Singletone] internal class BuilderQueue<T> - { - private readonly ThumbnailSettings config; - private readonly ILog logger; - private IServiceProvider ServiceProvider { get; } - + { + private readonly ThumbnailSettings config; + private readonly ILog logger; + private IServiceProvider ServiceProvider { get; } + public BuilderQueue(IServiceProvider serviceProvider, IOptionsMonitor<ILog> log, ThumbnailSettings settings) - { - logger = log.Get("ASC.Files.ThumbnailBuilder"); - ServiceProvider = serviceProvider; - config = settings; + { + logger = log.Get("ASC.Files.ThumbnailBuilder"); + ServiceProvider = serviceProvider; + config = settings; } public void BuildThumbnails(IEnumerable<FileData<T>> filesWithoutThumbnails) @@ -64,14 +63,14 @@ namespace ASC.Files.ThumbnailBuilder Parallel.ForEach( filesWithoutThumbnails, new ParallelOptions { MaxDegreeOfParallelism = config.MaxDegreeOfParallelism }, - (fileData) => - { - using var scope = ServiceProvider.CreateScope(); - var commonLinkUtilitySettings = scope.ServiceProvider.GetService<CommonLinkUtilitySettings>(); - commonLinkUtilitySettings.ServerUri = fileData.BaseUri; - - var builder = scope.ServiceProvider.GetService<Builder<T>>(); - builder.BuildThumbnail(fileData); + (fileData) => + { + using var scope = ServiceProvider.CreateScope(); + var commonLinkUtilitySettings = scope.ServiceProvider.GetService<CommonLinkUtilitySettings>(); + commonLinkUtilitySettings.ServerUri = fileData.BaseUri; + + var builder = scope.ServiceProvider.GetService<Builder<T>>(); + builder.BuildThumbnail(fileData); } ); } @@ -80,46 +79,49 @@ namespace ASC.Files.ThumbnailBuilder logger.Error(string.Format("BuildThumbnails: filesWithoutThumbnails.Count: {0}.", filesWithoutThumbnails.Count()), exception); } } - } - + } + [Scope] internal class Builder<T> - { - private readonly ThumbnailSettings config; - private readonly ILog logger; - - private TenantManager TenantManager { get; } - private IDaoFactory DaoFactory { get; } - private DocumentServiceConnector DocumentServiceConnector { get; } - private DocumentServiceHelper DocumentServiceHelper { get; } - private Global Global { get; } - private PathProvider PathProvider { get; } - - public Builder( - ThumbnailSettings settings, - TenantManager tenantManager, - IDaoFactory daoFactory, - DocumentServiceConnector documentServiceConnector, - DocumentServiceHelper documentServiceHelper, - Global global, - PathProvider pathProvider, - IOptionsMonitor<ILog> log) - { - this.config = settings; - TenantManager = tenantManager; - DaoFactory = daoFactory; - DocumentServiceConnector = documentServiceConnector; - DocumentServiceHelper = documentServiceHelper; - Global = global; - PathProvider = pathProvider; + { + private readonly ThumbnailSettings config; + private readonly ILog logger; + + private TenantManager TenantManager { get; } + private IDaoFactory DaoFactory { get; } + private DocumentServiceConnector DocumentServiceConnector { get; } + private DocumentServiceHelper DocumentServiceHelper { get; } + private Global Global { get; } + private PathProvider PathProvider { get; } + private IHttpClientFactory ClientFactory { get; } + + public Builder( + ThumbnailSettings settings, + TenantManager tenantManager, + IDaoFactory daoFactory, + DocumentServiceConnector documentServiceConnector, + DocumentServiceHelper documentServiceHelper, + Global global, + PathProvider pathProvider, + IOptionsMonitor<ILog> log, + IHttpClientFactory clientFactory) + { + this.config = settings; + TenantManager = tenantManager; + DaoFactory = daoFactory; + DocumentServiceConnector = documentServiceConnector; + DocumentServiceHelper = documentServiceHelper; + Global = global; + PathProvider = pathProvider; logger = log.Get("ASC.Files.ThumbnailBuilder"); + ClientFactory = clientFactory; } internal void BuildThumbnail(FileData<T> fileData) { try { - TenantManager.SetCurrentTenant(fileData.TenantId); + TenantManager.SetCurrentTenant(fileData.TenantId); var fileDao = DaoFactory.GetFileDao<T>(); if (fileDao == null) @@ -284,18 +286,12 @@ namespace ASC.Files.ThumbnailBuilder private void SaveThumbnail(IFileDao<T> fileDao, File<T> file, string thumbnailUrl) { - logger.DebugFormat("SaveThumbnail: FileId: {0}. ThumbnailUrl {1}.", file.ID, thumbnailUrl); - - var request = new HttpRequestMessage(); + logger.DebugFormat("SaveThumbnail: FileId: {0}. ThumbnailUrl {1}.", file.ID, thumbnailUrl); + + var request = new HttpRequestMessage(); request.RequestUri = new Uri(thumbnailUrl); - //HACK: http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono && ServicePointManager.ServerCertificateValidationCallback == null) - { - ServicePointManager.ServerCertificateValidationCallback += (s, c, n, p) => true; - } - - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using (var stream = new ResponseStream(response)) { @@ -335,7 +331,7 @@ namespace ASC.Files.ThumbnailBuilder fileDao.SaveThumbnail(file, targetStream); } } - } + } GC.Collect(); } diff --git a/products/ASC.Files/Service/Thumbnail/FileDataProvider.cs b/products/ASC.Files/Service/Thumbnail/FileDataProvider.cs index 72851ed8e7..46a6f62cc7 100644 --- a/products/ASC.Files/Service/Thumbnail/FileDataProvider.cs +++ b/products/ASC.Files/Service/Thumbnail/FileDataProvider.cs @@ -23,7 +23,6 @@ using System.Linq.Expressions; using ASC.Common; using ASC.Common.Caching; using ASC.Core.Common.EF; -using ASC.Core.Common.EF.Context; using ASC.Core.Tenants; using ASC.Files.Core; using ASC.Files.Core.EF; @@ -100,11 +99,11 @@ namespace ASC.Files.ThumbnailBuilder !r.tariff.Comment.Contains("trial") ) ) && - ( + !r.quota.Features.Contains("free") && !r.quota.Features.Contains("non-profit") && !r.quota.Features.Contains("trial") - ) + ) .GroupBy(r => r.tariff.Tenant) .Select(r => new { tenant = r.Key, stamp = r.Max(b => b.tariff.Stamp) }) @@ -142,7 +141,7 @@ namespace ASC.Files.ThumbnailBuilder var premiumTenants = GetPremiumTenants(); - if (premiumTenants.Any()) + if (premiumTenants.Length > 0) { result = GetFileData(r => premiumTenants.Contains(r.TenantId)); diff --git a/products/ASC.Files/Service/Thumbnail/Worker.cs b/products/ASC.Files/Service/Thumbnail/Worker.cs index b7298ee91f..17fe67cfe1 100644 --- a/products/ASC.Files/Service/Thumbnail/Worker.cs +++ b/products/ASC.Files/Service/Thumbnail/Worker.cs @@ -81,7 +81,7 @@ namespace ASC.Files.ThumbnailBuilder var filesWithoutThumbnails = Launcher.Queue.Select(pair => pair.Value).ToList(); - if (!filesWithoutThumbnails.Any()) + if (filesWithoutThumbnails.Count == 0) { logger.TraceFormat("Procedure: Waiting for data. Sleep {0}.", thumbnailSettings.LaunchFrequency); timer.Change(TimeSpan.FromSeconds(thumbnailSettings.LaunchFrequency), TimeSpan.FromMilliseconds(-1)); @@ -106,7 +106,7 @@ namespace ASC.Files.ThumbnailBuilder } } - public class WorkerExtension + public static class WorkerExtension { public static void Register(DIHelper services) { diff --git a/products/ASC.People/Server/Controllers/PeopleController.cs b/products/ASC.People/Server/Controllers/PeopleController.cs index 17d7da9cde..e5513ebbff 100644 --- a/products/ASC.People/Server/Controllers/PeopleController.cs +++ b/products/ASC.People/Server/Controllers/PeopleController.cs @@ -99,6 +99,7 @@ namespace ASC.Employee.Core.Controllers private Constants Constants { get; } private Recaptcha Recaptcha { get; } private ILog Log { get; } + private IHttpClientFactory ClientFactory { get; } public PeopleController( MessageService messageService, @@ -140,7 +141,8 @@ namespace ASC.Employee.Core.Controllers MobileDetector mobileDetector, ProviderManager providerManager, Constants constants, - Recaptcha recaptcha + Recaptcha recaptcha, + IHttpClientFactory clientFactory ) { Log = option.Get("ASC.Api"); @@ -183,6 +185,7 @@ namespace ASC.Employee.Core.Controllers ProviderManager = providerManager; Constants = constants; Recaptcha = recaptcha; + ClientFactory = clientFactory; } [Read("info")] @@ -496,7 +499,7 @@ namespace ASC.Employee.Core.Controllers } catch (Exception ex) { - Log.Debug(String.Format("ERROR write to template_unsubscribe {0}, email:{1}", ex.Message, model.Email.ToLowerInvariant())); + Log.Debug($"ERROR write to template_unsubscribe {ex.Message}, email:{model.Email.ToLowerInvariant()}"); } } @@ -562,8 +565,8 @@ namespace ASC.Employee.Core.Controllers ? true : ("female".Equals(memberModel.Sex, StringComparison.OrdinalIgnoreCase) ? (bool?)false : null); - user.BirthDate = memberModel.Birthday != null && memberModel.Birthday != DateTime.MinValue ? TenantUtil.DateTimeFromUtc(Convert.ToDateTime(memberModel.Birthday)) : null; - user.WorkFromDate = memberModel.Worksfrom != null && memberModel.Worksfrom != DateTime.MinValue ? TenantUtil.DateTimeFromUtc(Convert.ToDateTime(memberModel.Worksfrom)) : DateTime.UtcNow.Date; + user.BirthDate = memberModel.Birthday != null && memberModel.Birthday != DateTime.MinValue ? TenantUtil.DateTimeFromUtc(memberModel.Birthday) : null; + user.WorkFromDate = memberModel.Worksfrom != null && memberModel.Worksfrom != DateTime.MinValue ? TenantUtil.DateTimeFromUtc(memberModel.Worksfrom) : DateTime.UtcNow.Date; UpdateContacts(memberModel.Contacts, user); @@ -631,8 +634,8 @@ namespace ASC.Employee.Core.Controllers ? true : ("female".Equals(memberModel.Sex, StringComparison.OrdinalIgnoreCase) ? (bool?)false : null); - user.BirthDate = memberModel.Birthday != null ? TenantUtil.DateTimeFromUtc(Convert.ToDateTime(memberModel.Birthday)) : null; - user.WorkFromDate = memberModel.Worksfrom != null ? TenantUtil.DateTimeFromUtc(Convert.ToDateTime(memberModel.Worksfrom)) : DateTime.UtcNow.Date; + user.BirthDate = memberModel.Birthday != null ? TenantUtil.DateTimeFromUtc(memberModel.Birthday) : null; + user.WorkFromDate = memberModel.Worksfrom != null ? TenantUtil.DateTimeFromUtc(memberModel.Worksfrom) : DateTime.UtcNow.Date; UpdateContacts(memberModel.Contacts, user); @@ -751,14 +754,14 @@ namespace ASC.Employee.Core.Controllers ? true : ("female".Equals(memberModel.Sex, StringComparison.OrdinalIgnoreCase) ? (bool?)false : null)) ?? user.Sex; - user.BirthDate = memberModel.Birthday != null ? TenantUtil.DateTimeFromUtc(Convert.ToDateTime(memberModel.Birthday)) : user.BirthDate; + user.BirthDate = memberModel.Birthday != null ? TenantUtil.DateTimeFromUtc(memberModel.Birthday) : user.BirthDate; if (user.BirthDate == resetDate) { user.BirthDate = null; } - user.WorkFromDate = memberModel.Worksfrom != null ? TenantUtil.DateTimeFromUtc(Convert.ToDateTime(memberModel.Worksfrom)) : user.WorkFromDate; + user.WorkFromDate = memberModel.Worksfrom != null ? TenantUtil.DateTimeFromUtc(memberModel.Worksfrom) : user.WorkFromDate; if (user.WorkFromDate == resetDate) { @@ -785,7 +788,7 @@ namespace ASC.Employee.Core.Controllers } // change user type - var canBeGuestFlag = !user.IsOwner(Tenant) && !user.IsAdmin(UserManager) && !user.GetListAdminModules(WebItemSecurity).Any() && !user.IsMe(AuthContext); + var canBeGuestFlag = !user.IsOwner(Tenant) && !user.IsAdmin(UserManager) && user.GetListAdminModules(WebItemSecurity).Count == 0 && !user.IsMe(AuthContext); if (memberModel.IsVisitor && !user.IsVisitor(UserManager) && canBeGuestFlag) { @@ -934,6 +937,7 @@ namespace ASC.Employee.Core.Controllers if (UserManager.IsSystemUser(user.ID)) throw new SecurityException(); + user.ContactsList.Clear(); UpdateContacts(memberModel.Contacts, user); UserManager.SaveUserInfo(user); return EmployeeWraperFullHelper.GetFull(user); @@ -1184,8 +1188,8 @@ namespace ASC.Employee.Core.Controllers private object SendUserPassword(MemberModel memberModel) { - string error; - if (!string.IsNullOrEmpty(error = UserManagerWrapper.SendUserPassword(memberModel.Email))) + string error = UserManagerWrapper.SendUserPassword(memberModel.Email); + if (!string.IsNullOrEmpty(error)) { Log.ErrorFormat("Password recovery ({0}): {1}", memberModel.Email, error); } @@ -1387,7 +1391,7 @@ namespace ASC.Employee.Core.Controllers foreach (var user in users) { - if (user.IsOwner(Tenant) || user.IsAdmin(UserManager) || user.IsMe(AuthContext) || user.GetListAdminModules(WebItemSecurity).Any()) + if (user.IsOwner(Tenant) || user.IsAdmin(UserManager) || user.IsMe(AuthContext) || user.GetListAdminModules(WebItemSecurity).Count > 0) continue; switch (type) @@ -1496,8 +1500,6 @@ namespace ASC.Employee.Core.Controllers if (user.IsActive) continue; var viewer = UserManager.GetUsers(SecurityContext.CurrentAccount.ID); - if (user == null) throw new Exception(Resource.ErrorUserNotFound); - if (viewer == null) throw new Exception(Resource.ErrorAccessDenied); if (viewer.IsAdmin(UserManager) || viewer.ID == user.ID) @@ -1605,7 +1607,7 @@ namespace ASC.Employee.Core.Controllers foreach (var provider in ProviderManager.AuthProviders.Where(provider => string.IsNullOrEmpty(fromOnly) || fromOnly == provider || (provider == "google" && fromOnly == "openid"))) { - if (inviteView && provider.ToLower() == "twitter") continue; + if (inviteView && provider.Equals("twitter", StringComparison.OrdinalIgnoreCase)) continue; var loginProvider = ProviderManager.GetLoginProvider(provider); if (loginProvider != null && loginProvider.IsEnabled) @@ -1865,7 +1867,7 @@ namespace ASC.Employee.Core.Controllers var request = new HttpRequestMessage(); request.RequestUri = new Uri(url); - using (var httpClient = new HttpClient()) + var httpClient = ClientFactory.CreateClient(); using (var response = httpClient.Send(request)) using (var stream = response.Content.ReadAsStream()) { @@ -2110,12 +2112,12 @@ namespace ASC.Employee.Core.Controllers if (!files.StartsWith("http://") && !files.StartsWith("https://")) { - files = new Uri(ApiContext.HttpContextAccessor.HttpContext.Request.GetDisplayUrl()).GetLeftPart(UriPartial.Scheme | UriPartial.Authority) + "/" + files.TrimStart('/'); + files = new Uri(ApiContext.HttpContextAccessor.HttpContext.Request.GetDisplayUrl()).GetLeftPart(UriPartial.Authority) + "/" + files.TrimStart('/'); } var request = new HttpRequestMessage(); request.RequestUri = new Uri(files); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using var inputStream = response.Content.ReadAsStream(); using var br = new BinaryReader(inputStream); diff --git a/products/ASC.People/Server/Program.cs b/products/ASC.People/Server/Program.cs index 4017ed5863..1a67d25604 100644 --- a/products/ASC.People/Server/Program.cs +++ b/products/ASC.People/Server/Program.cs @@ -15,7 +15,7 @@ using Microsoft.Extensions.Hosting; namespace ASC.People { - public class Program + public static class Program { public async static Task Main(string[] args) { diff --git a/products/ASC.People/Server/Startup.cs b/products/ASC.People/Server/Startup.cs index 31d8e6196b..77b01317d7 100644 --- a/products/ASC.People/Server/Startup.cs +++ b/products/ASC.People/Server/Startup.cs @@ -7,12 +7,9 @@ using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Hosting; -using StackExchange.Redis.Extensions.Core.Configuration; -using StackExchange.Redis.Extensions.Newtonsoft; - namespace ASC.People { -public class Startup : BaseStartup + public class Startup : BaseStartup { public override bool ConfirmAddScheme { get => true; } diff --git a/web/ASC.Web.Api/Controllers/AuthenticationController.cs b/web/ASC.Web.Api/Controllers/AuthenticationController.cs index 58fab2bfdd..825f5cf83b 100644 --- a/web/ASC.Web.Api/Controllers/AuthenticationController.cs +++ b/web/ASC.Web.Api/Controllers/AuthenticationController.cs @@ -353,7 +353,7 @@ namespace ASC.Web.Api.Controllers var token = SecurityContext.AuthenticateMe(user.ID); MessageService.Send(sms ? MessageAction.LoginSuccessViaApiSms : MessageAction.LoginSuccessViaApiTfa); - ; + var expires = TenantCookieSettingsHelper.GetExpiresTime(tenant); var result = new AuthenticationTokenData diff --git a/web/ASC.Web.Api/Controllers/CapabilitiesController.cs b/web/ASC.Web.Api/Controllers/CapabilitiesController.cs index 7c83de70a3..9a4f50d326 100644 --- a/web/ASC.Web.Api/Controllers/CapabilitiesController.cs +++ b/web/ASC.Web.Api/Controllers/CapabilitiesController.cs @@ -77,7 +77,7 @@ namespace ASC.Web.Api.Controllers try { - if (SetupInfo.IsVisibleSettings(ManagementType.LdapSettings.ToString()) + if (SetupInfo.IsVisibleSettings(nameof(ManagementType.LdapSettings)) && (!CoreBaseSettings.Standalone || TenantManager.GetTenantQuota(TenantManager.GetCurrentTenant().TenantId).Ldap)) { @@ -108,7 +108,7 @@ namespace ASC.Web.Api.Controllers try { - if (SetupInfo.IsVisibleSettings(ManagementType.SingleSignOnSettings.ToString()) + if (SetupInfo.IsVisibleSettings(nameof(ManagementType.SingleSignOnSettings)) && TenantManager.GetTenantQuota(TenantManager.GetCurrentTenant().TenantId).Sso) { //var settings = SettingsManager.Load<SsoSettingsV2>(); @@ -119,8 +119,7 @@ namespace ASC.Web.Api.Controllers var configUrl = Configuration["web:sso:saml:login:url"] ?? ""; - result.SsoUrl = string.Format("{0}://{1}{2}{3}", uri.Scheme, uri.Host, - (uri.Port == 80 || uri.Port == 443) ? "" : ":" + uri.Port, configUrl); + result.SsoUrl = $"{uri.Scheme}://{uri.Host}{((uri.Port == 80 || uri.Port == 443) ? "" : ":" + uri.Port)}{configUrl}"; result.SsoLabel = string.Empty; // result.SsoLabel = settings.SpLoginLabel; //} diff --git a/web/ASC.Web.Api/Controllers/PortalController.cs b/web/ASC.Web.Api/Controllers/PortalController.cs index bdf46f7742..ae40c0e318 100644 --- a/web/ASC.Web.Api/Controllers/PortalController.cs +++ b/web/ASC.Web.Api/Controllers/PortalController.cs @@ -56,7 +56,8 @@ namespace ASC.Web.Api.Controllers private SetupInfo SetupInfo { get; } private DocumentServiceLicense DocumentServiceLicense { get; } private TenantExtra TenantExtra { get; set; } - private ILog Log { get; } + public ILog Log { get; } + public IHttpClientFactory ClientFactory { get; } public PortalController( @@ -77,7 +78,8 @@ namespace ASC.Web.Api.Controllers CoreBaseSettings coreBaseSettings, LicenseReader licenseReader, SetupInfo setupInfo, - DocumentServiceLicense documentServiceLicense + DocumentServiceLicense documentServiceLicense, + IHttpClientFactory clientFactory ) { Log = options.CurrentValue; @@ -98,6 +100,7 @@ namespace ASC.Web.Api.Controllers SetupInfo = setupInfo; DocumentServiceLicense = documentServiceLicense; TenantExtra = tenantExtra; + ClientFactory = clientFactory; } [Read("")] @@ -173,7 +176,7 @@ namespace ASC.Web.Api.Controllers [Read("userscount")] public long GetUsersCount() { - return CoreBaseSettings.Personal ? 1 : UserManager.GetUserNames(EmployeeStatus.Active).Count(); + return CoreBaseSettings.Personal ? 1 : UserManager.GetUserNames(EmployeeStatus.Active).Length; } [Read("tariff")] @@ -211,7 +214,7 @@ namespace ASC.Web.Api.Controllers [Read("thumb")] public FileResult GetThumb(string url) { - if (!SecurityContext.IsAuthenticated || !(Configuration["bookmarking:thumbnail-url"] != null)) + if (!SecurityContext.IsAuthenticated || Configuration["bookmarking:thumbnail-url"] == null) { return null; } @@ -222,7 +225,7 @@ namespace ASC.Web.Api.Controllers var request = new HttpRequestMessage(); request.RequestUri = new Uri(string.Format(Configuration["bookmarking:thumbnail-url"], url)); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using var stream = response.Content.ReadAsStream(); var bytes = new byte[stream.Length]; diff --git a/web/ASC.Web.Api/Controllers/SecurityController.cs b/web/ASC.Web.Api/Controllers/SecurityController.cs index 0b9a81ca5c..b8d0f40bd5 100644 --- a/web/ASC.Web.Api/Controllers/SecurityController.cs +++ b/web/ASC.Web.Api/Controllers/SecurityController.cs @@ -60,7 +60,7 @@ namespace ASC.Web.Api.Controllers [Read("audit/login/last")] public IEnumerable<EventWrapper> GetLastLoginEvents() { - if (!SetupInfo.IsVisibleSettings(ManagementType.LoginHistory.ToString())) + if (!SetupInfo.IsVisibleSettings(nameof(ManagementType.LoginHistory))) { throw new BillingException(Resource.ErrorNotAllowedOption, "Audit"); } @@ -73,7 +73,7 @@ namespace ASC.Web.Api.Controllers [Read("audit/events/last")] public IEnumerable<EventWrapper> GetLastAuditEvents() { - if (!SetupInfo.IsVisibleSettings(ManagementType.AuditTrail.ToString())) + if (!SetupInfo.IsVisibleSettings(nameof(ManagementType.AuditTrail))) { throw new BillingException(Resource.ErrorNotAllowedOption, "Audit"); } @@ -90,7 +90,7 @@ namespace ASC.Web.Api.Controllers var tenantId = TenantManager.GetCurrentTenant().TenantId; - if (!TenantExtra.GetTenantQuota().Audit || !SetupInfo.IsVisibleSettings(ManagementType.LoginHistory.ToString())) + if (!TenantExtra.GetTenantQuota().Audit || !SetupInfo.IsVisibleSettings(nameof(ManagementType.LoginHistory))) throw new BillingException(Resource.ErrorNotAllowedOption, "Audit"); var settings = SettingsManager.LoadForTenant<TenantAuditSettings>(TenantManager.GetCurrentTenant().TenantId); @@ -113,7 +113,7 @@ namespace ASC.Web.Api.Controllers var tenantId = TenantManager.GetCurrentTenant().TenantId; - if (!TenantExtra.GetTenantQuota().Audit || !SetupInfo.IsVisibleSettings(ManagementType.AuditTrail.ToString())) + if (!TenantExtra.GetTenantQuota().Audit || !SetupInfo.IsVisibleSettings(nameof(ManagementType.AuditTrail))) throw new BillingException(Resource.ErrorNotAllowedOption, "Audit"); var settings = SettingsManager.LoadForTenant<TenantAuditSettings>(TenantManager.GetCurrentTenant().TenantId); @@ -133,7 +133,7 @@ namespace ASC.Web.Api.Controllers [Read("audit/settings/lifetime")] public TenantAuditSettings GetAuditSettings() { - if (!SetupInfo.IsVisibleSettings(ManagementType.LoginHistory.ToString())) + if (!SetupInfo.IsVisibleSettings(nameof(ManagementType.LoginHistory))) { throw new BillingException(Resource.ErrorNotAllowedOption, "Audit"); } @@ -158,7 +158,7 @@ namespace ASC.Web.Api.Controllers private TenantAuditSettings SetAuditSettings(TenantAuditSettingsWrapper wrapper) { - if (!TenantExtra.GetTenantQuota().Audit || !SetupInfo.IsVisibleSettings(ManagementType.LoginHistory.ToString())) + if (!TenantExtra.GetTenantQuota().Audit || !SetupInfo.IsVisibleSettings(nameof(ManagementType.LoginHistory))) throw new BillingException(Resource.ErrorNotAllowedOption, "Audit"); PermissionContext.DemandPermissions(SecutiryConstants.EditPortalSettings); diff --git a/web/ASC.Web.Api/Controllers/SettingsController.cs b/web/ASC.Web.Api/Controllers/SettingsController.cs index cddec6aa4a..e678e7c4d9 100644 --- a/web/ASC.Web.Api/Controllers/SettingsController.cs +++ b/web/ASC.Web.Api/Controllers/SettingsController.cs @@ -174,6 +174,7 @@ namespace ASC.Api.Settings private InstanceCrypto InstanceCrypto { get; } private Signature Signature { get; } private DbWorker WebhookDbWorker { get; } + public IHttpClientFactory ClientFactory { get; } public SettingsController( IOptionsMonitor<ILog> option, @@ -238,7 +239,8 @@ namespace ASC.Api.Settings Constants constants, InstanceCrypto instanceCrypto, Signature signature, - DbWorker dbWorker) + DbWorker dbWorker, + IHttpClientFactory clientFactory) { Log = option.Get("ASC.Api"); WebHostEnvironment = webHostEnvironment; @@ -303,6 +305,7 @@ namespace ASC.Api.Settings Constants = constants; InstanceCrypto = instanceCrypto; Signature = signature; + ClientFactory = clientFactory; } [Read("", Check = false)] @@ -875,7 +878,6 @@ namespace ASC.Api.Settings { var EnabledModules = WebItemManagerSecurity.GetItems(WebZoneType.All, ItemAvailableState.Normal) .Where(item => !item.IsSubItem() && item.Visible) - .ToList() .Select(item => new { id = item.ProductClassName.HtmlEncode(), @@ -1110,7 +1112,11 @@ namespace ASC.Api.Settings if (model.Logo != null) { var logoDict = new Dictionary<int, string>(); - model.Logo.ToList().ForEach(n => logoDict.Add(Int32.Parse(n.Key), n.Value)); + + foreach(var l in model.Logo) + { + logoDict.Add(Int32.Parse(l.Key), l.Value); + } TenantWhiteLabelSettingsHelper.SetLogo(settings, logoDict, storage); } @@ -1131,7 +1137,7 @@ namespace ASC.Api.Settings throw new BillingException(Resource.ErrorNotAllowedOption, "WhiteLabel"); } - if (HttpContext.Request.Form?.Files == null || !HttpContext.Request.Form.Files.Any()) + if (HttpContext.Request.Form?.Files == null || HttpContext.Request.Form.Files.Count == 0) { throw new InvalidOperationException("No input files"); } @@ -1168,7 +1174,7 @@ namespace ASC.Api.Settings foreach (var f in HttpContext.Request.Form.Files) { var parts = f.FileName.Split('.'); - var logoType = (WhiteLabelLogoTypeEnum)(Convert.ToInt32(parts[0])); + var logoType = (WhiteLabelLogoTypeEnum)Convert.ToInt32(parts[0]); var fileExt = parts[1]; TenantWhiteLabelSettingsHelper.SetLogoFromStream(settings, logoType, fileExt, f.OpenReadStream(), storage); } @@ -1191,11 +1197,12 @@ namespace ASC.Api.Settings return new[] { - new {type = (int)WhiteLabelLogoTypeEnum.LightSmall, name = WhiteLabelLogoTypeEnum.LightSmall.ToString(), height = TenantWhiteLabelSettings.logoLightSmallSize.Height, width = TenantWhiteLabelSettings.logoLightSmallSize.Width}, - new {type = (int)WhiteLabelLogoTypeEnum.Dark, name = WhiteLabelLogoTypeEnum.Dark.ToString(), height = TenantWhiteLabelSettings.logoDarkSize.Height, width = TenantWhiteLabelSettings.logoDarkSize.Width}, - new {type = (int)WhiteLabelLogoTypeEnum.Favicon, name = WhiteLabelLogoTypeEnum.Favicon.ToString(), height = TenantWhiteLabelSettings.logoFaviconSize.Height, width = TenantWhiteLabelSettings.logoFaviconSize.Width}, - new {type = (int)WhiteLabelLogoTypeEnum.DocsEditor, name = WhiteLabelLogoTypeEnum.DocsEditor.ToString(), height = TenantWhiteLabelSettings.logoDocsEditorSize.Height, width = TenantWhiteLabelSettings.logoDocsEditorSize.Width}, - new {type = (int)WhiteLabelLogoTypeEnum.DocsEditorEmbed, name = WhiteLabelLogoTypeEnum.DocsEditorEmbed.ToString(), height = TenantWhiteLabelSettings.logoDocsEditorEmbedSize.Height, width = TenantWhiteLabelSettings.logoDocsEditorEmbedSize.Width} + new {type = (int)WhiteLabelLogoTypeEnum.LightSmall, name = nameof(WhiteLabelLogoTypeEnum.LightSmall), height = TenantWhiteLabelSettings.logoLightSmallSize.Height, width = TenantWhiteLabelSettings.logoLightSmallSize.Width}, + new {type = (int)WhiteLabelLogoTypeEnum.Dark, name = nameof(WhiteLabelLogoTypeEnum.Dark), height = TenantWhiteLabelSettings.logoDarkSize.Height, width = TenantWhiteLabelSettings.logoDarkSize.Width}, + new {type = (int)WhiteLabelLogoTypeEnum.Favicon, name = nameof(WhiteLabelLogoTypeEnum.Favicon), height = TenantWhiteLabelSettings.logoFaviconSize.Height, width = TenantWhiteLabelSettings.logoFaviconSize.Width}, + new {type = (int)WhiteLabelLogoTypeEnum.DocsEditor, name = nameof(WhiteLabelLogoTypeEnum.DocsEditor), height = TenantWhiteLabelSettings.logoDocsEditorSize.Height, width = TenantWhiteLabelSettings.logoDocsEditorSize.Width}, + new {type = (int)WhiteLabelLogoTypeEnum.DocsEditorEmbed, name = nameof(WhiteLabelLogoTypeEnum.DocsEditorEmbed), height = TenantWhiteLabelSettings.logoDocsEditorEmbedSize.Height, width = TenantWhiteLabelSettings.logoDocsEditorEmbedSize.Width} + }; } @@ -1376,7 +1383,7 @@ namespace ASC.Api.Settings try { var request = new HttpRequestMessage(); - request.RequestUri = new Uri(string.Format("{0}/tips/deletereaded", SetupInfo.TipsAddress)); + request.RequestUri = new Uri($"{SetupInfo.TipsAddress}/tips/deletereaded"); var data = new NameValueCollection { @@ -1386,7 +1393,7 @@ namespace ASC.Api.Settings var body = JsonSerializer.Serialize(data);//todo check request.Content = new StringContent(body); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); } @@ -1801,7 +1808,7 @@ namespace ASC.Api.Settings MessageService.Send(MessageAction.OwnerSentChangeOwnerInstructions, MessageTarget.Create(owner.ID), owner.DisplayUserName(false, DisplayUserSettingsHelper)); - var emailLink = string.Format("<a href=\"mailto:{0}\">{0}</a>", owner.Email); + var emailLink = $"<a href=\"mailto:{owner.Email}\">{owner.Email}</a>"; return new { Status = 1, Message = Resource.ChangePortalOwnerMsg.Replace(":email", emailLink) }; } @@ -1945,7 +1952,7 @@ namespace ASC.Api.Settings TenantManager.SaveTenantQuota(quota); - var DEFAULT_TRIAL_PERIOD = 30; + const int DEFAULT_TRIAL_PERIOD = 30; var tariff = new Tariff { @@ -1986,9 +1993,9 @@ namespace ASC.Api.Settings return dueDate >= DateTime.UtcNow.Date ? Resource.LicenseUploaded : string.Format( - (TenantExtra.GetTenantQuota().Update + TenantExtra.GetTenantQuota().Update ? Resource.LicenseUploadedOverdueSupport - : Resource.LicenseUploadedOverdue), + : Resource.LicenseUploadedOverdue, "", "", dueDate.Date.ToLongDateString()); @@ -2230,7 +2237,7 @@ namespace ASC.Api.Settings TenantExtra.DemandControlPanelPermission(); var current = SettingsManager.Load<StorageSettings>(); - var consumers = ConsumerFactory.GetAll<DataStoreConsumer>().ToList(); + var consumers = ConsumerFactory.GetAll<DataStoreConsumer>(); return consumers.Select(consumer => new StorageWrapper(consumer, current)).ToList(); } @@ -2270,7 +2277,7 @@ namespace ASC.Api.Settings { var activeTenants = TenantManager.GetTenants(); - if (activeTenants.Any()) + if (activeTenants.Count > 0) { StartEncryption(storageEncryption.NotifyUsers); } @@ -2318,7 +2325,7 @@ namespace ASC.Api.Settings foreach (var tenant in tenants) { var progress = BackupAjaxHandler.GetBackupProgress(tenant.TenantId); - if (progress != null && progress.IsCompleted == false) + if (progress != null && !progress.IsCompleted) { throw new Exception(); } @@ -2528,7 +2535,7 @@ namespace ASC.Api.Settings TenantExtra.DemandControlPanelPermission(); var current = SettingsManager.Load<CdnStorageSettings>(); - var consumers = ConsumerFactory.GetAll<DataStoreConsumer>().Where(r => r.Cdn != null).ToList(); + var consumers = ConsumerFactory.GetAll<DataStoreConsumer>().Where(r => r.Cdn != null); return consumers.Select(consumer => new StorageWrapper(consumer, current)).ToList(); } @@ -2606,7 +2613,7 @@ namespace ASC.Api.Settings }; } - var consumers = ConsumerFactory.GetAll<DataStoreConsumer>().ToList(); + var consumers = ConsumerFactory.GetAll<DataStoreConsumer>(); return consumers.Select(consumer => new StorageWrapper(consumer, current)).ToList(); } @@ -2622,9 +2629,9 @@ namespace ASC.Api.Settings public object GetSocketSettings() { var hubUrl = Configuration["web:hub"] ?? string.Empty; - if (hubUrl != string.Empty) + if (hubUrl.Length != 0) { - if (!hubUrl.EndsWith("/")) + if (!hubUrl.EndsWith('/')) { hubUrl += "/"; } @@ -2746,7 +2753,7 @@ namespace ASC.Api.Settings private bool SaveMailWhiteLabelSettings(MailWhiteLabelSettings settings) { - if (settings == null) throw new ArgumentNullException("settings"); + if (settings == null) throw new ArgumentNullException(nameof(settings)); DemandRebrandingPermission(); @@ -2844,7 +2851,7 @@ namespace ASC.Api.Settings PermissionContext.DemandPermissions(SecutiryConstants.EditPortalSettings); var saveAvailable = CoreBaseSettings.Standalone || TenantManager.GetTenantQuota(TenantManager.GetCurrentTenant().TenantId).ThirdParty; - if (!SetupInfo.IsVisibleSettings(ManagementType.ThirdPartyAuthorization.ToString()) + if (!SetupInfo.IsVisibleSettings(nameof(ManagementType.ThirdPartyAuthorization)) || !saveAvailable) throw new BillingException(Resource.ErrorNotAllowedOption, "ThirdPartyAuthorization"); @@ -3020,7 +3027,7 @@ namespace ASC.Api.Settings throw new Exception(Resource.ErrorRequestLimitExceeded); } - MemoryCache.Set(key, ++count, TimeSpan.FromMinutes(expirationMinutes)); + MemoryCache.Set(key, count + 1, TimeSpan.FromMinutes(expirationMinutes)); } } } \ No newline at end of file diff --git a/web/ASC.Web.Api/Controllers/SmtpSettingsController.cs b/web/ASC.Web.Api/Controllers/SmtpSettingsController.cs index 6b040484b6..980c88b456 100644 --- a/web/ASC.Web.Api/Controllers/SmtpSettingsController.cs +++ b/web/ASC.Web.Api/Controllers/SmtpSettingsController.cs @@ -100,7 +100,7 @@ namespace ASC.Api.Settings //TODO: Add validation check if (smtpSettings == null) - throw new ArgumentNullException("smtpSettings"); + throw new ArgumentNullException(nameof(smtpSettings)); PermissionContext.DemandPermissions(SecutiryConstants.EditPortalSettings); @@ -231,7 +231,7 @@ namespace ASC.Api.Settings private static void CheckSmtpPermissions() { - if (!SetupInfo.IsVisibleSettings(ManagementType.SmtpSettings.ToString())) + if (!SetupInfo.IsVisibleSettings(nameof(ManagementType.SmtpSettings))) { throw new BillingException(Resource.ErrorNotAllowedOption, "Smtp"); } diff --git a/web/ASC.Web.Api/Controllers/ThirdPartyController.cs b/web/ASC.Web.Api/Controllers/ThirdPartyController.cs index 65c975614c..5808c024bf 100644 --- a/web/ASC.Web.Api/Controllers/ThirdPartyController.cs +++ b/web/ASC.Web.Api/Controllers/ThirdPartyController.cs @@ -140,7 +140,7 @@ namespace ASC.Web.Api.Controllers private static string AppendCode(string url, string code = null, string error = null) { - url += (url.Contains("#") ? "&" : "#") + url += (url.Contains('#') ? "&" : "#") + (string.IsNullOrEmpty(error) ? (string.IsNullOrEmpty(code) ? string.Empty diff --git a/web/ASC.Web.Api/Core/FirstTimeTenantSettings.cs b/web/ASC.Web.Api/Core/FirstTimeTenantSettings.cs index 24cc65fec9..8027e62eec 100644 --- a/web/ASC.Web.Api/Core/FirstTimeTenantSettings.cs +++ b/web/ASC.Web.Api/Core/FirstTimeTenantSettings.cs @@ -70,6 +70,7 @@ namespace ASC.Web.Studio.UserControls.FirstTime private StudioNotifyService StudioNotifyService { get; } private TimeZoneConverter TimeZoneConverter { get; } public CoreBaseSettings CoreBaseSettings { get; } + public IHttpClientFactory ClientFactory { get; } public FirstTimeTenantSettings( IOptionsMonitor<ILog> options, @@ -84,7 +85,8 @@ namespace ASC.Web.Studio.UserControls.FirstTime LicenseReader licenseReader, StudioNotifyService studioNotifyService, TimeZoneConverter timeZoneConverter, - CoreBaseSettings coreBaseSettings) + CoreBaseSettings coreBaseSettings, + IHttpClientFactory clientFactory) { Log = options.CurrentValue; TenantManager = tenantManager; @@ -99,6 +101,7 @@ namespace ASC.Web.Studio.UserControls.FirstTime StudioNotifyService = studioNotifyService; TimeZoneConverter = timeZoneConverter; CoreBaseSettings = coreBaseSettings; + ClientFactory = clientFactory; } public WizardSettings SaveData(WizardModel wizardModel) @@ -247,7 +250,7 @@ namespace ASC.Web.Studio.UserControls.FirstTime try { - using (var httpClient = new HttpClient()) + var httpClient = ClientFactory.CreateClient(); using (var response = httpClient.Send(request)) using (var responseStream = response.Content.ReadAsStream()) using (var reader = new StreamReader(responseStream)) @@ -286,7 +289,7 @@ namespace ASC.Web.Studio.UserControls.FirstTime var data = JsonSerializer.Serialize(values); request.Content = new StringContent(data); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); Log.Debug("Subscribe response: " + response);//toto write diff --git a/web/ASC.Web.Api/Models/Smtp/SmtpOperation.cs b/web/ASC.Web.Api/Models/Smtp/SmtpOperation.cs index 759ab0693a..df85dedbef 100644 --- a/web/ASC.Web.Api/Models/Smtp/SmtpOperation.cs +++ b/web/ASC.Web.Api/Models/Smtp/SmtpOperation.cs @@ -221,17 +221,11 @@ namespace ASC.Api.Settings.Smtp public SmtpClient GetSmtpClient() { - var sslCertificatePermit = Configuration["mail.certificate-permit"] != null && - Convert.ToBoolean(Configuration["mail.certificate-permit"]); - var client = new SmtpClient { Timeout = (int)TimeSpan.FromSeconds(30).TotalMilliseconds }; - if (sslCertificatePermit) - client.ServerCertificateValidationCallback = (sender, certificate, chain, errors) => true; - return client; } diff --git a/web/ASC.Web.Api/Program.cs b/web/ASC.Web.Api/Program.cs index 836553f1dc..5c73f946ed 100644 --- a/web/ASC.Web.Api/Program.cs +++ b/web/ASC.Web.Api/Program.cs @@ -15,7 +15,7 @@ using Microsoft.Extensions.Hosting; namespace ASC.Web.Api { - public class Program + public static class Program { public async static Task Main(string[] args) { diff --git a/web/ASC.Web.Core/Calendars/BaseCalendar.cs b/web/ASC.Web.Core/Calendars/BaseCalendar.cs index d67a7a0b42..942991c97c 100644 --- a/web/ASC.Web.Core/Calendars/BaseCalendar.cs +++ b/web/ASC.Web.Core/Calendars/BaseCalendar.cs @@ -35,7 +35,7 @@ namespace ASC.Web.Core.Calendars { public abstract class BaseCalendar : ICalendar, ICloneable { - public BaseCalendar(AuthContext authContext, TimeZoneConverter timeZoneConverter) + protected BaseCalendar(AuthContext authContext, TimeZoneConverter timeZoneConverter) { this.Context = new CalendarContext(); this.SharingOptions = new SharingOptions(); @@ -92,11 +92,11 @@ namespace ASC.Web.Core.Calendars sb.AppendLine("METHOD:PUBLISH"); sb.AppendLine("CALSCALE:GREGORIAN"); - sb.AppendLine(string.Format("X-WR-CALNAME:{0}", Name)); - sb.AppendLine(string.Format("X-WR-TIMEZONE:{0}", TimeZoneConverter.WindowsTzId2OlsonTzId(TimeZone.Id))); + sb.AppendLine($"X-WR-CALNAME:{Name}"); + sb.AppendLine($"X-WR-TIMEZONE:{TimeZoneConverter.WindowsTzId2OlsonTzId(TimeZone.Id)}"); //tz sb.AppendLine("BEGIN:VTIMEZONE"); - sb.AppendLine(string.Format("TZID:{0}", TimeZoneConverter.WindowsTzId2OlsonTzId(TimeZone.Id))); + sb.AppendLine($"TZID:{TimeZoneConverter.WindowsTzId2OlsonTzId(TimeZone.Id)}"); sb.AppendLine("END:VTIMEZONE"); //events diff --git a/web/ASC.Web.Core/Calendars/BaseEvent.cs b/web/ASC.Web.Core/Calendars/BaseEvent.cs index 80d0ba2165..dca6649370 100644 --- a/web/ASC.Web.Core/Calendars/BaseEvent.cs +++ b/web/ASC.Web.Core/Calendars/BaseEvent.cs @@ -33,7 +33,7 @@ namespace ASC.Web.Core.Calendars { public virtual TimeZoneInfo TimeZone { get; set; } - public BaseEvent() + protected BaseEvent() { this.Context = new EventContext(); this.AlertType = EventAlertType.Never; @@ -96,11 +96,14 @@ namespace ASC.Web.Core.Calendars var sb = new StringBuilder(); sb.AppendLine("BEGIN:VEVENT"); - sb.AppendLine(string.Format("UID:{0}", string.IsNullOrEmpty(this.Uid) ? this.Id : this.Uid)); - sb.AppendLine(string.Format("SUMMARY:{0}", this.Name)); + + var id = string.IsNullOrEmpty(Uid) ? Id : Uid; + + sb.AppendLine($"UID:{id}"); + sb.AppendLine($"SUMMARY:{Name}"); if (!string.IsNullOrEmpty(this.Description)) - sb.AppendLine(string.Format("DESCRIPTION:{0}", this.Description.Replace("\n", "\\n"))); + sb.AppendLine($"DESCRIPTION:{Description.Replace("\n", "\\n")}"); if (this.AllDayLong) { @@ -115,18 +118,30 @@ namespace ASC.Web.Core.Calendars } if (this.UtcStartDate != DateTime.MinValue) - sb.AppendLine(string.Format("DTSTART;VALUE=DATE:{0}", startDate.ToString("yyyyMMdd"))); + { + var start = startDate.ToString("yyyyMMdd"); + sb.AppendLine($"DTSTART;VALUE=DATE:{start}"); + } if (this.UtcEndDate != DateTime.MinValue) - sb.AppendLine(string.Format("DTEND;VALUE=DATE:{0}", endDate.AddDays(1).ToString("yyyyMMdd"))); + { + var end = endDate.AddDays(1).ToString("yyyyMMdd"); + sb.AppendLine($"DTEND;VALUE=DATE:{end}"); + } } else { if (this.UtcStartDate != DateTime.MinValue) - sb.AppendLine(string.Format("DTSTART:{0}", this.UtcStartDate.ToString("yyyyMMdd'T'HHmmss'Z'"))); + { + var utcStart = UtcStartDate.ToString("yyyyMMdd'T'HHmmss'Z'"); + sb.AppendLine($"DTSTART:{utcStart}"); + } if (this.UtcEndDate != DateTime.MinValue) - sb.AppendLine(string.Format("DTEND:{0}", this.UtcEndDate.ToString("yyyyMMdd'T'HHmmss'Z'"))); + { + var utcEnd = UtcEndDate.ToString("yyyyMMdd'T'HHmmss'Z'"); + sb.AppendLine($"DTEND:{utcEnd}"); + } } diff --git a/web/ASC.Web.Core/Calendars/BaseTodo.cs b/web/ASC.Web.Core/Calendars/BaseTodo.cs index 4b30e3e07a..e2f81514cb 100644 --- a/web/ASC.Web.Core/Calendars/BaseTodo.cs +++ b/web/ASC.Web.Core/Calendars/BaseTodo.cs @@ -33,7 +33,7 @@ namespace ASC.Web.Core.Calendars { internal TimeZoneInfo TimeZone { get; set; } - public BaseTodo() + protected BaseTodo() { this.Context = new TodoContext(); } @@ -80,19 +80,27 @@ namespace ASC.Web.Core.Calendars { var sb = new StringBuilder(); - sb.AppendLine("BEGIN:TODO"); - sb.AppendLine(string.Format("UID:{0}", string.IsNullOrEmpty(this.Uid) ? this.Id : this.Uid)); - sb.AppendLine(string.Format("SUMMARY:{0}", this.Name)); + sb.AppendLine("BEGIN:TODO"); + + var id = string.IsNullOrEmpty(this.Uid) ? this.Id : this.Uid; + + sb.AppendLine($"UID:{id}"); + sb.AppendLine($"SUMMARY:{Name}"); if (!string.IsNullOrEmpty(this.Description)) - sb.AppendLine(string.Format("DESCRIPTION:{0}", this.Description.Replace("\n", "\\n"))); + sb.AppendLine($"DESCRIPTION:{Description.Replace("\n", "\\n")}"); - if (this.UtcStartDate != DateTime.MinValue) - sb.AppendLine(string.Format("DTSTART:{0}", this.UtcStartDate.ToString("yyyyMMdd'T'HHmmss'Z'"))); - - if (this.Completed != DateTime.MinValue) - sb.AppendLine(string.Format("COMPLETED:{0}", this.Completed.ToString("yyyyMMdd'T'HHmmss'Z'"))); + if (this.UtcStartDate != DateTime.MinValue) + { + var utcStart = UtcStartDate.ToString("yyyyMMdd'T'HHmmss'Z'"); + sb.AppendLine($"DTSTART:{utcStart}"); + } + if (this.Completed != DateTime.MinValue) + { + var completed = Completed.ToString("yyyyMMdd'T'HHmmss'Z'"); + sb.AppendLine($"COMPLETED:{completed}"); + } sb.Append("END:TODO"); return sb.ToString(); diff --git a/web/ASC.Web.Core/Calendars/RecurrenceRule.cs b/web/ASC.Web.Core/Calendars/RecurrenceRule.cs index d89a288a28..b1d4bdd894 100644 --- a/web/ASC.Web.Core/Calendars/RecurrenceRule.cs +++ b/web/ASC.Web.Core/Calendars/RecurrenceRule.cs @@ -76,7 +76,7 @@ namespace ASC.Web.Core.Calendars public static string ToShortString(this DateTime targetDateTime) { - return String.Format("{0} {1}", targetDateTime.ToShortDateString(), targetDateTime.ToShortTimeString()); + return $"{targetDateTime.ToShortDateString()} {targetDateTime.ToShortTimeString()}"; } } @@ -120,7 +120,7 @@ namespace ASC.Web.Core.Calendars { get { - return ((Id ?? "").ToLower()) switch + return (Id ?? "").ToLower() switch { "su" => DayOfWeek.Sunday, "mo" => DayOfWeek.Monday, @@ -160,7 +160,7 @@ namespace ASC.Web.Core.Calendars return dates; } - public static WeekDay Parse(string iCalStrValue) + public static WeekDay ParseWeekDay(string iCalStrValue) { var d = new WeekDay(); @@ -215,7 +215,7 @@ namespace ASC.Web.Core.Calendars this.Until = DateTime.MinValue; this.Count = -1; this.Interval = 1; - this.WKST = WeekDay.Parse("mo"); + this.WKST = WeekDay.ParseWeekDay("mo"); this.ExDates = new List<ExDate>(); } @@ -238,7 +238,7 @@ namespace ASC.Web.Core.Calendars if (ByMonthDay != null && !ByMonthDay.Contains(d.Day) && !ByMonthDay.Contains(d.Day - d.GetDaysInMonth() + 1)) return false; - if (ByDay != null && !ByDay.ToList().Exists(item => item.DayOfWeek == d.DayOfWeek)) + if (ByDay != null && !ByDay.Any(item => item.DayOfWeek == d.DayOfWeek)) return false; return true; @@ -256,7 +256,7 @@ namespace ASC.Web.Core.Calendars { var dates = new List<DateTime>(); var utcStartDateOffset = isAllDayLong ? TimeSpan.Zero : eventTimeZone.GetUtcOffset(utcStartDate); - var endDate = (this.Until == DateTime.MinValue ? toDate : (toDate > this.Until ? this.Until : toDate)); + var endDate = this.Until == DateTime.MinValue ? toDate : (toDate > this.Until ? this.Until : toDate); //push start date dates.Add(utcStartDate); @@ -381,18 +381,18 @@ namespace ASC.Web.Core.Calendars dateRange.RemoveAll(date => !ByMonth.Contains(date.Month)); if (ByYearDay != null) - dateRange.RemoveAll(date => (!ByYearDay.Contains(date.DayOfYear) && !ByYearDay.Contains(date.DayOfYear - (date.GetDaysInYear() + 1)))); + dateRange.RemoveAll(date => !ByYearDay.Contains(date.DayOfYear) && !ByYearDay.Contains(date.DayOfYear - (date.GetDaysInYear() + 1))); if (ByMonthDay != null) - dateRange.RemoveAll(date => (!ByMonthDay.Contains(date.Day) && !ByMonthDay.Contains(date.Day - (date.GetDaysInMonth() + 1)))); + dateRange.RemoveAll(date => !ByMonthDay.Contains(date.Day) && !ByMonthDay.Contains(date.Day - (date.GetDaysInMonth() + 1))); if (ByDay != null) - dateRange.RemoveAll(date => !ByDay.ToList().Exists(wd => wd.DayOfWeek == date.DayOfWeek)); + dateRange.RemoveAll(date => !ByDay.Any(wd => wd.DayOfWeek == date.DayOfWeek)); if (ByDay == null && ByMonthDay == null && ByYearDay == null) dateRange.RemoveAll(date => date.Day != d.Day); - GetDatesWithTime(ref dates, utcStartDate, endDate, (d - utcStartDateOffset), dateRange.Select(item => item - utcStartDateOffset).ToList()); + GetDatesWithTime(ref dates, utcStartDate, endDate, d - utcStartDateOffset, dateRange.Select(item => item - utcStartDateOffset).ToList()); d = d.AddDays(7 * this.Interval); @@ -422,10 +422,10 @@ namespace ASC.Web.Core.Calendars } if (ByYearDay != null) - dateRange.RemoveAll(date => (!ByYearDay.Contains(date.DayOfYear) && !ByYearDay.Contains(date.DayOfYear - (date.GetDaysInYear() + 1)))); + dateRange.RemoveAll(date => !ByYearDay.Contains(date.DayOfYear) && !ByYearDay.Contains(date.DayOfYear - (date.GetDaysInYear() + 1))); if (ByMonthDay != null) - dateRange.RemoveAll(date => (!ByMonthDay.Contains(date.Day) && !ByMonthDay.Contains(date.Day - (date.GetDaysInMonth() + 1)))); + dateRange.RemoveAll(date => !ByMonthDay.Contains(date.Day) && !ByMonthDay.Contains(date.Day - (date.GetDaysInMonth() + 1))); //only for MONTHLY or YEARLY if (ByDay != null) @@ -440,7 +440,7 @@ namespace ASC.Web.Core.Calendars if (ByDay == null && ByMonthDay == null && ByYearDay == null) dateRange.RemoveAll(date => date.Day != d.Day); - GetDatesWithTime(ref dates, utcStartDate, endDate, (d - utcStartDateOffset), dateRange); + GetDatesWithTime(ref dates, utcStartDate, endDate, d - utcStartDateOffset, dateRange); var nextd = d.AddMonths(this.Interval); @@ -513,7 +513,7 @@ namespace ASC.Web.Core.Calendars dateRange.RemoveAll(date => { var weekOfYear = date.GetWeekOfYear(this.WKST.DayOfWeek); - return ((!ByWeekNo.Contains(weekOfYear) && !ByWeekNo.Contains(weekOfYear - (date.GetWeekOfYearCount(this.WKST.DayOfWeek) + 1)))); + return !ByWeekNo.Contains(weekOfYear) && !ByWeekNo.Contains(weekOfYear - (date.GetWeekOfYearCount(this.WKST.DayOfWeek) + 1)); }); } isFirst = false; @@ -527,7 +527,7 @@ namespace ASC.Web.Core.Calendars dateRange.Add(new DateTime(d.Year, 1, 1).AddDays((yearDay > 0 ? yearDay : (d.GetDaysInYear() + yearDay)) - 1)); } else - dateRange.RemoveAll(date => (!ByYearDay.Contains(date.DayOfYear) && !ByYearDay.Contains(date.DayOfYear - (date.GetDaysInYear() + 1)))); + dateRange.RemoveAll(date => !ByYearDay.Contains(date.DayOfYear) && !ByYearDay.Contains(date.DayOfYear - (date.GetDaysInYear() + 1))); isFirst = false; } @@ -547,7 +547,7 @@ namespace ASC.Web.Core.Calendars } } else - dateRange.RemoveAll(date => (!ByMonthDay.Contains(date.Day) && !ByMonthDay.Contains(date.Day - (date.GetDaysInMonth() + 1)))); + dateRange.RemoveAll(date => !ByMonthDay.Contains(date.Day) && !ByMonthDay.Contains(date.Day - (date.GetDaysInMonth() + 1))); isFirst = false; } @@ -576,7 +576,7 @@ namespace ASC.Web.Core.Calendars if (isFirst) dateRange.Add(d); - GetDatesWithTime(ref dates, utcStartDate, endDate, (d - utcStartDateOffset), dateRange); + GetDatesWithTime(ref dates, utcStartDate, endDate, d - utcStartDateOffset, dateRange); d = d.AddYears(this.Interval); @@ -738,23 +738,23 @@ namespace ASC.Web.Core.Calendars if (Until != DateTime.MinValue) { - sb.AppendFormat(";until={0}", Until.ToString("yyyyMMdd'T'HHmmss'Z'")); + sb.Append($";until={Until.ToString("yyyyMMdd'T'HHmmss'Z'")}"); } else if (Count >= 0) { - sb.AppendFormat(";count={0}", Count); + sb.Append($";count={Count}"); } if (Interval > 1) { - sb.AppendFormat(";interval={0}", Interval); + sb.Append($";interval={Interval}"); } if (BySecond != null && BySecond.Length > 0) { sb.Append(";bysecond="); foreach (var s in BySecond) - sb.AppendFormat("{0},", s); + sb.Append($"{s},"); sb.Remove(sb.Length - 1, 1); } @@ -833,11 +833,11 @@ namespace ASC.Web.Core.Calendars } if (WKST.DayOfWeek != DayOfWeek.Monday) - sb.AppendFormat(";wkst={0}", WKST.Id); + sb.Append($";wkst={WKST.Id}"); if (!iCal && ExDates != null && ExDates.Count > 0) { - sb.AppendFormat(";exdates="); + sb.Append(";exdates="); foreach (var d in this.ExDates) { if (d.IsDateTime) @@ -869,7 +869,7 @@ namespace ASC.Web.Core.Calendars public static Frequency ParseFrequency(string frequency) { - return (frequency.ToLower()) switch + return frequency.ToLower() switch { "monthly" => Frequency.Monthly, @@ -931,7 +931,7 @@ namespace ASC.Web.Core.Calendars break; case "byday": - rr.ByDay = val.Split(',').Select(v => RecurrenceRule.WeekDay.Parse(v)).ToArray(); + rr.ByDay = val.Split(',').Select(v => RecurrenceRule.WeekDay.ParseWeekDay(v)).ToArray(); break; case "bymonthday": @@ -955,7 +955,7 @@ namespace ASC.Web.Core.Calendars break; case "wkst": - rr.WKST = RecurrenceRule.WeekDay.Parse(val); + rr.WKST = RecurrenceRule.WeekDay.ParseWeekDay(val); break; case "exdates": @@ -963,7 +963,7 @@ namespace ASC.Web.Core.Calendars foreach (var date in val.Split(',')) { if (DateTime.TryParseExact(date.ToUpper(), _dateTimeFormats, CultureInfo.InvariantCulture, DateTimeStyles.AdjustToUniversal, out var dt)) - rr.ExDates.Add(new ExDate() { Date = dt, IsDateTime = (date.ToLower().IndexOf('t') >= 0) }); + rr.ExDates.Add(new ExDate() { Date = dt, IsDateTime = date.IndexOf('t', StringComparison.InvariantCultureIgnoreCase) >= 0 }); } break; @@ -989,7 +989,7 @@ namespace ASC.Web.Core.Calendars if (!this.ExDates[0].IsDateTime) sb.Append(";VALUE=DATE"); - sb.Append(":"); + sb.Append(':'); foreach (var d in this.ExDates) { if (d.IsDateTime) @@ -997,7 +997,7 @@ namespace ASC.Web.Core.Calendars else sb.Append(d.Date.ToString("yyyyMMdd")); - sb.Append(","); + sb.Append(','); } sb.Remove(sb.Length - 1, 1); } @@ -1020,11 +1020,11 @@ namespace ASC.Web.Core.Calendars { var days = new List<WeekDay>(); foreach (var d in ByDay) - days.Add(WeekDay.Parse(d.ToString())); + days.Add(WeekDay.ParseWeekDay(d.ToString())); o.ByDay = days.ToArray(); } - o.WKST = WeekDay.Parse(this.WKST.ToString()); + o.WKST = WeekDay.ParseWeekDay(this.WKST.ToString()); return o; } diff --git a/web/ASC.Web.Core/CommonPhotoManager.cs b/web/ASC.Web.Core/CommonPhotoManager.cs index 6140715abd..bedb1f67e4 100644 --- a/web/ASC.Web.Core/CommonPhotoManager.cs +++ b/web/ASC.Web.Core/CommonPhotoManager.cs @@ -36,7 +36,7 @@ using SixLabors.ImageSharp.Processing; namespace ASC.Web.Core { - public class CommonPhotoManager + public static class CommonPhotoManager { public static Image DoThumbnail(Image image, Size size, bool crop, bool transparent, bool rectangle) @@ -51,11 +51,9 @@ namespace ASC.Web.Core var maxSide = realWidth > realHeight ? realWidth : realHeight; var minSide = realWidth < realHeight ? realWidth : realHeight; - var alignWidth = true; - if (crop) alignWidth = (minSide == realWidth); - else alignWidth = (maxSide == realWidth); + var alignWidth = crop ? (minSide == realWidth) : (maxSide == realWidth); - var scaleFactor = (alignWidth) ? (realWidth / (1.0 * width)) : (realHeight / (1.0 * height)); + var scaleFactor = alignWidth ? (realWidth / (1.0 * width)) : (realHeight / (1.0 * height)); if (scaleFactor < 1) scaleFactor = 1; diff --git a/web/ASC.Web.Core/Extensions/StringExtension.cs b/web/ASC.Web.Core/Extensions/StringExtension.cs index 126cc5569f..fdee36c266 100644 --- a/web/ASC.Web.Core/Extensions/StringExtension.cs +++ b/web/ASC.Web.Core/Extensions/StringExtension.cs @@ -52,7 +52,7 @@ namespace System /// <returns></returns> public static string ReplaceSingleQuote(this string str) { - return str?.Replace("'", "′"); + return str?.Replace('\'', '′'); } public static bool TestEmailRegex(this string emailAddress) diff --git a/web/ASC.Web.Core/Extensions/UserInfoExtension.cs b/web/ASC.Web.Core/Extensions/UserInfoExtension.cs index 603170b1e1..a65d7e6a93 100644 --- a/web/ASC.Web.Core/Extensions/UserInfoExtension.cs +++ b/web/ASC.Web.Core/Extensions/UserInfoExtension.cs @@ -103,13 +103,13 @@ namespace ASC.Core.Users //check for removed users if (userInfo.ID == Constants.LostUser.ID) { - sb.AppendFormat("<span class='userLink text-medium-describe' style='white-space:nowrap;'>{0}</span>", userInfo.DisplayUserName(displayUserSettingsHelper)); + sb.Append($"<span class='userLink text-medium-describe' style='white-space:nowrap;'>{userInfo.DisplayUserName(displayUserSettingsHelper)}</span>"); } else { var popupID = Guid.NewGuid(); - sb.AppendFormat("<span class=\"userLink\" style='white-space:nowrap;' id='{0}' data-uid='{1}'>", popupID, userInfo.ID); - sb.AppendFormat("<a class='linkDescribe' href=\"{0}\">{1}</a>", userInfo.GetUserProfilePageURLGeneral(commonLinkUtility), userInfo.DisplayUserName(displayUserSettingsHelper)); + sb.Append($"<span class=\"userLink\" style='white-space:nowrap;' id='{popupID}' data-uid='{userInfo.ID}'>"); + sb.Append($"<a class='linkDescribe' href=\"{userInfo.GetUserProfilePageURLGeneral(commonLinkUtility)}\">{userInfo.DisplayUserName(displayUserSettingsHelper)}</a>"); sb.Append("</span>"); sb.AppendFormat("<script language='javascript'> StudioUserProfileInfo.RegistryElement('{0}','\"{1}\"); </script>", popupID, userInfo.ID); diff --git a/web/ASC.Web.Core/FileSizeComment.cs b/web/ASC.Web.Core/FileSizeComment.cs index c5a3e77ff7..10823dfc6a 100644 --- a/web/ASC.Web.Core/FileSizeComment.cs +++ b/web/ASC.Web.Core/FileSizeComment.cs @@ -57,12 +57,12 @@ namespace ASC.Web.Studio.Core public static string GetFileSizeExceptionString(long size) { - return string.Format("{0} ({1}).", Resource.FileSizeMaxExceed, FilesSizeToString(size)); + return $"{Resource.FileSizeMaxExceed} ({FilesSizeToString(size)})."; } public static string GetPersonalFreeSpaceExceptionString(long size) { - return string.Format("{0} ({1}).", Resource.PersonalFreeSpaceException, FilesSizeToString(size)); + return $"{Resource.PersonalFreeSpaceException} ({FilesSizeToString(size)})."; } /// <summary> diff --git a/web/ASC.Web.Core/Files/DocumentService.cs b/web/ASC.Web.Core/Files/DocumentService.cs index 044ad3fef2..aa24156847 100644 --- a/web/ASC.Web.Core/Files/DocumentService.cs +++ b/web/ASC.Web.Core/Files/DocumentService.cs @@ -41,7 +41,6 @@ using System.Text.Json.Serialization; using System.Text.RegularExpressions; using ASC.Common.Web; -using ASC.Core; using ASC.Core.Billing; using Newtonsoft.Json; @@ -57,13 +56,13 @@ namespace ASC.Web.Core.Files /// <summary> /// Timeout to request conversion /// </summary> - public static int Timeout = 120000; + public static readonly int Timeout = 120000; //public static int Timeout = Convert.ToInt32(ConfigurationManagerExtension.AppSettings["files.docservice.timeout"] ?? "120000"); /// <summary> /// Number of tries request conversion /// </summary> - public static int MaxTry = 3; + public static readonly int MaxTry = 3; /// <summary> /// Translation key to a supported form. @@ -112,14 +111,15 @@ namespace ASC.Web.Core.Files SpreadsheetLayout spreadsheetLayout, bool isAsync, string signatureSecret, + IHttpClientFactory clientFactory, out string convertedDocumentUri) { fromExtension = string.IsNullOrEmpty(fromExtension) ? Path.GetExtension(documentUri) : fromExtension; - if (string.IsNullOrEmpty(fromExtension)) throw new ArgumentNullException("fromExtension", "Document's extension for conversion is not known"); - if (string.IsNullOrEmpty(toExtension)) throw new ArgumentNullException("toExtension", "Extension for conversion is not known"); + if (string.IsNullOrEmpty(fromExtension)) throw new ArgumentNullException(nameof(fromExtension), "Document's extension for conversion is not known"); + if (string.IsNullOrEmpty(toExtension)) throw new ArgumentNullException(nameof(toExtension), "Extension for conversion is not known"); var title = Path.GetFileName(documentUri ?? ""); - title = string.IsNullOrEmpty(title) || title.Contains("?") ? Guid.NewGuid().ToString() : title; + title = string.IsNullOrEmpty(title) || title.Contains('?') ? Guid.NewGuid().ToString() : title; documentRevisionId = string.IsNullOrEmpty(documentRevisionId) ? documentUri @@ -131,7 +131,7 @@ namespace ASC.Web.Core.Files request.Method = HttpMethod.Post; request.Headers.Accept.Add(MediaTypeWithQualityHeaderValue.Parse("application/json")); - using var httpClient = new HttpClient(); + var httpClient = clientFactory.CreateClient(); httpClient.Timeout = TimeSpan.FromMilliseconds(Timeout); var body = new ConvertionBody @@ -173,12 +173,6 @@ namespace ASC.Web.Core.Files request.Content = new StringContent(bodyString, Encoding.UTF8, "application/json"); - // hack. http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono) - { - ServicePointManager.ServerCertificateValidationCallback += (s, ce, ca, p) => true; - } - string dataResponse; HttpResponseMessage response = null; Stream responseStream = null; @@ -238,13 +232,14 @@ namespace ASC.Web.Core.Files string callbackUrl, string[] users, MetaData meta, - string signatureSecret) + string signatureSecret, + IHttpClientFactory clientFactory) { var request = new HttpRequestMessage(); request.RequestUri = new Uri(documentTrackerUrl); request.Method = HttpMethod.Post; - using var httpClient = new HttpClient(); + var httpClient = clientFactory.CreateClient(); httpClient.Timeout = TimeSpan.FromMilliseconds(Timeout); var body = new CommandBody @@ -280,12 +275,6 @@ namespace ASC.Web.Core.Files request.Content = new StringContent(bodyString, Encoding.UTF8, "application/json"); - // hack. http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono) - { - ServicePointManager.ServerCertificateValidationCallback += (s, ce, ca, p) => true; - } - string dataResponse; using (var response = httpClient.Send(request)) using (var stream = response.Content.ReadAsStream()) @@ -319,10 +308,11 @@ namespace ASC.Web.Core.Files string scriptUrl, bool isAsync, string signatureSecret, + IHttpClientFactory clientFactory, out Dictionary<string, string> urls) { if (string.IsNullOrEmpty(docbuilderUrl)) - throw new ArgumentNullException("docbuilderUrl"); + throw new ArgumentNullException(nameof(docbuilderUrl)); if (string.IsNullOrEmpty(requestKey) && string.IsNullOrEmpty(scriptUrl)) throw new ArgumentException("requestKey or inputScript is empty"); @@ -331,7 +321,7 @@ namespace ASC.Web.Core.Files request.RequestUri = new Uri(docbuilderUrl); request.Method = HttpMethod.Post; - using var httpClient = new HttpClient(); + var httpClient = clientFactory.CreateClient(); httpClient.Timeout = TimeSpan.FromMilliseconds(Timeout); var body = new BuilderBody @@ -364,12 +354,6 @@ namespace ASC.Web.Core.Files request.Content = new StringContent(bodyString, Encoding.UTF8, "application/json"); - // hack. http://ubuntuforums.org/showthread.php?t=1841740 - if (WorkContext.IsMono) - { - ServicePointManager.ServerCertificateValidationCallback += (s, ce, ca, p) => true; - } - string dataResponse = null; using (var response = httpClient.Send(request)) @@ -406,15 +390,15 @@ namespace ASC.Web.Core.Files return responseFromService.Value<string>("key"); } - public static bool HealthcheckRequest(string healthcheckUrl) + public static bool HealthcheckRequest(string healthcheckUrl, IHttpClientFactory clientFactory) { if (string.IsNullOrEmpty(healthcheckUrl)) - throw new ArgumentNullException("healthcheckUrl"); + throw new ArgumentNullException(nameof(healthcheckUrl)); var request = new HttpRequestMessage(); request.RequestUri = new Uri(healthcheckUrl); - using var httpClient = new HttpClient(); + var httpClient = clientFactory.CreateClient(); httpClient.Timeout = TimeSpan.FromMilliseconds(Timeout); using var response = httpClient.Send(request); @@ -726,7 +710,7 @@ namespace ASC.Web.Core.Files [Serializable] public class DocumentServiceException : Exception { - public ErrorCode Code; + public ErrorCode Code { get; set; } public DocumentServiceException(ErrorCode errorCode, string message) : base(message) @@ -804,7 +788,7 @@ namespace ASC.Web.Core.Files /// <returns>The percentage of completion of conversion</returns> private static int GetResponseUri(string jsonDocumentResponse, out string responseUri) { - if (string.IsNullOrEmpty(jsonDocumentResponse)) throw new ArgumentException("Invalid param", "jsonDocumentResponse"); + if (string.IsNullOrEmpty(jsonDocumentResponse)) throw new ArgumentException("Invalid param", nameof(jsonDocumentResponse)); var responseFromService = JObject.Parse(jsonDocumentResponse); if (responseFromService == null) throw new WebException("Invalid answer format"); diff --git a/web/ASC.Web.Core/Files/DocumentServiceLicense.cs b/web/ASC.Web.Core/Files/DocumentServiceLicense.cs index 64b87e0386..cb034a9633 100644 --- a/web/ASC.Web.Core/Files/DocumentServiceLicense.cs +++ b/web/ASC.Web.Core/Files/DocumentServiceLicense.cs @@ -16,6 +16,7 @@ using System; using System.Collections.Generic; +using System.Net.Http; using ASC.Common; using ASC.Common.Caching; @@ -35,17 +36,21 @@ namespace ASC.Web.Core.Files public CoreBaseSettings CoreBaseSettings { get; } private FilesLinkUtility FilesLinkUtility { get; } private FileUtility FileUtility { get; } + private IHttpClientFactory ClientFactory { get; } + public DocumentServiceLicense( ICache cache, CoreBaseSettings coreBaseSettings, FilesLinkUtility filesLinkUtility, - FileUtility fileUtility) + FileUtility fileUtility, + IHttpClientFactory clientFactory) { Cache = cache; CoreBaseSettings = coreBaseSettings; FilesLinkUtility = filesLinkUtility; FileUtility = fileUtility; + ClientFactory = clientFactory; } private CommandResponse GetDocumentServiceLicense() @@ -65,7 +70,9 @@ namespace ASC.Web.Core.Files null, null, null, - FileUtility.SignatureSecret); + FileUtility.SignatureSecret, + ClientFactory + ); Cache.Insert(cacheKey, commandResponse, DateTime.UtcNow.Add(CACHE_EXPIRATION)); } diff --git a/web/ASC.Web.Core/Files/FileUtility.cs b/web/ASC.Web.Core/Files/FileUtility.cs index 0df84a8bb2..00eb7d8691 100644 --- a/web/ASC.Web.Core/Files/FileUtility.cs +++ b/web/ASC.Web.Core/Files/FileUtility.cs @@ -49,20 +49,20 @@ namespace ASC.Web.Core.Files } private List<string> extsIndexing; - public List<string> ExtsIndexing { get => extsIndexing ??= (Configuration.GetSection("files:index").Get<string[]>() ?? new string[] { }).ToList(); } + public List<string> ExtsIndexing { get => extsIndexing ??= Configuration.GetSection("files:index").Get<List<string>>() ?? new List<string>(); } private List<string> extsImagePreviewed; - public List<string> ExtsImagePreviewed { get => extsImagePreviewed ??= (Configuration.GetSection("files:viewed-images").Get<string[]>() ?? new string[] { }).ToList(); } + public List<string> ExtsImagePreviewed { get => extsImagePreviewed ??= Configuration.GetSection("files:viewed-images").Get<List<string>>() ?? new List<string>(); } private List<string> extsMediaPreviewed; - public List<string> ExtsMediaPreviewed { get => extsMediaPreviewed ??= (Configuration.GetSection("files:viewed-media").Get<string[]>() ?? new string[] { }).ToList(); } + public List<string> ExtsMediaPreviewed { get => extsMediaPreviewed ??= Configuration.GetSection("files:viewed-media").Get<List<string>>() ?? new List<string>(); } private List<string> extsWebPreviewed; public List<string> ExtsWebPreviewed { get { - return extsWebPreviewed ??= (Configuration.GetSection("files:docservice:viewed-docs").Get<string[]>() ?? new string[] { }).ToList(); + return extsWebPreviewed ??= Configuration.GetSection("files:docservice:viewed-docs").Get<List<string>>() ?? new List<string>(); } } @@ -71,19 +71,19 @@ namespace ASC.Web.Core.Files { get { - return extsWebEdited ??= (Configuration.GetSection("files:docservice:edited-docs").Get<string[]>() ?? new string[] { }).ToList(); + return extsWebEdited ??= Configuration.GetSection("files:docservice:edited-docs").Get<List<string>>() ?? new List<string>(); } } private List<string> extsWebEncrypt; - public List<string> ExtsWebEncrypt { get => extsWebEncrypt ??= (Configuration.GetSection("files:docservice:encrypted-docs").Get<string[]>() ?? new string[] { }).ToList(); } + public List<string> ExtsWebEncrypt { get => extsWebEncrypt ??= Configuration.GetSection("files:docservice:encrypted-docs").Get<List<string>>() ?? new List<string>(); } private List<string> extsWebReviewed; public List<string> ExtsWebReviewed { get { - return extsWebReviewed ??= (Configuration.GetSection("files:docservice:reviewed-docs").Get<string[]>() ?? new string[] { }).ToList(); + return extsWebReviewed ??= Configuration.GetSection("files:docservice:reviewed-docs").Get<List<string>>() ?? new List<string>(); } } @@ -92,7 +92,7 @@ namespace ASC.Web.Core.Files { get { - return extsWebCustomFilterEditing ??= (Configuration.GetSection("files:docservice:customfilter-docs").Get<string[]>() ?? new string[] { }).ToList(); + return extsWebCustomFilterEditing ??= Configuration.GetSection("files:docservice:customfilter-docs").Get<List<string>>() ?? new List<string>(); } } @@ -101,7 +101,7 @@ namespace ASC.Web.Core.Files { get { - return extsWebRestrictedEditing ??= (Configuration.GetSection("files:docservice:formfilling-docs").Get<string[]>() ?? new string[] { }).ToList(); + return extsWebRestrictedEditing ??= Configuration.GetSection("files:docservice:formfilling-docs").Get<List<string>>() ?? new List<string>(); } } @@ -110,7 +110,7 @@ namespace ASC.Web.Core.Files { get { - return extsWebCommented ??= (Configuration.GetSection("files:docservice:commented-docs").Get<string[]>() ?? new string[] { }).ToList(); + return extsWebCommented ??= Configuration.GetSection("files:docservice:commented-docs").Get<List<string>>() ?? new List<string>(); } } @@ -119,7 +119,7 @@ namespace ASC.Web.Core.Files { get { - return extsWebTemplate ??= (Configuration.GetSection("files:docservice:template-docs").Get<string[]>() ?? new string[] { }).ToList(); + return extsWebTemplate ??= Configuration.GetSection("files:docservice:template-docs").Get<List<string>>() ?? new List<string>(); } } @@ -128,14 +128,14 @@ namespace ASC.Web.Core.Files { get { - return extsMustConvert ??= (Configuration.GetSection("files:docservice:convert-docs").Get<string[]>() ?? new string[] { }).ToList(); + return extsMustConvert ??= Configuration.GetSection("files:docservice:convert-docs").Get<List<string>>() ?? new List<string>(); } } private List<string> extsCoAuthoring; public List<string> ExtsCoAuthoring { - get => extsCoAuthoring ??= (Configuration.GetSection("files:docservice:coauthor-docs").Get<string[]>() ?? new string[] { }).ToList(); + get => extsCoAuthoring ??= Configuration.GetSection("files:docservice:coauthor-docs").Get<List<string>>() ?? new List<string>(); } private string masterFormExtension; @@ -336,19 +336,18 @@ namespace ASC.Web.Core.Files var dbManager = FilesDbContext; var list = dbManager.FilesConverts.Select(r => new { r.Input, r.Output }).ToList(); - - list.ForEach(item => - { - var input = item.Input; - var output = item.Output; - if (string.IsNullOrEmpty(input) || string.IsNullOrEmpty(output)) - return; - input = input.ToLower().Trim(); - output = output.ToLower().Trim(); - if (!_extsConvertible.ContainsKey(input)) - _extsConvertible[input] = new List<string>(); - _extsConvertible[input].Add(output); - }); + foreach (var item in list) + { + var input = item.Input; + var output = item.Output; + if (string.IsNullOrEmpty(input) || string.IsNullOrEmpty(output)) + continue; + input = input.ToLower().Trim(); + output = output.ToLower().Trim(); + if (!_extsConvertible.ContainsKey(input)) + _extsConvertible[input] = new List<string>(); + _extsConvertible[input].Add(output); + } } return _extsConvertible; } diff --git a/web/ASC.Web.Core/Helpers/ApiSystemHelper.cs b/web/ASC.Web.Core/Helpers/ApiSystemHelper.cs index ebb370dea2..55678c7b92 100644 --- a/web/ASC.Web.Core/Helpers/ApiSystemHelper.cs +++ b/web/ASC.Web.Core/Helpers/ApiSystemHelper.cs @@ -51,18 +51,21 @@ namespace ASC.Web.Core.Helpers public class ApiSystemHelper { public string ApiSystemUrl { get; private set; } - public string ApiCacheUrl { get; private set; } - private static byte[] Skey { get; set; } - private CommonLinkUtility CommonLinkUtility { get; } + private CommonLinkUtility CommonLinkUtility { get; } + private IHttpClientFactory ClientFactory { get; } - public ApiSystemHelper(IConfiguration configuration, CommonLinkUtility commonLinkUtility, MachinePseudoKeys machinePseudoKeys) + public ApiSystemHelper(IConfiguration configuration, + CommonLinkUtility commonLinkUtility, + MachinePseudoKeys machinePseudoKeys, + IHttpClientFactory clientFactory) { ApiSystemUrl = configuration["web:api-system"]; ApiCacheUrl = configuration["web:api-cache"]; CommonLinkUtility = commonLinkUtility; - Skey = machinePseudoKeys.GetMachineConstant(); + Skey = machinePseudoKeys.GetMachineConstant(); + ClientFactory = clientFactory; } @@ -71,7 +74,7 @@ namespace ASC.Web.Core.Helpers using var hasher = new HMACSHA1(Skey); var now = DateTime.UtcNow.ToString("yyyyMMddHHmmss"); var hash = WebEncoders.Base64UrlEncode(hasher.ComputeHash(Encoding.UTF8.GetBytes(string.Join("\n", now, pkey)))); - return string.Format("ASC {0}:{1}:{2}", pkey, now, hash); + return $"ASC {pkey}:{now}:{hash}"; } #region system @@ -80,7 +83,7 @@ namespace ASC.Web.Core.Helpers { try { - var data = string.Format("portalName={0}", HttpUtility.UrlEncode(domain)); + var data = $"portalName={HttpUtility.UrlEncode(domain)}"; SendToApi(ApiSystemUrl, "portal/validateportalname", WebRequestMethods.Http.Post, userId, data); } catch (WebException exception) @@ -122,7 +125,7 @@ namespace ASC.Web.Core.Helpers public void AddTenantToCache(string domain, Guid userId) { - var data = string.Format("portalName={0}", HttpUtility.UrlEncode(domain)); + var data = $"portalName={HttpUtility.UrlEncode(domain)}"; SendToApi(ApiCacheUrl, "portal/add", WebRequestMethods.Http.Post, userId, data); } @@ -147,10 +150,10 @@ namespace ASC.Web.Core.Helpers if (!Uri.TryCreate(absoluteApiUrl, UriKind.Absolute, out var uri)) { var appUrl = CommonLinkUtility.GetFullAbsolutePath("/"); - absoluteApiUrl = string.Format("{0}/{1}", appUrl.TrimEnd('/'), absoluteApiUrl.TrimStart('/')).TrimEnd('/'); + absoluteApiUrl = $"{appUrl.TrimEnd('/')}/{absoluteApiUrl.TrimStart('/')}".TrimEnd('/'); } - var url = string.Format("{0}/{1}", absoluteApiUrl, apiPath); + var url = $"{absoluteApiUrl}/{apiPath}"; var request = new HttpRequestMessage(); request.RequestUri = new Uri(url); @@ -163,7 +166,7 @@ namespace ASC.Web.Core.Helpers request.Content = new StringContent(data, Encoding.UTF8, "application/x-www-form-urlencoded"); } - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using var stream = response.Content.ReadAsStream(); using var reader = new StreamReader(stream, Encoding.UTF8); diff --git a/web/ASC.Web.Core/Helpers/GrammaticalHelper.cs b/web/ASC.Web.Core/Helpers/GrammaticalHelper.cs index 5a590261b0..a574a8b5dc 100644 --- a/web/ASC.Web.Core/Helpers/GrammaticalHelper.cs +++ b/web/ASC.Web.Core/Helpers/GrammaticalHelper.cs @@ -28,19 +28,17 @@ using System; namespace ASC.Web.Core.Helpers { - public class GrammaticalHelper + public static class GrammaticalHelper { public static string ChooseNumeralCase(int number, string nominative, string genitiveSingular, string genitivePlural) { if ( - string.Compare( - System.Threading.Thread.CurrentThread.CurrentUICulture.ThreeLetterISOLanguageName, - "rus", true) == 0) + System.Threading.Thread.CurrentThread.CurrentUICulture.ThreeLetterISOLanguageName.Equals("rus", StringComparison.InvariantCultureIgnoreCase)) { int[] formsTable = { 2, 0, 1, 1, 1, 2, 2, 2, 2, 2 }; number = Math.Abs(number); - var res = formsTable[((((number % 100) / 10) != 1) ? 1 : 0) * (number % 10)]; + var res = formsTable[(((number % 100 / 10) != 1) ? 1 : 0) * (number % 10)]; return res switch { 0 => nominative, diff --git a/web/ASC.Web.Core/Helpers/ResourceEnumConverter.cs b/web/ASC.Web.Core/Helpers/ResourceEnumConverter.cs index 13378990f9..8a87666a1b 100644 --- a/web/ASC.Web.Core/Helpers/ResourceEnumConverter.cs +++ b/web/ASC.Web.Core/Helpers/ResourceEnumConverter.cs @@ -88,7 +88,7 @@ namespace ASC.Web.Core.Helpers private string GetValueText(CultureInfo culture, object value) { var type = value.GetType(); - var resourceName = string.Format("{0}_{1}", type.Name, value.ToString()); + var resourceName = $"{type.Name}_{value}"; var result = _resourceManager.GetString(resourceName, culture); if (result == null) result = resourceName; @@ -106,7 +106,7 @@ namespace ASC.Web.Core.Helpers { 0 => false, 1 => true, - _ => ((value & (value - 1)) == 0), + _ => (value & (value - 1)) == 0, }; } @@ -144,7 +144,7 @@ namespace ASC.Web.Core.Helpers } else { - result = string.Format("{0}, {1}", result, valueText); + result = $"{result}, {valueText}"; } } } @@ -216,7 +216,7 @@ namespace ASC.Web.Core.Helpers { if (value is string @string) { - var result = (_isFlagEnum) ? + var result = _isFlagEnum ? GetFlagValue(culture, @string) : GetValue(culture, @string); if (result == null) { @@ -242,7 +242,7 @@ namespace ASC.Web.Core.Helpers { if (value != null && destinationType == typeof(string)) { - object result = (_isFlagEnum) ? + object result = _isFlagEnum ? GetFlagValueText(culture, value) : GetValueText(culture, value); return result; } diff --git a/web/ASC.Web.Core/Mobile/CachedMobileAppInstallRegistrator.cs b/web/ASC.Web.Core/Mobile/CachedMobileAppInstallRegistrator.cs index 64bebf52ec..db8693d74c 100644 --- a/web/ASC.Web.Core/Mobile/CachedMobileAppInstallRegistrator.cs +++ b/web/ASC.Web.Core/Mobile/CachedMobileAppInstallRegistrator.cs @@ -49,7 +49,7 @@ namespace ASC.Web.Core.Mobile { Cache = cache; TenantManager = tenantManager; - this.registrator = registrator ?? throw new ArgumentNullException("registrator"); + this.registrator = registrator ?? throw new ArgumentNullException(nameof(registrator)); this.cacheExpiration = cacheExpiration; } diff --git a/web/ASC.Web.Core/Mobile/MobileAppInstallRegistrator.cs b/web/ASC.Web.Core/Mobile/MobileAppInstallRegistrator.cs index 6de24e1302..ee47b36b5c 100644 --- a/web/ASC.Web.Core/Mobile/MobileAppInstallRegistrator.cs +++ b/web/ASC.Web.Core/Mobile/MobileAppInstallRegistrator.cs @@ -69,7 +69,7 @@ namespace ASC.Web.Core.Mobile q = q.Where(r => r.AppType == (int)appType.Value); } - return q.Count() > 0; + return q.Any(); } } } \ No newline at end of file diff --git a/web/ASC.Web.Core/Mobile/MobileDetector.cs b/web/ASC.Web.Core/Mobile/MobileDetector.cs index 1d289aa8be..e06196ee79 100644 --- a/web/ASC.Web.Core/Mobile/MobileDetector.cs +++ b/web/ASC.Web.Core/Mobile/MobileDetector.cs @@ -78,7 +78,8 @@ namespace ASC.Web.Core.Mobile } else { - cache.Insert(key, (result = regex.IsMatch(ua)).ToString(), TimeSpan.FromMinutes(10)); + result = regex.IsMatch(ua); + cache.Insert(key, result.ToString(), TimeSpan.FromMinutes(10)); } } return result.GetValueOrDefault(); diff --git a/web/ASC.Web.Core/Notify/NotifyConfiguration.cs b/web/ASC.Web.Core/Notify/NotifyConfiguration.cs index 0cd3f54935..2a381adb07 100644 --- a/web/ASC.Web.Core/Notify/NotifyConfiguration.cs +++ b/web/ASC.Web.Core/Notify/NotifyConfiguration.cs @@ -88,7 +88,7 @@ namespace ASC.Web.Studio.Core.Notify } } - private static void NotifyClientRegisterCallback(Context context, INotifyClient client) + private void NotifyClientRegisterCallback(Context context, INotifyClient client) { #region url correction @@ -236,7 +236,7 @@ namespace ASC.Web.Studio.Core.Notify if (!string.IsNullOrEmpty(logoText)) { r.CurrentMessage.Body = r.CurrentMessage.Body - .Replace(string.Format("${{{0}}}", CommonTags.LetterLogoText), logoText); + .Replace("${{"+ CommonTags.LetterLogoText + "}}", logoText); } } catch (Exception error) @@ -250,7 +250,7 @@ namespace ASC.Web.Studio.Core.Notify #endregion } - private static void BeforeTransferRequest(NotifyEngine sender, NotifyRequest request, IServiceScope scope) + private void BeforeTransferRequest(NotifyEngine sender, NotifyRequest request, IServiceScope scope) { var aid = Guid.Empty; var aname = string.Empty; @@ -455,7 +455,7 @@ namespace ASC.Web.Studio.Core.Notify } } - public class NotifyConfigurationExtension + public static class NotifyConfigurationExtension { public static void Register(DIHelper services) { diff --git a/web/ASC.Web.Core/Notify/StudioNotifyHelper.cs b/web/ASC.Web.Core/Notify/StudioNotifyHelper.cs index 0a438cd3a4..c163ee188e 100644 --- a/web/ASC.Web.Core/Notify/StudioNotifyHelper.cs +++ b/web/ASC.Web.Core/Notify/StudioNotifyHelper.cs @@ -170,7 +170,7 @@ namespace ASC.Web.Studio.Core.Notify var sended = spamEmailSettings.MailsSended; var mayTake = Math.Max(0, CountMailsToNotActivated - sended); - var tryCount = res.Count(); + var tryCount = res.Count; if (mayTake < tryCount) { res = res.Take(mayTake).ToList(); diff --git a/web/ASC.Web.Core/Notify/StudioNotifyService.cs b/web/ASC.Web.Core/Notify/StudioNotifyService.cs index b95dc80352..d2fe3b90d0 100644 --- a/web/ASC.Web.Core/Notify/StudioNotifyService.cs +++ b/web/ASC.Web.Core/Notify/StudioNotifyService.cs @@ -125,26 +125,26 @@ namespace ASC.Web.Studio.Core.Notify public void SendRequestTariff(bool license, string fname, string lname, string title, string email, string phone, string ctitle, string csize, string site, string message) { fname = (fname ?? "").Trim(); - if (string.IsNullOrEmpty(fname)) throw new ArgumentNullException("fname"); + if (string.IsNullOrEmpty(fname)) throw new ArgumentNullException(nameof(fname)); lname = (lname ?? "").Trim(); - if (string.IsNullOrEmpty(lname)) throw new ArgumentNullException("lname"); + if (string.IsNullOrEmpty(lname)) throw new ArgumentNullException(nameof(lname)); title = (title ?? "").Trim(); email = (email ?? "").Trim(); - if (string.IsNullOrEmpty(email)) throw new ArgumentNullException("email"); + if (string.IsNullOrEmpty(email)) throw new ArgumentNullException(nameof(email)); phone = (phone ?? "").Trim(); - if (string.IsNullOrEmpty(phone)) throw new ArgumentNullException("phone"); + if (string.IsNullOrEmpty(phone)) throw new ArgumentNullException(nameof(phone)); ctitle = (ctitle ?? "").Trim(); - if (string.IsNullOrEmpty(ctitle)) throw new ArgumentNullException("ctitle"); + if (string.IsNullOrEmpty(ctitle)) throw new ArgumentNullException(nameof(ctitle)); csize = (csize ?? "").Trim(); - if (string.IsNullOrEmpty(csize)) throw new ArgumentNullException("csize"); + if (string.IsNullOrEmpty(csize)) throw new ArgumentNullException(nameof(csize)); site = (site ?? "").Trim(); - if (string.IsNullOrEmpty(site) && !CoreBaseSettings.CustomMode) throw new ArgumentNullException("site"); + if (string.IsNullOrEmpty(site) && !CoreBaseSettings.CustomMode) throw new ArgumentNullException(nameof(site)); message = (message ?? "").Trim(); - if (string.IsNullOrEmpty(message) && !CoreBaseSettings.CustomMode) throw new ArgumentNullException("message"); + if (string.IsNullOrEmpty(message) && !CoreBaseSettings.CustomMode) throw new ArgumentNullException(nameof(message)); var salesEmail = SettingsManager.LoadForDefaultTenant<AdditionalWhiteLabelSettings>().SalesEmail ?? SetupInfo.SalesEmail; - var recipient = (IRecipient)(new DirectRecipient(AuthContext.CurrentAccount.ID.ToString(), string.Empty, new[] { salesEmail }, false)); + var recipient = (IRecipient)new DirectRecipient(AuthContext.CurrentAccount.ID.ToString(), string.Empty, new[] { salesEmail }, false); client.SendNoticeToAsync(license ? Actions.RequestLicense : Actions.RequestTariff, new[] { recipient }, @@ -181,7 +181,7 @@ namespace ASC.Web.Studio.Core.Notify var hash = Authentication.GetUserPasswordStamp(userInfo.ID).ToString("s"); var confirmationUrl = CommonLinkUtility.GetConfirmationUrl(userInfo.Email, ConfirmType.PasswordChange, hash, userInfo.ID); - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonChangePassword; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonChangePassword; var action = CoreBaseSettings.Personal ? (CoreBaseSettings.CustomMode ? Actions.PersonalCustomModePasswordChange : Actions.PersonalPasswordChange) @@ -202,7 +202,7 @@ namespace ASC.Web.Studio.Core.Notify { var confirmationUrl = CommonLinkUtility.GetConfirmationUrl(email, ConfirmType.EmailChange, AuthContext.CurrentAccount.ID); - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonChangeEmail; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonChangeEmail; var action = CoreBaseSettings.Personal ? (CoreBaseSettings.CustomMode ? Actions.PersonalCustomModeEmailChangeV115 : Actions.PersonalEmailChangeV115) @@ -220,7 +220,7 @@ namespace ASC.Web.Studio.Core.Notify { var confirmationUrl = CommonLinkUtility.GetConfirmationUrl(email, ConfirmType.EmailActivation, null, user.ID); - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonActivateEmail; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonActivateEmail; client.SendNoticeToAsync( Actions.ActivateEmail, @@ -251,8 +251,7 @@ namespace ASC.Web.Studio.Core.Notify if (!skipSettings) { - var link = string.Format("{0}/addons/mail/#accounts/changepwd={1}", - CommonLinkUtility.GetFullAbsolutePath("~").TrimEnd('/'), address); + var link = $"{CommonLinkUtility.GetFullAbsolutePath("~").TrimEnd('/')}/addons/mail/#accounts/changepwd={address}"; tags.Add(new TagValue(Tags.MyStaffLink, link)); tags.Add(new TagValue(Tags.Server, server)); @@ -288,7 +287,7 @@ namespace ASC.Web.Studio.Core.Notify { var confirmationUrl = CommonLinkUtility.GetConfirmationUrl(userInfo.Email.ToLower(), ConfirmType.PhoneActivation); - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonChangePhone; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonChangePhone; client.SendNoticeToAsync( Actions.PhoneChange, @@ -301,7 +300,7 @@ namespace ASC.Web.Studio.Core.Notify { var confirmationUrl = CommonLinkUtility.GetConfirmationUrl(userInfo.Email.ToLower(), ConfirmType.TfaActivation); - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonChangeTfa; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonChangeTfa; client.SendNoticeToAsync( Actions.TfaChange, @@ -324,7 +323,7 @@ namespace ASC.Web.Studio.Core.Notify var inviteUrl = CommonLinkUtility.GetConfirmationUrl(email, ConfirmType.EmpInvite, (int)emplType) + string.Format("&emplType={0}", (int)emplType); - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonJoin; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonJoin; client.SendNoticeToAsync( Actions.JoinUsers, @@ -452,7 +451,7 @@ namespace ASC.Web.Studio.Core.Notify var confirmationUrl = GenerateActivationConfirmUrl(newUserInfo); - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonAccept; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonAccept; client.SendNoticeToAsync( notifyAction, @@ -490,7 +489,7 @@ namespace ASC.Web.Studio.Core.Notify var confirmationUrl = GenerateActivationConfirmUrl(newUserInfo); - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonAccept; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonAccept; client.SendNoticeToAsync( notifyAction, @@ -655,7 +654,7 @@ namespace ASC.Web.Studio.Core.Notify { var u = UserManager.GetUsers(t.OwnerId); - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonDeactivatePortal; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonDeactivatePortal; client.SendNoticeToAsync( Actions.PortalDeactivate, @@ -670,7 +669,7 @@ namespace ASC.Web.Studio.Core.Notify { var u = UserManager.GetUsers(t.OwnerId); - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonDeletePortal; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonDeletePortal; client.SendNoticeToAsync( Actions.PortalDelete, @@ -683,7 +682,7 @@ namespace ASC.Web.Studio.Core.Notify public void SendMsgPortalDeletionSuccess(UserInfo owner, string url) { - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonLeaveFeedback; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonLeaveFeedback; client.SendNoticeToAsync( Actions.PortalDeleteSuccessV115, @@ -699,7 +698,7 @@ namespace ASC.Web.Studio.Core.Notify { var u = UserManager.GetUsers(t.OwnerId); - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonConfirmPortalAddressChange; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonConfirmPortalAddressChange; client.SendNoticeToAsync( Actions.DnsChange, @@ -714,7 +713,7 @@ namespace ASC.Web.Studio.Core.Notify public void SendMsgConfirmChangeOwner(UserInfo owner, UserInfo newOwner, string confirmOwnerUpdateUrl) { - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonConfirmPortalOwnerUpdate; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonConfirmPortalOwnerUpdate; client.SendNoticeToAsync( Actions.ConfirmOwnerChange, @@ -752,7 +751,7 @@ namespace ASC.Web.Studio.Core.Notify var confirmationUrl = CommonLinkUtility.GetConfirmationUrl(u.Email, ConfirmType.EmailActivation); confirmationUrl += "&first=true"; - static string greenButtonText() => WebstudioNotifyPatternResource.ButtonConfirm; + string greenButtonText() => WebstudioNotifyPatternResource.ButtonConfirm; client.SendNoticeToAsync( notifyAction, diff --git a/web/ASC.Web.Core/Notify/StudioNotifyServiceSender.cs b/web/ASC.Web.Core/Notify/StudioNotifyServiceSender.cs index 061291e4d8..09d5fa5b36 100644 --- a/web/ASC.Web.Core/Notify/StudioNotifyServiceSender.cs +++ b/web/ASC.Web.Core/Notify/StudioNotifyServiceSender.cs @@ -101,7 +101,7 @@ namespace ASC.Web.Studio.Core.Notify (NotifyAction)item.Action, item.ObjectId, item.Recipients?.Select(r => r.IsGroup ? new RecipientsGroup(r.Id, r.Name) : (IRecipient)new DirectRecipient(r.Id, r.Name, r.Addresses.ToArray(), r.CheckActivation)).ToArray(), - item.SenderNames.Any() ? item.SenderNames.ToArray() : null, + item.SenderNames.Count > 0 ? item.SenderNames.ToArray() : null, item.CheckSubsciption, item.Tags.Select(r => new TagValue(r.Tag_, r.Value)).ToArray()); } diff --git a/web/ASC.Web.Core/Notify/StudioPeriodicNotify.cs b/web/ASC.Web.Core/Notify/StudioPeriodicNotify.cs index 1963ea9430..c1f626a331 100644 --- a/web/ASC.Web.Core/Notify/StudioPeriodicNotify.cs +++ b/web/ASC.Web.Core/Notify/StudioPeriodicNotify.cs @@ -72,8 +72,7 @@ namespace ASC.Web.Studio.Core.Notify Log.Info("Start SendSaasTariffLetters"); - var activeTenants = new List<Tenant>(); - var monthQuotasIds = new List<int>(); + List<Tenant> activeTenants; using (var scope = ServiceProvider.CreateScope()) { @@ -119,7 +118,7 @@ namespace ASC.Web.Studio.Core.Notify Func<string> greenButtonText = () => string.Empty; - static string blueButtonText() => WebstudioNotifyPatternResource.ButtonRequestCallButton; + string blueButtonText() => WebstudioNotifyPatternResource.ButtonRequestCallButton; var greenButtonUrl = string.Empty; Func<string> tableItemText1 = () => string.Empty; @@ -156,17 +155,17 @@ namespace ASC.Web.Studio.Core.Notify Func<string> tableItemLearnMoreText1 = () => string.Empty; - static string tableItemLearnMoreText2() => string.Empty; + string tableItemLearnMoreText2() => string.Empty; - static string tableItemLearnMoreText3() => string.Empty; + string tableItemLearnMoreText3() => string.Empty; - static string tableItemLearnMoreText4() => string.Empty; + string tableItemLearnMoreText4() => string.Empty; - static string tableItemLearnMoreText5() => string.Empty; + string tableItemLearnMoreText5() => string.Empty; - static string tableItemLearnMoreText6() => string.Empty; + string tableItemLearnMoreText6() => string.Empty; - static string tableItemLearnMoreText7() => string.Empty; + string tableItemLearnMoreText7() => string.Empty; var tableItemLearnMoreUrl1 = string.Empty; var tableItemLearnMoreUrl2 = string.Empty; @@ -205,7 +204,7 @@ namespace ASC.Web.Studio.Core.Notify toadmins = true; greenButtonText = () => WebstudioNotifyPatternResource.ButtonAccessYouWebOffice; - greenButtonUrl = String.Format("{0}/", commonLinkUtility.GetFullAbsolutePath("~").TrimEnd('/')); + greenButtonUrl = $"{commonLinkUtility.GetFullAbsolutePath("~").TrimEnd('/')}/"; } #endregion @@ -268,7 +267,7 @@ namespace ASC.Web.Studio.Core.Notify tableItemComment7 = () => WebstudioNotifyPatternResource.pattern_saas_admin_user_docs_tips_v115_item_differences; greenButtonText = () => WebstudioNotifyPatternResource.ButtonAccessYouWebOffice; - greenButtonUrl = string.Format("{0}/products/files/", commonLinkUtility.GetFullAbsolutePath("~").TrimEnd('/')); + greenButtonUrl = $"{commonLinkUtility.GetFullAbsolutePath("~").TrimEnd('/')}/products/files/"; } #endregion @@ -437,7 +436,7 @@ namespace ASC.Web.Studio.Core.Notify new[] { senderName }, new TagValue(Tags.UserName, u.FirstName.HtmlEncode()), new TagValue(Tags.PricingPage, commonLinkUtility.GetFullAbsolutePath("~/tariffs.aspx")), - new TagValue(Tags.ActiveUsers, userManager.GetUsers().Count()), + new TagValue(Tags.ActiveUsers, userManager.GetUsers().Length), new TagValue(Tags.Price, rquota.Price), new TagValue(Tags.PricePeriod, rquota.Year3 ? UserControlsCommonResource.TariffPerYear3 : rquota.Year ? UserControlsCommonResource.TariffPerYear : UserControlsCommonResource.TariffPerMonth), new TagValue(Tags.DueDate, dueDate.ToLongDateString()), @@ -473,7 +472,7 @@ namespace ASC.Web.Studio.Core.Notify Log.Info("Start SendTariffEnterpriseLetters"); - var activeTenants = new List<Tenant>(); + List<Tenant> activeTenants; using (var scope = ServiceProvider.CreateScope()) { @@ -503,7 +502,7 @@ namespace ASC.Web.Studio.Core.Notify var quota = tenantManager.GetTenantQuota(tenant.TenantId); var createdDate = tenant.CreatedDateTime.Date; - var actualEndDate = (tariff.DueDate != DateTime.MaxValue ? tariff.DueDate : tariff.LicenseDate); + var actualEndDate = tariff.DueDate != DateTime.MaxValue ? tariff.DueDate : tariff.LicenseDate; var dueDateIsNotMax = actualEndDate != DateTime.MaxValue; var dueDate = actualEndDate.Date; @@ -518,7 +517,7 @@ namespace ASC.Web.Studio.Core.Notify Func<string> greenButtonText = () => string.Empty; - static string blueButtonText() => WebstudioNotifyPatternResource.ButtonRequestCallButton; + string blueButtonText() => WebstudioNotifyPatternResource.ButtonRequestCallButton; var greenButtonUrl = string.Empty; Func<string> tableItemText1 = () => string.Empty; @@ -555,17 +554,17 @@ namespace ASC.Web.Studio.Core.Notify Func<string> tableItemLearnMoreText1 = () => string.Empty; - static string tableItemLearnMoreText2() => string.Empty; + string tableItemLearnMoreText2() => string.Empty; - static string tableItemLearnMoreText3() => string.Empty; + string tableItemLearnMoreText3() => string.Empty; - static string tableItemLearnMoreText4() => string.Empty; + string tableItemLearnMoreText4() => string.Empty; - static string tableItemLearnMoreText5() => string.Empty; + string tableItemLearnMoreText5() => string.Empty; - static string tableItemLearnMoreText6() => string.Empty; + string tableItemLearnMoreText6() => string.Empty; - static string tableItemLearnMoreText7() => string.Empty; + string tableItemLearnMoreText7() => string.Empty; var tableItemLearnMoreUrl1 = string.Empty; var tableItemLearnMoreUrl2 = string.Empty; @@ -616,14 +615,14 @@ namespace ASC.Web.Studio.Core.Notify #region 4 days after registration to admins ENTERPRISE TRIAL + only 1 user + defaultRebranding - else if (createdDate.AddDays(4) == nowDate && userManager.GetUsers().Count() == 1) + else if (createdDate.AddDays(4) == nowDate && userManager.GetUsers().Length == 1) { action = Actions.EnterpriseAdminInviteTeammatesV10; paymentMessage = false; toadmins = true; greenButtonText = () => WebstudioNotifyPatternResource.ButtonInviteRightNow; - greenButtonUrl = string.Format("{0}/products/people/", commonLinkUtility.GetFullAbsolutePath("~").TrimEnd('/')); + greenButtonUrl = $"{commonLinkUtility.GetFullAbsolutePath("~").TrimEnd('/')}/products/people/"; } #endregion @@ -696,7 +695,7 @@ namespace ASC.Web.Studio.Core.Notify tableItemComment7 = () => WebstudioNotifyPatternResource.pattern_saas_admin_user_docs_tips_v115_item_apps; greenButtonText = () => WebstudioNotifyPatternResource.ButtonAccessYouWebOffice; - greenButtonUrl = string.Format("{0}/products/files/", commonLinkUtility.GetFullAbsolutePath("~").TrimEnd('/')); + greenButtonUrl = $"{commonLinkUtility.GetFullAbsolutePath("~").TrimEnd('/')}/products/files/"; } #endregion @@ -839,7 +838,7 @@ namespace ASC.Web.Studio.Core.Notify new[] { senderName }, new TagValue(Tags.UserName, u.FirstName.HtmlEncode()), new TagValue(Tags.PricingPage, commonLinkUtility.GetFullAbsolutePath("~/tariffs.aspx")), - new TagValue(Tags.ActiveUsers, userManager.GetUsers().Count()), + new TagValue(Tags.ActiveUsers, userManager.GetUsers().Length), new TagValue(Tags.Price, rquota.Price), new TagValue(Tags.PricePeriod, rquota.Year3 ? UserControlsCommonResource.TariffPerYear3 : rquota.Year ? UserControlsCommonResource.TariffPerYear : UserControlsCommonResource.TariffPerMonth), new TagValue(Tags.DueDate, dueDate.ToLongDateString()), @@ -872,7 +871,7 @@ namespace ASC.Web.Studio.Core.Notify Log.Info("Start SendOpensourceTariffLetters"); - var activeTenants = new List<Tenant>(); + List<Tenant> activeTenants; using (var scope = ServiceProvider.CreateScope()) { @@ -941,7 +940,7 @@ namespace ASC.Web.Studio.Core.Notify Log.Info("Start SendLettersPersonal..."); - var activeTenants = new List<Tenant>(); + List<Tenant> activeTenants; using (var scope = ServiceProvider.CreateScope()) { @@ -1167,7 +1166,7 @@ namespace ASC.Web.Studio.Core.Notify } } - public class StudioPeriodicNotifyExtension + public static class StudioPeriodicNotifyExtension { public static void Register(DIHelper services) { diff --git a/web/ASC.Web.Core/Notify/StudioWhatsNewNotify.cs b/web/ASC.Web.Core/Notify/StudioWhatsNewNotify.cs index 7ee1f26c4d..bee1e9770d 100644 --- a/web/ASC.Web.Core/Notify/StudioWhatsNewNotify.cs +++ b/web/ASC.Web.Core/Notify/StudioWhatsNewNotify.cs @@ -142,7 +142,7 @@ namespace ASC.Web.Studio.Core.Notify UserAbsoluteURL = f.Author != null && f.Author.UserInfo != null ? commonLinkUtility.GetFullAbsolutePath(f.Author.UserInfo.GetUserProfilePageURL(commonLinkUtility)) : string.Empty, Title = HtmlUtil.GetText(f.Title, 512), URL = commonLinkUtility.GetFullAbsolutePath(f.ItemUrl), - BreadCrumbs = new string[0], + BreadCrumbs = Array.Empty<string>(), Action = GetWhatsNewActionText(f) }).ToList()); @@ -165,7 +165,7 @@ namespace ASC.Web.Studio.Core.Notify UserAbsoluteURL = prawbc.Author != null && prawbc.Author.UserInfo != null ? commonLinkUtility.GetFullAbsolutePath(prawbc.Author.UserInfo.GetUserProfilePageURL(commonLinkUtility)) : string.Empty, Title = HtmlUtil.GetText(prawbc.Title, 512), URL = commonLinkUtility.GetFullAbsolutePath(prawbc.ItemUrl), - BreadCrumbs = new string[0], + BreadCrumbs = Array.Empty<string>(), Action = GetWhatsNewActionText(prawbc) }); } @@ -174,7 +174,7 @@ namespace ASC.Web.Studio.Core.Notify foreach (var gr in groupByPrjs) { var grlist = gr.ToList(); - for (var i = 0; i < grlist.Count(); i++) + for (var i = 0; i < grlist.Count; i++) { var ls = grlist[i]; whatsNewUserActivityGroupByPrjs.Add( @@ -185,7 +185,7 @@ namespace ASC.Web.Studio.Core.Notify UserAbsoluteURL = ls.Author != null && ls.Author.UserInfo != null ? commonLinkUtility.GetFullAbsolutePath(ls.Author.UserInfo.GetUserProfilePageURL(commonLinkUtility)) : string.Empty, Title = HtmlUtil.GetText(ls.Title, 512), URL = commonLinkUtility.GetFullAbsolutePath(ls.ItemUrl), - BreadCrumbs = i == 0 ? new string[1] { gr.Key } : new string[0], + BreadCrumbs = i == 0 ? new string[1] { gr.Key } : Array.Empty<string>(), Action = GetWhatsNewActionText(ls) }); } diff --git a/web/ASC.Web.Core/Notify/TagValues.cs b/web/ASC.Web.Core/Notify/TagValues.cs index d37196f810..3082af2943 100644 --- a/web/ASC.Web.Core/Notify/TagValues.cs +++ b/web/ASC.Web.Core/Notify/TagValues.cs @@ -53,14 +53,10 @@ namespace ASC.Web.Studio.Core.Notify string action() { var btnText = btnTextFunc != null ? btnTextFunc() ?? string.Empty : string.Empty; - - return - string.Format( - @"<table style=""height: 48px; width: 540px; border-collapse: collapse; empty-cells: show; vertical-align: middle; text-align: center; margin: 30px auto; padding: 0;""><tbody><tr cellpadding=""0"" cellspacing=""0"" border=""0"">{2}<td style=""height: 48px; width: 380px; margin:0; padding:0; background-color: #66b76d; -moz-border-radius: 2px; -webkit-border-radius: 2px; border-radius: 2px;""><a style=""{3}"" target=""_blank"" href=""{0}"">{1}</a></td>{2}</tr></tbody></table>", - btnUrl, - btnText, - "<td style=\"height: 48px; width: 80px; margin:0; padding:0;\"> </td>", - "color: #fff; font-family: Helvetica, Arial, Tahoma; font-size: 18px; font-weight: 600; vertical-align: middle; display: block; padding: 12px 0; text-align: center; text-decoration: none; background-color: #66b76d;"); + const string td = "<td style=\"height: 48px; width: 80px; margin:0; padding:0;\"> </td>"; + const string color = "color: #fff; font-family: Helvetica, Arial, Tahoma; font-size: 18px; font-weight: 600; vertical-align: middle; display: block; padding: 12px 0; text-align: center; text-decoration: none; background-color: #66b76d;"; + + return $@"<table style=""height: 48px; width: 540px; border-collapse: collapse; empty-cells: show; vertical-align: middle; text-align: center; margin: 30px auto; padding: 0;""><tbody><tr cellpadding=""0"" cellspacing=""0"" border=""0"">{td}<td style=""height: 48px; width: 380px; margin:0; padding:0; background-color: #66b76d; -moz-border-radius: 2px; -webkit-border-radius: 2px; border-radius: 2px;""><a style=""{color}"" target=""_blank"" href=""{btnUrl}"">{btnText}</a></td>{td}</tr></tbody></table>"; } return new ASC.Notify.Patterns.TagActionValue("BlueButton", action); @@ -71,15 +67,11 @@ namespace ASC.Web.Studio.Core.Notify string action() { var btnText = btnTextFunc != null ? btnTextFunc() ?? string.Empty : string.Empty; + const string td = "<td style=\"height: 48px; width: 80px; margin:0; padding:0;\"> </td>"; + const string color = "color: #fff; font-family: Helvetica, Arial, Tahoma; font-size: 18px; font-weight: 600; vertical-align: middle; display: block; padding: 12px 0; text-align: center; text-decoration: none; background-color: #66b76d;"; - return - string.Format( - @"<table style=""height: 48px; width: 540px; border-collapse: collapse; empty-cells: show; vertical-align: middle; text-align: center; margin: 30px auto; padding: 0;""><tbody><tr cellpadding=""0"" cellspacing=""0"" border=""0"">{2}<td style=""height: 48px; width: 380px; margin:0; padding:0; background-color: #66b76d; -moz-border-radius: 2px; -webkit-border-radius: 2px; border-radius: 2px;""><a style=""{3}"" target=""_blank"" href=""{0}"">{1}</a></td>{2}</tr></tbody></table>", - btnUrl, - btnText, - "<td style=\"height: 48px; width: 80px; margin:0; padding:0;\"> </td>", - "color: #fff; font-family: Helvetica, Arial, Tahoma; font-size: 18px; font-weight: 600; vertical-align: middle; display: block; padding: 12px 0; text-align: center; text-decoration: none; background-color: #66b76d;"); - } + return $@"<table style=""height: 48px; width: 540px; border-collapse: collapse; empty-cells: show; vertical-align: middle; text-align: center; margin: 30px auto; padding: 0;""><tbody><tr cellpadding=""0"" cellspacing=""0"" border=""0"">{td}<td style=""height: 48px; width: 380px; margin:0; padding:0; background-color: #66b76d; -moz-border-radius: 2px; -webkit-border-radius: 2px; border-radius: 2px;""><a style=""{color}"" target=""_blank"" href=""{btnUrl}"">{btnText}</a></td>{td}</tr></tbody></table>"; + } return new TagActionValue("GreenButton", action); } @@ -112,10 +104,7 @@ namespace ASC.Web.Studio.Core.Notify ? bottomlinkTextFunc() ?? string.Empty : string.Empty; - var imgHtml = string.Format( - "<img style=\"border: 0; padding: 0 15px 0 5px; width: auto; height: auto;\" alt=\"{1}\" src=\"{0}\"/>", - imgSrc ?? string.Empty, - linkText); + var imgHtml = $"<img style=\"border: 0; padding: 0 15px 0 5px; width: auto; height: auto;\" alt=\"{linkText}\" src=\"{imgSrc ?? string.Empty}\"/>"; var linkHtml = string.Empty; @@ -123,22 +112,14 @@ namespace ASC.Web.Studio.Core.Notify { linkHtml = !string.IsNullOrEmpty(linkUrl) - ? string.Format( - "<a target=\"_blank\" style=\"color:#0078bd; font-family: Arial; font-size: 14px; font-weight: bold;\" href=\"{0}\">{1}</a><br/>", - linkUrl, - linkText) - : string.Format( - "<div style=\"display:block; color:#333333; font-family: Arial; font-size: 14px; font-weight: bold;margin-bottom: 10px;\">{0}</div>", - linkText); + ? $"<a target=\"_blank\" style=\"color:#0078bd; font-family: Arial; font-size: 14px; font-weight: bold;\" href=\"{linkUrl}\">{linkText}</a><br/>" + : $"<div style=\"display:block; color:#333333; font-family: Arial; font-size: 14px; font-weight: bold;margin-bottom: 10px;\">{linkText}</div>"; } var underCommentLinkHtml = string.IsNullOrEmpty(bottomlinkUrl) ? string.Empty - : string.Format( - "<br/><a target=\"_blank\" style=\"color: #0078bd; font-family: Arial; font-size: 14px;\" href=\"{0}\">{1}</a>", - bottomlinkUrl, - bottomlinkText); + : $"<br/><a target=\"_blank\" style=\"color: #0078bd; font-family: Arial; font-size: 14px;\" href=\"{bottomlinkUrl}\">{bottomlinkText}</a>"; var html = "<tr><td style=\"vertical-align: top; padding: 5px 10px; width: 70px;\">" + @@ -159,7 +140,7 @@ namespace ASC.Web.Studio.Core.Notify { var imgSrc = studioNotifyHelper.GetNotificationImageUrl(imageFileName); - var imgHtml = string.Format("<img style=\"border: 0; padding: 0; width: auto; height: auto;\" alt=\"\" src=\"{0}\"/>", imgSrc); + var imgHtml = $"<img style=\"border: 0; padding: 0; width: auto; height: auto;\" alt=\"\" src=\"{imgSrc}\"/>"; var tagName = "Image" + (id > 0 ? id.ToString() : string.Empty); diff --git a/web/ASC.Web.Core/Notify/Tags.cs b/web/ASC.Web.Core/Notify/Tags.cs index f408fdee39..9bc5de9f29 100644 --- a/web/ASC.Web.Core/Notify/Tags.cs +++ b/web/ASC.Web.Core/Notify/Tags.cs @@ -82,7 +82,7 @@ namespace ASC.Web.Studio.Core.Notify public const string SmtpPort = "SmtpPort"; } - public sealed class CommonTags + public static class CommonTags { public const string VirtualRootPath = "__VirtualRootPath"; @@ -112,9 +112,9 @@ namespace ASC.Web.Studio.Core.Notify public const string Culture = "Culture"; - public static string Footer = "Footer"; + public static readonly string Footer = "Footer"; - public static string MasterTemplate = "MasterTemplate"; + public static readonly string MasterTemplate = "MasterTemplate"; public const string HelpLink = "__HelpLink"; diff --git a/web/ASC.Web.Core/PrivacyRoomSettings.cs b/web/ASC.Web.Core/PrivacyRoomSettings.cs index eb5537bc97..e1cea08d23 100644 --- a/web/ASC.Web.Core/PrivacyRoomSettings.cs +++ b/web/ASC.Web.Core/PrivacyRoomSettings.cs @@ -67,7 +67,7 @@ namespace ASC.Web.Studio.Core public static bool IsAvailable(TenantManager tenantManager) { - return SetupInfo.IsVisibleSettings(ManagementType.PrivacyRoom.ToString()) + return SetupInfo.IsVisibleSettings(nameof(ManagementType.PrivacyRoom)) && tenantManager.GetTenantQuota(tenantManager.GetCurrentTenant().TenantId).PrivacyRoom; } } diff --git a/web/ASC.Web.Core/QuotaSync.cs b/web/ASC.Web.Core/QuotaSync.cs index bfe2b7a48f..4f62fb6ce2 100644 --- a/web/ASC.Web.Core/QuotaSync.cs +++ b/web/ASC.Web.Core/QuotaSync.cs @@ -25,7 +25,6 @@ using System; -using System.Linq; using ASC.Common.Threading; using ASC.Core; @@ -56,14 +55,14 @@ namespace ASC.Web.Studio.Core.Quota var (tenantManager, storageFactoryConfig, storageFactory) = scopeClass; tenantManager.SetCurrentTenant(TenantId); - var storageModules = storageFactoryConfig.GetModuleList(string.Empty).ToList(); + var storageModules = storageFactoryConfig.GetModuleList(string.Empty); foreach (var module in storageModules) { var storage = storageFactory.GetStorage(TenantId.ToString(), module); storage.ResetQuota(""); - var domains = storageFactoryConfig.GetDomainList(string.Empty, module).ToList(); + var domains = storageFactoryConfig.GetDomainList(string.Empty, module); foreach (var domain in domains) { storage.ResetQuota(domain); diff --git a/web/ASC.Web.Core/Recaptcha.cs b/web/ASC.Web.Core/Recaptcha.cs index 6e017f9be7..1b4207a7c1 100644 --- a/web/ASC.Web.Core/Recaptcha.cs +++ b/web/ASC.Web.Core/Recaptcha.cs @@ -27,10 +27,12 @@ namespace ASC.Web.Core public class Recaptcha { private SetupInfo SetupInfo { get; } + private IHttpClientFactory ClientFactory { get; } - public Recaptcha(SetupInfo setupInfo) + public Recaptcha(SetupInfo setupInfo, IHttpClientFactory clientFactory) { SetupInfo = setupInfo; + ClientFactory = clientFactory; } @@ -38,14 +40,14 @@ namespace ASC.Web.Core { try { - var data = string.Format("secret={0}&remoteip={1}&response={2}", SetupInfo.RecaptchaPrivateKey, ip, response); + var data = $"secret={SetupInfo.RecaptchaPrivateKey}&remoteip={ip}&response={response}"; var request = new HttpRequestMessage(); request.RequestUri = new Uri(SetupInfo.RecaptchaVerifyUrl); request.Method = HttpMethod.Post; request.Content = new StringContent(data, Encoding.UTF8, "application/x-www-form-urlencoded"); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var httpClientResponse = httpClient.Send(request); using (var reader = new StreamReader(httpClientResponse.Content.ReadAsStream())) { diff --git a/web/ASC.Web.Core/SecutiryConstants.cs b/web/ASC.Web.Core/SecutiryConstants.cs index 50e9146bee..5aeeb83070 100644 --- a/web/ASC.Web.Core/SecutiryConstants.cs +++ b/web/ASC.Web.Core/SecutiryConstants.cs @@ -28,7 +28,7 @@ using ASC.Common.Security.Authorizing; namespace ASC.Web.Studio.Core { - public sealed class SecutiryConstants + public static class SecutiryConstants { public static readonly Action EditPortalSettings = new Action(new System.Guid("{60DB830E-80A8-4997-8B83-3D6EA525749B}"), "Edit Portal Settings"); } diff --git a/web/ASC.Web.Core/Sms/SmsKeyStorage.cs b/web/ASC.Web.Core/Sms/SmsKeyStorage.cs index c5dc7d9cf1..bb0f3c0f84 100644 --- a/web/ASC.Web.Core/Sms/SmsKeyStorage.cs +++ b/web/ASC.Web.Core/Sms/SmsKeyStorage.cs @@ -27,6 +27,7 @@ using System; using System.Collections.Generic; using System.Globalization; +using System.Security.Cryptography; using ASC.Common; using ASC.Common.Caching; @@ -107,7 +108,7 @@ namespace ASC.Web.Core.Sms { if (string.IsNullOrEmpty(phone)) { - throw new ArgumentNullException("phone"); + throw new ArgumentNullException(nameof(phone)); } lock (KeyLocker) @@ -120,7 +121,7 @@ namespace ASC.Web.Core.Sms return false; } - key = new Random().Next((int)Math.Pow(10, KeyLength - 1), (int)Math.Pow(10, KeyLength)).ToString(CultureInfo.InvariantCulture); + key = RandomNumberGenerator.GetInt32((int)Math.Pow(10, KeyLength - 1), (int)Math.Pow(10, KeyLength)).ToString(CultureInfo.InvariantCulture); phoneKeys[key] = DateTime.UtcNow; KeyCache.Insert(cacheKey, phoneKeys, DateTime.UtcNow.Add(StoreInterval)); @@ -173,7 +174,7 @@ namespace ASC.Web.Core.Sms if (createDate.Add(StoreInterval) < DateTime.UtcNow) return Result.Timeout; - CheckCache.Insert(cacheCheck, (--counter).ToString(CultureInfo.InvariantCulture), DateTime.UtcNow.Add(StoreInterval)); + CheckCache.Insert(cacheCheck, (counter - 1).ToString(CultureInfo.InvariantCulture), DateTime.UtcNow.Add(StoreInterval)); return Result.Ok; } } diff --git a/web/ASC.Web.Core/Sms/SmsManager.cs b/web/ASC.Web.Core/Sms/SmsManager.cs index ca670c2867..b1f5874c25 100644 --- a/web/ASC.Web.Core/Sms/SmsManager.cs +++ b/web/ASC.Web.Core/Sms/SmsManager.cs @@ -140,7 +140,7 @@ namespace ASC.Web.Studio.Core.SMS if (!SecurityContext.IsAuthenticated) { - var cookiesKey = SecurityContext.AuthenticateMe(user.ID); + SecurityContext.AuthenticateMe(user.ID); //CookiesManager.SetCookies(CookiesType.AuthKey, cookiesKey); } diff --git a/web/ASC.Web.Core/Sms/SmsProvider.cs b/web/ASC.Web.Core/Sms/SmsProvider.cs index 85ab695d12..993931efcc 100644 --- a/web/ASC.Web.Core/Sms/SmsProvider.cs +++ b/web/ASC.Web.Core/Sms/SmsProvider.cs @@ -119,7 +119,8 @@ namespace ASC.Web.Core.Sms public abstract class SmsProvider : Consumer { - protected readonly ILog Log; + protected ILog Log { get; } + protected IHttpClientFactory ClientFactory { get; } protected ICache MemoryCache { get; set; } protected virtual string SendMessageUrlFormat { get; set; } @@ -140,12 +141,14 @@ namespace ASC.Web.Core.Sms ICacheNotify<ConsumerCacheItem> cache, ConsumerFactory consumerFactory, IOptionsMonitor<ILog> options, + IHttpClientFactory clientFactory, ICache memCache, string name, int order, Dictionary<string, string> props, Dictionary<string, string> additional = null) : base(tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, name, order, props, additional) { MemoryCache = memCache; Log = options.CurrentValue; + ClientFactory = clientFactory; } public virtual bool Enable() @@ -172,7 +175,7 @@ namespace ASC.Web.Core.Sms request.RequestUri = new Uri(url); request.Content.Headers.ContentType = new MediaTypeHeaderValue("application/x-www-form-urlencoded"); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); httpClient.Timeout = TimeSpan.FromMilliseconds(15000); using var response = httpClient.Send(request); @@ -207,22 +210,21 @@ namespace ASC.Web.Core.Sms ICacheNotify<ConsumerCacheItem> cache, ConsumerFactory consumerFactory, IOptionsMonitor<ILog> options, + IHttpClientFactory clientFactory, ICache memCache, string name, int order, Dictionary<string, string> props, Dictionary<string, string> additional = null) - : base(tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, options, memCache, name, order, props, additional) + : base(tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, options, clientFactory, memCache, name, order, props, additional) { } protected override string SendMessageUrlFormat { get { return "https://smsc.ru/sys/send.php?login={key}&psw={secret}&phones={phone}&mes={text}&fmt=3&sender={sender}&charset=utf-8"; } - set { } } protected override string GetBalanceUrlFormat { get { return "https://smsc.ru/sys/balance.php?login={key}&psw={secret}"; } - set { } } protected override string Key @@ -266,7 +268,7 @@ namespace ASC.Web.Core.Sms request.RequestUri = new Uri(url); request.Content.Headers.ContentType = new MediaTypeHeaderValue("application/x-www-form-urlencoded"); - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); httpClient.Timeout = TimeSpan.FromMilliseconds(1000); using var response = httpClient.Send(request); @@ -316,19 +318,16 @@ namespace ASC.Web.Core.Sms protected override string SendMessageUrlFormat { get { return "https://platform.clickatell.com/messages/http/send?apiKey={secret}&to={phone}&content={text}&from={sender}"; } - set { } } protected override string Secret { get { return this["clickatellapiKey"]; } - set { } } protected override string Sender { get { return this["clickatellSender"]; } - set { } } public override bool Enable() @@ -348,9 +347,10 @@ namespace ASC.Web.Core.Sms ICacheNotify<ConsumerCacheItem> cache, ConsumerFactory consumerFactory, IOptionsMonitor<ILog> options, + IHttpClientFactory clientFactory, ICache memCache, string name, int order, Dictionary<string, string> props, Dictionary<string, string> additional = null) - : base(tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, options, memCache, name, order, props, additional) + : base(tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, options, clientFactory, memCache, name, order, props, additional) { } } @@ -369,9 +369,10 @@ namespace ASC.Web.Core.Sms ICacheNotify<ConsumerCacheItem> cache, ConsumerFactory consumerFactory, IOptionsMonitor<ILog> options, + IHttpClientFactory clientFactory, ICache memCache, string name, int order, Dictionary<string, string> additional = null) - : base(tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, options, memCache, name, order, null, additional) + : base(tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, options, clientFactory, memCache, name, order, null, additional) { } } @@ -382,19 +383,16 @@ namespace ASC.Web.Core.Sms protected override string Key { get { return this["twilioAccountSid"]; } - set { } } protected override string Secret { get { return this["twilioAuthToken"]; } - set { } } protected override string Sender { get { return this["twiliosender"]; } - set { } } public AuthContext AuthContext { get; } @@ -413,7 +411,7 @@ namespace ASC.Web.Core.Sms public override bool SendMessage(string number, string message) { - if (!number.StartsWith("+")) number = "+" + number; + if (!number.StartsWith('+')) number = "+" + number; var twilioRestClient = new TwilioRestClient(Key, Secret); try @@ -451,9 +449,10 @@ namespace ASC.Web.Core.Sms ICacheNotify<ConsumerCacheItem> cache, ConsumerFactory consumerFactory, IOptionsMonitor<ILog> options, + IHttpClientFactory clientFactory, ICache memCache, string name, int order, Dictionary<string, string> props) - : base(tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, options, memCache, name, order, props) + : base(tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, options, clientFactory, memCache, name, order, props) { AuthContext = authContext; TenantUtil = tenantUtil; @@ -502,9 +501,10 @@ namespace ASC.Web.Core.Sms ICacheNotify<ConsumerCacheItem> cache, ConsumerFactory consumerFactory, IOptionsMonitor<ILog> options, + IHttpClientFactory clientFactory, ICache memCache, string name, int order) - : base(authContext, tenantUtil, securityContext, baseCommonLinkUtility, twilioProviderCleaner, tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, options, memCache, name, order, null) + : base(authContext, tenantUtil, securityContext, baseCommonLinkUtility, twilioProviderCleaner, tenantManager, coreBaseSettings, coreSettings, configuration, cache, consumerFactory, options, clientFactory, memCache, name, order, null) { } } diff --git a/web/ASC.Web.Core/Sms/SmsSender.cs b/web/ASC.Web.Core/Sms/SmsSender.cs index ba3afbfe63..3f6a3adde9 100644 --- a/web/ASC.Web.Core/Sms/SmsSender.cs +++ b/web/ASC.Web.Core/Sms/SmsSender.cs @@ -62,11 +62,11 @@ namespace ASC.Web.Core.Sms { if (string.IsNullOrEmpty(number)) { - throw new ArgumentNullException("number"); + throw new ArgumentNullException(nameof(number)); } if (string.IsNullOrEmpty(message)) { - throw new ArgumentNullException("message"); + throw new ArgumentNullException(nameof(message)); } if (!SmsProviderManager.Enabled()) { @@ -106,13 +106,13 @@ namespace ASC.Web.Core.Sms return mobilePhone; var sb = new StringBuilder(); - sb.Append("+"); - sb.Append(mobilePhone.Substring(0, startLen)); + sb.Append('+'); + sb.Append(mobilePhone, 0, startLen); for (var i = startLen; i < mobilePhone.Length - endLen; i++) { - sb.Append("*"); + sb.Append('*'); } - sb.Append(mobilePhone.Substring(mobilePhone.Length - endLen)); + sb.Append(mobilePhone, mobilePhone.Length - endLen, mobilePhone.Length - (endLen +1)); return sb.ToString(); } } diff --git a/web/ASC.Web.Core/Subscriptions/SubscriptionType.cs b/web/ASC.Web.Core/Subscriptions/SubscriptionType.cs index 42c38ee875..f9aef8e83f 100644 --- a/web/ASC.Web.Core/Subscriptions/SubscriptionType.cs +++ b/web/ASC.Web.Core/Subscriptions/SubscriptionType.cs @@ -47,9 +47,9 @@ namespace ASC.Web.Core.Subscriptions public bool CanSubscribe { get; set; } - public IsEmptySubscriptionTypeDelegate IsEmptySubscriptionType; + public IsEmptySubscriptionTypeDelegate IsEmptySubscriptionType { get; set; } - public GetSubscriptionObjectsDelegate GetSubscriptionObjects; + public GetSubscriptionObjectsDelegate GetSubscriptionObjects { get; set; } } } diff --git a/web/ASC.Web.Core/Tfa/TfaAppUserSettings.cs b/web/ASC.Web.Core/Tfa/TfaAppUserSettings.cs index 684d378ae5..69725e06ed 100644 --- a/web/ASC.Web.Core/Tfa/TfaAppUserSettings.cs +++ b/web/ASC.Web.Core/Tfa/TfaAppUserSettings.cs @@ -82,7 +82,7 @@ namespace ASC.Web.Studio.Core.TFA var settings = settingsManager.LoadForUser<TfaAppUserSettings>(userId); var query = settings.CodesSetting.Where(x => x.GetEncryptedCode(instanceCrypto, signature) == code).ToList(); - if (query.Any()) + if (query.Count > 0) query.First().IsUsed = true; settingsManager.SaveForUser(settings, userId); diff --git a/web/ASC.Web.Core/Tfa/TfaManager.cs b/web/ASC.Web.Core/Tfa/TfaManager.cs index cd1061bd27..8c555b0e1a 100644 --- a/web/ASC.Web.Core/Tfa/TfaManager.cs +++ b/web/ASC.Web.Core/Tfa/TfaManager.cs @@ -146,7 +146,7 @@ namespace ASC.Web.Studio.Core.TFA } } - Cache.Insert("tfa/" + user.ID, (--counter).ToString(CultureInfo.InvariantCulture), DateTime.UtcNow.Add(TimeSpan.FromMinutes(1))); + Cache.Insert("tfa/" + user.ID, (counter - 1).ToString(CultureInfo.InvariantCulture), DateTime.UtcNow.Add(TimeSpan.FromMinutes(1))); if (!SecurityContext.IsAuthenticated) { @@ -170,7 +170,7 @@ namespace ASC.Web.Studio.Core.TFA const string alphabet = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890-_"; - var data = new byte[length]; + byte[] data; var list = new List<BackupCode>(); @@ -181,7 +181,7 @@ namespace ASC.Web.Studio.Core.TFA var result = new StringBuilder(length); foreach (var b in data) { - result.Append(alphabet[b % (alphabet.Length)]); + result.Append(alphabet[b % alphabet.Length]); } var code = new BackupCode(); diff --git a/web/ASC.Web.Core/Users/CustomNamingPeople.cs b/web/ASC.Web.Core/Users/CustomNamingPeople.cs index 7d16a6d47d..512f33a7c8 100644 --- a/web/ASC.Web.Core/Users/CustomNamingPeople.cs +++ b/web/ASC.Web.Core/Users/CustomNamingPeople.cs @@ -164,19 +164,12 @@ namespace ASC.Web.Core.Users [Scope] public class CustomNamingPeople { - private static object Locked; + private static object Locked = new object(); private static bool loaded = false; private static readonly List<PeopleNamesItem> items = new List<PeopleNamesItem>(); private SettingsManager SettingsManager { get; } - static CustomNamingPeople() - { - Locked = new object(); - loaded = false; - items = new List<PeopleNamesItem>(); - } - public CustomNamingPeople(SettingsManager settingsManager) { SettingsManager = settingsManager; diff --git a/web/ASC.Web.Core/Users/Import/TextFileUserImporter.cs b/web/ASC.Web.Core/Users/Import/TextFileUserImporter.cs index 4932763ba9..1f46253b11 100644 --- a/web/ASC.Web.Core/Users/Import/TextFileUserImporter.cs +++ b/web/ASC.Web.Core/Users/Import/TextFileUserImporter.cs @@ -115,7 +115,7 @@ namespace ASC.Web.Core.Users.Import var value = ConvertFromString(dataFields[j], propinfo.PropertyType); if (value != null) { - propinfo.SetValue(exportedUser, value, new object[] { }); + propinfo.SetValue(exportedUser, value, Array.Empty<object>()); } } } @@ -150,9 +150,9 @@ namespace ASC.Web.Core.Users.Import foreach (var info in infos) { var propertyField = field.Trim(); - if (NameMapping != null && NameMapping.ContainsKey(propertyField)) + if (NameMapping != null) { - propertyField = NameMapping[propertyField]; + NameMapping.TryGetValue(propertyField, out propertyField); } if (!string.IsNullOrEmpty(propertyField) && !ExcludeList.Contains(propertyField) && propertyField.Equals(info.Name, StringComparison.OrdinalIgnoreCase)) { diff --git a/web/ASC.Web.Core/Users/UserManagerWrapper.cs b/web/ASC.Web.Core/Users/UserManagerWrapper.cs index 09133c0921..ba9c0fee41 100644 --- a/web/ASC.Web.Core/Users/UserManagerWrapper.cs +++ b/web/ASC.Web.Core/Users/UserManagerWrapper.cs @@ -27,6 +27,7 @@ using System; using System.Globalization; using System.Net.Mail; +using System.Security.Cryptography; using System.Text; using System.Text.RegularExpressions; @@ -97,14 +98,14 @@ namespace ASC.Web.Core.Users private string MakeUniqueName(UserInfo userInfo) { if (string.IsNullOrEmpty(userInfo.Email)) - throw new ArgumentException(Resource.ErrorEmailEmpty, "userInfo"); + throw new ArgumentException(Resource.ErrorEmailEmpty, nameof(userInfo)); var uniqueName = new MailAddress(userInfo.Email).User; var startUniqueName = uniqueName; var i = 0; while (!TestUniqueUserName(uniqueName)) { - uniqueName = string.Format("{0}{1}", startUniqueName, (++i).ToString(CultureInfo.InvariantCulture)); + uniqueName = $"{startUniqueName}{(++i).ToString(CultureInfo.InvariantCulture)}"; } return uniqueName; } @@ -117,7 +118,7 @@ namespace ASC.Web.Core.Users public UserInfo AddUser(UserInfo userInfo, string passwordHash, bool afterInvite = false, bool notify = true, bool isVisitor = false, bool fromInviteLink = false, bool makeUniqueName = true) { - if (userInfo == null) throw new ArgumentNullException("userInfo"); + if (userInfo == null) throw new ArgumentNullException(nameof(userInfo)); if (!UserFormatter.IsValidUserName(userInfo.FirstName, userInfo.LastName)) throw new Exception(Resource.ErrorIncorrectUserName); @@ -234,12 +235,12 @@ namespace ASC.Web.Core.Users if (passwordSettings.SpecSymbols) pwdBuilder.Append(@"(?=.*[\W])"); - pwdBuilder.Append(@"."); + pwdBuilder.Append('.'); } - pwdBuilder.Append(@"{"); + pwdBuilder.Append('{'); pwdBuilder.Append(passwordSettings.MinLength); - pwdBuilder.Append(@","); + pwdBuilder.Append(','); pwdBuilder.Append(PasswordSettings.MaxLength); pwdBuilder.Append(@"}$"); @@ -256,7 +257,7 @@ namespace ASC.Web.Core.Users public string SendUserPassword(string email) { email = (email ?? "").Trim(); - if (!email.TestEmailRegex()) throw new ArgumentNullException("email", Resource.ErrorNotCorrectEmail); + if (!email.TestEmailRegex()) throw new ArgumentNullException(nameof(email), Resource.ErrorNotCorrectEmail); if (!IPSecurity.Verify()) { @@ -294,32 +295,30 @@ namespace ASC.Web.Core.Users return Guid.NewGuid().ToString(); } - private static readonly Random Rnd = new Random(); - internal static string GeneratePassword(int minLength, int maxLength, string noise) { - var length = Rnd.Next(minLength, maxLength + 1); + var length = RandomNumberGenerator.GetInt32(minLength, maxLength + 1); - var pwd = string.Empty; + var sb = new StringBuilder(); while (length-- > 0) { - pwd += noise.Substring(Rnd.Next(noise.Length - 1), 1); + sb.Append(noise[RandomNumberGenerator.GetInt32(noise.Length - 1)]); } - return pwd; + return sb.ToString(); } internal static string GenerateErrorMessage(PasswordSettings passwordSettings) { var error = new StringBuilder(); - error.AppendFormat("{0} ", Resource.ErrorPasswordMessage); + error.Append($"{Resource.ErrorPasswordMessage} "); error.AppendFormat(Resource.ErrorPasswordLength, passwordSettings.MinLength, PasswordSettings.MaxLength); if (passwordSettings.UpperCase) - error.AppendFormat(", {0}", Resource.ErrorPasswordNoUpperCase); + error.AppendFormat($", {Resource.ErrorPasswordNoUpperCase}"); if (passwordSettings.Digits) - error.AppendFormat(", {0}", Resource.ErrorPasswordNoDigits); + error.Append($", {Resource.ErrorPasswordNoDigits}"); if (passwordSettings.SpecSymbols) - error.AppendFormat(", {0}", Resource.ErrorPasswordNoSpecialSymbols); + error.Append($", {Resource.ErrorPasswordNoSpecialSymbols}"); return error.ToString(); } @@ -328,14 +327,14 @@ namespace ASC.Web.Core.Users { var info = new StringBuilder(); var passwordSettings = SettingsManager.Load<PasswordSettings>(); - info.AppendFormat("{0} ", Resource.ErrorPasswordMessageStart); + info.Append($"{Resource.ErrorPasswordMessageStart} "); info.AppendFormat(Resource.ErrorPasswordLength, passwordSettings.MinLength, PasswordSettings.MaxLength); if (passwordSettings.UpperCase) - info.AppendFormat(", {0}", Resource.ErrorPasswordNoUpperCase); + info.Append($", {Resource.ErrorPasswordNoUpperCase}"); if (passwordSettings.Digits) - info.AppendFormat(", {0}", Resource.ErrorPasswordNoDigits); + info.Append($", {Resource.ErrorPasswordNoDigits}"); if (passwordSettings.SpecSymbols) - info.AppendFormat(", {0}", Resource.ErrorPasswordNoSpecialSymbols); + info.Append($", {Resource.ErrorPasswordNoSpecialSymbols}"); return info.ToString(); } diff --git a/web/ASC.Web.Core/Users/UserPhotoManager.cs b/web/ASC.Web.Core/Users/UserPhotoManager.cs index be4dc9f334..1c3805791a 100644 --- a/web/ASC.Web.Core/Users/UserPhotoManager.cs +++ b/web/ASC.Web.Core/Users/UserPhotoManager.cs @@ -50,7 +50,7 @@ using SixLabors.ImageSharp.Processing; namespace ASC.Web.Core.Users { [Transient] - public class ResizeWorkerItem : DistributedTask + public sealed class ResizeWorkerItem : DistributedTask { public ResizeWorkerItem() { @@ -83,7 +83,7 @@ namespace ASC.Web.Core.Users { if (obj is null) return false; if (ReferenceEquals(this, obj)) return true; - if (obj.GetType() != typeof(ResizeWorkerItem)) return false; + if (!(obj is ResizeWorkerItem)) return false; return Equals((ResizeWorkerItem)obj); } @@ -233,10 +233,10 @@ namespace ASC.Web.Core.Users Log = options.Get("ASC.Web.Photo"); } - public string defaultAbsoluteWebPath; + private string _defaultAbsoluteWebPath; public string GetDefaultPhotoAbsoluteWebPath() { - return defaultAbsoluteWebPath ??= WebImageSupplier.GetAbsoluteWebPath(_defaultAvatar); + return _defaultAbsoluteWebPath ??= WebImageSupplier.GetAbsoluteWebPath(_defaultAvatar); } public string GetRetinaPhotoURL(Guid userID) @@ -296,34 +296,34 @@ namespace ASC.Web.Core.Users } - public string defaultSmallPhotoURL; + private string _defaultSmallPhotoURL; public string GetDefaultSmallPhotoURL() { - return defaultSmallPhotoURL ??= GetDefaultPhotoAbsoluteWebPath(SmallFotoSize); + return _defaultSmallPhotoURL ??= GetDefaultPhotoAbsoluteWebPath(SmallFotoSize); } - public string defaultMediumPhotoURL; + private string _defaultMediumPhotoURL; public string GetDefaultMediumPhotoURL() { - return defaultMediumPhotoURL ??= GetDefaultPhotoAbsoluteWebPath(MediumFotoSize); + return _defaultMediumPhotoURL ??= GetDefaultPhotoAbsoluteWebPath(MediumFotoSize); } - public string defaultBigPhotoURL; + private string _defaultBigPhotoURL; public string GetDefaultBigPhotoURL() { - return defaultBigPhotoURL ??= GetDefaultPhotoAbsoluteWebPath(BigFotoSize); + return _defaultBigPhotoURL ??= GetDefaultPhotoAbsoluteWebPath(BigFotoSize); } - public string defaultMaxPhotoURL; + private string _defaultMaxPhotoURL; public string GetDefaultMaxPhotoURL() { - return defaultMaxPhotoURL ??= GetDefaultPhotoAbsoluteWebPath(MaxFotoSize); + return _defaultMaxPhotoURL ??= GetDefaultPhotoAbsoluteWebPath(MaxFotoSize); } - public string defaultRetinaPhotoURL; + private string _defaultRetinaPhotoURL; public string GetDefaultRetinaPhotoURL() { - return defaultRetinaPhotoURL ??= GetDefaultPhotoAbsoluteWebPath(RetinaFotoSize); + return _defaultRetinaPhotoURL ??= GetDefaultPhotoAbsoluteWebPath(RetinaFotoSize); } public static Size OriginalFotoSize { get; } = new Size(1280, 1280); @@ -806,7 +806,7 @@ namespace ASC.Web.Core.Users var store = GetDataStore(); store.DeleteFiles(_tempDomainName, "", fileNameWithoutExt + "*.*", false); } - catch { }; + catch { } } @@ -832,7 +832,7 @@ namespace ASC.Web.Core.Users var moduleID = Guid.Empty; var widening = CommonPhotoManager.GetImgFormatName(format); var size = img.Size(); - var fileName = string.Format("{0}{1}_size_{2}-{3}.{4}", (moduleID == Guid.Empty ? "" : moduleID.ToString()), userID, img.Width, img.Height, widening); + var fileName = string.Format("{0}{1}_size_{2}-{3}.{4}", moduleID == Guid.Empty ? "" : moduleID.ToString(), userID, img.Width, img.Height, widening); var store = GetDataStore(); string photoUrl; @@ -1023,7 +1023,7 @@ namespace ASC.Web.Core.Users } } - public class ResizeWorkerItemExtension + public static class ResizeWorkerItemExtension { public static void Register(DIHelper services) { diff --git a/web/ASC.Web.Core/Users/UserPhotoThumbnailManager.cs b/web/ASC.Web.Core/Users/UserPhotoThumbnailManager.cs index fe1279878c..d019cff558 100644 --- a/web/ASC.Web.Core/Users/UserPhotoThumbnailManager.cs +++ b/web/ASC.Web.Core/Users/UserPhotoThumbnailManager.cs @@ -35,7 +35,7 @@ using SixLabors.ImageSharp.Processing; namespace ASC.Web.Core.Users { - public class UserPhotoThumbnailManager + public static class UserPhotoThumbnailManager { public static List<ThumbnailItem> SaveThumbnails(UserPhotoManager userPhotoManager, SettingsManager settingsManager, int x, int y, int width, int height, Guid userId) { diff --git a/web/ASC.Web.Core/Utility/CommonLinkUtility.cs b/web/ASC.Web.Core/Utility/CommonLinkUtility.cs index f0a1d81360..e8bbd64422 100644 --- a/web/ASC.Web.Core/Utility/CommonLinkUtility.cs +++ b/web/ASC.Web.Core/Utility/CommonLinkUtility.cs @@ -282,7 +282,7 @@ namespace ASC.Web.Studio.Utility foreach (var item in WebItemManager.GetItemsAll()) { var _itemName = GetWebItemNameFromUrl(item.StartURL); - if (string.Compare(itemName, _itemName, StringComparison.InvariantCultureIgnoreCase) == 0) + if (itemName.Equals(_itemName, StringComparison.InvariantCultureIgnoreCase)) return item; } } @@ -345,7 +345,7 @@ namespace ASC.Web.Studio.Utility var _productName = GetProductNameFromUrl(product.StartURL); if (!string.IsNullOrEmpty(_productName)) { - if (string.Compare(productName, _productName, StringComparison.InvariantCultureIgnoreCase) == 0) + if (string.Equals(productName, _productName, StringComparison.InvariantCultureIgnoreCase)) { currentProduct = product; @@ -356,7 +356,7 @@ namespace ASC.Web.Studio.Utility var _moduleName = GetModuleNameFromUrl(module.StartURL); if (!string.IsNullOrEmpty(_moduleName)) { - if (string.Compare(moduleName, _moduleName, StringComparison.InvariantCultureIgnoreCase) == 0) + if (string.Equals(moduleName, _moduleName, StringComparison.InvariantCultureIgnoreCase)) { currentModule = module; break; @@ -463,7 +463,7 @@ namespace ASC.Web.Studio.Utility if (!string.IsNullOrEmpty(sysName)) foreach (var product in WebItemManager.GetItemsAll<IProduct>()) { - if (string.CompareOrdinal(sysName, WebItemExtension.GetSysName(product)) == 0) + if (string.Equals(sysName, WebItemExtension.GetSysName(product))) { result = product; break; diff --git a/web/ASC.Web.Core/Utility/Skins/WebImageSupplier.cs b/web/ASC.Web.Core/Utility/Skins/WebImageSupplier.cs index 8bffe180c5..40036983ee 100644 --- a/web/ASC.Web.Core/Utility/Skins/WebImageSupplier.cs +++ b/web/ASC.Web.Core/Utility/Skins/WebImageSupplier.cs @@ -111,8 +111,8 @@ namespace ASC.Web.Core.Utility.Skins return string.Empty; } - var dir = webitem.StartURL.Contains(".") ? - webitem.StartURL.Substring(0, webitem.StartURL.LastIndexOf("/")) : + var dir = webitem.StartURL.Contains('.') ? + webitem.StartURL.Substring(0, webitem.StartURL.LastIndexOf('/')) : webitem.StartURL.TrimEnd('/'); return dir + "/App_Themes"; } diff --git a/web/ASC.Web.Core/Utility/UrlShortener.cs b/web/ASC.Web.Core/Utility/UrlShortener.cs index ac8f8ecd05..5f80da9fbf 100644 --- a/web/ASC.Web.Core/Utility/UrlShortener.cs +++ b/web/ASC.Web.Core/Utility/UrlShortener.cs @@ -38,7 +38,7 @@ namespace ASC.Web.Core.Utility } else if (!string.IsNullOrEmpty(Configuration["web:url-shortener:value"])) { - _instance = new OnlyoShortener(Configuration, CommonLinkUtility, MachinePseudoKeys); + _instance = new OnlyoShortener(Configuration, CommonLinkUtility, MachinePseudoKeys, ClientFactory); } else { @@ -58,17 +58,20 @@ namespace ASC.Web.Core.Utility private ConsumerFactory ConsumerFactory { get; } private CommonLinkUtility CommonLinkUtility { get; } private MachinePseudoKeys MachinePseudoKeys { get; } + private IHttpClientFactory ClientFactory { get; } public UrlShortener( IConfiguration configuration, ConsumerFactory consumerFactory, CommonLinkUtility commonLinkUtility, - MachinePseudoKeys machinePseudoKeys) + MachinePseudoKeys machinePseudoKeys, + IHttpClientFactory clientFactory) { Configuration = configuration; ConsumerFactory = consumerFactory; CommonLinkUtility = commonLinkUtility; MachinePseudoKeys = machinePseudoKeys; + ClientFactory = clientFactory; } } @@ -91,24 +94,27 @@ namespace ASC.Web.Core.Utility { private readonly string url; private readonly string internalUrl; - private readonly byte[] sKey; + private readonly byte[] sKey; + + private CommonLinkUtility CommonLinkUtility { get; } + private IHttpClientFactory ClientFactory { get; } public OnlyoShortener( IConfiguration configuration, CommonLinkUtility commonLinkUtility, - MachinePseudoKeys machinePseudoKeys) + MachinePseudoKeys machinePseudoKeys, + IHttpClientFactory clientFactory) { url = configuration["web:url-shortener:value"]; internalUrl = configuration["web:url-shortener:internal"]; sKey = machinePseudoKeys.GetMachineConstant(); - if (!url.EndsWith("/")) + if (!url.EndsWith('/')) url += '/'; - CommonLinkUtility = commonLinkUtility; + CommonLinkUtility = commonLinkUtility; + ClientFactory = clientFactory; } - private CommonLinkUtility CommonLinkUtility { get; } - public string GetShortenLink(string shareLink) { var request = new HttpRequestMessage(); @@ -116,7 +122,7 @@ namespace ASC.Web.Core.Utility request.Headers.Add("Authorization", CreateAuthToken()); request.Headers.Add("Encoding", Encoding.UTF8.ToString());//todo check - using var httpClient = new HttpClient(); + var httpClient = ClientFactory.CreateClient(); using var response = httpClient.Send(request); using var stream = response.Content.ReadAsStream(); using var rs = new StreamReader(stream); @@ -128,7 +134,7 @@ namespace ASC.Web.Core.Utility using var hasher = new HMACSHA1(sKey); var now = DateTime.UtcNow.ToString("yyyyMMddHHmmss"); var hash = Convert.ToBase64String(hasher.ComputeHash(Encoding.UTF8.GetBytes(string.Join("\n", now, pkey)))); - return string.Format("ASC {0}:{1}:{2}", pkey, now, hash); + return $"ASC {pkey}:{now}:{hash}"; } } diff --git a/web/ASC.Web.Core/WebItemManager.cs b/web/ASC.Web.Core/WebItemManager.cs index 1388b56f57..9cb9ca2f43 100644 --- a/web/ASC.Web.Core/WebItemManager.cs +++ b/web/ASC.Web.Core/WebItemManager.cs @@ -156,7 +156,7 @@ namespace ASC.Web.Core } catch (Exception exc) { - log.Error(string.Format("Couldn't load web item {0}", file), exc); + log.Error($"Couldn't load web item {file}", exc); } } @@ -261,10 +261,11 @@ namespace ASC.Web.Core public List<IWebItem> GetSubItems(Guid parentItemID, ItemAvailableState avaliableState) { - return GetItems(WebZoneType.All, avaliableState).OfType<IModule>() - .Where(p => p.ProjectId == parentItemID) - .Cast<IWebItem>() - .ToList(); + return GetItems(WebZoneType.All, avaliableState) + .OfType<IModule>() + .Where(p => p.ProjectId == parentItemID) + .Cast<IWebItem>() + .ToList(); } } } \ No newline at end of file diff --git a/web/ASC.Web.Core/WebItemSecurity.cs b/web/ASC.Web.Core/WebItemSecurity.cs index 49c20ae116..3dce5b757d 100644 --- a/web/ASC.Web.Core/WebItemSecurity.cs +++ b/web/ASC.Web.Core/WebItemSecurity.cs @@ -84,7 +84,8 @@ namespace ASC.Web.Core var dic = Get(tenantId); if (dic == null) { - Cache.Insert(GetCacheKey(tenantId), dic = new Dictionary<string, bool>(), DateTime.UtcNow.Add(TimeSpan.FromMinutes(1))); + dic = new Dictionary<string, bool>(); + Cache.Insert(GetCacheKey(tenantId), dic, DateTime.UtcNow.Add(TimeSpan.FromMinutes(1))); } return dic; @@ -140,7 +141,7 @@ namespace ASC.Web.Core public bool IsAvailableForUser(Guid itemId, Guid @for) { var id = itemId.ToString(); - var result = false; + bool result; var tenant = TenantManager.GetCurrentTenant(); var dic = WebItemSecurityCache.GetOrInsert(tenant.TenantId); @@ -148,9 +149,9 @@ namespace ASC.Web.Core { lock (dic) { - if (dic.ContainsKey(id + @for)) + if (dic.TryGetValue(id + @for, out var value)) { - return dic[id + @for]; + return value; } } } @@ -253,7 +254,7 @@ namespace ASC.Web.Core { WebItemId = id, - Enabled = !info.Any() || (!module && info.Any(i => i.Item2)) || (module && info.All(i => i.Item2)), + Enabled = info.Count == 0 || (!module && info.Any(i => i.Item2)) || (module && info.All(i => i.Item2)), Users = info .Select(i => UserManager.GetUsers(i.Item1)) @@ -273,7 +274,7 @@ namespace ASC.Web.Core .GroupBy(a => a.SubjectId) .Select(a => Tuple.Create(a.Key, a.First().Reaction == AceType.Allow)) .ToList(); - if (!result.Any()) + if (result.Count == 0) { result.Add(Tuple.Create(ASC.Core.Users.Constants.GroupEveryone.ID, false)); } @@ -398,7 +399,7 @@ namespace ASC.Web.Core { if (string.IsNullOrEmpty(id)) { - throw new ArgumentNullException("id"); + throw new ArgumentNullException(nameof(id)); } var itemId = Guid.Empty; diff --git a/web/ASC.Web.Core/WhiteLabel/TenantWhiteLabelSettings.cs b/web/ASC.Web.Core/WhiteLabel/TenantWhiteLabelSettings.cs index b146d0ca05..271502dcb7 100644 --- a/web/ASC.Web.Core/WhiteLabel/TenantWhiteLabelSettings.cs +++ b/web/ASC.Web.Core/WhiteLabel/TenantWhiteLabelSettings.cs @@ -346,7 +346,6 @@ namespace ASC.Web.Core.WhiteLabel using (var memory = new MemoryStream(data)) using (var image = Image.Load(memory)) { - var logoSize = image.Size(); var logoFileName = BuildLogoFileName(type, logoFileExt, false); memory.Seek(0, SeekOrigin.Begin); @@ -367,7 +366,7 @@ namespace ASC.Web.Core.WhiteLabel foreach (var currentLogo in logo) { - var currentLogoType = (WhiteLabelLogoTypeEnum)(currentLogo.Key); + var currentLogoType = (WhiteLabelLogoTypeEnum)currentLogo.Key; var currentLogoPath = currentLogo.Value; if (!string.IsNullOrEmpty(currentLogoPath)) @@ -404,7 +403,7 @@ namespace ASC.Web.Core.WhiteLabel public void SetLogoFromStream(TenantWhiteLabelSettings tenantWhiteLabelSettings, WhiteLabelLogoTypeEnum type, string fileExt, Stream fileStream, IDataStore storage = null) { - byte[] data = null; + byte[] data; using (var memoryStream = new MemoryStream()) { fileStream.CopyTo(memoryStream); @@ -520,7 +519,7 @@ namespace ASC.Web.Core.WhiteLabel public static string BuildLogoFileName(WhiteLabelLogoTypeEnum type, string fileExt, bool general) { - return string.Format("logo_{0}{2}.{1}", type.ToString().ToLowerInvariant(), fileExt, general ? "_general" : ""); + return $"logo_{type.ToString().ToLowerInvariant()}{(general ? "_general" : "")}.{fileExt}"; } public static Size GetSize(WhiteLabelLogoTypeEnum type, bool general) @@ -555,8 +554,8 @@ namespace ASC.Web.Core.WhiteLabel try { using var stream = new MemoryStream(data); - using var img = Image.Load(stream, out var format); - var imgFormat = format; + using var img = Image.Load(stream, out var format); + if (size != img.Size()) { using var img2 = CommonPhotoManager.DoThumbnail(img, size, false, true, false); diff --git a/web/ASC.Web.HealthChecks.UI/Program.cs b/web/ASC.Web.HealthChecks.UI/Program.cs index 5261aa70ec..4f643d32f4 100644 --- a/web/ASC.Web.HealthChecks.UI/Program.cs +++ b/web/ASC.Web.HealthChecks.UI/Program.cs @@ -1,13 +1,11 @@ using System.Threading.Tasks; -using ASC.Api.Core; - using Microsoft.AspNetCore.Hosting; using Microsoft.Extensions.Hosting; namespace ASC.Web.HealthChecks.UI { - public class Program + public static class Program { public async static Task Main(string[] args) { diff --git a/web/ASC.Web.Studio/Program.cs b/web/ASC.Web.Studio/Program.cs index 4c09f77e21..b6964c19d3 100644 --- a/web/ASC.Web.Studio/Program.cs +++ b/web/ASC.Web.Studio/Program.cs @@ -15,7 +15,7 @@ using Microsoft.Extensions.Hosting; namespace ASC.Web.Studio { - public class Program + public static class Program { public async static Task Main(string[] args) { diff --git a/web/ASC.Web.Studio/Startup.cs b/web/ASC.Web.Studio/Startup.cs index a2c2023cee..887a039237 100644 --- a/web/ASC.Web.Studio/Startup.cs +++ b/web/ASC.Web.Studio/Startup.cs @@ -12,9 +12,6 @@ using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Hosting; -using StackExchange.Redis.Extensions.Core.Configuration; -using StackExchange.Redis.Extensions.Newtonsoft; - namespace ASC.Web.Studio { public class Startup : BaseStartup