-
Notifications
You must be signed in to change notification settings - Fork 0
/
dump.go
82 lines (70 loc) · 1.83 KB
/
dump.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
package caches
import (
"encoding/gob"
"os"
"sync"
"time"
)
// dump 持久化
type dump struct {
Data map[string]*value
Options Options
Status *Status
}
// newEmptyDump 创建一个空的dump结构对象并返回
func newEmptyDump() *dump {
return &dump{}
}
// newDump 创建一个dump对象并使用指定的Cache对象初始化
func newDump(c *Cache) *dump {
return &dump{
Data: c.data,
Options: c.options,
Status: c.status,
}
}
// nowSuffix 返回一个类似于20060102150405的文件后缀名
func nowSuffix() string {
return "." + time.Now().Format("20060102150405")
}
// to 会将dump持久化到dumpfile中
func (d *dump) to(dumpFile string) error {
newDumpFile := dumpFile + nowSuffix()
file, err := os.OpenFile(newDumpFile, os.O_CREATE|os.O_TRUNC|os.O_WRONLY, 0644)
if err != nil {
return err
}
defer file.Close()
err = gob.NewEncoder(file).Encode(d)
if err != nil {
// 注意这里先把文件关闭,不然os.Remove是没有权限删除文件
file.Close()
os.Remove(newDumpFile)
return err
}
// 将旧的持久化文件删除
os.Remove(dumpFile)
// 将新的持久化文件改名为旧的持久化名字,相当于替换,这样就可以保证持久化文件的名字不变
// 注意先关闭文件,不然无权限操作
file.Close()
return os.Rename(newDumpFile, dumpFile)
}
// from 会从dumpfile中恢复数据到一个Cache结构对象并返回
func (d *dump) from(dumpFile string) (*Cache, error) {
// 读取dumpFile文件并使用反序列化器进行反序列化
file, err := os.Open(dumpFile)
if err != nil {
return nil, err
}
defer file.Close()
if err = gob.NewDecoder(file).Decode(d); err != nil {
return nil, err
}
// 初始化一个缓存对象并返回
return &Cache{
data: d.Data,
options: d.Options,
status: d.Status,
lock: &sync.RWMutex{},
}, nil
}