1 /*
2  * Copyright (c) 2023-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 #include <cstdio>
17 #include <thread>
18 #include <unistd.h>
19 
20 #include <gtest/gtest.h>
21 #include <nlohmann/json.hpp>
22 
23 #include "accesstoken_kit.h"
24 #include "context_impl.h"
25 #include "file_access_framework_errno.h"
26 #include "file_access_observer_common.h"
27 #include "iservice_registry.h"
28 #include "iobserver_callback.h"
29 #include "nativetoken_kit.h"
30 #include "observer_callback_stub.h"
31 #include "token_setproc.h"
32 
33 #define private public
34 #include "file_access_helper.h"
35 #undef private
36 
37 namespace {
38 using namespace std;
39 using namespace OHOS;
40 using namespace FileAccessFwk;
41 using json = nlohmann::json;
42 const int ABILITY_ID = 5003;
43 const int INIT_THREADS_NUMBER = 4;
44 shared_ptr<FileAccessHelper> g_fah = nullptr;
45 int g_notifyEvent = -1;
46 int g_notifyFlag = -1;
47 string g_notifyUri = "";
48 vector<string> g_notifyUris;
49 const int SLEEP_TIME = 600 * 1000;
50 const int UID_TRANSFORM_TMP = 20000000;
51 const int UID_DEFAULT = 0;
52 const uint64_t SYSTEM_APP_MASK =  (static_cast<uint64_t>(1) << 32); // 1: Base number, 32: Left shifted bit numbers
53 
54 shared_ptr<OHOS::AbilityRuntime::Context> g_context = nullptr;
55 
SetNativeToken()56 void SetNativeToken()
57 {
58     uint64_t tokenId;
59     const char *perms[] = {
60         "ohos.permission.FILE_ACCESS_MANAGER",
61         "ohos.permission.GET_BUNDLE_INFO_PRIVILEGED",
62         "ohos.permission.CONNECT_FILE_ACCESS_EXTENSION"
63     };
64     NativeTokenInfoParams infoInstance = {
65         .dcapsNum = 0,
66         .permsNum = 3,
67         .aclsNum = 0,
68         .dcaps = nullptr,
69         .perms = perms,
70         .acls = nullptr,
71         .aplStr = "system_core",
72     };
73 
74     infoInstance.processName = "SetUpTestCase";
75     tokenId = GetAccessTokenId(&infoInstance);
76     const uint64_t systemAppMask = (static_cast<uint64_t>(1) << 32);
77     tokenId |= systemAppMask;
78     SetSelfTokenID(tokenId);
79     OHOS::Security::AccessToken::AccessTokenKit::ReloadNativeTokenInfo();
80 }
81 
SetNativeToken(const char * processName,const char * perms[],int32_t permsNum)82 void SetNativeToken(const char* processName, const char*perms[], int32_t permsNum)
83 {
84     uint64_t tokenId;
85     NativeTokenInfoParams infoInstance = {
86         .dcapsNum = 0,
87         .permsNum = permsNum,
88         .aclsNum = 0,
89         .dcaps = nullptr,
90         .perms = perms,
91         .acls = nullptr,
92         .aplStr = "system_core",
93     };
94     tokenId = GetAccessTokenId(&infoInstance);
95     const uint64_t systemAppMask = SYSTEM_APP_MASK;
96     tokenId |= systemAppMask;
97     SetSelfTokenID(tokenId);
98     OHOS::Security::AccessToken::AccessTokenKit::ReloadNativeTokenInfo();
99 }
100 
101 class FileExtensionNotifyTest : public testing::Test {
102 public:
SetUpTestCase(void)103     static void SetUpTestCase(void)
104     {
105         cout << "FileExtensionNotifyTest code test" << endl;
106         SetNativeToken();
107         auto saManager = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
108         if (saManager == nullptr) {
109             return;
110         }
111         auto remoteObj = saManager->GetSystemAbility(ABILITY_ID);
112         g_context = make_shared<OHOS::AbilityRuntime::ContextImpl>();
113         g_context->SetToken(remoteObj);
114         AAFwk::Want want;
115         vector<AAFwk::Want> wantVec;
116         setuid(UID_TRANSFORM_TMP);
117         int ret = FileAccessHelper::GetRegisteredFileAccessExtAbilityInfo(wantVec);
118         EXPECT_EQ(ret, OHOS::FileAccessFwk::ERR_OK);
119         bool sus = false;
120         for (size_t i = 0; i < wantVec.size(); i++) {
121             auto element = wantVec[i].GetElement();
122             if (element.GetBundleName() == "com.ohos.UserFile.ExternalFileManager" &&
123                 element.GetAbilityName() == "FileExtensionAbility") {
124                 want = wantVec[i];
125                 sus = true;
126                 break;
127             }
128         }
129         EXPECT_TRUE(sus);
130         vector<AAFwk::Want> wants{want};
131         g_fah = FileAccessHelper::Creator(remoteObj, wants);
132         if (g_fah == nullptr) {
133             GTEST_LOG_(ERROR) << "external_file_access_test g_fah is nullptr";
134             exit(1);
135         }
136         setuid(UID_DEFAULT);
137     }
TearDownTestCase()138     static void TearDownTestCase()
139     {
140         if (g_fah) {
141             g_fah->Release();
142         }
143         g_fah = nullptr;
144     };
SetUp()145     void SetUp(){};
TearDown()146     void TearDown(){};
147 };
148 
149 class MyObserver : public ObserverCallbackStub {
150 public:
MyObserver()151     MyObserver() {};
152     virtual ~MyObserver() = default;
153     void OnChange(NotifyMessage &notifyMessage) override;
154 };
155 
OnChange(NotifyMessage & notifyMessage)156 void MyObserver::OnChange(NotifyMessage &notifyMessage)
157 {
158     g_notifyEvent = static_cast<int>(notifyMessage.notifyType_);
159     std::string notifyUri = notifyMessage.uris_[0];
160     g_notifyUri = notifyUri;
161     GTEST_LOG_(INFO) << "enter notify uri =" + notifyUri + " type =" + std::to_string(g_notifyEvent) +" uri size" +
162         std::to_string(notifyMessage.uris_.size());
163 }
164 
165 class TestObserver : public ObserverCallbackStub {
166 public:
TestObserver()167     TestObserver() {};
168     virtual ~TestObserver() = default;
169     void OnChange(NotifyMessage &notifyMessage) override;
170 };
171 
OnChange(NotifyMessage & notifyMessage)172 void TestObserver::OnChange(NotifyMessage &notifyMessage)
173 {
174     g_notifyFlag = static_cast<int>(notifyMessage.notifyType_);
175     std::string notifyUri = notifyMessage.uris_[0];
176     g_notifyUris = notifyMessage.uris_;
177     GTEST_LOG_(INFO) << "enter TestObserver uri =" + notifyUri + "type =" + std::to_string(g_notifyFlag);
178 }
179 
ReadyRegisterNotify00(Uri & parentUri,sptr<IFileAccessObserver> & myObserver1,sptr<IFileAccessObserver> & myObserver2,sptr<IFileAccessObserver> & myObserver3,sptr<IFileAccessObserver> & myObserver4)180 static tuple<Uri, Uri, Uri, Uri> ReadyRegisterNotify00(Uri& parentUri,
181                                                        sptr<IFileAccessObserver>& myObserver1,
182                                                        sptr<IFileAccessObserver>& myObserver2,
183                                                        sptr<IFileAccessObserver>& myObserver3,
184                                                        sptr<IFileAccessObserver>& myObserver4)
185 {
186     bool notifyForDescendants = false;
187     Uri newDirUriTest1("");
188     EXPECT_NE(g_fah, nullptr);
189     int result = g_fah->Mkdir(parentUri, "uri_dir1", newDirUriTest1);
190     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
191     Uri newDirUriTest2("");
192     result = g_fah->Mkdir(parentUri, "uri_dir2", newDirUriTest2);
193     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
194     Uri newFileUri1("");
195     result = g_fah->CreateFile(parentUri, "uri_file1", newFileUri1);
196     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
197     GTEST_LOG_(INFO) <<  newFileUri1.ToString();
198     Uri newFileUri2("");
199     result = g_fah->CreateFile(parentUri, "uri_file2", newFileUri2);
200     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
201 
202     result = g_fah->RegisterNotify(newDirUriTest1, true, myObserver1);
203     EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
204     result = g_fah->RegisterNotify(newDirUriTest2, notifyForDescendants, myObserver2);
205     EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
206     result = g_fah->RegisterNotify(newFileUri1, notifyForDescendants, myObserver3);
207     EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
208     result = g_fah->RegisterNotify(newFileUri2, notifyForDescendants, myObserver4);
209     EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
210 
211     return {newDirUriTest1, newDirUriTest2, newFileUri1, newFileUri2};
212 }
213 
TriggerNotify00(Uri & newDirUriTest1,Uri & newDirUriTest2,Uri & newFileUri1,Uri & newFileUri2)214 static tuple<Uri, Uri> TriggerNotify00(Uri& newDirUriTest1, Uri& newDirUriTest2, Uri& newFileUri1, Uri& newFileUri2)
215 {
216     Uri testUri("");
217     EXPECT_NE(g_fah, nullptr);
218     int result = g_fah->CreateFile(newDirUriTest1, "testUri", testUri);
219     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
220     usleep(SLEEP_TIME);
221     EXPECT_EQ(g_notifyEvent, ADD_EVENT);
222     EXPECT_EQ(g_notifyUri, testUri.ToString());
223     Uri renameDirUri1("");
224     result = g_fah->Rename(newDirUriTest1, "testDir", renameDirUri1);
225     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
226     usleep(SLEEP_TIME);
227     EXPECT_EQ(g_notifyEvent, MOVED_SELF);
228     EXPECT_EQ(g_notifyUri, newDirUriTest1.ToString());
229     result = g_fah->Delete(newDirUriTest2);
230     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
231     usleep(SLEEP_TIME);
232     EXPECT_EQ(g_notifyEvent, DELETE_EVENT);
233     EXPECT_EQ(g_notifyUri, newDirUriTest2.ToString());
234 
235     Uri renameUri1("");
236     result = g_fah->Rename(newFileUri1, "renameUri1", renameUri1);
237     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
238     usleep(SLEEP_TIME);
239     EXPECT_EQ(g_notifyEvent, MOVED_SELF);
240     EXPECT_EQ(g_notifyUri, newFileUri1.ToString());
241     result = g_fah->Delete(newFileUri2);
242     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
243     usleep(SLEEP_TIME);
244     EXPECT_EQ(g_notifyEvent, DELETE_EVENT);
245     EXPECT_EQ(g_notifyUri, newFileUri2.ToString());
246 
247     return {renameDirUri1, renameUri1};
248 }
249 
250 /**
251  * @tc.number: user_file_service_external_file_access_notify_0000
252  * @tc.name: external_file_access_notify_0000
253  * @tc.desc: Test function of RegisterNotify and UnregisterNotify interface for SUCCESS.
254  * @tc.size: MEDIUM
255  * @tc.type: FUNC
256  * @tc.level Level 1
257  * @tc.require: SR000H0386
258  */
259 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0000, testing::ext::TestSize.Level1)
260 {
261     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0000";
262     try {
263         vector<RootInfo> info;
264         EXPECT_NE(g_fah, nullptr);
265         int result = g_fah->GetRoots(info);
266         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
267         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
268         sptr<IFileAccessObserver> myObserver2 = sptr(new (std::nothrow) MyObserver());
269         sptr<IFileAccessObserver> myObserver3 = sptr(new (std::nothrow) MyObserver());
270         sptr<IFileAccessObserver> myObserver4 = sptr(new (std::nothrow) MyObserver());
271         Uri parentUri(info[1].uri);
272         auto [newDirUriTest1, newDirUriTest2, newFileUri1, newFileUri2] =
273             ReadyRegisterNotify00(parentUri, myObserver1, myObserver2, myObserver3, myObserver4);
274 
275         auto [renameDirUri1, renameUri1] = TriggerNotify00(newDirUriTest1, newDirUriTest2, newFileUri1, newFileUri2);
276 
277         sleep(1);
278         result = g_fah->UnregisterNotify(newDirUriTest1, myObserver1);
279         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
280         result = g_fah->UnregisterNotify(newDirUriTest2, myObserver2);
281         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
282         result = g_fah->UnregisterNotify(newFileUri1, myObserver3);
283         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
284         result = g_fah->UnregisterNotify(newFileUri2, myObserver4);
285         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
286         result = g_fah->Delete(renameDirUri1);
287         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
288         result = g_fah->Delete(renameUri1);
289         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
290     } catch (...) {
291         GTEST_LOG_(ERROR) << "external_file_access_notify_0000 occurs an exception.";
292     }
293     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0000";
294 }
295 
ReadyRegisterNotify01(Uri & parentUri,sptr<IFileAccessObserver> myObserver1,sptr<IFileAccessObserver> myObserver2,sptr<IFileAccessObserver> myObserver3)296 static tuple<Uri, Uri, Uri> ReadyRegisterNotify01(Uri& parentUri, sptr<IFileAccessObserver> myObserver1,
297     sptr<IFileAccessObserver> myObserver2, sptr<IFileAccessObserver> myObserver3)
298 {
299     bool notifyForDescendants1 = true;
300     bool notifyForDescendants2 = false;
301     Uri newFileUri1("");
302     EXPECT_NE(g_fah, nullptr);
303     int result = g_fah->CreateFile(parentUri, "uri_file1", newFileUri1);
304     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
305     Uri newFileUri2("");
306     result = g_fah->CreateFile(parentUri, "uri_file2", newFileUri2);
307     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
308     Uri newFileUri3("");
309     result = g_fah->CreateFile(parentUri, "uri_file3", newFileUri3);
310     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
311 
312     result = g_fah->RegisterNotify(newFileUri1, notifyForDescendants1, myObserver1);
313     EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
314     result = g_fah->RegisterNotify(newFileUri2, notifyForDescendants1, myObserver2);
315     EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
316     result = g_fah->RegisterNotify(newFileUri3, notifyForDescendants2, myObserver3);
317     EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
318     return {newFileUri1, newFileUri2, newFileUri3};
319 }
320 
321 /**
322  * @tc.number: user_file_service_external_file_access_notify_0001
323  * @tc.name: external_file_access_notify_0001
324  * @tc.desc: Test function of RegisterNotify and UnregisterNotify interface for SUCCESS.
325  * @tc.size: MEDIUM
326  * @tc.type: FUNC
327  * @tc.level Level 1
328  * @tc.require: SR000H0386
329  */
330 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0001, testing::ext::TestSize.Level1)
331 {
332     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0001";
333     try {
334         vector<RootInfo> info;
335         EXPECT_NE(g_fah, nullptr);
336         int result = g_fah->GetRoots(info);
337         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
338 
339         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
340         sptr<IFileAccessObserver> myObserver2 = sptr(new (std::nothrow) MyObserver());
341         sptr<IFileAccessObserver> myObserver3 = sptr(new (std::nothrow) MyObserver());
342         Uri parentUri(info[1].uri);
343         auto [newFileUri1, newFileUri2, newFileUri3] =
344             ReadyRegisterNotify01(parentUri, myObserver1, myObserver2, myObserver3);
345 
346         Uri renameFileUri1("");
347         result = g_fah->Rename(newFileUri1, "renamefile", renameFileUri1);
348         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
349         usleep(SLEEP_TIME);
350         EXPECT_EQ(g_notifyEvent, MOVED_SELF);
351         EXPECT_EQ(g_notifyUri, newFileUri1.ToString());
352 
353         result = g_fah->Delete(newFileUri2);
354         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
355         usleep(SLEEP_TIME);
356         EXPECT_EQ(g_notifyEvent, DELETE_EVENT);
357         EXPECT_EQ(g_notifyUri, newFileUri2.ToString());
358         result = g_fah->Delete(newFileUri3);
359         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
360         usleep(SLEEP_TIME);
361         EXPECT_EQ(g_notifyEvent, DELETE_EVENT);
362         EXPECT_EQ(g_notifyUri, newFileUri3.ToString());
363 
364         sleep(1);
365         result = g_fah->UnregisterNotify(newFileUri1, myObserver1);
366         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
367         result = g_fah->UnregisterNotify(newFileUri2, myObserver2);
368         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
369         result = g_fah->UnregisterNotify(newFileUri3, myObserver3);
370         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
371         result = g_fah->Delete(renameFileUri1);
372         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
373     } catch (...) {
374         GTEST_LOG_(ERROR) << "external_file_access_notify_0001 occurs an exception.";
375     }
376     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0001";
377 }
378 
ReadyRegisterNotify02(Uri & parentUri)379 static tuple<Uri, Uri, Uri, Uri> ReadyRegisterNotify02(Uri& parentUri)
380 {
381     Uri newDirUriTest1("");
382     EXPECT_NE(g_fah, nullptr);
383     int result = g_fah->Mkdir(parentUri, "uri_dir1", newDirUriTest1);
384     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
385     Uri newDirUriTest2("");
386     result = g_fah->Mkdir(parentUri, "uri_dir2", newDirUriTest2);
387     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
388     Uri newFileUri1("");
389     result = g_fah->CreateFile(parentUri, "uri_file1", newFileUri1);
390     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
391     Uri newFileUri2("");
392     result = g_fah->CreateFile(parentUri, "uri_file2", newFileUri2);
393     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
394 
395     return {newDirUriTest1, newDirUriTest2, newFileUri1, newFileUri2};
396 }
397 
TriggerNotify02(Uri & newDirUriTest1,Uri & newDirUriTest2,Uri & newFileUri1,Uri & newFileUri2)398 static tuple<Uri, Uri> TriggerNotify02(Uri& newDirUriTest1, Uri& newDirUriTest2, Uri& newFileUri1, Uri& newFileUri2)
399 {
400     const int tm = 2;
401     Uri testFile("");
402     EXPECT_NE(g_fah, nullptr);
403     int result = g_fah->CreateFile(newDirUriTest1, "test_file", testFile);
404     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
405     usleep(SLEEP_TIME);
406     Uri renameDirUri1("");
407     result = g_fah->Rename(newDirUriTest1, "renameDir", renameDirUri1);
408     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
409     usleep(SLEEP_TIME);
410     EXPECT_EQ(g_notifyEvent, MOVED_SELF);
411     EXPECT_EQ(g_notifyUri, newDirUriTest1.ToString());
412     result = g_fah->Delete(newDirUriTest2);
413     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
414     usleep(SLEEP_TIME);
415     EXPECT_EQ(g_notifyEvent, DELETE_EVENT);
416     EXPECT_EQ(g_notifyUri, newDirUriTest2.ToString());
417     Uri renameFileUri1("");
418     result = g_fah->Rename(newFileUri1, "renamefile", renameFileUri1);
419     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
420     usleep(SLEEP_TIME);
421     EXPECT_EQ(g_notifyEvent, MOVED_SELF);
422     EXPECT_EQ(g_notifyUri, newFileUri1.ToString());
423     result = g_fah->Delete(newFileUri2);
424     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
425     usleep(SLEEP_TIME);
426     EXPECT_EQ(g_notifyEvent, DELETE_EVENT);
427     EXPECT_EQ(g_notifyUri, newFileUri2.ToString());
428     sleep(tm);
429     return {renameDirUri1, renameFileUri1};
430 }
431 /**
432  * @tc.number: user_file_service_external_file_access_notify_0002
433  * @tc.name: external_file_access_notify_0002
434  * @tc.desc: Test function of RegisterNotify and UnregisterNotify interface for SUCCESS.
435  * @tc.size: MEDIUM
436  * @tc.type: FUNC
437  * @tc.level Level 1
438  * @tc.require: SR000H0386
439  */
440 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0002, testing::ext::TestSize.Level1)
441 {
442     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0002";
443     try {
444         vector<RootInfo> info;
445         EXPECT_NE(g_fah, nullptr);
446         int result = g_fah->GetRoots(info);
447         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
448         bool notifyForDescendants = true;
449         vector<sptr<IFileAccessObserver>> observers;
450         const int len = 12;
451         const int group = 3;
452         for (int i = 0; i < len; i++) {
453             observers.emplace_back(new (std::nothrow) MyObserver());
454         }
455         Uri parentUri(info[1].uri);
456         auto [newDirUriTest1, newDirUriTest2, newFileUri1, newFileUri2] = ReadyRegisterNotify02(parentUri);
457 
458         for (int i = 0; i < group; i++) {
459             result = g_fah->RegisterNotify(newDirUriTest1, notifyForDescendants, observers[i]);
460             EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
461             result = g_fah->RegisterNotify(newDirUriTest2, notifyForDescendants, observers[3 + i]);
462             EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
463             result = g_fah->RegisterNotify(newFileUri1, notifyForDescendants, observers[6 + i]);
464             EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
465             result = g_fah->RegisterNotify(newFileUri2, notifyForDescendants, observers[9 + i]);
466             EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
467         }
468 
469         auto [renameDirUri1, renameFileUri1] =
470             TriggerNotify02(newDirUriTest1, newDirUriTest2, newFileUri1, newFileUri2);
471 
472         for (int i = 0; i < group; i++) {
473             result = g_fah->UnregisterNotify(newDirUriTest1, observers[i]);
474             EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
475             result = g_fah->UnregisterNotify(newDirUriTest2, observers[3 + i]);
476             EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
477             result = g_fah->UnregisterNotify(newFileUri1, observers[6 + i]);
478             EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
479             result = g_fah->UnregisterNotify(newFileUri2, observers[9 + i]);
480             EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
481         }
482         result = g_fah->Delete(renameDirUri1);
483         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
484         result = g_fah->Delete(renameFileUri1);
485         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
486     } catch (...) {
487         GTEST_LOG_(ERROR) << "external_file_access_notify_0002 occurs an exception.";
488     }
489     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0002";
490 }
491 
492 /**
493  * @tc.number: user_file_service_external_file_access_notify_0003
494  * @tc.name: external_file_access_notify_0003
495  * @tc.desc: Test function of RegisterNotify and UnregisterNotify interface for SUCCESS.
496  * @tc.size: MEDIUM
497  * @tc.type: FUNC
498  * @tc.level Level 1
499  * @tc.require: SR000H0386
500  */
501 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0003, testing::ext::TestSize.Level1)
502 {
503     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0003";
504     try {
505         vector<RootInfo> info;
506         EXPECT_NE(g_fah, nullptr);
507         int result = g_fah->GetRoots(info);
508         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
509         bool notifyForDescendants = true;
510         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
511         sptr<IFileAccessObserver> myObserver2 = sptr(new (std::nothrow) MyObserver());
512         Uri parentUri(info[1].uri);
513         Uri newDirUriTest1("");
514         result = g_fah->Mkdir(parentUri, "uri_dir1", newDirUriTest1);
515         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
516         Uri newFileUri1("");
517         result = g_fah->CreateFile(parentUri, "uri_file1", newFileUri1);
518         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
519         result = g_fah->RegisterNotify(newDirUriTest1, notifyForDescendants, myObserver1);
520         EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
521         result = g_fah->RegisterNotify(newDirUriTest1, notifyForDescendants, myObserver1);
522         EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
523 
524         result = g_fah->RegisterNotify(newFileUri1, notifyForDescendants, myObserver2);
525         EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
526         result = g_fah->RegisterNotify(newFileUri1, notifyForDescendants, myObserver2);
527         EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
528         result = g_fah->UnregisterNotify(newDirUriTest1);
529         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
530         result = g_fah->UnregisterNotify(newFileUri1);
531         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
532         result = g_fah->Delete(newDirUriTest1);
533         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
534         result = g_fah->Delete(newFileUri1);
535         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
536     } catch (...) {
537         GTEST_LOG_(ERROR) << "external_file_access_notify_0003 occurs an exception.";
538     }
539     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0003";
540 }
541 
ReadyRegisterNotify05(Uri & parentUri,sptr<IFileAccessObserver> & myObserver1)542 static tuple<Uri, Uri, Uri, Uri> ReadyRegisterNotify05(Uri& parentUri, sptr<IFileAccessObserver>& myObserver1)
543 {
544     bool notifyForDescendants = true;
545     Uri uri_dir("");
546     EXPECT_NE(g_fah, nullptr);
547     int result = g_fah->Mkdir(parentUri, "uri_dir123", uri_dir);
548     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
549     Uri uri_dirSub1("");
550     result = g_fah->Mkdir(uri_dir, "uri_dirSub1", uri_dirSub1);
551     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
552     result = g_fah->RegisterNotify(uri_dir, notifyForDescendants, myObserver1);
553     EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
554     result = g_fah->RegisterNotify(uri_dirSub1, notifyForDescendants, myObserver1);
555     EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
556     Uri uri_dirSub2("");
557     result = g_fah->Mkdir(uri_dir, "uri_dirSub2", uri_dirSub2);
558     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
559     usleep(SLEEP_TIME);
560     EXPECT_EQ(g_notifyEvent, ADD_EVENT);
561     EXPECT_EQ(g_notifyUri, uri_dirSub2.ToString());
562     result = g_fah->RegisterNotify(uri_dirSub2, notifyForDescendants, myObserver1);
563     EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
564     Uri renameDirUri1("");
565     result = g_fah->Rename(uri_dirSub2, "renameDir1", renameDirUri1);
566     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
567     usleep(SLEEP_TIME);
568     return {uri_dir, uri_dirSub1, uri_dirSub2, renameDirUri1};
569 }
570 
571 /**
572  * @tc.number: user_file_service_external_file_access_notify_0005
573  * @tc.name: external_file_access_notify_0005
574  * @tc.desc: Test function of RegisterNotify and UnregisterNotify interface for SUCCESS.
575  * @tc.size: MEDIUM
576  * @tc.type: FUNC
577  * @tc.level Level 1
578  * @tc.require: SR000H0386
579  */
580 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0005, testing::ext::TestSize.Level1)
581 {
582     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0005";
583     try {
584         vector<RootInfo> info;
585         EXPECT_NE(g_fah, nullptr);
586         int result = g_fah->GetRoots(info);
587         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
588         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
589         Uri parentUri(info[1].uri);
590         auto [uri_dir, uri_dirSub1, uri_dirSub2, renameDirUri1] = ReadyRegisterNotify05(parentUri, myObserver1);
591         if (g_notifyEvent != MOVED_TO) {
592             if (g_notifyEvent != MOVED_SELF) {
593                 EXPECT_EQ(g_notifyEvent, MOVED_FROM);
594                 EXPECT_EQ(g_notifyUri, uri_dirSub2.ToString());
595             } else {
596                 EXPECT_EQ(g_notifyEvent, MOVED_SELF);
597                 EXPECT_EQ(g_notifyUri, uri_dirSub2.ToString());
598             }
599         } else {
600             EXPECT_EQ(g_notifyEvent, MOVED_TO);
601             EXPECT_EQ(g_notifyUri, renameDirUri1.ToString());
602         }
603         result = g_fah->Delete(uri_dirSub1);
604         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
605         usleep(SLEEP_TIME);
606         EXPECT_EQ(g_notifyEvent, DELETE_EVENT);
607         EXPECT_EQ(g_notifyUri, uri_dirSub1.ToString());
608 
609         sleep(2);
610         result = g_fah->UnregisterNotify(uri_dir, myObserver1);
611         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
612         result = g_fah->Delete(renameDirUri1);
613         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
614         result = g_fah->Delete(uri_dir);
615         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
616         sleep(1);
617     } catch (...) {
618         GTEST_LOG_(ERROR) << "external_file_access_notify_0005 occurs an exception.";
619     }
620     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0005";
621 }
622 
623 /**
624  * @tc.number: user_file_service_external_file_access_notify_0006
625  * @tc.name: external_file_access_notify_0006
626  * @tc.desc: Duplicate UnregisterNotify failed.
627  * @tc.size: MEDIUM
628  * @tc.type: FUNC
629  * @tc.level Level 1
630  * @tc.require: SR000H0386
631  */
632 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0006, testing::ext::TestSize.Level1)
633 {
634     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0006";
635     try {
636         vector<RootInfo> info;
637         EXPECT_NE(g_fah, nullptr);
638         int result = g_fah->GetRoots(info);
639         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
640         bool notifyForDescendants = true;
641         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
642         Uri parentUri(info[1].uri);
643         Uri newFileUri1("");
644         result = g_fah->CreateFile(parentUri, "uri_file", newFileUri1);
645         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
646         result = g_fah->RegisterNotify(newFileUri1, notifyForDescendants, myObserver1);
647         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
648         result = g_fah->Delete(newFileUri1);
649         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
650         usleep(SLEEP_TIME);
651         EXPECT_EQ(g_notifyEvent, DELETE_EVENT);
652         EXPECT_EQ(g_notifyUri, newFileUri1.ToString());
653         sleep(1);
654         result = g_fah->UnregisterNotify(newFileUri1, myObserver1);
655         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
656         result = g_fah->UnregisterNotify(newFileUri1, myObserver1);
657         EXPECT_NE(result, OHOS::FileAccessFwk::ERR_OK);
658     } catch (...) {
659         GTEST_LOG_(ERROR) << "external_file_access_notify_0006 occurs an exception.";
660     }
661     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0006";
662 }
663 
664 /**
665  * @tc.number: user_file_service_external_file_access_notify_0007
666  * @tc.name: external_file_access_notify_0007
667  * @tc.desc: Test function of RegisterNotify and UnregisterNotify failed when callback is Invalid.
668  * @tc.size: MEDIUM
669  * @tc.type: FUNC
670  * @tc.level Level 1
671  * @tc.require: SR000H0386
672  */
673 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0007, testing::ext::TestSize.Level1)
674 {
675     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0007";
676     try {
677         vector<RootInfo> info;
678         EXPECT_NE(g_fah, nullptr);
679         int result = g_fah->GetRoots(info);
680         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
681         sptr<IFileAccessObserver> myObserver1 = nullptr;
682         bool notifyForDescendants = true;
683         Uri parentUri(info[1].uri);
684         Uri newFileUri1("");
685         result = g_fah->CreateFile(parentUri, "uri_file007", newFileUri1);
686         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
687         result = g_fah->RegisterNotify(newFileUri1, notifyForDescendants, myObserver1);
688         EXPECT_NE(result, OHOS::FileAccessFwk::ERR_OK);
689         result = g_fah->UnregisterNotify(newFileUri1, myObserver1);
690         EXPECT_NE(result, OHOS::FileAccessFwk::ERR_OK);
691         result = g_fah->Delete(newFileUri1);
692         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
693     } catch (...) {
694         GTEST_LOG_(ERROR) << "external_file_access_notify_0007 occurs an exception.";
695     }
696     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0007";
697 }
698 
699 /**
700  * @tc.number: user_file_service_external_file_access_notify_0008
701  * @tc.name: external_file_access_notify_0008
702  * @tc.desc: Test function of UnregisterNotify failed when uri is Invalid.
703  * @tc.size: MEDIUM
704  * @tc.type: FUNC
705  * @tc.level Level 1
706  * @tc.require: SR000H0386
707  */
708 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0008, testing::ext::TestSize.Level1)
709 {
710     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0008";
711     try {
712         vector<RootInfo> info;
713         EXPECT_NE(g_fah, nullptr);
714         int result = g_fah->GetRoots(info);
715         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
716         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
717         Uri newFileUri1("*/&%");
718         bool notifyForDescendants = true;
719         result = g_fah->RegisterNotify(newFileUri1, notifyForDescendants, myObserver1);
720         EXPECT_NE(result, OHOS::FileAccessFwk::ERR_OK);
721         result = g_fah->UnregisterNotify(newFileUri1, myObserver1);
722         EXPECT_NE(result, OHOS::FileAccessFwk::ERR_OK);
723     } catch (...) {
724         GTEST_LOG_(ERROR) << "external_file_access_notify_0008 occurs an exception.";
725     }
726     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0008";
727 }
728 
729 /**
730  * @tc.number: user_file_service_external_file_access_notify_0009
731  * @tc.name: external_file_access_notify_0009
732  * @tc.desc: Test function of RegisterNotify and UnregisterNotify interface for SUCCESS when the file is Chinese name.
733  * @tc.size: MEDIUM
734  * @tc.type: FUNC
735  * @tc.level Level 1
736  * @tc.require: SR000H0386
737  */
738 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0009, testing::ext::TestSize.Level1)
739 {
740     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0009";
741     try {
742         vector<RootInfo> info;
743         EXPECT_NE(g_fah, nullptr);
744         int result = g_fah->GetRoots(info);
745         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
746         bool notifyForDescendants = true;
747         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
748         Uri parentUri(info[1].uri);
749         Uri newFileUri1("");
750         result = g_fah->CreateFile(parentUri, "测试文件", newFileUri1);
751         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
752         result = g_fah->RegisterNotify(newFileUri1, notifyForDescendants, myObserver1);
753         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
754         result = g_fah->Delete(newFileUri1);
755         usleep(SLEEP_TIME);
756         EXPECT_EQ(g_notifyEvent, DELETE_EVENT);
757         EXPECT_EQ(g_notifyUri, newFileUri1.ToString());
758         sleep(1);
759         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
760         result = g_fah->UnregisterNotify(newFileUri1, myObserver1);
761         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
762     } catch (...) {
763         GTEST_LOG_(ERROR) << "external_file_access_notify_0009 occurs an exception.";
764     }
765     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0009";
766 }
767 
768 /**
769  * @tc.number: user_file_service_external_file_access_notify_0010
770  * @tc.name: external_file_access_notify_0010
771  * @tc.desc: Test function of UnregisterNotify interface for failed when the Uri and callback do not match.
772  * @tc.size: MEDIUM
773  * @tc.type: FUNC
774  * @tc.level Level 1
775  * @tc.require: SR000H0386
776  */
777 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0010, testing::ext::TestSize.Level1)
778 {
779     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0010";
780     try {
781         vector<RootInfo> info;
782         EXPECT_NE(g_fah, nullptr);
783         int result = g_fah->GetRoots(info);
784         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
785         bool notifyForDescendants = true;
786         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
787         sptr<IFileAccessObserver> myObserver2 = sptr(new (std::nothrow) MyObserver());
788         Uri parentUri(info[1].uri);
789         Uri newFileUri1("");
790         result = g_fah->CreateFile(parentUri, "uri_file1", newFileUri1);
791         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
792         Uri newFileUri2("");
793         result = g_fah->CreateFile(parentUri, "uri_file2", newFileUri2);
794         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
795         result = g_fah->RegisterNotify(newFileUri1, notifyForDescendants, myObserver1);
796         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
797         result = g_fah->RegisterNotify(newFileUri2, notifyForDescendants, myObserver2);
798         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
799 
800         result = g_fah->UnregisterNotify(newFileUri1, myObserver2);
801         EXPECT_NE(result, OHOS::FileAccessFwk::ERR_OK);
802         result = g_fah->UnregisterNotify(newFileUri1, myObserver1);
803         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
804         result = g_fah->UnregisterNotify(newFileUri2, myObserver2);
805         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
806         result = g_fah->Delete(newFileUri1);
807         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
808         result = g_fah->Delete(newFileUri2);
809         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
810     } catch (...) {
811         GTEST_LOG_(ERROR) << "external_file_access_notify_0010 occurs an exception.";
812     }
813     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0010";
814 }
815 
ReadyRegisterNotify11(Uri & parentUri,Uri & newFileDir1,sptr<IFileAccessObserver> & myObserver1,sptr<IFileAccessObserver> & myObserver2)816 static tuple<Uri, Uri> ReadyRegisterNotify11(Uri& parentUri, Uri &newFileDir1, sptr<IFileAccessObserver>& myObserver1,
817     sptr<IFileAccessObserver>& myObserver2)
818 {
819     const int tm = SLEEP_TIME * 2;
820     bool notifyForDescendants1 = true;
821     EXPECT_NE(g_fah, nullptr);
822     int result = g_fah->Mkdir(parentUri, "uri_dir11", newFileDir1);
823     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
824     Uri newFileUri1("");
825     result = g_fah->CreateFile(newFileDir1, "uri_file11", newFileUri1);
826     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
827     sleep(1);
828     result = g_fah->RegisterNotify(newFileDir1, notifyForDescendants1, myObserver1);
829     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
830     result = g_fah->RegisterNotify(newFileUri1, notifyForDescendants1, myObserver2);
831     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
832     Uri renameFileUri1("");
833     result = g_fah->Rename(newFileUri1, "renamefile1", renameFileUri1);
834     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
835     usleep(tm);
836 
837     return {newFileUri1, renameFileUri1};
838 }
839 
840 /**
841  * @tc.number: user_file_service_external_file_access_notify_0011
842  * @tc.name: external_file_access_notify_0011
843  * @tc.desc: Test function of RegisterNotify interface for SUCCESS when set the notifyForDescendants to true and
844  * @tc.desc: then set to false
845  * @tc.size: MEDIUM
846  * @tc.type: FUNC
847  * @tc.level Level 1
848  * @tc.require: SR000H0386
849  */
850 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0011, testing::ext::TestSize.Level1)
851 {
852     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0011";
853     try {
854         vector<RootInfo> info;
855         EXPECT_NE(g_fah, nullptr);
856         int result = g_fah->GetRoots(info);
857         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
858         bool notifyForDescendants2 = false;
859         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) TestObserver());
860         sptr<IFileAccessObserver> myObserver2 = sptr(new (std::nothrow) MyObserver());
861         Uri parentUri(info[1].uri);
862         Uri newFileDir1("");
863         auto [newFileUri1, renameFileUri1] =
864             ReadyRegisterNotify11(parentUri, newFileDir1, myObserver1, myObserver2);
865         usleep(SLEEP_TIME * 2);
866         if (g_notifyEvent != MOVED_TO) {
867             if (g_notifyEvent != MOVED_SELF) {
868                 EXPECT_EQ(g_notifyEvent, MOVED_FROM);
869                 EXPECT_EQ(g_notifyUri, newFileUri1.ToString());
870             } else {
871                 EXPECT_EQ(g_notifyEvent, MOVED_SELF);
872                 EXPECT_EQ(g_notifyUri, newFileUri1.ToString());
873             }
874         } else {
875             EXPECT_EQ(g_notifyEvent, MOVED_TO);
876             EXPECT_EQ(g_notifyUri, renameFileUri1.ToString());
877         }
878         result = g_fah->RegisterNotify(newFileDir1, notifyForDescendants2, myObserver1);
879         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
880         sleep(2);
881         result = g_fah->Delete(renameFileUri1);
882         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
883         usleep(SLEEP_TIME);
884         EXPECT_EQ(g_notifyEvent, DELETE_EVENT);
885         EXPECT_EQ(g_notifyUri, newFileUri1.ToString());
886         EXPECT_NE(g_notifyFlag, DELETE_EVENT);
887 
888         sleep(1);
889         result = g_fah->UnregisterNotify(newFileDir1, myObserver1);
890         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
891         result = g_fah->UnregisterNotify(newFileUri1, myObserver2);
892         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
893         result = g_fah->Delete(newFileDir1);
894         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
895     } catch (...) {
896         GTEST_LOG_(ERROR) << "external_file_access_notify_0011 occurs an exception.";
897     }
898     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0011";
899 }
900 
RegisterDirNotify(Uri parentUri,std::string dirName,IFileAccessObserver * observer)901 static void RegisterDirNotify(Uri parentUri, std::string dirName, IFileAccessObserver *observer)
902 {
903     Uri newDirUriTest("");
904     bool notifyForDescendants = true;
905     EXPECT_NE(g_fah, nullptr);
906     int result = g_fah->Mkdir(parentUri, dirName, newDirUriTest);
907     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
908     sptr<IFileAccessObserver> myObserver(observer);
909     result = g_fah->RegisterNotify(newDirUriTest, notifyForDescendants, myObserver);
910     EXPECT_GE(result, OHOS::FileAccessFwk::ERR_OK);
911     result = g_fah->Delete(newDirUriTest);
912     EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
913     usleep(SLEEP_TIME);
914     EXPECT_EQ(g_notifyEvent, DELETE_EVENT);
915     EXPECT_EQ(g_notifyUri, newDirUriTest.ToString());
916     sleep(2);
917     g_fah->UnregisterNotify(newDirUriTest, myObserver);
918 }
919 
920 /**
921  * @tc.number: user_file_service_external_file_access_notify_0012
922  * @tc.name: external_file_access_notify_0012
923  * @tc.desc: Test function of RegisterNotify and UnregisterNotify interface for SUCCESS which Concurrent.
924  * @tc.size: MEDIUM
925  * @tc.type: FUNC
926  * @tc.level Level 1
927  * @tc.require: SR000H0386
928  */
929 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_00012, testing::ext::TestSize.Level1)
930 {
931     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_00012";
932     try {
933         vector<RootInfo> info;
934         EXPECT_NE(g_fah, nullptr);
935         int result = g_fah->GetRoots(info);
936         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
937         Uri parentUri(info[1].uri);
938         Uri newFileUri1("");
939         GTEST_LOG_(INFO) << parentUri.ToString();
940         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
941         for (int i = 0; i < INIT_THREADS_NUMBER; i++) {
942             std::thread execthread1(RegisterDirNotify, parentUri, "WatcherTest", myObserver1.GetRefPtr());
943             execthread1.join();
944         }
945     } catch (...) {
946         GTEST_LOG_(ERROR) << "external_file_access_notify_00012 occurs an exception.";
947     }
948     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_00012";
949 }
950 
951 /**
952  * @tc.number: user_file_service_external_file_access_notify_0013
953  * @tc.name: external_file_access_notify_0013
954  * @tc.desc: Test function of RegisterNotify and UnregisterNotify interface for SUCCESS which Concurrent.
955  * @tc.size: MEDIUM
956  * @tc.type: FUNC
957  * @tc.level Level 1
958  * @tc.require: SR000H0386
959  */
960 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_00013, testing::ext::TestSize.Level1)
961 {
962     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_00013";
963     try {
964         vector<RootInfo> info;
965         EXPECT_NE(g_fah, nullptr);
966         int result = g_fah->GetRoots(info);
967         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
968         Uri parentUri(info[1].uri);
969         GTEST_LOG_(INFO) << parentUri.ToString();
970         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
971         std::thread execthread1(RegisterDirNotify, parentUri, "WatcherTest1", myObserver1.GetRefPtr());
972         execthread1.join();
973         std::thread execthread2(RegisterDirNotify, parentUri, "WatcherTest2", myObserver1.GetRefPtr());
974         execthread2.join();
975         std::thread execthread3(RegisterDirNotify, parentUri, "WatcherTest3", myObserver1.GetRefPtr());
976         execthread3.join();
977     } catch (...) {
978         GTEST_LOG_(ERROR) << "external_file_access_notify_00013 occurs an exception.";
979     }
980     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_00013";
981 }
982 
983 /**
984  * @tc.number: user_file_service_external_file_access_notify_0014
985  * @tc.name: external_file_access_notify_0014
986  * @tc.desc: Test function of RegisterNotify and UnregisterNotify interface for SUCCESS which Concurrent.
987  * @tc.size: MEDIUM
988  * @tc.type: FUNC
989  * @tc.level Level 1
990  * @tc.require: SR000H0386
991  */
992 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_00014, testing::ext::TestSize.Level1)
993 {
994     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_00014";
995     try {
996         vector<RootInfo> info;
997         EXPECT_NE(g_fah, nullptr);
998         int result = g_fah->GetRoots(info);
999         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1000         Uri parentUri(info[1].uri);
1001         GTEST_LOG_(INFO) << parentUri.ToString();
1002         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
1003         sptr<IFileAccessObserver> myObserver2 = sptr(new (std::nothrow) MyObserver());
1004         sptr<IFileAccessObserver> myObserver3 = sptr(new (std::nothrow) MyObserver());
1005 
1006         std::thread execthread1(RegisterDirNotify, parentUri, "WatcherTest", myObserver1.GetRefPtr());
1007         execthread1.join();
1008         sleep(1);
1009         std::thread execthread2(RegisterDirNotify, parentUri, "WatcherTest", myObserver2.GetRefPtr());
1010         execthread2.join();
1011         sleep(1);
1012         std::thread execthread3(RegisterDirNotify, parentUri, "WatcherTest", myObserver3.GetRefPtr());
1013         execthread3.join();
1014     } catch (...) {
1015         GTEST_LOG_(ERROR) << "external_file_access_notify_00014 occurs an exception.";
1016     }
1017     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_00014";
1018 }
1019 
1020 /**
1021  * @tc.number: user_file_service_external_file_access_notify_0015
1022  * @tc.name: external_file_access_notify_0015
1023  * @tc.desc: Test function of RegisterNotify and UnregisterNotify interface for SUCCESS which Concurrent.
1024  * @tc.size: MEDIUM
1025  * @tc.type: FUNC
1026  * @tc.level Level 1
1027  * @tc.require: SR000H0386
1028  */
1029 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_00015, testing::ext::TestSize.Level1)
1030 {
1031     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_00015";
1032     try {
1033         vector<RootInfo> info;
1034         EXPECT_NE(g_fah, nullptr);
1035         int result = g_fah->GetRoots(info);
1036         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1037         Uri parentUri(info[1].uri);
1038         GTEST_LOG_(INFO) << parentUri.ToString();
1039         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
1040         sptr<IFileAccessObserver> myObserver2 = sptr(new (std::nothrow) MyObserver());
1041         sptr<IFileAccessObserver> myObserver3 = sptr(new (std::nothrow) MyObserver());
1042 
1043         std::thread execthread1(RegisterDirNotify, parentUri, "WatcherTest1", myObserver1.GetRefPtr());
1044         execthread1.join();
1045         std::thread execthread2(RegisterDirNotify, parentUri, "WatcherTest2", myObserver2.GetRefPtr());
1046         execthread2.join();
1047         std::thread execthread3(RegisterDirNotify, parentUri, "WatcherTest3", myObserver3.GetRefPtr());
1048         execthread3.join();
1049     } catch (...) {
1050         GTEST_LOG_(ERROR) << "external_file_access_notify_00015 occurs an exception.";
1051     }
1052     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_00015";
1053 }
1054 
1055 /**
1056  * @tc.number: user_file_service_external_file_access_notify_0016
1057  * @tc.name: external_file_access_notify_0016
1058  * @tc.desc: Test UnregisterNotify all callbacks related to the current uri
1059  * @tc.size: MEDIUM
1060  * @tc.type: FUNC
1061  * @tc.level Level 1
1062  * @tc.require: SR000H0386
1063  */
1064 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0016, testing::ext::TestSize.Level1)
1065 {
1066     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0016";
1067     try {
1068         vector<RootInfo> info;
1069         EXPECT_NE(g_fah, nullptr);
1070         int result = g_fah->GetRoots(info);
1071         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1072         bool notifyForDescendants = true;
1073         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
1074         sptr<IFileAccessObserver> myObserver2 = sptr(new (std::nothrow) MyObserver());
1075         sptr<IFileAccessObserver> myObserver3 = sptr(new (std::nothrow) MyObserver());
1076         Uri parentUri(info[1].uri);
1077         Uri newFileDir1("");
1078         result = g_fah->Mkdir(parentUri, "uri_dir0016", newFileDir1);
1079         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1080         result = g_fah->RegisterNotify(newFileDir1, notifyForDescendants, myObserver1);
1081         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1082         result = g_fah->RegisterNotify(newFileDir1, notifyForDescendants, myObserver2);
1083         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1084         result = g_fah->RegisterNotify(newFileDir1, notifyForDescendants, myObserver3);
1085         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1086 
1087         result = g_fah->UnregisterNotify(newFileDir1);
1088         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1089         result = g_fah->UnregisterNotify(newFileDir1, myObserver1);
1090         EXPECT_NE(result, OHOS::FileAccessFwk::ERR_OK);
1091 
1092         result = g_fah->Delete(newFileDir1);
1093         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1094     } catch (...) {
1095         GTEST_LOG_(ERROR) << "external_file_access_notify_0016 occurs an exception.";
1096     }
1097     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0016";
1098 }
1099 
1100 /**
1101  * @tc.number: user_file_service_external_file_access_notify_0017
1102  * @tc.name: external_file_access_notify_0017
1103  * @tc.desc: Test event changes exceeding 500ms trigger callback
1104  * @tc.size: MEDIUM
1105  * @tc.type: FUNC
1106  * @tc.level Level 1
1107  * @tc.require: SR000H0386
1108  */
1109 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0017, testing::ext::TestSize.Level1)
1110 {
1111     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0017";
1112     try {
1113         vector<RootInfo> info;
1114         EXPECT_NE(g_fah, nullptr);
1115         int result = g_fah->GetRoots(info);
1116         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1117         bool notifyForDescendants = true;
1118         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
1119         Uri parentUri(info[1].uri);
1120         Uri newFileDir1("");
1121         result = g_fah->Mkdir(parentUri, "uri_dir", newFileDir1);
1122         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1123         result = g_fah->RegisterNotify(newFileDir1, notifyForDescendants, myObserver1);
1124         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1125         Uri fileUri("");
1126         result = g_fah->CreateFile(newFileDir1, "uri_file", fileUri);
1127         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1128         usleep(SLEEP_TIME / 10);
1129         EXPECT_NE(g_notifyEvent, ADD_EVENT);
1130         usleep(SLEEP_TIME);
1131         EXPECT_EQ(g_notifyEvent, ADD_EVENT);
1132 
1133         result = g_fah->UnregisterNotify(newFileDir1, myObserver1);
1134         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1135 
1136         result = g_fah->Delete(newFileDir1);
1137         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1138     } catch (...) {
1139         GTEST_LOG_(ERROR) << "external_file_access_notify_0017 occurs an exception.";
1140     }
1141     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0017";
1142 }
1143 
1144 /**
1145  * @tc.number: user_file_service_external_file_access_notify_0018
1146  * @tc.name: external_file_access_notify_0018
1147  * @tc.desc: Test event changes More than 32 notifications callback
1148  * @tc.size: MEDIUM
1149  * @tc.type: FUNC
1150  * @tc.level Level 1
1151  * @tc.require: SR000H0386
1152  */
1153 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0018, testing::ext::TestSize.Level1)
1154 {
1155     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0018";
1156     try {
1157         vector<RootInfo> info;
1158         EXPECT_NE(g_fah, nullptr);
1159         int result = g_fah->GetRoots(info);
1160         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1161         bool notifyForDescendants = true;
1162         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) TestObserver());
1163         Uri parentUri(info[1].uri);
1164         Uri newFileDir1("");
1165         result = g_fah->Mkdir(parentUri, "uri_dir", newFileDir1);
1166         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1167         result = g_fah->RegisterNotify(newFileDir1, notifyForDescendants, myObserver1);
1168         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1169         Uri fileUri("");
1170         for (int i = 0; i < 64; i++) {
1171             result = g_fah->CreateFile(newFileDir1, "uri_file" + to_string(i), fileUri);
1172             EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1173         }
1174         sleep(1);
1175         EXPECT_LE(g_notifyUris.size(), 32);
1176         g_notifyUris.clear();
1177         result = g_fah->UnregisterNotify(newFileDir1, myObserver1);
1178         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1179 
1180         result = g_fah->Delete(newFileDir1);
1181         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1182     } catch (...) {
1183         GTEST_LOG_(ERROR) << "external_file_access_notify_0018 occurs an exception.";
1184     }
1185     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0018";
1186 }
1187 
1188 /**
1189  * @tc.number: user_file_service_external_file_access_notify_0019
1190  * @tc.name: external_file_access_notify_0019
1191  * @tc.desc: Test event changes More than one notifications callback
1192  * @tc.size: MEDIUM
1193  * @tc.type: FUNC
1194  * @tc.level Level 1
1195  * @tc.require: SR000H0386
1196  */
1197 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0019, testing::ext::TestSize.Level1)
1198 {
1199     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0019";
1200     try {
1201         vector<RootInfo> info;
1202         EXPECT_NE(g_fah, nullptr);
1203         int result = g_fah->GetRoots(info);
1204         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1205         bool notifyForDescendants = true;
1206         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) TestObserver());
1207         Uri parentUri(info[1].uri);
1208         Uri newFileDir1("");
1209         result = g_fah->Mkdir(parentUri, "uri_dir", newFileDir1);
1210         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1211         result = g_fah->RegisterNotify(newFileDir1, notifyForDescendants, myObserver1);
1212         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1213         Uri fileUri("");
1214         for (int i = 0; i < 10; i++) {
1215             result = g_fah->CreateFile(newFileDir1, "uri_file" + to_string(i), fileUri);
1216             EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1217         }
1218         usleep(SLEEP_TIME);
1219         EXPECT_GT(g_notifyUris.size(), 1);
1220         g_notifyUris.clear();
1221         result = g_fah->UnregisterNotify(newFileDir1, myObserver1);
1222         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1223 
1224         result = g_fah->Delete(newFileDir1);
1225         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1226     } catch (...) {
1227         GTEST_LOG_(ERROR) << "external_file_access_notify_0019 occurs an exception.";
1228     }
1229     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0019";
1230 }
1231 
1232 HWTEST_F(FileExtensionNotifyTest, external_file_access_notify_0020, testing::ext::TestSize.Level1)
1233 {
1234     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-begin external_file_access_notify_0020";
1235     try {
1236         g_notifyEvent = -1;
1237         vector<RootInfo> info;
1238         const char* perms[] = {
1239             "ohos.permission.GET_BUNDLE_INFO_PRIVILEGED"
1240         };
1241         SetNativeToken("SetUpTestCase", perms, sizeof(perms) / sizeof(perms[0]));
1242         EXPECT_NE(g_fah, nullptr);
1243         int result = g_fah->GetRoots(info);
1244         EXPECT_EQ(result, OHOS::FileAccessFwk::E_PERMISSION);
1245         SetNativeToken();
1246         result = g_fah->GetRoots(info);
1247         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1248 
1249         bool notifyForDescendants = true;
1250         sptr<IFileAccessObserver> myObserver1 = sptr(new (std::nothrow) MyObserver());
1251         Uri parentUri(info[1].uri);
1252         Uri newFileDir1("");
1253         SetNativeToken("SetUpTestCase", perms, sizeof(perms) / sizeof(perms[0]));
1254         result = g_fah->Mkdir(parentUri, "uri_dir", newFileDir1);
1255         EXPECT_EQ(result, OHOS::FileAccessFwk::E_PERMISSION);
1256         SetNativeToken();
1257         result = g_fah->Mkdir(parentUri, "uri_dir", newFileDir1);
1258         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1259 
1260         SetNativeToken("SetUpTestCase", perms, sizeof(perms) / sizeof(perms[0]));
1261         result = g_fah->RegisterNotify(newFileDir1, notifyForDescendants, myObserver1);
1262         EXPECT_EQ(result, OHOS::FileAccessFwk::E_PERMISSION);
1263 
1264         result = g_fah->UnregisterNotify(newFileDir1, myObserver1);
1265         EXPECT_EQ(result, OHOS::FileAccessFwk::E_PERMISSION);
1266 
1267         result = g_fah->Delete(newFileDir1);
1268         EXPECT_EQ(result, OHOS::FileAccessFwk::E_PERMISSION);
1269 
1270         SetNativeToken();
1271         result = g_fah->Delete(newFileDir1);
1272         EXPECT_EQ(result, OHOS::FileAccessFwk::ERR_OK);
1273 
1274     } catch (...) {
1275         GTEST_LOG_(ERROR) << "external_file_access_notify_0020 occurs an exception.";
1276     }
1277     GTEST_LOG_(INFO) << "FileExtensionNotifyTest-end external_file_access_notify_0020";
1278 }
1279 } // namespace