• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "ecmascript/builtins/builtins_displaynames.h"
17 
18 #include "ecmascript/global_env.h"
19 #include "ecmascript/js_displaynames.h"
20 #include "ecmascript/tests/test_helper.h"
21 
22 using namespace panda::ecmascript;
23 using namespace panda::ecmascript::builtins;
24 namespace panda::test {
25 class BuiltinsDisplayNamesTest : public testing::Test {
26 public:
SetUpTestCase()27     static void SetUpTestCase()
28     {
29         GTEST_LOG_(INFO) << "SetUpTestCase";
30     }
31 
TearDownTestCase()32     static void TearDownTestCase()
33     {
34         GTEST_LOG_(INFO) << "TearDownCase";
35     }
36 
SetUp()37     void SetUp() override
38     {
39         JSRuntimeOptions options;
40 #if PANDA_TARGET_LINUX
41         // for consistency requirement, use ohos_icu4j/data/icudt67l.dat as icu-data-path
42         options.SetIcuDataPath(ICU_PATH);
43 #endif
44         options.SetEnableForceGC(true);
45         instance = JSNApi::CreateEcmaVM(options);
46         instance->SetEnableForceGC(true);
47         ASSERT_TRUE(instance != nullptr) << "Cannot create EcmaVM";
48         thread = instance->GetJSThread();
49         scope = new EcmaHandleScope(thread);
50     }
51 
TearDown()52     void TearDown() override
53     {
54         TestHelper::DestroyEcmaVMWithScope(instance, scope);
55     }
56 
57     EcmaVM *instance {nullptr};
58     EcmaHandleScope *scope {nullptr};
59     JSThread *thread {nullptr};
60 };
61 
JSDisplayNamesCreateWithOptionTest(JSThread * thread,JSHandle<JSTaggedValue> & locale,JSHandle<JSTaggedValue> & typeValue)62 static JSTaggedValue JSDisplayNamesCreateWithOptionTest(JSThread *thread, JSHandle<JSTaggedValue> &locale,
63                                                         JSHandle<JSTaggedValue> &typeValue)
64 {
65     ObjectFactory *factory = thread->GetEcmaVM()->GetFactory();
66     JSHandle<GlobalEnv> env = thread->GetEcmaVM()->GetGlobalEnv();
67     JSHandle<JSFunction> newTarget(env->GetDisplayNamesFunction());
68     JSHandle<JSTaggedValue> objFun = env->GetObjectFunction();
69     JSHandle<JSObject> optionsObj = factory->NewJSObjectByConstructor(JSHandle<JSFunction>(objFun), objFun);
70 
71     JSHandle<JSTaggedValue> typeKey = thread->GlobalConstants()->GetHandledTypeString();
72     JSObject::SetProperty(thread, optionsObj, typeKey, typeValue);
73 
74     JSHandle<JSTaggedValue> localesString = locale;
75     auto ecmaRuntimeCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue(*newTarget), 8);
76     ecmaRuntimeCallInfo->SetFunction(newTarget.GetTaggedValue());
77     ecmaRuntimeCallInfo->SetThis(JSTaggedValue::Undefined());
78     ecmaRuntimeCallInfo->SetCallArg(0, localesString.GetTaggedValue());
79     ecmaRuntimeCallInfo->SetCallArg(1, optionsObj.GetTaggedValue());
80 
81     [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, ecmaRuntimeCallInfo);
82     JSTaggedValue result = BuiltinsDisplayNames::DisplayNamesConstructor(ecmaRuntimeCallInfo);
83     TestHelper::TearDownFrame(thread, prev);
84 
85     EXPECT_TRUE(result.IsJSDisplayNames());
86     return result;
87 }
88 
89 // new DisplayNames(locales, options)
HWTEST_F_L0(BuiltinsDisplayNamesTest,DisplayNamesConstructor)90 HWTEST_F_L0(BuiltinsDisplayNamesTest, DisplayNamesConstructor)
91 {
92     ObjectFactory *factory = thread->GetEcmaVM()->GetFactory();
93     JSHandle<GlobalEnv> env = thread->GetEcmaVM()->GetGlobalEnv();
94     JSHandle<JSFunction> newTarget(env->GetDisplayNamesFunction());
95     JSHandle<JSTaggedValue> objFun = env->GetObjectFunction();
96 
97     JSHandle<JSTaggedValue> typeKey = thread->GlobalConstants()->GetHandledTypeString();
98     JSHandle<JSTaggedValue> styleKey = thread->GlobalConstants()->GetHandledStyleString();
99     JSHandle<JSTaggedValue> fallbackKey = thread->GlobalConstants()->GetHandledFallbackString();
100 
101     JSHandle<JSTaggedValue> localeString(factory->NewFromASCII("en"));
102     JSHandle<JSTaggedValue> typeValue(factory->NewFromASCII("language"));
103     JSHandle<JSTaggedValue> styleValue(factory->NewFromASCII("narrow"));
104     JSHandle<JSTaggedValue> fallbackValue(factory->NewFromASCII("code"));
105 
106     JSHandle<JSObject> optionsObj = factory->NewJSObjectByConstructor(JSHandle<JSFunction>(objFun), objFun);
107     JSObject::SetProperty(thread, optionsObj, typeKey, typeValue);
108     JSObject::SetProperty(thread, optionsObj, styleKey, styleValue);
109     JSObject::SetProperty(thread, optionsObj, fallbackKey, fallbackValue);
110 
111     auto ecmaRuntimeCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue(*newTarget), 8);
112     ecmaRuntimeCallInfo->SetFunction(newTarget.GetTaggedValue());
113     ecmaRuntimeCallInfo->SetThis(JSTaggedValue::Undefined());
114     ecmaRuntimeCallInfo->SetCallArg(0, localeString.GetTaggedValue());
115     ecmaRuntimeCallInfo->SetCallArg(1, optionsObj.GetTaggedValue());
116 
117     [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, ecmaRuntimeCallInfo);
118     JSTaggedValue result = BuiltinsDisplayNames::DisplayNamesConstructor(ecmaRuntimeCallInfo);
119     TestHelper::TearDownFrame(thread, prev);
120     EXPECT_TRUE(result.IsJSDisplayNames());
121 }
122 
123 // Of(fr, type(language))
HWTEST_F_L0(BuiltinsDisplayNamesTest,Of_001)124 HWTEST_F_L0(BuiltinsDisplayNamesTest, Of_001)
125 {
126     ObjectFactory *factory = thread->GetEcmaVM()->GetFactory();
127     JSHandle<JSTaggedValue> locale(factory->NewFromASCII("en"));
128     JSHandle<JSTaggedValue> typeValue(factory->NewFromASCII("language"));
129     JSHandle<JSDisplayNames> jsDisplayNames =
130         JSHandle<JSDisplayNames>(thread, JSDisplayNamesCreateWithOptionTest(thread, locale, typeValue));
131 
132     JSHandle<JSTaggedValue> stringValue(factory->NewFromASCII("fr"));
133     auto ecmaRuntimeCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6);
134     ecmaRuntimeCallInfo->SetFunction(JSTaggedValue::Undefined());
135     ecmaRuntimeCallInfo->SetThis(jsDisplayNames.GetTaggedValue());
136     ecmaRuntimeCallInfo->SetCallArg(0, stringValue.GetTaggedValue());
137 
138     [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, ecmaRuntimeCallInfo);
139     JSTaggedValue result = BuiltinsDisplayNames::Of(ecmaRuntimeCallInfo);
140     TestHelper::TearDownFrame(thread, prev);
141 
142     EXPECT_TRUE(result.IsString());
143     JSHandle<EcmaString> handleEcmaStr(thread, result);
144     EXPECT_STREQ("French", EcmaStringAccessor(handleEcmaStr).ToCString().c_str());
145 }
146 
147 // Of(419, type(region))
HWTEST_F_L0(BuiltinsDisplayNamesTest,Of_002)148 HWTEST_F_L0(BuiltinsDisplayNamesTest, Of_002)
149 {
150     ObjectFactory *factory = thread->GetEcmaVM()->GetFactory();
151     JSHandle<JSTaggedValue> locale(factory->NewFromASCII("en"));
152     JSHandle<JSTaggedValue> typeValue(factory->NewFromASCII("region"));
153     JSHandle<JSDisplayNames> jsDisplayNames =
154         JSHandle<JSDisplayNames>(thread, JSDisplayNamesCreateWithOptionTest(thread, locale, typeValue));
155 
156     JSHandle<JSTaggedValue> stringValue(factory->NewFromASCII("419"));
157     auto ecmaRuntimeCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6);
158     ecmaRuntimeCallInfo->SetFunction(JSTaggedValue::Undefined());
159     ecmaRuntimeCallInfo->SetThis(jsDisplayNames.GetTaggedValue());
160     ecmaRuntimeCallInfo->SetCallArg(0, stringValue.GetTaggedValue());
161 
162     [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, ecmaRuntimeCallInfo);
163     JSTaggedValue result = BuiltinsDisplayNames::Of(ecmaRuntimeCallInfo);
164     TestHelper::TearDownFrame(thread, prev);
165 
166     EXPECT_TRUE(result.IsString());
167     JSHandle<EcmaString> handleEcmaStr(thread, result);
168     EXPECT_STREQ("Latin America", EcmaStringAccessor(handleEcmaStr).ToCString().c_str());
169 }
170 
171 // Of(EUR, type(currency))
HWTEST_F_L0(BuiltinsDisplayNamesTest,Of_003)172 HWTEST_F_L0(BuiltinsDisplayNamesTest, Of_003)
173 {
174     ObjectFactory *factory = thread->GetEcmaVM()->GetFactory();
175     JSHandle<JSTaggedValue> locale(factory->NewFromASCII("en"));
176     JSHandle<JSTaggedValue> typeValue(factory->NewFromASCII("currency"));
177     JSHandle<JSDisplayNames> jsDisplayNames =
178         JSHandle<JSDisplayNames>(thread, JSDisplayNamesCreateWithOptionTest(thread, locale, typeValue));
179 
180     JSHandle<JSTaggedValue> stringValue(factory->NewFromASCII("EUR"));
181     auto ecmaRuntimeCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6);
182     ecmaRuntimeCallInfo->SetFunction(JSTaggedValue::Undefined());
183     ecmaRuntimeCallInfo->SetThis(jsDisplayNames.GetTaggedValue());
184     ecmaRuntimeCallInfo->SetCallArg(0, stringValue.GetTaggedValue());
185 
186     [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, ecmaRuntimeCallInfo);
187     JSTaggedValue result = BuiltinsDisplayNames::Of(ecmaRuntimeCallInfo);
188     TestHelper::TearDownFrame(thread, prev);
189 
190     EXPECT_TRUE(result.IsString());
191     JSHandle<EcmaString> handleEcmaStr(thread, result);
192     EXPECT_STREQ("Euro", EcmaStringAccessor(handleEcmaStr).ToCString().c_str());
193 }
194 
195 // Of(Code Cover)
HWTEST_F_L0(BuiltinsDisplayNamesTest,Of_004)196 HWTEST_F_L0(BuiltinsDisplayNamesTest, Of_004)
197 {
198     // IsNotJSDisplayNames
199     auto ecmaRuntimeCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 6);
200     ecmaRuntimeCallInfo->SetFunction(JSTaggedValue::Undefined());
201     ecmaRuntimeCallInfo->SetThis(JSTaggedValue::Undefined());
202     ecmaRuntimeCallInfo->SetCallArg(0, JSTaggedValue::Undefined());
203 
204     [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, ecmaRuntimeCallInfo);
205     JSTaggedValue result = BuiltinsDisplayNames::Of(ecmaRuntimeCallInfo);
206     TestHelper::TearDownFrame(thread, prev);
207     EXPECT_TRUE(thread->HasPendingException());
208     EXPECT_EQ(result, JSTaggedValue::Exception());
209     thread->ClearException();
210 }
211 
212 // SupportedLocalesOf("best fit")
HWTEST_F_L0(BuiltinsDisplayNamesTest,SupportedLocalesOf_001)213 HWTEST_F_L0(BuiltinsDisplayNamesTest, SupportedLocalesOf_001)
214 {
215     ObjectFactory *factory = thread->GetEcmaVM()->GetFactory();
216     JSHandle<JSTaggedValue> locale(factory->NewFromASCII("id-u-co-pinyin-de-ID"));
217 
218     auto ecmaRuntimeCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8);
219     ecmaRuntimeCallInfo->SetFunction(JSTaggedValue::Undefined());
220     ecmaRuntimeCallInfo->SetThis(JSTaggedValue::Undefined());
221     ecmaRuntimeCallInfo->SetCallArg(0, locale.GetTaggedValue());
222     // set the tag is default value
223     ecmaRuntimeCallInfo->SetCallArg(1, JSTaggedValue::Undefined());
224 
225     [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, ecmaRuntimeCallInfo);
226     JSTaggedValue resultArr = BuiltinsDisplayNames::SupportedLocalesOf(ecmaRuntimeCallInfo);
227     TestHelper::TearDownFrame(thread, prev);
228 
229     JSHandle<JSArray> resultHandle(thread, resultArr);
230     JSHandle<TaggedArray> elements(thread, resultHandle->GetElements());
231     EXPECT_EQ(elements->GetLength(), 1U);
232     JSHandle<EcmaString> handleEcmaStr(thread, elements->Get(0));
233     EXPECT_STREQ("id-u-co-pinyin-de-id", EcmaStringAccessor(handleEcmaStr).ToCString().c_str());
234 }
235 
236 // SupportedLocalesOf("look up")
HWTEST_F_L0(BuiltinsDisplayNamesTest,SupportedLocalesOf_002)237 HWTEST_F_L0(BuiltinsDisplayNamesTest, SupportedLocalesOf_002)
238 {
239     ObjectFactory *factory = thread->GetEcmaVM()->GetFactory();
240     JSHandle<GlobalEnv> env = thread->GetEcmaVM()->GetGlobalEnv();
241     JSHandle<JSTaggedValue> objFun = env->GetObjectFunction();
242 
243     JSHandle<JSTaggedValue> localeMatcherKey = thread->GlobalConstants()->GetHandledLocaleMatcherString();
244     JSHandle<JSTaggedValue> localeMatcherValue(factory->NewFromASCII("lookup"));
245     JSHandle<JSObject> optionsObj = factory->NewJSObjectByConstructor(JSHandle<JSFunction>(objFun), objFun);
246     JSObject::SetProperty(thread, optionsObj, localeMatcherKey, localeMatcherValue);
247     JSHandle<JSTaggedValue> locale(factory->NewFromASCII("de-DE-u-co-phonebk"));
248 
249     auto ecmaRuntimeCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 8);
250     ecmaRuntimeCallInfo->SetFunction(JSTaggedValue::Undefined());
251     ecmaRuntimeCallInfo->SetThis(JSTaggedValue::Undefined());
252     ecmaRuntimeCallInfo->SetCallArg(0, locale.GetTaggedValue());
253     ecmaRuntimeCallInfo->SetCallArg(1, optionsObj.GetTaggedValue());
254 
255     [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, ecmaRuntimeCallInfo);
256     JSTaggedValue resultArr = BuiltinsDisplayNames::SupportedLocalesOf(ecmaRuntimeCallInfo);
257     TestHelper::TearDownFrame(thread, prev);
258 
259     JSHandle<JSArray> resultHandle(thread, resultArr);
260     JSHandle<TaggedArray> elements(thread, resultHandle->GetElements());
261     EXPECT_EQ(elements->GetLength(), 1U);
262     JSHandle<EcmaString> handleEcmaStr(thread, elements->Get(0));
263     EXPECT_STREQ("de-DE-u-co-phonebk", EcmaStringAccessor(handleEcmaStr).ToCString().c_str());
264 }
265 
HWTEST_F_L0(BuiltinsDisplayNamesTest,ResolvedOptions)266 HWTEST_F_L0(BuiltinsDisplayNamesTest, ResolvedOptions)
267 {
268     ObjectFactory *factory = thread->GetEcmaVM()->GetFactory();
269     auto globalConst = thread->GlobalConstants();
270     JSHandle<JSTaggedValue> locale(factory->NewFromASCII("de-DE"));
271     JSHandle<JSTaggedValue> typeValue(factory->NewFromASCII("currency"));
272     JSHandle<JSDisplayNames> jsDisplayNames =
273         JSHandle<JSDisplayNames>(thread, JSDisplayNamesCreateWithOptionTest(
274                                             thread, locale, typeValue));
275     auto ecmaRuntimeCallInfo = TestHelper::CreateEcmaRuntimeCallInfo(thread, JSTaggedValue::Undefined(), 4);
276     ecmaRuntimeCallInfo->SetFunction(JSTaggedValue::Undefined());
277     ecmaRuntimeCallInfo->SetThis(jsDisplayNames.GetTaggedValue());
278 
279     [[maybe_unused]] auto prev = TestHelper::SetupFrame(thread, ecmaRuntimeCallInfo);
280     JSTaggedValue result = BuiltinsDisplayNames::ResolvedOptions(ecmaRuntimeCallInfo);
281     TestHelper::TearDownFrame(thread, prev);
282 
283     JSHandle<JSTaggedValue> resultObj =
284         JSHandle<JSTaggedValue>(thread, JSTaggedValue(static_cast<JSTaggedType>(result.GetRawData())));
285     // judge whether the properties of the object are the same as those of jsdatetimeformat tag
286     JSHandle<JSTaggedValue> localeKey = globalConst->GetHandledLocaleString();
287     JSHandle<JSTaggedValue> localeValue(factory->NewFromASCII("de-DE"));
288     EXPECT_EQ(JSTaggedValue::SameValue(
289         JSObject::GetProperty(thread, resultObj, localeKey).GetValue(), localeValue), true);
290     JSHandle<JSTaggedValue> typeKey = globalConst->GetHandledTypeString();
291     EXPECT_EQ(JSTaggedValue::SameValue(
292         JSObject::GetProperty(thread, resultObj, typeKey).GetValue(), typeValue), true);
293 }
294 }
295