151 lines
4.5 KiB
C#
151 lines
4.5 KiB
C#
using Server.WatchBody.Web;
|
||
using Server.WatchBody.Web.Config;
|
||
using Server.WatchBody.Web.Db;
|
||
using Server.WatchBody.Fetch;
|
||
using Server.WatchBody.Import;
|
||
using Server.WatchBody.Web.Services;
|
||
|
||
// Точка входа сервера (m02; режимы — requirements 2.3, З-36):
|
||
// --mode serve REST API (по умолчанию)
|
||
// --mode migrate применение 2-db\migrations\ по журналу src.migration
|
||
// --config <path> путь к appsettings (иначе WATCHBODY_APPSETTINGS либо
|
||
// appsettings.json рядом с исполняемым файлом)
|
||
// Валидация конфига — фатальна: лог + stderr, код возврата 1;
|
||
// migrate: успех — 0, сбой — 1.
|
||
|
||
string? mode = null, configArg = null;
|
||
for (var i = 0; i < args.Length - 1; i++)
|
||
{
|
||
switch (args[i])
|
||
{
|
||
case "--mode":
|
||
mode = args[i + 1];
|
||
break;
|
||
case "--config":
|
||
configArg = args[i + 1];
|
||
break;
|
||
}
|
||
}
|
||
mode ??= "serve";
|
||
|
||
var configPath = configArg
|
||
?? Environment.GetEnvironmentVariable("WATCHBODY_APPSETTINGS")
|
||
?? Path.Combine(AppContext.BaseDirectory, "appsettings.json");
|
||
|
||
ServerConfig config;
|
||
try
|
||
{
|
||
config = ServerConfig.Load(configPath);
|
||
}
|
||
catch (Exception e)
|
||
{
|
||
Console.Error.WriteLine($"конфиг {configPath} не читается: {e.Message}");
|
||
return 1;
|
||
}
|
||
|
||
if (mode == "migrate")
|
||
{
|
||
try
|
||
{
|
||
var applied = new MigrationRunner(
|
||
new PostgresConnectionString(config.DbConnectionString)).Apply(config.MigrationsDir);
|
||
Console.WriteLine($"migrate: применено миграций — {applied}");
|
||
return 0;
|
||
}
|
||
catch (Exception e)
|
||
{
|
||
Console.Error.WriteLine($"migrate: сбой — {e.Message}");
|
||
return 1;
|
||
}
|
||
}
|
||
|
||
if (mode == "import")
|
||
{
|
||
try
|
||
{
|
||
var connectionStringImport = new PostgresConnectionString(config.DbConnectionString);
|
||
Directory.CreateDirectory(config.ImportDir);
|
||
Directory.CreateDirectory(config.ImportArchiveDir);
|
||
var (processed, failed) = new ImportService(connectionStringImport).Run(
|
||
config.ImportDir, config.ImportArchiveDir);
|
||
Console.WriteLine($"import: обработано {processed}, сбоев {failed}");
|
||
return failed == 0 ? 0 : 2;
|
||
}
|
||
catch (Exception e)
|
||
{
|
||
Console.Error.WriteLine($"import: авария конфигурации — {e.Message}");
|
||
return 1;
|
||
}
|
||
}
|
||
|
||
if (mode == "fetch")
|
||
{
|
||
if (config.GarminLogin.Length == 0 || config.GarminPassword.Length == 0 ||
|
||
config.GarminAthleteName.Length == 0)
|
||
{
|
||
Console.Error.WriteLine(
|
||
"fetch: требуются Garmin.Login, Garmin.Password и Garmin.AthleteName");
|
||
return 1;
|
||
}
|
||
try
|
||
{
|
||
Directory.CreateDirectory(config.GarminDownloadDir);
|
||
var client = new GarminClient(
|
||
config.GarminLogin, config.GarminPassword, config.GarminBaseUrl);
|
||
var (downloaded, skipped, failed) = new FitFetcher(
|
||
new PostgresConnectionString(config.DbConnectionString),
|
||
client, config.GarminDownloadDir, config.GarminAthleteName
|
||
).FetchNew();
|
||
Console.WriteLine($"fetch: скачано {downloaded}, пропущено {skipped}, сбоев {failed}");
|
||
return failed == 0 ? 0 : 2;
|
||
}
|
||
catch (GarminAuthException e)
|
||
{
|
||
Console.Error.WriteLine(
|
||
$"fetch: логин Garmin не удался — {e.Message}; " +
|
||
"fallback: папка импорта (--mode import)");
|
||
return 2;
|
||
}
|
||
catch (FetchException e)
|
||
{
|
||
Console.Error.WriteLine($"fetch: {e.Message}");
|
||
return 1;
|
||
}
|
||
catch (Exception e)
|
||
{
|
||
Console.Error.WriteLine($"fetch: авария — {e.Message}");
|
||
return 1;
|
||
}
|
||
}
|
||
|
||
if (mode != "serve")
|
||
{
|
||
Console.Error.WriteLine($"неизвестный режим '{mode}' (serve|import|fetch|migrate)");
|
||
return 1;
|
||
}
|
||
|
||
var errors = config.Validate();
|
||
if (errors.Count > 0)
|
||
{
|
||
foreach (var error in errors) Console.Error.WriteLine($"конфиг: {error}");
|
||
return 1;
|
||
}
|
||
|
||
var connectionString = new PostgresConnectionString(config.DbConnectionString);
|
||
try
|
||
{
|
||
WebAppStartup.Initialize(connectionString, config);
|
||
}
|
||
catch (Exception e)
|
||
{
|
||
Console.Error.WriteLine($"инициализация не удалась: {e.Message}");
|
||
return 1;
|
||
}
|
||
|
||
var builder = WebApplication.CreateBuilder(args);
|
||
var app = WebAppStartup.Build(builder, config, connectionString);
|
||
app.Run();
|
||
return 0;
|
||
|
||
public partial class Program;
|