perf(性能优化): 统一调度优化并行与内存
build.yaml / build (push) Successful in 47s

This commit is contained in:
xiaoqidun committed 2026-10-19 21:39:40 +08:00
1 parent 4f530eb5b8
commit eb20f66ffb
4 files changed
+212 -29

No files matched your search

+52 -3
View File
@@ -38,6 +38,9 @@ import (
// editorSnapshotArchiveLimit 限制编辑器常驻的快照压缩包字节数
const editorSnapshotArchiveLimit = 32 << 20
// editorSnapshotChunkSize 指定快照压缩数据的分块大小
const editorSnapshotChunkSize = 256 << 10
// ErrSaveTarget 表示编辑器尚未绑定保存目标
var ErrSaveTarget = errors.New("save target is not set")
@@ -76,6 +79,12 @@ type editorSnapshotArchive struct {
retained *zip.Reader
}
// editorSnapshotBuffer 分块保存压缩数据,写入完成后支持并发随机读取
type editorSnapshotBuffer struct {
chunks [][]byte
size int64
}
// editorProgress 编辑与保存阶段的进度回调,nil表示不回报进度
type editorProgress func(stage string, completed, total int) error
@@ -152,7 +161,7 @@ func (e *Editor) copySnapshotArchive(ctx context.Context, source *zip.Reader) (*
return archive, nil
}
}
var data bytes.Buffer
var data editorSnapshotBuffer
var count int64
archive := zip.NewWriter(convertWriter{ctx: ctx, writer: &data, count: &count})
for _, file := range source.File {
@@ -166,7 +175,7 @@ func (e *Editor) copySnapshotArchive(ctx context.Context, source *zip.Reader) (*
if err := archive.Close(); err != nil {
return nil, err
}
reader, err := zip.NewReader(bytes.NewReader(data.Bytes()), int64(data.Len()))
reader, err := zip.NewReader(&data, data.size)
if err != nil {
return nil, err
}
@@ -174,13 +183,53 @@ func (e *Editor) copySnapshotArchive(ctx context.Context, source *zip.Reader) (*
return nil, err
}
cached := &editorSnapshotArchive{files: slices.Clone(source.File), archive: weak.Make(reader)}
if data.Cap() <= editorSnapshotArchiveLimit {
if len(data.chunks) <= editorSnapshotArchiveLimit/editorSnapshotChunkSize {
cached.retained = reader
}
e.snapshotArchive = cached
return reader, nil
}
// Write 追加快照数据,不扩容或复制已有块
// 入参: data 压缩数据
// 返回: int 写入字节数, error 写入错误
func (b *editorSnapshotBuffer) Write(data []byte) (int, error) {
size := len(data)
for len(data) > 0 {
offset := int(b.size % editorSnapshotChunkSize)
if offset == 0 {
b.chunks = append(b.chunks, make([]byte, editorSnapshotChunkSize))
}
n := copy(b.chunks[len(b.chunks)-1][offset:], data)
b.size += int64(n)
data = data[n:]
}
return size, nil
}
// ReadAt 跨块读取快照,不复制或合并底层存储
// 入参: data 目标缓冲, offset 数据偏移
// 返回: int 读取字节数, error 偏移或结束错误
func (b *editorSnapshotBuffer) ReadAt(data []byte, offset int64) (int, error) {
if offset < 0 {
return 0, fmt.Errorf("negative snapshot offset")
}
read := 0
for len(data) > 0 {
if offset >= b.size {
return read, io.EOF
}
block := b.chunks[offset/editorSnapshotChunkSize]
start := int(offset % editorSnapshotChunkSize)
size := min(int64(len(block)-start), b.size-offset, int64(len(data)))
n := copy(data, block[start:start+int(size)])
read += n
offset += int64(n)
data = data[n:]
}
return read, nil
}
// NewFileOutput 创建本地保存目标并记录当前文件状态,不创建或修改文件
// 同一目标应复用返回值,以便后续保存检测外部修改
// 替换前比较文件标识、大小和修改时间,不提供跨进程排他锁