Files
ERP/oa-backend/src/main/java/com/kaidi/oa/seed/ItDeptDemoSeeder.java
T
Qiufeng 1affcd9a5e
Signed Release / release (push) Failing after 5m1s
feat: add PostgreSQL web installation wizard
2026-08-04 07:42:20 +08:00

382 lines
19 KiB
Java

package com.kaidi.oa.seed;
import com.kaidi.oa.domain.ItAsset;
import com.kaidi.oa.domain.ItAssetEvent;
import com.kaidi.oa.domain.ItInspection;
import com.kaidi.oa.domain.ItMonitorItem;
import com.kaidi.oa.domain.ItNetworkDevice;
import com.kaidi.oa.domain.ItSecPolicyConfig;
import com.kaidi.oa.repository.ItAssetEventRepository;
import com.kaidi.oa.repository.ItAssetRepository;
import com.kaidi.oa.repository.ItInspectionRepository;
import com.kaidi.oa.repository.ItMonitorItemRepository;
import com.kaidi.oa.repository.ItNetworkDeviceRepository;
import com.kaidi.oa.repository.ItSecPolicyConfigRepository;
import org.springframework.boot.ApplicationArguments;
import org.springframework.boot.ApplicationRunner;
import org.springframework.core.annotation.Order;
import java.math.BigDecimal;
import java.time.Instant;
import java.time.LocalDate;
import java.time.ZoneOffset;
/**
* 信息部演示数据Seeder:补全监控项/巡检读数/网络设备/安全策略零数据演示缺口。
* @Order(204) 在所有主数据Seeder后运行,幂等(count > 0 则跳过)。
*/
@Order(204)
@DemoSeed
public class ItDeptDemoSeeder implements ApplicationRunner {
private final ItMonitorItemRepository monitorRepo;
private final ItInspectionRepository inspectionRepo;
private final ItNetworkDeviceRepository networkRepo;
private final ItSecPolicyConfigRepository policyRepo;
private final ItAssetRepository assetRepo;
private final ItAssetEventRepository assetEventRepo;
public ItDeptDemoSeeder(ItMonitorItemRepository monitorRepo,
ItInspectionRepository inspectionRepo,
ItNetworkDeviceRepository networkRepo,
ItSecPolicyConfigRepository policyRepo,
ItAssetRepository assetRepo,
ItAssetEventRepository assetEventRepo) {
this.monitorRepo = monitorRepo;
this.inspectionRepo = inspectionRepo;
this.networkRepo = networkRepo;
this.policyRepo = policyRepo;
this.assetRepo = assetRepo;
this.assetEventRepo = assetEventRepo;
}
@Override
public void run(ApplicationArguments args) {
seedMonitorItems();
seedNetworkDevices();
seedSecPolicies();
seedAssetAmounts();
seedAssetEvents();
}
// -------- 监控项 + 巡检读数 --------
private void seedMonitorItems() {
if (monitorRepo.count() > 0) return;
// ERP应用服务器 CPU
ItMonitorItem m1 = monitor("ERP应用服务器", "CPU使用率", "%", "above", 75.0, 90.0, "张伟");
addInspection(m1, 45.2, "正常", false, "张伟", "-3");
addInspection(m1, 68.5, "正常", false, "张伟", "-2");
addInspection(m1, 82.1, "告警", true, "张伟", "-1");
addInspection(m1, 55.3, "正常", false, "张伟", "0");
// ERP应用服务器 内存
ItMonitorItem m2 = monitor("ERP应用服务器", "内存使用率", "%", "above", 80.0, 92.0, "张伟");
addInspection(m2, 71.0, "正常", false, "系统", "-2");
addInspection(m2, 88.5, "告警", true, "系统", "-1");
addInspection(m2, 93.2, "故障", true, "系统", "0");
// 数据库主库
ItMonitorItem m3 = monitor("数据库主库", "磁盘使用率", "%", "above", 70.0, 85.0, "李娜");
addInspection(m3, 52.3, "正常", false, "李娜", "-5");
addInspection(m3, 65.7, "正常", false, "李娜", "-2");
addInspection(m3, 73.4, "告警", true, "李娜", "0");
// 数据库连接数
ItMonitorItem m4 = monitor("数据库主库", "连接数", "个", "above", 150.0, 200.0, "李娜");
addInspection(m4, 87.0, "正常", false, "李娜", "-3");
addInspection(m4, 134.0, "正常", false, "李娜", "-1");
addInspection(m4, 112.0, "正常", false, "李娜", "0");
// OA服务响应时间
ItMonitorItem m5 = monitor("OA应用系统", "响应时间", "ms", "above", 500.0, 2000.0, "陈静");
addInspection(m5, 235.0, "正常", false, "系统", "-4");
addInspection(m5, 312.0, "正常", false, "系统", "-2");
addInspection(m5, 648.0, "告警", true, "系统", "0");
// 核心交换机 网络流量
ItMonitorItem m6 = monitor("核心交换机", "网络流量", "Mbps", "above", 800.0, 950.0, "张伟");
addInspection(m6, 452.0, "正常", false, "张伟", "-6");
addInspection(m6, 623.0, "正常", false, "张伟", "-3");
addInspection(m6, 712.0, "正常", false, "张伟", "0");
// 存储阵列 可用空间
ItMonitorItem m7 = monitor("存储阵列", "可用空间率", "%", "below", 20.0, 10.0, "李娜");
addInspection(m7, 45.0, "正常", false, "李娜", "-7");
addInspection(m7, 28.5, "正常", false, "李娜", "-3");
addInspection(m7, 18.2, "告警", true, "李娜", "0");
}
private ItMonitorItem monitor(String target, String metric, String unit,
String direction, Double warn, Double crit, String owner) {
ItMonitorItem m = new ItMonitorItem();
m.setTarget(target);
m.setMetric(metric);
m.setUnit(unit);
m.setDirection(direction);
m.setWarnThreshold(warn);
m.setCritThreshold(crit);
m.setOwner(owner);
m.setEnabled(Boolean.TRUE);
m.setLastStatus("未采集");
m.setCreatedAt(Instant.now());
return monitorRepo.save(m);
}
private void addInspection(ItMonitorItem m, double value, String result,
boolean alerted, String inspector, String daysAgo) {
int days = Integer.parseInt(daysAgo);
LocalDate date = LocalDate.now().plusDays(days);
ItInspection ins = new ItInspection();
ins.setMonitorItemId(m.getId());
ins.setTarget(m.getTarget());
ins.setMetric(m.getMetric());
ins.setValue(value);
ins.setResult(result);
ins.setAlerted(alerted);
ins.setInspector(inspector);
ins.setCheckDate(date.toString());
ins.setCheckedAt(date.atStartOfDay(ZoneOffset.UTC).toInstant());
ins.setCreatedAt(Instant.now());
ItInspection saved = inspectionRepo.save(ins);
// 回写监控项最近状态
m.setLastValue(value);
m.setLastStatus(result);
m.setLastCheckAt(saved.getCheckedAt());
monitorRepo.save(m);
}
// -------- 网络设备 --------
private void seedNetworkDevices() {
if (networkRepo.count() > 0) return;
netdev("深信服AF-2000防火墙", "防火墙", "深信服 AF-2000",
"192.168.1.1", "全网", "机房A", "V5.5.0.6", "张伟",
"2025-01-20", "2028-01-20", "VLAN10-管理区/VLAN20-业务区/VLAN30-DMZ区;安全策略48条", "正常", "2026-05-15");
netdev("华为S5720核心交换机", "交换机", "华为 S5720-52X",
"192.168.1.2", "VLAN10/20/30/40", "机房A", "V200R020C10", "张伟",
"2024-06-15", "2027-06-15", "24口PoE+4个SFP+上行口;VLAN间路由已配置", "正常", "2026-05-20");
netdev("华为S5700接入交换机-1F", "交换机", "华为 S5700-28X",
"192.168.1.3", "VLAN20/40", "1楼弱电箱", "V200R019C10", "李娜",
"2024-08-10", "2027-08-10", "负责1楼24个信息点接入", "正常", "2026-04-18");
netdev("深信服VPN网关", "VPN网关", "深信服 SSL-VPN 2000",
"192.168.1.4", "VPN-Pool/10.8.0.0/24", "机房B", "V5.2.3", "张伟",
"2024-12-01", "2027-12-01", "IKEv2 AES-256-GCM/SHA2-256;在线用户峰值50人", "正常", "2026-06-01");
netdev("深信服IPS-2000入侵防御", "IDS/IPS", "深信服 IPS-2000",
"192.168.1.5", "旁路检测", "机房A", "IPS-V4.1.2", "张伟",
"2024-03-15", "2027-03-15", "特征库版本2026.06.01;每日自动更新;高风险告警即时阻断", "正常", "2026-06-01");
netdev("华为AR路由器", "路由器", "华为 AR3260",
"10.0.0.1", "外网/内网边界", "机房B", "V200R009C10", "张伟",
"2024-05-01", "2027-05-01", "双ISP链路,主链路电信100M,备链路联通50M", "正常", "2026-05-28");
netdev("360天擎防病毒服务器", "防病毒服务器", "360天擎 v4.5",
"192.168.1.10", "VLAN20/40", "机房A", "V4.5.11.0", "李娜",
"2023-09-01", "2026-09-01", "病毒库2026-06-15;全网200终端已接入", "正常", "2026-06-15");
netdev("SANGFOR上网行为管理", "上网行为管理", "深信服 AC-3000",
"192.168.1.6", "出口前", "机房A", "V12.0.73", "张伟",
"2023-11-10", "2026-11-10", "违规内容拦截/带宽管理/行为审计;日均报表已启用", "告警", null);
}
private void netdev(String name, String deviceType, String model,
String ip, String vlan, String location, String firmware,
String admin, String purchase, String warranty, String note,
String runStatus, String lastBackup) {
ItNetworkDevice d = new ItNetworkDevice();
d.setName(name);
d.setDeviceType(deviceType);
d.setModel(model);
d.setManagementIp(ip);
d.setVlanSegment(vlan);
d.setLocation(location);
d.setFirmwareVersion(firmware);
d.setAdmin(admin);
d.setPurchaseDate(purchase);
d.setWarrantyDate(warranty);
d.setNote(note);
d.setRunStatus(runStatus);
d.setConfigBackupStatus(lastBackup != null ? "已备份" : "未备份");
d.setLastConfigBackupDate(lastBackup);
d.setCreatedAt(Instant.now());
networkRepo.save(d);
}
// -------- 安全策略配置 --------
private void seedSecPolicies() {
if (policyRepo.count() > 0) return;
// VPN策略
policy(null, "深信服VPN网关", "VPN策略", "总部-远程访问VPN",
"VPN-001", "外网→内网", "任意", "192.168.0.0/16", "TCP/443,UDP/500-4500",
"允许", 1, "IKEv2/AES-256-GCM/SHA2-256;证书认证;MFA双因子;最大并发500用户");
policy(null, "深信服VPN网关", "VPN策略", "分公司点对点VPN",
"VPN-002", "分公司→总部", "10.2.0.0/24", "192.168.0.0/16", "ANY",
"允许", 2, "分公司岳阳(10.2.0.0/24)通过IPSEC VPN访问总部内网;预共享密钥AES-256");
// 防火墙规则
policy(null, "深信服AF-2000防火墙", "防火墙规则", "拒绝外网访问内网管理口",
"FW-001", "外网→内网", "ANY", "192.168.1.0/24", "TCP/22,TCP/23,TCP/3389",
"拒绝", 1, "安全基线:禁止外网直接SSH/Telnet/RDP到内网管理设备");
policy(null, "深信服AF-2000防火墙", "防火墙规则", "允许内网访问外网HTTP/HTTPS",
"FW-002", "内网→外网", "192.168.0.0/16", "ANY", "TCP/80,TCP/443",
"允许", 10, "员工上网;经上网行为管理过滤后允许");
policy(null, "深信服AF-2000防火墙", "防火墙规则", "DMZ区发布ERP对外服务",
"FW-003", "外网→DMZ", "ANY", "192.168.30.100", "TCP/443",
"允许", 5, "ERP系统移动端访问入口;仅开放HTTPS 443端口");
// IPS规则
policy(null, "深信服IPS-2000入侵防御", "IPS规则", "SQL注入攻击拦截",
"IPS-001", "双向", "ANY", "任意", "TCP/80,TCP/443,TCP/8080",
"阻断", 1, "特征库SQL注入检测;严格模式;每日告警统计");
policy(null, "深信服IPS-2000入侵防御", "IPS规则", "暴力破解攻击防护",
"IPS-002", "入站", "ANY", "任意", "TCP/22,TCP/3389,TCP/8090",
"阻断", 2, "5次/分钟触发阻断;IP封锁1小时;通知管理员");
policy(null, "深信服IPS-2000入侵防御", "IPS规则", "Web漏洞利用检测",
"IPS-003", "入站", "ANY", "任意", "TCP/80,TCP/443",
"告警", 3, "XSS/文件包含/目录遍历检测;告警模式记录日志");
// IDS特征
policy(null, "深信服IPS-2000入侵防御", "IDS特征", "异常流量基线检测",
"IDS-001", "双向", "内网", "内网", "ANY",
"告警", 1, "基于流量基线的异常检测:单IP流量超基线3倍触发告警");
// 上网行为
policy(null, "SANGFOR上网行为管理", "上网行为", "禁止访问非工作网站",
"AC-001", "内网→外网", "192.168.0.0/16", "ANY", "TCP/80,TCP/443",
"拒绝", 5, "工作时间(9:00-18:00)拦截娱乐/游戏/社交类网站;白名单放行业务系统");
policy(null, "SANGFOR上网行为管理", "上网行为", "带宽QoS策略",
"AC-002", "内网→外网", "192.168.0.0/16", "ANY", "ANY",
"允许", 10, "业务系统优先级最高;视频流媒体限速2Mbps/人;总出口100M按部门分配");
}
private void policy(Long deviceId, String deviceName, String policyType, String policyName,
String policyNo, String trafficDir, String srcAddr, String dstAddr,
String portProto, String policyAction, Integer priority, String remark) {
ItSecPolicyConfig c = new ItSecPolicyConfig();
c.setDeviceId(deviceId);
c.setDeviceName(deviceName);
c.setPolicyType(policyType);
c.setPolicyName(policyName);
c.setPolicyNo(policyNo);
c.setTrafficDir(trafficDir);
c.setSrcAddress(srcAddr);
c.setDstAddress(dstAddr);
c.setPortProto(portProto);
c.setPolicyAction(policyAction);
c.setEnabled(Boolean.TRUE);
c.setPriority(priority);
c.setRemark(remark);
c.setLastSyncDate(LocalDate.now().toString());
c.setOperator("张伟");
c.setCreatedAt(Instant.now());
policyRepo.save(c);
}
// -------- 回填IT资产采购金额(让折旧能算出真实金额)--------
private void seedAssetAmounts() {
// 为现有IT资产补全采购金额、折旧年限,让折旧端点能返回真实金额。
for (ItAsset a : assetRepo.findAll()) {
if (a.getPurchaseAmount() != null && a.getPurchaseAmount().compareTo(BigDecimal.ZERO) > 0) {
continue; // 已有金额跳过
}
// 根据类型设置参考采购金额
BigDecimal amount;
int depYears;
int residual;
switch (a.getCategory() != null ? a.getCategory() : "") {
case "服务器" -> { amount = new BigDecimal("55000.00"); depYears = 5; residual = 5; }
case "网络设备" -> { amount = new BigDecimal("18000.00"); depYears = 5; residual = 5; }
case "终端" -> { amount = new BigDecimal("8500.00"); depYears = 3; residual = 5; }
case "软件" -> { amount = new BigDecimal("25000.00"); depYears = 3; residual = 0; }
case "办公设备" -> { amount = new BigDecimal("6500.00"); depYears = 5; residual = 5; }
default -> { amount = new BigDecimal("5000.00"); depYears = 5; residual = 5; }
}
// 根据资产编号微调真实感
if ("IT-001".equals(a.getAssetNo())) amount = new BigDecimal("62800.00");
if ("IT-002".equals(a.getAssetNo())) amount = new BigDecimal("128000.00");
if ("IT-008".equals(a.getAssetNo())) amount = new BigDecimal("180000.00");
if ("IT-009".equals(a.getAssetNo())) amount = new BigDecimal("68000.00");
a.setPurchaseAmount(amount);
if (a.getDepreciationYears() == null) a.setDepreciationYears(depYears);
if (a.getResidualRatePct() == null) a.setResidualRatePct(residual);
if (a.getSerialNo() == null) {
a.setSerialNo("SN" + a.getAssetNo().replace("-", "") + "2024");
}
if (a.getBarcode() == null) {
a.setBarcode("BC" + a.getAssetNo().replace("-", ""));
}
assetRepo.save(a);
}
}
// -------- 资产生命周期事件演示数据 --------
private void seedAssetEvents() {
if (assetEventRepo.count() > 0) return;
// 为IT-007 (闲置惠普笔记本) 生成一条历史调拨记录
for (ItAsset a : assetRepo.findAll()) {
if (!"IT-007".equals(a.getAssetNo())) continue;
ItAssetEvent ev = new ItAssetEvent();
ev.setAssetId(a.getId());
ev.setAssetNo(a.getAssetNo());
ev.setAssetName(a.getName());
ev.setEventType("调拨");
ev.setEventNo("TR-20250618-0001");
ev.setFromHolder("设计研究中心");
ev.setToHolder("");
ev.setFromLocation("设计室");
ev.setToLocation("信息部库房");
ev.setReason("项目结束,设备归还信息部统一管理");
ev.setOperator("陈静");
ev.setStatus("已完成");
ev.setEventDate("2025-06-18");
ev.setCreatedAt(Instant.now());
assetEventRepo.save(ev);
break;
}
// 为IT-010 (维修复印机) 生成维修工单
for (ItAsset a : assetRepo.findAll()) {
if (!"IT-010".equals(a.getAssetNo())) continue;
ItAssetEvent ev = new ItAssetEvent();
ev.setAssetId(a.getId());
ev.setAssetNo(a.getAssetNo());
ev.setAssetName(a.getName());
ev.setEventType("维修");
ev.setEventNo("WO-20260608-0001");
ev.setFromHolder("行政部");
ev.setVendor("佳能维修服务中心(长沙)");
ev.setReason("定影器故障,打印出现竖向条纹");
ev.setExpectedReturnDate("2026-06-20");
ev.setOperator("李娜");
ev.setStatus("处理中");
ev.setEventDate("2026-06-08");
ev.setCreatedAt(Instant.now());
assetEventRepo.save(ev);
break;
}
// 为IT-011 (已报废爱普生投影仪) 生成报废记录
for (ItAsset a : assetRepo.findAll()) {
if (!"IT-011".equals(a.getAssetNo())) continue;
ItAssetEvent ev = new ItAssetEvent();
ev.setAssetId(a.getId());
ev.setAssetNo(a.getAssetNo());
ev.setAssetName(a.getName());
ev.setEventType("报废");
ev.setEventNo("SC-20260101-0001");
ev.setFromHolder("行政部");
ev.setReason("灯泡寿命耗尽,维修费用超过设备残值,申请报废");
ev.setOperator("陈静");
ev.setStatus("已完成");
ev.setResult("报废处置");
ev.setCompletedDate("2026-01-05");
ev.setEventDate("2026-01-02");
ev.setCreatedAt(Instant.now());
assetEventRepo.save(ev);
break;
}
}
}