From 99f0f702f8e0a863d564521a219ca385be8c9f42 Mon Sep 17 00:00:00 2001 From: MaksimChegulov Date: Thu, 3 Mar 2022 21:01:34 +0300 Subject: [PATCH] Files: refactor --- .../ASC.Files/Server/Api/ApiControllerBase.cs | 2 +- products/ASC.Files/Server/GlobalUsings.cs | 2 - .../Server/Helpers/FilesControllerHelper.cs | 1655 +++++++++-------- .../ASC.Files/Server/ProductEntryPoint.cs | 35 +- products/ASC.Files/Server/Startup.cs | 109 +- 5 files changed, 913 insertions(+), 890 deletions(-) diff --git a/products/ASC.Files/Server/Api/ApiControllerBase.cs b/products/ASC.Files/Server/Api/ApiControllerBase.cs index 40877f64d7..1fc85c8d78 100644 --- a/products/ASC.Files/Server/Api/ApiControllerBase.cs +++ b/products/ASC.Files/Server/Api/ApiControllerBase.cs @@ -4,7 +4,7 @@ [DefaultRoute] [ApiController] [ControllerName("files")] -public class ApiControllerBase : ControllerBase +public abstract class ApiControllerBase : ControllerBase { protected readonly FilesControllerHelper _filesControllerHelperInt; protected readonly FilesControllerHelper _filesControllerHelperString; diff --git a/products/ASC.Files/Server/GlobalUsings.cs b/products/ASC.Files/Server/GlobalUsings.cs index 4730d41fdc..76d3e673ed 100644 --- a/products/ASC.Files/Server/GlobalUsings.cs +++ b/products/ASC.Files/Server/GlobalUsings.cs @@ -65,5 +65,3 @@ global using Microsoft.Extensions.Hosting; global using Microsoft.Extensions.Options; global using Newtonsoft.Json.Linq; - -global using static ASC.Api.Documents.FilesController; diff --git a/products/ASC.Files/Server/Helpers/FilesControllerHelper.cs b/products/ASC.Files/Server/Helpers/FilesControllerHelper.cs index 5643843a07..80eb3aa90a 100644 --- a/products/ASC.Files/Server/Helpers/FilesControllerHelper.cs +++ b/products/ASC.Files/Server/Helpers/FilesControllerHelper.cs @@ -1,813 +1,841 @@ - -using ASC.Core; -using ASC.Web.Core.Files; -using ASC.Web.Files.Classes; - -using FileShare = ASC.Files.Core.Security.FileShare; +using FileShare = ASC.Files.Core.Security.FileShare; using MimeMapping = ASC.Common.Web.MimeMapping; using SortedByType = ASC.Files.Core.SortedByType; -namespace ASC.Files.Helpers +namespace ASC.Files.Helpers; + +[Scope] +public class FilesControllerHelper { - [Scope] - public class FilesControllerHelper + private readonly ApiContext _apiContext; + private readonly FileStorageService _fileStorageService; + private readonly GlobalFolderHelper _globalFolderHelper; + private readonly CoreBaseSettings _coreBaseSettings; + private readonly FileUtility _fileUtility; + private readonly FileWrapperHelper _fileWrapperHelper; + private readonly FilesSettingsHelper _filesSettingsHelper; + private readonly FilesLinkUtility _filesLinkUtility; + private readonly FileUploader _fileUploader; + private readonly DocumentServiceHelper _documentServiceHelper; + private readonly TenantManager _tenantManager; + private readonly SecurityContext _securityContext; + private readonly FolderWrapperHelper _folderWrapperHelper; + private readonly FileOperationWraperHelper _fileOperationWraperHelper; + private readonly FileShareWrapperHelper _fileShareWrapperHelper; + private readonly FileShareParamsHelper _fileShareParamsHelper; + private readonly EntryManager _entryManager; + private readonly FolderContentWrapperHelper _folderContentWrapperHelper; + private readonly ChunkedUploadSessionHelper _chunkedUploadSessionHelper; + private readonly DocumentServiceTrackerHelper _documentServiceTracker; + private readonly SettingsManager _settingsManager; + private readonly EncryptionKeyPairHelper _encryptionKeyPairHelper; + private readonly IHttpContextAccessor _httpContextAccessor; + private readonly FileConverter _fileConverter; + private readonly ApiDateTimeHelper _apiDateTimeHelper; + private readonly UserManager _userManager; + private readonly DisplayUserSettingsHelper _displayUserSettingsHelper; + public readonly SocketManager _socketManager; + public readonly IServiceProvider _serviceProvider; + private readonly ILog _logger; + private readonly IHttpClientFactory _clientFactory; + + /// + /// + /// + /// + public FilesControllerHelper( + ApiContext context, + FileStorageService fileStorageService, + FileWrapperHelper fileWrapperHelper, + FilesSettingsHelper filesSettingsHelper, + FilesLinkUtility filesLinkUtility, + FileUploader fileUploader, + DocumentServiceHelper documentServiceHelper, + TenantManager tenantManager, + SecurityContext securityContext, + FolderWrapperHelper folderWrapperHelper, + FileOperationWraperHelper fileOperationWraperHelper, + FileShareWrapperHelper fileShareWrapperHelper, + FileShareParamsHelper fileShareParamsHelper, + EntryManager entryManager, + FolderContentWrapperHelper folderContentWrapperHelper, + ChunkedUploadSessionHelper chunkedUploadSessionHelper, + DocumentServiceTrackerHelper documentServiceTracker, + IOptionsMonitor optionMonitor, + SettingsManager settingsManager, + EncryptionKeyPairHelper encryptionKeyPairHelper, + IHttpContextAccessor httpContextAccessor, + FileConverter fileConverter, + ApiDateTimeHelper apiDateTimeHelper, + UserManager userManager, + DisplayUserSettingsHelper displayUserSettingsHelper, + IServiceProvider serviceProvider, + SocketManager socketManager, + IHttpClientFactory clientFactory, + GlobalFolderHelper globalFolderHelper, + CoreBaseSettings coreBaseSettings, + FileUtility fileUtility) { - private readonly ApiContext ApiContext; - private readonly FileStorageService FileStorageService; - private readonly GlobalFolderHelper _globalFolderHelper; - private readonly CoreBaseSettings _coreBaseSettings; - private readonly FileUtility _fileUtility; + _apiContext = context; + _fileStorageService = fileStorageService; + _fileWrapperHelper = fileWrapperHelper; + _filesSettingsHelper = filesSettingsHelper; + _filesLinkUtility = filesLinkUtility; + _fileUploader = fileUploader; + _documentServiceHelper = documentServiceHelper; + _tenantManager = tenantManager; + _securityContext = securityContext; + _folderWrapperHelper = folderWrapperHelper; + _fileOperationWraperHelper = fileOperationWraperHelper; + _fileShareWrapperHelper = fileShareWrapperHelper; + _fileShareParamsHelper = fileShareParamsHelper; + _entryManager = entryManager; + _folderContentWrapperHelper = folderContentWrapperHelper; + _chunkedUploadSessionHelper = chunkedUploadSessionHelper; + _documentServiceTracker = documentServiceTracker; + _settingsManager = settingsManager; + _encryptionKeyPairHelper = encryptionKeyPairHelper; + _apiDateTimeHelper = apiDateTimeHelper; + _userManager = userManager; + _displayUserSettingsHelper = displayUserSettingsHelper; + _serviceProvider = serviceProvider; + _socketManager = socketManager; + _httpContextAccessor = httpContextAccessor; + _fileConverter = fileConverter; + _logger = optionMonitor.Get("ASC.Files"); + _clientFactory = clientFactory; + _globalFolderHelper = globalFolderHelper; + _fileUtility = fileUtility; + _coreBaseSettings = coreBaseSettings; + } - private FileWrapperHelper FileWrapperHelper { get; } - private FilesSettingsHelper FilesSettingsHelper { get; } - private FilesLinkUtility FilesLinkUtility { get; } - private FileUploader FileUploader { get; } - private DocumentServiceHelper DocumentServiceHelper { get; } - private TenantManager TenantManager { get; } - private SecurityContext SecurityContext { get; } - private FolderWrapperHelper FolderWrapperHelper { get; } - private FileOperationWraperHelper FileOperationWraperHelper { get; } - private FileShareWrapperHelper FileShareWrapperHelper { get; } - private FileShareParamsHelper FileShareParamsHelper { get; } - private EntryManager EntryManager { get; } - private FolderContentWrapperHelper FolderContentWrapperHelper { get; } - private ChunkedUploadSessionHelper ChunkedUploadSessionHelper { get; } - private DocumentServiceTrackerHelper DocumentServiceTracker { get; } - private SettingsManager SettingsManager { get; } - private EncryptionKeyPairHelper EncryptionKeyPairHelper { get; } - private IHttpContextAccessor HttpContextAccessor { get; } - private FileConverter FileConverter { get; } - private ApiDateTimeHelper ApiDateTimeHelper { get; } - private UserManager UserManager { get; } - private DisplayUserSettingsHelper DisplayUserSettingsHelper { get; } - public SocketManager SocketManager { get; } - public IServiceProvider ServiceProvider { get; } - private ILog Logger { get; set; } - private IHttpClientFactory ClientFactory { get; set; } + public async Task> GetRootFoldersIdsAsync(bool withoutTrash, bool withoutAdditionalFolder) + { + var IsVisitor = _userManager.GetUsers(_securityContext.CurrentAccount.ID).IsVisitor(_userManager); + var IsOutsider = _userManager.GetUsers(_securityContext.CurrentAccount.ID).IsOutsider(_userManager); + var folders = new SortedSet(); - /// - /// - /// - /// - public FilesControllerHelper( - ApiContext context, - FileStorageService fileStorageService, - FileWrapperHelper fileWrapperHelper, - FilesSettingsHelper filesSettingsHelper, - FilesLinkUtility filesLinkUtility, - FileUploader fileUploader, - DocumentServiceHelper documentServiceHelper, - TenantManager tenantManager, - SecurityContext securityContext, - FolderWrapperHelper folderWrapperHelper, - FileOperationWraperHelper fileOperationWraperHelper, - FileShareWrapperHelper fileShareWrapperHelper, - FileShareParamsHelper fileShareParamsHelper, - EntryManager entryManager, - FolderContentWrapperHelper folderContentWrapperHelper, - ChunkedUploadSessionHelper chunkedUploadSessionHelper, - DocumentServiceTrackerHelper documentServiceTracker, - IOptionsMonitor optionMonitor, - SettingsManager settingsManager, - EncryptionKeyPairHelper encryptionKeyPairHelper, - IHttpContextAccessor httpContextAccessor, - FileConverter fileConverter, - ApiDateTimeHelper apiDateTimeHelper, - UserManager userManager, - DisplayUserSettingsHelper displayUserSettingsHelper, - IServiceProvider serviceProvider, - SocketManager socketManager, - IHttpClientFactory clientFactory) + if (IsOutsider) { - ApiContext = context; - FileStorageService = fileStorageService; - FileWrapperHelper = fileWrapperHelper; - FilesSettingsHelper = filesSettingsHelper; - FilesLinkUtility = filesLinkUtility; - FileUploader = fileUploader; - DocumentServiceHelper = documentServiceHelper; - TenantManager = tenantManager; - SecurityContext = securityContext; - FolderWrapperHelper = folderWrapperHelper; - FileOperationWraperHelper = fileOperationWraperHelper; - FileShareWrapperHelper = fileShareWrapperHelper; - FileShareParamsHelper = fileShareParamsHelper; - EntryManager = entryManager; - FolderContentWrapperHelper = folderContentWrapperHelper; - ChunkedUploadSessionHelper = chunkedUploadSessionHelper; - DocumentServiceTracker = documentServiceTracker; - SettingsManager = settingsManager; - EncryptionKeyPairHelper = encryptionKeyPairHelper; - ApiDateTimeHelper = apiDateTimeHelper; - UserManager = userManager; - DisplayUserSettingsHelper = displayUserSettingsHelper; - ServiceProvider = serviceProvider; - SocketManager = socketManager; - HttpContextAccessor = httpContextAccessor; - FileConverter = fileConverter; - Logger = optionMonitor.Get("ASC.Files"); - ClientFactory = clientFactory; + withoutTrash = true; + withoutAdditionalFolder = true; } - public async Task> GetRootFoldersIdsAsync(bool withoutTrash, bool withoutAdditionalFolder) + if (!IsVisitor) { - var IsVisitor = UserManager.GetUsers(SecurityContext.CurrentAccount.ID).IsVisitor(UserManager); - var IsOutsider = UserManager.GetUsers(SecurityContext.CurrentAccount.ID).IsOutsider(UserManager); - var folders = new SortedSet(); - - if (IsOutsider) - { - withoutTrash = true; - withoutAdditionalFolder = true; - } - - if (!IsVisitor) - { - folders.Add(_globalFolderHelper.FolderMy); - } - - if (!_coreBaseSettings.Personal && ! UserManager.GetUsers(SecurityContext.CurrentAccount.ID).IsOutsider(UserManager)) - { - folders.Add(await _globalFolderHelper.FolderShareAsync); - } - - if (!IsVisitor && !withoutAdditionalFolder) - { - if (FilesSettingsHelper.FavoritesSection) - { - folders.Add(await _globalFolderHelper.FolderFavoritesAsync); - } - if (FilesSettingsHelper.RecentSection) - { - folders.Add(await _globalFolderHelper.FolderRecentAsync); - } - - if (!_coreBaseSettings.Personal && PrivacyRoomSettings.IsAvailable(TenantManager)) - { - folders.Add(await _globalFolderHelper.FolderPrivacyAsync); - } - } - - if (!_coreBaseSettings.Personal) - { - folders.Add(await _globalFolderHelper.FolderCommonAsync); - } - - if (!IsVisitor - && !withoutAdditionalFolder - && _fileUtility.ExtsWebTemplate.Count > 0 - && FilesSettingsHelper.TemplatesSection) - { - folders.Add(await _globalFolderHelper.FolderTemplatesAsync); - } - - if (!withoutTrash) - { - folders.Add((int)_globalFolderHelper.FolderTrash); - } - - return folders; + folders.Add(_globalFolderHelper.FolderMy); } - public async Task> GetFolderAsync(T folderId, Guid userIdOrGroupId, FilterType filterType, bool withSubFolders) + if (!_coreBaseSettings.Personal && !_userManager.GetUsers(_securityContext.CurrentAccount.ID).IsOutsider(_userManager)) { - var folderContentWrapper = await ToFolderContentWrapperAsync(folderId, userIdOrGroupId, filterType, withSubFolders); - return folderContentWrapper.NotFoundIfNull(); + folders.Add(await _globalFolderHelper.FolderShareAsync); } - public async Task UploadFileAsync(T folderId, UploadModel uploadModel) + if (!IsVisitor && !withoutAdditionalFolder) { - if (uploadModel.StoreOriginalFileFlag.HasValue) + if (_filesSettingsHelper.FavoritesSection) { - FilesSettingsHelper.StoreOriginalFiles = uploadModel.StoreOriginalFileFlag.Value; + folders.Add(await _globalFolderHelper.FolderFavoritesAsync); + } + if (_filesSettingsHelper.RecentSection) + { + folders.Add(await _globalFolderHelper.FolderRecentAsync); } - IEnumerable files = HttpContextAccessor.HttpContext.Request.Form.Files; - if (files == null || !files.Any()) + if (!_coreBaseSettings.Personal && PrivacyRoomSettings.IsAvailable(_tenantManager)) { - files = uploadModel.Files; + folders.Add(await _globalFolderHelper.FolderPrivacyAsync); + } + } + + if (!_coreBaseSettings.Personal) + { + folders.Add(await _globalFolderHelper.FolderCommonAsync); + } + + if (!IsVisitor + && !withoutAdditionalFolder + && _fileUtility.ExtsWebTemplate.Count > 0 + && _filesSettingsHelper.TemplatesSection) + { + folders.Add(await _globalFolderHelper.FolderTemplatesAsync); + } + + if (!withoutTrash) + { + folders.Add((int)_globalFolderHelper.FolderTrash); + } + + return folders; + } + + public async Task> GetFolderAsync(T folderId, Guid userIdOrGroupId, FilterType filterType, bool withSubFolders) + { + var folderContentWrapper = await ToFolderContentWrapperAsync(folderId, userIdOrGroupId, filterType, withSubFolders); + + return folderContentWrapper.NotFoundIfNull(); + } + + public async Task UploadFileAsync(T folderId, UploadModel uploadModel) + { + if (uploadModel.StoreOriginalFileFlag.HasValue) + { + _filesSettingsHelper.StoreOriginalFiles = uploadModel.StoreOriginalFileFlag.Value; + } + + IEnumerable files = _httpContextAccessor.HttpContext.Request.Form.Files; + if (files == null || !files.Any()) + { + files = uploadModel.Files; + } + + if (files != null && files.Any()) + { + if (files.Count() == 1) + { + //Only one file. return it + var postedFile = files.First(); + + return await InsertFileAsync(folderId, postedFile.OpenReadStream(), postedFile.FileName, uploadModel.CreateNewIfExist, uploadModel.KeepConvertStatus); } - if (files != null && files.Any()) + //For case with multiple files + var result = new List(); + + foreach (var postedFile in uploadModel.Files) { - if (files.Count() == 1) - { - //Only one file. return it - var postedFile = files.First(); - return await InsertFileAsync(folderId, postedFile.OpenReadStream(), postedFile.FileName, uploadModel.CreateNewIfExist, uploadModel.KeepConvertStatus); - } - - //For case with multiple files - var result = new List(); - - foreach (var postedFile in uploadModel.Files) - { - result.Add(await InsertFileAsync(folderId, postedFile.OpenReadStream(), postedFile.FileName, uploadModel.CreateNewIfExist, uploadModel.KeepConvertStatus)); + result.Add(await InsertFileAsync(folderId, postedFile.OpenReadStream(), postedFile.FileName, uploadModel.CreateNewIfExist, uploadModel.KeepConvertStatus)); } - return result; + return result; + } + + if (uploadModel.File != null) + { + var fileName = "file" + MimeMapping.GetExtention(uploadModel.ContentType.MediaType); + if (uploadModel.ContentDisposition != null) + { + fileName = uploadModel.ContentDisposition.FileName; } - if (uploadModel.File != null) + return new List> { - var fileName = "file" + MimeMapping.GetExtention(uploadModel.ContentType.MediaType); - if (uploadModel.ContentDisposition != null) - { - fileName = uploadModel.ContentDisposition.FileName; - } + await InsertFileAsync(folderId, uploadModel.File.OpenReadStream(), fileName, uploadModel.CreateNewIfExist, uploadModel.KeepConvertStatus) + }; + } - return new List> + throw new InvalidOperationException("No input files"); + } + + public async Task> InsertFileAsync(T folderId, Stream file, string title, bool? createNewIfExist, bool keepConvertStatus = false) + { + try + { + var resultFile = await _fileUploader.ExecAsync(folderId, title, file.Length, file, createNewIfExist ?? !_filesSettingsHelper.UpdateIfExist, !keepConvertStatus); + + await _socketManager.CreateFileAsync(resultFile); + + return await _fileWrapperHelper.GetAsync(resultFile); + } + catch (FileNotFoundException e) + { + throw new ItemNotFoundException("File not found", e); + } + catch (DirectoryNotFoundException e) + { + throw new ItemNotFoundException("Folder not found", e); + } + } + + public async Task> UpdateFileStreamAsync(Stream file, T fileId, string fileExtension, bool encrypted = false, bool forcesave = false) + { + try + { + var resultFile = await _fileStorageService.UpdateFileStreamAsync(fileId, file, fileExtension, encrypted, forcesave); + + return await _fileWrapperHelper.GetAsync(resultFile); + } + catch (FileNotFoundException e) + { + throw new ItemNotFoundException("File not found", e); + } + } + + public async Task> SaveEditingAsync(T fileId, string fileExtension, string downloadUri, Stream stream, string doc, bool forcesave) + { + return await _fileWrapperHelper.GetAsync(await _fileStorageService.SaveEditingAsync(fileId, fileExtension, downloadUri, stream, doc, forcesave)); + } + + public Task StartEditAsync(T fileId, bool editingAlone, string doc) + { + return _fileStorageService.StartEditAsync(fileId, editingAlone, doc); + } + + public Task> TrackEditFileAsync(T fileId, Guid tabId, string docKeyForTrack, string doc, bool isFinish) + { + return _fileStorageService.TrackEditFileAsync(fileId, tabId, docKeyForTrack, doc, isFinish); + } + + public async Task> OpenEditAsync(T fileId, int version, string doc, bool view) + { + var docParams = await _documentServiceHelper.GetParamsAsync(fileId, version, doc, true, !view, true); + var configuration = docParams.Configuration; + + configuration.EditorType = EditorType.External; + if (configuration.EditorConfig.ModeWrite) + { + configuration.EditorConfig.CallbackUrl = _documentServiceTracker.GetCallbackUrl(configuration.Document.Info.GetFile().ID.ToString()); + } + + if (configuration.Document.Info.GetFile().RootFolderType == FolderType.Privacy && PrivacyRoomSettings.GetEnabled(_settingsManager)) + { + var keyPair = _encryptionKeyPairHelper.GetKeyPair(); + if (keyPair != null) + { + configuration.EditorConfig.EncryptionKeys = new EncryptionKeysConfig { - await InsertFileAsync(folderId, uploadModel.File.OpenReadStream(), fileName, uploadModel.CreateNewIfExist, uploadModel.KeepConvertStatus) + PrivateKeyEnc = keyPair.PrivateKeyEnc, + PublicKey = keyPair.PublicKey, }; } - - throw new InvalidOperationException("No input files"); } - public async Task> InsertFileAsync(T folderId, Stream file, string title, bool? createNewIfExist, bool keepConvertStatus = false) + if (!configuration.Document.Info.GetFile().Encrypted && !configuration.Document.Info.GetFile().ProviderEntry) _entryManager.MarkAsRecent(configuration.Document.Info.GetFile()); + + configuration.Token = _documentServiceHelper.GetSignature(configuration); + + return configuration; + } + + public async Task CreateUploadSessionAsync(T folderId, string fileName, long fileSize, string relativePath, ApiDateTime lastModified, bool encrypted) + { + var file = await _fileUploader.VerifyChunkedUploadAsync(folderId, fileName, fileSize, _filesSettingsHelper.UpdateIfExist, lastModified, relativePath); + + if (_filesLinkUtility.IsLocalFileUploader) { - try - { - var resultFile = await FileUploader.ExecAsync(folderId, title, file.Length, file, createNewIfExist ?? !FilesSettingsHelper.UpdateIfExist, !keepConvertStatus); + var session = await _fileUploader.InitiateUploadAsync(file.FolderID, file.ID ?? default, file.Title, file.ContentLength, encrypted); - await SocketManager.CreateFileAsync(resultFile); + var responseObject = await _chunkedUploadSessionHelper.ToResponseObjectAsync(session, true); - return await FileWrapperHelper.GetAsync(resultFile); - } - catch (FileNotFoundException e) + return new { - throw new ItemNotFoundException("File not found", e); - } - catch (DirectoryNotFoundException e) + success = true, + data = responseObject + }; + } + + var createSessionUrl = _filesLinkUtility.GetInitiateUploadSessionUrl(_tenantManager.GetCurrentTenant().Id, file.FolderID, file.ID, file.Title, file.ContentLength, encrypted, _securityContext); + + var httpClient = _clientFactory.CreateClient(); + + var request = new HttpRequestMessage(); + request.RequestUri = new Uri(createSessionUrl); + request.Method = HttpMethod.Post; + + // hack for uploader.onlyoffice.com in api requests + var rewriterHeader = _apiContext.HttpContextAccessor.HttpContext.Request.Headers[HttpRequestExtensions.UrlRewriterHeader]; + if (!string.IsNullOrEmpty(rewriterHeader)) + { + request.Headers.Add(HttpRequestExtensions.UrlRewriterHeader, rewriterHeader.ToString()); + } + + using var response = await httpClient.SendAsync(request); + using var responseStream = await response.Content.ReadAsStreamAsync(); + using var streamReader = new StreamReader(responseStream); + + return JObject.Parse(await streamReader.ReadToEndAsync()); //result is json string + } + + public Task> CreateTextFileAsync(T folderId, string title, string content) + { + if (title == null) + { + throw new ArgumentNullException(nameof(title)); + } + + //Try detect content + var extension = ".txt"; + if (!string.IsNullOrEmpty(content)) + { + if (Regex.IsMatch(content, @"<([^\s>]*)(\s[^<]*)>")) { - throw new ItemNotFoundException("Folder not found", e); + extension = ".html"; } } - public async Task> UpdateFileStreamAsync(Stream file, T fileId, string fileExtension, bool encrypted = false, bool forcesave = false) + return CreateFileAsync(folderId, title, content, extension); + } + + private async Task> CreateFileAsync(T folderId, string title, string content, string extension) + { + using var memStream = new MemoryStream(Encoding.UTF8.GetBytes(content)); + var file = await _fileUploader.ExecAsync(folderId, + title.EndsWith(extension, StringComparison.OrdinalIgnoreCase) ? title : (title + extension), + memStream.Length, memStream); + + return await _fileWrapperHelper.GetAsync(file); + } + + public Task> CreateHtmlFileAsync(T folderId, string title, string content) + { + if (title == null) { - try - { - var resultFile = await FileStorageService.UpdateFileStreamAsync(fileId, file, fileExtension, encrypted, forcesave); - return await FileWrapperHelper.GetAsync(resultFile); - } - catch (FileNotFoundException e) - { - throw new ItemNotFoundException("File not found", e); - } + throw new ArgumentNullException(nameof(title)); } - public async Task> SaveEditingAsync(T fileId, string fileExtension, string downloadUri, Stream stream, string doc, bool forcesave) + return CreateFileAsync(folderId, title, content, ".html"); + } + + public async Task> CreateFolderAsync(T folderId, string title) + { + var folder = await _fileStorageService.CreateNewFolderAsync(folderId, title); + + return await _folderWrapperHelper.GetAsync(folder); + } + + public async Task> CreateFileAsync(T folderId, string title, JsonElement templateId, bool enableExternalExt = false) + { + File file; + + if (templateId.ValueKind == JsonValueKind.Number) { - return await FileWrapperHelper.GetAsync(await FileStorageService.SaveEditingAsync(fileId, fileExtension, downloadUri, stream, doc, forcesave)); + file = await _fileStorageService.CreateNewFileAsync(new FileModel { ParentId = folderId, Title = title, TemplateId = templateId.GetInt32() }, enableExternalExt); + } + else if (templateId.ValueKind == JsonValueKind.String) + { + file = await _fileStorageService.CreateNewFileAsync(new FileModel { ParentId = folderId, Title = title, TemplateId = templateId.GetString() }, enableExternalExt); + } + else + { + file = await _fileStorageService.CreateNewFileAsync(new FileModel { ParentId = folderId, Title = title, TemplateId = 0 }, enableExternalExt); } - public Task StartEditAsync(T fileId, bool editingAlone, string doc) + return await _fileWrapperHelper.GetAsync(file); + } + + public async Task> RenameFolderAsync(T folderId, string title) + { + var folder = await _fileStorageService.FolderRenameAsync(folderId, title); + + return await _folderWrapperHelper.GetAsync(folder); + } + + public async Task> GetFolderInfoAsync(T folderId) + { + var folder = await _fileStorageService.GetFolderAsync(folderId).NotFoundIfNull("Folder not found"); + + return await _folderWrapperHelper.GetAsync(folder); + } + + public async IAsyncEnumerable GetFolderPathAsync(T folderId) + { + var breadCrumbs = await _entryManager.GetBreadCrumbsAsync(folderId); + + foreach (var e in breadCrumbs) { - return FileStorageService.StartEditAsync(fileId, editingAlone, doc); + yield return await GetFileEntryWrapperAsync(e); + } + } + + public async Task> GetFileInfoAsync(T fileId, int version = -1) + { + var file = await _fileStorageService.GetFileAsync(fileId, version); + file = file.NotFoundIfNull("File not found"); + + return await _fileWrapperHelper.GetAsync(file); + } + + public async Task> CopyFileAsAsync(T fileId, TTemplate destFolderId, string destTitle, string password = null) + { + var service = _serviceProvider.GetService>(); + var controller = _serviceProvider.GetService>(); + var file = await _fileStorageService.GetFileAsync(fileId, -1); + var ext = FileUtility.GetFileExtension(file.Title); + var destExt = FileUtility.GetFileExtension(destTitle); + + if (ext == destExt) + { + var newFile = await service.CreateNewFileAsync(new FileModel { ParentId = destFolderId, Title = destTitle, TemplateId = fileId }, false); + + return await _fileWrapperHelper.GetAsync(newFile); } - public Task> TrackEditFileAsync(T fileId, Guid tabId, string docKeyForTrack, string doc, bool isFinish) + using (var fileStream = await _fileConverter.ExecAsync(file, destExt, password)) { - return FileStorageService.TrackEditFileAsync(fileId, tabId, docKeyForTrack, doc, isFinish); + return await controller.InsertFileAsync(destFolderId, fileStream, destTitle, true); + } + } + + public async Task> AddToRecentAsync(T fileId, int version = -1) + { + var file = await _fileStorageService.GetFileAsync(fileId, version).NotFoundIfNull("File not found"); + _entryManager.MarkAsRecent(file); + + return await _fileWrapperHelper.GetAsync(file); + } + + public async Task> GetNewItemsAsync(T folderId) + { + var newItems = await _fileStorageService.GetNewItemsAsync(folderId); + var result = new List(); + + foreach (var e in newItems) + { + result.Add(await GetFileEntryWrapperAsync(e)); } - public async Task> OpenEditAsync(T fileId, int version, string doc, bool view) - { - var docParams = await DocumentServiceHelper.GetParamsAsync(fileId, version, doc, true, !view, true); - var configuration = docParams.Configuration; + return result; + } - configuration.EditorType = EditorType.External; - if (configuration.EditorConfig.ModeWrite) + public async Task> UpdateFileAsync(T fileId, string title, int lastVersion) + { + if (!string.IsNullOrEmpty(title)) + { + await _fileStorageService.FileRenameAsync(fileId, title); + } + + if (lastVersion > 0) + { + await _fileStorageService.UpdateToVersionAsync(fileId, lastVersion); + } + + return await GetFileInfoAsync(fileId); + } + + public async Task> DeleteFileAsync(T fileId, bool deleteAfter, bool immediately) + { + var result = new List(); + + foreach (var e in _fileStorageService.DeleteFile("delete", fileId, false, deleteAfter, immediately)) + { + result.Add(await _fileOperationWraperHelper.GetAsync(e)); + } + + return result; + } + public IAsyncEnumerable> StartConversionAsync(CheckConversionModel model) + { + model.StartConvert = true; + return CheckConversionAsync(model); + } + + public async IAsyncEnumerable> CheckConversionAsync(CheckConversionModel model) + { + var checkConversaion = _fileStorageService.CheckConversionAsync(new List>() { model }, model.Sync); + + await foreach (var r in checkConversaion) + { + var o = new ConversationResult { - configuration.EditorConfig.CallbackUrl = DocumentServiceTracker.GetCallbackUrl(configuration.Document.Info.GetFile().ID.ToString()); - } + Id = r.Id, + Error = r.Error, + OperationType = r.OperationType, + Processed = r.Processed, + Progress = r.Progress, + Source = r.Source, + }; - if (configuration.Document.Info.GetFile().RootFolderType == FolderType.Privacy && PrivacyRoomSettings.GetEnabled(SettingsManager)) + if (!string.IsNullOrEmpty(r.Result)) { - var keyPair = EncryptionKeyPairHelper.GetKeyPair(); - if (keyPair != null) + try { - configuration.EditorConfig.EncryptionKeys = new EncryptionKeysConfig + var options = new JsonSerializerOptions { - PrivateKeyEnc = keyPair.PrivateKeyEnc, - PublicKey = keyPair.PublicKey, + AllowTrailingCommas = true, + PropertyNameCaseInsensitive = true }; + var jResult = JsonSerializer.Deserialize>(r.Result, options); + o.File = await GetFileInfoAsync(jResult.Id, jResult.Version); + } + catch (Exception e) + { + o.File = r.Result; + _logger.Error(e); } } - if (!configuration.Document.Info.GetFile().Encrypted && !configuration.Document.Info.GetFile().ProviderEntry) EntryManager.MarkAsRecent(configuration.Document.Info.GetFile()); + yield return o; + } + } - configuration.Token = DocumentServiceHelper.GetSignature(configuration); - return configuration; + public Task CheckFillFormDraftAsync(T fileId, int version, string doc, bool editPossible, bool view) + { + return _fileStorageService.CheckFillFormDraftAsync(fileId, version, doc, editPossible, view); + } + + public async Task> DeleteFolder(T folderId, bool deleteAfter, bool immediately) + { + var result = new List(); + + foreach (var e in _fileStorageService.DeleteFolder("delete", folderId, false, deleteAfter, immediately)) + { + result.Add(await _fileOperationWraperHelper.GetAsync(e)); } - public async Task CreateUploadSessionAsync(T folderId, string fileName, long fileSize, string relativePath, ApiDateTime lastModified, bool encrypted) - { - var file = await FileUploader.VerifyChunkedUploadAsync(folderId, fileName, fileSize, FilesSettingsHelper.UpdateIfExist, lastModified, relativePath); + return result; + } - if (FilesLinkUtility.IsLocalFileUploader) + public async IAsyncEnumerable MoveOrCopyBatchCheckAsync(BatchModel batchModel) + { + List checkedFiles; + List checkedFolders; + + if (batchModel.DestFolderId.ValueKind == JsonValueKind.Number) + { + (checkedFiles, checkedFolders) = await _fileStorageService.MoveOrCopyFilesCheckAsync(batchModel.FileIds.ToList(), batchModel.FolderIds.ToList(), batchModel.DestFolderId.GetInt32()); + } + else + { + (checkedFiles, checkedFolders) = await _fileStorageService.MoveOrCopyFilesCheckAsync(batchModel.FileIds.ToList(), batchModel.FolderIds.ToList(), batchModel.DestFolderId.GetString()); + } + + var entries = await _fileStorageService.GetItemsAsync(checkedFiles.OfType().Select(Convert.ToInt32), checkedFiles.OfType().Select(Convert.ToInt32), FilterType.FilesOnly, false, "", ""); + + entries.AddRange(await _fileStorageService.GetItemsAsync(checkedFiles.OfType(), checkedFiles.OfType(), FilterType.FilesOnly, false, "", "")); + + foreach (var e in entries) + { + yield return await GetFileEntryWrapperAsync(e); + } + } + + public async Task> MoveBatchItemsAsync(BatchModel batchModel) + { + var result = new List(); + + foreach (var e in _fileStorageService.MoveOrCopyItems(batchModel.FolderIds.ToList(), batchModel.FileIds.ToList(), batchModel.DestFolderId, batchModel.ConflictResolveType, false, batchModel.DeleteAfter)) + { + result.Add(await _fileOperationWraperHelper.GetAsync(e)); + } + + return result; + } + + public async Task> CopyBatchItemsAsync(BatchModel batchModel) + { + var result = new List(); + + foreach (var e in _fileStorageService.MoveOrCopyItems(batchModel.FolderIds.ToList(), batchModel.FileIds.ToList(), batchModel.DestFolderId, batchModel.ConflictResolveType, true, batchModel.DeleteAfter)) + { + result.Add(await _fileOperationWraperHelper.GetAsync(e)); + } + + return result; + } + + public async Task> MarkAsReadAsync(BaseBatchModel model) + { + var result = new List(); + + foreach (var e in _fileStorageService.MarkAsRead(model.FolderIds.ToList(), model.FileIds.ToList())) + { + result.Add(await _fileOperationWraperHelper.GetAsync(e)); + } + + return result; + } + + public async Task> TerminateTasksAsync() + { + var result = new List(); + + foreach (var e in _fileStorageService.TerminateTasks()) + { + result.Add(await _fileOperationWraperHelper.GetAsync(e)); + } + + return result; + } + + public async Task> GetOperationStatusesAsync() + { + var result = new List(); + + foreach (var e in _fileStorageService.GetTasksStatuses()) + { + result.Add(await _fileOperationWraperHelper.GetAsync(e)); + } + + return result; + } + + public async Task> BulkDownloadAsync(DownloadModel model) + { + var folders = new Dictionary(); + var files = new Dictionary(); + + foreach (var fileId in model.FileConvertIds.Where(fileId => !files.ContainsKey(fileId.Key))) + { + files.Add(fileId.Key, fileId.Value); + } + + foreach (var fileId in model.FileIds.Where(fileId => !files.ContainsKey(fileId))) + { + files.Add(fileId, string.Empty); + } + + foreach (var folderId in model.FolderIds.Where(folderId => !folders.ContainsKey(folderId))) + { + folders.Add(folderId, string.Empty); + } + + var result = new List(); + + foreach (var e in _fileStorageService.BulkDownload(folders, files)) + { + result.Add(await _fileOperationWraperHelper.GetAsync(e)); + } + + return result; + } + + public async Task> EmptyTrashAsync() + { + var emptyTrash = await _fileStorageService.EmptyTrashAsync(); + var result = new List(); + + foreach (var e in emptyTrash) + { + result.Add(await _fileOperationWraperHelper.GetAsync(e)); + } + + return result; + } + + public async Task>> GetFileVersionInfoAsync(T fileId) + { + var files = await _fileStorageService.GetFileHistoryAsync(fileId); + var result = new List>(); + + foreach (var e in files) + { + result.Add(await _fileWrapperHelper.GetAsync(e)); + } + + return result; + } + + public async Task>> ChangeHistoryAsync(T fileId, int version, bool continueVersion) + { + var pair = await _fileStorageService.CompleteVersionAsync(fileId, version, continueVersion); + var history = pair.Value; + + var result = new List>(); + + foreach (var e in history) + { + result.Add(await _fileWrapperHelper.GetAsync(e)); + } + + return result; + } + + public async Task> LockFileAsync(T fileId, bool lockFile) + { + var result = await _fileStorageService.LockFileAsync(fileId, lockFile); + return await _fileWrapperHelper.GetAsync(result); + } + + public Task GetPresignedUriAsync(T fileId) + { + return _fileStorageService.GetPresignedUriAsync(fileId); + } + + public async Task> GetEditHistoryAsync(T fileId, string doc = null) + { + var result = await _fileStorageService.GetEditHistoryAsync(fileId, doc); + + return result.Select(r => new EditHistoryWrapper(r, _apiDateTimeHelper, _userManager, _displayUserSettingsHelper)).ToList(); + } + + public Task GetEditDiffUrlAsync(T fileId, int version = 0, string doc = null) + { + return _fileStorageService.GetEditDiffUrlAsync(fileId, version, doc); + } + + public async Task> RestoreVersionAsync(T fileId, int version = 0, string url = null, string doc = null) + { + var result = await _fileStorageService.RestoreVersionAsync(fileId, version, url, doc); + + return result.Select(r => new EditHistoryWrapper(r, _apiDateTimeHelper, _userManager, _displayUserSettingsHelper)).ToList(); + } + + public Task UpdateCommentAsync(T fileId, int version, string comment) + { + return _fileStorageService.UpdateCommentAsync(fileId, version, comment); + } + + public Task> GetFileSecurityInfoAsync(T fileId) + { + return GetSecurityInfoAsync(new List { fileId }, new List { }); + } + + public Task> GetFolderSecurityInfoAsync(T folderId) + { + return GetSecurityInfoAsync(new List { }, new List { folderId }); + } + + public async IAsyncEnumerable GetFoldersAsync(T folderId) + { + var folders = await _fileStorageService.GetFoldersAsync(folderId); + foreach (var folder in folders) + { + yield return await GetFileEntryWrapperAsync(folder); + } + } + + public async Task> GetSecurityInfoAsync(IEnumerable fileIds, IEnumerable folderIds) + { + var fileShares = await _fileStorageService.GetSharedInfoAsync(fileIds, folderIds); + + return fileShares.Select(_fileShareWrapperHelper.Get).ToList(); + } + + public Task> SetFileSecurityInfoAsync(T fileId, IEnumerable share, bool notify, string sharingMessage) + { + return SetSecurityInfoAsync(new List { fileId }, new List(), share, notify, sharingMessage); + } + + public Task> SetFolderSecurityInfoAsync(T folderId, IEnumerable share, bool notify, string sharingMessage) + { + return SetSecurityInfoAsync(new List(), new List { folderId }, share, notify, sharingMessage); + } + + public async Task> SetSecurityInfoAsync(IEnumerable fileIds, IEnumerable folderIds, IEnumerable share, bool notify, string sharingMessage) + { + if (share != null && share.Any()) + { + var list = new List(share.Select(_fileShareParamsHelper.ToAceObject)); + var aceCollection = new AceCollection { - var session = await FileUploader.InitiateUploadAsync(file.FolderID, file.ID ?? default, file.Title, file.ContentLength, encrypted); - - var responseObject = await ChunkedUploadSessionHelper.ToResponseObjectAsync(session, true); - return new - { - success = true, - data = responseObject - }; - } - - var createSessionUrl = FilesLinkUtility.GetInitiateUploadSessionUrl(TenantManager.GetCurrentTenant().Id, file.FolderID, file.ID, file.Title, file.ContentLength, encrypted, SecurityContext); - - var httpClient = ClientFactory.CreateClient(); - - var request = new HttpRequestMessage(); - request.RequestUri = new Uri(createSessionUrl); - request.Method = HttpMethod.Post; - - // hack for uploader.onlyoffice.com in api requests - var rewriterHeader = ApiContext.HttpContextAccessor.HttpContext.Request.Headers[HttpRequestExtensions.UrlRewriterHeader]; - if (!string.IsNullOrEmpty(rewriterHeader)) - { - request.Headers.Add(HttpRequestExtensions.UrlRewriterHeader, rewriterHeader.ToString()); - } - - using var response = await httpClient.SendAsync(request); - using var responseStream = await response.Content.ReadAsStreamAsync(); - using var streamReader = new StreamReader(responseStream); - return JObject.Parse(await streamReader.ReadToEndAsync()); //result is json string + Files = fileIds, + Folders = folderIds, + Aces = list, + Message = sharingMessage + }; + await _fileStorageService.SetAceObjectAsync(aceCollection, notify); } - public Task> CreateTextFileAsync(T folderId, string title, string content) + return await GetSecurityInfoAsync(fileIds, folderIds); + } + + public async Task RemoveSecurityInfoAsync(List fileIds, List folderIds) + { + await _fileStorageService.RemoveAceAsync(fileIds, folderIds); + + return true; + } + + public async Task GenerateSharedLinkAsync(T fileId, FileShare share) + { + var file = await GetFileInfoAsync(fileId); + + var tmpInfo = await _fileStorageService.GetSharedInfoAsync(new List { fileId }, new List { }); + var sharedInfo = tmpInfo.Find(r => r.SubjectId == FileConstant.ShareLinkId); + + if (sharedInfo == null || sharedInfo.Share != share) { - if (title == null) throw new ArgumentNullException(nameof(title)); - //Try detect content - var extension = ".txt"; - if (!string.IsNullOrEmpty(content)) - { - if (Regex.IsMatch(content, @"<([^\s>]*)(\s[^<]*)>")) - { - extension = ".html"; - } - } - return CreateFileAsync(folderId, title, content, extension); - } - - private async Task> CreateFileAsync(T folderId, string title, string content, string extension) - { - using var memStream = new MemoryStream(Encoding.UTF8.GetBytes(content)); - var file = await FileUploader.ExecAsync(folderId, - title.EndsWith(extension, StringComparison.OrdinalIgnoreCase) ? title : (title + extension), - memStream.Length, memStream); - return await FileWrapperHelper.GetAsync(file); - } - - public Task> CreateHtmlFileAsync(T folderId, string title, string content) - { - if (title == null) throw new ArgumentNullException(nameof(title)); - return CreateFileAsync(folderId, title, content, ".html"); - } - - public async Task> CreateFolderAsync(T folderId, string title) - { - var folder = await FileStorageService.CreateNewFolderAsync(folderId, title); - - return await FolderWrapperHelper.GetAsync(folder); - } - - public async Task> CreateFileAsync(T folderId, string title, JsonElement templateId, bool enableExternalExt = false) - { - File file; - - if (templateId.ValueKind == JsonValueKind.Number) - { - file = await FileStorageService.CreateNewFileAsync(new FileModel { ParentId = folderId, Title = title, TemplateId = templateId.GetInt32() }, enableExternalExt); - } - else if (templateId.ValueKind == JsonValueKind.String) - { - file = await FileStorageService.CreateNewFileAsync(new FileModel { ParentId = folderId, Title = title, TemplateId = templateId.GetString() }, enableExternalExt); - } - else - { - file = await FileStorageService.CreateNewFileAsync(new FileModel { ParentId = folderId, Title = title, TemplateId = 0 }, enableExternalExt); - } - - return await FileWrapperHelper.GetAsync(file); - } - - public async Task> RenameFolderAsync(T folderId, string title) - { - var folder = await FileStorageService.FolderRenameAsync(folderId, title); - return await FolderWrapperHelper.GetAsync(folder); - } - - public async Task> GetFolderInfoAsync(T folderId) - { - var folder = await FileStorageService.GetFolderAsync(folderId).NotFoundIfNull("Folder not found"); - - return await FolderWrapperHelper.GetAsync(folder); - } - - public async IAsyncEnumerable GetFolderPathAsync(T folderId) - { - var breadCrumbs = await EntryManager.GetBreadCrumbsAsync(folderId); - - foreach (var e in breadCrumbs) - { - yield return await GetFileEntryWrapperAsync(e); - } - } - - public async Task> GetFileInfoAsync(T fileId, int version = -1) - { - var file = await FileStorageService.GetFileAsync(fileId, version); - file = file.NotFoundIfNull("File not found"); - return await FileWrapperHelper.GetAsync(file); - } - - public async Task> CopyFileAsAsync(T fileId, TTemplate destFolderId, string destTitle, string password = null) - { - var service = ServiceProvider.GetService>(); - var controller = ServiceProvider.GetService>(); - var file = await FileStorageService.GetFileAsync(fileId, -1); - var ext = FileUtility.GetFileExtension(file.Title); - var destExt = FileUtility.GetFileExtension(destTitle); - - if (ext == destExt) - { - var newFile = await service.CreateNewFileAsync(new FileModel { ParentId = destFolderId, Title = destTitle, TemplateId = fileId }, false); - return await FileWrapperHelper.GetAsync(newFile); - } - - using (var fileStream = await FileConverter.ExecAsync(file, destExt, password)) - { - return await controller.InsertFileAsync(destFolderId, fileStream, destTitle, true); - } - } - - public async Task> AddToRecentAsync(T fileId, int version = -1) - { - var file = await FileStorageService.GetFileAsync(fileId, version).NotFoundIfNull("File not found"); - EntryManager.MarkAsRecent(file); - return await FileWrapperHelper.GetAsync(file); - } - - public async Task> GetNewItemsAsync(T folderId) - { - var newItems = await FileStorageService.GetNewItemsAsync(folderId); - var result = new List(); - - foreach (var e in newItems) - { - result.Add(await GetFileEntryWrapperAsync(e)); - } - - return result; - } - - public async Task> UpdateFileAsync(T fileId, string title, int lastVersion) - { - if (!string.IsNullOrEmpty(title)) - await FileStorageService.FileRenameAsync(fileId, title); - - if (lastVersion > 0) - await FileStorageService.UpdateToVersionAsync(fileId, lastVersion); - - return await GetFileInfoAsync(fileId); - } - - public async Task> DeleteFileAsync(T fileId, bool deleteAfter, bool immediately) - { - var result = new List(); - - foreach (var e in FileStorageService.DeleteFile("delete", fileId, false, deleteAfter, immediately)) - { - result.Add(await FileOperationWraperHelper.GetAsync(e)); - } - - return result; - } - public IAsyncEnumerable> StartConversionAsync(CheckConversionModel model) - { - model.StartConvert = true; - return CheckConversionAsync(model); - } - - public async IAsyncEnumerable> CheckConversionAsync(CheckConversionModel model) - { - var checkConversaion = FileStorageService.CheckConversionAsync(new List>() { model }, model.Sync); - - await foreach (var r in checkConversaion) - { - var o = new ConversationResult - { - Id = r.Id, - Error = r.Error, - OperationType = r.OperationType, - Processed = r.Processed, - Progress = r.Progress, - Source = r.Source, - }; - - if (!string.IsNullOrEmpty(r.Result)) - { - try - { - var options = new JsonSerializerOptions - { - AllowTrailingCommas = true, - PropertyNameCaseInsensitive = true - }; - var jResult = JsonSerializer.Deserialize>(r.Result, options); - o.File = await GetFileInfoAsync(jResult.Id, jResult.Version); - } - catch (Exception e) - { - o.File = r.Result; - Logger.Error(e); - } - } - yield return o; - } - } - - public Task CheckFillFormDraftAsync(T fileId, int version, string doc, bool editPossible, bool view) - { - return FileStorageService.CheckFillFormDraftAsync(fileId, version, doc, editPossible, view); - } - - public async Task> DeleteFolder(T folderId, bool deleteAfter, bool immediately) - { - var result = new List(); - - foreach (var e in FileStorageService.DeleteFolder("delete", folderId, false, deleteAfter, immediately)) - { - result.Add(await FileOperationWraperHelper.GetAsync(e)); - } - - return result; - } - - public async IAsyncEnumerable MoveOrCopyBatchCheckAsync(BatchModel batchModel) - { - List checkedFiles; - List checkedFolders; - - if (batchModel.DestFolderId.ValueKind == JsonValueKind.Number) - { - (checkedFiles, checkedFolders) = await FileStorageService.MoveOrCopyFilesCheckAsync(batchModel.FileIds.ToList(), batchModel.FolderIds.ToList(), batchModel.DestFolderId.GetInt32()); - } - else - { - (checkedFiles, checkedFolders) = await FileStorageService.MoveOrCopyFilesCheckAsync(batchModel.FileIds.ToList(), batchModel.FolderIds.ToList(), batchModel.DestFolderId.GetString()); - } - - var entries = await FileStorageService.GetItemsAsync(checkedFiles.OfType().Select(Convert.ToInt32), checkedFiles.OfType().Select(Convert.ToInt32), FilterType.FilesOnly, false, "", ""); - - entries.AddRange(await FileStorageService.GetItemsAsync(checkedFiles.OfType(), checkedFiles.OfType(), FilterType.FilesOnly, false, "", "")); - - foreach (var e in entries) - { - yield return await GetFileEntryWrapperAsync(e); - } - } - - public async Task> MoveBatchItemsAsync(BatchModel batchModel) - { - var result = new List(); - - foreach (var e in FileStorageService.MoveOrCopyItems(batchModel.FolderIds.ToList(), batchModel.FileIds.ToList(), batchModel.DestFolderId, batchModel.ConflictResolveType, false, batchModel.DeleteAfter)) - { - result.Add(await FileOperationWraperHelper.GetAsync(e)); - } - - return result; - } - - public async Task> CopyBatchItemsAsync(BatchModel batchModel) - { - var result = new List(); - - foreach (var e in FileStorageService.MoveOrCopyItems(batchModel.FolderIds.ToList(), batchModel.FileIds.ToList(), batchModel.DestFolderId, batchModel.ConflictResolveType, true, batchModel.DeleteAfter)) - { - result.Add(await FileOperationWraperHelper.GetAsync(e)); - } - - return result; - } - - public async Task> MarkAsReadAsync(BaseBatchModel model) - { - var result = new List(); - - foreach (var e in FileStorageService.MarkAsRead(model.FolderIds.ToList(), model.FileIds.ToList())) - { - result.Add(await FileOperationWraperHelper.GetAsync(e)); - } - - return result; - } - - public async Task> TerminateTasksAsync() - { - var result = new List(); - - foreach (var e in FileStorageService.TerminateTasks()) - { - result.Add(await FileOperationWraperHelper.GetAsync(e)); - } - - return result; - } - - public async Task> GetOperationStatusesAsync() - { - var result = new List(); - - foreach (var e in FileStorageService.GetTasksStatuses()) - { - result.Add(await FileOperationWraperHelper.GetAsync(e)); - } - - return result; - } - - public async Task> BulkDownloadAsync(DownloadModel model) - { - var folders = new Dictionary(); - var files = new Dictionary(); - - foreach (var fileId in model.FileConvertIds.Where(fileId => !files.ContainsKey(fileId.Key))) - { - files.Add(fileId.Key, fileId.Value); - } - - foreach (var fileId in model.FileIds.Where(fileId => !files.ContainsKey(fileId))) - { - files.Add(fileId, string.Empty); - } - - foreach (var folderId in model.FolderIds.Where(folderId => !folders.ContainsKey(folderId))) - { - folders.Add(folderId, string.Empty); - } - - var result = new List(); - - foreach (var e in FileStorageService.BulkDownload(folders, files)) - { - result.Add(await FileOperationWraperHelper.GetAsync(e)); - } - - return result; - } - - public async Task> EmptyTrashAsync() - { - var emptyTrash = await FileStorageService.EmptyTrashAsync(); - var result = new List(); - - foreach (var e in emptyTrash) - { - result.Add(await FileOperationWraperHelper.GetAsync(e)); - } - - return result; - } - - public async Task>> GetFileVersionInfoAsync(T fileId) - { - var files = await FileStorageService.GetFileHistoryAsync(fileId); - var result = new List>(); - - foreach (var e in files) - { - result.Add(await FileWrapperHelper.GetAsync(e)); - } - - return result; - } - - public async Task>> ChangeHistoryAsync(T fileId, int version, bool continueVersion) - { - var pair = await FileStorageService.CompleteVersionAsync(fileId, version, continueVersion); - var history = pair.Value; - - var result = new List>(); - - foreach (var e in history) - { - result.Add(await FileWrapperHelper.GetAsync(e)); - } - - return result; - } - - public async Task> LockFileAsync(T fileId, bool lockFile) - { - var result = await FileStorageService.LockFileAsync(fileId, lockFile); - return await FileWrapperHelper.GetAsync(result); - } - - public Task GetPresignedUriAsync(T fileId) - { - return FileStorageService.GetPresignedUriAsync(fileId); - } - - public async Task> GetEditHistoryAsync(T fileId, string doc = null) - { - var result = await FileStorageService.GetEditHistoryAsync(fileId, doc); - return result.Select(r => new EditHistoryWrapper(r, ApiDateTimeHelper, UserManager, DisplayUserSettingsHelper)).ToList(); - } - - public Task GetEditDiffUrlAsync(T fileId, int version = 0, string doc = null) - { - return FileStorageService.GetEditDiffUrlAsync(fileId, version, doc); - } - - public async Task> RestoreVersionAsync(T fileId, int version = 0, string url = null, string doc = null) - { - var result = await FileStorageService.RestoreVersionAsync(fileId, version, url, doc); - return result.Select(r => new EditHistoryWrapper(r, ApiDateTimeHelper, UserManager, DisplayUserSettingsHelper)).ToList(); - } - - public Task UpdateCommentAsync(T fileId, int version, string comment) - { - return FileStorageService.UpdateCommentAsync(fileId, version, comment); - } - - public Task> GetFileSecurityInfoAsync(T fileId) - { - return GetSecurityInfoAsync(new List { fileId }, new List { }); - } - - public Task> GetFolderSecurityInfoAsync(T folderId) - { - return GetSecurityInfoAsync(new List { }, new List { folderId }); - } - - public async IAsyncEnumerable GetFoldersAsync(T folderId) - { - var folders = await FileStorageService.GetFoldersAsync(folderId); - foreach (var folder in folders) - { - yield return await GetFileEntryWrapperAsync(folder); - } - } - - public async Task> GetSecurityInfoAsync(IEnumerable fileIds, IEnumerable folderIds) - { - var fileShares = await FileStorageService.GetSharedInfoAsync(fileIds, folderIds); - return fileShares.Select(FileShareWrapperHelper.Get).ToList(); - } - - public Task> SetFileSecurityInfoAsync(T fileId, IEnumerable share, bool notify, string sharingMessage) - { - return SetSecurityInfoAsync(new List { fileId }, new List(), share, notify, sharingMessage); - } - - public Task> SetFolderSecurityInfoAsync(T folderId, IEnumerable share, bool notify, string sharingMessage) - { - return SetSecurityInfoAsync(new List(), new List { folderId }, share, notify, sharingMessage); - } - - public async Task> SetSecurityInfoAsync(IEnumerable fileIds, IEnumerable folderIds, IEnumerable share, bool notify, string sharingMessage) - { - if (share != null && share.Any()) - { - var list = new List(share.Select(FileShareParamsHelper.ToAceObject)); - var aceCollection = new AceCollection - { - Files = fileIds, - Folders = folderIds, - Aces = list, - Message = sharingMessage - }; - await FileStorageService.SetAceObjectAsync(aceCollection, notify); - } - - return await GetSecurityInfoAsync(fileIds, folderIds); - } - - public async Task RemoveSecurityInfoAsync(List fileIds, List folderIds) - { - await FileStorageService.RemoveAceAsync(fileIds, folderIds); - - return true; - } - - public async Task GenerateSharedLinkAsync(T fileId, FileShare share) - { - var file = await GetFileInfoAsync(fileId); - - var tmpInfo = await FileStorageService.GetSharedInfoAsync(new List { fileId }, new List { }); - var sharedInfo = tmpInfo.Find(r => r.SubjectId == FileConstant.ShareLinkId); - - if (sharedInfo == null || sharedInfo.Share != share) - { - var list = new List + var list = new List { new AceWrapper { @@ -816,95 +844,94 @@ namespace ASC.Files.Helpers Share = share } }; - var aceCollection = new AceCollection - { - Files = new List { fileId }, - Folders = new List(0), - Aces = list - }; - await FileStorageService.SetAceObjectAsync(aceCollection, false); + var aceCollection = new AceCollection + { + Files = new List { fileId }, + Folders = new List(0), + Aces = list + }; + await _fileStorageService.SetAceObjectAsync(aceCollection, false); - tmpInfo = await FileStorageService.GetSharedInfoAsync(new List { fileId }, new List { }); - sharedInfo = tmpInfo.Find(r => r.SubjectId == FileConstant.ShareLinkId); - } - - return sharedInfo.Link; + tmpInfo = await _fileStorageService.GetSharedInfoAsync(new List { fileId }, new List { }); + sharedInfo = tmpInfo.Find(r => r.SubjectId == FileConstant.ShareLinkId); } - public Task SetAceLinkAsync(T fileId, FileShare share) + return sharedInfo.Link; + } + + public Task SetAceLinkAsync(T fileId, FileShare share) + { + return _fileStorageService.SetAceLinkAsync(fileId, share); + } + + ///// + ///// + ///// + ///// + ///// + //[Read(@"@search/{query}")] + //public IEnumerable Search(string query) + //{ + // var searcher = new SearchHandler(); + // var files = searcher.SearchFiles(query).Select(r => (FileEntryWrapper)FileWrapperHelper.Get(r)); + // var folders = searcher.SearchFolders(query).Select(f => (FileEntryWrapper)FolderWrapperHelper.Get(f)); + + // return files.Concat(folders); + //} + + private async Task> ToFolderContentWrapperAsync(T folderId, Guid userIdOrGroupId, FilterType filterType, bool withSubFolders) + { + OrderBy orderBy = null; + if (Enum.TryParse(_apiContext.SortBy, true, out SortedByType sortBy)) { - return FileStorageService.SetAceLinkAsync(fileId, share); + orderBy = new OrderBy(sortBy, !_apiContext.SortDescending); } - ///// - ///// - ///// - ///// - ///// - //[Read(@"@search/{query}")] - //public IEnumerable Search(string query) - //{ - // var searcher = new SearchHandler(); - // var files = searcher.SearchFiles(query).Select(r => (FileEntryWrapper)FileWrapperHelper.Get(r)); - // var folders = searcher.SearchFolders(query).Select(f => (FileEntryWrapper)FolderWrapperHelper.Get(f)); + var startIndex = Convert.ToInt32(_apiContext.StartIndex); + var items = await _fileStorageService.GetFolderItemsAsync(folderId, + startIndex, + Convert.ToInt32(_apiContext.Count), + filterType, + filterType == FilterType.ByUser, + userIdOrGroupId.ToString(), + _apiContext.FilterValue, + false, + withSubFolders, + orderBy); + return await _folderContentWrapperHelper.GetAsync(items, startIndex); + } - // return files.Concat(folders); - //} - - private async Task> ToFolderContentWrapperAsync(T folderId, Guid userIdOrGroupId, FilterType filterType, bool withSubFolders) + internal async Task GetFileEntryWrapperAsync(FileEntry r) + { + FileEntryWrapper wrapper = null; + if (r is Folder fol1) { - OrderBy orderBy = null; - if (Enum.TryParse(ApiContext.SortBy, true, out SortedByType sortBy)) - { - orderBy = new OrderBy(sortBy, !ApiContext.SortDescending); - } - - var startIndex = Convert.ToInt32(ApiContext.StartIndex); - var items = await FileStorageService.GetFolderItemsAsync(folderId, - startIndex, - Convert.ToInt32(ApiContext.Count), - filterType, - filterType == FilterType.ByUser, - userIdOrGroupId.ToString(), - ApiContext.FilterValue, - false, - withSubFolders, - orderBy); - return await FolderContentWrapperHelper.GetAsync(items, startIndex); + wrapper = await _folderWrapperHelper.GetAsync(fol1); } - - internal async Task GetFileEntryWrapperAsync(FileEntry r) + else if (r is Folder fol2) { - FileEntryWrapper wrapper = null; - if (r is Folder fol1) - { - wrapper = await FolderWrapperHelper.GetAsync(fol1); - } - else if (r is Folder fol2) - { - wrapper = await FolderWrapperHelper.GetAsync(fol2); - } - else if (r is File file1) - { - wrapper = await FileWrapperHelper.GetAsync(file1); - } - else if (r is File file2) - { - wrapper = await FileWrapperHelper.GetAsync(file2); - } - - return wrapper; + wrapper = await _folderWrapperHelper.GetAsync(fol2); } - - internal IFormFile GetFileFromRequest(IModelWithFile model) + else if (r is File file1) { - IEnumerable files = HttpContextAccessor.HttpContext.Request.Form.Files; - if (files != null && files.Any()) - { - return files.First(); - } - - return model.File; + wrapper = await _fileWrapperHelper.GetAsync(file1); } + else if (r is File file2) + { + wrapper = await _fileWrapperHelper.GetAsync(file2); + } + + return wrapper; + } + + internal IFormFile GetFileFromRequest(IModelWithFile model) + { + IEnumerable files = _httpContextAccessor.HttpContext.Request.Form.Files; + if (files != null && files.Any()) + { + return files.First(); + } + + return model.File; } } diff --git a/products/ASC.Files/Server/ProductEntryPoint.cs b/products/ASC.Files/Server/ProductEntryPoint.cs index 8188a1398a..5dafadcbf8 100644 --- a/products/ASC.Files/Server/ProductEntryPoint.cs +++ b/products/ASC.Files/Server/ProductEntryPoint.cs @@ -23,25 +23,24 @@ * */ -namespace ASC.Files +namespace ASC.Files; + +[Scope] +public class ApiProductEntryPoint : ProductEntryPoint { - [Scope] - public class ApiProductEntryPoint : ProductEntryPoint + public override string ApiURL { - public override string ApiURL - { - get => "api/2.0/files/info.json"; - } + get => "api/2.0/files/info.json"; + } - public ApiProductEntryPoint( - // FilesSpaceUsageStatManager filesSpaceUsageStatManager, - CoreBaseSettings coreBaseSettings, - AuthContext authContext, - UserManager userManager - // SubscriptionManager subscriptionManager - ): base(coreBaseSettings, authContext, userManager, null) - { + public ApiProductEntryPoint( + //FilesSpaceUsageStatManager filesSpaceUsageStatManager, + CoreBaseSettings coreBaseSettings, + AuthContext authContext, + UserManager userManager + //SubscriptionManager subscriptionManager + ) : base(coreBaseSettings, authContext, userManager, null) + { - } - } -} \ No newline at end of file + } +} diff --git a/products/ASC.Files/Server/Startup.cs b/products/ASC.Files/Server/Startup.cs index 4feefe85fc..cb4a990d70 100644 --- a/products/ASC.Files/Server/Startup.cs +++ b/products/ASC.Files/Server/Startup.cs @@ -1,68 +1,67 @@ -namespace ASC.Files -{ - public class Startup : BaseStartup +namespace ASC.Files; + +public class Startup : BaseStartup +{ + public override JsonConverter[] Converters { get => new JsonConverter[] { new FileEntryWrapperConverter(), new FileShareConverter() }; } + + public Startup(IConfiguration configuration, IHostEnvironment hostEnvironment) + : base(configuration, hostEnvironment) { - public override JsonConverter[] Converters { get => new JsonConverter[] { new FileEntryWrapperConverter(), new FileShareConverter() }; } - - public Startup(IConfiguration configuration, IHostEnvironment hostEnvironment) - : base(configuration, hostEnvironment) - { - } - - public override void ConfigureServices(IServiceCollection services) - { - Encoding.RegisterProvider(CodePagesEncodingProvider.Instance); + } - services.AddMemoryCache(); + public override void ConfigureServices(IServiceCollection services) + { + Encoding.RegisterProvider(CodePagesEncodingProvider.Instance); - base.ConfigureServices(services); + services.AddMemoryCache(); - DIHelper.TryAdd(); - DIHelper.TryAdd(); - DIHelper.TryAdd(); - DIHelper.TryAdd(); + base.ConfigureServices(services); - NotifyConfigurationExtension.Register(DIHelper); - } + DIHelper.TryAdd(); + DIHelper.TryAdd(); + DIHelper.TryAdd(); + DIHelper.TryAdd(); - public override void Configure(IApplicationBuilder app, IWebHostEnvironment env) - { - app.UseCors(builder => - builder - .AllowAnyOrigin() - .AllowAnyHeader() - .AllowAnyMethod()); + NotifyConfigurationExtension.Register(DIHelper); + } - base.Configure(app, env); + public override void Configure(IApplicationBuilder app, IWebHostEnvironment env) + { + app.UseCors(builder => + builder + .AllowAnyOrigin() + .AllowAnyHeader() + .AllowAnyMethod()); - app.MapWhen( - context => context.Request.Path.ToString().EndsWith("httphandlers/filehandler.ashx"), - appBranch => - { - appBranch.UseFileHandler(); - }); + base.Configure(app, env); - app.MapWhen( - context => context.Request.Path.ToString().EndsWith("ChunkedUploader.ashx"), - appBranch => - { - appBranch.UseChunkedUploaderHandler(); - }); + app.MapWhen( + context => context.Request.Path.ToString().EndsWith("httphandlers/filehandler.ashx"), + appBranch => + { + appBranch.UseFileHandler(); + }); - app.MapWhen( - context => context.Request.Path.ToString().EndsWith("ThirdPartyAppHandler.ashx"), - appBranch => - { - appBranch.UseThirdPartyAppHandler(); - }); + app.MapWhen( + context => context.Request.Path.ToString().EndsWith("ChunkedUploader.ashx"), + appBranch => + { + appBranch.UseChunkedUploaderHandler(); + }); - app.MapWhen( - context => context.Request.Path.ToString().EndsWith("DocuSignHandler.ashx"), - appBranch => - { - appBranch.UseDocuSignHandler(); - }); - } - } + app.MapWhen( + context => context.Request.Path.ToString().EndsWith("ThirdPartyAppHandler.ashx"), + appBranch => + { + appBranch.UseThirdPartyAppHandler(); + }); + + app.MapWhen( + context => context.Request.Path.ToString().EndsWith("DocuSignHandler.ashx"), + appBranch => + { + appBranch.UseDocuSignHandler(); + }); + } }