图片来源网络,侵权联系删
以下架构评审根据的实际经验梳理的一份清单,希望能够对你有所帮助。
6. 弹性处理:应对异常,保障系统稳定
弹性处理是架构评审中不可或缺的一环。
- 通过消息队列的幂等性设计,确保了消息重复消费与接口重复调用时业务的正确性。
- 同时,引入了服务降级机制,对于非核心业务,在系统负载过高时自动降级,优先保障核心业务的正常运行。
例如,在支付接口出现故障时,自动切换至备用支付渠道,并向用户展示友好的提示信息,确保交易流程的顺畅进行。
- 还实现了服务的超时熔断、异常熔断与限流熔断功能,当某个服务出现故障或响应时间过长时,熔断机制会自动触发,阻止故障的进一步扩散。熔断后,通过隔离故障服务,确保单一服务故障不会影响全局系统的稳定运行。
架构示例图
架构示例代码
// 弹性处理系统实现
public class ResilientSystem {
// 熔断器状态
public enum CircuitState {
CLOSED, // 关闭状态,正常调用
OPEN, // 开启状态,直接返回错误
HALF_OPEN // 半开状态,尝试恢复
}
// 熔断器实现
public static class CircuitBreaker {
private CircuitState state;
private int failureCount;
private int failureThreshold;
private long timeout;
private long lastFailureTime;
public CircuitBreaker(int failureThreshold, long timeout) {
this.state = CircuitState.CLOSED;
this.failureCount = 0;
this.failureThreshold = failureThreshold;
this.timeout = timeout;
this.lastFailureTime = 0;
}
public synchronized boolean allowRequest() {
if (state == CircuitState.OPEN) {
// 检查是否超时,可以尝试半开状态
if (System.currentTimeMillis() - lastFailureTime > timeout) {
state = CircuitState.HALF_OPEN;
return true;
}
return false;
}
return true;
}
public synchronized void recordSuccess() {
if (state == CircuitState.HALF_OPEN) {
state = CircuitState.CLOSED;
failureCount = 0;
}
}
public synchronized void recordFailure() {
failureCount++;
lastFailureTime = System.currentTimeMillis();
if (failureCount >= failureThreshold) {
state = CircuitState.OPEN;
}
}
public CircuitState getState() {
return state;
}
}
// 限流器实现
public static class RateLimiter {
private int maxRequests;
private long windowSize;
private Deque<Long> requestTimestamps;
public RateLimiter(int maxRequests, long windowSize) {
this.maxRequests = maxRequests;
this.windowSize = windowSize;
this.requestTimestamps = new ArrayDeque<>();
}
public synchronized boolean allowRequest() {
long currentTime = System.currentTimeMillis();
// 移除过期的请求时间戳
while (!requestTimestamps.isEmpty() &&
currentTime - requestTimestamps.peekFirst() > windowSize) {
requestTimestamps.pollFirst();
}
// 检查是否超过限制
if (requestTimestamps.size() >= maxRequests) {
return false;
}
// 记录当前请求时间戳
requestTimestamps.addLast(currentTime);
return true;
}
}
// 服务降级处理器
public static class ServiceDegradationHandler {
private Map<String, Boolean> serviceStates;
private Map<String, Runnable> fallbackHandlers;
public ServiceDegradationHandler() {
this.serviceStates = new ConcurrentHashMap<>();
this.fallbackHandlers = new ConcurrentHashMap<>();
}
public void registerService(String serviceName, Runnable fallbackHandler) {
serviceStates.put(serviceName, true); // 默认服务正常
fallbackHandlers.put(serviceName, fallbackHandler);
}
public void markServiceDown(String serviceName) {
serviceStates.put(serviceName, false);
}
public void markServiceUp(String serviceName) {
serviceStates.put(serviceName, true);
}
public Object handleRequest(String serviceName, Supplier<Object> serviceCall) {
if (!isServiceAvailable(serviceName)) {
System.out.println("服务 " + serviceName + " 不可用,执行降级处理");
return fallbackHandlers.get(serviceName).run();
}
try {
return serviceCall.get();
} catch (Exception e) {
System.out.println("服务 " + serviceName + " 调用失败,执行降级处理: " + e.getMessage());
return fallbackHandlers.get(serviceName).run();
}
}
private boolean isServiceAvailable(String serviceName) {
return serviceStates.getOrDefault(serviceName, false);
}
}
// 幂等消息处理器
public static class IdempotentMessageProcessor {
private Set<String> processedMessages;
private MessageQueue messageQueue;
public IdempotentMessageProcessor(MessageQueue messageQueue) {
this.processedMessages = ConcurrentHashMap.newKeySet();
this.messageQueue = messageQueue;
}
public void processMessage(Message message) {
// 检查消息是否已处理
if (processedMessages.contains(message.getId())) {
System.out.println("消息 " + message.getId() + " 已处理,跳过");
return;
}
try {
// 处理消息
System.out.println("处理消息: " + message.getId());
// 模拟处理逻辑
Thread.sleep(100);
// 标记消息为已处理
processedMessages.add(message.getId());
// 模拟处理成功,从队列中移除
messageQueue.ackMessage(message.getId());
} catch (Exception e) {
System.out.println("处理消息失败: " + e.getMessage());
// 模拟重试
messageQueue.retryMessage(message);
}
}
}
// 消息队列
public static class MessageQueue {
private BlockingQueue<Message> queue;
private Map<String, Message> pendingMessages;
public MessageQueue() {
this.queue = new LinkedBlockingQueue<>();
this.pendingMessages = new ConcurrentHashMap<>();
}
public void enqueue(Message message) {
queue.add(message);
pendingMessages.put(message.getId(), message);
}
public Message dequeue() throws InterruptedException {
return queue.take();
}
public void ackMessage(String messageId) {
pendingMessages.remove(messageId);
}
public void retryMessage(Message message) {
// 模拟重试逻辑
System.out.println("重试消息: " + message.getId());
enqueue(message);
}
public int getPendingCount() {
return pendingMessages.size();
}
}
// 消息实体
public static class Message {
private String id;
private String content;
public Message(String id, String content) {
this.id = id;
this.content = content;
}
public String getId() {
return id;
}
public String getContent() {
return content;
}
}
// 服务接口
public interface Service {
Object call() throws Exception;
}
// 核心服务实现
public static class CoreService implements Service {
@Override
public Object call() throws Exception {
// 模拟核心服务调用
Thread.sleep(50);
return "核心服务响应";
}
}
// 非核心服务实现
public static class NonCoreService implements Service {
@Override
public Object call() throws Exception {
// 模拟非核心服务调用
Thread.sleep(100);
return "非核心服务响应";
}
}
// 备用服务实现
public static class BackupService implements Service {
@Override
public Object call() throws Exception {
// 模拟备用服务调用
Thread.sleep(30);
return "备用服务响应";
}
}
// 客户端
public static class Client {
private CircuitBreaker circuitBreaker;
private RateLimiter rateLimiter;
private ServiceDegradationHandler degradationHandler;
public Client(CircuitBreaker circuitBreaker, RateLimiter rateLimiter,
ServiceDegradationHandler degradationHandler) {
this.circuitBreaker = circuitBreaker;
this.rateLimiter = rateLimiter;
this.degradationHandler = degradationHandler;
}
public Object requestService(String serviceName, Service service) {
// 检查熔断器状态
if (!circuitBreaker.allowRequest()) {
System.out.println("熔断器开启,请求被拒绝");
return "服务不可用,请稍后再试";
}
// 检查限流
if (!rateLimiter.allowRequest()) {
System.out.println("请求被限流");
return "请求过于频繁,请稍后再试";
}
try {
// 调用服务
Object result = degradationHandler.handleRequest(serviceName, service::call);
// 记录成功
circuitBreaker.recordSuccess();
return result;
} catch (Exception e) {
// 记录失败
circuitBreaker.recordFailure();
throw e;
}
}
}
// 主方法 - 演示弹性处理系统
public static void main(String[] args) throws InterruptedException {
// 创建熔断器(失败阈值5次,超时时间5000毫秒)
CircuitBreaker circuitBreaker = new CircuitBreaker(5, 5000);
// 创建限流器(每秒最多10个请求)
RateLimiter rateLimiter = new RateLimiter(10, 1000);
// 创建服务降级处理器
ServiceDegradationHandler degradationHandler = new ServiceDegradationHandler();
// 注册服务和降级处理器
degradationHandler.registerService("core-service", () -> {
System.out.println("核心服务降级处理");
return "核心服务降级响应";
});
degradationHandler.registerService("non-core-service", () -> {
System.out.println("非核心服务降级处理");
return "非核心服务降级响应";
});
degradationHandler.registerService("payment-service", () -> {
System.out.println("支付服务降级处理 - 使用备用支付渠道");
return "备用支付渠道响应";
});
// 创建客户端
Client client = new Client(circuitBreaker, rateLimiter, degradationHandler);
// 创建消息队列和处理器
MessageQueue messageQueue = new MessageQueue();
IdempotentMessageProcessor messageProcessor = new IdempotentMessageProcessor(messageQueue);
// 模拟消息处理
for (int i = 1; i <= 10; i++) {
messageQueue.enqueue(new Message("msg-" + i, "消息内容 " + i));
}
// 启动消息处理线程
new Thread(() -> {
try {
while (true) {
Message message = messageQueue.dequeue();
messageProcessor.processMessage(message);
Thread.sleep(200);
}
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
}
}).start();
// 模拟正常请求
System.out.println("\n=== 正常请求测试 ===");
for (int i = 0; i < 5; i++) {
Object result = client.requestService("core-service", new CoreService());
System.out.println("响应: " + result);
Thread.sleep(100);
}
// 模拟服务故障
System.out.println("\n=== 服务故障测试 ===");
// 标记核心服务为不可用
degradationHandler.markServiceDown("core-service");
for (int i = 0; i < 5; i++) {
Object result = client.requestService("core-service", new CoreService());
System.out.println("响应: " + result);
Thread.sleep(100);
}
// 模拟非核心服务请求
System.out.println("\n=== 非核心服务请求测试 ===");
for (int i = 0; i < 5; i++) {
Object result = client.requestService("non-core-service", new NonCoreService());
System.out.println("响应: " + result);
Thread.sleep(100);
}
// 模拟限流
System.out.println("\n=== 限流测试 ===");
for (int i = 0; i < 15; i++) {
Object result = client.requestService("core-service", new CoreService());
System.out.println("响应: " + result);
Thread.sleep(50);
}
// 模拟熔断
System.out.println("\n=== 熔断测试 ===");
// 模拟连续失败触发熔断
for (int i = 0; i < 10; i++) {
try {
Object result = client.requestService("core-service", () -> {
throw new RuntimeException("模拟服务故障");
});
System.out.println("响应: " + result);
} catch (Exception e) {
System.out.println("异常: " + e.getMessage());
}
Thread.sleep(100);
}
// 检查熔断器状态
System.out.println("熔断器状态: " + circuitBreaker.getState());
// 模拟熔断恢复
System.out.println("\n=== 熔断恢复测试 ===");
Thread.sleep(6000); // 等待超时
for (int i = 0; i < 3; i++) {
Object result = client.requestService("core-service", new CoreService());
System.out.println("响应: " + result);
Thread.sleep(100);
}
// 检查最终消息处理状态
System.out.println("\n=== 消息处理状态 ===");
System.out.println("待处理消息数: " + messageQueue.getPendingCount());
}
}
7. 兼容性:确保系统协同,降低升级成本
对上下游系统进行了全面梳理,明确了各系统的依赖关系与影响范围。
在新老系统替换过程中,采用了灰度发布策略,先将新系统与老系统并行运行,逐步将流量切换至新系统,确保新老系统能够来回切换,降低切换风险。
同时,对数据存储进行了兼容性设计,使得新系统能够兼容老数据的读取与处理。
在对上下游系统有影响的升级过程中,提前与相关业务方进行沟通,制定了详细的升级方案,通过批量处理、数据迁移等手段,将升级成本降至最低。
例如,在一次数据库升级过程中,通过在线热迁移技术,将数据从旧数据库平滑迁移到新数据库,整个过程对业务无任何影响。
架构示例图
架构示例代码
// 兼容性系统实现
public class CompatibilitySystem {
// 系统版本枚举
public enum SystemVersion {
V1, // 老版本
V2 // 新版本
}
// 数据模型
public static class DataModel {
private String id;
private String name;
private Map<String, Object> attributes;
public DataModel(String id, String name) {
this.id = id;
this.name = name;
this.attributes = new HashMap<>();
}
public String getId() { return id; }
public String getName() { return name; }
public Map<String, Object> getAttributes() { return attributes; }
public void addAttribute(String key, Object value) {
attributes.put(key, value);
}
}
// 数据存储接口
public interface DataStorage {
DataModel getData(String id);
void saveData(DataModel data);
}
// 旧版数据存储
public static class V1DataStorage implements DataStorage {
private Map<String, DataModel> storage;
public V1DataStorage() {
this.storage = new HashMap<>();
// 初始化一些测试数据
DataModel user1 = new DataModel("user1", "张三");
user1.addAttribute("age", 30);
user1.addAttribute("email", "zhangsan@example.com");
storage.put("user1", user1);
DataModel user2 = new DataModel("user2", "李四");
user2.addAttribute("age", 25);
user2.addAttribute("email", "lisi@example.com");
storage.put("user2", user2);
}
@Override
public DataModel getData(String id) {
System.out.println("从V1数据存储获取数据: " + id);
return storage.get(id);
}
@Override
public void saveData(DataModel data) {
System.out.println("保存数据到V1数据存储: " + data.getId());
storage.put(data.getId(), data);
}
}
// 新版数据存储
public static class V2DataStorage implements DataStorage {
private Map<String, DataModel> storage;
public V2DataStorage() {
this.storage = new HashMap<>();
// 新版数据模型包含更多字段
DataModel user1 = new DataModel("user1", "张三");
user1.addAttribute("age", 30);
user1.addAttribute("email", "zhangsan@example.com");
user1.addAttribute("phone", "13800138000");
user1.addAttribute("address", "北京市海淀区");
storage.put("user1", user1);
DataModel user2 = new DataModel("user2", "李四");
user2.addAttribute("age", 25);
user2.addAttribute("email", "lisi@example.com");
user2.addAttribute("phone", "13900139000");
user2.addAttribute("address", "上海市浦东新区");
storage.put("user2", user2);
}
@Override
public DataModel getData(String id) {
System.out.println("从V2数据存储获取数据: " + id);
return storage.get(id);
}
@Override
public void saveData(DataModel data) {
System.out.println("保存数据到V2数据存储: " + data.getId());
storage.put(data.getId(), data);
}
}
// 兼容层
public static class CompatibilityLayer {
private DataStorage v1Storage;
private DataStorage v2Storage;
private SystemVersion currentVersion;
public CompatibilityLayer(DataStorage v1Storage, DataStorage v2Storage) {
this.v1Storage = v1Storage;
this.v2Storage = v2Storage;
this.currentVersion = SystemVersion.V1; // 初始使用V1
}
public void switchVersion(SystemVersion version) {
this.currentVersion = version;
System.out.println("系统切换到版本: " + version);
}
public DataModel getData(String id) {
// 根据当前版本决定从哪个存储获取数据
if (currentVersion == SystemVersion.V1) {
return v1Storage.getData(id);
} else {
return v2Storage.getData(id);
}
}
public void saveData(DataModel data) {
// 根据当前版本决定保存到哪个存储
if (currentVersion == SystemVersion.V1) {
// 新数据保存时需要兼容旧格式
DataModel compatibleData = convertToV1Format(data);
v1Storage.saveData(compatibleData);
} else {
v2Storage.saveData(data);
}
}
private DataModel convertToV1Format(DataModel data) {
// 将新格式数据转换为旧格式
DataModel v1Data = new DataModel(data.getId(), data.getName());
v1Data.addAttribute("age", data.getAttributes().get("age"));
v1Data.addAttribute("email", data.getAttributes().get("email"));
return v1Data;
}
}
// 灰度发布控制器
public static class GrayReleaseController {
private double v1TrafficRatio;
private double v2TrafficRatio;
private Random random;
public GrayReleaseController() {
this.v1TrafficRatio = 1.0; // 初始全部流量到V1
this.v2TrafficRatio = 0.0;
this.random = new Random();
}
public void setTrafficRatio(double v1Ratio, double v2Ratio) {
this.v1TrafficRatio = v1Ratio;
this.v2TrafficRatio = v2Ratio;
System.out.println("设置流量比例: V1=" + (v1Ratio * 100) + "%, V2=" + (v2Ratio * 100) + "%");
}
public SystemVersion determineVersion() {
double value = random.nextDouble();
if (value < v1TrafficRatio) {
return SystemVersion.V1;
} else {
return SystemVersion.V2;
}
}
public void graduallyShiftTraffic(int steps, int delayMs) throws InterruptedException {
double stepSize = 0.1 / steps;
for (int i = 0; i < steps; i++) {
v1TrafficRatio -= stepSize;
v2TrafficRatio += stepSize;
System.out.println("第 " + (i + 1) + " 步: V1=" + (v1TrafficRatio * 100) +
"%, V2=" + (v2TrafficRatio * 100) + "%");
Thread.sleep(delayMs);
}
}
}
// 数据迁移服务
public static class DataMigrationService {
private V1DataStorage v1Storage;
private V2DataStorage v2Storage;
public DataMigrationService(V1DataStorage v1Storage, V2DataStorage v2Storage) {
this.v1Storage = v1Storage;
this.v2Storage = v2Storage;
}
public void migrateData() {
System.out.println("开始数据迁移...");
// 获取所有V1数据
for (String id : v1Storage.getStorage().keySet()) {
DataModel v1Data = v1Storage.getData(id);
// 转换为V2格式
DataModel v2Data = convertToV2Format(v1Data);
// 保存到V2存储
v2Storage.saveData(v2Data);
System.out.println("迁移数据: " + id);
}
System.out.println("数据迁移完成");
}
private DataModel convertToV2Format(DataModel v1Data) {
// 将旧格式数据转换为新格式
DataModel v2Data = new DataModel(v1Data.getId(), v1Data.getName());
v2Data.addAttribute("age", v1Data.getAttributes().get("age"));
v2Data.addAttribute("email", v1Data.getAttributes().get("email"));
// 添加新字段(默认值)
if (!v2Data.getAttributes().containsKey("phone")) {
v2Data.addAttribute("phone", "未提供");
}
if (!v2Data.getAttributes().containsKey("address")) {
v2Data.addAttribute("address", "未提供");
}
return v2Data;
}
}
// API适配器
public static class ApiAdapter {
private CompatibilityLayer compatibilityLayer;
private GrayReleaseController grayReleaseController;
public ApiAdapter(CompatibilityLayer compatibilityLayer,
GrayReleaseController grayReleaseController) {
this.compatibilityLayer = compatibilityLayer;
this.grayReleaseController = grayReleaseController;
}
public Object handleRequest(String requestId, String action, Map<String, Object> params) {
// 根据灰度发布策略决定使用哪个版本
SystemVersion version = grayReleaseController.determineVersion();
System.out.println("请求 " + requestId + " 将由 " + version + " 处理");
try {
if ("getUser".equals(action)) {
String userId = (String) params.get("userId");
DataModel user = compatibilityLayer.getData(userId);
return user;
} else if ("saveUser".equals(action)) {
String userId = (String) params.get("userId");
String name = (String) params.get("name");
int age = (Integer) params.get("age");
String email = (String) params.get("email");
DataModel user = new DataModel(userId, name);
user.addAttribute("age", age);
user.addAttribute("email", email);
compatibilityLayer.saveData(user);
return "用户保存成功";
}
return "未知操作";
} catch (Exception e) {
return "处理请求失败: " + e.getMessage();
}
}
}
// 主方法 - 演示兼容性系统
public static void main(String[] args) throws InterruptedException {
// 创建数据存储
V1DataStorage v1Storage = new V1DataStorage();
V2DataStorage v2Storage = new V2DataStorage();
// 创建兼容层
CompatibilityLayer compatibilityLayer = new CompatibilityLayer(v1Storage, v2Storage);
// 创建灰度发布控制器
GrayReleaseController grayReleaseController = new GrayReleaseController();
// 创建数据迁移服务
DataMigrationService migrationService = new DataMigrationService(v1Storage, v2Storage);
// 创建API适配器
ApiAdapter apiAdapter = new ApiAdapter(compatibilityLayer, grayReleaseController);
// 测试初始状态(全部使用V1)
System.out.println("=== 初始状态测试(全部使用V1) ===");
Object result1 = apiAdapter.handleRequest("req1", "getUser", Map.of("userId", "user1"));
System.out.println("响应: " + result1);
// 执行数据迁移
System.out.println("\n=== 数据迁移测试 ===");
migrationService.migrateData();
// 测试灰度发布
System.out.println("\n=== 灰度发布测试 ===");
// 初始状态:100% V1
grayReleaseController.setTrafficRatio(1.0, 0.0);
for (int i = 0; i < 5; i++) {
Object result = apiAdapter.handleRequest("req" + i, "getUser", Map.of("userId", "user1"));
System.out.println("响应: " + result);
}
// 逐步切换流量到V2
System.out.println("\n逐步切换流量到V2...");
grayReleaseController.graduallyShiftTraffic(5, 1000);
// 测试新版本
System.out.println("\n=== 新版本测试 ===");
grayReleaseController.setTrafficRatio(0.0, 1.0);
for (int i = 0; i < 5; i++) {
Object result = apiAdapter.handleRequest("req" + i, "getUser", Map.of("userId", "user1"));
System.out.println("响应: " + result);
}
// 测试数据保存(兼容性)
System.out.println("\n=== 数据保存兼容性测试 ===");
Object saveResult = apiAdapter.handleRequest("saveReq", "saveUser",
Map.of("userId", "user3", "name", "王五", "age", 28, "email", "wangwu@example.com"));
System.out.println("响应: " + saveResult);
// 验证数据保存后的兼容性
Object getResult = apiAdapter.handleRequest("getReq", "getUser", Map.of("userId", "user3"));
System.out.println("获取保存的数据: " + getResult);
// 测试版本切换
System.out.println("\n=== 版本切换测试 ===");
compatibilityLayer.switchVersion(SystemVersion.V2);
Object getResultV2 = apiAdapter.handleRequest("getReqV2", "getUser", Map.of("userId", "user1"));
System.out.println("V2版本获取数据: " + getResultV2);
compatibilityLayer.switchVersion(SystemVersion.V1);
Object getResultV1 = apiAdapter.handleRequest("getReqV1", "getUser", Map.of("userId", "user1"));
System.out.println("V1版本获取数据: " + getResultV1);
}
}
8. 安全性:筑牢防线,守护数据资产
安全性是架构评审中的重中之重。从多个层面构建了安全防护体系。
在代码层面,严格执行SQL注入与XSS攻击的防范措施,对用户输入进行严格的过滤与验证。
在数据层面,实施了数据加密存储与传输,确保数据在各个环节的安全性。
在接口层面,引入了防刷保护机制,通过限流、验证码等手段,防止恶意攻击。
在权限控制方面,建立了精细的访问控制策略,对数据与功能权限进行严格限制,确保只有授权用户能够访问敏感信息。
还对后台运营系统进行了日志审计,记录所有操作行为,以便在发生安全事件时能够快速追溯与定位。
通过这些安全措施,有效地降低了数据泄露与系统被攻击的风险,守护了公司的数据资产。
架构示例图
架构示例代码
// 安全系统实现
public class SecuritySystem {
// SQL注入防护
public static class SqlInjectionProtection {
private static final String[] SQL_INJECTION_PATTERNS = {
"SELECT", "INSERT", "UPDATE", "DELETE", "DROP", "UNION",
"EXEC", "EXECUTE", "xp_", "--", "/*", "*/", ";"
};
public static String sanitizeInput(String input) {
if (input == null) {
return null;
}
String sanitized = input;
// 移除潜在的SQL注入字符
for (String pattern : SQL_INJECTION_PATTERNS) {
sanitized = sanitized.replaceAll("(?i)" + pattern, "");
}
// 使用预编译语句参数化查询
return sanitized;
}
public static PreparedStatement createPreparedStatement(Connection conn, String sql, Object... params)
throws SQLException {
// 使用预编译语句防止SQL注入
PreparedStatement stmt = conn.prepareStatement(sql);
for (int i = 0; i < params.length; i++) {
stmt.setObject(i + 1, params[i]);
}
return stmt;
}
}
// XSS防护
public static class XssProtection {
private static final String[] XSS_PATTERNS = {
"<script", "</script>", "javascript:", "onload=", "onerror=",
"onfocus=", "onblur=", "onclick=", "onmouseover=", "onchange="
};
public static String sanitizeHtml(String input) {
if (input == null) {
return null;
}
String sanitized = input;
// 移除潜在的XSS字符
for (String pattern : XSS_PATTERNS) {
sanitized = sanitized.replaceAll("(?i)" + pattern, "");
}
// HTML转义
sanitized = sanitized.replace("&", "&")
.replace("<", "<")
.replace(">", ">")
.replace("\"", """)
.replace("'", "'");
return sanitized;
}
}
// 数据加密
public static class DataEncryption {
private static final String ALGORITHM = "AES";
private static final String TRANSFORMATION = "AES/CBC/PKCS5Padding";
private static final String SECRET_KEY = "ThisIsASecretKey123";
private static final String IV = "ThisIsAnInitVec";
public static String encrypt(String data) throws Exception {
SecretKeySpec secretKey = new SecretKeySpec(SECRET_KEY.getBytes(), ALGORITHM);
IvParameterSpec ivParameterSpec = new IvParameterSpec(IV.getBytes());
Cipher cipher = Cipher.getInstance(TRANSFORMATION);
cipher.init(Cipher.ENCRYPT_MODE, secretKey, ivParameterSpec);
byte[] encrypted = cipher.doFinal(data.getBytes());
return Base64.getEncoder().encodeToString(encrypted);
}
public static String decrypt(String encryptedData) throws Exception {
SecretKeySpec secretKey = new SecretKeySpec(SECRET_KEY.getBytes(), ALGORITHM);
IvParameterSpec ivParameterSpec = new IvParameterSpec(IV.getBytes());
Cipher cipher = Cipher.getInstance(TRANSFORMATION);
cipher.init(Cipher.DECRYPT_MODE, secretKey, ivParameterSpec);
byte[] decoded = Base64.getDecoder().decode(encryptedData);
byte[] decrypted = cipher.doFinal(decoded);
return new String(decrypted);
}
}
// 请求限流
public static class RequestRateLimiter {
private Map<String, Deque<Long>> userRequests;
private int maxRequests;
private long windowSize;
public RequestRateLimiter(int maxRequests, long windowSize) {
this.userRequests = new ConcurrentHashMap<>();
this.maxRequests = maxRequests;
this.windowSize = windowSize;
}
public boolean allowRequest(String userId) {
Deque<Long> requests = userRequests.computeIfAbsent(userId, k -> new ArrayDeque<>());
long currentTime = System.currentTimeMillis();
// 移除过期的请求
while (!requests.isEmpty() && currentTime - requests.peekFirst() > windowSize) {
requests.pollFirst();
}
// 检查是否超过限制
if (requests.size() >= maxRequests) {
return false;
}
// 记录当前请求
requests.addLast(currentTime);
return true;
}
}
// 验证码生成器
public static class CaptchaGenerator {
private static final String CHARACTERS = "ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnpqrstuvwxyz23456789";
private static final int CAPTCHA_LENGTH = 6;
public static String generateCaptcha() {
Random random = new Random();
StringBuilder captcha = new StringBuilder(CAPTCHA_LENGTH);
for (int i = 0; i < CAPTCHA_LENGTH; i++) {
captcha.append(CHARACTERS.charAt(random.nextInt(CHARACTERS.length())));
}
return captcha.toString();
}
public static boolean verifyCaptcha(String inputCaptcha, String storedCaptcha) {
return inputCaptcha != null && inputCaptcha.equalsIgnoreCase(storedCaptcha);
}
}
// 认证服务
public static class AuthenticationService {
private Map<String, String> userCredentials;
private Map<String, String> userTokens;
public AuthenticationService() {
this.userCredentials = new ConcurrentHashMap<>();
this.userTokens = new ConcurrentHashMap<>();
// 初始化测试用户
userCredentials.put("admin", "admin123");
userCredentials.put("user1", "password1");
}
public String login(String username, String password) {
if (userCredentials.containsKey(username) &&
userCredentials.get(username).equals(password)) {
// 生成令牌
String token = UUID.randomUUID().toString();
userTokens.put(token, username);
System.out.println("用户 " + username + " 登录成功");
return token;
}
System.out.println("用户 " + username + " 登录失败");
return null;
}
public boolean verifyToken(String token) {
return userTokens.containsKey(token);
}
public String getUsernameByToken(String token) {
return userTokens.get(token);
}
public void logout(String token) {
userTokens.remove(token);
System.out.println("用户已登出");
}
}
// 授权服务
public static class AuthorizationService {
private Map<String, Set<String>> userPermissions;
public AuthorizationService() {
this.userPermissions = new ConcurrentHashMap<>();
// 初始化用户权限
Set<String> adminPermissions = new HashSet<>();
adminPermissions.add("user:create");
adminPermissions.add("user:read");
adminPermissions.add("user:update");
adminPermissions.add("user:delete");
adminPermissions.add("system:admin");
userPermissions.put("admin", adminPermissions);
Set<String> userPermissions = new HashSet<>();
userPermissions.add("user:read");
userPermissions.add("user:update:own");
userPermissions.add("order:create");
userPermissions.add("order:read");
userPermissions.add("order:update:own");
userPermissions.add("order:delete:own");
userPermissions.put("user1", userPermissions);
}
public boolean hasPermission(String username, String permission) {
Set<String> permissions = userPermissions.get(username);
return permissions != null && permissions.contains(permission);
}
public boolean hasAnyPermission(String username, String... permissions) {
Set<String> userPerms = userPermissions.get(username);
if (userPerms == null) {
return false;
}
for (String permission : permissions) {
if (userPerms.contains(permission)) {
return true;
}
}
return false;
}
public boolean hasAllPermissions(String username, String... permissions) {
Set<String> userPerms = userPermissions.get(username);
if (userPerms == null) {
return false;
}
for (String permission : permissions) {
if (!userPerms.contains(permission)) {
return false;
}
}
return true;
}
}
// 日志审计
public static class AuditLogger {
private List<AuditLog> logs;
public AuditLogger() {
this.logs = new CopyOnWriteArrayList<>();
}
public void log(String username, String action, String resource, String details) {
AuditLog log = new AuditLog(
username,
action,
resource,
details,
new Date(),
InetAddress.getLoopbackAddress().getHostAddress()
);
logs.add(log);
System.out.println("审计日志: " + log);
}
public List<AuditLog> getLogsForUser(String username) {
return logs.stream()
.filter(log -> log.getUsername().equals(username))
.collect(Collectors.toList());
}
public List<AuditLog> getLogsForResource(String resource) {
return logs.stream()
.filter(log -> log.getResource().equals(resource))
.collect(Collectors.toList());
}
public List<AuditLog> getLogsByTimeRange(Date startTime, Date endTime) {
return logs.stream()
.filter(log -> !log.getTimestamp().before(startTime) &&
!log.getTimestamp().after(endTime))
.collect(Collectors.toList());
}
}
// 审计日志实体
public static class AuditLog {
private String username;
private String action;
private String resource;
private String details;
private Date timestamp;
String ipAddress;
public AuditLog(String username, String action, String resource,
String details, Date timestamp, String ipAddress) {
this.username = username;
this.action = action;
this.resource = resource;
this.details = details;
this.timestamp = timestamp;
this.ipAddress = ipAddress;
}
// getter方法
public String getUsername() { return username; }
public String getAction() { return action; }
public String getResource() { return resource; }
public String getDetails() { return details; }
public Date getTimestamp() { return timestamp; }
public String getIpAddress() { return ipAddress; }
@Override
public String toString() {
return String.format("[%s] 用户 %s 执行了 %s 操作 on %s. 详情: %s. IP: %s",
timestamp, username, action, resource, details, ipAddress);
}
}
// 安全中间件
public static class SecurityMiddleware {
private AuthenticationService authService;
private AuthorizationService authzService;
private RequestRateLimiter rateLimiter;
private AuditLogger auditLogger;
public SecurityMiddleware(AuthenticationService authService,
AuthorizationService authzService,
RequestRateLimiter rateLimiter,
AuditLogger auditLogger) {
this.authService = authService;
this.authzService = authzService;
this.rateLimiter = rateLimiter;
this.auditLogger = auditLogger;
}
public SecurityResponse checkRequest(String token, String userId, String action, String resource) {
// 1. 检查令牌
if (!authService.verifyToken(token)) {
auditLogger.log(userId, "AUTH_FAILED", resource, "无效的访问令牌");
return new SecurityResponse(false, "无效的访问令牌");
}
String username = authService.getUsernameByToken(token);
// 2. 检查限流
if (!rateLimiter.allowRequest(username)) {
auditLogger.log(username, "RATE_LIMIT_EXCEEDED", resource, "请求频率超限");
return new SecurityResponse(false, "请求频率超限,请稍后再试");
}
// 3. 检查权限
String permission = resource + ":" + action;
if (!authzService.hasPermission(username, permission)) {
auditLogger.log(username, "PERMISSION_DENIED", resource, "权限不足");
return new SecurityResponse(false, "权限不足");
}
// 4. 记录成功日志
auditLogger.log(username, action, resource, "操作成功");
return new SecurityResponse(true, "安全检查通过");
}
}
// 安全响应
public static class SecurityResponse {
private boolean allowed;
private String message;
public SecurityResponse(boolean allowed, String message) {
this.allowed = allowed;
this.message = message;
}
public boolean isAllowed() { return allowed; }
public String getMessage() { return message; }
}
// 主方法 - 演示安全系统
public static void main(String[] args) throws Exception {
// 创建安全组件
AuthenticationService authService = new AuthenticationService();
AuthorizationService authzService = new AuthorizationService();
RequestRateLimiter rateLimiter = new RequestRateLimiter(10, 60000); // 每分钟10次请求
AuditLogger auditLogger = new AuditLogger();
// 创建安全中间件
SecurityMiddleware securityMiddleware = new SecurityMiddleware(
authService, authzService, rateLimiter, auditLogger);
// 测试SQL注入防护
System.out.println("=== SQL注入防护测试 ===");
String maliciousInput = "SELECT * FROM users WHERE id = 1; DROP TABLE users;";
String sanitizedInput = SqlInjectionProtection.sanitizeInput(maliciousInput);
System.out.println("原始输入: " + maliciousInput);
System.out.println("净化后输入: " + sanitizedInput);
// 测试XSS防护
System.out.println("\n=== XSS防护测试 ===");
String xssInput = "<script>alert('XSS攻击')</script>";
String sanitizedHtml = XssProtection.sanitizeHtml(xssInput);
System.out.println("原始HTML: " + xssInput);
System.out.println("净化后HTML: " + sanitizedHtml);
// 测试数据加密
System.out.println("\n=== 数据加密测试 ===");
String sensitiveData = "用户敏感信息";
String encrypted = DataEncryption.encrypt(sensitiveData);
String decrypted = DataEncryption.decrypt(encrypted);
System.out.println("原始数据: " + sensitiveData);
System.out.println("加密后: " + encrypted);
System.out.println("解密后: " + decrypted);
// 测试验证码
System.out.println("\n=== 验证码测试 ===");
String captcha = CaptchaGenerator.generateCaptcha();
System.out.println("生成的验证码: " + captcha);
System.out.println("验证码验证: " + CaptchaGenerator.verifyCaptcha(captcha, captcha));
// 测试认证授权
System.out.println("\n=== 认证授权测试 ===");
// 用户登录
String token = authService.login("admin", "admin123");
System.out.println("登录令牌: " + (token != null ? "成功" : "失败"));
if (token != null) {
// 检查权限
boolean hasPermission = authzService.hasPermission("admin", "user:create");
System.out.println("admin用户是否有创建用户权限: " + hasPermission);
// 使用安全中间件检查请求
SecurityResponse response = securityMiddleware.checkRequest(
token, "admin", "create", "user");
System.out.println("安全检查结果: " + response.getMessage());
// 模拟无权限操作
response = securityMiddleware.checkRequest(
token, "admin", "delete", "user");
System.out.println("无权限操作检查结果: " + response.getMessage());
// 用户登出
authService.logout(token);
}
// 测试请求限流
System.out.println("\n=== 请求限流测试 ===");
String testToken = authService.login("user1", "password1");
if (testToken != null) {
// 模拟多次请求
for (int i = 0; i < 15; i++) {
SecurityResponse response = securityMiddleware.checkRequest(
testToken, "user1", "read", "product");
System.out.println("请求 " + (i + 1) + ": " + response.getMessage());
if (!response.isAllowed()) {
break;
}
try {
Thread.sleep(100); // 模拟请求间隔
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
}
}
authService.logout(testToken);
}
// 测试日志审计
System.out.println("\n=== 日志审计测试 ===");
// 模拟一些操作
authService.login("admin", "admin123");
auditLogger.log("admin", "read", "user", "查看用户列表");
auditLogger.log("admin", "create", "user", "创建新用户");
auditLogger.log("user1", "read", "order", "查看订单");
// 查询特定用户的日志
List<AuditLog> adminLogs = auditLogger.getLogsForUser("admin");
System.out.println("\nadmin用户的操作日志:");
adminLogs.forEach(System.out::println);
// 查询特定资源的日志
List<AuditLog> userLogs = auditLogger.getLogsForResource("user");
System.out.println("\nuser资源的操作日志:");
userLogs.forEach(System.out::println);
}
}
9. 可测性:精准测试,确保系统质量
尽量缩小测试环境与线上的差异,确保测试结果能够真实反映线上系统的运行状态。
同时,支持在线上进行压测,但通过隔离测试数据、设置测试白名单等手段,避免对真实用户产生影响。
例如,在一次线上压测中,通过模拟10万并发用户,对系统的性能进行了全面测试,及时发现了系统中的性能瓶颈,并进行了针对性优化。
此外,还支持部署多套隔离的测试环境,满足不同测试场景的需求。在测试过程中,合理分配黑盒测试与白盒测试的工作量,确保测试的全面性与深入性。
例如,对于核心业务逻辑,采用白盒测试,深入代码层面进行验证;对于系统接口与用户交互,采用黑盒测试,从用户视角进行测试。
通过这些可测性设计,能够精准定位系统中的问题,确保系统上线后的稳定运行。
架构示例图
架构示例代码
// 可测试系统实现
public class TestableSystem {
// 业务服务接口
public interface BusinessService {
Result process(Request request);
}
// 请求对象
public static class Request {
private String id;
private String type;
private Map<String, Object> parameters;
public Request(String id, String type) {
this.id = id;
this.type = type;
this.parameters = new HashMap<>();
}
public String getId() { return id; }
public String getType() { return type; }
public Map<String, Object> getParameters() { return parameters; }
public void addParameter(String key, Object value) {
parameters.put(key, value);
}
}
// 结果对象
public static class Result {
private boolean success;
private String message;
private Object data;
public Result(boolean success, String message) {
this(success, message, null);
}
public Result(boolean success, String message, Object data) {
this.success = success;
this.message = message;
this.data = data;
}
public boolean isSuccess() { return success; }
public String getMessage() { return message; }
public Object getData() { return data; }
}
// 业务服务实现
public static class OrderService implements BusinessService {
private OrderRepository orderRepository;
public OrderService(OrderRepository orderRepository) {
this.orderRepository = orderRepository;
}
@Override
public Result process(Request request) {
try {
String orderId = request.getId();
String userId = (String) request.getParameters().get("userId");
BigDecimal amount = new BigDecimal((String) request.getParameters().get("amount"));
// 验证订单
if (orderId == null || orderId.isEmpty()) {
return new Result(false, "订单ID不能为空");
}
if (userId == null || userId.isEmpty()) {
return new Result(false, "用户ID不能为空");
}
if (amount == null || amount.compareTo(BigDecimal.ZERO) <= 0) {
return new Result(false, "订单金额必须大于0");
}
// 创建订单
Order order = new Order(orderId, userId, amount);
orderRepository.save(order);
return new Result(true, "订单创建成功", order);
} catch (Exception e) {
return new Result(false, "处理订单失败: " + e.getMessage());
}
}
}
// 订单仓库
public interface OrderRepository {
void save(Order order);
Order findById(String orderId);
List<Order> findByUserId(String userId);
}
// 内存订单仓库(用于测试)
public static class InMemoryOrderRepository implements OrderRepository {
private Map<String, Order> orders;
public InMemoryOrderRepository() {
this.orders = new ConcurrentHashMap<>();
}
@Override
public void save(Order order) {
orders.put(order.getId(), order);
}
@Override
public Order findById(String orderId) {
return orders.get(orderId);
}
@Override
public List<Order> findByUserId(String userId) {
return orders.values().stream()
.filter(order -> order.getUserId().equals(userId))
.collect(Collectors.toList());
}
public void clear() {
orders.clear();
}
}
// 订单实体
public static class Order {
private String id;
private String userId;
private BigDecimal amount;
private Date createTime;
public Order(String id, String userId, BigDecimal amount) {
this.id = id;
this.userId = userId;
this.amount = amount;
this.createTime = new Date();
}
public String getId() { return id; }
public String getUserId() { return userId; }
public BigDecimal getAmount() { return amount; }
public Date getCreateTime() { return createTime; }
}
// 单元测试
public static class UnitTest {
private OrderService orderService;
private InMemoryOrderRepository orderRepository;
public UnitTest() {
this.orderRepository = new InMemoryOrderRepository();
this.orderService = new OrderService(orderRepository);
}
public void testOrderCreation() {
// 测试正常订单创建
Request request = new Request("order123", "create");
request.addParameter("userId", "user123");
request.addParameter("amount", "100.00");
Result result = orderService.process(request);
assert result.isSuccess() : "订单创建应该成功";
assert result.getData() instanceof Order : "返回数据应该是Order对象";
Order order = (Order) result.getData();
assert order.getId().equals("order123") : "订单ID应该匹配";
assert order.getUserId().equals("user123") : "用户ID应该匹配";
assert order.getAmount().compareTo(new BigDecimal("100.00")) == 0 : "订单金额应该匹配";
System.out.println("单元测试通过: 订单创建");
}
public void testInvalidOrderId() {
// 测试无效订单ID
Request request = new Request("", "create");
request.addParameter("userId", "user123");
request.addParameter("amount", "100.00");
Result result = orderService.process(request);
assert !result.isSuccess() : "无效订单ID应该失败";
assert result.getMessage().equals("订单ID不能为空") : "错误消息应该匹配";
System.out.println("单元测试通过: 无效订单ID");
}
public void testInvalidAmount() {
// 测试无效金额
Request request = new Request("order123", "create");
request.addParameter("userId", "user123");
request.addParameter("amount", "-100.00");
Result result = orderService.process(request);
assert !result.isSuccess() : "无效金额应该失败";
assert result.getMessage().equals("订单金额必须大于0") : "错误消息应该匹配";
System.out.println("单元测试通过: 无效金额");
}
public void runAllTests() {
orderRepository.clear();
testOrderCreation();
testInvalidOrderId();
testInvalidAmount();
System.out.println("所有单元测试通过");
}
}
// 集成测试
public static class IntegrationTest {
private OrderService orderService;
private InMemoryOrderRepository orderRepository;
public IntegrationTest() {
this.orderRepository = new InMemoryOrderRepository();
this.orderService = new OrderService(orderRepository);
}
public void testOrderPersistence() {
// 创建订单
Request request = new Request("order123", "create");
request.addParameter("userId", "user123");
request.addParameter("amount", "100.00");
Result result = orderService.process(request);
assert result.isSuccess() : "订单创建应该成功";
// 验证订单是否持久化
Order savedOrder = orderRepository.findById("order123");
assert savedOrder != null : "订单应该被持久化";
assert savedOrder.getId().equals("order123") : "持久化的订单ID应该匹配";
System.out.println("集成测试通过: 订单持久化");
}
public void testUserOrderQuery() {
// 创建多个订单
Request request1 = new Request("order1", "create");
request1.addParameter("userId", "user123");
request1.addParameter("amount", "100.00");
orderService.process(request1);
Request request2 = new Request("order2", "create");
request2.addParameter("userId", "user123");
request2.addParameter("amount", "200.00");
orderService.process(request2);
Request request3 = new Request("order3", "create");
request3.addParameter("userId", "user456");
request3.addParameter("amount", "150.00");
orderService.process(request3);
// 查询用户订单
List<Order> userOrders = orderRepository.findByUserId("user123");
assert userOrders.size() == 2 : "用户应该有2个订单";
System.out.println("集成测试通过: 用户订单查询");
}
public void runAllTests() {
orderRepository.clear();
testOrderPersistence();
testUserOrderQuery();
System.out.println("所有集成测试通过");
}
}
// 性能测试
public static class PerformanceTest {
private OrderService orderService;
private InMemoryOrderRepository orderRepository;
public PerformanceTest() {
this.orderRepository = new InMemoryOrderRepository();
this.orderService = new OrderService(orderRepository);
}
public void testConcurrentOrderCreation(int threadCount, int requestsPerThread) {
ExecutorService executor = Executors.newFixedThreadPool(threadCount);
CountDownLatch latch = new CountDownLatch(threadCount * requestsPerThread);
long startTime = System.currentTimeMillis();
// 提交并发请求
for (int i = 0; i < threadCount; i++) {
final int threadId = i;
executor.submit(() -> {
for (int j = 0; j < requestsPerThread; j++) {
Request request = new Request("order-" + threadId + "-" + j, "create");
request.addParameter("userId", "user-" + threadId);
request.addParameter("amount", "100.00");
Result result = orderService.process(request);
assert result.isSuccess() : "订单创建应该成功";
latch.countDown();
}
});
}
try {
latch.await();
long endTime = System.currentTimeMillis();
double duration = (endTime - startTime) / 1000.0;
double tps = (threadCount * requestsPerThread) / duration;
System.out.println("性能测试结果:");
System.out.println("线程数: " + threadCount);
System.out.println("每线程请求数: " + requestsPerThread);
System.out.println("总请求数: " + (threadCount * requestsPerThread));
System.out.println("总耗时: " + duration + "秒");
System.out.println("TPS: " + tps);
// 验证所有订单都被创建
int totalOrders = orderRepository.findByUserId("user-0").size() +
orderRepository.findByUserId("user-1").size();
assert totalOrders == (threadCount * requestsPerThread) : "所有订单都应该被创建";
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
} finally {
executor.shutdown();
}
}
public void runPerformanceTest() {
orderRepository.clear();
testConcurrentOrderCreation(10, 100); // 10个线程,每个线程100个请求
System.out.println("性能测试完成");
}
}
// 测试数据生成器
public static class TestDataGenerator {
private static final Random random = new Random();
public static String generateOrderId() {
return "order-" + System.currentTimeMillis() + "-" + random.nextInt(10000);
}
public static String generateUserId() {
return "user-" + random.nextInt(10000);
}
public static String generateAmount() {
return String.format("%.2f", 10 + random.nextDouble() * 1000);
}
public static Request generateOrderRequest() {
Request request = new Request(generateOrderId(), "create");
request.addParameter("userId", generateUserId());
request.addParameter("amount", generateAmount());
return request;
}
public static List<Request> generateOrderRequests(int count) {
List<Request> requests = new ArrayList<>();
for (int i = 0; i < count; i++) {
requests.add(generateOrderRequest());
}
return requests;
}
}
// 主方法 - 演示可测试系统
public static void main(String[] args) {
// 运行单元测试
System.out.println("=== 运行单元测试 ===");
UnitTest unitTest = new UnitTest();
unitTest.runAllTests();
// 运行集成测试
System.out.println("\n=== 运行集成测试 ===");
IntegrationTest integrationTest = new IntegrationTest();
integrationTest.runAllTests();
// 运行性能测试
System.out.println("\n=== 运行性能测试 ===");
PerformanceTest performanceTest = new PerformanceTest();
performanceTest.runPerformanceTest();
// 测试数据生成器演示
System.out.println("\n=== 测试数据生成器演示 ===");
List<Request> requests = TestDataGenerator.generateOrderRequests(5);
for (Request request : requests) {
System.out.println("生成的请求: ID=" + request.getId() +
", 用户ID=" + request.getParameters().get("userId") +
", 金额=" + request.getParameters().get("amount"));
}
}
}
10. 可运维性:简化运维,降低运营成本
可运维性关注系统在长期运行过程中的维护与管理。
为系统设计了初始化与预热环节,确保系统在启动时能够快速进入稳定状态。针对数据指数级别递增的问题,制定了定期归档策略,将历史数据迁移到低成本存储介质中,降低了存储成本。
同时,建立了完善的系统巡检与维护机制,定期对系统进行性能监控、日志分析与故障排查,及时发现并解决潜在问题。
例如,通过自动化脚本,每天凌晨对系统进行全量巡检,生成巡检报告,并将异常情况及时通知运维人员。
此外,还设计了业务运维的可视化界面,使运维人员能够直观地了解系统运行状态,快速定位问题根源,提高了运维效率,降低了运营成本。
架构示例图
架构示例代码
// 可运维系统实现
public class OperableSystem {
// 系统初始化服务
public static class SystemInitializer {
private List<SystemComponent> components;
public SystemInitializer() {
this.components = new ArrayList<>();
}
public void registerComponent(SystemComponent component) {
components.add(component);
}
public void initialize() {
System.out.println("开始系统初始化...");
for (SystemComponent component : components) {
try {
System.out.println("初始化组件: " + component.getName());
component.initialize();
System.out.println("组件 " + component.getName() + " 初始化成功");
} catch (Exception e) {
System.err.println("组件 " + component.getName() + " 初始化失败: " + e.getMessage());
throw new RuntimeException("系统初始化失败", e);
}
}
System.out.println("系统初始化完成");
}
}
// 系统预热服务
public static class SystemWarmer {
private List<SystemComponent> components;
public SystemWarmer() {
this.components = new ArrayList<>();
}
public void registerComponent(SystemComponent component) {
components.add(component);
}
public void warmUp() {
System.out.println("开始系统预热...");
for (SystemComponent component : components) {
try {
System.out.println("预热组件: " + component.getName());
component.warmUp();
System.out.println("组件 " + component.getName() + " 预热完成");
} catch (Exception e) {
System.err.println("组件 " + component.getName() + " 预热失败: " + e.getMessage());
}
}
System.out.println("系统预热完成");
}
}
// 系统组件接口
public interface SystemComponent {
String getName();
void initialize() throws Exception;
void warmUp() throws Exception;
void shutdown() throws Exception;
}
// 数据库组件
public static class DatabaseComponent implements SystemComponent {
private String name;
private boolean initialized;
public DatabaseComponent(String name) {
this.name = name;
this.initialized = false;
}
@Override
public String getName() {
return name;
}
@Override
public void initialize() throws Exception {
// 模拟数据库初始化
System.out.println("初始化数据库连接池...");
Thread.sleep(1000); // 模拟初始化耗时
// 创建必要的表
System.out.println("创建数据库表结构...");
Thread.sleep(500);
initialized = true;
}
@Override
public void warmUp() throws Exception {
if (!initialized) {
throw new IllegalStateException("数据库未初始化");
}
// 预热数据库连接
System.out.println("预热数据库连接...");
Thread.sleep(500);
// 预加载常用数据
System.out.println("预加载常用数据...");
Thread.sleep(500);
}
@Override
public void shutdown() throws Exception {
System.out.println("关闭数据库连接...");
Thread.sleep(300);
}
}
// 缓存组件
public static class CacheComponent implements SystemComponent {
private String name;
private boolean initialized;
public CacheComponent(String name) {
this.name = name;
this.initialized = false;
}
@Override
public String getName() {
return name;
}
@Override
public void initialize() throws Exception {
// 模拟缓存初始化
System.out.println("初始化缓存连接...");
Thread.sleep(800);
initialized = true;
}
@Override
public void warmUp() throws Exception {
if (!initialized) {
throw new IllegalStateException("缓存未初始化");
}
// 预热缓存
System.out.println("预热缓存数据...");
Thread.sleep(1000);
}
@Override
public void shutdown() throws Exception {
System.out.println("关闭缓存连接...");
Thread.sleep(200);
}
}
// 数据归档服务
public static class DataArchivingService {
private StorageSystem storageSystem;
private DataArchivingPolicy policy;
public DataArchivingService(StorageSystem storageSystem, DataArchivingPolicy policy) {
this.storageSystem = storageSystem;
this.policy = policy;
}
public void archiveData() {
System.out.println("开始数据归档...");
// 获取需要归档的数据
List<DataRecord> dataToArchive = storageSystem.getDataToArchive(policy);
if (dataToArchive.isEmpty()) {
System.out.println("没有需要归档的数据");
return;
}
// 归档数据
for (DataRecord record : dataToArchive) {
try {
storageSystem.moveToArchive(record);
System.out.println("数据已归档: " + record.getId());
} catch (Exception e) {
System.err.println("数据归档失败: " + record.getId() + ", 错误: " + e.getMessage());
}
}
System.out.println("数据归档完成,共归档 " + dataToArchive.size() + " 条记录");
}
}
// 存储系统
public static class StorageSystem {
private Map<String, DataRecord> hotStorage;
private Map<String, DataRecord> coldStorage;
private Map<String, DataRecord> archiveStorage;
public StorageSystem() {
this.hotStorage = new ConcurrentHashMap<>();
this.coldStorage = new ConcurrentHashMap<>();
this.archiveStorage = new ConcurrentHashMap<>();
// 初始化一些测试数据
initializeTestData();
}
private void initializeTestData() {
// 创建一些测试数据
for (int i = 1; i <= 1000; i++) {
DataRecord record = new DataRecord("record-" + i, "数据内容 " + i,
new Date(System.currentTimeMillis() - i * 24 * 60 * 60 * 1000L));
if (i <= 100) {
hotStorage.put(record.getId(), record);
} else if (i <= 500) {
coldStorage.put(record.getId(), record);
} else {
archiveStorage.put(record.getId(), record);
}
}
}
public List<DataRecord> getDataToArchive(DataArchivingPolicy policy) {
List<DataRecord> toArchive = new ArrayList<>();
// 根据策略获取需要归档的数据
Date cutoffDate = new Date(System.currentTimeMillis() - policy.getArchiveThreshold());
coldStorage.forEach((id, record) -> {
if (record.getCreateTime().before(cutoffDate)) {
toArchive.add(record);
}
});
return toArchive;
}
public void moveToArchive(DataRecord record) {
// 从冷存储中移除
coldStorage.remove(record.getId());
// 添加到归档存储
archiveStorage.put(record.getId(), record);
}
public int getHotStorageSize() {
return hotStorage.size();
}
public int getColdStorageSize() {
return coldStorage.size();
}
public int getArchiveStorageSize() {
return archiveStorage.size();
}
}
// 数据记录
public static class DataRecord {
private String id;
private String content;
private Date createTime;
public DataRecord(String id, String content, Date createTime) {
this.id = id;
this.content = content;
this.createTime = createTime;
}
public String getId() { return id; }
public String getContent() { return content; }
public Date getCreateTime() { return createTime; }
}
// 数据归档策略
public static class DataArchivingPolicy {
private long archiveThreshold; // 归档阈值(毫秒)
private int batchSize; // 批处理大小
public DataArchivingPolicy(long archiveThreshold, int batchSize) {
this.archiveThreshold = archiveThreshold;
this.batchSize = batchSize;
}
public long getArchiveThreshold() {
return archiveThreshold;
}
public int getBatchSize() {
return batchSize;
}
}
// 系统巡检服务
public static class SystemInspectionService {
private List<SystemInspector> inspectors;
private NotificationService notificationService;
public SystemInspectionService(NotificationService notificationService) {
this.inspectors = new ArrayList<>();
this.notificationService = notificationService;
}
public void registerInspector(SystemInspector inspector) {
inspectors.add(inspector);
}
public InspectionReport performInspection() {
System.out.println("开始系统巡检...");
InspectionReport report = new InspectionReport();
for (SystemInspector inspector : inspectors) {
try {
InspectionResult result = inspector.inspect();
report.addResult(result);
if (!result.isHealthy()) {
notificationService.sendAlert(result.getMessage());
}
} catch (Exception e) {
InspectionResult errorResult = new InspectionResult(
inspector.getName(), false, "巡检失败: " + e.getMessage());
report.addResult(errorResult);
notificationService.sendAlert("系统巡检异常: " + e.getMessage());
}
}
System.out.println("系统巡检完成");
return report;
}
}
// 系统巡检器接口
public interface SystemInspector {
String getName();
InspectionResult inspect() throws Exception;
}
// CPU使用率巡检器
public static class CpuUsageInspector implements SystemInspector {
@Override
public String getName() {
return "CPU使用率巡检器";
}
@Override
public InspectionResult inspect() throws Exception {
// 模拟获取CPU使用率
double cpuUsage = 50 + Math.random() * 40; // 50-90%
if (cpuUsage > 80) {
return new InspectionResult(getName(), false,
"CPU使用率过高: " + String.format("%.2f", cpuUsage) + "%");
}
return new InspectionResult(getName(), true,
"CPU使用率正常: " + String.format("%.2f", cpuUsage) + "%");
}
}
// 内存使用率巡检器
public static class MemoryUsageInspector implements SystemInspector {
@Override
public String getName() {
return "内存使用率巡检器";
}
@Override
public InspectionResult inspect() throws Exception {
// 模拟获取内存使用率
double memoryUsage = 40 + Math.random() * 50; // 40-90%
if (memoryUsage > 85) {
return new InspectionResult(getName(), false,
"内存使用率过高: " + String.format("%.2f", memoryUsage) + "%");
}
return new InspectionResult(getName(), true,
"内存使用率正常: " + String.format("%.2f", memoryUsage) + "%");
}
}
// 磁盘空间巡检器
public static class DiskSpaceInspector implements SystemInspector {
@Override
public String getName() {
return "磁盘空间巡检器";
}
@Override
public InspectionResult inspect() throws Exception {
// 模拟获取磁盘使用率
double diskUsage = 30 + Math.random() * 60; // 30-90%
if (diskUsage > 85) {
return new InspectionResult(getName(), false,
"磁盘空间不足: " + String.format("%.2f", diskUsage) + "%");
}
return new InspectionResult(getName(), true,
"磁盘空间正常: " + String.format("%.2f", diskUsage) + "%");
}
}
// 巡检结果
public static class InspectionResult {
private String inspectorName;
private boolean healthy;
private String message;
public InspectionResult(String inspectorName, boolean healthy, String message) {
this.inspectorName = inspectorName;
this.healthy = healthy;
this.message = message;
}
public String getInspectorName() { return inspectorName; }
public boolean isHealthy() { return healthy; }
public String getMessage() { return message; }
}
// 巡检报告
public static class InspectionReport {
private List<InspectionResult> results;
public InspectionReport() {
this.results = new ArrayList<>();
}
public void addResult(InspectionResult result) {
results.add(result);
}
public boolean isSystemHealthy() {
return results.stream().allMatch(InspectionResult::isHealthy);
}
public String getSummary() {
int healthyCount = (int) results.stream().filter(InspectionResult::isHealthy).count();
int unhealthyCount = results.size() - healthyCount;
return String.format("巡检完成: 共%d项检查, %d项正常, %d项异常",
results.size(), healthyCount, unhealthyCount);
}
public List<InspectionResult> getUnhealthyResults() {
return results.stream()
.filter(result -> !result.isHealthy())
.collect(Collectors.toList());
}
}
// 通知服务
public static class NotificationService {
private List<String> notifications;
public NotificationService() {
this.notifications = new CopyOnWriteArrayList<>();
}
public void sendAlert(String message) {
String notification = "[ALERT] " + new Date() + ": " + message;
notifications.add(notification);
System.out.println(notification);
}
public void sendInfo(String message) {
String notification = "[INFO] " + new Date() + ": " + message;
notifications.add(notification);
System.out.println(notification);
}
public List<String> getNotifications() {
return notifications;
}
}
// 可视化分析服务
public static class VisualizationService {
private SystemInspectionService inspectionService;
public VisualizationService(SystemInspectionService inspectionService) {
this.inspectionService = inspectionService;
}
public void generateDashboard() {
InspectionReport report = inspectionService.performInspection();
System.out.println("\n=== 系统状态仪表板 ===");
System.out.println(report.getSummary());
if (!report.isSystemHealthy()) {
System.out.println("\n异常项目:");
for (InspectionResult result : report.getUnhealthyResults()) {
System.out.println("- " + result.getInspectorName() + ": " + result.getMessage());
}
}
System.out.println("\n=== 系统资源使用情况 ===");
System.out.println("- CPU使用率: " + (40 + Math.random() * 40) + "%");
System.out.println("- 内存使用率: " + (30 + Math.random() * 50) + "%");
System.out.println("- 磁盘使用率: " + (20 + Math.random() * 60) + "%");
System.out.println("\n=== 存储使用情况 ===");
System.out.println("- 热存储: " + (50 + Math.random() * 100) + "GB");
System.out.println("- 冷存储: " + (200 + Math.random() * 300) + "GB");
System.out.println("- 归档存储: " + (500 + Math.random() * 1000) + "GB");
}
}
// 主方法 - 演示可运维系统
public static void main(String[] args) throws Exception {
// 创建通知服务
NotificationService notificationService = new NotificationService();
// 创建系统初始化和预热服务
SystemInitializer systemInitializer = new SystemInitializer();
SystemWarmer systemWarmer = new SystemWarmer();
// 注册系统组件
DatabaseComponent dbComponent = new DatabaseComponent("主数据库");
CacheComponent cacheComponent = new CacheComponent("分布式缓存");
systemInitializer.registerComponent(dbComponent);
systemInitializer.registerComponent(cacheComponent);
systemWarmer.registerComponent(dbComponent);
systemWarmer.registerComponent(cacheComponent);
// 初始化系统
systemInitializer.initialize();
// 预热系统
systemWarmer.warmUp();
// 创建存储系统和归档策略
StorageSystem storageSystem = new StorageSystem();
DataArchivingPolicy archivingPolicy = new DataArchivingPolicy(
90L * 24 * 60 * 60 * 1000, // 90天
1000 // 每批处理1000条记录
);
// 创建数据归档服务
DataArchivingService archivingService = new DataArchivingService(storageSystem, archivingPolicy);
// 执行数据归档
archivingService.archiveData();
// 创建系统巡检服务
SystemInspectionService inspectionService = new SystemInspectionService(notificationService);
// 注册巡检器
inspectionService.registerInspector(new CpuUsageInspector());
inspectionService.registerInspector(new MemoryUsageInspector());
inspectionService.registerInspector(new DiskSpaceInspector());
// 执行系统巡检
InspectionReport report = inspectionService.performInspection();
System.out.println("\n" + report.getSummary());
// 创建可视化分析服务
VisualizationService visualizationService = new VisualizationService(inspectionService);
// 生成仪表板
visualizationService.generateDashboard();
// 显示通知
System.out.println("\n=== 通知历史 ===");
notificationService.getNotifications().forEach(System.out::println);
// 关闭系统组件
dbComponent.shutdown();
cacheComponent.shutdown();
}
}
11. 监控与报警:实时感知,快速响应
监控与报警是架构评审中保障系统稳定运行的最后一道防线。
- 对系统内外部依赖的接口进行了全面监控,包括接口的响应时间、错误率等关键指标。
- 在应用层面,暴露了丰富的系统内部指标,如线程池使用率、内存使用率等,为监控与报警提供了数据支持。
- 针对系统层面使用的中间件与存储,也建立了完善的监控报警机制。
例如,当数据库连接池使用率超过90%时,监控系统会立即发出报警,提醒运维人员及时采取措施,如增加数据库连接数或优化数据库查询。
通过这些监控报警设计,能够实时感知系统运行状态,快速响应异常情况,将故障影响降至最低。
架构示例图
架构示例代码
// 监控与报警系统实现
public class MonitoringAndAlertSystem {
// 监控指标类型
public enum MetricType {
COUNTER, // 计数器,只增不减
GAUGE, // 测量值,可增可减
HISTOGRAM, // 直方图,用于统计分布
SUMMARY // 摘要,用于统计分位数
}
// 监控指标
public static class Metric {
private String name;
private String description;
private MetricType type;
private double value;
private Map<String, String> labels;
private long timestamp;
public Metric(String name, String description, MetricType type) {
this.name = name;
this.description = description;
this.type = type;
this.value = 0;
this.labels = new HashMap<>();
this.timestamp = System.currentTimeMillis();
}
public void setValue(double value) {
this.value = value;
this.timestamp = System.currentTimeMillis();
}
public void increment(double delta) {
this.value += delta;
this.timestamp = System.currentTimeMillis();
}
public String getName() { return name; }
public String getDescription() { return description; }
public MetricType getType() { return type; }
public double getValue() { return value; }
public Map<String, String> getLabels() { return labels; }
public long getTimestamp() { return timestamp; }
public void addLabel(String key, String value) {
labels.put(key, value);
}
}
// 监控数据采集器
public static class MetricCollector {
private Map<String, Metric> metrics;
public MetricCollector() {
this.metrics = new ConcurrentHashMap<>();
}
public void registerMetric(Metric metric) {
metrics.put(metric.getName(), metric);
}
public void recordMetric(String name, double value) {
Metric metric = metrics.get(name);
if (metric != null) {
metric.setValue(value);
}
}
public void incrementMetric(String name, double delta) {
Metric metric = metrics.get(name);
if (metric != null) {
metric.increment(delta);
}
}
public Metric getMetric(String name) {
return metrics.get(name);
}
public List<Metric> getAllMetrics() {
return new ArrayList<>(metrics.values());
}
}
// 应用指标监控
public static class ApplicationMetrics {
private MetricCollector collector;
public ApplicationMetrics(MetricCollector collector) {
this.collector = collector;
// 注册应用指标
collector.registerMetric(new Metric("http_requests_total", "HTTP请求总数", MetricType.COUNTER));
collector.registerMetric(new Metric("http_requests_duration_seconds", "HTTP请求耗时", MetricType.HISTOGRAM));
collector.registerMetric(new Metric("jvm_memory_used_bytes", "JVM内存使用量", MetricType.GAUGE));
collector.registerMetric(new Metric("jvm_thread_count", "JVM线程数", MetricType.GAUGE));
collector.registerMetric(new Metric("app_errors_total", "应用错误总数", MetricType.COUNTER));
}
public void recordHttpRequest(String method, String path, int statusCode, double duration) {
// 记录HTTP请求
collector.incrementMetric("http_requests_total", 1);
// 记录请求耗时
Metric durationMetric = collector.getMetric("http_requests_duration_seconds");
if (durationMetric != null) {
durationMetric.increment(duration);
}
// 记录错误
if (statusCode >= 400) {
collector.incrementMetric("app_errors_total", 1);
}
}
public void updateJvmMetrics(long memoryUsed, int threadCount) {
// 更新JVM指标
collector.recordMetric("jvm_memory_used_bytes", memoryUsed);
collector.recordMetric("jvm_thread_count", threadCount);
}
}
// 中间件指标监控
public static class MiddlewareMetrics {
private MetricCollector collector;
public MiddlewareMetrics(MetricCollector collector) {
this.collector = collector;
// 注册中间件指标
collector.registerMetric(new Metric("database_connections_active", "数据库活跃连接数", MetricType.GAUGE));
collector.registerMetric(new Metric("database_connections_max", "数据库最大连接数", MetricType.GAUGE));
collector.registerMetric(new Metric("cache_hits_total", "缓存命中总数", MetricType.COUNTER));
collector.registerMetric(new Metric("cache_misses_total", "缓存未命中总数", MetricType.COUNTER));
collector.registerMetric(new Metric("message_queue_size", "消息队列大小", MetricType.GAUGE));
}
public void updateDatabaseMetrics(int activeConnections, int maxConnections) {
// 更新数据库指标
collector.recordMetric("database_connections_active", activeConnections);
collector.recordMetric("database_connections_max", maxConnections);
}
public void recordCacheHit() {
collector.incrementMetric("cache_hits_total", 1);
}
public void recordCacheMiss() {
collector.incrementMetric("cache_misses_total", 1);
}
public void updateMessageQueueSize(int size) {
collector.recordMetric("message_queue_size", size);
}
}
// 报警规则
public static class AlertRule {
private String name;
private String metricName;
private String operator;
private double threshold;
private String severity;
private String message;
public AlertRule(String name, String metricName, String operator,
double threshold, String severity, String message) {
this.name = name;
this.metricName = metricName;
this.operator = operator;
this.threshold = threshold;
this.severity = severity;
this.message = message;
}
public boolean evaluate(Metric metric) {
if (metric == null) {
return false;
}
double value = metric.getValue();
switch (operator) {
case ">":
return value > threshold;
case ">=":
return value >= threshold;
case "<":
return value < threshold;
case "<=":
return value <= threshold;
case "==":
return value == threshold;
case "!=":
return value != threshold;
default:
return false;
}
}
public String getName() { return name; }
public String getMetricName() { return metricName; }
public String getOperator() { return operator; }
public double getThreshold() { return threshold; }
public String getSeverity() { return severity; }
public String getMessage() { return message; }
}
// 报警系统
public static class AlertSystem {
private List<AlertRule> rules;
private List<Alert> activeAlerts;
private NotificationService notificationService;
public AlertSystem(NotificationService notificationService) {
this.rules = new ArrayList<>();
this.activeAlerts = new ArrayList<>();
this.notificationService = notificationService;
}
public void addRule(AlertRule rule) {
rules.add(rule);
}
public void evaluateMetrics(List<Metric> metrics) {
for (Metric metric : metrics) {
for (AlertRule rule : rules) {
if (rule.getMetricName().equals(metric.getName()) && rule.evaluate(metric)) {
// 检查是否已有活跃的报警
boolean existingAlert = activeAlerts.stream()
.anyMatch(alert -> alert.getRuleName().equals(rule.getName()));
if (!existingAlert) {
// 创建新报警
Alert alert = new Alert(
rule.getName(),
rule.getSeverity(),
rule.getMessage(),
metric.getValue(),
new Date()
);
activeAlerts.add(alert);
notificationService.sendAlert(alert);
}
}
}
}
// 检查是否需要关闭报警
checkAlertResolution();
}
private void checkAlertResolution() {
Iterator<Alert> iterator = activeAlerts.iterator();
while (iterator.hasNext()) {
Alert alert = iterator.next();
Metric metric = getMetricByName(alert.getRuleName());
if (metric != null && !getRuleByName(alert.getRuleName()).evaluate(metric)) {
// 报警已解决
iterator.remove();
notificationService.sendResolution(alert);
}
}
}
private Metric getMetricByName(String metricName) {
// 简化实现,实际应该从MetricCollector获取
return null;
}
private AlertRule getRuleByName(String ruleName) {
return rules.stream()
.filter(rule -> rule.getName().equals(ruleName))
.findFirst()
.orElse(null);
}
public List<Alert> getActiveAlerts() {
return new ArrayList<>(activeAlerts);
}
}
// 报警
public static class Alert {
private String ruleName;
private String severity;
private String message;
private double value;
private Date timestamp;
public Alert(String ruleName, String severity, String message, double value, Date timestamp) {
this.ruleName = ruleName;
this.severity = severity;
this.message = message;
this.value = value;
this.timestamp = timestamp;
}
public String getRuleName() { return ruleName; }
public String getSeverity() { return severity; }
public String getMessage() { return message; }
public double getValue() { return value; }
public Date getTimestamp() { return timestamp; }
}
// 通知服务
public static class NotificationService {
private List<String> notifications;
public NotificationService() {
this.notifications = new CopyOnWriteArrayList<>();
}
public void sendAlert(Alert alert) {
String message = String.format("[%s] %s: %s (当前值: %.2f) - %s",
alert.getSeverity(), alert.getRuleName(), alert.getMessage(),
alert.getValue(), new Date());
notifications.add(message);
System.out.println("报警: " + message);
// 这里可以添加实际的通知逻辑,如发送邮件、短信等
}
public void sendResolution(Alert alert) {
String message = String.format("[RESOLVED] %s: 报警已解决 - %s",
alert.getRuleName(), new Date());
notifications.add(message);
System.out.println("报警解决: " + message);
}
public List<String> getNotifications() {
return notifications;
}
}
// 自动化响应
public static class AutomatedResponse {
private AlertSystem alertSystem;
private Map<String, ResponseAction> actions;
public AutomatedResponse(AlertSystem alertSystem) {
this.alertSystem = alertSystem;
this.actions = new HashMap<>();
// 注册响应动作
actions.put("high_database_connections", new ScaleUpDatabaseAction());
actions.put("high_memory_usage", new RestartServiceAction());
actions.put("high_error_rate", new CircuitBreakerAction());
}
public void processAlerts() {
List<Alert> alerts = alertSystem.getActiveAlerts();
for (Alert alert : alerts) {
ResponseAction action = actions.get(alert.getRuleName());
if (action != null && alert.getSeverity().equals("CRITICAL")) {
try {
action.execute();
System.out.println("执行自动化响应: " + action.getClass().getSimpleName());
} catch (Exception e) {
System.err.println("自动化响应执行失败: " + e.getMessage());
}
}
}
}
}
// 响应动作接口
public interface ResponseAction {
void execute() throws Exception;
}
// 数据库扩容动作
public static class ScaleUpDatabaseAction implements ResponseAction {
@Override
public void execute() throws Exception {
System.out.println("执行数据库扩容...");
Thread.sleep(2000); // 模拟扩容过程
System.out.println("数据库扩容完成");
}
}
// 服务重启动作
public static class RestartServiceAction implements ResponseAction {
@Override
public void execute() throws Exception {
System.out.println("执行服务重启...");
Thread.sleep(3000); // 模拟重启过程
System.out.println("服务重启完成");
}
}
// 熔断器动作
public static class CircuitBreakerAction implements ResponseAction {
@Override
public void execute() throws Exception {
System.out.println("启用熔断器...");
Thread.sleep(1000); // 模拟熔断器启用过程
System.out.println("熔断器已启用");
}
}
// 监控仪表板
public static class MonitoringDashboard {
private MetricCollector collector;
private AlertSystem alertSystem;
public MonitoringDashboard(MetricCollector collector, AlertSystem alertSystem) {
this.collector = collector;
this.alertSystem = alertSystem;
}
public void display() {
System.out.println("\n=== 监控仪表板 ===");
System.out.println("时间: " + new Date());
// 显示关键指标
System.out.println("\n关键指标:");
for (Metric metric : collector.getAllMetrics()) {
System.out.printf("%-30s: %.2f %s%n",
metric.getName(), metric.getValue(), metric.getType());
}
// 显示活跃报警
List<Alert> activeAlerts = alertSystem.getActiveAlerts();
if (!activeAlerts.isEmpty()) {
System.out.println("\n活跃报警:");
for (Alert alert : activeAlerts) {
System.out.printf("[%s] %s: %s (当前值: %.2f)%n",
alert.getSeverity(), alert.getRuleName(), alert.getMessage(), alert.getValue());
}
} else {
System.out.println("\n当前无活跃报警");
}
}
}
// 主方法 - 演示监控与报警系统
public static void main(String[] args) throws InterruptedException {
// 创建监控数据采集器
MetricCollector collector = new MetricCollector();
// 创建应用和中间件指标监控
ApplicationMetrics appMetrics = new ApplicationMetrics(collector);
Middleware middlewareMetrics = new MiddlewareMetrics(collector);
// 创建通知服务
NotificationService notificationService = new NotificationService();
// 创建报警系统
AlertSystem alertSystem = new AlertSystem(notificationService);
// 添加报警规则
alertSystem.addRule(new AlertRule(
"high_database_connections",
"database_connections_active",
">=",
90,
"CRITICAL",
"数据库连接数过高"
));
alertSystem.addRule(new AlertRule(
"high_memory_usage",
"jvm_memory_used_bytes",
">=",
0.9,
"WARNING",
"JVM内存使用率过高"
));
alertSystem.addRule(new AlertRule(
"high_error_rate",
"app_errors_total",
">=",
100,
"CRITICAL",
"应用错误数过高"
));
// 创建自动化响应
AutomatedResponse automatedResponse = new AutomatedResponse(alertSystem);
// 创建监控仪表板
MonitoringDashboard dashboard = new MonitoringDashboard(collector, alertSystem);
// 模拟系统运行
for (int i = 0; i < 20; i++) {
// 模拟HTTP请求
appMetrics.recordHttpRequest("GET", "/api/users", 200, 0.05);
// 模拟数据库连接数变化
int dbConnections = 50 + (int)(Math.random() * 50);
middlewareMetrics.updateDatabaseMetrics(dbConnections, 100);
// 模拟缓存命中
if (Math.random() > 0.3) {
middlewareMetrics.recordCacheHit();
} else {
middlewareMetrics.recordCacheMiss();
}
// 模拟JVM内存使用
long memoryUsed = (long)(Runtime.getRuntime().totalMemory() * 0.6 + Math.random() * 0.3);
int threadCount = Thread.activeCount();
appMetrics.updateJvmMetrics(memoryUsed, threadCount);
// 模拟错误
if (i > 10 && Math.random() > 0.8) {
appMetrics.recordHttpRequest("POST", "/api/orders", 500, 0.1);
}
// 每5秒显示一次仪表板
if (i % 5 == 0) {
dashboard.display();
// 评估报警规则
alertSystem.evaluateMetrics(collector.getAllMetrics());
// 处理自动化响应
automatedResponse.processAlerts();
}
Thread.sleep(1000);
}
// 最终状态
dashboard.display();
// 显示通知历史
System.out.println("\n=== 通知历史 ===");
notificationService.getNotifications().forEach(System.out::println);
}
}
总结
架构评审是一个复杂而系统的过程,需要从多个维度全面考量。在实际项目中,应根据项目所处阶段与业务目标,合理权衡各维度的重要性,制定出最合适的架构方案。随着项目的发展,也可以借助公司中间件与容器的标准化,逐步将一些架构工作交由专业团队负责,让业务代码更加专注于业务逻辑的实现。
在项目初期,可以适当简化一些架构设计,但必须对关键问题有清晰的认识与规划,确保系统能够在未来的发展中持续满足业务需求,实现稳定、高效、可扩展的目标。