forked from ddrilling/AsbCloudServer
Merge branch 'feature/file_repository' into dev
This commit is contained in:
commit
0f1b4285f5
@ -13,4 +13,16 @@
|
|||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<None Remove="Data\DailyReport\" />
|
<None Remove="Data\DailyReport\" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<EditorConfigFiles Remove="D:\Source\AsbCloudApp\Services\.editorconfig" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<None Include="D:\Source\AsbCloudApp\Services\.editorconfig" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<ProjectReference Include="..\AsbCloudDb\AsbCloudDb.csproj" />
|
||||||
|
</ItemGroup>
|
||||||
</Project>
|
</Project>
|
||||||
|
@ -1,10 +1,11 @@
|
|||||||
using AsbCloudApp.Data;
|
using AsbCloudApp.Data;
|
||||||
|
using AsbCloudApp.Services;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Threading;
|
using System.Threading;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
namespace AsbCloudApp.Services
|
namespace AsbCloudApp.Repositories
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Сервис доступа к файлам
|
/// Сервис доступа к файлам
|
51
AsbCloudApp/Repositories/IFileStorageRepository.cs
Normal file
51
AsbCloudApp/Repositories/IFileStorageRepository.cs
Normal file
@ -0,0 +1,51 @@
|
|||||||
|
using System.IO;
|
||||||
|
using System.Threading;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
|
namespace AsbCloudApp.Repositories
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Репозиторий хранения фалов
|
||||||
|
/// </summary>
|
||||||
|
public interface IFileStorageRepository
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Директория хранения файлов
|
||||||
|
/// </summary>
|
||||||
|
string RootPath { get; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Получение длинны фала и проверка его наличия, если отсутствует падает исключение
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="srcFilePath"></param>
|
||||||
|
/// <returns></returns>
|
||||||
|
long GetLengthFile(string srcFilePath);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Перемещение файла
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="srcFilePath"></param>
|
||||||
|
/// <param name="filePath"></param>
|
||||||
|
void MoveFile(string srcFilePath, string filePath);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Копирование файла
|
||||||
|
/// </summary>
|
||||||
|
/// <returns></returns>
|
||||||
|
Task CopyFileAsync(string filePath, Stream fileStream, CancellationToken token);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Удаление файла
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="fileName"></param>
|
||||||
|
void DeleteFile(string fileName);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Проверка наличия файла
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="fullPath"></param>
|
||||||
|
/// <param name="fileName"></param>
|
||||||
|
/// <returns></returns>
|
||||||
|
bool FileExists(string fullPath, string fileName);
|
||||||
|
}
|
||||||
|
}
|
@ -1,10 +1,5 @@
|
|||||||
using AsbCloudApp.Data;
|
using AsbCloudApp.Data;
|
||||||
using AsbCloudApp.Exceptions;
|
using AsbCloudApp.Repositories;
|
||||||
using AsbCloudApp.Services;
|
|
||||||
using AsbCloudDb.Model;
|
|
||||||
using AsbCloudInfrastructure.Repository;
|
|
||||||
using Mapster;
|
|
||||||
using Microsoft.EntityFrameworkCore;
|
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
@ -12,28 +7,43 @@ using System.Linq;
|
|||||||
using System.Threading;
|
using System.Threading;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
namespace AsbCloudInfrastructure.Services
|
namespace AsbCloudApp.Services
|
||||||
{
|
{
|
||||||
public class FileService : IFileService
|
/// <summary>
|
||||||
|
/// Сервис доступа к файлам
|
||||||
|
/// </summary>
|
||||||
|
public class FileService
|
||||||
{
|
{
|
||||||
public string RootPath { get; private set; }
|
|
||||||
private readonly IFileRepository fileRepository;
|
private readonly IFileRepository fileRepository;
|
||||||
|
private readonly IFileStorageRepository fileStorageRepository;
|
||||||
|
|
||||||
public FileService(IFileRepository fileRepository)
|
/// <summary>
|
||||||
|
/// Сервис доступа к файлам
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="fileRepository"></param>
|
||||||
|
/// <param name="fileStorageRepository"></param>
|
||||||
|
public FileService(IFileRepository fileRepository, IFileStorageRepository fileStorageRepository)
|
||||||
{
|
{
|
||||||
RootPath = "files";
|
|
||||||
this.fileRepository = fileRepository;
|
this.fileRepository = fileRepository;
|
||||||
|
this.fileStorageRepository = fileStorageRepository;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// переместить файл
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idWell"></param>
|
||||||
|
/// <param name="idUser"></param>
|
||||||
|
/// <param name="idCategory"></param>
|
||||||
|
/// <param name="destinationFileName"></param>
|
||||||
|
/// <param name="srcFilePath"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<FileInfoDto> MoveAsync(int idWell, int? idUser, int idCategory,
|
public async Task<FileInfoDto> MoveAsync(int idWell, int? idUser, int idCategory,
|
||||||
string destinationFileName, string srcFilePath, CancellationToken token = default)
|
string destinationFileName, string srcFilePath, CancellationToken token = default)
|
||||||
{
|
{
|
||||||
destinationFileName = Path.GetFileName(destinationFileName);
|
destinationFileName = Path.GetFileName(destinationFileName);
|
||||||
srcFilePath = Path.GetFullPath(srcFilePath);
|
srcFilePath = Path.GetFullPath(srcFilePath);
|
||||||
if (!File.Exists(srcFilePath))
|
var fileSize = fileStorageRepository.GetLengthFile(srcFilePath);
|
||||||
throw new ArgumentInvalidException($"file {srcFilePath} doesn't exist", nameof(srcFilePath));
|
|
||||||
|
|
||||||
var sysFileInfo = new System.IO.FileInfo(srcFilePath);
|
|
||||||
|
|
||||||
//save info to db
|
//save info to db
|
||||||
var dto = new FileInfoDto {
|
var dto = new FileInfoDto {
|
||||||
@ -41,18 +51,27 @@ namespace AsbCloudInfrastructure.Services
|
|||||||
IdAuthor = idUser,
|
IdAuthor = idUser,
|
||||||
IdCategory = idCategory,
|
IdCategory = idCategory,
|
||||||
Name = destinationFileName,
|
Name = destinationFileName,
|
||||||
Size = sysFileInfo.Length
|
Size = fileSize
|
||||||
};
|
};
|
||||||
var fileId = await fileRepository.InsertAsync(dto, token)
|
var fileId = await fileRepository.InsertAsync(dto, token)
|
||||||
.ConfigureAwait(false);
|
.ConfigureAwait(false);
|
||||||
|
|
||||||
string filePath = MakeFilePath(idWell, idCategory, destinationFileName, fileId);
|
string filePath = MakeFilePath(idWell, idCategory, destinationFileName, fileId);
|
||||||
Directory.CreateDirectory(Path.GetDirectoryName(filePath));
|
fileStorageRepository.MoveFile(srcFilePath, filePath);
|
||||||
File.Move(srcFilePath, filePath);
|
|
||||||
|
|
||||||
return await GetInfoAsync(fileId, token);
|
return await GetInfoAsync(fileId, token);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Сохранить файл
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idWell"></param>
|
||||||
|
/// <param name="idUser"></param>
|
||||||
|
/// <param name="idCategory"></param>
|
||||||
|
/// <param name="fileFullName"></param>
|
||||||
|
/// <param name="fileStream"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<FileInfoDto> SaveAsync(int idWell, int? idUser, int idCategory,
|
public async Task<FileInfoDto> SaveAsync(int idWell, int? idUser, int idCategory,
|
||||||
string fileFullName, Stream fileStream, CancellationToken token)
|
string fileFullName, Stream fileStream, CancellationToken token)
|
||||||
{
|
{
|
||||||
@ -71,21 +90,17 @@ namespace AsbCloudInfrastructure.Services
|
|||||||
|
|
||||||
//save stream to disk
|
//save stream to disk
|
||||||
string filePath = MakeFilePath(idWell, idCategory, fileFullName, fileId);
|
string filePath = MakeFilePath(idWell, idCategory, fileFullName, fileId);
|
||||||
|
await fileStorageRepository.CopyFileAsync(filePath, fileStream, token);
|
||||||
Directory.CreateDirectory(Path.GetDirectoryName(filePath));
|
|
||||||
|
|
||||||
using var newfileStream = new FileStream(filePath, FileMode.Create);
|
|
||||||
await fileStream.CopyToAsync(newfileStream, token).ConfigureAwait(false);
|
|
||||||
|
|
||||||
return await GetInfoAsync(fileId, token);
|
return await GetInfoAsync(fileId, token);
|
||||||
}
|
}
|
||||||
|
|
||||||
private string MakeFilePath(int idWell, int idCategory, string fileFullName, int fileId)
|
/// <summary>
|
||||||
{
|
/// Инфо о файле
|
||||||
return Path.Combine(RootPath, $"{idWell}",
|
/// </summary>
|
||||||
$"{idCategory}", $"{fileId}" + $"{Path.GetExtension(fileFullName)}");
|
/// <param name="idFile"></param>
|
||||||
}
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<FileInfoDto> GetInfoAsync(int idFile,
|
public async Task<FileInfoDto> GetInfoAsync(int idFile,
|
||||||
CancellationToken token)
|
CancellationToken token)
|
||||||
{
|
{
|
||||||
@ -95,17 +110,26 @@ namespace AsbCloudInfrastructure.Services
|
|||||||
|
|
||||||
var relativePath = GetUrl(dto.IdWell, dto.IdCategory, dto.Id, ext);
|
var relativePath = GetUrl(dto.IdWell, dto.IdCategory, dto.Id, ext);
|
||||||
var fullPath = Path.GetFullPath(relativePath);
|
var fullPath = Path.GetFullPath(relativePath);
|
||||||
if (!File.Exists(fullPath))
|
fileStorageRepository.FileExists(fullPath, relativePath);
|
||||||
{
|
|
||||||
throw new FileNotFoundException("not found", relativePath);
|
|
||||||
}
|
|
||||||
|
|
||||||
return dto;
|
return dto;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// удалить файл
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idFile"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public Task<int> DeleteAsync(int idFile, CancellationToken token)
|
public Task<int> DeleteAsync(int idFile, CancellationToken token)
|
||||||
=> DeleteAsync(new int[] { idFile }, token);
|
=> DeleteAsync(new int[] { idFile }, token);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// удалить файлы
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="ids"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<int> DeleteAsync(IEnumerable<int> ids, CancellationToken token)
|
public async Task<int> DeleteAsync(IEnumerable<int> ids, CancellationToken token)
|
||||||
{
|
{
|
||||||
if (ids is null || !ids.Any())
|
if (ids is null || !ids.Any())
|
||||||
@ -119,13 +143,17 @@ namespace AsbCloudInfrastructure.Services
|
|||||||
foreach (var file in files)
|
foreach (var file in files)
|
||||||
{
|
{
|
||||||
var fileName = GetUrl(file.IdWell, file.IdCategory, file.Id, Path.GetExtension(file.Name));
|
var fileName = GetUrl(file.IdWell, file.IdCategory, file.Id, Path.GetExtension(file.Name));
|
||||||
if (File.Exists(fileName))
|
fileStorageRepository.DeleteFile(fileName);
|
||||||
File.Delete(fileName);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return files.Any() ? 1 : 0;
|
return files.Any() ? 1 : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// получить путь для скачивания
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idFile"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<string> GetUrl(int idFile)
|
public async Task<string> GetUrl(int idFile)
|
||||||
{
|
{
|
||||||
var fileInfo = await fileRepository.GetOrDefaultAsync(idFile, CancellationToken.None).ConfigureAwait(false);
|
var fileInfo = await fileRepository.GetOrDefaultAsync(idFile, CancellationToken.None).ConfigureAwait(false);
|
||||||
@ -133,16 +161,41 @@ namespace AsbCloudInfrastructure.Services
|
|||||||
return GetUrl(fileInfo.IdWell, fileInfo.IdCategory, fileInfo.Id, Path.GetExtension(fileInfo.Name));
|
return GetUrl(fileInfo.IdWell, fileInfo.IdCategory, fileInfo.Id, Path.GetExtension(fileInfo.Name));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// получить путь для скачивания
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="fileInfo"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public string GetUrl(FileInfoDto fileInfo) =>
|
public string GetUrl(FileInfoDto fileInfo) =>
|
||||||
GetUrl(fileInfo.IdWell, fileInfo.IdCategory, fileInfo.Id, Path.GetExtension(fileInfo.Name));
|
GetUrl(fileInfo.IdWell, fileInfo.IdCategory, fileInfo.Id, Path.GetExtension(fileInfo.Name));
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// получить путь для скачивания
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idWell"></param>
|
||||||
|
/// <param name="idCategory"></param>
|
||||||
|
/// <param name="idFile"></param>
|
||||||
|
/// <param name="dotExtention"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public string GetUrl(int idWell, int idCategory, int idFile, string dotExtention) =>
|
public string GetUrl(int idWell, int idCategory, int idFile, string dotExtention) =>
|
||||||
Path.Combine(RootPath, idWell.ToString(), idCategory.ToString(), $"{idFile}{dotExtention}");
|
Path.Combine(fileStorageRepository.RootPath, idWell.ToString(), idCategory.ToString(), $"{idFile}{dotExtention}");
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// пометить метку файла как удаленную
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idMark"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public Task<int> MarkFileMarkAsDeletedAsync(int idMark,
|
public Task<int> MarkFileMarkAsDeletedAsync(int idMark,
|
||||||
CancellationToken token)
|
CancellationToken token)
|
||||||
=> fileRepository.MarkFileMarkAsDeletedAsync(new int[] { idMark }, token);
|
=> fileRepository.MarkFileMarkAsDeletedAsync(new int[] { idMark }, token);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Инфо о файле
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idsFile"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<IEnumerable<FileInfoDto>> GetInfoByIdsAsync(IEnumerable<int> idsFile, CancellationToken token)
|
public async Task<IEnumerable<FileInfoDto>> GetInfoByIdsAsync(IEnumerable<int> idsFile, CancellationToken token)
|
||||||
{
|
{
|
||||||
var result = await fileRepository.GetInfoByIdsAsync(idsFile, token).ConfigureAwait(false);
|
var result = await fileRepository.GetInfoByIdsAsync(idsFile, token).ConfigureAwait(false);
|
||||||
@ -153,47 +206,107 @@ namespace AsbCloudInfrastructure.Services
|
|||||||
var ext = Path.GetExtension(entity.Name);
|
var ext = Path.GetExtension(entity.Name);
|
||||||
var relativePath = GetUrl(entity.IdWell, entity.IdCategory, entity.Id, ext);
|
var relativePath = GetUrl(entity.IdWell, entity.IdCategory, entity.Id, ext);
|
||||||
var fullPath = Path.GetFullPath(relativePath);
|
var fullPath = Path.GetFullPath(relativePath);
|
||||||
if (!File.Exists(fullPath))
|
fileStorageRepository.FileExists(fullPath, relativePath);
|
||||||
{
|
|
||||||
throw new FileNotFoundException("not found", relativePath);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Получить список файлов в контейнере
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idWell"></param>
|
||||||
|
/// <param name="idCategory"></param>
|
||||||
|
/// <param name="companyName"></param>
|
||||||
|
/// <param name="fileName"></param>
|
||||||
|
/// <param name="begin"></param>
|
||||||
|
/// <param name="end"></param>
|
||||||
|
/// <param name="skip"></param>
|
||||||
|
/// <param name="take"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<PaginationContainer<FileInfoDto>> GetInfosAsync(int idWell,
|
public async Task<PaginationContainer<FileInfoDto>> GetInfosAsync(int idWell,
|
||||||
int idCategory, string companyName = default, string fileName = default, DateTime begin = default,
|
int idCategory, string companyName = default, string fileName = default, DateTime begin = default,
|
||||||
DateTime end = default, int skip = 0, int take = 32, CancellationToken token = default)
|
DateTime end = default, int skip = 0, int take = 32, CancellationToken token = default)
|
||||||
=> await fileRepository.GetInfosAsync(idWell, idCategory, companyName, fileName, begin, end, skip, take, token)
|
=> await fileRepository.GetInfosAsync(idWell, idCategory, companyName, fileName, begin, end, skip, take, token)
|
||||||
.ConfigureAwait(false);
|
.ConfigureAwait(false);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Пометить файл как удаленный
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idFile"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<int> MarkAsDeletedAsync(int idFile, CancellationToken token = default)
|
public async Task<int> MarkAsDeletedAsync(int idFile, CancellationToken token = default)
|
||||||
=> await fileRepository.MarkAsDeletedAsync(idFile, token)
|
=> await fileRepository.MarkAsDeletedAsync(idFile, token)
|
||||||
.ConfigureAwait(false);
|
.ConfigureAwait(false);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// добавить метку на файл
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="fileMarkDto"></param>
|
||||||
|
/// <param name="idUser"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<int> CreateFileMarkAsync(FileMarkDto fileMarkDto, int idUser, CancellationToken token)
|
public async Task<int> CreateFileMarkAsync(FileMarkDto fileMarkDto, int idUser, CancellationToken token)
|
||||||
=> await fileRepository.CreateFileMarkAsync(fileMarkDto, idUser, token)
|
=> await fileRepository.CreateFileMarkAsync(fileMarkDto, idUser, token)
|
||||||
.ConfigureAwait(false);
|
.ConfigureAwait(false);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Получить запись по id
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="id"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<FileInfoDto> GetOrDefaultAsync(int id, CancellationToken token)
|
public async Task<FileInfoDto> GetOrDefaultAsync(int id, CancellationToken token)
|
||||||
=> await fileRepository.GetOrDefaultAsync(id, token)
|
=> await fileRepository.GetOrDefaultAsync(id, token)
|
||||||
.ConfigureAwait(false);
|
.ConfigureAwait(false);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// получить инфо о файле по метке
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idMark"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<FileInfoDto> GetByMarkId(int idMark, CancellationToken token)
|
public async Task<FileInfoDto> GetByMarkId(int idMark, CancellationToken token)
|
||||||
=> await fileRepository.GetByMarkId(idMark, token)
|
=> await fileRepository.GetByMarkId(idMark, token)
|
||||||
.ConfigureAwait(false);
|
.ConfigureAwait(false);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// получить инфо о файле по метке
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idMark"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<int> MarkFileMarkAsDeletedAsync(IEnumerable<int> idsMarks, CancellationToken token)
|
public async Task<int> MarkFileMarkAsDeletedAsync(IEnumerable<int> idsMarks, CancellationToken token)
|
||||||
=> await fileRepository.MarkFileMarkAsDeletedAsync(idsMarks, token)
|
=> await fileRepository.MarkFileMarkAsDeletedAsync(idsMarks, token)
|
||||||
.ConfigureAwait(false);
|
.ConfigureAwait(false);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Получение файлов по скважине
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idWell"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<IEnumerable<FileInfoDto>> GetInfosByWellIdAsync(int idWell, CancellationToken token)
|
public async Task<IEnumerable<FileInfoDto>> GetInfosByWellIdAsync(int idWell, CancellationToken token)
|
||||||
=> await fileRepository.GetInfosByWellIdAsync(idWell, token)
|
=> await fileRepository.GetInfosByWellIdAsync(idWell, token)
|
||||||
.ConfigureAwait(false);
|
.ConfigureAwait(false);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Получить файлы определенной категории
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="idWell"></param>
|
||||||
|
/// <param name="idCategory"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
public async Task<IEnumerable<FileInfoDto>> GetInfosByCategoryAsync(int idWell, int idCategory, CancellationToken token)
|
public async Task<IEnumerable<FileInfoDto>> GetInfosByCategoryAsync(int idWell, int idCategory, CancellationToken token)
|
||||||
=> await fileRepository.GetInfosByCategoryAsync(idWell, idCategory, token)
|
=> await fileRepository.GetInfosByCategoryAsync(idWell, idCategory, token)
|
||||||
.ConfigureAwait(false);
|
.ConfigureAwait(false);
|
||||||
|
|
||||||
|
private string MakeFilePath(int idWell, int idCategory, string fileFullName, int fileId)
|
||||||
|
{
|
||||||
|
return Path.Combine(fileStorageRepository.RootPath, $"{idWell}",
|
||||||
|
$"{idCategory}", $"{fileId}" + $"{Path.GetExtension(fileFullName)}");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -1,186 +0,0 @@
|
|||||||
using AsbCloudApp.Data;
|
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.IO;
|
|
||||||
using System.Threading;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace AsbCloudApp.Services
|
|
||||||
{
|
|
||||||
//TODO: refactor IFileService
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Сервис доступа к файлам
|
|
||||||
/// </summary>
|
|
||||||
public interface IFileService
|
|
||||||
{
|
|
||||||
/// <summary>
|
|
||||||
/// Директория хранения файлов
|
|
||||||
/// </summary>
|
|
||||||
string RootPath { get; }
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Сохранить файл
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idWell"></param>
|
|
||||||
/// <param name="idUser"></param>
|
|
||||||
/// <param name="idCategory"></param>
|
|
||||||
/// <param name="fileFullName"></param>
|
|
||||||
/// <param name="fileStream"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<FileInfoDto> SaveAsync(int idWell, int? idUser, int idCategory, string fileFullName, Stream fileStream, CancellationToken token = default);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Инфо о файле
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idFile"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<FileInfoDto> GetInfoAsync(int idFile,
|
|
||||||
CancellationToken token);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// удалить файл
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="id"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<int> DeleteAsync(int id, CancellationToken token);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// удалить файлы
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="ids"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<int> DeleteAsync(IEnumerable<int> ids, CancellationToken token);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// получить путь для скачивания
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="fileInfo"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
string GetUrl(FileInfoDto fileInfo);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// получить путь для скачивания
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idFile"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<string> GetUrl(int idFile);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// получить путь для скачивания
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idWell"></param>
|
|
||||||
/// <param name="idCategory"></param>
|
|
||||||
/// <param name="idFile"></param>
|
|
||||||
/// <param name="dotExtention"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
string GetUrl(int idWell, int idCategory, int idFile, string dotExtention);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// пометить метку файла как удаленную
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idMark"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<int> MarkFileMarkAsDeletedAsync(int idMark, CancellationToken token);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// переместить файл
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idWell"></param>
|
|
||||||
/// <param name="idUser"></param>
|
|
||||||
/// <param name="idCategory"></param>
|
|
||||||
/// <param name="destinationFileName"></param>
|
|
||||||
/// <param name="srcFileFullName"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<FileInfoDto> MoveAsync(int idWell, int? idUser, int idCategory, string destinationFileName, string srcFileFullName, CancellationToken token = default);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Инфо о файле
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idsFile"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<IEnumerable<FileInfoDto>> GetInfoByIdsAsync(IEnumerable<int> idsFile, CancellationToken token);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Получить список файлов в контейнере
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idWell"></param>
|
|
||||||
/// <param name="idCategory"></param>
|
|
||||||
/// <param name="companyName"></param>
|
|
||||||
/// <param name="fileName"></param>
|
|
||||||
/// <param name="begin"></param>
|
|
||||||
/// <param name="end"></param>
|
|
||||||
/// <param name="skip"></param>
|
|
||||||
/// <param name="take"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<PaginationContainer<FileInfoDto>> GetInfosAsync(int idWell,
|
|
||||||
int idCategory, string companyName = default, string fileName = default, DateTime begin = default,
|
|
||||||
DateTime end = default, int skip = 0, int take = 32, CancellationToken token = default);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Пометить файл как удаленный
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idFile"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<int> MarkAsDeletedAsync(int idFile, CancellationToken token = default);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// добавить метку на файл
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="fileMarkDto"></param>
|
|
||||||
/// <param name="idUser"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<int> CreateFileMarkAsync(FileMarkDto fileMarkDto, int idUser, CancellationToken token);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Получить запись по id
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="id"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<FileInfoDto> GetOrDefaultAsync(int id, CancellationToken token);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// получить инфо о файле по метке
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idMark"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<FileInfoDto> GetByMarkId(int idMark, CancellationToken token);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// пометить метки файлов как удаленные
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idsMarks"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<int> MarkFileMarkAsDeletedAsync(IEnumerable<int> idsMarks, CancellationToken token);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Получение файлов по скважине
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idWell"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<IEnumerable<FileInfoDto>> GetInfosByWellIdAsync(int idWell, CancellationToken token);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Получить файлы определенной категории
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="idWell"></param>
|
|
||||||
/// <param name="idCategory"></param>
|
|
||||||
/// <param name="token"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
Task<IEnumerable<FileInfoDto>> GetInfosByCategoryAsync(int idWell, int idCategory, CancellationToken token);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,6 +1,7 @@
|
|||||||
using AsbCloudApp.Data;
|
using AsbCloudApp.Data;
|
||||||
using AsbCloudApp.Data.SAUB;
|
using AsbCloudApp.Data.SAUB;
|
||||||
using AsbCloudApp.Data.Subsystems;
|
using AsbCloudApp.Data.Subsystems;
|
||||||
|
using AsbCloudApp.Repositories;
|
||||||
using AsbCloudApp.Services;
|
using AsbCloudApp.Services;
|
||||||
using AsbCloudApp.Services.Subsystems;
|
using AsbCloudApp.Services.Subsystems;
|
||||||
using AsbCloudDb.Model;
|
using AsbCloudDb.Model;
|
||||||
@ -109,7 +110,7 @@ namespace AsbCloudInfrastructure
|
|||||||
services.AddTransient<IDrillingProgramService, DrillingProgramService>();
|
services.AddTransient<IDrillingProgramService, DrillingProgramService>();
|
||||||
services.AddTransient<IDrillParamsService, DrillParamsService>();
|
services.AddTransient<IDrillParamsService, DrillParamsService>();
|
||||||
services.AddTransient<IEventService, EventService>();
|
services.AddTransient<IEventService, EventService>();
|
||||||
services.AddTransient<IFileService, FileService>();
|
services.AddTransient<FileService>();
|
||||||
services.AddTransient<IMeasureService, MeasureService>();
|
services.AddTransient<IMeasureService, MeasureService>();
|
||||||
services.AddTransient<IMessageService, MessageService>();
|
services.AddTransient<IMessageService, MessageService>();
|
||||||
services.AddTransient<IOperationsStatService, OperationsStatService>();
|
services.AddTransient<IOperationsStatService, OperationsStatService>();
|
||||||
@ -159,6 +160,7 @@ namespace AsbCloudInfrastructure
|
|||||||
.Include(c => c.Wells)
|
.Include(c => c.Wells)
|
||||||
.Include(c => c.Deposit))); // может быть включен в сервис ClusterService
|
.Include(c => c.Deposit))); // может быть включен в сервис ClusterService
|
||||||
services.AddTransient<IFileRepository, FileRepository>();
|
services.AddTransient<IFileRepository, FileRepository>();
|
||||||
|
services.AddTransient<IFileStorageRepository, FileStorageRepository>();
|
||||||
// Subsystem service
|
// Subsystem service
|
||||||
services.AddTransient<ICrudService<SubsystemDto>, CrudCacheServiceBase<SubsystemDto, Subsystem>>();
|
services.AddTransient<ICrudService<SubsystemDto>, CrudCacheServiceBase<SubsystemDto, Subsystem>>();
|
||||||
services.AddTransient<ISubsystemService, SubsystemService>();
|
services.AddTransient<ISubsystemService, SubsystemService>();
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
using AsbCloudApp.Data;
|
using AsbCloudApp.Data;
|
||||||
using AsbCloudApp.Services;
|
using AsbCloudApp.Repositories;
|
||||||
using AsbCloudDb.Model;
|
using AsbCloudDb.Model;
|
||||||
using Mapster;
|
using Mapster;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
59
AsbCloudInfrastructure/Repository/FileStorageRepository.cs
Normal file
59
AsbCloudInfrastructure/Repository/FileStorageRepository.cs
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
using AsbCloudApp.Exceptions;
|
||||||
|
using AsbCloudApp.Repositories;
|
||||||
|
using System.IO;
|
||||||
|
using System.Threading;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
|
namespace AsbCloudInfrastructure.Repository
|
||||||
|
{
|
||||||
|
public class FileStorageRepository : IFileStorageRepository
|
||||||
|
{
|
||||||
|
public string RootPath { get; private set; }
|
||||||
|
|
||||||
|
public FileStorageRepository()
|
||||||
|
{
|
||||||
|
RootPath = "files";
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task CopyFileAsync(string filePath, Stream fileStream, CancellationToken token)
|
||||||
|
{
|
||||||
|
CreateDirectory(filePath);
|
||||||
|
using var newfileStream = new FileStream(filePath, FileMode.Create);
|
||||||
|
await fileStream.CopyToAsync(newfileStream, token).ConfigureAwait(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void DeleteFile(string fileName)
|
||||||
|
{
|
||||||
|
if (File.Exists(fileName))
|
||||||
|
File.Delete(fileName);
|
||||||
|
}
|
||||||
|
|
||||||
|
public long GetLengthFile(string srcFilePath)
|
||||||
|
{
|
||||||
|
if (!File.Exists(srcFilePath))
|
||||||
|
throw new ArgumentInvalidException($"file {srcFilePath} doesn't exist", nameof(srcFilePath));
|
||||||
|
|
||||||
|
var sysFileInfo = new FileInfo(srcFilePath);
|
||||||
|
return sysFileInfo.Length;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void MoveFile(string srcFilePath, string filePath)
|
||||||
|
{
|
||||||
|
CreateDirectory(filePath);
|
||||||
|
File.Move(srcFilePath, filePath);
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool FileExists(string fullPath, string fileName)
|
||||||
|
{
|
||||||
|
if (!File.Exists(fullPath))
|
||||||
|
throw new FileNotFoundException("not found", fileName);
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void CreateDirectory(string filePath)
|
||||||
|
{
|
||||||
|
Directory.CreateDirectory(Path.GetDirectoryName(filePath));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -20,7 +20,7 @@ namespace AsbCloudInfrastructure.Services.DrillingProgram
|
|||||||
private static readonly Dictionary<string, DrillingProgramCreateError> drillingProgramCreateErrors = new Dictionary<string, DrillingProgramCreateError>();
|
private static readonly Dictionary<string, DrillingProgramCreateError> drillingProgramCreateErrors = new Dictionary<string, DrillingProgramCreateError>();
|
||||||
|
|
||||||
private readonly IAsbCloudDbContext context;
|
private readonly IAsbCloudDbContext context;
|
||||||
private readonly IFileService fileService;
|
private readonly FileService fileService;
|
||||||
private readonly IUserService userService;
|
private readonly IUserService userService;
|
||||||
private readonly IWellService wellService;
|
private readonly IWellService wellService;
|
||||||
private readonly IConfiguration configuration;
|
private readonly IConfiguration configuration;
|
||||||
@ -50,7 +50,7 @@ namespace AsbCloudInfrastructure.Services.DrillingProgram
|
|||||||
|
|
||||||
public DrillingProgramService(
|
public DrillingProgramService(
|
||||||
IAsbCloudDbContext context,
|
IAsbCloudDbContext context,
|
||||||
IFileService fileService,
|
FileService fileService,
|
||||||
IUserService userService,
|
IUserService userService,
|
||||||
IWellService wellService,
|
IWellService wellService,
|
||||||
IConfiguration configuration,
|
IConfiguration configuration,
|
||||||
@ -481,7 +481,8 @@ namespace AsbCloudInfrastructure.Services.DrillingProgram
|
|||||||
.Options;
|
.Options;
|
||||||
using var context = new AsbCloudDbContext(contextOptions);
|
using var context = new AsbCloudDbContext(contextOptions);
|
||||||
var fileRepository = new FileRepository(context);
|
var fileRepository = new FileRepository(context);
|
||||||
var fileService = new FileService(fileRepository);
|
var fileStorageRepository = new FileStorageRepository();
|
||||||
|
var fileService = new FileService(fileRepository, fileStorageRepository);
|
||||||
var files = state.Parts.Select(p => fileService.GetUrl(p.File));
|
var files = state.Parts.Select(p => fileService.GetUrl(p.File));
|
||||||
DrillingProgramMaker.UniteExcelFiles(files, tempResultFilePath, state.Parts, well);
|
DrillingProgramMaker.UniteExcelFiles(files, tempResultFilePath, state.Parts, well);
|
||||||
await fileService.MoveAsync(idWell, null, idFileCategoryDrillingProgram, resultFileName, tempResultFilePath, token);
|
await fileService.MoveAsync(idWell, null, idFileCategoryDrillingProgram, resultFileName, tempResultFilePath, token);
|
||||||
|
@ -67,7 +67,8 @@ namespace AsbCloudInfrastructure.Services
|
|||||||
generator.Make(reportFileName);
|
generator.Make(reportFileName);
|
||||||
|
|
||||||
var fileRepository = new FileRepository(context);
|
var fileRepository = new FileRepository(context);
|
||||||
var fileService = new FileService(fileRepository);
|
var fileStorageRepository = new FileStorageRepository();
|
||||||
|
var fileService = new FileService(fileRepository, fileStorageRepository);
|
||||||
var fileInfo = await fileService.MoveAsync(idWell, idUser, ReportCategoryId, reportFileName, reportFileName, token);
|
var fileInfo = await fileService.MoveAsync(idWell, idUser, ReportCategoryId, reportFileName, reportFileName, token);
|
||||||
|
|
||||||
progressHandler.Invoke(new
|
progressHandler.Invoke(new
|
||||||
|
@ -22,7 +22,7 @@ namespace AsbCloudInfrastructure.Services
|
|||||||
public class WellFinalDocumentsService : IWellFinalDocumentsService
|
public class WellFinalDocumentsService : IWellFinalDocumentsService
|
||||||
{
|
{
|
||||||
private readonly IAsbCloudDbContext context;
|
private readonly IAsbCloudDbContext context;
|
||||||
private readonly IFileService fileService;
|
private readonly FileService fileService;
|
||||||
private readonly IUserService userService;
|
private readonly IUserService userService;
|
||||||
private readonly IWellService wellService;
|
private readonly IWellService wellService;
|
||||||
private readonly IConfiguration configuration;
|
private readonly IConfiguration configuration;
|
||||||
@ -32,7 +32,7 @@ namespace AsbCloudInfrastructure.Services
|
|||||||
private const int FileServiceThrewException = -1;
|
private const int FileServiceThrewException = -1;
|
||||||
|
|
||||||
public WellFinalDocumentsService(IAsbCloudDbContext context,
|
public WellFinalDocumentsService(IAsbCloudDbContext context,
|
||||||
IFileService fileService,
|
FileService fileService,
|
||||||
IUserService userService,
|
IUserService userService,
|
||||||
IWellService wellService,
|
IWellService wellService,
|
||||||
IConfiguration configuration,
|
IConfiguration configuration,
|
||||||
|
17
AsbCloudWebApi.Tests/IRepositoryFactory.cs
Normal file
17
AsbCloudWebApi.Tests/IRepositoryFactory.cs
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Threading;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
|
namespace AsbCloudWebApi.Tests
|
||||||
|
{
|
||||||
|
public interface IRepositoryFactory<TDto>
|
||||||
|
{
|
||||||
|
Task<int> DeleteAsync(int id, CancellationToken token);
|
||||||
|
Task<IEnumerable<TDto>> GetAllAsync(CancellationToken token);
|
||||||
|
TDto? GetOrDefault(int id);
|
||||||
|
Task<TDto?> GetOrDefaultAsync(int id, CancellationToken token);
|
||||||
|
Task<int> InsertAsync(TDto newItem, CancellationToken token);
|
||||||
|
Task<int> InsertRangeAsync(IEnumerable<TDto> newItems, CancellationToken token);
|
||||||
|
Task<int> UpdateAsync(TDto item, CancellationToken token);
|
||||||
|
}
|
||||||
|
}
|
42
AsbCloudWebApi.Tests/RepositoryFactory.cs
Normal file
42
AsbCloudWebApi.Tests/RepositoryFactory.cs
Normal file
@ -0,0 +1,42 @@
|
|||||||
|
using AsbCloudApp.Services;
|
||||||
|
using Moq;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Threading;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
|
namespace AsbCloudWebApi.Tests
|
||||||
|
{
|
||||||
|
public class RepositoryFactory
|
||||||
|
{
|
||||||
|
public static Mock<TRepository> Make<TRepository, TDto>(ICollection<TDto> data)
|
||||||
|
where TDto : AsbCloudApp.Data.IId
|
||||||
|
where TRepository : class, ICrudService<TDto>
|
||||||
|
{
|
||||||
|
var repositoryMock = new Mock<TRepository>();
|
||||||
|
|
||||||
|
repositoryMock.Setup(x => x.InsertAsync(It.IsAny<TDto>(), It.IsAny<CancellationToken>()))
|
||||||
|
.Returns((TDto dto, CancellationToken token) => {
|
||||||
|
var id = data.Max(x => x.Id);
|
||||||
|
dto.Id = ++id;
|
||||||
|
data.Add(dto);
|
||||||
|
return Task.FromResult(dto.Id);
|
||||||
|
});
|
||||||
|
repositoryMock.Setup(x => x.DeleteAsync(It.IsAny<int>(), It.IsAny<CancellationToken>()))
|
||||||
|
.Returns((int idFile, CancellationToken token) => {
|
||||||
|
var cnt = data.Count;
|
||||||
|
var dto = data.FirstOrDefault(x => x.Id == idFile);
|
||||||
|
data.Remove(dto);
|
||||||
|
return Task.FromResult(cnt - data.Count);
|
||||||
|
});
|
||||||
|
|
||||||
|
repositoryMock.Setup(x => x.GetAllAsync(It.IsAny<CancellationToken>())).ReturnsAsync(data);
|
||||||
|
repositoryMock.Setup(x => x.GetOrDefaultAsync(It.IsAny<int>(), It.IsAny<CancellationToken>()))
|
||||||
|
.Returns((int idFile, CancellationToken token) => {
|
||||||
|
return Task.FromResult(data.FirstOrDefault(x => x.Id == idFile));
|
||||||
|
});
|
||||||
|
|
||||||
|
return repositoryMock;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -78,7 +78,7 @@ namespace AsbCloudWebApi.Tests.ServicesTests
|
|||||||
new RelationCompanyWell { IdCompany = 3003, IdWell = 3002, },
|
new RelationCompanyWell { IdCompany = 3003, IdWell = 3002, },
|
||||||
};
|
};
|
||||||
|
|
||||||
private readonly Mock<IFileService> fileServiceMock;
|
private readonly Mock<FileService> fileServiceMock;
|
||||||
private readonly Mock<IUserService> userServiceMock;
|
private readonly Mock<IUserService> userServiceMock;
|
||||||
private readonly Mock<IWellService> wellServiceMock;
|
private readonly Mock<IWellService> wellServiceMock;
|
||||||
private readonly Mock<IConfiguration> configurationMock;
|
private readonly Mock<IConfiguration> configurationMock;
|
||||||
@ -97,7 +97,7 @@ namespace AsbCloudWebApi.Tests.ServicesTests
|
|||||||
db.RelationCompaniesWells.AddRange(relationsCompanyWell);
|
db.RelationCompaniesWells.AddRange(relationsCompanyWell);
|
||||||
db.SaveChanges();
|
db.SaveChanges();
|
||||||
|
|
||||||
fileServiceMock = new Mock<IFileService>();
|
fileServiceMock = new Mock<FileService>();
|
||||||
userServiceMock = new Mock<IUserService>();
|
userServiceMock = new Mock<IUserService>();
|
||||||
wellServiceMock = new Mock<IWellService>();
|
wellServiceMock = new Mock<IWellService>();
|
||||||
configurationMock = new Mock<IConfiguration>();
|
configurationMock = new Mock<IConfiguration>();
|
||||||
|
224
AsbCloudWebApi.Tests/ServicesTests/FileServiceTest.cs
Normal file
224
AsbCloudWebApi.Tests/ServicesTests/FileServiceTest.cs
Normal file
@ -0,0 +1,224 @@
|
|||||||
|
using AsbCloudApp.Data;
|
||||||
|
using AsbCloudApp.Repositories;
|
||||||
|
using AsbCloudApp.Services;
|
||||||
|
using AsbCloudDb.Model;
|
||||||
|
using AsbCloudInfrastructure.Repository;
|
||||||
|
using AsbCloudInfrastructure.Services;
|
||||||
|
using DocumentFormat.OpenXml.Spreadsheet;
|
||||||
|
using DocumentFormat.OpenXml.Wordprocessing;
|
||||||
|
using Moq;
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.IO;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using System.Threading;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using Xunit;
|
||||||
|
using static AsbCloudWebApi.Tests.TestHelpter;
|
||||||
|
|
||||||
|
namespace AsbCloudWebApi.Tests.ServicesTests
|
||||||
|
{
|
||||||
|
public class FileServiceTest
|
||||||
|
{
|
||||||
|
private FileService fileService;
|
||||||
|
|
||||||
|
private static UserDto Author = new UserDto {
|
||||||
|
Id = 1,
|
||||||
|
IdCompany = 1
|
||||||
|
};
|
||||||
|
|
||||||
|
private static List<FileMarkDto> FileMarks = new List<FileMarkDto> {
|
||||||
|
new FileMarkDto
|
||||||
|
{
|
||||||
|
Id = 132,
|
||||||
|
IdFile = 1742,
|
||||||
|
User = Author,
|
||||||
|
Comment = "qqq",
|
||||||
|
IdMarkType = 1,
|
||||||
|
DateCreated = DateTime.Now,
|
||||||
|
IsDeleted = false
|
||||||
|
},
|
||||||
|
new FileMarkDto
|
||||||
|
{
|
||||||
|
Id = 133,
|
||||||
|
IdFile = 1742,
|
||||||
|
User = Author,
|
||||||
|
Comment = "qqq3",
|
||||||
|
IdMarkType = 1,
|
||||||
|
DateCreated = DateTime.Now,
|
||||||
|
IsDeleted = false
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
private static List<FileInfoDto> Files = new List<FileInfoDto> {
|
||||||
|
new FileInfoDto {
|
||||||
|
Id = 1742,
|
||||||
|
IdAuthor = 1,
|
||||||
|
Author = Author,
|
||||||
|
IdWell = 90,
|
||||||
|
IdCategory = 10040,
|
||||||
|
Name = "test.txt",
|
||||||
|
Size = 0,
|
||||||
|
UploadDate = DateTime.Now,
|
||||||
|
FileMarks = FileMarks
|
||||||
|
},
|
||||||
|
new FileInfoDto
|
||||||
|
{
|
||||||
|
Id = 1743,
|
||||||
|
IdAuthor = 1,
|
||||||
|
Author = Author,
|
||||||
|
IdWell = 90,
|
||||||
|
IdCategory = 10021,
|
||||||
|
Name = "test1.txt",
|
||||||
|
Size = 0,
|
||||||
|
UploadDate = DateTime.Now
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
public FileServiceTest()
|
||||||
|
{
|
||||||
|
var repositoryMock = RepositoryFactory.Make<IFileRepository, FileInfoDto>(Files);
|
||||||
|
|
||||||
|
repositoryMock.Setup(x => x.GetByMarkId(It.IsAny<int>(), It.IsAny<CancellationToken>()))
|
||||||
|
.Returns((int idMark, CancellationToken token) => {
|
||||||
|
var data = Files.FirstOrDefault(x => x.FileMarks.Any(m => m.Id == idMark));
|
||||||
|
return Task.FromResult(data);
|
||||||
|
});
|
||||||
|
repositoryMock.Setup(x => x.GetInfoByIdsAsync(It.IsAny<IEnumerable<int>>(), It.IsAny<CancellationToken>()))
|
||||||
|
.Returns((int[] idsFile, CancellationToken token) => {
|
||||||
|
var data = Files.Where(x => idsFile.Contains(x.Id));
|
||||||
|
return Task.FromResult(data);
|
||||||
|
});
|
||||||
|
|
||||||
|
repositoryMock.Setup(x => x.DeleteAsync(It.IsAny<IEnumerable<int>>(), It.IsAny<CancellationToken>()))
|
||||||
|
.Returns((int[] idsFile, CancellationToken token) => {
|
||||||
|
var dtos = Files.Where(x => idsFile.Contains(x.Id)).ToArray();
|
||||||
|
Files.RemoveAll(x => dtos.Select(d => d.Id).Contains(x.Id));
|
||||||
|
return Task.FromResult(dtos.AsEnumerable());
|
||||||
|
});
|
||||||
|
|
||||||
|
repositoryMock.Setup(x => x.MarkFileMarkAsDeletedAsync(It.IsAny<IEnumerable<int>>(), It.IsAny<CancellationToken>()))
|
||||||
|
.Returns((int[] idsMarks, CancellationToken token) => {
|
||||||
|
var data = FileMarks.Where(m => idsMarks.Contains(m.Id));
|
||||||
|
|
||||||
|
foreach (var fileMark in data)
|
||||||
|
fileMark.IsDeleted = true;
|
||||||
|
|
||||||
|
var result = data.All(x => x.IsDeleted) ? 1 : 0;
|
||||||
|
return Task.FromResult(result);
|
||||||
|
});
|
||||||
|
|
||||||
|
repositoryMock.Setup(x => x.MarkAsDeletedAsync(It.IsAny<int>(), It.IsAny<CancellationToken>()))
|
||||||
|
.Returns((int idFile, CancellationToken token) => {
|
||||||
|
var result = Files.Where(x => x.Id == idFile).Any() ? 1 : 0;
|
||||||
|
return Task.FromResult(result);
|
||||||
|
});
|
||||||
|
|
||||||
|
repositoryMock.Setup(x => x.GetInfosByWellIdAsync(It.IsAny<int>(), It.IsAny<CancellationToken>()))
|
||||||
|
.Returns((int idWell, CancellationToken token) => {
|
||||||
|
var data = Files.Where(x => x.IdWell == idWell);
|
||||||
|
return Task.FromResult(data);
|
||||||
|
});
|
||||||
|
|
||||||
|
repositoryMock.Setup(x => x.GetInfosByCategoryAsync(It.IsAny<int>(), It.IsAny<int>(), It.IsAny<CancellationToken>()))
|
||||||
|
.Returns((int idWell, int idCategory, CancellationToken token) => {
|
||||||
|
var data = Files.Where(x => x.IdWell == idWell && x.IdCategory == idCategory);
|
||||||
|
return Task.FromResult(data);
|
||||||
|
});
|
||||||
|
|
||||||
|
repositoryMock.Setup(x => x.CreateFileMarkAsync(It.IsAny<FileMarkDto>(), It.IsAny<int>(), It.IsAny<CancellationToken>()))
|
||||||
|
.Returns((FileMarkDto dto, int idUser, CancellationToken token) => {
|
||||||
|
dto.Id = FileMarks.Max(x => x.Id) + 1;
|
||||||
|
dto.DateCreated = DateTime.UtcNow;
|
||||||
|
dto.User = null;
|
||||||
|
FileMarks.Add(dto);
|
||||||
|
|
||||||
|
var result = FileMarks.Any(x => x.Id == dto.Id) ? 1 : 0;
|
||||||
|
return Task.FromResult(result);
|
||||||
|
});
|
||||||
|
|
||||||
|
var storageRepositoryMock = new Mock<IFileStorageRepository>();
|
||||||
|
|
||||||
|
storageRepositoryMock.Setup(x => x.RootPath).Returns("files");
|
||||||
|
|
||||||
|
fileService = new FileService(repositoryMock.Object, storageRepositoryMock.Object);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task GetByMarkId_returns_FileInfo_by_idMark()
|
||||||
|
{
|
||||||
|
var data = await fileService.GetByMarkId(133, CancellationToken.None);
|
||||||
|
Assert.NotNull(data);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task GetInfoAsync_returns_FileInfo()
|
||||||
|
{
|
||||||
|
var data = await fileService.GetInfoAsync(1742, CancellationToken.None);
|
||||||
|
Assert.NotNull(data);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task GetInfoByIdsAsync_returns_FileInfo()
|
||||||
|
{
|
||||||
|
var data = await fileService.GetInfoByIdsAsync(new int[] { 1742, 1743 }, CancellationToken.None);
|
||||||
|
Assert.NotNull(data);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task SaveAsync_returns_FileInfo()
|
||||||
|
{
|
||||||
|
using var stream = new MemoryStream(Array.Empty<byte>());
|
||||||
|
var data = await fileService.SaveAsync(90, 1, 10040, "test.txt", stream, CancellationToken.None);
|
||||||
|
Assert.NotNull(data);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task DeleteAsync()
|
||||||
|
{
|
||||||
|
var result = await fileService.DeleteAsync(new int[] { 1743 }, CancellationToken.None);
|
||||||
|
Assert.True(result > 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task MarkFileMarkAsDeletedAsync()
|
||||||
|
{
|
||||||
|
var result = await fileService.MarkFileMarkAsDeletedAsync(new int[] { 132, 133 }, CancellationToken.None);
|
||||||
|
Assert.True(result > 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task MarkAsDeletedAsync()
|
||||||
|
{
|
||||||
|
var result = await fileService.MarkAsDeletedAsync(1742, CancellationToken.None);
|
||||||
|
Assert.True(result > 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task GetInfosByWellIdAsync_returns_FileInfo()
|
||||||
|
{
|
||||||
|
var data = await fileService.GetInfosByWellIdAsync(90, CancellationToken.None);
|
||||||
|
Assert.NotNull(data);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task GetInfosByCategoryAsync_returns_FileInfo()
|
||||||
|
{
|
||||||
|
var data = await fileService.GetInfosByCategoryAsync(90, 10040, CancellationToken.None);
|
||||||
|
Assert.NotNull(data);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task CreateFileMarkAsync()
|
||||||
|
{
|
||||||
|
var dto = new FileMarkDto {
|
||||||
|
Comment = "test",
|
||||||
|
IdFile = 1742,
|
||||||
|
IdMarkType = 1
|
||||||
|
};
|
||||||
|
var result = await fileService.CreateFileMarkAsync(dto, 1, CancellationToken.None);
|
||||||
|
Assert.True(result > 0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -17,7 +17,7 @@ namespace AsbCloudWebApi.Tests.ServicesTests
|
|||||||
{
|
{
|
||||||
private readonly AsbCloudDbContext context;
|
private readonly AsbCloudDbContext context;
|
||||||
private WellFinalDocumentsService service;
|
private WellFinalDocumentsService service;
|
||||||
private readonly Mock<IFileService> fileServiceMock;
|
private readonly Mock<FileService> fileServiceMock;
|
||||||
private readonly Mock<IUserService> userServiceMock;
|
private readonly Mock<IUserService> userServiceMock;
|
||||||
private readonly Mock<IWellService> wellServiceMock;
|
private readonly Mock<IWellService> wellServiceMock;
|
||||||
private readonly Mock<IConfiguration> configurationMock;
|
private readonly Mock<IConfiguration> configurationMock;
|
||||||
@ -44,7 +44,7 @@ namespace AsbCloudWebApi.Tests.ServicesTests
|
|||||||
context = TestHelpter.MakeTestContext();
|
context = TestHelpter.MakeTestContext();
|
||||||
context.SaveChanges();
|
context.SaveChanges();
|
||||||
|
|
||||||
fileServiceMock = new Mock<IFileService>();
|
fileServiceMock = new Mock<FileService>();
|
||||||
userServiceMock = new Mock<IUserService>();
|
userServiceMock = new Mock<IUserService>();
|
||||||
userServiceMock.Setup(x => x.GetAllAsync(CancellationToken.None)).Returns(Task.Run(() => users.Select(x => (UserExtendedDto)x)));
|
userServiceMock.Setup(x => x.GetAllAsync(CancellationToken.None)).Returns(Task.Run(() => users.Select(x => (UserExtendedDto)x)));
|
||||||
|
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
using AsbCloudDb.Model;
|
using AsbCloudApp.Services;
|
||||||
|
using AsbCloudDb.Model;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using Microsoft.EntityFrameworkCore.Diagnostics;
|
using Microsoft.EntityFrameworkCore.Diagnostics;
|
||||||
|
|
||||||
|
@ -20,10 +20,10 @@ namespace AsbCloudWebApi.Controllers
|
|||||||
[Authorize]
|
[Authorize]
|
||||||
public class FileController : ControllerBase
|
public class FileController : ControllerBase
|
||||||
{
|
{
|
||||||
private readonly IFileService fileService;
|
private readonly FileService fileService;
|
||||||
private readonly IWellService wellService;
|
private readonly IWellService wellService;
|
||||||
|
|
||||||
public FileController(IFileService fileService, IWellService wellService)
|
public FileController(FileService fileService, IWellService wellService)
|
||||||
{
|
{
|
||||||
this.fileService = fileService;
|
this.fileService = fileService;
|
||||||
this.wellService = wellService;
|
this.wellService = wellService;
|
||||||
|
@ -18,12 +18,12 @@ namespace AsbCloudWebApi.Controllers
|
|||||||
public class ReportController : ControllerBase
|
public class ReportController : ControllerBase
|
||||||
{
|
{
|
||||||
private readonly IReportService reportService;
|
private readonly IReportService reportService;
|
||||||
private readonly IFileService fileService;
|
private readonly FileService fileService;
|
||||||
private readonly IWellService wellService;
|
private readonly IWellService wellService;
|
||||||
private readonly IHubContext<ReportsHub> reportsHubContext;
|
private readonly IHubContext<ReportsHub> reportsHubContext;
|
||||||
|
|
||||||
public ReportController(IReportService reportService, IWellService wellService,
|
public ReportController(IReportService reportService, IWellService wellService,
|
||||||
IFileService fileService, IHubContext<ReportsHub> reportsHubContext)
|
FileService fileService, IHubContext<ReportsHub> reportsHubContext)
|
||||||
{
|
{
|
||||||
this.reportService = reportService;
|
this.reportService = reportService;
|
||||||
this.fileService = fileService;
|
this.fileService = fileService;
|
||||||
|
Loading…
Reference in New Issue
Block a user