using System.ComponentModel; using System.Runtime.CompilerServices; using System.Windows.Media; using OrpaonVision.Core.Training; using OrpaonVision.Core.Training.Contracts.Commands; using OrpaonVision.Core.Training.Contracts; namespace OrpaonVision.ConfigApp.ViewModels; /// /// 训练管理ViewModel。 /// public sealed class TrainingManagementViewModel : INotifyPropertyChanged { private readonly IDatasetAppService _datasetAppService; private readonly ITrainingJobAppService _trainingJobAppService; private readonly IModelPackageAppService _modelPackageAppService; private readonly IModelVersionAppService _modelVersionAppService; private string _statusText = "准备就绪。"; private Brush _statusBrush = Brushes.DarkGreen; private string _outputText = string.Empty; /// /// 构造函数。 /// public TrainingManagementViewModel( IDatasetAppService datasetAppService, ITrainingJobAppService trainingJobAppService, IModelPackageAppService modelPackageAppService, IModelVersionAppService modelVersionAppService) { _datasetAppService = datasetAppService; _trainingJobAppService = trainingJobAppService; _modelPackageAppService = modelPackageAppService; _modelVersionAppService = modelVersionAppService; } /// /// 状态文本。 /// public string StatusText { get => _statusText; private set => SetProperty(ref _statusText, value); } /// /// 状态画刷。 /// public Brush StatusBrush { get => _statusBrush; private set => SetProperty(ref _statusBrush, value); } /// /// 输出文本。 /// public string OutputText { get => _outputText; private set => SetProperty(ref _outputText, value); } /// /// 构建示例数据集。 /// public async Task BuildSampleDatasetAsync() { try { StatusBrush = Brushes.DarkGreen; StatusText = "正在构建示例数据集..."; // 这里演示如何调用数据集构建服务 // 实际实现需要具体的标注任务ID和机种ID var command = new OrpaonVision.Core.Training.Contracts.Commands.BuildDatasetCommand { Name = "示例数据集", Description = "用于演示的数据集", ProductTypeId = Guid.NewGuid(), // 实际应该从UI获取 AnnotationTaskIds = [Guid.NewGuid()], // 实际应该从UI获取 CreatedBy = "DemoUser" }; // var result = await _datasetAppService.BuildDatasetAsync(command); // 这里为了演示,直接返回成功 StatusText = "示例数据集构建完成(演示)"; OutputText = $"数据集构建命令已准备:{command.Name} - {command.Description}"; } catch (Exception ex) { StatusBrush = Brushes.OrangeRed; StatusText = "数据集构建失败"; OutputText = $"错误:{ex.Message}"; } } /// /// 提交示例训练任务。 /// public async Task SubmitSampleTrainingJobAsync() { try { StatusBrush = Brushes.DarkGreen; StatusText = "正在提交训练任务..."; // 这里演示如何调用训练任务服务 var command = new OrpaonVision.Core.Training.Contracts.Commands.SubmitTrainingJobCommand { Name = "示例训练任务", Description = "用于演示的训练任务", DatasetVersionId = Guid.NewGuid(), // 实际应该从UI获取 AlgorithmType = "YOLOv8", TotalEpochs = 50, BatchSize = 16, LearningRate = 0.001m, CreatedBy = "DemoUser" }; // var result = await _trainingJobAppService.SubmitAsync(command); // 这里为了演示,直接返回成功 StatusText = "训练任务提交完成(演示)"; OutputText = $"训练任务命令已准备:{command.Name} - {command.AlgorithmType} - {command.TotalEpochs}轮"; } catch (Exception ex) { StatusBrush = Brushes.OrangeRed; StatusText = "训练任务提交失败"; OutputText = $"错误:{ex.Message}"; } } /// /// 构建示例模型包。 /// public async Task BuildSampleModelPackageAsync() { try { StatusBrush = Brushes.DarkGreen; StatusText = "正在构建模型包..."; var command = new OrpaonVision.Core.Training.Contracts.Commands.BuildModelPackageCommand { Name = "示例模型包", Description = "用于演示的模型包", ModelVersionId = Guid.NewGuid(), TrainingJobId = Guid.NewGuid(), ProductTypeId = Guid.NewGuid(), ModelFilePath = "/models/yolov8_best.onnx", LabelMappingPath = "/models/labels.json", ConfigPath = "/models/config.json", Accuracy = 0.95m, Recall = 0.92m, F1Score = 0.93m, ValidationLoss = 0.15m, CompatibilityVersion = "1.0.0", CreatedBy = "DemoUser" }; var result = await _modelPackageAppService.BuildPackageAsync(command); if (result.Succeeded) { StatusBrush = Brushes.DarkGreen; StatusText = "模型包构建成功"; OutputText = $"模型包构建成功:ID={result.Data} - 准确率{command.Accuracy:P2} - F1分数{command.F1Score:P2}"; } else { StatusBrush = Brushes.OrangeRed; StatusText = "模型包构建失败"; OutputText = $"错误:{result.Message}"; } } catch (Exception ex) { StatusBrush = Brushes.OrangeRed; StatusText = "模型包构建失败"; OutputText = $"错误:{ex.Message}"; } } /// /// 导出示例模型包。 /// public async Task ExportSampleModelPackageAsync() { try { StatusBrush = Brushes.DarkGreen; StatusText = "正在导出模型包..."; var command = new OrpaonVision.Core.Training.Contracts.Commands.ExportModelPackageCommand { ModelPackageId = Guid.NewGuid(), ExportFormat = "ZIP", IncludeSourceCode = false, IncludeTestData = true, Operator = "DemoUser" }; var result = await _modelPackageAppService.ExportPackageAsync(command); if (result.Succeeded) { StatusBrush = Brushes.DarkGreen; StatusText = "模型包导出成功"; OutputText = $"模型包导出成功:{result.Data.FileName} - 大小{result.Data.FileSizeBytes:N0} 字节 - 校验和{result.Data.Checksum}"; } else { StatusBrush = Brushes.OrangeRed; StatusText = "模型包导出失败"; OutputText = $"错误:{result.Message}"; } } catch (Exception ex) { StatusBrush = Brushes.OrangeRed; StatusText = "模型包导出失败"; OutputText = $"错误:{ex.Message}"; } } /// /// 批准示例模型版本。 /// public async Task ApproveSampleModelVersionAsync() { try { StatusBrush = Brushes.DarkGreen; StatusText = "正在批准模型版本..."; var command = new OrpaonVision.Core.Training.Contracts.Commands.ApproveModelVersionCommand { ModelVersionId = Guid.NewGuid(), ApprovalComment = "模型性能满足要求,批准发布。", ApprovedBy = "DemoUser", ApprovalLevel = "Standard", ForceApprove = false }; // var result = await _modelVersionAppService.MarkAsApprovedAsync(command); StatusText = "模型版本批准完成(演示)"; OutputText = $"模型版本批准命令已准备:批准者{command.ApprovedBy} - 级别{command.ApprovalLevel}"; } catch (Exception ex) { StatusBrush = Brushes.OrangeRed; StatusText = "模型版本批准失败"; OutputText = $"错误:{ex.Message}"; } } /// public event PropertyChangedEventHandler? PropertyChanged; private void SetProperty(ref T field, T value, [CallerMemberName] string? propertyName = null) { if (EqualityComparer.Default.Equals(field, value)) { return; } field = value; PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName)); } }