• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // © 2024 and later: Unicode, Inc. and others.
2 // License & terms of use: http://www.unicode.org/copyright.html
3 
4 #ifndef _TESTMESSAGEFORMAT2
5 #define _TESTMESSAGEFORMAT2
6 
7 #include "unicode/rep.h"
8 #include "unicode/utypes.h"
9 
10 #if !UCONFIG_NO_FORMATTING
11 
12 #if !UCONFIG_NO_MF2
13 
14 #include "messageformat2test_utils.h"
15 #include "unicode/unistr.h"
16 #include "unicode/messageformat2_formattable.h"
17 #include "unicode/parseerr.h"
18 #include "intltest.h"
19 
20 /**
21  * TestMessageFormat2 tests MessageFormat2
22  */
23 
24 struct TestResult {
25     const UnicodeString pattern;
26     const UnicodeString output;
27 };
28 
29 struct TestResultError {
30     const UnicodeString pattern;
31     const UnicodeString output;
32     UErrorCode expected;
33 };
34 
35 class TestMessageFormat2: public IntlTest {
36 public:
37     void runIndexedTest( int32_t index, UBool exec, const char* &name, char* par = NULL ) override;
38 
39     /**
40      * test MessageFormat2 with various given patterns
41      **/
42     void dataDrivenTests(void);
43     void testAPICustomFunctions(void);
44     // Test custom functions
45     void testCustomFunctions(void);
46     // Test the data model API
47     void testDataModelAPI(void);
48     // Test the formatting API
49     void testFormatterAPI(void);
50     void testAPI(void);
51     void testAPISimple(void);
52 
53 private:
54     void jsonTestsFromFiles(IcuTestErrorCode&);
55 
56     // Built-in function testing
57     void testNumbers(IcuTestErrorCode&);
58 
59     // Custom function testing
60     void testPersonFormatter(IcuTestErrorCode&);
61     void testCustomFunctionsComplexMessage(IcuTestErrorCode&);
62     void testGrammarCasesFormatter(IcuTestErrorCode&);
63     void testListFormatter(IcuTestErrorCode&);
64     void testMessageRefFormatter(IcuTestErrorCode&);
65 
66     // Feature tests
67     void testEmptyMessage(message2::TestCase::Builder&, IcuTestErrorCode&);
68     void testPlainText(message2::TestCase::Builder&, IcuTestErrorCode&);
69     void testPlaceholders(message2::TestCase::Builder&, IcuTestErrorCode&);
70     void testArgumentMissing(message2::TestCase::Builder&, IcuTestErrorCode&);
71     void testDefaultLocale(message2::TestCase::Builder&, IcuTestErrorCode&);
72     void testSpecialPluralWithDecimals(message2::TestCase::Builder&, IcuTestErrorCode&);
73     void testDefaultFunctionAndOptions(message2::TestCase::Builder&, IcuTestErrorCode&);
74     void testSimpleSelection(message2::TestCase::Builder&, IcuTestErrorCode&);
75     void testComplexSelection(message2::TestCase::Builder&, IcuTestErrorCode&);
76     void testSimpleLocalVariable(message2::TestCase::Builder&, IcuTestErrorCode&);
77     void testLocalVariableWithSelect(message2::TestCase::Builder&, IcuTestErrorCode&);
78     void testDateFormat(message2::TestCase::Builder&, IcuTestErrorCode&);
79     void testPlural(message2::TestCase::Builder&, IcuTestErrorCode&);
80 
81     void testPluralOrdinal(message2::TestCase::Builder&, IcuTestErrorCode&);
82     void testDeclareBeforeUse(message2::TestCase::Builder&, IcuTestErrorCode&);
83 
84     // MessageFormat 1 tests
85     void testSample(message2::TestCase::Builder&, IcuTestErrorCode&);
86     void testStaticFormat(message2::TestCase::Builder&, IcuTestErrorCode&);
87     void testSimpleFormat(message2::TestCase::Builder&, IcuTestErrorCode&);
88     void testSelectFormatToPattern(message2::TestCase::Builder&, IcuTestErrorCode&);
89     void testMessageFormatDateTimeSkeleton(message2::TestCase::Builder&, IcuTestErrorCode&);
90     void testMf1Behavior(message2::TestCase::Builder&, IcuTestErrorCode&);
91 
92     void testHighLoneSurrogate(void);
93     void testLowLoneSurrogate(void);
94 }; // class TestMessageFormat2
95 
96 U_NAMESPACE_BEGIN
97 
98 namespace message2 {
99 
100 // Custom function classes
101 class PersonNameFormatterFactory : public FormatterFactory {
102 
103     public:
104     Formatter* createFormatter(const Locale&, UErrorCode&) override;
105 };
106 
107 class Person : public FormattableObject {
108     public:
109     UnicodeString title;
110     UnicodeString firstName;
111     UnicodeString lastName;
Person(UnicodeString t,UnicodeString f,UnicodeString l)112     Person(UnicodeString t, UnicodeString f, UnicodeString l) : title(t), firstName(f), lastName(l), tagName("person") {}
113     ~Person();
tag()114     const UnicodeString& tag() const override { return tagName; }
115     private:
116     const UnicodeString tagName;
117 };
118 
119 class PersonNameFormatter : public Formatter {
120     public:
121     FormattedPlaceholder format(FormattedPlaceholder&&, FunctionOptions&& opts, UErrorCode& errorCode) const override;
122 };
123 
124 class FormattableProperties : public FormattableObject {
125     public:
tag()126     const UnicodeString& tag() const override { return tagName; }
FormattableProperties(Hashtable * hash)127     FormattableProperties(Hashtable* hash) : properties(hash), tagName("properties") {
128         U_ASSERT(hash != nullptr);
129     }
130     ~FormattableProperties();
131     LocalPointer<Hashtable> properties;
132 private:
133     const UnicodeString tagName;
134 };
135 
136 class GrammarCasesFormatterFactory : public FormatterFactory {
137     public:
138     Formatter* createFormatter(const Locale&, UErrorCode&) override;
139 };
140 
141 class GrammarCasesFormatter : public Formatter {
142     public:
143     FormattedPlaceholder format(FormattedPlaceholder&&, FunctionOptions&& opts, UErrorCode& errorCode) const override;
144     static MFFunctionRegistry customRegistry(UErrorCode&);
145     private:
146     void getDativeAndGenitive(const UnicodeString&, UnicodeString& result) const;
147 };
148 
149 class ListFormatterFactory : public FormatterFactory {
150     public:
151     Formatter* createFormatter(const Locale&, UErrorCode&) override;
152 };
153 
154 class ListFormatter : public Formatter {
155     public:
156     FormattedPlaceholder format(FormattedPlaceholder&&, FunctionOptions&& opts, UErrorCode& errorCode) const override;
157     static MFFunctionRegistry customRegistry(UErrorCode&);
158     private:
159     friend class ListFormatterFactory;
160     const Locale& locale;
ListFormatter(const Locale & loc)161     ListFormatter(const Locale& loc) : locale(loc) {}
162 };
163 
164 class ResourceManagerFactory : public FormatterFactory {
165     public:
166     Formatter* createFormatter(const Locale&, UErrorCode&) override;
167 };
168 
169 class ResourceManager : public Formatter {
170     public:
171     FormattedPlaceholder format(FormattedPlaceholder&&, FunctionOptions&& opts, UErrorCode& errorCode) const override;
172     static MFFunctionRegistry customRegistry(UErrorCode&);
173     static Hashtable* properties(UErrorCode&);
174     static UnicodeString propertiesAsString(const Hashtable&);
175     static Hashtable* parseProperties(const UnicodeString&, UErrorCode&);
176 
177     private:
178     friend class ResourceManagerFactory;
ResourceManager(const Locale & loc)179     ResourceManager(const Locale& loc) : locale(loc) {}
180     const Locale& locale;
181 };
182 
183 } // namespace message2
184 U_NAMESPACE_END
185 
186 #endif /* #if !UCONFIG_NO_MF2 */
187 
188 #endif /* #if !UCONFIG_NO_FORMATTING */
189 
190 #endif
191