mirror of
https://github.com/DrizzleTime/Foxel.git
synced 2026-09-06 16:17:06 +08:00
Refactor face clustering service and related interfaces
This commit is contained in:
@@ -0,0 +1,28 @@
|
|||||||
|
using Scalar.AspNetCore;
|
||||||
|
|
||||||
|
namespace Foxel.Extensions;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// API相关的扩展方法
|
||||||
|
/// </summary>
|
||||||
|
public static class ApiExtensions
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// 添加应用程序OpenAPI
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddApplicationOpenApi(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
services.AddOpenApi(opt => { opt.AddDocumentTransformer<BearerSecuritySchemeTransformer>(); });
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 使用应用程序OpenAPI
|
||||||
|
/// </summary>
|
||||||
|
public static WebApplication UseApplicationOpenApi(this WebApplication app)
|
||||||
|
{
|
||||||
|
app.MapOpenApi();
|
||||||
|
app.MapScalarApiReference();
|
||||||
|
return app;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,28 +0,0 @@
|
|||||||
using Microsoft.Extensions.FileProviders;
|
|
||||||
using Scalar.AspNetCore;
|
|
||||||
|
|
||||||
namespace Foxel.Extensions;
|
|
||||||
|
|
||||||
public static class ApplicationBuilderExtensions
|
|
||||||
{
|
|
||||||
public static void UseApplicationStaticFiles(this WebApplication app)
|
|
||||||
{
|
|
||||||
var uploadsPath = Path.Combine(Directory.GetCurrentDirectory(), "Uploads");
|
|
||||||
if (!Directory.Exists(uploadsPath))
|
|
||||||
{
|
|
||||||
Directory.CreateDirectory(uploadsPath);
|
|
||||||
}
|
|
||||||
|
|
||||||
app.UseStaticFiles(new StaticFileOptions
|
|
||||||
{
|
|
||||||
FileProvider = new PhysicalFileProvider(uploadsPath),
|
|
||||||
RequestPath = "/Uploads"
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void UseApplicationOpenApi(this WebApplication app)
|
|
||||||
{
|
|
||||||
app.MapOpenApi();
|
|
||||||
app.MapScalarApiReference();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -0,0 +1,56 @@
|
|||||||
|
using Foxel.Services.Initializer;
|
||||||
|
|
||||||
|
namespace Foxel.Extensions;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 应用程序配置扩展方法
|
||||||
|
/// </summary>
|
||||||
|
public static class ApplicationConfigurationExtensions
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// 配置应用程序中间件管道
|
||||||
|
/// </summary>
|
||||||
|
public static WebApplication ConfigureApplicationPipeline(this WebApplication app)
|
||||||
|
{
|
||||||
|
// 转发头处理
|
||||||
|
app.UseForwardedHeaders();
|
||||||
|
|
||||||
|
// 静态文件
|
||||||
|
app.UseApplicationStaticFiles();
|
||||||
|
|
||||||
|
// 开发环境特定配置
|
||||||
|
if (!app.Environment.IsDevelopment())
|
||||||
|
{
|
||||||
|
app.UseExceptionHandler("/Error", createScopeForErrors: true);
|
||||||
|
app.UseHsts();
|
||||||
|
}
|
||||||
|
|
||||||
|
// API文档
|
||||||
|
app.UseApplicationOpenApi();
|
||||||
|
|
||||||
|
// CORS
|
||||||
|
app.UseCors("MyAllowSpecificOrigins");
|
||||||
|
|
||||||
|
// 身份验证和授权
|
||||||
|
app.UseAuthentication();
|
||||||
|
app.UseAuthorization();
|
||||||
|
|
||||||
|
// 路由
|
||||||
|
app.MapControllers();
|
||||||
|
app.UseHttpsRedirection();
|
||||||
|
|
||||||
|
return app;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 初始化应用程序
|
||||||
|
/// </summary>
|
||||||
|
public static async Task<WebApplication> InitializeApplicationAsync(this WebApplication app)
|
||||||
|
{
|
||||||
|
using var scope = app.Services.CreateScope();
|
||||||
|
var initializer = scope.ServiceProvider.GetRequiredService<IDatabaseInitializer>();
|
||||||
|
await initializer.InitializeAsync();
|
||||||
|
|
||||||
|
return app;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,40 @@
|
|||||||
|
namespace Foxel.Extensions;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 应用程序服务配置扩展方法
|
||||||
|
/// </summary>
|
||||||
|
public static class ApplicationServiceExtensions
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// 添加所有应用程序服务
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddApplicationServices(this IServiceCollection services, IConfiguration configuration)
|
||||||
|
{
|
||||||
|
// 基础服务
|
||||||
|
services.AddControllers();
|
||||||
|
services.AddHttpServices();
|
||||||
|
|
||||||
|
// 数据库
|
||||||
|
services.AddApplicationDbContext(configuration);
|
||||||
|
|
||||||
|
// 核心业务服务
|
||||||
|
services.AddCoreServices();
|
||||||
|
services.AddManagementServices();
|
||||||
|
services.AddBackgroundServices();
|
||||||
|
services.AddAiServices();
|
||||||
|
services.AddInitializationServices();
|
||||||
|
|
||||||
|
// 身份验证和授权
|
||||||
|
services.AddApplicationAuthentication();
|
||||||
|
services.AddApplicationAuthorization();
|
||||||
|
services.AddApplicationCors();
|
||||||
|
|
||||||
|
// API文档
|
||||||
|
services.AddApplicationOpenApi();
|
||||||
|
|
||||||
|
// HTTP相关
|
||||||
|
services.AddForwardedHeaders();
|
||||||
|
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,75 @@
|
|||||||
|
using Microsoft.AspNetCore.Authentication.JwtBearer;
|
||||||
|
using Microsoft.AspNetCore.Authentication.Cookies;
|
||||||
|
using Microsoft.IdentityModel.Tokens;
|
||||||
|
using System.Text;
|
||||||
|
using Foxel.Services.Configuration;
|
||||||
|
|
||||||
|
namespace Foxel.Extensions;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 身份验证和授权相关的扩展方法
|
||||||
|
/// </summary>
|
||||||
|
public static class AuthenticationExtensions
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// 添加应用程序身份验证
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddApplicationAuthentication(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
// 构建临时服务提供者来获取配置服务
|
||||||
|
using var serviceProvider = services.BuildServiceProvider();
|
||||||
|
var configuration = serviceProvider.GetRequiredService<IConfigService>();
|
||||||
|
|
||||||
|
services.AddAuthentication(options =>
|
||||||
|
{
|
||||||
|
options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
|
||||||
|
options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
|
||||||
|
options.DefaultSignInScheme = CookieAuthenticationDefaults.AuthenticationScheme;
|
||||||
|
})
|
||||||
|
.AddJwtBearer(options =>
|
||||||
|
{
|
||||||
|
options.TokenValidationParameters = new TokenValidationParameters
|
||||||
|
{
|
||||||
|
ValidateIssuer = true,
|
||||||
|
ValidateAudience = true,
|
||||||
|
ValidateLifetime = true,
|
||||||
|
ValidateIssuerSigningKey = true,
|
||||||
|
ValidIssuer = configuration["Jwt:Issuer"],
|
||||||
|
ValidAudience = configuration["Jwt:Audience"],
|
||||||
|
IssuerSigningKey = new SymmetricSecurityKey(
|
||||||
|
Encoding.UTF8.GetBytes(configuration["Jwt:SecretKey"]))
|
||||||
|
};
|
||||||
|
});
|
||||||
|
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 添加应用程序授权
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddApplicationAuthorization(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
services.AddAuthorization(options =>
|
||||||
|
{
|
||||||
|
options.DefaultPolicy = new Microsoft.AspNetCore.Authorization.AuthorizationPolicyBuilder()
|
||||||
|
.RequireAuthenticatedUser()
|
||||||
|
.Build();
|
||||||
|
});
|
||||||
|
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 添加应用程序CORS配置
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddApplicationCors(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
services.AddCors(options =>
|
||||||
|
{
|
||||||
|
options.AddPolicy(name: "MyAllowSpecificOrigins",
|
||||||
|
policy => { policy.WithOrigins().AllowAnyOrigin().AllowAnyHeader().AllowAnyMethod(); });
|
||||||
|
});
|
||||||
|
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,94 @@
|
|||||||
|
using Foxel.Services;
|
||||||
|
using Foxel.Services.AI;
|
||||||
|
using Foxel.Services.Auth;
|
||||||
|
using Foxel.Services.Background;
|
||||||
|
using Foxel.Services.Background.Processors;
|
||||||
|
using Foxel.Services.Configuration;
|
||||||
|
using Foxel.Services.Initializer;
|
||||||
|
using Foxel.Services.Management;
|
||||||
|
using Foxel.Services.Mapping;
|
||||||
|
using Foxel.Services.Media;
|
||||||
|
using Foxel.Services.Storage;
|
||||||
|
using Foxel.Services.VectorDb;
|
||||||
|
|
||||||
|
namespace Foxel.Extensions;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 核心业务服务相关的扩展方法
|
||||||
|
/// </summary>
|
||||||
|
public static class CoreServiceExtensions
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// 添加核心业务服务
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddCoreServices(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
// 配置服务
|
||||||
|
services.AddSingleton<IConfigService, ConfigService>();
|
||||||
|
|
||||||
|
// 核心业务服务
|
||||||
|
services.AddSingleton<IAiService, AiService>();
|
||||||
|
services.AddSingleton<IPictureService, PictureService>();
|
||||||
|
services.AddSingleton<IAuthService, AuthService>();
|
||||||
|
services.AddSingleton<ITagService, TagService>();
|
||||||
|
services.AddSingleton<IAlbumService, AlbumService>();
|
||||||
|
services.AddSingleton<IStorageService, StorageService>();
|
||||||
|
services.AddSingleton<IMappingService, MappingService>();
|
||||||
|
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 添加管理服务
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddManagementServices(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
services.AddSingleton<IUserManagementService, UserManagementService>();
|
||||||
|
services.AddSingleton<IPictureManagementService, PictureManagementService>();
|
||||||
|
services.AddSingleton<IAlbumManagementService, AlbumManagementService>();
|
||||||
|
services.AddSingleton<ILogManagementService, LogManagementService>();
|
||||||
|
services.AddSingleton<IStorageManagementService, StorageManagementService>();
|
||||||
|
services.AddSingleton<IFaceManagementService, FaceManagementService>();
|
||||||
|
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 添加后台任务服务
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddBackgroundServices(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
services.AddSingleton<IBackgroundTaskQueue, BackgroundTaskQueue>();
|
||||||
|
services.AddHostedService<QueuedHostedService>();
|
||||||
|
|
||||||
|
// 任务处理器
|
||||||
|
services.AddSingleton<PictureTaskProcessor>();
|
||||||
|
services.AddSingleton<FaceRecognitionTaskProcessor>();
|
||||||
|
services.AddSingleton<VisualRecognitionTaskProcessor>();
|
||||||
|
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 添加AI和向量数据库服务
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddAiServices(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
services.AddSingleton<IFaceClusteringService, FaceClusteringService>();
|
||||||
|
services.AddSingleton<VectorDbManager>();
|
||||||
|
services.AddSingleton<IVectorDbService>(provider =>
|
||||||
|
provider.GetRequiredService<VectorDbManager>());
|
||||||
|
services.AddHostedService<VectorDbInitializer>();
|
||||||
|
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 添加初始化服务
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddInitializationServices(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
services.AddSingleton<IDatabaseInitializer, DatabaseInitializer>();
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,27 @@
|
|||||||
|
using Microsoft.EntityFrameworkCore;
|
||||||
|
|
||||||
|
namespace Foxel.Extensions;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 数据库相关的扩展方法
|
||||||
|
/// </summary>
|
||||||
|
public static class DatabaseExtensions
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// 添加应用程序数据库上下文
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddApplicationDbContext(this IServiceCollection services, IConfiguration configuration)
|
||||||
|
{
|
||||||
|
var connectionString = configuration.GetConnectionString("DefaultConnection");
|
||||||
|
if (string.IsNullOrEmpty(connectionString))
|
||||||
|
{
|
||||||
|
connectionString = Environment.GetEnvironmentVariable("DEFAULT_CONNECTION");
|
||||||
|
}
|
||||||
|
|
||||||
|
Console.WriteLine($"数据库连接: {connectionString}");
|
||||||
|
services.AddDbContextFactory<MyDbContext>(options =>
|
||||||
|
options.UseNpgsql(connectionString));
|
||||||
|
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,56 @@
|
|||||||
|
using Microsoft.AspNetCore.HttpOverrides;
|
||||||
|
using Microsoft.Extensions.FileProviders;
|
||||||
|
|
||||||
|
namespace Foxel.Extensions;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// HTTP相关的扩展方法
|
||||||
|
/// </summary>
|
||||||
|
public static class HttpExtensions
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// 添加HTTP相关服务
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddHttpServices(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
services.AddHttpClient();
|
||||||
|
services.AddHttpContextAccessor();
|
||||||
|
services.AddMemoryCache();
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 配置转发头信息
|
||||||
|
/// </summary>
|
||||||
|
public static IServiceCollection AddForwardedHeaders(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
services.Configure<ForwardedHeadersOptions>(options =>
|
||||||
|
{
|
||||||
|
options.ForwardedHeaders = ForwardedHeaders.XForwardedFor | ForwardedHeaders.XForwardedProto;
|
||||||
|
options.KnownNetworks.Clear();
|
||||||
|
options.KnownProxies.Clear();
|
||||||
|
});
|
||||||
|
|
||||||
|
return services;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 使用应用程序静态文件
|
||||||
|
/// </summary>
|
||||||
|
public static WebApplication UseApplicationStaticFiles(this WebApplication app)
|
||||||
|
{
|
||||||
|
var uploadsPath = Path.Combine(Directory.GetCurrentDirectory(), "Uploads");
|
||||||
|
if (!Directory.Exists(uploadsPath))
|
||||||
|
{
|
||||||
|
Directory.CreateDirectory(uploadsPath);
|
||||||
|
}
|
||||||
|
|
||||||
|
app.UseStaticFiles(new StaticFileOptions
|
||||||
|
{
|
||||||
|
FileProvider = new PhysicalFileProvider(uploadsPath),
|
||||||
|
RequestPath = "/Uploads"
|
||||||
|
});
|
||||||
|
|
||||||
|
return app;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,117 +0,0 @@
|
|||||||
using Foxel.Services;
|
|
||||||
using Microsoft.AspNetCore.Authentication.JwtBearer;
|
|
||||||
using Microsoft.AspNetCore.Authentication.Cookies;
|
|
||||||
using Microsoft.EntityFrameworkCore;
|
|
||||||
using Microsoft.IdentityModel.Tokens;
|
|
||||||
using System.Text;
|
|
||||||
using Foxel.Services.AI;
|
|
||||||
using Foxel.Services.Auth;
|
|
||||||
using Foxel.Services.Background;
|
|
||||||
using Foxel.Services.Configuration;
|
|
||||||
using Foxel.Services.Initializer;
|
|
||||||
using Foxel.Services.Management;
|
|
||||||
using Foxel.Services.Media;
|
|
||||||
using Foxel.Services.Storage;
|
|
||||||
using Foxel.Services.Background.Processors;
|
|
||||||
using Foxel.Services.Mapping;
|
|
||||||
using Foxel.Services.VectorDb;
|
|
||||||
|
|
||||||
namespace Foxel.Extensions;
|
|
||||||
|
|
||||||
public static class ServiceCollectionExtensions
|
|
||||||
{
|
|
||||||
public static void AddCoreServices(this IServiceCollection services)
|
|
||||||
{
|
|
||||||
services.AddSingleton<IConfigService, ConfigService>();
|
|
||||||
services.AddSingleton<IAiService, AiService>();
|
|
||||||
services.AddSingleton<IPictureService, PictureService>();
|
|
||||||
services.AddSingleton<IAuthService, AuthService>();
|
|
||||||
services.AddSingleton<ITagService, TagService>();
|
|
||||||
services.AddSingleton<IAlbumService, AlbumService>();
|
|
||||||
services.AddSingleton<IUserManagementService, UserManagementService>();
|
|
||||||
services.AddSingleton<IPictureManagementService, PictureManagementService>();
|
|
||||||
services.AddSingleton<IAlbumManagementService, AlbumManagementService>();
|
|
||||||
services.AddSingleton<ILogManagementService, LogManagementService>();
|
|
||||||
services.AddSingleton<IStorageManagementService, StorageManagementService>();
|
|
||||||
services.AddSingleton<IBackgroundTaskQueue, BackgroundTaskQueue>();
|
|
||||||
services.AddHostedService<QueuedHostedService>();
|
|
||||||
services.AddSingleton<IStorageService, StorageService>();
|
|
||||||
services.AddSingleton<PictureTaskProcessor>();
|
|
||||||
services.AddSingleton<FaceRecognitionTaskProcessor>();
|
|
||||||
services.AddSingleton<VisualRecognitionTaskProcessor>();
|
|
||||||
services.AddSingleton<IDatabaseInitializer, DatabaseInitializer>();
|
|
||||||
services.AddSingleton<IMappingService, MappingService>();
|
|
||||||
services.AddSingleton<IFaceManagementService, FaceManagementService>();
|
|
||||||
services.AddSingleton<IFaceClusteringService, FaceClusteringService>();
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void AddApplicationDbContext(this IServiceCollection services, IConfiguration configuration)
|
|
||||||
{
|
|
||||||
var connectionString = configuration.GetConnectionString("DefaultConnection");
|
|
||||||
if (string.IsNullOrEmpty(connectionString))
|
|
||||||
{
|
|
||||||
connectionString = Environment.GetEnvironmentVariable("DEFAULT_CONNECTION");
|
|
||||||
}
|
|
||||||
|
|
||||||
Console.WriteLine($"数据库连接: {connectionString}");
|
|
||||||
services.AddDbContextFactory<MyDbContext>(options =>
|
|
||||||
options.UseNpgsql(connectionString));
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void AddApplicationOpenApi(this IServiceCollection services)
|
|
||||||
{
|
|
||||||
services.AddOpenApi(opt => { opt.AddDocumentTransformer<BearerSecuritySchemeTransformer>(); });
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void AddApplicationAuthentication(this IServiceCollection services)
|
|
||||||
{
|
|
||||||
IConfigService configuration = services.BuildServiceProvider().GetRequiredService<IConfigService>();
|
|
||||||
services.AddAuthentication(options =>
|
|
||||||
{
|
|
||||||
options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
|
|
||||||
options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
|
|
||||||
options.DefaultSignInScheme = CookieAuthenticationDefaults.AuthenticationScheme;
|
|
||||||
})
|
|
||||||
.AddJwtBearer(options =>
|
|
||||||
{
|
|
||||||
options.TokenValidationParameters = new TokenValidationParameters
|
|
||||||
{
|
|
||||||
ValidateIssuer = true,
|
|
||||||
ValidateAudience = true,
|
|
||||||
ValidateLifetime = true,
|
|
||||||
ValidateIssuerSigningKey = true,
|
|
||||||
ValidIssuer = configuration["Jwt:Issuer"],
|
|
||||||
ValidAudience = configuration["Jwt:Audience"],
|
|
||||||
IssuerSigningKey = new SymmetricSecurityKey(
|
|
||||||
Encoding.UTF8.GetBytes(configuration["Jwt:SecretKey"]))
|
|
||||||
};
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void AddApplicationAuthorization(this IServiceCollection services)
|
|
||||||
{
|
|
||||||
services.AddAuthorization(options =>
|
|
||||||
{
|
|
||||||
options.DefaultPolicy = new Microsoft.AspNetCore.Authorization.AuthorizationPolicyBuilder()
|
|
||||||
.RequireAuthenticatedUser()
|
|
||||||
.Build();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void AddApplicationCors(this IServiceCollection services)
|
|
||||||
{
|
|
||||||
services.AddCors(options =>
|
|
||||||
{
|
|
||||||
options.AddPolicy(name: "MyAllowSpecificOrigins",
|
|
||||||
policy => { policy.WithOrigins().AllowAnyOrigin().AllowAnyHeader().AllowAnyMethod(); });
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void AddVectorDbServices(this IServiceCollection services)
|
|
||||||
{
|
|
||||||
services.AddSingleton<VectorDbManager>();
|
|
||||||
services.AddSingleton<IVectorDbService>(provider =>
|
|
||||||
provider.GetRequiredService<VectorDbManager>());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -0,0 +1,8 @@
|
|||||||
|
namespace Foxel.Models;
|
||||||
|
|
||||||
|
public class BatchDeleteResult
|
||||||
|
{
|
||||||
|
public int SuccessCount { get; set; }
|
||||||
|
public int FailedCount { get; set; }
|
||||||
|
public List<int> FailedIds { get; set; } = new();
|
||||||
|
}
|
||||||
+14
-39
@@ -1,52 +1,27 @@
|
|||||||
using Foxel.Extensions;
|
using Foxel.Extensions;
|
||||||
using Foxel.Services.Initializer;
|
|
||||||
using Foxel.Services.VectorDb;
|
|
||||||
using Microsoft.AspNetCore.HttpOverrides;
|
|
||||||
|
|
||||||
var builder = WebApplication.CreateBuilder(args);
|
var builder = WebApplication.CreateBuilder(args);
|
||||||
var environment = builder.Environment;
|
var environment = builder.Environment;
|
||||||
|
|
||||||
Console.WriteLine($"当前环境: {environment.EnvironmentName}");
|
Console.WriteLine($"当前环境: {environment.EnvironmentName}");
|
||||||
|
|
||||||
|
// 配置日志记录
|
||||||
builder.Logging.AddDatabaseLogging(config =>
|
builder.Logging.AddDatabaseLogging(config =>
|
||||||
{
|
{
|
||||||
config.MinLevel = LogLevel.Information;
|
config.MinLevel = LogLevel.Information;
|
||||||
config.Enabled = true;
|
config.Enabled = true;
|
||||||
});
|
});
|
||||||
builder.Services.AddMemoryCache();
|
|
||||||
builder.Services.AddApplicationDbContext(builder.Configuration);
|
// 添加所有应用程序服务
|
||||||
builder.Services.AddApplicationOpenApi();
|
builder.Services.AddApplicationServices(builder.Configuration);
|
||||||
builder.Services.AddControllers();
|
|
||||||
builder.Services.AddHttpClient();
|
|
||||||
builder.Services.AddCoreServices();
|
|
||||||
builder.Services.AddHttpContextAccessor();
|
|
||||||
builder.Services.AddApplicationAuthentication();
|
|
||||||
builder.Services.AddApplicationAuthorization();
|
|
||||||
builder.Services.AddApplicationCors();
|
|
||||||
builder.Services.AddVectorDbServices();
|
|
||||||
builder.Services.AddHostedService<VectorDbInitializer>();
|
|
||||||
builder.Services.Configure<ForwardedHeadersOptions>(options =>
|
|
||||||
{
|
|
||||||
options.ForwardedHeaders = ForwardedHeaders.XForwardedFor | ForwardedHeaders.XForwardedProto;
|
|
||||||
options.KnownNetworks.Clear();
|
|
||||||
options.KnownProxies.Clear();
|
|
||||||
});
|
|
||||||
var app = builder.Build();
|
var app = builder.Build();
|
||||||
|
|
||||||
using (var scope = app.Services.CreateScope())
|
// 初始化应用程序
|
||||||
{
|
await app.InitializeApplicationAsync();
|
||||||
var initializer = scope.ServiceProvider.GetRequiredService<IDatabaseInitializer>();
|
|
||||||
await initializer.InitializeAsync();
|
// 配置中间件管道
|
||||||
}
|
app.ConfigureApplicationPipeline();
|
||||||
app.UseForwardedHeaders();
|
|
||||||
app.UseApplicationStaticFiles();
|
// 启动应用程序
|
||||||
if (!app.Environment.IsDevelopment())
|
|
||||||
{
|
|
||||||
app.UseExceptionHandler("/Error", createScopeForErrors: true);
|
|
||||||
app.UseHsts();
|
|
||||||
}
|
|
||||||
app.UseApplicationOpenApi();
|
|
||||||
app.UseCors("MyAllowSpecificOrigins");
|
|
||||||
app.UseAuthentication();
|
|
||||||
app.UseAuthorization();
|
|
||||||
app.MapControllers();
|
|
||||||
app.UseHttpsRedirection();
|
|
||||||
app.Run();
|
app.Run();
|
||||||
@@ -12,11 +12,4 @@ public interface IUserManagementService
|
|||||||
Task<UserResponse> UpdateUserAsync(int id, string userName, string email, string role);
|
Task<UserResponse> UpdateUserAsync(int id, string userName, string email, string role);
|
||||||
Task<bool> DeleteUserAsync(int id);
|
Task<bool> DeleteUserAsync(int id);
|
||||||
Task<BatchDeleteResult> BatchDeleteUsersAsync(List<int> ids);
|
Task<BatchDeleteResult> BatchDeleteUsersAsync(List<int> ids);
|
||||||
}
|
}
|
||||||
|
|
||||||
public class BatchDeleteResult
|
|
||||||
{
|
|
||||||
public int SuccessCount { get; set; }
|
|
||||||
public int FailedCount { get; set; }
|
|
||||||
public List<int> FailedIds { get; set; } = new();
|
|
||||||
}
|
|
||||||
Reference in New Issue
Block a user