1 /**
2 * Copyright (c) 2025 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 <cassert>
17 #include <cstring>
18 #include <gtest/gtest.h>
19
20 #include "libabckit/include/c/abckit.h"
21 #include "helpers/helpers.h"
22 #include "libabckit/include/c/metadata_core.h"
23 #include "libabckit/include/c/extensions/arkts/metadata_arkts.h"
24 #include "helpers/visit_helper/visit_helper-inl.h"
25
26 namespace libabckit::test {
27
28 static auto g_impl = AbckitGetApiImpl(ABCKIT_VERSION_RELEASE_1_0_0);
29 static auto g_implI = AbckitGetInspectApiImpl(ABCKIT_VERSION_RELEASE_1_0_0);
30 static auto g_implG = AbckitGetGraphApiImpl(ABCKIT_VERSION_RELEASE_1_0_0);
31 static auto g_implArktsI = AbckitGetArktsInspectApiImpl(ABCKIT_VERSION_RELEASE_1_0_0);
32
33 class LibAbcKitInspectApiMethodsTest : public ::testing::Test {};
34
35 // ========================================
36 // Helpers
37 // ========================================
38
MethodGetModuleTest(AbckitFile * file,const char * methodName)39 static std::string_view MethodGetModuleTest(AbckitFile *file, const char *methodName)
40 {
41 auto *method = helpers::FindMethodByName(file, methodName);
42 auto *sourceRaw = g_implI->moduleGetName(g_implI->functionGetModule(method));
43 return helpers::AbckitStringToString(sourceRaw);
44 }
45
46 // ========================================
47 // Methods Tests
48 // ========================================
49
50 // Test: test-kind=api, api=InspectApiImpl::functionGetName, abc-kind=ArkTS2, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,StaticMethodGetName)51 TEST_F(LibAbcKitInspectApiMethodsTest, StaticMethodGetName)
52 {
53 AbckitFile *file = nullptr;
54 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_static.abc", &file);
55
56 std::set<std::string> names = {
57 "main:void;",
58 "m0F0:void;",
59 "m0F1:void;",
60 "m0F2$asyncimpl:std.core.Object;",
61 "m0F2:std.core.Promise;",
62 "m0N0F0:void;",
63 "m0N0F1:void;",
64 "m0N0F2$asyncimpl:std.core.Object;",
65 "m0N0F2:std.core.Promise;",
66 "m0N0N0F0:void;",
67 "_cctor_:void;",
68 "lambda$invoke$0:void;",
69 "lambda$invoke$1:void;",
70 "M0C0F0:methods_static.M0C0;void;",
71 "M0C0F1:void;",
72 "M0C0F2$asyncimpl:methods_static.M0C0;std.core.Object;",
73 "M0C0F2:methods_static.M0C0;std.core.Promise;",
74 "_ctor_:methods_static.M0C0;void;",
75 "M0N0C0F0:methods_static.M0N0C0;void;",
76 "M0N0C0F1:void;",
77 "M0N0C0F2$asyncimpl:methods_static.M0N0C0;std.core.Object;",
78 "M0N0C0F2:methods_static.M0N0C0;std.core.Promise;",
79 "_ctor_:methods_static.M0N0C0;void;",
80 };
81
82 helpers::EnumerateAllMethods(file, [&](AbckitCoreFunction *m) {
83 auto *abckitname = g_implI->functionGetName(m);
84 EXPECT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
85 EXPECT_NE(abckitname, nullptr);
86 auto name = helpers::AbckitStringToString(abckitname);
87 EXPECT_EQ(names.count(name.data()), 1);
88 names.erase(name.data());
89 });
90 ASSERT_TRUE(names.empty());
91
92 g_impl->closeFile(file);
93 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
94 }
95
96 // Test: test-kind=api, api=InspectApiImpl::functionGetName, abc-kind=ArkTS1, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,DynamicFunctionGetName)97 TEST_F(LibAbcKitInspectApiMethodsTest, DynamicFunctionGetName)
98 {
99 AbckitFile *file = nullptr;
100 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_dynamic.abc", &file);
101
102 std::set<std::string> names = {
103 "M0C0",
104 "M0C0F1",
105 "M0C0F0",
106 "M0C0F2",
107 "M0N0C0",
108 "M0N0C0F1",
109 "M0N0C0F0",
110 "M0N0C0F2",
111 "m0N0N0F0",
112 "m0N0F0",
113 "m0N0F1",
114 "m0N0F2",
115 "m0F0",
116 "methods_dynamic.#*@0*#m0F0F0",
117 "m0F1",
118 "m0F2",
119 "methods_dynamic.#*@0*#",
120 "methods_dynamic.#*@0*#^1",
121 "func_main_0",
122 };
123
124 helpers::EnumerateAllMethods(file, [&](AbckitCoreFunction *m) {
125 auto *abckitname = g_implI->functionGetName(m);
126 EXPECT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
127 EXPECT_NE(abckitname, nullptr);
128 auto name = helpers::AbckitStringToString(abckitname);
129 EXPECT_EQ(names.count(name.data()), 1);
130 names.erase(name.data());
131 });
132 ASSERT_TRUE(names.empty());
133
134 g_impl->closeFile(file);
135 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
136 }
137
138 // Test: test-kind=api, api=InspectApiImpl::functionGetFile, abc-kind=ArkTS2, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,FunctionGetFile)139 TEST_F(LibAbcKitInspectApiMethodsTest, FunctionGetFile)
140 {
141 AbckitFile *file = nullptr;
142 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_static.abc", &file);
143
144 g_implI->fileEnumerateModules(file, nullptr, [](AbckitCoreModule *m, [[maybe_unused]] void *data) -> bool {
145 helpers::ClassByNameContext ctxClassFinder = {nullptr, "M0C0"};
146 g_implI->moduleEnumerateClasses(m, &ctxClassFinder, helpers::ClassByNameFinder);
147 EXPECT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
148 EXPECT_NE(ctxClassFinder.klass, nullptr);
149
150 helpers::MethodByNameContext ctxMethodFinder = {nullptr, "M0C0F0"};
151 g_implI->classEnumerateMethods(ctxClassFinder.klass, &ctxMethodFinder, helpers::MethodByNameFinder);
152 EXPECT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
153 EXPECT_NE(ctxMethodFinder.method, nullptr);
154
155 auto *ctxClass = g_implI->classGetFile(ctxClassFinder.klass);
156 auto *ctxMethod = g_implI->functionGetFile(ctxMethodFinder.method);
157 EXPECT_EQ(ctxClass, ctxMethod);
158
159 return true;
160 });
161
162 g_impl->closeFile(file);
163 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
164 }
165
166 // Test: test-kind=api, api=InspectApiImpl::functionGetFile, abc-kind=ArkTS1, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,DynamicFunctionGetFile)167 TEST_F(LibAbcKitInspectApiMethodsTest, DynamicFunctionGetFile)
168 {
169 AbckitFile *file = nullptr;
170 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_dynamic.abc", &file);
171
172 g_implI->fileEnumerateModules(file, nullptr, [](AbckitCoreModule *m, [[maybe_unused]] void *data) -> bool {
173 helpers::ClassByNameContext ctxClassFinder = {nullptr, "M0C0"};
174 g_implI->moduleEnumerateClasses(m, &ctxClassFinder, helpers::ClassByNameFinder);
175 EXPECT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
176 EXPECT_NE(ctxClassFinder.klass, nullptr);
177
178 helpers::MethodByNameContext ctxMethodFinder = {nullptr, "M0C0F0"};
179 g_implI->classEnumerateMethods(ctxClassFinder.klass, &ctxMethodFinder, helpers::MethodByNameFinder);
180 EXPECT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
181 EXPECT_NE(ctxMethodFinder.method, nullptr);
182
183 auto *ctxClass = g_implI->classGetFile(ctxClassFinder.klass);
184 auto *ctxMethod = g_implI->functionGetFile(ctxMethodFinder.method);
185 EXPECT_EQ(ctxClass, ctxMethod);
186
187 return true;
188 });
189
190 g_impl->closeFile(file);
191 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
192 }
193
194 // Test: test-kind=api, api=InspectApiImpl::functionIsCtor, abc-kind=ArkTS1, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,DynamicFunctionIsCtor)195 TEST_F(LibAbcKitInspectApiMethodsTest, DynamicFunctionIsCtor)
196 {
197 AbckitFile *file = nullptr;
198 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_dynamic.abc", &file);
199
200 std::set<std::string> ctorMethods = {
201 "M0C0",
202 "M0N0C0",
203 };
204
205 helpers::EnumerateAllMethods(file, [&ctorMethods](AbckitCoreFunction *method) {
206 auto methodName = helpers::AbckitStringToString(g_implI->functionGetName(method));
207 bool isCtor = g_implI->functionIsCtor(method);
208 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
209 if (isCtor) {
210 EXPECT_EQ(ctorMethods.count(methodName.data()), 1);
211 ctorMethods.erase(methodName.data());
212 } else {
213 EXPECT_EQ(ctorMethods.count(methodName.data()), 0);
214 }
215 });
216 ASSERT_TRUE(ctorMethods.empty());
217
218 g_impl->closeFile(file);
219 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
220 }
221
222 // Test: test-kind=api, api=InspectApiImpl::functionIsCtor, abc-kind=ArkTS2, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,StaticFunctionIsCtor)223 TEST_F(LibAbcKitInspectApiMethodsTest, StaticFunctionIsCtor)
224 {
225 AbckitFile *file = nullptr;
226 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_static.abc", &file);
227
228 std::set<std::string> ctorMethods = {"_ctor_:methods_static.M0C0;void;", "_ctor_:methods_static.M0N0C0;void;"};
229
230 helpers::EnumerateAllMethods(file, [&ctorMethods](AbckitCoreFunction *method) {
231 auto methodName = helpers::AbckitStringToString(g_implI->functionGetName(method));
232 bool isCtor = g_implI->functionIsCtor(method);
233 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
234 if (isCtor) {
235 EXPECT_EQ(ctorMethods.count(methodName.data()), 1);
236 ctorMethods.erase(methodName.data());
237 } else {
238 EXPECT_EQ(ctorMethods.count(methodName.data()), 0);
239 }
240 });
241 ASSERT_TRUE(ctorMethods.empty());
242
243 g_impl->closeFile(file);
244 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
245 }
246
247 // Test: test-kind=api, api=InspectApiImpl::functionIsStatic, abc-kind=ArkTS1, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,DynamicFunctionIsStatic)248 TEST_F(LibAbcKitInspectApiMethodsTest, DynamicFunctionIsStatic)
249 {
250 AbckitFile *file = nullptr;
251 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_dynamic.abc", &file);
252
253 std::set<std::string> staticMethods = {
254 "M0C0F1",
255 "M0N0C0F1",
256 "m0N0N0F0",
257 "m0N0F0",
258 "m0N0F1",
259 "m0N0F2",
260 "m0F0",
261 "methods_dynamic.#*@0*#m0F0F0",
262 "m0F1",
263 "m0F2",
264 "methods_dynamic.#*@0*#",
265 "methods_dynamic.#*@0*#^1",
266 "func_main_0",
267 };
268
269 helpers::EnumerateAllMethods(file, [&staticMethods](AbckitCoreFunction *method) {
270 auto methodName = helpers::AbckitStringToString(g_implI->functionGetName(method));
271 bool isStatic = g_implI->functionIsStatic(method);
272 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
273 if (isStatic) {
274 EXPECT_EQ(staticMethods.count(methodName.data()), 1);
275 staticMethods.erase(methodName.data());
276 } else {
277 EXPECT_EQ(staticMethods.count(methodName.data()), 0);
278 }
279 });
280 ASSERT_TRUE(staticMethods.empty());
281
282 g_impl->closeFile(file);
283 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
284 }
285
286 // Test: test-kind=api, api=InspectApiImpl::functionIsStatic, abc-kind=ArkTS2, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,StaticFunctionIsStatic)287 TEST_F(LibAbcKitInspectApiMethodsTest, StaticFunctionIsStatic)
288 {
289 AbckitFile *file = nullptr;
290 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_static.abc", &file);
291
292 std::set<std::string> staticMethods = {
293 "main:void;",
294 "M0N0C0F1:void;",
295 "M0C0F1:void;",
296 "m0F0:void;",
297 "m0F1:void;",
298 "m0F2$asyncimpl:std.core.Object;",
299 "m0F2:std.core.Promise;",
300 "m0N0F0:void;",
301 "m0N0F1:void;",
302 "m0N0F2$asyncimpl:std.core.Object;",
303 "m0N0F2:std.core.Promise;",
304 "m0N0N0F0:void;",
305 "_cctor_:void;",
306 "lambda$invoke$0:void;",
307 "lambda$invoke$1:void;",
308 };
309
310 helpers::EnumerateAllMethods(file, [&staticMethods](AbckitCoreFunction *method) {
311 auto methodName = helpers::AbckitStringToString(g_implI->functionGetName(method));
312 bool isStatic = g_implI->functionIsStatic(method);
313 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
314 if (isStatic) {
315 EXPECT_EQ(staticMethods.count(methodName.data()), 1);
316 staticMethods.erase(methodName.data());
317 } else {
318 EXPECT_EQ(staticMethods.count(methodName.data()), 0);
319 }
320 });
321 ASSERT_TRUE(staticMethods.empty());
322
323 g_impl->closeFile(file);
324 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
325 }
326
327 // Test: test-kind=api, api=InspectApiImpl::functionIsAnonymous, abc-kind=ArkTS1, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,DynamicFunctionIsAnonymous)328 TEST_F(LibAbcKitInspectApiMethodsTest, DynamicFunctionIsAnonymous)
329 {
330 AbckitFile *file = nullptr;
331 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_dynamic.abc", &file);
332
333 std::set<std::string> anonymousMethods = {
334 "methods_dynamic.#*@0*#",
335 "methods_dynamic.#*@0*#^1",
336 "methods_dynamic.#*@0*#m0F0F0",
337 };
338
339 helpers::EnumerateAllMethods(file, [&anonymousMethods](AbckitCoreFunction *method) {
340 auto methodName = helpers::AbckitStringToString(g_implI->functionGetName(method));
341 bool isAnonymous = g_implI->functionIsAnonymous(method);
342 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
343 if (isAnonymous) {
344 EXPECT_EQ(anonymousMethods.count(methodName.data()), 1);
345 anonymousMethods.erase(methodName.data());
346 } else {
347 EXPECT_EQ(anonymousMethods.count(methodName.data()), 0);
348 }
349 });
350 ASSERT_TRUE(anonymousMethods.empty());
351
352 g_impl->closeFile(file);
353 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
354 }
355
356 // Test: test-kind=api, api=InspectApiImpl::functionIsAnonymous, abc-kind=ArkTS2, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,StaticFunctionIsAnonymous)357 TEST_F(LibAbcKitInspectApiMethodsTest, StaticFunctionIsAnonymous)
358 {
359 AbckitFile *file = nullptr;
360 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_static.abc", &file);
361
362 std::set<std::string> anonymousMethods = {
363 "lambda$invoke$0:void;",
364 "lambda$invoke$1:void;",
365 };
366
367 helpers::EnumerateAllMethods(file, [&anonymousMethods](AbckitCoreFunction *method) {
368 auto methodName = helpers::AbckitStringToString(g_implI->functionGetName(method));
369 bool isAnonymous = g_implI->functionIsAnonymous(method);
370 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
371 if (isAnonymous) {
372 EXPECT_EQ(anonymousMethods.count(methodName.data()), 1);
373 anonymousMethods.erase(methodName.data());
374 } else {
375 EXPECT_EQ(anonymousMethods.count(methodName.data()), 0);
376 }
377 anonymousMethods.erase(methodName.data());
378 });
379 ASSERT_TRUE(anonymousMethods.empty());
380
381 g_impl->closeFile(file);
382 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
383 }
384
385 // Test: test-kind=api, api=InspectApiImpl::functionGetParentFunction, abc-kind=ArkTS1, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,DynamicFunctionGetParentFunction)386 TEST_F(LibAbcKitInspectApiMethodsTest, DynamicFunctionGetParentFunction)
387 {
388 AbckitFile *file = nullptr;
389 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_dynamic.abc", &file);
390
391 std::unordered_map<std::string, std::string> parentFunctions = {
392 {"M0C0F1", ""},
393 {"M0C0", ""},
394 {"M0C0F0", ""},
395 {"M0C0F2", ""},
396 {"M0N0C0F1", ""},
397 {"M0N0C0", ""},
398 {"M0N0C0F0", ""},
399 {"M0N0C0F2", ""},
400 {"m0N0N0F0", ""},
401 {"m0N0F0", ""},
402 {"m0N0F1", ""},
403 {"m0N0F2", ""},
404 {"m0F0", ""},
405 {"methods_dynamic.#*@0*#m0F0F0", ""},
406 {"m0F1", ""},
407 {"m0F2", ""},
408 {"methods_dynamic.#*@0*#", ""},
409 {"methods_dynamic.#*@0*#^1", ""},
410 {"func_main_0", ""},
411 };
412
413 helpers::EnumerateAllMethods(file, [&parentFunctions](AbckitCoreFunction *method) {
414 auto methodName = helpers::AbckitStringToString(g_implI->functionGetName(method));
415 ASSERT_EQ(parentFunctions.count(methodName.data()), 1);
416 AbckitCoreFunction *parentFunction = g_implI->functionGetParentFunction(method);
417 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
418 if (parentFunction == nullptr) {
419 ASSERT_EQ(parentFunctions.at(methodName.data()), "");
420 } else {
421 auto className = helpers::AbckitStringToString(g_implI->functionGetName(parentFunction));
422 ASSERT_EQ(parentFunctions.at(methodName.data()), className);
423 }
424 parentFunctions.erase(methodName.data());
425 });
426 ASSERT_TRUE(parentFunctions.empty());
427
428 g_impl->closeFile(file);
429 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
430 }
431
432 // Test: test-kind=api, api=InspectApiImpl::functionGetParentClass, abc-kind=ArkTS1, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,DynamicFunctionGetParentClass)433 TEST_F(LibAbcKitInspectApiMethodsTest, DynamicFunctionGetParentClass)
434 {
435 AbckitFile *file = nullptr;
436 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_dynamic.abc", &file);
437
438 std::unordered_map<std::string, std::string> methodClasses = {
439 {"M0C0F1", "M0C0"},
440 {"M0C0", "M0C0"},
441 {"M0C0F0", "M0C0"},
442 {"M0C0F2", "M0C0"},
443 {"M0N0C0F1", "M0N0C0"},
444 {"M0N0C0", "M0N0C0"},
445 {"M0N0C0F0", "M0N0C0"},
446 {"M0N0C0F2", "M0N0C0"},
447 {"m0N0N0F0", ""},
448 {"m0N0F0", ""},
449 {"m0N0F1", ""},
450 {"m0N0F2", ""},
451 {"m0F0", ""},
452 {"m0F1", ""},
453 {"m0F2", ""},
454 {"methods_dynamic.#*@0*#m0F0F0", ""},
455 {"methods_dynamic.#*@0*#", ""},
456 {"methods_dynamic.#*@0*#^1", ""},
457 {"func_main_0", ""},
458 };
459
460 helpers::EnumerateAllMethods(file, [&methodClasses](AbckitCoreFunction *method) {
461 auto methodName = helpers::AbckitStringToString(g_implI->functionGetName(method));
462 ASSERT_EQ(methodClasses.count(methodName.data()), 1);
463 AbckitCoreClass *methodClass = g_implI->functionGetParentClass(method);
464 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
465 if (methodClass == nullptr) {
466 ASSERT_EQ(methodClasses.at(methodName.data()), "");
467 } else {
468 auto className = helpers::AbckitStringToString(g_implI->classGetName(methodClass));
469 ASSERT_EQ(methodClasses.at(methodName.data()), className);
470 }
471 methodClasses.erase(methodName.data());
472 });
473 ASSERT_TRUE(methodClasses.empty());
474
475 g_impl->closeFile(file);
476 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
477 }
478
479 // Test: test-kind=api, api=InspectApiImpl::functionGetParentClass, abc-kind=ArkTS2, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,StaticFunctionGetParentClass)480 TEST_F(LibAbcKitInspectApiMethodsTest, StaticFunctionGetParentClass)
481 {
482 AbckitFile *file = nullptr;
483 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_static.abc", &file);
484
485 std::unordered_map<std::string, std::string> methodClasses = {
486 {"main:void;", ""},
487 {"m0F0:void;", ""},
488 {"m0F1:void;", ""},
489 {"m0F2$asyncimpl:std.core.Object;", ""},
490 {"m0F2:std.core.Promise;", ""},
491 {"m0N0F0:void;", ""},
492 {"m0N0F1:void;", ""},
493 {"m0N0F2$asyncimpl:std.core.Object;", ""},
494 {"m0N0F2:std.core.Promise;", ""},
495 {"m0N0N0F0:void;", ""},
496 {"_cctor_:void;", ""},
497 {"lambda$invoke$0:void;", ""},
498 {"lambda$invoke$1:void;", ""},
499 {"M0C0F0:methods_static.M0C0;void;", "M0C0"},
500 {"M0C0F1:void;", "M0C0"},
501 {"M0C0F2$asyncimpl:methods_static.M0C0;std.core.Object;", "M0C0"},
502 {"M0C0F2:methods_static.M0C0;std.core.Promise;", "M0C0"},
503 {"_ctor_:methods_static.M0C0;void;", "M0C0"},
504 {"M0N0C0F0:methods_static.M0N0C0;void;", "M0N0C0"},
505 {"M0N0C0F1:void;", "M0N0C0"},
506 {"M0N0C0F2$asyncimpl:methods_static.M0N0C0;std.core.Object;", "M0N0C0"},
507 {"M0N0C0F2:methods_static.M0N0C0;std.core.Promise;", "M0N0C0"},
508 {"_ctor_:methods_static.M0N0C0;void;", "M0N0C0"},
509 };
510
511 helpers::EnumerateAllMethods(file, [&methodClasses](AbckitCoreFunction *method) {
512 auto methodName = helpers::AbckitStringToString(g_implI->functionGetName(method));
513 ASSERT_EQ(methodClasses.count(methodName.data()), 1);
514 AbckitCoreClass *methodClass = g_implI->functionGetParentClass(method);
515 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
516 if (methodClass == nullptr) {
517 ASSERT_EQ(methodClasses.at(methodName.data()), "");
518 } else {
519 auto className = helpers::AbckitStringToString(g_implI->classGetName(methodClass));
520 ASSERT_EQ(methodClasses.at(methodName.data()), className);
521 }
522 methodClasses.erase(methodName.data());
523 });
524 ASSERT_TRUE(methodClasses.empty());
525
526 g_impl->closeFile(file);
527 ASSERT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
528 }
529
530 // Test: test-kind=api, api=InspectApiImpl::functionGetModule, abc-kind=ArkTS2, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,StaticFunctionGetModule)531 TEST_F(LibAbcKitInspectApiMethodsTest, StaticFunctionGetModule)
532 {
533 AbckitFile *file = nullptr;
534 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_static.abc", &file);
535 auto moduleName = MethodGetModuleTest(file, "m0F0");
536 ASSERT_EQ("methods_static", moduleName);
537 g_impl->closeFile(file);
538 }
539
540 // Test: test-kind=api, api=InspectApiImpl::functionGetModule, abc-kind=ArkTS1, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,DynamicFunctionGetModule)541 TEST_F(LibAbcKitInspectApiMethodsTest, DynamicFunctionGetModule)
542 {
543 AbckitFile *file = nullptr;
544 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/methods_dynamic.abc", &file);
545 auto moduleName = MethodGetModuleTest(file, "m0F0");
546 ASSERT_EQ("methods_dynamic", moduleName);
547 g_impl->closeFile(file);
548 }
549
550 // Test: test-kind=api, api=ArktsInspectApiImpl::functionIsNative, abc-kind=ArkTS2, category=positive, extension=c
TEST_F(LibAbcKitInspectApiMethodsTest,StaticMethodIsNative)551 TEST_F(LibAbcKitInspectApiMethodsTest, StaticMethodIsNative)
552 {
553 AbckitFile *file = nullptr;
554 helpers::AssertOpenAbc(ABCKIT_ABC_DIR "ut/metadata_core/inspect_api/methods/native_method.abc", &file);
555
556 g_implI->fileEnumerateModules(file, nullptr, [](AbckitCoreModule *m, [[maybe_unused]] void *data) {
557 helpers::ClassByNameContext ctxFinder = {nullptr, "Y"};
558 g_implI->moduleEnumerateClasses(m, &ctxFinder, helpers::ClassByNameFinder);
559 EXPECT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
560 EXPECT_NE(ctxFinder.klass, nullptr);
561
562 helpers::MethodByNameContext methodCtxFinder = {nullptr, "bar"};
563 g_implI->classEnumerateMethods(ctxFinder.klass, &methodCtxFinder, helpers::MethodByNameFinder);
564 EXPECT_EQ(g_impl->getLastError(), ABCKIT_STATUS_NO_ERROR);
565 EXPECT_NE(methodCtxFinder.method, nullptr);
566
567 AbckitArktsFunction *methodArkTS = g_implArktsI->coreFunctionToArktsFunction(methodCtxFinder.method);
568 bool isAbstract = g_implArktsI->functionIsNative(methodArkTS);
569 EXPECT_EQ(isAbstract, true);
570
571 return true;
572 });
573
574 g_impl->closeFile(file);
575 }
576
577 } // namespace libabckit::test
578