跳到主要内容

设计日志系统

问题

如何设计一个高性能的 iOS 日志系统?

答案

架构

核心实现

enum LogLevel: Int, Comparable {
case debug = 0, info, warning, error, fatal

static func < (lhs: LogLevel, rhs: LogLevel) -> Bool {
lhs.rawValue < rhs.rawValue
}
}

class Logger {
static let shared = Logger()
private let queue = DispatchQueue(label: "com.app.logger")
private var buffer: [LogEntry] = []
private let batchSize = 50

func log(_ level: LogLevel, _ message: String, file: String = #file, line: Int = #line) {
let entry = LogEntry(
level: level,
message: message,
file: (file as NSString).lastPathComponent,
line: line,
timestamp: Date()
)

queue.async {
self.buffer.append(entry)
if self.buffer.count >= self.batchSize {
self.flush()
}
}
}

private func flush() {
let entries = buffer
buffer.removeAll()
// 写入磁盘 / 上报
DiskWriter.write(entries)
}
}

关键设计点

设计点方案
高性能写入mmap 内存映射,进程崩溃不丢失
日志压缩zlib 压缩后上报
隐私保护敏感字段脱敏
分级Debug 不上报,Error 立即上报
上报触发定时 + App 启动 + 错误触发

常见面试问题

Q1: 为什么用 mmap?

答案:mmap 将文件映射到内存,写日志就是写内存,由 OS 定时刷盘。即使 App 崩溃,已写入的数据不会丢失(不像内存 buffer 崩溃时丢失)。微信的 MMKV 和 Mars 的 xlog 都使用了 mmap。

相关链接