1 /*
2 * Copyright (C) 2024 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 #define MLOG_TAG "MultiStagesPhotoCaptureManager"
17
18 #include "multistages_photo_capture_manager.h"
19
20 #include "database_adapter.h"
21 #include "image_packer.h"
22 #include "exif_utils.h"
23 #include "medialibrary_asset_operations.h"
24 #include "medialibrary_bundle_manager.h"
25 #include "medialibrary_command.h"
26 #include "medialibrary_errno.h"
27 #include "medialibrary_rdbstore.h"
28 #include "medialibrary_type_const.h"
29 #include "medialibrary_tracer.h"
30 #include "media_file_uri.h"
31 #include "media_file_utils.h"
32 #include "media_log.h"
33 #include "medialibrary_formmap_operations.h"
34 #include "picture_manager_thread.h"
35 #include "multistages_capture_dfx_first_visit.h"
36 #include "multistages_capture_dfx_request_policy.h"
37 #include "multistages_capture_dfx_total_time.h"
38 #include "multistages_capture_dfx_trigger_ratio.h"
39 #include "multistages_capture_request_task_manager.h"
40 #include "request_policy.h"
41 #include "result_set_utils.h"
42
43 using namespace std;
44 #ifdef ABILITY_CAMERA_SUPPORT
45 using namespace OHOS::CameraStandard;
46 #endif
47
48 namespace OHOS {
49 namespace Media {
50 const int32_t SAVE_PICTURE_TIMEOUT_SEC = 20;
51
MultiStagesPhotoCaptureManager()52 MultiStagesPhotoCaptureManager::MultiStagesPhotoCaptureManager()
53 {
54 deferredProcSession_ = make_shared<DeferredPhotoProcessingAdapter>();
55 }
56
~MultiStagesPhotoCaptureManager()57 MultiStagesPhotoCaptureManager::~MultiStagesPhotoCaptureManager() {}
58
GetInstance()59 MultiStagesPhotoCaptureManager& MultiStagesPhotoCaptureManager::GetInstance()
60 {
61 static MultiStagesPhotoCaptureManager instance;
62 return instance;
63 }
64
Init()65 bool MultiStagesPhotoCaptureManager::Init()
66 {
67 SyncWithDeferredProcSession();
68 return true;
69 }
70
CancelRequestAndRemoveImage(const vector<string> & columns)71 void MultiStagesPhotoCaptureManager::CancelRequestAndRemoveImage(const vector<string> &columns)
72 {
73 if (columns.size() < 1) {
74 MEDIA_ERR_LOG("invalid param");
75 return;
76 }
77 int32_t fileId = stoi(columns[0]);
78 string photoId = MultiStagesCaptureRequestTaskManager::GetProcessingPhotoId(fileId);
79 MEDIA_INFO_LOG("fileId: %{public}d, photoId: %{public}s", fileId, photoId.c_str());
80 CancelProcessRequest(photoId);
81 RemoveImage(photoId, false);
82 }
83
HandleMultiStagesOperation(MediaLibraryCommand & cmd,const vector<string> & columns)84 shared_ptr<OHOS::NativeRdb::ResultSet> MultiStagesPhotoCaptureManager::HandleMultiStagesOperation(
85 MediaLibraryCommand &cmd, const vector<string> &columns)
86 {
87 switch (cmd.GetOprnType()) {
88 case OperationType::PROCESS_IMAGE: {
89 int fileId = std::stoi(columns[0]); // 0 indicates file id
90 int deliveryMode = std::stoi(columns[1]); // 1 indicates delivery mode
91 ProcessImage(fileId, deliveryMode);
92 MultiStagesCaptureDfxTriggerRatio::GetInstance().SetTrigger(MultiStagesCaptureTriggerType::THIRD_PART);
93 break;
94 }
95 case OperationType::ADD_IMAGE: {
96 AddImage(cmd);
97 break;
98 }
99 case OperationType::SET_LOCATION: {
100 UpdateLocation(cmd.GetValueBucket());
101 break;
102 }
103 case OperationType::CANCEL_PROCESS_IMAGE: {
104 string photoId = columns[0]; // 0 indicates photo id
105 MEDIA_INFO_LOG("cancel request photoId: %{public}s", photoId.c_str());
106 CancelProcessRequest(photoId);
107 break;
108 }
109 case OperationType::REMOVE_MSC_TASK: {
110 CancelRequestAndRemoveImage(columns);
111 break;
112 }
113 case OperationType::ADD_LOWQUALITY_IMAGE: {
114 MEDIA_DEBUG_LOG("save low quality Image");
115 SaveLowQualityImageInfo(cmd);
116 break;
117 }
118 default:
119 break;
120 }
121 return nullptr;
122 }
123
SaveLowQualityImageInfo(MediaLibraryCommand & cmd)124 void MultiStagesPhotoCaptureManager::SaveLowQualityImageInfo(MediaLibraryCommand &cmd)
125 {
126 auto values = cmd.GetValueBucket();
127 string photoId = "";
128 ValueObject valueObject;
129 if (values.GetObject(PhotoColumn::PHOTO_ID, valueObject)) {
130 valueObject.GetString(photoId);
131 }
132 int32_t deferredProcType = -1;
133 if (values.GetObject(PhotoColumn::PHOTO_DEFERRED_PROC_TYPE, valueObject)) {
134 valueObject.GetInt(deferredProcType);
135 }
136 int32_t fileId = 0;
137 if (values.GetObject(MediaColumn::MEDIA_ID, valueObject)) {
138 valueObject.GetInt(fileId);
139 }
140 }
141
142 // 低质量入缓存
DealLowQualityPicture(const std::string & imageId,std::shared_ptr<Media::Picture> picture,bool isEdited)143 void MultiStagesPhotoCaptureManager::DealLowQualityPicture(const std::string &imageId,
144 std::shared_ptr<Media::Picture> picture, bool isEdited)
145 {
146 auto pictureManagerThread = PictureManagerThread::GetInstance();
147 if (pictureManagerThread == nullptr) {
148 return;
149 }
150 if (pictureManagerThread->IsExsitPictureByImageId(imageId)) {
151 return;
152 }
153 // 将低质量图存入缓存
154 time_t currentTime;
155 if ((currentTime = time(NULL)) == -1) {
156 MEDIA_ERR_LOG("Get time is error");
157 currentTime = time(NULL);
158 }
159 time_t expireTime = currentTime + SAVE_PICTURE_TIMEOUT_SEC;
160 std::string imageIdInPair = imageId;
161 sptr<PicturePair> picturePair = new PicturePair(std::move(picture), imageIdInPair, expireTime, true, false);
162 // 存低质量裸picture
163 pictureManagerThread->InsertPictureData(imageId, picturePair, LOW_QUALITY_PICTURE);
164 MEDIA_INFO_LOG("photoid: %{public}s", imageId.c_str());
165 }
166
IsHighQualityPhotoExist(const std::string & uri)167 bool MultiStagesPhotoCaptureManager::IsHighQualityPhotoExist(const std::string &uri)
168 {
169 string filePath = MediaFileUri::GetPathFromUri(uri, true);
170 string filePathTemp = filePath + ".high";
171 return MediaFileUtils::IsFileExists(filePathTemp) || MediaFileUtils::IsFileExists(filePath);
172 }
173
SaveLowQualityPicture(const std::string & imageId)174 void MultiStagesPhotoCaptureManager::SaveLowQualityPicture(const std::string &imageId)
175 {
176 MEDIA_INFO_LOG("photoid: %{public}s", imageId.c_str());
177 auto pictureManagerThread = PictureManagerThread::GetInstance();
178 if (pictureManagerThread == nullptr) {
179 return;
180 }
181 pictureManagerThread->SaveLowQualityPicture(imageId);
182 }
183
184 // 高质量编辑图片存20S
DealHighQualityPicture(const std::string & imageId,std::shared_ptr<Media::Picture> picture,bool isEdited)185 void MultiStagesPhotoCaptureManager::DealHighQualityPicture(const std::string &imageId,
186 std::shared_ptr<Media::Picture> picture, bool isEdited)
187 {
188 MEDIA_INFO_LOG("photoid: %{public}s", imageId.c_str());
189 auto pictureManagerThread = PictureManagerThread::GetInstance();
190 if (pictureManagerThread == nullptr) {
191 return;
192 }
193 // 将低质量图存入缓存
194 time_t currentTime;
195 if ((currentTime = time(NULL)) == -1) {
196 MEDIA_ERR_LOG("Get time is error");
197 currentTime = time(NULL);
198 }
199 time_t expireTime = currentTime + SAVE_PICTURE_TIMEOUT_SEC;
200 std::string imageIdInPair = imageId;
201 sptr<PicturePair> picturePair= new PicturePair(std::move(picture), imageIdInPair, expireTime, true, isEdited);
202 pictureManagerThread->InsertPictureData(imageId, picturePair, HIGH_QUALITY_PICTURE);
203 }
204
UpdateDbInfo(MediaLibraryCommand & cmd)205 int32_t MultiStagesPhotoCaptureManager::UpdateDbInfo(MediaLibraryCommand &cmd)
206 {
207 MediaLibraryCommand cmdLocal (OperationObject::FILESYSTEM_PHOTO, OperationType::UPDATE);
208 auto values = cmd.GetValueBucket();
209 ValueObject valueObject;
210 int32_t photoQuality = static_cast<int32_t>(MultiStagesPhotoQuality::LOW);
211 if (values.GetObject(PhotoColumn::PHOTO_QUALITY, valueObject)) {
212 valueObject.GetInt(photoQuality);
213 }
214 if (photoQuality == static_cast<int32_t>(MultiStagesPhotoQuality::LOW)) {
215 values.PutInt(MEDIA_DATA_DB_DIRTY, -1); // prevent uploading low-quality photo
216 }
217 cmdLocal.SetValueBucket(values);
218 cmdLocal.GetAbsRdbPredicates()->SetWhereClause(cmd.GetAbsRdbPredicates()->GetWhereClause());
219 cmdLocal.GetAbsRdbPredicates()->SetWhereArgs(cmd.GetAbsRdbPredicates()->GetWhereArgs());
220 auto result = DatabaseAdapter::Update(cmdLocal);
221 if (result != NativeRdb::E_OK) {
222 MEDIA_ERR_LOG("update failed");
223 }
224 return result;
225 }
226
UpdateLocation(const NativeRdb::ValuesBucket & values)227 void MultiStagesPhotoCaptureManager::UpdateLocation(const NativeRdb::ValuesBucket &values)
228 {
229 MediaLibraryTracer tracer;
230 tracer.Start("UpdateLocation");
231 double longitude = 0;
232 ValueObject valueObject;
233 if (values.GetObject(PhotoColumn::PHOTO_LONGITUDE, valueObject)) {
234 valueObject.GetDouble(longitude);
235 }
236 double latitude = 0;
237 if (values.GetObject(PhotoColumn::PHOTO_LATITUDE, valueObject)) {
238 valueObject.GetDouble(latitude);
239 }
240
241 int32_t fileId = 0;
242 if (values.GetObject(MediaColumn::MEDIA_ID, valueObject)) {
243 valueObject.GetInt(fileId);
244 }
245
246 MediaLibraryCommand queryCmd(OperationObject::FILESYSTEM_PHOTO, OperationType::QUERY);
247 queryCmd.GetAbsRdbPredicates()->SetWhereClause(MediaColumn::MEDIA_ID + " = " + to_string(fileId));
248 vector<string> columns { MediaColumn::MEDIA_FILE_PATH };
249
250 auto resultSet = DatabaseAdapter::Query(queryCmd, columns);
251 if (resultSet == nullptr || resultSet->GoToFirstRow() != 0) {
252 MEDIA_ERR_LOG("result set is empty");
253 return;
254 }
255 string path = GetStringVal(MediaColumn::MEDIA_FILE_PATH, resultSet);
256 resultSet->Close();
257
258 // update exif info
259 auto ret = ExifUtils::WriteGpsExifInfo(path, longitude, latitude);
260 if (ret != E_OK) {
261 MEDIA_ERR_LOG("write gps info fail");
262 return;
263 }
264
265 string originPath = MediaLibraryAssetOperations::GetEditDataSourcePath(path);
266 if (MediaFileUtils::IsFileExists(originPath)) {
267 // write gps info if this photo was edited.
268 auto ret = ExifUtils::WriteGpsExifInfo(path, longitude, latitude);
269 if (ret != E_OK) {
270 MEDIA_ERR_LOG("write origin file gps info fail");
271 return;
272 }
273 }
274
275 MediaLibraryCommand cmd(OperationObject::FILESYSTEM_PHOTO, OperationType::UPDATE);
276 cmd.GetAbsRdbPredicates()->EqualTo(PhotoColumn::MEDIA_ID, fileId);
277 ValuesBucket updateValues;
278 updateValues.PutDouble(MEDIA_DATA_DB_LATITUDE, latitude);
279 updateValues.PutDouble(MEDIA_DATA_DB_LONGITUDE, longitude);
280 cmd.SetValueBucket(updateValues);
281
282 auto result = DatabaseAdapter::Update(cmd);
283 if (result != NativeRdb::E_OK) {
284 MEDIA_ERR_LOG("update fail fileId: %{public}d", fileId);
285 }
286 }
287
AddImageInternal(int32_t fileId,const string & photoId,int32_t deferredProcType,bool discardable)288 void MultiStagesPhotoCaptureManager::AddImageInternal(int32_t fileId, const string &photoId, int32_t deferredProcType,
289 bool discardable)
290 {
291 MultiStagesCaptureRequestTaskManager::AddPhotoInProgress(fileId, photoId, discardable);
292
293 #ifdef ABILITY_CAMERA_SUPPORT
294 DpsMetadata metadata;
295 metadata.Set(CameraStandard::DEFERRED_PROCESSING_TYPE_KEY, deferredProcType);
296 deferredProcSession_->AddImage(photoId, metadata, discardable);
297 #endif
298 }
299
AddImage(int32_t fileId,const string & photoId,int32_t deferredProcType)300 void MultiStagesPhotoCaptureManager::AddImage(int32_t fileId, const string &photoId, int32_t deferredProcType)
301 {
302 if (photoId.empty()) {
303 MEDIA_ERR_LOG("photo is empty");
304 return;
305 }
306 MEDIA_INFO_LOG("enter fileId: %{public}d, photoId: %{public}s, deferredProcType: %{public}d", fileId,
307 photoId.c_str(), deferredProcType);
308
309 // called when camera low quality photo saved, isTrashed must be false.
310 AddImageInternal(fileId, photoId, deferredProcType, false);
311 }
312
AddImage(MediaLibraryCommand & cmd)313 void MultiStagesPhotoCaptureManager::AddImage(MediaLibraryCommand &cmd)
314 {
315 MEDIA_DEBUG_LOG("calling addImage");
316 UpdateDbInfo(cmd);
317 auto values = cmd.GetValueBucket();
318 ValueObject valueObject;
319 int32_t photoQuality = static_cast<int32_t>(MultiStagesPhotoQuality::LOW);
320 if (values.GetObject(PhotoColumn::PHOTO_QUALITY, valueObject)) {
321 valueObject.GetInt(photoQuality);
322 }
323 string photoId = "";
324 if (values.GetObject(PhotoColumn::PHOTO_ID, valueObject)) {
325 valueObject.GetString(photoId);
326 }
327 auto pictureManagerThread = PictureManagerThread::GetInstance();
328 if (pictureManagerThread == nullptr) {
329 return;
330 }
331 if (photoQuality == static_cast<int32_t>(MultiStagesPhotoQuality::FULL)) {
332 pictureManagerThread->SavePictureWithImageId(photoId);
333 UpdatePictureQuality(photoId);
334 return;
335 }
336 int32_t deferredProcType = -1;
337 if (values.GetObject(PhotoColumn::PHOTO_DEFERRED_PROC_TYPE, valueObject)) {
338 valueObject.GetInt(deferredProcType);
339 }
340 int32_t fileId = 0;
341 if (values.GetObject(MediaColumn::MEDIA_ID, valueObject)) {
342 valueObject.GetInt(fileId);
343 }
344 AddImage(fileId, photoId, deferredProcType);
345 MultiStagesCaptureDfxTotalTime::GetInstance().AddStartTime(photoId);
346 MultiStagesCaptureDfxTriggerRatio::GetInstance().SetTrigger(MultiStagesCaptureTriggerType::AUTO);
347 if (OPRN_ADD_LOWQUALITY_IMAGE == cmd.GetQuerySetParam("save_picture")) {
348 MEDIA_DEBUG_LOG("save last low quality Image");
349 SaveLowQualityImageInfo(cmd);
350 }
351 }
352
UpdatePictureQuality(const std::string & photoId)353 int32_t MultiStagesPhotoCaptureManager::UpdatePictureQuality(const std::string &photoId)
354 {
355 MediaLibraryTracer tracer;
356 tracer.Start("UpdatePictureQuality " + photoId);
357 MediaLibraryCommand updateCmd(OperationObject::FILESYSTEM_PHOTO, OperationType::UPDATE);
358 NativeRdb::ValuesBucket updateValues;
359 updateValues.PutInt(PhotoColumn::PHOTO_QUALITY, static_cast<int32_t>(MultiStagesPhotoQuality::FULL));
360 updateCmd.SetValueBucket(updateValues);
361 updateCmd.GetAbsRdbPredicates()->EqualTo(PhotoColumn::PHOTO_ID, photoId);
362 int32_t updatePhotoQualityResult = DatabaseAdapter::Update(updateCmd);
363 updateCmd.GetAbsRdbPredicates()->EqualTo(PhotoColumn::PHOTO_IS_TEMP, false);
364 updateCmd.GetAbsRdbPredicates()->NotEqualTo(PhotoColumn::PHOTO_SUBTYPE,
365 to_string(static_cast<int32_t>(PhotoSubType::MOVING_PHOTO)));
366 NativeRdb::ValuesBucket updateValuesDirty;
367 updateValuesDirty.PutInt(PhotoColumn::PHOTO_DIRTY, static_cast<int32_t>(DirtyType::TYPE_NEW));
368 updateCmd.SetValueBucket(updateValuesDirty);
369 auto isDirtyResult = DatabaseAdapter::Update(updateCmd);
370 if (isDirtyResult < 0) {
371 MEDIA_WARN_LOG("update dirty flag fail, photoId: %{public}s", photoId.c_str());
372 }
373 return updatePhotoQualityResult;
374 }
375
SyncWithDeferredProcSessionInternal()376 void MultiStagesPhotoCaptureManager::SyncWithDeferredProcSessionInternal()
377 {
378 MEDIA_INFO_LOG("enter");
379 // 进程重启场景,媒体库需要和延时子服务同步
380 MediaLibraryCommand cmd(OperationObject::FILESYSTEM_PHOTO, OperationType::QUERY);
381 string where = MEDIA_DATA_DB_PHOTO_ID + " is not null and " +
382 MEDIA_DATA_DB_PHOTO_QUALITY + " > 0 and " + MEDIA_DATA_DB_MEDIA_TYPE + " = " +
383 to_string(static_cast<int32_t>(MediaType::MEDIA_TYPE_IMAGE));
384 cmd.GetAbsRdbPredicates()->SetWhereClause(where);
385 vector<string> columns { MEDIA_DATA_DB_ID, MEDIA_DATA_DB_PHOTO_ID, MEDIA_DATA_DB_DATE_TRASHED,
386 MEDIA_DATA_DB_DEFERRED_PROC_TYPE };
387
388 auto resultSet = DatabaseAdapter::Query(cmd, columns);
389 if (resultSet == nullptr || resultSet->GoToFirstRow() != 0) {
390 MEDIA_ERR_LOG("result set is empty");
391 return;
392 }
393
394 MediaLibraryTracer tracer;
395 tracer.Start("MultiStagesPhotoCaptureManager::SyncWithDeferredProcSession");
396
397 deferredProcSession_->BeginSynchronize();
398 do {
399 int32_t fileId = GetInt32Val(MEDIA_DATA_DB_ID, resultSet);
400 string photoId = GetStringVal(MEDIA_DATA_DB_PHOTO_ID, resultSet);
401 bool isTrashed = GetInt32Val(MEDIA_DATA_DB_DATE_TRASHED, resultSet) > 0;
402 if (setOfDeleted_.find(fileId) != setOfDeleted_.end()) {
403 MEDIA_INFO_LOG("remove image, fileId: %{public}d, photoId: %{public}s", fileId, photoId.c_str());
404 deferredProcSession_->RemoveImage(photoId);
405 continue;
406 }
407 MEDIA_INFO_LOG("AddImage fileId: %{public}d, photoId: %{public}s", fileId, photoId.c_str());
408 int32_t deferredProcType = GetInt32Val(MEDIA_DATA_DB_DEFERRED_PROC_TYPE, resultSet);
409 AddImageInternal(fileId, photoId, deferredProcType, isTrashed);
410 } while (!resultSet->GoToNextRow());
411 resultSet->Close();
412
413 deferredProcSession_->EndSynchronize();
414 MEDIA_INFO_LOG("exit");
415 }
416
SyncWithDeferredPhotoProcSessionAsync(AsyncTaskData * data)417 static void SyncWithDeferredPhotoProcSessionAsync(AsyncTaskData *data)
418 {
419 MultiStagesPhotoCaptureManager::GetInstance().SyncWithDeferredProcSessionInternal();
420 }
421
SyncWithDeferredProcSession()422 void MultiStagesPhotoCaptureManager::SyncWithDeferredProcSession()
423 {
424 shared_ptr<MediaLibraryAsyncWorker> asyncWorker = MediaLibraryAsyncWorker::GetInstance();
425 if (asyncWorker == nullptr) {
426 MEDIA_INFO_LOG("can not get async worker");
427 return;
428 }
429
430 shared_ptr<MediaLibraryAsyncTask> asyncTask =
431 make_shared<MediaLibraryAsyncTask>(SyncWithDeferredPhotoProcSessionAsync, nullptr);
432 if (asyncTask == nullptr) {
433 MEDIA_ERR_LOG("SyncWithDeferredProcSession create task fail");
434 return;
435 }
436 MEDIA_INFO_LOG("SyncWithDeferredProcSession add task success");
437 asyncWorker->AddTask(asyncTask, false);
438 }
439
CancelProcessRequest(const string & photoId)440 bool MultiStagesPhotoCaptureManager::CancelProcessRequest(const string &photoId)
441 {
442 if (!MultiStagesCaptureRequestTaskManager::IsPhotoInProcess(photoId)) {
443 MEDIA_ERR_LOG("photoId is empty or not in process");
444 return false;
445 }
446
447 int32_t currentRequestCount =
448 MultiStagesCaptureRequestTaskManager::UpdatePhotoInProcessRequestCount(photoId, RequestType::CANCEL_REQUEST);
449 if (currentRequestCount > 0) {
450 MEDIA_ERR_LOG("not cancel request because request count(%{public}d) greater than 0", currentRequestCount);
451
452 return false;
453 }
454 auto isCancelSucc = deferredProcSession_->CancelProcessImage(photoId);
455 MEDIA_INFO_LOG("cancel request isCancelSucc: %{public}d", isCancelSucc);
456
457 return true;
458 }
459
RemoveImage(const string & photoId,bool isRestorable)460 void MultiStagesPhotoCaptureManager::RemoveImage(const string &photoId, bool isRestorable)
461 {
462 if (!MultiStagesCaptureRequestTaskManager::IsPhotoInProcess(photoId)) {
463 // In order to ensure image can be completely deleted, do not return here, only record the log.
464 MEDIA_ERR_LOG("photoId is empty or not in process ");
465 }
466
467 MultiStagesCaptureRequestTaskManager::RemovePhotoInProgress(photoId, isRestorable);
468 deferredProcSession_->RemoveImage(photoId, isRestorable);
469 }
470
RestoreImage(const string & photoId)471 void MultiStagesPhotoCaptureManager::RestoreImage(const string &photoId)
472 {
473 if (photoId.empty()) {
474 MEDIA_DEBUG_LOG("photoId is empty");
475 }
476
477 MultiStagesCaptureRequestTaskManager::UpdatePhotoInProgress(photoId);
478 deferredProcSession_->RestoreImage(photoId);
479 }
480
ProcessImage(int fileId,int deliveryMode)481 void MultiStagesPhotoCaptureManager::ProcessImage(int fileId, int deliveryMode)
482 {
483 string photoId = MultiStagesCaptureRequestTaskManager::GetProcessingPhotoId(fileId) ;
484 if (photoId.size() == 0) {
485 MEDIA_ERR_LOG("processimage image id is invalid, fileId: %{public}d", fileId);
486 return;
487 }
488
489 string callerBundleName = MediaLibraryBundleManager::GetInstance()->GetClientBundleName();
490
491 MultiStagesCaptureDfxTriggerRatio::GetInstance().SetTrigger(MultiStagesCaptureTriggerType::THIRD_PART);
492 MultiStagesCaptureDfxRequestPolicy::GetInstance().SetPolicy(callerBundleName,
493 static_cast<RequestPolicy>(deliveryMode));
494 MultiStagesCaptureDfxFirstVisit::GetInstance().Report(photoId);
495 int32_t currentRequestCount =
496 MultiStagesCaptureRequestTaskManager::UpdatePhotoInProcessRequestCount(photoId, RequestType::REQUEST);
497 MEDIA_INFO_LOG("processimage, pkg name: %{public}s, photoid %{public}s, mode: %{public}d, count: %{public}d",
498 callerBundleName.c_str(), photoId.c_str(), deliveryMode, currentRequestCount);
499 if ((deliveryMode == static_cast<int32_t>(RequestPolicy::HIGH_QUALITY_MODE) ||
500 deliveryMode == static_cast<int32_t>(RequestPolicy::BALANCE_MODE)) &&
501 currentRequestCount <= 1) {
502 deferredProcSession_->ProcessImage(callerBundleName, photoId);
503 }
504 }
505
IsPhotoDeleted(const std::string & photoId)506 bool MultiStagesPhotoCaptureManager::IsPhotoDeleted(const std::string &photoId)
507 {
508 if (!MultiStagesCaptureRequestTaskManager::IsPhotoInProcess(photoId)) {
509 return false;
510 }
511
512 return true;
513 }
514 } // namespace Media
515 } // namespace OHOS