123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856 |
- // 扩展Window接口以包含echarts属性
- declare global {
- interface Window {
- echarts: any;
- }
- }
- import { Component, OnInit, AfterViewInit, ViewChild, ElementRef } from '@angular/core';
- import { CommonModule } from '@angular/common';
- import { RouterModule } from '@angular/router';
- import { FormsModule } from '@angular/forms';
- import { SettingDialogComponent } from './setting-dialog/setting-dialog'; // @ts-ignore: Component used in code but not in template
- import { MatDialog } from '@angular/material/dialog';
- import { MatSelectModule } from '@angular/material/select';
- import { MatFormFieldModule } from '@angular/material/form-field';
- import { MatSlideToggleModule } from '@angular/material/slide-toggle';
- // 定义工作流阶段接口
- interface WorkflowStage {
- id: string;
- name: string;
- order: number;
- description: string;
- isActive: boolean;
- }
- // 定义SOP模板接口
- interface SOPTemplate {
- id: string;
- name: string;
- description: string;
- steps: string[];
- isActive: boolean;
- }
- // 定义报价规则接口
- interface PricingRule {
- id: string;
- name: string;
- description: string;
- condition: string;
- price: number;
- isActive: boolean;
- }
- // 定义绩效规则接口
- interface PerformanceRule {
- id: string;
- name: string;
- description: string;
- metric: string;
- threshold: number;
- reward: string;
- isActive: boolean;
- }
- @Component({
- selector: 'app-system-settings',
- standalone: true,
- imports: [
- CommonModule,
- RouterModule,
- FormsModule,
- MatFormFieldModule,
- MatSelectModule,
- MatSlideToggleModule
- ],
- templateUrl: './system-settings.html'
- })
- export class SystemSettings implements OnInit {
- // 当前激活的标签页
- activeTab: string = 'workflow';
-
- // 搜索关键词
- workflowSearchTerm: string = '';
- sopSearchTerm: string = '';
- pricingSearchTerm: string = '';
- performanceSearchTerm: string = '';
-
- // 数据列表
- workflowStages: WorkflowStage[] = [];
- sopTemplates: SOPTemplate[] = [];
- pricingRules: PricingRule[] = [];
- performanceRules: PerformanceRule[] = [];
-
- // 过滤后的数据列表
- filteredWorkflowStages: WorkflowStage[] = [];
- filteredSOPTemplates: SOPTemplate[] = [];
- filteredPricingRules: PricingRule[] = [];
- filteredPerformanceRules: PerformanceRule[] = [];
-
- // 常用指标
- performanceMetrics = ['项目完成率', '客户满意度', '按时交付率', '产值'];
-
- // 图表实例引用
- @ViewChild('dataUsageChart') private dataUsageChart!: ElementRef;
- @ViewChild('backupHistoryChart') private backupHistoryChart!: ElementRef;
- @ViewChild('systemPerformanceChart') private systemPerformanceChart!: ElementRef;
-
- // 数据统计信息
- systemStats = {
- totalDataSize: 128,
- usedDataSize: 76,
- backupCount: 12,
- activeUsers: 32,
- systemUptime: '99.9%',
- lastBackup: '2025-09-15 02:00:00'
- };
-
- // 系统配置选项
- systemOptions = {
- enableAuditLog: true,
- enableNotification: true,
- autoBackupEnabled: true,
- backupFrequency: 'daily',
- dataRetentionDays: 365,
- enableDataExport: true
- };
-
- // 备份历史数据
- backupHistory = [
- { date: '2025-09-15', size: 6.2, status: 'success' },
- { date: '2025-09-14', size: 6.1, status: 'success' },
- { date: '2025-09-13', size: 6.0, status: 'success' },
- { date: '2025-09-12', size: 5.9, status: 'success' },
- { date: '2025-09-11', size: 5.8, status: 'success' },
- { date: '2025-09-10', size: 5.7, status: 'warning' },
- { date: '2025-09-09', size: 5.6, status: 'success' },
- { date: '2025-09-08', size: 5.5, status: 'error' },
- { date: '2025-09-07', size: 5.4, status: 'success' },
- { date: '2025-09-06', size: 5.3, status: 'success' },
- { date: '2025-09-05', size: 5.2, status: 'success' },
- { date: '2025-09-04', size: 5.1, status: 'success' }
- ];
-
- // 系统性能数据
- systemPerformance = [
- { time: '00:00', cpuUsage: 15, memoryUsage: 30, diskIO: 10 },
- { time: '04:00', cpuUsage: 10, memoryUsage: 25, diskIO: 5 },
- { time: '08:00', cpuUsage: 25, memoryUsage: 40, diskIO: 25 },
- { time: '12:00', cpuUsage: 40, memoryUsage: 55, diskIO: 45 },
- { time: '16:00', cpuUsage: 35, memoryUsage: 50, diskIO: 40 },
- { time: '20:00', cpuUsage: 20, memoryUsage: 35, diskIO: 20 }
- ];
-
- // 数据类型分布
- dataDistribution = [
- { name: '项目数据', value: 35 },
- { name: '客户数据', value: 25 },
- { name: '日志数据', value: 20 },
- { name: '配置数据', value: 10 },
- { name: '其他数据', value: 10 }
- ];
-
- constructor(private dialog: MatDialog) {}
-
- ngOnInit(): void {
- // 加载各类数据
- this.loadWorkflowStages();
- this.loadSOPTemplates();
- this.loadPricingRules();
- this.loadPerformanceRules();
- this.loadSystemOptions();
-
- // 初始化图表(延迟初始化,确保DOM已经加载)
- setTimeout(() => {
- this.initDataUsageChart();
- this.initBackupHistoryChart();
- this.initSystemPerformanceChart();
- }, 100);
- }
-
- // 切换标签页
- switchTab(tab: string): void {
- this.activeTab = tab;
- }
-
- // 加载工作流阶段数据
- loadWorkflowStages(): void {
- this.workflowStages = [
- {
- id: '1',
- name: '需求沟通',
- order: 1,
- description: '与客户沟通需求,了解项目背景和期望',
- isActive: true
- },
- {
- id: '2',
- name: '方案设计',
- order: 2,
- description: '根据需求设计解决方案和技术架构',
- isActive: true
- },
- {
- id: '3',
- name: '开发实现',
- order: 3,
- description: '按照方案进行开发和实现',
- isActive: true
- },
- {
- id: '4',
- name: '测试验证',
- order: 4,
- description: '对开发结果进行测试和验证',
- isActive: true
- },
- {
- id: '5',
- name: '部署上线',
- order: 5,
- description: '将项目部署到生产环境',
- isActive: true
- },
- {
- id: '6',
- name: '运维维护',
- order: 6,
- description: '项目上线后的运行维护和优化',
- isActive: true
- }
- ];
- this.onWorkflowSearch();
- }
-
- // 加载SOP模板数据
- loadSOPTemplates(): void {
- this.sopTemplates = [
- {
- id: '1',
- name: '新客户接入流程',
- description: '规范新客户从接触到签约的全流程',
- steps: [
- '初步接触与需求了解',
- '提供解决方案与报价',
- '商务谈判',
- '签订合同',
- '客户信息录入系统',
- '启动项目'
- ],
- isActive: true
- },
- {
- id: '2',
- name: '项目开发流程',
- description: '标准项目开发的流程规范',
- steps: [
- '需求分析与文档编写',
- '系统设计',
- '编码实现',
- '单元测试',
- '集成测试',
- '系统测试',
- '用户验收测试',
- '上线部署'
- ],
- isActive: true
- },
- {
- id: '3',
- name: '问题处理流程',
- description: '处理客户反馈问题的标准流程',
- steps: [
- '问题记录与分类',
- '问题评估与优先级确定',
- '问题分析与解决',
- '验证解决方案',
- '更新文档',
- '反馈给客户'
- ],
- isActive: true
- }
- ];
- this.onSOPSearch();
- }
-
- // 加载报价规则数据
- loadPricingRules(): void {
- this.pricingRules = [
- {
- id: '1',
- name: '基础开发服务',
- description: '标准软件开发服务报价',
- condition: '基础功能开发',
- price: 12000,
- isActive: true
- },
- {
- id: '2',
- name: '高级开发服务',
- description: '包含复杂功能的开发服务报价',
- condition: '高级功能开发',
- price: 25000,
- isActive: true
- },
- {
- id: '3',
- name: '维护服务',
- description: '系统上线后的维护服务报价',
- condition: '系统维护',
- price: 5000,
- isActive: true
- }
- ];
- this.onPricingSearch();
- }
-
- // 加载绩效规则数据
- loadPerformanceRules(): void {
- this.performanceRules = [
- {
- id: '1',
- name: '项目按时完成率',
- description: '评估项目是否按时完成',
- metric: '按时交付率',
- threshold: 90,
- reward: '绩效加分10分',
- isActive: true
- },
- {
- id: '2',
- name: '客户满意度',
- description: '评估客户对服务的满意程度',
- metric: '客户满意度',
- threshold: 95,
- reward: '绩效加分15分',
- isActive: true
- },
- {
- id: '3',
- name: '项目完成质量',
- description: '评估项目交付质量',
- metric: '项目完成率',
- threshold: 85,
- reward: '绩效加分12分',
- isActive: true
- }
- ];
- this.onPerformanceSearch();
- }
-
- // 加载系统配置
- loadSystemOptions(): void {
- // 这里可以添加从后端加载配置的逻辑
- // 目前使用的是模拟数据
- }
-
- // 打开工作流阶段对话框
- openWorkflowDialog(stage?: WorkflowStage): void {
- // 打开对话框的逻辑
- console.log('打开工作流阶段对话框', stage);
- }
-
- // 打开SOP模板对话框
- openSOPDialog(template?: SOPTemplate): void {
- // 打开对话框的逻辑
- console.log('打开SOP模板对话框', template);
- }
-
- // 打开报价规则对话框
- openPricingDialog(rule?: PricingRule): void {
- // 打开对话框的逻辑
- console.log('打开报价规则对话框', rule);
- }
-
- // 打开绩效规则对话框
- openPerformanceDialog(rule?: PerformanceRule): void {
- // 打开对话框的逻辑
- console.log('打开绩效规则对话框', rule);
- }
-
- // 保存设置项
- saveSetting(type: string, updatedItem: any): void {
- switch (type) {
- case 'workflow':
- if (updatedItem.id) {
- // 更新现有阶段
- this.workflowStages = this.workflowStages.map(stage =>
- stage.id === updatedItem.id ? updatedItem : stage
- );
- } else {
- // 添加新阶段
- updatedItem.id = (this.workflowStages.length + 1).toString();
- this.workflowStages.push(updatedItem);
- }
- this.onWorkflowSearch();
- break;
- case 'sop':
- if (updatedItem.id) {
- // 更新现有模板
- this.sopTemplates = this.sopTemplates.map(template =>
- template.id === updatedItem.id ? updatedItem : template
- );
- } else {
- // 添加新模板
- updatedItem.id = (this.sopTemplates.length + 1).toString();
- this.sopTemplates.push(updatedItem);
- }
- this.onSOPSearch();
- break;
- case 'pricing':
- if (updatedItem.id) {
- // 更新现有规则
- this.pricingRules = this.pricingRules.map(rule =>
- rule.id === updatedItem.id ? updatedItem : rule
- );
- } else {
- // 添加新规则
- updatedItem.id = (this.pricingRules.length + 1).toString();
- this.pricingRules.push(updatedItem);
- }
- this.onPricingSearch();
- break;
- case 'performance':
- if (updatedItem.id) {
- // 更新现有规则
- this.performanceRules = this.performanceRules.map(rule =>
- rule.id === updatedItem.id ? updatedItem : rule
- );
- } else {
- // 添加新规则
- updatedItem.id = (this.performanceRules.length + 1).toString();
- this.performanceRules.push(updatedItem);
- }
- this.onPerformanceSearch();
- break;
- }
- }
-
- // 删除设置项
- deleteSetting(type: string, id: string): void {
- if (confirm('确定要删除此项设置吗?')) {
- switch (type) {
- case 'workflow':
- this.workflowStages = this.workflowStages.filter(stage => stage.id !== id);
- this.onWorkflowSearch();
- break;
- case 'sop':
- this.sopTemplates = this.sopTemplates.filter(template => template.id !== id);
- this.onSOPSearch();
- break;
- case 'pricing':
- this.pricingRules = this.pricingRules.filter(rule => rule.id !== id);
- this.onPricingSearch();
- break;
- case 'performance':
- this.performanceRules = this.performanceRules.filter(rule => rule.id !== id);
- this.onPerformanceSearch();
- break;
- }
- }
- }
-
- // 更新设置项的激活状态
- toggleActive(type: string, id: string, isActive: boolean): void {
- switch (type) {
- case 'workflow':
- this.workflowStages = this.workflowStages.map(stage =>
- stage.id === id ? { ...stage, isActive } : stage
- );
- this.onWorkflowSearch();
- break;
- case 'sop':
- this.sopTemplates = this.sopTemplates.map(template =>
- template.id === id ? { ...template, isActive } : template
- );
- this.onSOPSearch();
- break;
- case 'pricing':
- this.pricingRules = this.pricingRules.map(rule =>
- rule.id === id ? { ...rule, isActive } : rule
- );
- this.onPricingSearch();
- break;
- case 'performance':
- this.performanceRules = this.performanceRules.map(rule =>
- rule.id === id ? { ...rule, isActive } : rule
- );
- this.onPerformanceSearch();
- break;
- }
- }
-
- // 搜索工作流阶段
- onWorkflowSearch(): void {
- if (!this.workflowSearchTerm.trim()) {
- this.filteredWorkflowStages = this.workflowStages;
- } else {
- const searchTerm = this.workflowSearchTerm.toLowerCase();
- this.filteredWorkflowStages = this.workflowStages.filter(
- stage => stage.name.toLowerCase().includes(searchTerm) ||
- stage.description.toLowerCase().includes(searchTerm)
- );
- }
- }
-
- // 搜索SOP模板
- onSOPSearch(): void {
- if (!this.sopSearchTerm.trim()) {
- this.filteredSOPTemplates = this.sopTemplates;
- } else {
- const searchTerm = this.sopSearchTerm.toLowerCase();
- this.filteredSOPTemplates = this.sopTemplates.filter(
- template => template.name.toLowerCase().includes(searchTerm) ||
- template.description.toLowerCase().includes(searchTerm) ||
- template.steps.some(step => step.toLowerCase().includes(searchTerm))
- );
- }
- }
-
- // 搜索报价规则
- onPricingSearch(): void {
- if (!this.pricingSearchTerm.trim()) {
- this.filteredPricingRules = this.pricingRules;
- } else {
- const searchTerm = this.pricingSearchTerm.toLowerCase();
- this.filteredPricingRules = this.pricingRules.filter(
- rule => rule.name.toLowerCase().includes(searchTerm) ||
- rule.description.toLowerCase().includes(searchTerm) ||
- rule.condition.toLowerCase().includes(searchTerm)
- );
- }
- }
-
- // 搜索绩效规则
- onPerformanceSearch(): void {
- if (!this.performanceSearchTerm.trim()) {
- this.filteredPerformanceRules = this.performanceRules;
- } else {
- const searchTerm = this.performanceSearchTerm.toLowerCase();
- this.filteredPerformanceRules = this.performanceRules.filter(
- rule => rule.name.toLowerCase().includes(searchTerm) ||
- rule.description.toLowerCase().includes(searchTerm) ||
- rule.metric.toLowerCase().includes(searchTerm)
- );
- }
- }
-
- // 保存系统配置
- saveSystemOptions(): void {
- console.log('保存系统配置:', this.systemOptions);
- // 这里可以添加保存到后端的逻辑
- alert('系统配置保存成功!');
- }
-
- // 初始化数据使用情况图表
- initDataUsageChart(): void {
- if (window['echarts'] && this.dataUsageChart) {
- const chart = window['echarts'].init(this.dataUsageChart.nativeElement);
-
- const option = {
- title: {
- text: '数据存储使用情况',
- left: 'center',
- textStyle: {
- fontWeight: 'normal',
- fontSize: 16
- }
- },
- tooltip: {
- trigger: 'item',
- formatter: '{b}: {c}GB ({d}%)'
- },
- legend: {
- orient: 'vertical',
- left: 10,
- top: 'center'
- },
- series: [
- {
- name: '数据存储',
- type: 'pie',
- radius: ['40%', '70%'],
- avoidLabelOverlap: false,
- itemStyle: {
- borderRadius: 10,
- borderColor: '#fff',
- borderWidth: 2
- },
- label: {
- show: false,
- position: 'center'
- },
- emphasis: {
- label: {
- show: true,
- fontSize: 18,
- fontWeight: 'bold'
- }
- },
- labelLine: {
- show: false
- },
- data: [
- {
- value: this.systemStats.usedDataSize,
- name: '已使用',
- itemStyle: { color: '#165DFF' }
- },
- {
- value: this.systemStats.totalDataSize - this.systemStats.usedDataSize,
- name: '未使用',
- itemStyle: { color: '#E5E6EB' }
- }
- ]
- },
- {
- name: '数据类型分布',
- type: 'pie',
- radius: ['15%', '30%'],
- center: ['75%', '60%'],
- data: this.dataDistribution,
- itemStyle: {
- borderRadius: 5
- },
- label: {
- show: false
- }
- }
- ]
- };
-
- chart.setOption(option);
-
- // 响应式调整
- window.addEventListener('resize', () => {
- chart.resize();
- });
- }
- }
-
- // 初始化备份历史图表
- initBackupHistoryChart(): void {
- if (window['echarts'] && this.backupHistoryChart) {
- const chart = window['echarts'].init(this.backupHistoryChart.nativeElement);
-
- const dates = this.backupHistory.map(item => item.date);
- const sizes = this.backupHistory.map(item => item.size);
- const statusColors = this.backupHistory.map(item => {
- switch(item.status) {
- case 'success': return '#00B42A';
- case 'warning': return '#FFAA00';
- case 'error': return '#F53F3F';
- default: return '#86909C';
- }
- });
-
- const option = {
- title: {
- text: '备份历史记录',
- left: 'center',
- textStyle: {
- fontWeight: 'normal',
- fontSize: 16
- }
- },
- tooltip: {
- trigger: 'axis',
- axisPointer: {
- type: 'cross',
- label: {
- backgroundColor: '#6a7985'
- }
- },
- formatter: (params: any) => {
- const data = params[0];
- const statusItem = this.backupHistory[data.dataIndex];
- const statusText: Record<string, string> = {
- 'success': '成功',
- 'warning': '警告',
- 'error': '失败'
- };
- return `${data.name}<br/>备份大小: ${data.value}GB<br/>状态: ${statusText[statusItem.status]}`;
- }
- },
- grid: {
- left: '3%',
- right: '4%',
- bottom: '3%',
- containLabel: true
- },
- xAxis: {
- type: 'category',
- boundaryGap: false,
- data: dates,
- axisLabel: {
- rotate: 45
- }
- },
- yAxis: {
- type: 'value',
- name: '备份大小 (GB)',
- min: 0
- },
- series: [
- {
- name: '备份大小',
- type: 'line',
- smooth: true,
- data: sizes,
- lineStyle: {
- width: 3,
- color: '#165DFF'
- },
- areaStyle: {
- color: new window['echarts'].graphic.LinearGradient(0, 0, 0, 1, [
- {
- offset: 0,
- color: 'rgba(22, 93, 255, 0.3)'
- },
- {
- offset: 1,
- color: 'rgba(22, 93, 255, 0.05)'
- }
- ])
- },
- symbol: 'circle',
- symbolSize: 8,
- itemStyle: {
- color: function(params: any) {
- return statusColors[params.dataIndex];
- }
- }
- }
- ]
- };
-
- chart.setOption(option);
-
- // 响应式调整
- window.addEventListener('resize', () => {
- chart.resize();
- });
- }
- }
-
- // 初始化系统性能图表
- initSystemPerformanceChart(): void {
- if (window['echarts'] && this.systemPerformanceChart) {
- const chart = window['echarts'].init(this.systemPerformanceChart.nativeElement);
-
- const times = this.systemPerformance.map(item => item.time);
- const cpuUsage = this.systemPerformance.map(item => item.cpuUsage);
- const memoryUsage = this.systemPerformance.map(item => item.memoryUsage);
- const diskIO = this.systemPerformance.map(item => item.diskIO);
-
- const option = {
- title: {
- text: '系统性能监控',
- left: 'center',
- textStyle: {
- fontWeight: 'normal',
- fontSize: 16
- }
- },
- tooltip: {
- trigger: 'axis'
- },
- legend: {
- data: ['CPU使用率', '内存使用率', '磁盘IO'],
- bottom: 0
- },
- grid: {
- left: '3%',
- right: '4%',
- bottom: '15%',
- containLabel: true
- },
- xAxis: {
- type: 'category',
- boundaryGap: false,
- data: times
- },
- yAxis: {
- type: 'value',
- name: '使用率 (%)',
- min: 0,
- max: 100
- },
- series: [
- {
- name: 'CPU使用率',
- type: 'line',
- stack: 'Total',
- data: cpuUsage,
- lineStyle: {
- color: '#165DFF'
- },
- areaStyle: {
- color: new window['echarts'].graphic.LinearGradient(0, 0, 0, 1, [
- {
- offset: 0,
- color: 'rgba(22, 93, 255, 0.5)'
- },
- {
- offset: 1,
- color: 'rgba(22, 93, 255, 0.1)'
- }
- ])
- }
- },
- {
- name: '内存使用率',
- type: 'line',
- stack: 'Total',
- data: memoryUsage,
- lineStyle: {
- color: '#722ED1'
- },
- areaStyle: {
- color: new window['echarts'].graphic.LinearGradient(0, 0, 0, 1, [
- {
- offset: 0,
- color: 'rgba(114, 46, 209, 0.5)'
- },
- {
- offset: 1,
- color: 'rgba(114, 46, 209, 0.1)'
- }
- ])
- }
- },
- {
- name: '磁盘IO',
- type: 'line',
- stack: 'Total',
- data: diskIO,
- lineStyle: {
- color: '#F7BA1E'
- },
- areaStyle: {
- color: new window['echarts'].graphic.LinearGradient(0, 0, 0, 1, [
- {
- offset: 0,
- color: 'rgba(247, 186, 30, 0.5)'
- },
- {
- offset: 1,
- color: 'rgba(247, 186, 30, 0.1)'
- }
- ])
- }
- }
- ]
- };
-
- chart.setOption(option);
-
- // 响应式调整
- window.addEventListener('resize', () => {
- chart.resize();
- });
- }
- }
- }
|