using Furion;
|
using Furion.DatabaseAccessor;
|
using Furion.DistributedIDGenerator;
|
using Mapster;
|
using Microsoft.AspNetCore.Mvc.ActionConstraints;
|
using Microsoft.AspNetCore.Mvc.Controllers;
|
using Microsoft.AspNetCore.Routing;
|
using Microsoft.EntityFrameworkCore;
|
using Microsoft.Extensions.DependencyInjection;
|
using System;
|
using System.Collections.Generic;
|
using System.Linq;
|
using System.Text;
|
using System.Threading;
|
using System.Threading.Tasks;
|
|
namespace FlexJobApi.Core
|
{
|
/// <summary>
|
/// 资源工具
|
/// </summary>
|
public static class ResourceUtils
|
{
|
/// <summary>
|
/// 生成资源
|
/// </summary>
|
/// <param name="cancellationToken"></param>
|
/// <returns></returns>
|
public static async Task BuildWebApis(CancellationToken cancellationToken = default)
|
{
|
var traceId = App.GetTraceId() ?? IDGen.NextID().ToString();
|
var scopeFactory = App.GetService<IServiceScopeFactory>();
|
var serviceScope = scopeFactory.CreateScope();
|
var rep = serviceScope.ServiceProvider.GetRequiredService<IRepository<Resource>>();
|
var endpointDataSource = App.GetService<EndpointDataSource>();
|
var routeEndpoints = endpointDataSource.Endpoints.OfType<RouteEndpoint>();
|
var xmlDoc = await XmlDocUtils.GetXmlDocAsync();
|
var enumWebApiMethods = await EnumUtils.GetModel<EnumWebApiMethod>();
|
var webApis = await rep.AsQueryable().ToListAsync();
|
foreach (var routeEndpoint in routeEndpoints)
|
{
|
var model = new ResourceModel();
|
model.TraceId = traceId;
|
model.Route = "/" + routeEndpoint.RoutePattern.RawText;
|
var controllerActionDescriptor = routeEndpoint.Metadata.GetMetadata<ControllerActionDescriptor>();
|
var methodInfo = controllerActionDescriptor.MethodInfo;
|
var methodInfoXmlDoc = await controllerActionDescriptor.MethodInfo.GetXmlDocMemberAsync(xmlDoc);
|
var controllerTypeXmlDoc = await methodInfo.DeclaringType?.GetXmlDocMemberAsync();
|
model.Code = methodInfoXmlDoc.Name;
|
model.Service = methodInfo.Module.Name.Split(".")[1];
|
model.Method = enumWebApiMethods.GetEnum((controllerActionDescriptor.ActionConstraints[0] as HttpMethodActionConstraint).HttpMethods.FirstOrDefault());
|
model.Name = $"{controllerTypeXmlDoc?.Summary ?? "没写注释"}-{methodInfoXmlDoc?.Summary ?? "没写注释"}";
|
model.RequestTypeName = methodInfo.GetParameters().FirstOrDefault().ParameterType.FullName;
|
var returnType = methodInfo.ReturnType;
|
if (returnType.IsGenericType && returnType.GetGenericTypeDefinition() == typeof(Task<>))
|
returnType = returnType.GetGenericArguments()[0];
|
if (returnType != null && returnType != typeof(Task))
|
model.ResponseTypeName = methodInfo.ReturnType.FullName;
|
|
var webApi = webApis.FirstOrDefault(it => it.Route == model.Route && it.Method == model.Method);
|
if (webApi == null)
|
{
|
webApi = new Resource();
|
model.Adapt(webApi);
|
await rep.InsertAsync(webApi);
|
webApis.Add(webApi);
|
}
|
else
|
{
|
model.Adapt(webApi);
|
await rep.UpdateAsync(webApi);
|
}
|
}
|
var expiredWebApis = webApis.Where(it => it.TraceId != traceId).ToList();
|
foreach (var webApi in expiredWebApis)
|
{
|
webApi.IsExpired = true;
|
await rep.UpdateAsync(webApi);
|
}
|
|
await rep.SaveNowAsync();
|
}
|
}
|
}
|