入职任务预览,入职任务cope,验证填入的信息
This commit is contained in:
+12
@@ -0,0 +1,12 @@
|
||||
namespace SimpleAdmin.Application;
|
||||
|
||||
/// <summary>
|
||||
/// 校验任务合同变量的必填状态和员工动态变量数据类型。
|
||||
/// </summary>
|
||||
public interface IOnboardingContractVariableValidationService : ITransient
|
||||
{
|
||||
/// <summary>
|
||||
/// 校验指定任务的全部合同变量快照。
|
||||
/// </summary>
|
||||
Task Validate(long taskId);
|
||||
}
|
||||
+187
@@ -0,0 +1,187 @@
|
||||
namespace SimpleAdmin.Application;
|
||||
|
||||
/// <summary>
|
||||
/// 统一校验任务合同变量,确保最终提交的数据可以安全用于合同生成。
|
||||
/// </summary>
|
||||
public class OnboardingContractVariableValidationService
|
||||
: IOnboardingContractVariableValidationService
|
||||
{
|
||||
private readonly SqlSugarScope _db;
|
||||
|
||||
public OnboardingContractVariableValidationService()
|
||||
{
|
||||
_db = DbContext.DB;
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public async Task Validate(long taskId)
|
||||
{
|
||||
var contracts = await _db.Queryable<ObTaskContract>()
|
||||
.Where(item => item.TaskId == taskId)
|
||||
.ToListAsync();
|
||||
if (contracts.Count == 0)
|
||||
return;
|
||||
|
||||
var contractIds = contracts
|
||||
.Select(item => item.Id)
|
||||
.ToList();
|
||||
var templateVersionIds = contracts
|
||||
.Select(item => item.TemplateVersionId)
|
||||
.Distinct()
|
||||
.ToList();
|
||||
var variables = await _db.Queryable<ObTaskContractVariable>()
|
||||
.Where(item => contractIds.Contains(item.TaskContractId))
|
||||
.ToListAsync();
|
||||
var definitions = await _db.Queryable<ObTemplateVariable>()
|
||||
.Where(item => templateVersionIds.Contains(item.TemplateVersionId))
|
||||
.ToListAsync();
|
||||
|
||||
foreach (var contract in contracts)
|
||||
{
|
||||
var contractDefinitions = definitions
|
||||
.Where(item => item.TemplateVersionId == contract.TemplateVersionId)
|
||||
.OrderBy(item => item.SortCode);
|
||||
|
||||
foreach (var definition in contractDefinitions)
|
||||
{
|
||||
var variable = variables.FirstOrDefault(item =>
|
||||
item.TaskContractId == contract.Id
|
||||
&& item.VariableCode == definition.VariableCode);
|
||||
var value = variable?.VariableValue?.Trim();
|
||||
|
||||
if (definition.Required && string.IsNullOrWhiteSpace(value))
|
||||
{
|
||||
throw Oops.Bah(
|
||||
$"合同“{contract.ContractName}”的必填变量“{definition.VariableName}”尚未填写");
|
||||
}
|
||||
|
||||
if (string.IsNullOrWhiteSpace(value)
|
||||
|| definition.VariableType != ContractVariableType.Employee)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
ValidateDataType(contract.ContractName, definition, value);
|
||||
ValidateOptions(contract.ContractName, definition, value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static void ValidateDataType(
|
||||
string contractName,
|
||||
ObTemplateVariable definition,
|
||||
string value)
|
||||
{
|
||||
var dataType = definition.DataType?.Trim().ToLowerInvariant() ?? "string";
|
||||
switch (dataType)
|
||||
{
|
||||
case "string":
|
||||
return;
|
||||
case "number":
|
||||
var numberIsValid = decimal.TryParse(
|
||||
value,
|
||||
global::System.Globalization.NumberStyles.Number,
|
||||
global::System.Globalization.CultureInfo.InvariantCulture,
|
||||
out _);
|
||||
if (!numberIsValid)
|
||||
{
|
||||
throw Oops.Bah(
|
||||
$"合同“{contractName}”的变量“{definition.VariableName}”必须填写数字");
|
||||
}
|
||||
|
||||
return;
|
||||
case "date":
|
||||
var dateIsValid = DateTime.TryParseExact(
|
||||
value,
|
||||
"yyyy-MM-dd",
|
||||
global::System.Globalization.CultureInfo.InvariantCulture,
|
||||
global::System.Globalization.DateTimeStyles.None,
|
||||
out _);
|
||||
if (!dateIsValid)
|
||||
{
|
||||
throw Oops.Bah(
|
||||
$"合同“{contractName}”的变量“{definition.VariableName}”必须填写正确日期");
|
||||
}
|
||||
|
||||
return;
|
||||
default:
|
||||
throw Oops.Bah(
|
||||
$"合同“{contractName}”的变量“{definition.VariableName}”数据类型配置不正确");
|
||||
}
|
||||
}
|
||||
|
||||
private static void ValidateOptions(
|
||||
string contractName,
|
||||
ObTemplateVariable definition,
|
||||
string value)
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(definition.OptionsJson))
|
||||
return;
|
||||
|
||||
var options = ParseOptions(contractName, definition);
|
||||
if (options.Contains(value))
|
||||
return;
|
||||
|
||||
throw Oops.Bah(
|
||||
$"合同“{contractName}”的变量“{definition.VariableName}”必须从配置选项中选择");
|
||||
}
|
||||
|
||||
private static HashSet<string> ParseOptions(
|
||||
string contractName,
|
||||
ObTemplateVariable definition)
|
||||
{
|
||||
try
|
||||
{
|
||||
using var document = global::System.Text.Json.JsonDocument.Parse(
|
||||
definition.OptionsJson);
|
||||
if (document.RootElement.ValueKind != global::System.Text.Json.JsonValueKind.Array)
|
||||
throw new global::System.Text.Json.JsonException();
|
||||
|
||||
var options = document.RootElement
|
||||
.EnumerateArray()
|
||||
.Select(GetOptionValue)
|
||||
.Where(item => !string.IsNullOrWhiteSpace(item))
|
||||
.ToHashSet(StringComparer.Ordinal);
|
||||
|
||||
if (options.Count == 0)
|
||||
throw new global::System.Text.Json.JsonException();
|
||||
|
||||
return options;
|
||||
}
|
||||
catch (global::System.Text.Json.JsonException)
|
||||
{
|
||||
throw Oops.Bah(
|
||||
$"合同“{contractName}”的变量“{definition.VariableName}”可选项配置不正确");
|
||||
}
|
||||
}
|
||||
|
||||
private static string GetOptionValue(
|
||||
global::System.Text.Json.JsonElement option)
|
||||
{
|
||||
if (option.ValueKind == global::System.Text.Json.JsonValueKind.String)
|
||||
return option.GetString()?.Trim();
|
||||
|
||||
if (option.ValueKind == global::System.Text.Json.JsonValueKind.Object)
|
||||
{
|
||||
if (option.TryGetProperty("value", out var value))
|
||||
return GetJsonText(value);
|
||||
if (option.TryGetProperty("label", out var label))
|
||||
return GetJsonText(label);
|
||||
}
|
||||
|
||||
return GetJsonText(option);
|
||||
}
|
||||
|
||||
private static string GetJsonText(
|
||||
global::System.Text.Json.JsonElement value)
|
||||
{
|
||||
return value.ValueKind switch
|
||||
{
|
||||
global::System.Text.Json.JsonValueKind.String => value.GetString()?.Trim(),
|
||||
global::System.Text.Json.JsonValueKind.Number => value.ToString(),
|
||||
global::System.Text.Json.JsonValueKind.True => bool.TrueString,
|
||||
global::System.Text.Json.JsonValueKind.False => bool.FalseString,
|
||||
_ => null
|
||||
};
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user