1 /*
2 * Copyright (C) 2022 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 #define MLOG_TAG "Thumbnail"
16
17 #include "thumbnail_service.h"
18
19 #include "display_manager.h"
20 #include "ipc_skeleton.h"
21 #include "ithumbnail_helper.h"
22 #include "media_column.h"
23 #include "media_file_utils.h"
24 #include "medialibrary_async_worker.h"
25 #include "medialibrary_db_const.h"
26 #include "medialibrary_errno.h"
27 #include "medialibrary_kvstore_manager.h"
28 #include "medialibrary_photo_operations.h"
29 #include "medialibrary_type_const.h"
30 #include "medialibrary_unistore_manager.h"
31 #include "media_log.h"
32 #include "result_set_utils.h"
33 #include "thumbnail_aging_helper.h"
34 #include "thumbnail_const.h"
35 #include "thumbnail_generate_helper.h"
36 #include "thumbnail_generate_worker_manager.h"
37 #include "thumbnail_uri_utils.h"
38 #include "post_event_utils.h"
39 #ifdef HAS_THERMAL_MANAGER_PART
40 #include "thermal_mgr_client.h"
41 #endif
42
43 using namespace std;
44 using namespace OHOS::DistributedKv;
45 using namespace OHOS::NativeRdb;
46 using namespace OHOS::AbilityRuntime;
47
48 namespace OHOS {
49 namespace Media {
50 std::shared_ptr<ThumbnailService> ThumbnailService::thumbnailServiceInstance_{nullptr};
51 std::mutex ThumbnailService::instanceLock_;
ThumbnailService(void)52 ThumbnailService::ThumbnailService(void)
53 {
54 rdbStorePtr_ = nullptr;
55 rdbPredicatePtr_ = nullptr;
56 #ifdef DISTRIBUTED
57 kvStorePtr_ = nullptr;
58 #endif
59 }
60
GetInstance()61 shared_ptr<ThumbnailService> ThumbnailService::GetInstance()
62 {
63 if (thumbnailServiceInstance_ == nullptr) {
64 std::lock_guard<std::mutex> lockGuard(instanceLock_);
65 if (thumbnailServiceInstance_ != nullptr) {
66 return thumbnailServiceInstance_;
67 }
68 thumbnailServiceInstance_ = shared_ptr<ThumbnailService>(new ThumbnailService());
69 }
70
71 return thumbnailServiceInstance_;
72 }
73
GetDefaultWindowSize(Size & size)74 static bool GetDefaultWindowSize(Size &size)
75 {
76 auto &displayMgr = OHOS::Rosen::DisplayManager::GetInstance();
77 auto display = displayMgr.GetDefaultDisplay();
78 if (display == nullptr) {
79 MEDIA_ERR_LOG("Get display window size failed");
80 return false;
81 }
82 size.width = display->GetWidth();
83 size.height = display->GetHeight();
84 if (size.width <= 0) {
85 MEDIA_WARN_LOG("Get Default display width is invalid %{public}d", size.width);
86 size.width = DEFAULT_LCD_SIZE;
87 }
88 if (size.height <= 0) {
89 MEDIA_WARN_LOG("Get Default display height is invalid %{public}d", size.height);
90 size.height = DEFAULT_LCD_SIZE;
91 }
92 MEDIA_INFO_LOG("display window size::w %{public}d, h %{public}d", size.width, size.height);
93
94 return true;
95 }
96
CheckSizeValid()97 bool ThumbnailService::CheckSizeValid()
98 {
99 if (!isScreenSizeInit_) {
100 if (!GetDefaultWindowSize(screenSize_)) {
101 return false;
102 }
103 isScreenSizeInit_ = true;
104 }
105 return true;
106 }
107
Init(const shared_ptr<MediaLibraryRdbStore> rdbStore,const shared_ptr<SingleKvStore> & kvStore,const shared_ptr<Context> & context)108 void ThumbnailService::Init(const shared_ptr<MediaLibraryRdbStore> rdbStore,
109 #ifdef DISTRIBUTED
110 const shared_ptr<SingleKvStore> &kvStore,
111 #endif
112 const shared_ptr<Context> &context)
113 {
114 rdbStorePtr_ = rdbStore;
115 #ifdef DISTRIBUTED
116 kvStorePtr_ = kvStore;
117 #endif
118 context_ = context;
119
120 if (!GetDefaultWindowSize(screenSize_)) {
121 MEDIA_ERR_LOG("GetDefaultWindowSize failed");
122 } else {
123 isScreenSizeInit_ = true;
124 }
125 }
126
ReleaseService()127 void ThumbnailService::ReleaseService()
128 {
129 StopAllWorker();
130 rdbStorePtr_ = nullptr;
131 #ifdef DISTRIBUTED
132 kvStorePtr_ = nullptr;
133 #endif
134 context_ = nullptr;
135 thumbnailServiceInstance_ = nullptr;
136 }
137
138 #ifdef MEDIALIBRARY_COMPATIBILITY
GetPathFromDb(const shared_ptr<MediaLibraryRdbStore> rdbStorePtr,const string & fileId,const string & table,string & path)139 static int32_t GetPathFromDb(const shared_ptr<MediaLibraryRdbStore> rdbStorePtr, const string &fileId,
140 const string &table, string &path)
141 {
142 if (rdbStorePtr == nullptr) {
143 VariantMap map = {{KEY_ERR_FILE, __FILE__}, {KEY_ERR_LINE, __LINE__}, {KEY_ERR_CODE, E_HAS_DB_ERROR},
144 {KEY_OPT_TYPE, OptType::THUMB}};
145 PostEventUtils::GetInstance().PostErrorProcess(ErrType::DB_OPT_ERR, map);
146 return E_HAS_DB_ERROR;
147 }
148 if (!all_of(fileId.begin(), fileId.end(), ::isdigit)) {
149 return E_INVALID_FILEID;
150 }
151 string querySql = "SELECT " + MediaColumn::MEDIA_FILE_PATH + " FROM " + table +
152 " WHERE " + MediaColumn::MEDIA_ID + "=?";
153 vector<string> selectionArgs = { fileId };
154 auto resultSet = rdbStorePtr->QuerySql(querySql, selectionArgs);
155 if (resultSet == nullptr || resultSet->GoToFirstRow() != NativeRdb::E_OK) {
156 VariantMap map = {{KEY_ERR_FILE, __FILE__}, {KEY_ERR_LINE, __LINE__}, {KEY_ERR_CODE, E_HAS_DB_ERROR},
157 {KEY_OPT_TYPE, OptType::THUMB}};
158 PostEventUtils::GetInstance().PostErrorProcess(ErrType::DB_OPT_ERR, map);
159 return E_HAS_DB_ERROR;
160 }
161 path = GetStringVal(MediaColumn::MEDIA_FILE_PATH, resultSet);
162 if (path.empty()) {
163 return E_INVALID_PATH;
164 }
165 return E_OK;
166 }
167 #endif
168
GetThumbFd(const string & path,const string & table,const string & id,const string & uri,const Size & size,bool isAstc)169 int ThumbnailService::GetThumbFd(const string &path, const string &table, const string &id, const string &uri,
170 const Size &size, bool isAstc)
171 {
172 ThumbRdbOpt opts = {
173 .store = rdbStorePtr_,
174 .path = path,
175 .table = table,
176 .row = id,
177 .uri = uri,
178 };
179 ThumbnailType thumbType = GetThumbType(size.width, size.height, isAstc);
180 if (thumbType != ThumbnailType::THUMB && thumbType != ThumbnailType::THUMB_ASTC) {
181 opts.screenSize = screenSize_;
182 }
183 int fd = ThumbnailGenerateHelper::GetThumbnailPixelMap(opts, thumbType);
184 if (fd < 0) {
185 MEDIA_ERR_LOG("GetThumbnailPixelMap failed : %{public}d", fd);
186 }
187 return fd;
188 }
189
GetThumbnailFd(const string & uri,bool isAstc)190 int ThumbnailService::GetThumbnailFd(const string &uri, bool isAstc)
191 {
192 if (!CheckSizeValid()) {
193 MEDIA_ERR_LOG("GetThumbnailFd failed for invaild size, uri: %{public}s", uri.c_str());
194 return E_THUMBNAIL_INVALID_SIZE;
195 }
196 string id;
197 string path;
198 string table;
199 Size size;
200 if (!ThumbnailUriUtils::ParseThumbnailInfo(uri, id, size, path, table)) {
201 VariantMap map = {{KEY_ERR_FILE, __FILE__}, {KEY_ERR_LINE, __LINE__}, {KEY_ERR_CODE, E_FAIL},
202 {KEY_OPT_FILE, uri}, {KEY_OPT_TYPE, OptType::THUMB}};
203 PostEventUtils::GetInstance().PostErrorProcess(ErrType::FILE_OPT_ERR, map);
204 return E_FAIL;
205 }
206 #ifdef MEDIALIBRARY_COMPATIBILITY
207 if (path.empty()) {
208 int32_t errCode = GetPathFromDb(rdbStorePtr_, id, table, path);
209 if (errCode != E_OK) {
210 VariantMap map = {{KEY_ERR_FILE, __FILE__}, {KEY_ERR_LINE, __LINE__}, {KEY_ERR_CODE, errCode},
211 {KEY_OPT_TYPE, OptType::THUMB}};
212 PostEventUtils::GetInstance().PostErrorProcess(ErrType::DB_OPT_ERR, map);
213 MEDIA_ERR_LOG("GetPathFromDb failed, errCode = %{public}d", errCode);
214 return errCode;
215 }
216 }
217 #endif
218 return GetThumbFd(path, table, id, uri, size, isAstc);
219 }
220
ParseThumbnailParam(const std::string & uri,string & fileId,string & networkId,string & tableName)221 int32_t ThumbnailService::ParseThumbnailParam(const std::string &uri, string &fileId, string &networkId,
222 string &tableName)
223 {
224 if (!CheckSizeValid()) {
225 VariantMap map = {{KEY_ERR_FILE, __FILE__}, {KEY_ERR_LINE, __LINE__}, {KEY_ERR_CODE, E_THUMBNAIL_INVALID_SIZE},
226 {KEY_OPT_FILE, uri}, {KEY_OPT_TYPE, OptType::THUMB}};
227 PostEventUtils::GetInstance().PostErrorProcess(ErrType::FILE_OPT_ERR, map);
228 return E_THUMBNAIL_INVALID_SIZE;
229 }
230 if (!ThumbnailUriUtils::ParseFileUri(uri, fileId, networkId, tableName)) {
231 VariantMap map = {{KEY_ERR_FILE, __FILE__}, {KEY_ERR_LINE, __LINE__}, {KEY_ERR_CODE, E_ERR},
232 {KEY_OPT_FILE, uri}, {KEY_OPT_TYPE, OptType::THUMB}};
233 PostEventUtils::GetInstance().PostErrorProcess(ErrType::FILE_OPT_ERR, map);
234 MEDIA_ERR_LOG("ParseThumbnailInfo faild");
235 return E_ERR;
236 }
237 return E_OK;
238 }
239
CreateThumbnailFileScaned(const std::string & uri,const string & path,bool isSync)240 int32_t ThumbnailService::CreateThumbnailFileScaned(const std::string &uri, const string &path, bool isSync)
241 {
242 string fileId;
243 string networkId;
244 string tableName;
245
246 int err = ParseThumbnailParam(uri, fileId, networkId, tableName);
247 if (err != E_OK) {
248 VariantMap map = {{KEY_ERR_FILE, __FILE__}, {KEY_ERR_LINE, __LINE__}, {KEY_ERR_CODE, E_ERR},
249 {KEY_OPT_FILE, uri}, {KEY_OPT_TYPE, OptType::THUMB}};
250 PostEventUtils::GetInstance().PostErrorProcess(ErrType::FILE_OPT_ERR, map);
251 return err;
252 }
253
254 std::string dateTaken = ThumbnailUriUtils::GetDateTakenFromUri(uri);
255 std::string fileUri = ThumbnailUriUtils::GetFileUriFromUri(uri);
256 ThumbRdbOpt opts = {
257 .store = rdbStorePtr_,
258 .path = path,
259 .table = tableName,
260 .row = fileId,
261 .dateTaken = dateTaken,
262 .fileUri = fileUri,
263 .screenSize = screenSize_
264 };
265
266 err = ThumbnailGenerateHelper::CreateThumbnailFileScaned(opts, isSync);
267 if (err != E_OK) {
268 MEDIA_ERR_LOG("CreateThumbnailFileScaned failed : %{public}d", err);
269 return err;
270 }
271 return E_OK;
272 }
273
InterruptBgworker()274 void ThumbnailService::InterruptBgworker()
275 {
276 shared_ptr<MediaLibraryAsyncWorker> asyncWorker = MediaLibraryAsyncWorker::GetInstance();
277 if (asyncWorker != nullptr) {
278 asyncWorker->Interrupt();
279 }
280
281 std::shared_ptr<ThumbnailGenerateWorker> thumbnailWorker =
282 ThumbnailGenerateWorkerManager::GetInstance().GetThumbnailWorker(ThumbnailTaskType::BACKGROUND);
283 if (thumbnailWorker == nullptr) {
284 MEDIA_ERR_LOG("thumbnailWorker is null");
285 return;
286 }
287 thumbnailWorker->ReleaseTaskQueue(ThumbnailTaskPriority::LOW);
288 }
289
StopAllWorker()290 void ThumbnailService::StopAllWorker()
291 {
292 shared_ptr<MediaLibraryAsyncWorker> asyncWorker = MediaLibraryAsyncWorker::GetInstance();
293 if (asyncWorker != nullptr) {
294 asyncWorker->Stop();
295 }
296
297 ThumbnailGenerateWorkerManager::GetInstance().ClearAllTask();
298 }
299
GenerateThumbnailBackground()300 int32_t ThumbnailService::GenerateThumbnailBackground()
301 {
302 if (!CheckSizeValid()) {
303 return E_THUMBNAIL_INVALID_SIZE;
304 }
305 int32_t err = 0;
306 vector<string> tableList;
307 tableList.emplace_back(PhotoColumn::PHOTOS_TABLE);
308 tableList.emplace_back(AudioColumn::AUDIOS_TABLE);
309 tableList.emplace_back(MEDIALIBRARY_TABLE);
310
311 for (const auto &tableName : tableList) {
312 ThumbRdbOpt opts = {
313 .store = rdbStorePtr_,
314 #ifdef DISTRIBUTED
315 .kvStore = kvStorePtr_,
316 #endif
317 .table = tableName
318 };
319
320 if ((tableName == PhotoColumn::PHOTOS_TABLE) && ThumbnailUtils::IsSupportGenAstc()) {
321 // CreateAstcBackground contains thumbnails created.
322 err = ThumbnailGenerateHelper::CreateAstcBackground(opts);
323 if (err != E_OK) {
324 MEDIA_ERR_LOG("CreateAstcBackground failed : %{public}d", err);
325 }
326 } else {
327 err = ThumbnailGenerateHelper::CreateThumbnailBackground(opts);
328 if (err != E_OK) {
329 MEDIA_ERR_LOG("CreateThumbnailBackground failed : %{public}d", err);
330 }
331 }
332
333 if (tableName != AudioColumn::AUDIOS_TABLE) {
334 err = ThumbnailGenerateHelper::CreateLcdBackground(opts);
335 if (err != E_OK) {
336 MEDIA_ERR_LOG("CreateLcdBackground failed : %{public}d", err);
337 }
338 }
339 }
340
341 return err;
342 }
343
UpgradeThumbnailBackground(bool isWifiConnected)344 int32_t ThumbnailService::UpgradeThumbnailBackground(bool isWifiConnected)
345 {
346 ThumbRdbOpt opts = {
347 .store = rdbStorePtr_,
348 .table = PhotoColumn::PHOTOS_TABLE
349 };
350 int32_t err = ThumbnailGenerateHelper::UpgradeThumbnailBackground(opts, isWifiConnected);
351 if (err != E_OK) {
352 MEDIA_ERR_LOG("UpgradeThumbnailBackground failed : %{public}d", err);
353 }
354 return err;
355 }
356
RestoreThumbnailDualFrame()357 int32_t ThumbnailService::RestoreThumbnailDualFrame()
358 {
359 ThumbRdbOpt opts = {
360 .store = rdbStorePtr_,
361 .table = PhotoColumn::PHOTOS_TABLE
362 };
363 return ThumbnailGenerateHelper::RestoreAstcDualFrame(opts);
364 }
365
LcdAging()366 int32_t ThumbnailService::LcdAging()
367 {
368 int32_t err = 0;
369 vector<string> tableList;
370 tableList.emplace_back(PhotoColumn::PHOTOS_TABLE);
371 tableList.emplace_back(AudioColumn::AUDIOS_TABLE);
372 tableList.emplace_back(MEDIALIBRARY_TABLE);
373
374 for (const auto &tableName : tableList) {
375 ThumbRdbOpt opts = {
376 .store = rdbStorePtr_,
377 #ifdef DISTRIBUTED
378 .kvStore = kvStorePtr_,
379 #endif
380 .table = tableName,
381 };
382 err = ThumbnailAgingHelper::AgingLcdBatch(opts);
383 if (err != E_OK) {
384 MEDIA_ERR_LOG("AgingLcdBatch failed : %{public}d", err);
385 }
386 }
387
388 return E_OK;
389 }
390
391 #ifdef DISTRIBUTED
LcdDistributeAging(const string & udid)392 int32_t ThumbnailService::LcdDistributeAging(const string &udid)
393 {
394 ThumbRdbOpt opts = {
395 .store = rdbStorePtr_,
396 .kvStore = kvStorePtr_,
397 .udid = udid
398 };
399 int32_t err = ThumbnailAgingHelper::AgingDistributeLcdBatch(opts);
400 if (err != E_OK) {
401 MEDIA_ERR_LOG("AgingDistributeLcdBatch failed : %{public}d", err);
402 return err;
403 }
404 return E_OK;
405 }
406
InvalidateDistributeThumbnail(const string & udid)407 int32_t ThumbnailService::InvalidateDistributeThumbnail(const string &udid)
408 {
409 ThumbRdbOpt opts = {
410 .store = rdbStorePtr_,
411 .kvStore = kvStorePtr_,
412 .udid = udid
413 };
414 int32_t err = ThumbnailAgingHelper::InvalidateDistributeBatch(opts);
415 if (err != E_OK) {
416 MEDIA_ERR_LOG("InvalidateDistributeBatch failed : %{public}d", err);
417 }
418 return err;
419 }
420 #endif
421
HasInvalidateThumbnail(const std::string & id,const std::string & tableName,const std::string & path,const std::string & dateTaken)422 bool ThumbnailService::HasInvalidateThumbnail(const std::string &id,
423 const std::string &tableName, const std::string &path, const std::string &dateTaken)
424 {
425 ThumbRdbOpt opts = {
426 .store = rdbStorePtr_,
427 .path = path,
428 .table = tableName,
429 .row = id,
430 .dateTaken = dateTaken,
431 };
432 ThumbnailData thumbnailData;
433 if (!ThumbnailUtils::DeleteOriginImage(opts)) {
434 MEDIA_ERR_LOG("failed to delete origin image");
435 return false;
436 }
437 if (opts.path.find(ROOT_MEDIA_DIR + PHOTO_BUCKET) != string::npos) {
438 return MediaLibraryPhotoOperations::HasDroppedThumbnailSize(id);
439 }
440 return true;
441 }
442
GetAgingDataSize(const int64_t & time,int & count)443 int32_t ThumbnailService::GetAgingDataSize(const int64_t &time, int &count)
444 {
445 int32_t err = 0;
446 vector<string> tableList;
447 tableList.emplace_back(PhotoColumn::PHOTOS_TABLE);
448 tableList.emplace_back(AudioColumn::AUDIOS_TABLE);
449 tableList.emplace_back(MEDIALIBRARY_TABLE);
450
451 for (const auto &tableName : tableList) {
452 ThumbRdbOpt opts = {
453 .store = rdbStorePtr_,
454 #ifdef DISTRIBUTED
455 .kvStore = kvStorePtr_,
456 #endif
457 .table = tableName,
458 };
459 int tempCount = 0;
460 err = ThumbnailAgingHelper::GetAgingDataCount(time, true, opts, tempCount);
461 if (err != E_OK) {
462 MEDIA_ERR_LOG("AgingLcdBatch failed : %{public}d", err);
463 return err;
464 }
465 count += tempCount;
466 }
467
468 return err;
469 }
470
QueryNewThumbnailCount(const int64_t & time,int32_t & count)471 int32_t ThumbnailService::QueryNewThumbnailCount(const int64_t &time, int32_t &count)
472 {
473 int32_t err = 0;
474 vector<string> tableList;
475 tableList.emplace_back(PhotoColumn::PHOTOS_TABLE);
476 tableList.emplace_back(AudioColumn::AUDIOS_TABLE);
477 tableList.emplace_back(MEDIALIBRARY_TABLE);
478
479 for (const auto &tableName : tableList) {
480 ThumbRdbOpt opts = {
481 .store = rdbStorePtr_,
482 #ifdef DISTRIBUTED
483 .kvStore = kvStorePtr_,
484 #endif
485 .table = tableName
486 };
487 int32_t tempCount = 0;
488 err = ThumbnailGenerateHelper::GetNewThumbnailCount(opts, time, tempCount);
489 if (err != E_OK) {
490 MEDIA_ERR_LOG("GetNewThumbnailCount failed : %{public}d", err);
491 return err;
492 }
493 count += tempCount;
494 }
495 return E_OK;
496 }
497
CreateAstcCloudDownload(const string & id,bool isCloudInsertTaskPriorityHigh)498 int32_t ThumbnailService::CreateAstcCloudDownload(const string &id, bool isCloudInsertTaskPriorityHigh)
499 {
500 if (!isCloudInsertTaskPriorityHigh && !currentStatusForTask_) {
501 return E_CLOUD_NOT_SUITABLE_FOR_TASK;
502 }
503 ThumbRdbOpt opts = {
504 .store = rdbStorePtr_,
505 .table = PhotoColumn::PHOTOS_TABLE,
506 .fileId = id,
507 };
508
509 int err = ThumbnailGenerateHelper::CreateAstcCloudDownload(opts, isCloudInsertTaskPriorityHigh);
510 if (err != E_OK) {
511 MEDIA_ERR_LOG("CreateAstcCloudDownload failed : %{public}d", err);
512 return err;
513 }
514 return err;
515 }
516
DeleteAstcWithFileIdAndDateTaken(const std::string & fileId,const std::string & dateTaken)517 void ThumbnailService::DeleteAstcWithFileIdAndDateTaken(const std::string &fileId, const std::string &dateTaken)
518 {
519 ThumbnailData data;
520 ThumbRdbOpt opts = {
521 .store = rdbStorePtr_,
522 .table = PhotoColumn::PHOTOS_TABLE,
523 .row = fileId,
524 .dateTaken = dateTaken
525 };
526
527 IThumbnailHelper::AddThumbnailGenerateTask(IThumbnailHelper::DeleteMonthAndYearAstc,
528 opts, data, ThumbnailTaskType::BACKGROUND, ThumbnailTaskPriority::HIGH);
529 }
530
CreateAstcBatchOnDemand(NativeRdb::RdbPredicates & rdbPredicate,int32_t requestId)531 int32_t ThumbnailService::CreateAstcBatchOnDemand(NativeRdb::RdbPredicates &rdbPredicate, int32_t requestId)
532 {
533 if (requestId <= 0) {
534 MEDIA_ERR_LOG("create astc batch failed, invalid request id:%{public}d", requestId);
535 return E_INVALID_VALUES;
536 }
537
538 CancelAstcBatchTask(requestId - 1);
539 if (GetCurrentTemperatureLevel() >= READY_TEMPERATURE_LEVEL) {
540 isTemperatureHighForReady_ = true;
541 currentRequestId_ = requestId;
542 rdbPredicatePtr_ = make_shared<NativeRdb::RdbPredicates>(rdbPredicate);
543 MEDIA_INFO_LOG("temperature is too high, the operation is suspended");
544 return E_OK;
545 }
546 ThumbRdbOpt opts = {
547 .store = rdbStorePtr_,
548 .table = PhotoColumn::PHOTOS_TABLE
549 };
550 return ThumbnailGenerateHelper::CreateAstcBatchOnDemand(opts, rdbPredicate, requestId);
551 }
552
CancelAstcBatchTask(int32_t requestId)553 void ThumbnailService::CancelAstcBatchTask(int32_t requestId)
554 {
555 if (requestId <= 0) {
556 MEDIA_ERR_LOG("cancel astc batch failed, invalid request id:%{public}d", requestId);
557 return;
558 }
559 if (isTemperatureHighForReady_) {
560 currentRequestId_ = 0;
561 }
562 MEDIA_INFO_LOG("CancelAstcBatchTask requestId: %{public}d", requestId);
563 std::shared_ptr<ThumbnailGenerateWorker> thumbnailWorker =
564 ThumbnailGenerateWorkerManager::GetInstance().GetThumbnailWorker(ThumbnailTaskType::FOREGROUND);
565 if (thumbnailWorker == nullptr) {
566 MEDIA_ERR_LOG("thumbnailWorker is null");
567 return;
568 }
569 thumbnailWorker->IgnoreTaskByRequestId(requestId);
570 }
571
UpdateAstcWithNewDateTaken(const std::string & fileId,const std::string & newDateTaken,const std::string & formerDateTaken)572 void ThumbnailService::UpdateAstcWithNewDateTaken(const std::string &fileId, const std::string &newDateTaken,
573 const std::string &formerDateTaken)
574 {
575 ThumbnailData data;
576 data.dateTaken = newDateTaken;
577 ThumbRdbOpt opts = {
578 .store = rdbStorePtr_,
579 .table = PhotoColumn::PHOTOS_TABLE,
580 .row = fileId,
581 .dateTaken = formerDateTaken
582 };
583
584 IThumbnailHelper::AddThumbnailGenerateTask(IThumbnailHelper::UpdateAstcDateTaken,
585 opts, data, ThumbnailTaskType::BACKGROUND, ThumbnailTaskPriority::HIGH);
586 }
587
CheckCloudThumbnailDownloadFinish()588 int32_t ThumbnailService::CheckCloudThumbnailDownloadFinish()
589 {
590 if (!ThumbnailUtils::CheckCloudThumbnailDownloadFinish(rdbStorePtr_)) {
591 return E_CLOUD_THUMBNAIL_NOT_DOWNLOAD_FINISH;
592 }
593 return E_OK;
594 }
595
UpdateThumbnailReadyToFailed(ThumbRdbOpt & opts,std::string id)596 static void UpdateThumbnailReadyToFailed(ThumbRdbOpt &opts, std::string id)
597 {
598 if (opts.store == nullptr || id.empty()) {
599 return;
600 }
601
602 ValuesBucket values;
603 int changedRows;
604 values.PutLong(PhotoColumn::PHOTO_THUMBNAIL_READY, THUMBNAIL_READY_FAILED);
605 int32_t err = opts.store->Update(changedRows, opts.table, values, MEDIA_DATA_DB_ID + " = ?", vector<string> { id });
606 if (err != NativeRdb::E_OK) {
607 MEDIA_ERR_LOG("RdbStore Update failed! %{public}d", err);
608 }
609 }
610
IsAstcChangeOldKeyToNewKeySuccess(std::shared_ptr<MediaLibraryKvStore> & monthKvStore,std::shared_ptr<MediaLibraryKvStore> & yearKvStore,const std::string & oldKey,const std::string & newKey)611 static bool IsAstcChangeOldKeyToNewKeySuccess(std::shared_ptr<MediaLibraryKvStore> &monthKvStore,
612 std::shared_ptr<MediaLibraryKvStore> &yearKvStore, const std::string &oldKey, const std::string &newKey)
613 {
614 if (oldKey.compare(newKey) == 0) {
615 MEDIA_INFO_LOG("OldKey: %{public}s is same to newKey", oldKey.c_str());
616 return true;
617 }
618 std::vector<uint8_t> monthValue;
619 std::vector<uint8_t> yearValue;
620 if (yearKvStore->Query(newKey, yearValue) == E_OK) {
621 MEDIA_INFO_LOG("NewKey Astc exists, fileID %{public}s", newKey.c_str());
622 monthKvStore->Delete(oldKey);
623 yearKvStore->Delete(oldKey);
624 return true;
625 }
626 bool isChangeKeySuccess = true;
627 if (monthKvStore->Query(oldKey, monthValue) != E_OK || monthKvStore->Insert(newKey, monthValue) != E_OK ||
628 monthKvStore->Delete(oldKey) != E_OK) {
629 MEDIA_ERR_LOG("MonthValue update failed, fileID %{public}s", newKey.c_str());
630 isChangeKeySuccess = false;
631 }
632 if (yearKvStore->Query(oldKey, yearValue) != E_OK || yearKvStore->Insert(newKey, yearValue) != E_OK ||
633 yearKvStore->Delete(oldKey) != E_OK) {
634 MEDIA_ERR_LOG("YearValue update failed, fileID %{public}s", newKey.c_str());
635 isChangeKeySuccess = false;
636 }
637 return isChangeKeySuccess;
638 }
639
AstcChangeKeyFromDateAddedToDateTaken()640 void ThumbnailService::AstcChangeKeyFromDateAddedToDateTaken()
641 {
642 if (rdbStorePtr_ == nullptr) {
643 MEDIA_ERR_LOG("RdbStorePtr is null");
644 return;
645 }
646 vector<ThumbnailData> infos;
647 if (!ThumbnailUtils::QueryOldKeyAstcInfos(rdbStorePtr_, PhotoColumn::PHOTOS_TABLE, infos)) {
648 return;
649 }
650 MEDIA_INFO_LOG("Old key astc data size: %{public}d", static_cast<int>(infos.size()));
651 if (infos.empty()) {
652 return;
653 }
654 ThumbRdbOpt opts = {
655 .store = rdbStorePtr_,
656 .table = PhotoColumn::PHOTOS_TABLE,
657 };
658
659 auto monthKvStore = MediaLibraryKvStoreManager::GetInstance()
660 .GetKvStore(KvStoreRoleType::OWNER, KvStoreValueType::MONTH_ASTC);
661 if (monthKvStore == nullptr) {
662 MEDIA_ERR_LOG("Init month kvStore failed");
663 return;
664 }
665 auto yearKvStore = MediaLibraryKvStoreManager::GetInstance()
666 .GetKvStore(KvStoreRoleType::OWNER, KvStoreValueType::YEAR_ASTC);
667 if (yearKvStore == nullptr) {
668 MEDIA_ERR_LOG("Init year kvStore failed");
669 return;
670 }
671 for (size_t i = 0; i < infos.size(); i++) {
672 std::string oldKey;
673 std::string newKey;
674 if (!MediaFileUtils::GenerateKvStoreKey(infos[i].id, infos[i].dateAdded, oldKey) ||
675 !MediaFileUtils::GenerateKvStoreKey(infos[i].id, infos[i].dateTaken, newKey)) {
676 continue;
677 }
678 if (!IsAstcChangeOldKeyToNewKeySuccess(monthKvStore, yearKvStore, oldKey, newKey)) {
679 monthKvStore->Delete(oldKey);
680 yearKvStore->Delete(oldKey);
681 UpdateThumbnailReadyToFailed(opts, infos[i].id);
682 }
683 }
684 MEDIA_INFO_LOG("PerformKvStoreChangeKeyTask End");
685 }
686
UpdateCurrentStatusForTask(const bool & currentStatusForTask)687 void ThumbnailService::UpdateCurrentStatusForTask(const bool ¤tStatusForTask)
688 {
689 currentStatusForTask_ = currentStatusForTask;
690 }
691
GetCurrentStatusForTask()692 bool ThumbnailService::GetCurrentStatusForTask()
693 {
694 return currentStatusForTask_;
695 }
696
NotifyTempStatusForReady(const int32_t & currentTemperatureLevel)697 void ThumbnailService::NotifyTempStatusForReady(const int32_t ¤tTemperatureLevel)
698 {
699 currentTemperatureLevel_ = currentTemperatureLevel;
700 if (isTemperatureHighForReady_ && currentTemperatureLevel_ < READY_TEMPERATURE_LEVEL) {
701 MEDIA_INFO_LOG("temperature is normal, the opreation is resumed");
702 isTemperatureHighForReady_ = false;
703 if (rdbPredicatePtr_ != nullptr && currentRequestId_ > 0) {
704 CreateAstcBatchOnDemand(*rdbPredicatePtr_, currentRequestId_);
705 }
706 }
707 }
708
GetCurrentTemperatureLevel()709 int32_t ThumbnailService::GetCurrentTemperatureLevel()
710 {
711 return currentTemperatureLevel_;
712 }
713
CheckLcdSizeAndUpdateStatus()714 void ThumbnailService::CheckLcdSizeAndUpdateStatus()
715 {
716 ThumbRdbOpt opts = {
717 .store = rdbStorePtr_,
718 .table = PhotoColumn::PHOTOS_TABLE
719 };
720 int32_t err = ThumbnailGenerateHelper::CheckLcdSizeAndUpdateStatus(opts);
721 if (err != E_OK) {
722 MEDIA_ERR_LOG("CheckLcdSizeAndUpdateStatus failed: %{public}d", err);
723 }
724 }
725
726 } // namespace Media
727 } // namespace OHOS
728