1 /*
2 * Copyright (c) 2021 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "sys_event_db_backup.h"
17
18 #include <cinttypes>
19
20 #include "file_util.h"
21 #include "logger.h"
22 #include "sys_event_dao.h"
23 #include "time_util.h"
24
25 namespace OHOS {
26 namespace HiviewDFX {
27 DEFINE_LOG_TAG("HiView-SysEventDbBak");
28 using EventStore::SysEventDao;
29 using EventStore::SysEventQuery;
30 using EventStore::EventCol;
31 using EventStore::Op;
32 using EventStore::ResultSet;
33
RemoveSysEventFile()34 static void RemoveSysEventFile()
35 {
36 if (FileUtil::FileExists(SysEventDao::GetDataFile())) {
37 if (!FileUtil::RemoveFile(SysEventDao::GetDataFile())) {
38 HIVIEW_LOGW("remove sys event wal db failed");
39 }
40 }
41
42 std::string walDbFile = SysEventDao::GetDataFile() + "-wal";
43 if (FileUtil::FileExists(walDbFile)) {
44 if (!FileUtil::RemoveFile(walDbFile)) {
45 HIVIEW_LOGW("remove sys event wal db failed");
46 }
47 }
48 }
49
SysEventDbBackup(int64_t & backupTime)50 SysEventDbBackup::SysEventDbBackup(int64_t &backupTime) : backupTime_(backupTime)
51 {
52 dbBakFile_ = SysEventDao::GetDataDir() + "back_hisysevent.db";
53 }
54
~SysEventDbBackup()55 SysEventDbBackup::~SysEventDbBackup()
56 {
57 }
58
CheckDbStoreBroken()59 void SysEventDbBackup::CheckDbStoreBroken()
60 {
61 if (!IsBroken()) {
62 BackupOnline();
63 return;
64 }
65
66 Recover();
67 }
68
IsBroken()69 bool SysEventDbBackup::IsBroken()
70 {
71 SysEventQuery sysEventQuery = SysEventDao::BuildQuery();
72 ResultSet result = sysEventQuery.Where(EventCol::TS, Op::GT, 0).And(EventCol::TS, Op::LT, 1000).Execute(1); // 1s
73 if (result.GetErrCode() != 0) {
74 HIVIEW_LOGE("sys event db is broken");
75 return true;
76 }
77 return false;
78 }
79
NeedBackup()80 bool SysEventDbBackup::NeedBackup()
81 {
82 int64_t now = TimeUtil::GetMilliseconds();
83 if (backupTime_ == 0) {
84 backupTime_ = now;
85 return false;
86 }
87
88 int64_t oneDayInMis = TimeUtil::SECONDS_PER_DAY * TimeUtil::SEC_TO_MILLISEC;
89 HIVIEW_LOGI("sys event backup db pass time %" PRId64 "", (now - backupTime_));
90 if ((now - backupTime_) > oneDayInMis) {
91 backupTime_ = now;
92 return true;
93 } else if (now < backupTime_) {
94 backupTime_ = now;
95 return true;
96 }
97 return false;
98 }
99
BackupOnline()100 bool SysEventDbBackup::BackupOnline()
101 {
102 if (!NeedBackup()) {
103 return true;
104 }
105
106 if (SysEventDao::BackupDB(dbBakFile_) < 0) {
107 HIVIEW_LOGE("sys event backup db failed");
108 return false;
109 }
110
111 HIVIEW_LOGW("sys event backup db success");
112 return true;
113 }
114
Recover()115 bool SysEventDbBackup::Recover()
116 {
117 HIVIEW_LOGW("sys event recover db");
118 if (!RecoverFromBackup()) {
119 return RecoverByRebuild();
120 }
121 if (IsBroken()) {
122 return RecoverByRebuild();
123 }
124 return true;
125 }
126
RecoverFromBackup()127 bool SysEventDbBackup::RecoverFromBackup()
128 {
129 if (!FileUtil::FileExists(dbBakFile_)) {
130 HIVIEW_LOGE("sys event backup db does not exists");
131 return false;
132 }
133
134 if (SysEventDao::DeleteDB() < 0) {
135 HIVIEW_LOGE("can not delete sys event db");
136 return false;
137 }
138
139 HIVIEW_LOGW("recover sys event db with backup db file");
140 RemoveSysEventFile();
141
142 if (!FileUtil::RenameFile(dbBakFile_, SysEventDao::GetDataFile())) {
143 HIVIEW_LOGW("recover sys event db from backup db failed");
144 return false;
145 }
146 return true;
147 }
148
RecoverByRebuild()149 bool SysEventDbBackup::RecoverByRebuild()
150 {
151 HIVIEW_LOGW("recover sys event db by rebuild");
152 if (SysEventDao::CloseDB() < 0) {
153 return false;
154 }
155 RemoveSysEventFile();
156 IsBroken();
157 return true;
158 }
159 } // namespace HiviewDFX
160 } // namespace OHOS