forked from amkovkov/GranuSightSoftware2
161 lines
6.6 KiB
C#
161 lines
6.6 KiB
C#
using System.CommandLine;
|
|
|
|
using Microsoft.EntityFrameworkCore;
|
|
using Microsoft.Extensions.Hosting;
|
|
using Microsoft.Extensions.Logging;
|
|
using Microsoft.Extensions.DependencyInjection;
|
|
using Microsoft.Extensions.Configuration;
|
|
|
|
using GSS2.Core;
|
|
using GSS2.Core.Hardware;
|
|
using GSS2.Core.Analysis.AmineContent.Database.Calibration;
|
|
using GSS2.Core.Analysis.AmineContent.Database.Results;
|
|
|
|
namespace GSS2.Commands;
|
|
|
|
public static class ImageStorageClear
|
|
{
|
|
private class ImageStorageClearWorker : BackgroundService
|
|
{
|
|
private readonly ILogger<ImageStorageClearWorker> _logger;
|
|
private readonly IHostApplicationLifetime _applicationLifetime;
|
|
private readonly AmineContentCalibrationContext _context;
|
|
private readonly ImageStorageService _imageStorage;
|
|
|
|
public ImageStorageClearWorker(
|
|
ILogger<ImageStorageClearWorker> logger,
|
|
IHostApplicationLifetime applicationLifetime,
|
|
AmineContentCalibrationContext context,
|
|
ImageStorageService imageStorage
|
|
)
|
|
{
|
|
_applicationLifetime = applicationLifetime;
|
|
_logger = logger;
|
|
_context = context;
|
|
_imageStorage = imageStorage;
|
|
}
|
|
|
|
protected override async Task ExecuteAsync(CancellationToken stoppingToken)
|
|
{
|
|
// Логгируем информацию
|
|
_logger.LogInformation("Очистка хранилища от неиспользуеммых изображений...");
|
|
|
|
// Получаем все изобрважения из базы данных
|
|
var recordsFiles = _context.ImageRecords.Select(r => r.ImagePath);
|
|
// Получаем все изобрважения в хранилище
|
|
var storedFiles = _imageStorage.ListFiles()
|
|
.Select(Path.GetFileName)
|
|
.OfType<string>();
|
|
|
|
// Находим неиспользуеммые изображения
|
|
var unusedFiles = storedFiles.Except(recordsFiles)
|
|
.ToList()
|
|
.Order();
|
|
|
|
// Если неиспользуеммых изображений нет, то закрываемся
|
|
if (unusedFiles is null || unusedFiles.Count() == 0)
|
|
{
|
|
_logger.LogInformation("Неиспользуеммые изображения не найдены");
|
|
_applicationLifetime.StopApplication();
|
|
return;
|
|
}
|
|
|
|
_logger.LogInformation("Найдено неиспользуеммых изображений: {}\n\t{}", unusedFiles.Count(), string.Join("\n\t", unusedFiles));
|
|
|
|
// Пока пользователь не выдал правильное действие или не закрыл приложение
|
|
while (!stoppingToken.IsCancellationRequested)
|
|
{
|
|
// Задаём вопрос
|
|
_logger.LogInformation("Удалить эти файлы? (Да/Нет) ");
|
|
// Читаем консоль
|
|
var input = Console.ReadLine()?.Trim().ToLower();
|
|
|
|
// Если нет, то выходим
|
|
if (input == "n" || input == "no" || input == "н" || input == "нет")
|
|
break;
|
|
// Если да, то удалёем файлы и выходим
|
|
if (input == "y" || input == "yes" || input == "д" || input == "да")
|
|
{
|
|
foreach (var file in unusedFiles)
|
|
_imageStorage.Delete(file);
|
|
break;
|
|
}
|
|
}
|
|
|
|
_applicationLifetime.StopApplication();
|
|
}
|
|
}
|
|
|
|
public static readonly RootCommand RootCommand;
|
|
private static readonly Command Command;
|
|
|
|
static ImageStorageClear()
|
|
{
|
|
// Создаём команды, опции, аргументы и пр.
|
|
RootCommand = new("Очистить хранилище от неиспользуемых изображений");
|
|
Command = new("image-storage-clear")
|
|
{
|
|
Description = "Очистить хранилище от неиспользуемых изображений"
|
|
};
|
|
|
|
// Изменяем описания стандартных опций
|
|
Helper.TranslateDefaultOptionDescriptions(RootCommand);
|
|
|
|
// Наполняем команды
|
|
RootCommand.SetAction(CommandAction);
|
|
|
|
Command.SetAction(CommandAction);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Получить команду как корневую
|
|
/// </summary>
|
|
public static RootCommand GetCommand() => RootCommand;
|
|
|
|
/// <summary>
|
|
/// Зарегистрировать команду как подкоманду
|
|
/// </summary>
|
|
/// <param name="command">Команда в которой необходимо зарегистрировать подкоманду</param>
|
|
public static void RegisterCommand(Command command) => command.Add(Command);
|
|
|
|
private static void CommandAction(ParseResult result)
|
|
{
|
|
// Создаём хост
|
|
var builder = Host.CreateApplicationBuilder();
|
|
|
|
// Добавляем конфигурацию из appsettings.json
|
|
builder.Configuration.AddAppSettingsJson();
|
|
|
|
// Конфигурируем логгер
|
|
builder.Logging.ConfigureLogging();
|
|
|
|
// Добавляем сервисы баз данных
|
|
builder.Services.AddAmineContentCalibrationContext(builder.Configuration);
|
|
builder.Services.AddAmineContentResultsContext(builder.Configuration);
|
|
|
|
// Добавляем сервисы аппаратной части
|
|
builder.Services.AddImageStorageService(new DirectoryInfo(builder.Configuration.GetValue<string>("ImageStorage") ?? "images"));
|
|
|
|
// Добавляем рабочий сервис
|
|
builder.Services.AddHostedService<ImageStorageClearWorker>();
|
|
|
|
// Собираем хост
|
|
var host = builder.Build();
|
|
|
|
// Применяем миграции баз данных если их схема данных изменялась
|
|
using (var scope = host.Services.CreateScope())
|
|
{
|
|
var context = scope.ServiceProvider.GetRequiredService<AmineContentCalibrationContext>();
|
|
context.Database.Migrate();
|
|
}
|
|
using (var scope = host.Services.CreateScope())
|
|
{
|
|
var context = scope.ServiceProvider.GetRequiredService<AmineContentResultsContext>();
|
|
context.Database.Migrate();
|
|
}
|
|
|
|
// Запускаем хост
|
|
host.Run();
|
|
}
|
|
}
|