Tz2/Assets/Zion/Scripts/ERP/Interfaces/ApiConfigValidator.cs

450 lines
15 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using System;
using System.Collections.Generic;
using System.Linq;
using UnityEngine;
namespace Zion.ERP.Inventory
{
/// <summary>
/// API配置验证器
/// </summary>
public static class ApiConfigValidator
{
/// <summary>
/// 验证结果
/// </summary>
public class ValidationResult
{
/// <summary>
/// 是否验证通过
/// </summary>
public bool IsValid { get; set; }
/// <summary>
/// 错误信息列表
/// </summary>
public List<string> Errors { get; set; } = new List<string>();
/// <summary>
/// 警告信息列表
/// </summary>
public List<string> Warnings { get; set; } = new List<string>();
/// <summary>
/// 验证通过的信息
/// </summary>
public List<string> Info { get; set; } = new List<string>();
}
/// <summary>
/// 验证API配置
/// </summary>
/// <param name="config">配置数据</param>
/// <returns>验证结果</returns>
public static ValidationResult Validate(ApiConfigData config)
{
var result = new ValidationResult();
if (config == null)
{
result.IsValid = false;
result.Errors.Add("配置数据为空");
return result;
}
// 验证基本信息
ValidateBasicInfo(config, result);
// 验证环境配置
ValidateEnvironments(config, result);
// 验证API接口配置
ValidateEndpoints(config, result);
// 验证全局参数
ValidateGlobalParameters(config, result);
// 验证配置完整性
ValidateCompleteness(config, result);
// 设置验证结果
result.IsValid = result.Errors.Count == 0;
return result;
}
/// <summary>
/// 验证基本信息
/// </summary>
private static void ValidateBasicInfo(ApiConfigData config, ValidationResult result)
{
if (string.IsNullOrEmpty(config.Version))
{
result.Errors.Add("版本号不能为空");
}
else if (!IsValidVersion(config.Version))
{
result.Errors.Add($"版本号格式不正确:{config.Version}");
}
if (string.IsNullOrEmpty(config.Description))
{
result.Warnings.Add("建议添加配置描述");
}
result.Info.Add($"配置版本:{config.Version}");
result.Info.Add($"当前环境:{config.CurrentEnvironment}");
}
/// <summary>
/// 验证环境配置
/// </summary>
private static void ValidateEnvironments(ApiConfigData config, ValidationResult result)
{
if (config.Environments == null || config.Environments.Count == 0)
{
result.Errors.Add("未配置任何环境");
return;
}
// 检查环境名称重复
var environmentNames = config.Environments.Select(e => e.Environment).ToList();
var duplicateEnvironments = environmentNames.GroupBy(x => x).Where(g => g.Count() > 1).Select(g => g.Key);
foreach (var env in duplicateEnvironments)
{
result.Errors.Add($"环境名称重复:{env}");
}
// 验证每个环境配置
foreach (var env in config.Environments)
{
ValidateEnvironment(env, result);
}
// 检查当前环境是否存在
var currentEnv = config.Environments.FirstOrDefault(e => e.Environment == config.CurrentEnvironment);
if (currentEnv == null)
{
result.Errors.Add($"当前环境 {config.CurrentEnvironment} 不存在");
}
else if (!currentEnv.IsEnabled)
{
result.Warnings.Add($"当前环境 {config.CurrentEnvironment} 未启用");
}
result.Info.Add($"配置了 {config.Environments.Count} 个环境");
}
/// <summary>
/// 验证单个环境配置
/// </summary>
private static void ValidateEnvironment(ApiEnvironmentConfig env, ValidationResult result)
{
if (string.IsNullOrEmpty(env.BaseUrl))
{
result.Errors.Add($"环境 {env.Environment} 的基础URL不能为空");
}
else if (!IsValidUrl(env.BaseUrl))
{
result.Errors.Add($"环境 {env.Environment} 的基础URL格式不正确{env.BaseUrl}");
}
if (env.DefaultTimeout <= 0)
{
result.Errors.Add($"环境 {env.Environment} 的默认超时时间必须大于0");
}
if (env.DefaultRetryCount < 0)
{
result.Errors.Add($"环境 {env.Environment} 的默认重试次数不能为负数");
}
if (string.IsNullOrEmpty(env.Description))
{
result.Warnings.Add($"建议为环境 {env.Environment} 添加描述");
}
}
/// <summary>
/// 验证API接口配置
/// </summary>
private static void ValidateEndpoints(ApiConfigData config, ValidationResult result)
{
if (config.Endpoints == null || config.Endpoints.Count == 0)
{
result.Warnings.Add("未配置任何API接口");
return;
}
// 检查接口名称重复
var endpointNames = config.Endpoints.Select(e => e.Name).ToList();
var duplicateEndpoints = endpointNames.GroupBy(x => x).Where(g => g.Count() > 1).Select(g => g.Key);
foreach (var endpoint in duplicateEndpoints)
{
result.Errors.Add($"API接口名称重复{endpoint}");
}
// 验证每个接口配置
foreach (var endpoint in config.Endpoints)
{
ValidateEndpoint(endpoint, result);
}
result.Info.Add($"配置了 {config.Endpoints.Count} 个API接口");
result.Info.Add($"启用了 {config.Endpoints.Count(e => e.IsEnabled)} 个API接口");
}
/// <summary>
/// 验证单个API接口配置
/// </summary>
private static void ValidateEndpoint(ApiEndpoint endpoint, ValidationResult result)
{
if (string.IsNullOrEmpty(endpoint.Name))
{
result.Errors.Add("API接口名称不能为空");
}
else if (!IsValidEndpointName(endpoint.Name))
{
result.Errors.Add($"API接口名称格式不正确{endpoint.Name}");
}
if (string.IsNullOrEmpty(endpoint.Description))
{
result.Warnings.Add($"建议为API接口 {endpoint.Name} 添加描述");
}
if (string.IsNullOrEmpty(endpoint.UrlTemplate))
{
result.Errors.Add($"API接口 {endpoint.Name} 的URL模板不能为空");
}
else
{
ValidateUrlTemplate(endpoint.UrlTemplate, endpoint.Name, result);
}
if (string.IsNullOrEmpty(endpoint.Method))
{
result.Errors.Add($"API接口 {endpoint.Name} 的HTTP方法不能为空");
}
else if (!IsValidHttpMethod(endpoint.Method))
{
result.Errors.Add($"API接口 {endpoint.Name} 的HTTP方法不正确{endpoint.Method}");
}
if (endpoint.Timeout <= 0)
{
result.Errors.Add($"API接口 {endpoint.Name} 的超时时间必须大于0");
}
if (endpoint.RetryCount < 0)
{
result.Errors.Add($"API接口 {endpoint.Name} 的重试次数不能为负数");
}
// 验证参数配置
if (endpoint.Parameters != null)
{
foreach (var param in endpoint.Parameters)
{
ValidateParameter(param, $"API接口 {endpoint.Name}", result);
}
}
}
/// <summary>
/// 验证URL模板
/// </summary>
private static void ValidateUrlTemplate(string urlTemplate, string endpointName, ValidationResult result)
{
// 检查是否包含必需的基础URL占位符
if (!urlTemplate.Contains("{BaseUrl}") && !urlTemplate.StartsWith("http"))
{
result.Errors.Add($"API接口 {endpointName} 的URL模板缺少基础URL占位符或完整的URL");
}
// 检查占位符格式
var placeholders = ExtractPlaceholders(urlTemplate);
foreach (var placeholder in placeholders)
{
if (!IsValidPlaceholder(placeholder))
{
result.Warnings.Add($"API接口 {endpointName} 的URL模板包含未知占位符{placeholder}");
}
}
}
/// <summary>
/// 验证全局参数
/// </summary>
private static void ValidateGlobalParameters(ApiConfigData config, ValidationResult result)
{
if (config.GlobalParameters == null || config.GlobalParameters.Count == 0)
{
result.Info.Add("未配置全局参数");
return;
}
// 检查参数名称重复
var paramNames = config.GlobalParameters.Select(p => p.Name).ToList();
var duplicateParams = paramNames.GroupBy(x => x).Where(g => g.Count() > 1).Select(g => g.Key);
foreach (var param in duplicateParams)
{
result.Errors.Add($"全局参数名称重复:{param}");
}
// 验证每个参数
foreach (var param in config.GlobalParameters)
{
ValidateParameter(param, "全局参数", result);
}
result.Info.Add($"配置了 {config.GlobalParameters.Count} 个全局参数");
}
/// <summary>
/// 验证单个参数
/// </summary>
private static void ValidateParameter(ApiParameter param, string context, ValidationResult result)
{
if (string.IsNullOrEmpty(param.Name))
{
result.Errors.Add($"{context} 参数名称不能为空");
}
if (param.IsRequired && string.IsNullOrEmpty(param.Value))
{
result.Errors.Add($"{context} {param.Name} 是必需参数,但值为空");
}
if (string.IsNullOrEmpty(param.Description))
{
result.Warnings.Add($"建议为{context} {param.Name} 添加描述");
}
}
/// <summary>
/// 验证配置完整性
/// </summary>
private static void ValidateCompleteness(ApiConfigData config, ValidationResult result)
{
// 检查是否有启用的环境
var enabledEnvironments = config.Environments?.Where(e => e.IsEnabled).ToList();
if (enabledEnvironments == null || enabledEnvironments.Count == 0)
{
result.Errors.Add("没有启用的环境配置");
}
// 检查是否有启用的API接口
var enabledEndpoints = config.Endpoints?.Where(e => e.IsEnabled).ToList();
if (enabledEndpoints == null || enabledEndpoints.Count == 0)
{
result.Warnings.Add("没有启用的API接口");
}
// 检查配置的完整性
if (config.Environments != null && config.Environments.Count > 0 &&
config.Endpoints != null && config.Endpoints.Count > 0)
{
result.Info.Add("配置结构完整");
}
}
/// <summary>
/// 验证版本号格式
/// </summary>
private static bool IsValidVersion(string version)
{
return System.Text.RegularExpressions.Regex.IsMatch(version, @"^\d+\.\d+\.\d+$");
}
/// <summary>
/// 验证URL格式
/// </summary>
private static bool IsValidUrl(string url)
{
return Uri.TryCreate(url, UriKind.Absolute, out _);
}
/// <summary>
/// 验证API接口名称格式
/// </summary>
private static bool IsValidEndpointName(string name)
{
return System.Text.RegularExpressions.Regex.IsMatch(name, @"^[A-Za-z][A-Za-z0-9_]*$");
}
/// <summary>
/// 验证HTTP方法
/// </summary>
private static bool IsValidHttpMethod(string method)
{
var validMethods = new[] { "GET", "POST", "PUT", "DELETE", "PATCH", "HEAD", "OPTIONS" };
return validMethods.Contains(method.ToUpper());
}
/// <summary>
/// 验证占位符
/// </summary>
private static bool IsValidPlaceholder(string placeholder)
{
var validPlaceholders = new[] { "BaseUrl", "PaperId", "ExamRoomId" };
return validPlaceholders.Contains(placeholder);
}
/// <summary>
/// 提取URL模板中的占位符
/// </summary>
private static List<string> ExtractPlaceholders(string urlTemplate)
{
var placeholders = new List<string>();
var matches = System.Text.RegularExpressions.Regex.Matches(urlTemplate, @"\{([^}]+)\}");
foreach (System.Text.RegularExpressions.Match match in matches)
{
placeholders.Add(match.Groups[1].Value);
}
return placeholders;
}
/// <summary>
/// 打印验证结果
/// </summary>
public static void PrintValidationResult(ValidationResult result)
{
if (result.IsValid)
{
Debug.Log("✅ API配置验证通过");
}
else
{
Debug.LogError("❌ API配置验证失败");
}
if (result.Errors.Count > 0)
{
Debug.LogError("错误信息:");
foreach (var error in result.Errors)
{
Debug.LogError($" - {error}");
}
}
if (result.Warnings.Count > 0)
{
Debug.LogWarning("警告信息:");
foreach (var warning in result.Warnings)
{
Debug.LogWarning($" - {warning}");
}
}
if (result.Info.Count > 0)
{
Debug.Log("信息:");
foreach (var info in result.Info)
{
Debug.Log($" - {info}");
}
}
}
}
}