messageformat2_data_model.h 123 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619262026212622262326242625262626272628262926302631263226332634263526362637263826392640264126422643264426452646264726482649265026512652265326542655265626572658265926602661266226632664266526662667266826692670267126722673267426752676267726782679268026812682268326842685268626872688268926902691269226932694269526962697269826992700270127022703270427052706270727082709271027112712271327142715271627172718271927202721272227232724272527262727272827292730273127322733273427352736273727382739274027412742274327442745274627472748274927502751275227532754275527562757275827592760276127622763276427652766276727682769277027712772277327742775277627772778277927802781278227832784278527862787278827892790279127922793279427952796279727982799280028012802280328042805280628072808280928102811281228132814281528162817281828192820282128222823282428252826282728282829283028312832283328342835283628372838283928402841284228432844284528462847284828492850285128522853285428552856285728582859286028612862286328642865286628672868286928702871287228732874287528762877287828792880288128822883288428852886288728882889289028912892289328942895289628972898289929002901290229032904290529062907290829092910291129122913291429152916291729182919292029212922292329242925292629272928292929302931293229332934293529362937293829392940294129422943294429452946294729482949295029512952295329542955295629572958295929602961296229632964296529662967296829692970297129722973297429752976297729782979298029812982298329842985298629872988298929902991299229932994299529962997299829993000300130023003300430053006300730083009301030113012301330143015301630173018301930203021302230233024302530263027302830293030303130323033303430353036303730383039304030413042304330443045304630473048304930503051305230533054305530563057305830593060306130623063306430653066306730683069307030713072307330743075307630773078307930803081308230833084308530863087308830893090
  1. // © 2024 and later: Unicode, Inc. and others.
  2. // License & terms of use: http://www.unicode.org/copyright.html
  3. #include "unicode/utypes.h"
  4. #ifndef MESSAGEFORMAT_DATA_MODEL_H
  5. #define MESSAGEFORMAT_DATA_MODEL_H
  6. #if U_SHOW_CPLUSPLUS_API
  7. #if !UCONFIG_NO_FORMATTING
  8. #if !UCONFIG_NO_MF2
  9. #include "unicode/localpointer.h"
  10. #include "unicode/messageformat2_data_model_names.h"
  11. #ifndef U_HIDE_DEPRECATED_API
  12. #include <algorithm>
  13. #include <cstddef>
  14. #include <iterator>
  15. #include <optional>
  16. #include <variant>
  17. #include <vector>
  18. U_NAMESPACE_BEGIN
  19. class UVector;
  20. // Helpers
  21. // Note: this _must_ be declared `inline` or else gcc will generate code
  22. // for its instantiations, which needs to be avoided because it returns
  23. // a std::vector
  24. template<typename T>
  25. static inline std::vector<T> toStdVector(const T* arr, int32_t len) {
  26. std::vector<T> result;
  27. for (int32_t i = 0; i < len; i++) {
  28. result.push_back(arr[i]);
  29. }
  30. return result;
  31. }
  32. #if defined(U_REAL_MSVC)
  33. #pragma warning(push)
  34. // Ignore warning 4251 as these templates are instantiated later in this file,
  35. // after the classes used to instantiate them have been defined.
  36. #pragma warning(disable: 4251)
  37. #endif
  38. namespace message2 {
  39. class Checker;
  40. class MFDataModel;
  41. class MessageFormatter;
  42. class Parser;
  43. class Serializer;
  44. namespace data_model {
  45. class Binding;
  46. class Literal;
  47. class Operator;
  48. /**
  49. * The `Reserved` class represents a `reserved` annotation, as in the `reserved` nonterminal
  50. * in the MessageFormat 2 grammar or the `Reserved` interface
  51. * defined in
  52. * https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model.md#expressions
  53. *
  54. * `Reserved` is immutable, copyable and movable.
  55. *
  56. * @internal ICU 75 technology preview
  57. * @deprecated This API is for technology preview only.
  58. */
  59. class U_I18N_API Reserved : public UMemory {
  60. public:
  61. /**
  62. * A `Reserved` is a sequence of literals.
  63. *
  64. * @return The number of literals.
  65. *
  66. * @internal ICU 75 technology preview
  67. * @deprecated This API is for technology preview only.
  68. */
  69. int32_t numParts() const;
  70. /**
  71. * Indexes into the sequence.
  72. * Precondition: i < numParts()
  73. *
  74. * @param i Index of the part being accessed.
  75. * @return A reference to he i'th literal in the sequence
  76. *
  77. * @internal ICU 75 technology preview
  78. * @deprecated This API is for technology preview only.
  79. */
  80. const Literal& getPart(int32_t i) const;
  81. /**
  82. * The mutable `Reserved::Builder` class allows the reserved sequence to be
  83. * constructed one part at a time.
  84. *
  85. * Builder is not copyable or movable.
  86. *
  87. * @internal ICU 75 technology preview
  88. * @deprecated This API is for technology preview only.
  89. */
  90. class U_I18N_API Builder : public UMemory {
  91. private:
  92. UVector* parts; // Not a LocalPointer for the same reason as in `SelectorKeys::Builder`
  93. public:
  94. /**
  95. * Adds a single literal to the reserved sequence.
  96. *
  97. * @param part The literal to be added. Passed by move.
  98. * @param status Input/output error code
  99. * @return A reference to the builder.
  100. *
  101. * @internal ICU 75 technology preview
  102. * @deprecated This API is for technology preview only.
  103. */
  104. Builder& add(Literal&& part, UErrorCode& status) noexcept;
  105. /**
  106. * Constructs a new immutable `Reserved` using the list of parts
  107. * set with previous `add()` calls.
  108. *
  109. * The builder object (`this`) can still be used after calling `build()`.
  110. *
  111. * param status Input/output error code
  112. * @return The new Reserved object
  113. *
  114. * @internal ICU 75 technology preview
  115. * @deprecated This API is for technology preview only.
  116. */
  117. Reserved build(UErrorCode& status) const noexcept;
  118. /**
  119. * Default constructor.
  120. * Returns a builder with an empty Reserved sequence.
  121. *
  122. * param status Input/output error code
  123. *
  124. * @internal ICU 75 technology preview
  125. * @deprecated This API is for technology preview only.
  126. */
  127. Builder(UErrorCode& status);
  128. /**
  129. * Destructor.
  130. *
  131. * @internal ICU 75 technology preview
  132. * @deprecated This API is for technology preview only.
  133. */
  134. virtual ~Builder();
  135. Builder(const Builder&) = delete;
  136. Builder& operator=(const Builder&) = delete;
  137. Builder(Builder&&) = delete;
  138. Builder& operator=(Builder&&) = delete;
  139. }; // class Reserved::Builder
  140. /**
  141. * Non-member swap function.
  142. * @param r1 will get r2's contents
  143. * @param r2 will get r1's contents
  144. *
  145. * @internal ICU 75 technology preview
  146. * @deprecated This API is for technology preview only.
  147. */
  148. friend inline void swap(Reserved& r1, Reserved& r2) noexcept {
  149. using std::swap;
  150. swap(r1.bogus, r2.bogus);
  151. swap(r1.parts, r2.parts);
  152. swap(r1.len, r2.len);
  153. }
  154. /**
  155. * Copy constructor.
  156. *
  157. * @internal ICU 75 technology preview
  158. * @deprecated This API is for technology preview only.
  159. */
  160. Reserved(const Reserved& other);
  161. /**
  162. * Assignment operator
  163. *
  164. * @internal ICU 75 technology preview
  165. * @deprecated This API is for technology preview only.
  166. */
  167. Reserved& operator=(Reserved) noexcept;
  168. /**
  169. * Default constructor.
  170. * Puts the Reserved into a valid but undefined state.
  171. *
  172. * @internal ICU 75 technology preview
  173. * @deprecated This API is for technology preview only.
  174. */
  175. Reserved() { parts = LocalArray<Literal>(); }
  176. /**
  177. * Destructor.
  178. *
  179. * @internal ICU 75 technology preview
  180. * @deprecated This API is for technology preview only.
  181. */
  182. virtual ~Reserved();
  183. private:
  184. friend class Builder;
  185. friend class Operator;
  186. // True if a copy failed; this has to be distinguished
  187. // from a valid `Reserved` with empty parts
  188. bool bogus = false;
  189. // Possibly-empty list of parts
  190. // `literal` reserved as a quoted literal; `reserved-char` / `reserved-escape`
  191. // strings represented as unquoted literals
  192. /* const */ LocalArray<Literal> parts;
  193. int32_t len = 0;
  194. Reserved(const UVector& parts, UErrorCode& status) noexcept;
  195. // Helper
  196. static void initLiterals(Reserved&, const Reserved&);
  197. };
  198. /**
  199. * The `Literal` class corresponds to the `literal` nonterminal in the MessageFormat 2 grammar,
  200. * https://github.com/unicode-org/message-format-wg/blob/main/spec/message.abnf and the
  201. * `Literal` interface defined in
  202. * // https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model.md#expressions
  203. *
  204. * `Literal` is immutable, copyable and movable.
  205. *
  206. * @internal ICU 75 technology preview
  207. * @deprecated This API is for technology preview only.
  208. */
  209. class U_I18N_API Literal : public UObject {
  210. public:
  211. /**
  212. * Returns the quoted representation of this literal (enclosed in '|' characters)
  213. *
  214. * @return A string representation of the literal enclosed in quote characters.
  215. *
  216. * @internal ICU 75 technology preview
  217. * @deprecated This API is for technology preview only.
  218. */
  219. UnicodeString quoted() const;
  220. /**
  221. * Returns the parsed string contents of this literal.
  222. *
  223. * @return A string representation of this literal.
  224. *
  225. * @internal ICU 75 technology preview
  226. * @deprecated This API is for technology preview only.
  227. */
  228. const UnicodeString& unquoted() const;
  229. /**
  230. * Determines if this literal appeared as a quoted literal in the message.
  231. *
  232. * @return true if and only if this literal appeared as a quoted literal in the
  233. * message.
  234. *
  235. * @internal ICU 75 technology preview
  236. * @deprecated This API is for technology preview only.
  237. */
  238. UBool isQuoted() const { return thisIsQuoted; }
  239. /**
  240. * Literal constructor.
  241. *
  242. * @param q True if and only if this literal was parsed with the `quoted` nonterminal
  243. * (appeared enclosed in '|' characters in the message text).
  244. * @param s The string contents of this literal; escape sequences are assumed to have
  245. * been interpreted already.
  246. *
  247. * @internal ICU 75 technology preview
  248. * @deprecated This API is for technology preview only.
  249. */
  250. Literal(UBool q, const UnicodeString& s) : thisIsQuoted(q), contents(s) {}
  251. /**
  252. * Copy constructor.
  253. *
  254. * @internal ICU 75 technology preview
  255. * @deprecated This API is for technology preview only.
  256. */
  257. Literal(const Literal& other) : thisIsQuoted(other.thisIsQuoted), contents(other.contents) {}
  258. /**
  259. * Non-member swap function.
  260. * @param l1 will get l2's contents
  261. * @param l2 will get l1's contents
  262. *
  263. * @internal ICU 75 technology preview
  264. * @deprecated This API is for technology preview only.
  265. */
  266. friend inline void swap(Literal& l1, Literal& l2) noexcept {
  267. using std::swap;
  268. swap(l1.thisIsQuoted, l2.thisIsQuoted);
  269. swap(l1.contents, l2.contents);
  270. }
  271. /**
  272. * Assignment operator.
  273. *
  274. * @internal ICU 75 technology preview
  275. * @deprecated This API is for technology preview only.
  276. */
  277. Literal& operator=(Literal) noexcept;
  278. /**
  279. * Default constructor.
  280. * Puts the Literal into a valid but undefined state.
  281. *
  282. * @internal ICU 75 technology preview
  283. * @deprecated This API is for technology preview only.
  284. */
  285. Literal() = default;
  286. /**
  287. * Less than operator. Compares `this.stringContents()` with
  288. * `other.stringContents()`. This method is used in representing
  289. * the mapping from key lists to patterns in a message with variants,
  290. * and is not expected to be useful otherwise.
  291. *
  292. * @param other The Literal to compare to this one.
  293. * @return true if the parsed string corresponding to this `Literal`
  294. * is less than the parsed string corresponding to the other `Literal`
  295. * (according to `UnicodeString`'s less-than operator).
  296. * Returns false otherwise.
  297. *
  298. * @internal ICU 75 technology preview
  299. * @deprecated This API is for technology preview only.
  300. */
  301. bool operator<(const Literal& other) const;
  302. /**
  303. * Equality operator. Compares `this.stringContents()` with
  304. * `other.stringContents()`. This method is used in representing
  305. * the mapping from key lists to patterns in a message with variants,
  306. * and is not expected to be useful otherwise.
  307. *
  308. * @param other The Literal to compare to this one.
  309. * @return true if the parsed string corresponding to this `Literal`
  310. * equals the parsed string corresponding to the other `Literal`
  311. * (according to `UnicodeString`'s equality operator).
  312. * Returns false otherwise.
  313. *
  314. * @internal ICU 75 technology preview
  315. * @deprecated This API is for technology preview only.
  316. */
  317. bool operator==(const Literal& other) const;
  318. /**
  319. * Destructor.
  320. *
  321. * @internal ICU 75 technology preview
  322. * @deprecated This API is for technology preview only.
  323. */
  324. virtual ~Literal();
  325. private:
  326. friend class Reserved::Builder;
  327. /* const */ bool thisIsQuoted = false;
  328. /* const */ UnicodeString contents;
  329. };
  330. } // namespace data_model
  331. } // namespace message2
  332. /// @cond DOXYGEN_IGNORE
  333. // Export an explicit template instantiation of the LocalPointer that is used as a
  334. // data member of various MFDataModel classes.
  335. // (When building DLLs for Windows this is required.)
  336. // (See measunit_impl.h, datefmt.h, collationiterator.h, erarules.h and others
  337. // for similar examples.)
  338. #if U_PF_WINDOWS <= U_PLATFORM && U_PLATFORM <= U_PF_CYGWIN
  339. template class U_I18N_API LocalPointerBase<message2::data_model::Literal>;
  340. template class U_I18N_API LocalArray<message2::data_model::Literal>;
  341. #endif
  342. #if defined(U_REAL_MSVC)
  343. #pragma warning(pop)
  344. #endif
  345. /// @endcond
  346. U_NAMESPACE_END
  347. /// @cond DOXYGEN_IGNORE
  348. // Export an explicit template instantiation of the std::variants and std::optionals
  349. // that are used as a data member of various MFDataModel classes.
  350. // (When building DLLs for Windows this is required.)
  351. // (See measunit_impl.h, datefmt.h, collationiterator.h, erarules.h and others
  352. // for similar examples.)
  353. #if U_PF_WINDOWS <= U_PLATFORM && U_PLATFORM <= U_PF_CYGWIN
  354. #if defined(U_REAL_MSVC) && defined(_MSVC_STL_VERSION)
  355. struct U_I18N_API std::_Nontrivial_dummy_type;
  356. template class U_I18N_API std::_Variant_storage_<false, icu::UnicodeString, icu::message2::data_model::Literal>;
  357. #endif
  358. template class U_I18N_API std::variant<icu::UnicodeString, icu::message2::data_model::Literal>;
  359. template class U_I18N_API std::optional<std::variant<icu::UnicodeString, icu::message2::data_model::Literal>>;
  360. template class U_I18N_API std::optional<icu::message2::data_model::Literal>;
  361. #endif
  362. /// @endcond
  363. U_NAMESPACE_BEGIN
  364. namespace message2 {
  365. namespace data_model {
  366. /**
  367. * The `Operand` class corresponds to the `operand` nonterminal in the MessageFormat 2 grammar,
  368. * https://github.com/unicode-org/message-format-wg/blob/main/spec/message.abnf .
  369. * It represents a `Literal | VariableRef` -- see the `operand?` field of the `FunctionRef`
  370. * interface defined at:
  371. * https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model.md#expressions
  372. * with the difference that it can also represent a null operand (the absent operand in an
  373. * `annotation` with no operand).
  374. *
  375. * `Operand` is immutable and is copyable and movable.
  376. *
  377. * @internal ICU 75 technology preview
  378. * @deprecated This API is for technology preview only.
  379. */
  380. class U_I18N_API Operand : public UObject {
  381. public:
  382. /**
  383. * Determines if this operand represents a variable.
  384. *
  385. * @return True if and only if the operand is a variable.
  386. *
  387. * @internal ICU 75 technology preview
  388. * @deprecated This API is for technology preview only.
  389. */
  390. UBool isVariable() const;
  391. /**
  392. * Determines if this operand represents a literal.
  393. *
  394. * @return True if and only if the operand is a literal.
  395. *
  396. * @internal ICU 75 technology preview
  397. * @deprecated This API is for technology preview only.
  398. */
  399. UBool isLiteral() const;
  400. /**
  401. * Determines if this operand is the null operand.
  402. *
  403. * @return True if and only if the operand is the null operand.
  404. *
  405. * @internal ICU 75 technology preview
  406. * @deprecated This API is for technology preview only.
  407. */
  408. virtual UBool isNull() const;
  409. /**
  410. * Returns a reference to this operand's variable name.
  411. * Precondition: isVariable()
  412. *
  413. * @return A reference to the name of the variable
  414. *
  415. * @internal ICU 75 technology preview
  416. * @deprecated This API is for technology preview only.
  417. */
  418. const UnicodeString& asVariable() const;
  419. /**
  420. * Returns a reference to this operand's literal contents.
  421. * Precondition: isLiteral()
  422. *
  423. * @return A reference to the literal
  424. *
  425. * @internal ICU 75 technology preview
  426. * @deprecated This API is for technology preview only.
  427. */
  428. const Literal& asLiteral() const;
  429. /**
  430. * Default constructor.
  431. * Creates a null Operand.
  432. *
  433. * @internal ICU 75 technology preview
  434. * @deprecated This API is for technology preview only.
  435. */
  436. Operand() : contents(std::nullopt) {}
  437. /**
  438. * Variable operand constructor.
  439. *
  440. * @param v The variable name; an operand corresponding
  441. * to a reference to `v` is returned.
  442. *
  443. * @internal ICU 75 technology preview
  444. * @deprecated This API is for technology preview only.
  445. */
  446. explicit Operand(const UnicodeString& v) : contents(VariableName(v)) {}
  447. /**
  448. * Literal operand constructor.
  449. *
  450. * @param l The literal to use for this operand; an operand
  451. * corresponding to `l` is returned.
  452. *
  453. * @internal ICU 75 technology preview
  454. * @deprecated This API is for technology preview only.
  455. */
  456. explicit Operand(const Literal& l) : contents(l) {}
  457. /**
  458. * Non-member swap function.
  459. * @param o1 will get o2's contents
  460. * @param o2 will get o1's contents
  461. *
  462. * @internal ICU 75 technology preview
  463. * @deprecated This API is for technology preview only.
  464. */
  465. friend inline void swap(Operand& o1, Operand& o2) noexcept {
  466. using std::swap;
  467. (void) o1;
  468. (void) o2;
  469. swap(o1.contents, o2.contents);
  470. }
  471. /**
  472. * Assignment operator.
  473. *
  474. * @internal ICU 75 technology preview
  475. * @deprecated This API is for technology preview only.
  476. */
  477. virtual Operand& operator=(Operand) noexcept;
  478. /**
  479. * Copy constructor.
  480. *
  481. * @internal ICU 75 technology preview
  482. * @deprecated This API is for technology preview only.
  483. */
  484. Operand(const Operand&);
  485. /**
  486. * Destructor.
  487. *
  488. * @internal ICU 75 technology preview
  489. * @deprecated This API is for technology preview only.
  490. */
  491. virtual ~Operand();
  492. private:
  493. std::optional<std::variant<VariableName, Literal>> contents;
  494. }; // class Operand
  495. /**
  496. * The `Key` class corresponds to the `key` nonterminal in the MessageFormat 2 grammar,
  497. * https://github.com/unicode-org/message-format-wg/blob/main/spec/message.abnf .
  498. * It also corresponds to
  499. * the `Literal | CatchallKey` that is the
  500. * element type of the `keys` array in the `Variant` interface
  501. * defined in https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model.md#messages
  502. *
  503. * A key is either a literal or the wildcard symbol (represented in messages as '*')
  504. *
  505. * `Key` is immutable, copyable and movable.
  506. *
  507. * @internal ICU 75 technology preview
  508. * @deprecated This API is for technology preview only.
  509. */
  510. class U_I18N_API Key : public UObject {
  511. public:
  512. /**
  513. * Determines if this is a wildcard key
  514. *
  515. * @return True if and only if this is the wildcard key
  516. *
  517. * @internal ICU 75 technology preview
  518. * @deprecated This API is for technology preview only.
  519. */
  520. UBool isWildcard() const { return !contents.has_value(); }
  521. /**
  522. * Returns the contents of this key as a literal.
  523. * Precondition: !isWildcard()
  524. *
  525. * @return The literal contents of the key
  526. *
  527. * @internal ICU 75 technology preview
  528. * @deprecated This API is for technology preview only.
  529. */
  530. const Literal& asLiteral() const;
  531. /**
  532. * Copy constructor.
  533. *
  534. * @internal ICU 75 technology preview
  535. * @deprecated This API is for technology preview only.
  536. */
  537. Key(const Key& other) : contents(other.contents) {}
  538. /**
  539. * Wildcard constructor; constructs a Key representing the
  540. * catchall or wildcard key, '*'.
  541. *
  542. * @internal ICU 75 technology preview
  543. * @deprecated This API is for technology preview only.
  544. */
  545. Key() : contents(std::nullopt) {}
  546. /**
  547. * Literal key constructor.
  548. *
  549. * @param lit A Literal to use for this key. The result matches the
  550. * literal `lit`.
  551. *
  552. * @internal ICU 75 technology preview
  553. * @deprecated This API is for technology preview only.
  554. */
  555. explicit Key(const Literal& lit) : contents(lit) {}
  556. /**
  557. * Non-member swap function.
  558. * @param k1 will get k2's contents
  559. * @param k2 will get k1's contents
  560. *
  561. * @internal ICU 75 technology preview
  562. * @deprecated This API is for technology preview only.
  563. */
  564. friend inline void swap(Key& k1, Key& k2) noexcept {
  565. using std::swap;
  566. swap(k1.contents, k2.contents);
  567. }
  568. /**
  569. * Assignment operator
  570. *
  571. * @internal ICU 75 technology preview
  572. * @deprecated This API is for technology preview only.
  573. */
  574. Key& operator=(Key) noexcept;
  575. /**
  576. * Less than operator. Compares the literal of `this` with the literal of `other`.
  577. * This method is used in representing the mapping from key lists to patterns
  578. * in a message with variants, and is not expected to be useful otherwise.
  579. *
  580. * @param other The Key to compare to this one.
  581. * @return true if the two `Key`s are not wildcards and if `this.asLiteral()`
  582. * < `other.asLiteral()`.
  583. * Returns false otherwise.
  584. *
  585. * @internal ICU 75 technology preview
  586. * @deprecated This API is for technology preview only.
  587. */
  588. bool operator<(const Key& other) const;
  589. /**
  590. * Equality operator. Compares the literal of `this` with the literal of `other`.
  591. * This method is used in representing the mapping from key lists to patterns
  592. * in a message with variants, and is not expected to be useful otherwise.
  593. *
  594. * @param other The Key to compare to this one.
  595. * @return true if either both `Key`s are wildcards, or `this.asLiteral()`
  596. * == `other.asLiteral()`.
  597. * Returns false otherwise.
  598. *
  599. * @internal ICU 75 technology preview
  600. * @deprecated This API is for technology preview only.
  601. */
  602. bool operator==(const Key& other) const;
  603. /**
  604. * Destructor.
  605. *
  606. * @internal ICU 75 technology preview
  607. * @deprecated This API is for technology preview only.
  608. */
  609. virtual ~Key();
  610. private:
  611. /* const */ std::optional<Literal> contents;
  612. }; // class Key
  613. } // namespace data_model
  614. } // namespace message2
  615. /// @cond DOXYGEN_IGNORE
  616. // Export an explicit template instantiation of the LocalPointer that is used as a
  617. // data member of various MFDataModel classes.
  618. // (When building DLLs for Windows this is required.)
  619. // (See measunit_impl.h, datefmt.h, collationiterator.h, erarules.h and others
  620. // for similar examples.)
  621. #if U_PF_WINDOWS <= U_PLATFORM && U_PLATFORM <= U_PF_CYGWIN
  622. template class U_I18N_API LocalPointerBase<message2::data_model::Key>;
  623. template class U_I18N_API LocalArray<message2::data_model::Key>;
  624. #endif
  625. /// @endcond
  626. namespace message2 {
  627. namespace data_model {
  628. /**
  629. * The `SelectorKeys` class represents the key list for a single variant.
  630. * It corresponds to the `keys` array in the `Variant` interface
  631. * defined in https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model.md#messages
  632. *
  633. * `SelectorKeys` is immutable, copyable and movable.
  634. *
  635. * @internal ICU 75 technology preview
  636. * @deprecated This API is for technology preview only.
  637. */
  638. class U_I18N_API SelectorKeys : public UObject {
  639. public:
  640. /**
  641. * Returns the underlying list of keys.
  642. *
  643. * @return The list of keys for this variant.
  644. * Returns an empty list if allocating this `SelectorKeys`
  645. * object previously failed.
  646. *
  647. * @internal ICU 75 technology preview
  648. * @deprecated This API is for technology preview only.
  649. */
  650. std::vector<Key> getKeys() const {
  651. return toStdVector<Key>(keys.getAlias(), len);
  652. }
  653. /**
  654. * The mutable `SelectorKeys::Builder` class allows the key list to be constructed
  655. * one key at a time.
  656. *
  657. * Builder is not copyable or movable.
  658. *
  659. * @internal ICU 75 technology preview
  660. * @deprecated This API is for technology preview only.
  661. */
  662. class U_I18N_API Builder : public UMemory {
  663. private:
  664. friend class SelectorKeys;
  665. UVector* keys; // This is a raw pointer and not a LocalPointer<UVector> to avoid undefined behavior warnings,
  666. // since UVector is forward-declared
  667. // The vector owns its elements
  668. public:
  669. /**
  670. * Adds a single key to the list.
  671. *
  672. * @param key The key to be added. Passed by move
  673. * @param status Input/output error code
  674. * @return A reference to the builder.
  675. *
  676. * @internal ICU 75 technology preview
  677. * @deprecated This API is for technology preview only.
  678. */
  679. Builder& add(Key&& key, UErrorCode& status) noexcept;
  680. /**
  681. * Constructs a new immutable `SelectorKeys` using the list of keys
  682. * set with previous `add()` calls.
  683. *
  684. * The builder object (`this`) can still be used after calling `build()`.
  685. *
  686. * @param status Input/output error code
  687. * @return The new SelectorKeys object
  688. *
  689. * @internal ICU 75 technology preview
  690. * @deprecated This API is for technology preview only.
  691. */
  692. SelectorKeys build(UErrorCode& status) const;
  693. /**
  694. * Default constructor.
  695. * Returns a Builder with an empty list of keys.
  696. *
  697. * @param status Input/output error code
  698. *
  699. * @internal ICU 75 technology preview
  700. * @deprecated This API is for technology preview only.
  701. */
  702. Builder(UErrorCode& status);
  703. /**
  704. * Destructor.
  705. *
  706. * @internal ICU 75 technology preview
  707. * @deprecated This API is for technology preview only.
  708. */
  709. virtual ~Builder();
  710. Builder(const Builder&) = delete;
  711. Builder& operator=(const Builder&) = delete;
  712. Builder(Builder&&) = delete;
  713. Builder& operator=(Builder&&) = delete;
  714. }; // class SelectorKeys::Builder
  715. /**
  716. * Less than operator. Compares the two key lists lexicographically.
  717. * This method makes it possible for a `SelectorKeys` to be used as a map
  718. * key, which allows variants to be represented as a map. It is not expected
  719. * to be useful otherwise.
  720. *
  721. * @param other The SelectorKeys to compare to this one.
  722. * @return true if `this` is less than `other`, comparing the two key lists
  723. * lexicographically.
  724. * Returns false otherwise.
  725. *
  726. * @internal ICU 75 technology preview
  727. * @deprecated This API is for technology preview only.
  728. */
  729. bool operator<(const SelectorKeys& other) const;
  730. /**
  731. * Default constructor.
  732. * Puts the SelectorKeys into a valid but undefined state.
  733. *
  734. * @internal ICU 75 technology preview
  735. * @deprecated This API is for technology preview only.
  736. */
  737. SelectorKeys() : len(0) {}
  738. /**
  739. * Non-member swap function.
  740. * @param s1 will get s2's contents
  741. * @param s2 will get s1's contents
  742. *
  743. * @internal ICU 75 technology preview
  744. * @deprecated This API is for technology preview only.
  745. */
  746. friend inline void swap(SelectorKeys& s1, SelectorKeys& s2) noexcept {
  747. using std::swap;
  748. swap(s1.len, s2.len);
  749. swap(s1.keys, s2.keys);
  750. }
  751. /**
  752. * Copy constructor.
  753. *
  754. * @internal ICU 75 technology preview
  755. * @deprecated This API is for technology preview only.
  756. */
  757. SelectorKeys(const SelectorKeys& other);
  758. /**
  759. * Assignment operator.
  760. *
  761. * @internal ICU 75 technology preview
  762. * @deprecated This API is for technology preview only.
  763. */
  764. SelectorKeys& operator=(SelectorKeys other) noexcept;
  765. /**
  766. * Destructor.
  767. *
  768. * @internal ICU 75 technology preview
  769. * @deprecated This API is for technology preview only.
  770. */
  771. virtual ~SelectorKeys();
  772. private:
  773. friend class Builder;
  774. friend class message2::Checker;
  775. friend class message2::MessageFormatter;
  776. friend class message2::Serializer;
  777. /* const */ LocalArray<Key> keys;
  778. /* const */ int32_t len;
  779. const Key* getKeysInternal() const;
  780. SelectorKeys(const UVector& ks, UErrorCode& status);
  781. }; // class SelectorKeys
  782. } // namespace data_model
  783. namespace data_model {
  784. class Operator;
  785. /**
  786. * An `Option` pairs an option name with an Operand.
  787. *
  788. * `Option` is immutable, copyable and movable.
  789. *
  790. * @internal ICU 75 technology preview
  791. * @deprecated This API is for technology preview only.
  792. */
  793. class U_I18N_API Option : public UObject {
  794. public:
  795. /**
  796. * Accesses the right-hand side of the option.
  797. *
  798. * @return A reference to the operand.
  799. *
  800. * @internal ICU 75 technology preview
  801. * @deprecated This API is for technology preview only.
  802. */
  803. const Operand& getValue() const { return rand; }
  804. /**
  805. * Accesses the left-hand side of the option.
  806. *
  807. * @return A reference to the option name.
  808. *
  809. * @internal ICU 75 technology preview
  810. * @deprecated This API is for technology preview only.
  811. */
  812. const UnicodeString& getName() const { return name; }
  813. /**
  814. * Constructor. Returns an `Option` representing the
  815. * named option "name=rand".
  816. *
  817. * @param n The name of the option.
  818. * @param r The value of the option.
  819. *
  820. * @internal ICU 75 technology preview
  821. * @deprecated This API is for technology preview only.
  822. */
  823. Option(const UnicodeString& n, Operand&& r) : name(n), rand(std::move(r)) {}
  824. /**
  825. * Default constructor.
  826. * Returns an Option in a valid but undefined state.
  827. *
  828. * @internal ICU 75 technology preview
  829. * @deprecated This API is for technology preview only.
  830. */
  831. Option() {}
  832. /**
  833. * Non-member swap function.
  834. * @param o1 will get o2's contents
  835. * @param o2 will get o1's contents
  836. *
  837. * @internal ICU 75 technology preview
  838. * @deprecated This API is for technology preview only.
  839. */
  840. friend inline void swap(Option& o1, Option& o2) noexcept {
  841. using std::swap;
  842. swap(o1.name, o2.name);
  843. swap(o1.rand, o2.rand);
  844. }
  845. /**
  846. * Copy constructor.
  847. *
  848. * @internal ICU 75 technology preview
  849. * @deprecated This API is for technology preview only.
  850. */
  851. Option(const Option& other);
  852. /**
  853. * Assignment operator
  854. *
  855. * @internal ICU 75 technology preview
  856. * @deprecated This API is for technology preview only.
  857. */
  858. Option& operator=(Option other) noexcept;
  859. /**
  860. * Destructor.
  861. *
  862. * @internal ICU 75 technology preview
  863. * @deprecated This API is for technology preview only.
  864. */
  865. virtual ~Option();
  866. private:
  867. /* const */ UnicodeString name;
  868. /* const */ Operand rand;
  869. }; // class Option
  870. } // namespace data_model
  871. } // namespace message2
  872. /// @cond DOXYGEN_IGNORE
  873. // Export an explicit template instantiation of the LocalPointer that is used as a
  874. // data member of various MFDataModel classes.
  875. // (When building DLLs for Windows this is required.)
  876. // (See measunit_impl.h, datefmt.h, collationiterator.h, erarules.h and others
  877. // for similar examples.)
  878. #if U_PF_WINDOWS <= U_PLATFORM && U_PLATFORM <= U_PF_CYGWIN
  879. template class U_I18N_API LocalPointerBase<message2::data_model::Option>;
  880. template class U_I18N_API LocalArray<message2::data_model::Option>;
  881. #endif
  882. /// @endcond
  883. namespace message2 {
  884. namespace data_model {
  885. // Internal only
  886. #ifndef U_IN_DOXYGEN
  887. // Options
  888. // This is a wrapper class around a vector of options that provides lookup operations
  889. class U_I18N_API OptionMap : public UObject {
  890. public:
  891. int32_t size() const;
  892. // Needs to take an error code b/c an earlier copy might have failed
  893. const Option& getOption(int32_t, UErrorCode&) const;
  894. friend inline void swap(OptionMap& m1, OptionMap& m2) noexcept {
  895. using std::swap;
  896. swap(m1.bogus, m2.bogus);
  897. swap(m1.options, m2.options);
  898. swap(m1.len, m2.len);
  899. }
  900. OptionMap() : len(0) {}
  901. OptionMap(const OptionMap&);
  902. OptionMap& operator=(OptionMap);
  903. std::vector<Option> getOptions() const {
  904. return toStdVector<Option>(options.getAlias(), len);
  905. }
  906. OptionMap(const UVector&, UErrorCode&);
  907. OptionMap(Option*, int32_t);
  908. virtual ~OptionMap();
  909. class U_I18N_API Builder : public UObject {
  910. private:
  911. UVector* options;
  912. bool checkDuplicates = true;
  913. public:
  914. Builder& add(Option&& opt, UErrorCode&);
  915. Builder(UErrorCode&);
  916. static Builder attributes(UErrorCode&);
  917. // As this class is private, build() is destructive
  918. OptionMap build(UErrorCode&);
  919. friend inline void swap(Builder& m1, Builder& m2) noexcept {
  920. using std::swap;
  921. swap(m1.options, m2.options);
  922. swap(m1.checkDuplicates, m2.checkDuplicates);
  923. }
  924. Builder(Builder&&);
  925. Builder(const Builder&) = delete;
  926. Builder& operator=(Builder) noexcept;
  927. virtual ~Builder();
  928. }; // class OptionMap::Builder
  929. private:
  930. friend class message2::Serializer;
  931. bool bogus = false;
  932. LocalArray<Option> options;
  933. int32_t len;
  934. }; // class OptionMap
  935. #endif
  936. // Internal use only
  937. #ifndef U_IN_DOXYGEN
  938. class U_I18N_API Callable : public UObject {
  939. public:
  940. friend inline void swap(Callable& c1, Callable& c2) noexcept {
  941. using std::swap;
  942. swap(c1.name, c2.name);
  943. swap(c1.options, c2.options);
  944. }
  945. const FunctionName& getName() const { return name; }
  946. const OptionMap& getOptions() const { return options; }
  947. Callable(const FunctionName& f, const OptionMap& opts) : name(f), options(opts) {}
  948. Callable& operator=(Callable) noexcept;
  949. Callable(const Callable&);
  950. Callable() = default;
  951. virtual ~Callable();
  952. private:
  953. /* const */ FunctionName name;
  954. /* const */ OptionMap options;
  955. };
  956. #endif
  957. } // namespace data_model
  958. } // namespace message2
  959. U_NAMESPACE_END
  960. /// @cond DOXYGEN_IGNORE
  961. // Export an explicit template instantiation of the std::variant that is used as a
  962. // data member of various MFDataModel classes.
  963. // (When building DLLs for Windows this is required.)
  964. // (See measunit_impl.h, datefmt.h, collationiterator.h, erarules.h and others
  965. // for similar examples.)
  966. #if U_PF_WINDOWS <= U_PLATFORM && U_PLATFORM <= U_PF_CYGWIN
  967. #if defined(U_REAL_MSVC) && defined(_MSVC_STL_VERSION)
  968. template class U_I18N_API std::_Variant_storage_<false, icu::message2::data_model::Reserved,icu::message2::data_model::Callable>;
  969. #endif
  970. template class U_I18N_API std::variant<icu::message2::data_model::Reserved,icu::message2::data_model::Callable>;
  971. #endif
  972. /// @endcond
  973. U_NAMESPACE_BEGIN
  974. namespace message2 {
  975. namespace data_model {
  976. /**
  977. * The `Operator` class corresponds to the `FunctionRef | Reserved` type in the
  978. * `Expression` interface defined in
  979. * https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model.md#patterns
  980. *
  981. * It represents the annotation that an expression can have: either a function name paired
  982. * with a map from option names to operands (possibly empty),
  983. * or a reserved sequence, which has no meaning and results in an error if the formatter
  984. * is invoked.
  985. *
  986. * `Operator` is immutable, copyable and movable.
  987. *
  988. * @internal ICU 75 technology preview
  989. * @deprecated This API is for technology preview only.
  990. */
  991. class U_I18N_API Operator : public UObject {
  992. public:
  993. /**
  994. * Determines if this operator is a reserved annotation.
  995. *
  996. * @return true if and only if this operator represents a reserved sequence.
  997. *
  998. * @internal ICU 75 technology preview
  999. * @deprecated This API is for technology preview only.
  1000. */
  1001. UBool isReserved() const { return std::holds_alternative<Reserved>(contents); }
  1002. /**
  1003. * Accesses the function name.
  1004. * Precondition: !isReserved()
  1005. *
  1006. * @return The function name of this operator.
  1007. *
  1008. * @internal ICU 75 technology preview
  1009. * @deprecated This API is for technology preview only.
  1010. */
  1011. const FunctionName& getFunctionName() const;
  1012. /**
  1013. * Accesses the underlying reserved sequence.
  1014. * Precondition: isReserved()
  1015. *
  1016. * @return The reserved sequence represented by this operator.
  1017. *
  1018. * @internal ICU 75 technology preview
  1019. * @deprecated This API is for technology preview only.
  1020. */
  1021. const Reserved& asReserved() const;
  1022. /**
  1023. * Accesses function options.
  1024. * Precondition: !isReserved()
  1025. *
  1026. * @return A vector of function options for this operator.
  1027. *
  1028. * @internal ICU 75 technology preview
  1029. * @deprecated This API is for technology preview only.
  1030. */
  1031. std::vector<Option> getOptions() const {
  1032. const Callable* f = std::get_if<Callable>(&contents);
  1033. // This case should never happen, as the precondition is !isReserved()
  1034. if (f == nullptr) { return {}; }
  1035. const OptionMap& opts = f->getOptions();
  1036. return opts.getOptions();
  1037. }
  1038. /**
  1039. * The mutable `Operator::Builder` class allows the operator to be constructed
  1040. * incrementally.
  1041. *
  1042. * Builder is not copyable or movable.
  1043. *
  1044. * @internal ICU 75 technology preview
  1045. * @deprecated This API is for technology preview only.
  1046. */
  1047. class U_I18N_API Builder : public UMemory {
  1048. private:
  1049. friend class Operator;
  1050. bool isReservedSequence = false;
  1051. bool hasFunctionName = false;
  1052. bool hasOptions = false;
  1053. Reserved asReserved;
  1054. FunctionName functionName;
  1055. OptionMap::Builder options;
  1056. public:
  1057. /**
  1058. * Sets this operator to be a reserved sequence.
  1059. * If a function name and/or options were previously set,
  1060. * clears them.
  1061. *
  1062. * @param reserved The reserved sequence to set as the contents of this Operator.
  1063. * (Passed by move.)
  1064. * @return A reference to the builder.
  1065. *
  1066. * @internal ICU 75 technology preview
  1067. * @deprecated This API is for technology preview only.
  1068. */
  1069. Builder& setReserved(Reserved&& reserved);
  1070. /**
  1071. * Sets this operator to be a function annotation and sets its name
  1072. * to `func`.
  1073. * If a reserved sequence was previously set, clears it.
  1074. *
  1075. * @param func The function name.
  1076. * @return A reference to the builder.
  1077. *
  1078. * @internal ICU 75 technology preview
  1079. * @deprecated This API is for technology preview only.
  1080. */
  1081. Builder& setFunctionName(FunctionName&& func);
  1082. /**
  1083. * Sets this operator to be a function annotation and adds a
  1084. * single option.
  1085. * If a reserved sequence was previously set, clears it.
  1086. *
  1087. * @param key The name of the option.
  1088. * @param value The value (right-hand side) of the option.
  1089. * @param status Input/output error code.
  1090. * @return A reference to the builder.
  1091. *
  1092. * @internal ICU 75 technology preview
  1093. * @deprecated This API is for technology preview only.
  1094. */
  1095. Builder& addOption(const UnicodeString &key, Operand&& value, UErrorCode& status) noexcept;
  1096. /**
  1097. * Constructs a new immutable `Operator` using the `reserved` annotation
  1098. * or the function name and options that were previously set.
  1099. * If neither `setReserved()` nor `setFunctionName()` was previously
  1100. * called, then `status` is set to U_INVALID_STATE_ERROR.
  1101. *
  1102. * The builder object (`this`) can still be used after calling `build()`.
  1103. *
  1104. * The `build()` method is non-const for internal implementation reasons,
  1105. * but is observably const.
  1106. *
  1107. * @param status Input/output error code.
  1108. * @return The new Operator
  1109. *
  1110. * @internal ICU 75 technology preview
  1111. * @deprecated This API is for technology preview only.
  1112. */
  1113. Operator build(UErrorCode& status);
  1114. /**
  1115. * Default constructor.
  1116. * Returns a Builder with no function name or reserved sequence set.
  1117. *
  1118. * @param status Input/output error code.
  1119. *
  1120. * @internal ICU 75 technology preview
  1121. * @deprecated This API is for technology preview only.
  1122. */
  1123. Builder(UErrorCode& status);
  1124. /**
  1125. * Destructor.
  1126. *
  1127. * @internal ICU 75 technology preview
  1128. * @deprecated This API is for technology preview only.
  1129. */
  1130. virtual ~Builder();
  1131. Builder(const Builder&) = delete;
  1132. Builder& operator=(const Builder&) = delete;
  1133. Builder(Builder&&) = delete;
  1134. Builder& operator=(Builder&&) = delete;
  1135. }; // class Operator::Builder
  1136. /**
  1137. * Copy constructor.
  1138. *
  1139. * @internal ICU 75 technology preview
  1140. * @deprecated This API is for technology preview only.
  1141. */
  1142. Operator(const Operator& other) noexcept;
  1143. /**
  1144. * Non-member swap function.
  1145. * @param o1 will get o2's contents
  1146. * @param o2 will get o1's contents
  1147. *
  1148. * @internal ICU 75 technology preview
  1149. * @deprecated This API is for technology preview only.
  1150. */
  1151. friend inline void swap(Operator& o1, Operator& o2) noexcept {
  1152. using std::swap;
  1153. swap(o1.contents, o2.contents);
  1154. }
  1155. /**
  1156. * Assignment operator.
  1157. *
  1158. * @internal ICU 75 technology preview
  1159. * @deprecated This API is for technology preview only.
  1160. */
  1161. Operator& operator=(Operator) noexcept;
  1162. /**
  1163. * Default constructor.
  1164. * Puts the Operator into a valid but undefined state.
  1165. *
  1166. * @internal ICU 75 technology preview
  1167. * @deprecated This API is for technology preview only.
  1168. */
  1169. Operator() : contents(Reserved()) {}
  1170. /**
  1171. * Destructor.
  1172. *
  1173. * @internal ICU 75 technology preview
  1174. * @deprecated This API is for technology preview only.
  1175. */
  1176. virtual ~Operator();
  1177. private:
  1178. friend class Binding;
  1179. friend class Builder;
  1180. friend class message2::Checker;
  1181. friend class message2::MessageFormatter;
  1182. friend class message2::Serializer;
  1183. // Function call constructor
  1184. Operator(const FunctionName& f, const UVector& options, UErrorCode&);
  1185. // Reserved sequence constructor
  1186. Operator(const Reserved& r) : contents(r) {}
  1187. const OptionMap& getOptionsInternal() const;
  1188. Operator(const FunctionName&, const OptionMap&);
  1189. /* const */ std::variant<Reserved, Callable> contents;
  1190. }; // class Operator
  1191. } // namespace data_model
  1192. } // namespace message2
  1193. U_NAMESPACE_END
  1194. /// @cond DOXYGEN_IGNORE
  1195. // Export an explicit template instantiation of the std::optional that is used as a
  1196. // data member of various MFDataModel classes.
  1197. // (When building DLLs for Windows this is required.)
  1198. // (See measunit_impl.h, datefmt.h, collationiterator.h, erarules.h and others
  1199. // for similar examples.)
  1200. #if U_PF_WINDOWS <= U_PLATFORM && U_PLATFORM <= U_PF_CYGWIN
  1201. template class U_I18N_API std::optional<icu::message2::data_model::Operator>;
  1202. template class U_I18N_API std::optional<icu::message2::data_model::Reserved>;
  1203. #endif
  1204. /// @endcond
  1205. U_NAMESPACE_BEGIN
  1206. namespace message2 {
  1207. namespace data_model {
  1208. // Internal only
  1209. typedef enum UMarkupType {
  1210. UMARKUP_OPEN = 0,
  1211. UMARKUP_CLOSE,
  1212. UMARKUP_STANDALONE,
  1213. UMARKUP_COUNT
  1214. } UMarkupType;
  1215. /**
  1216. * The `Markup` class corresponds to the `markup` nonterminal in the MessageFormat 2
  1217. * grammar and the `markup` interface defined in
  1218. * https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model/message.json
  1219. *
  1220. * `Markup` is immutable, copyable and movable.
  1221. *
  1222. * @internal ICU 75 technology preview
  1223. * @deprecated This API is for technology preview only.
  1224. */
  1225. class U_I18N_API Markup : public UObject {
  1226. public:
  1227. /**
  1228. * Checks if this markup is an opening tag.
  1229. *
  1230. * @return True if and only if this represents an opening tag.
  1231. *
  1232. * @internal ICU 75 technology preview
  1233. * @deprecated This API is for technology preview only.
  1234. */
  1235. UBool isOpen() const { return (type == UMARKUP_OPEN); }
  1236. /**
  1237. * Checks if this markup is an closing tag.
  1238. *
  1239. * @return True if and only if this represents an closing tag.
  1240. *
  1241. * @internal ICU 75 technology preview
  1242. * @deprecated This API is for technology preview only.
  1243. */
  1244. UBool isClose() const { return (type == UMARKUP_CLOSE); }
  1245. /**
  1246. * Checks if this markup is an standalone tag.
  1247. *
  1248. * @return True if and only if this represents a standalone tag.
  1249. *
  1250. * @internal ICU 75 technology preview
  1251. * @deprecated This API is for technology preview only.
  1252. */
  1253. UBool isStandalone() const { return (type == UMARKUP_STANDALONE); }
  1254. /**
  1255. * Gets the name of this markup
  1256. *
  1257. * @return A reference to the string identifying the markup
  1258. *
  1259. * @internal ICU 75 technology preview
  1260. * @deprecated This API is for technology preview only.
  1261. */
  1262. const UnicodeString& getName() const { return name; }
  1263. /**
  1264. * Gets the options of this markup
  1265. *
  1266. * @return A reference to the string identifying the markup
  1267. *
  1268. * @internal ICU 75 technology preview
  1269. * @deprecated This API is for technology preview only.
  1270. */
  1271. std::vector<Option> getOptions() const { return options.getOptions(); }
  1272. /**
  1273. * Gets the attributes of this markup
  1274. *
  1275. * @return A vector of attributes
  1276. *
  1277. * @internal ICU 75 technology preview
  1278. * @deprecated This API is for technology preview only.
  1279. */
  1280. std::vector<Option> getAttributes() const { return attributes.getOptions(); }
  1281. /**
  1282. * Default constructor.
  1283. * Puts the Markup into a valid but undefined state.
  1284. *
  1285. * @internal ICU 75 technology preview
  1286. * @deprecated This API is for technology preview only.
  1287. */
  1288. Markup() {}
  1289. /**
  1290. * Destructor.
  1291. *
  1292. * @internal ICU 75 technology preview
  1293. * @deprecated This API is for technology preview only.
  1294. */
  1295. virtual ~Markup();
  1296. /**
  1297. * The mutable `Markup::Builder` class allows the markup to be constructed
  1298. * incrementally.
  1299. *
  1300. * Builder is not copyable or movable.
  1301. *
  1302. * @internal ICU 75 technology preview
  1303. * @deprecated This API is for technology preview only.
  1304. */
  1305. class U_I18N_API Builder : public UMemory {
  1306. private:
  1307. friend class Markup;
  1308. UnicodeString name;
  1309. OptionMap::Builder options;
  1310. OptionMap::Builder attributes;
  1311. UMarkupType type = UMARKUP_COUNT;
  1312. public:
  1313. /**
  1314. * Sets the name of this markup.
  1315. *
  1316. * @param n A string representing the name.
  1317. * @return A reference to the builder.
  1318. *
  1319. * @internal ICU 75 technology preview
  1320. * @deprecated This API is for technology preview only.
  1321. */
  1322. Builder& setName(const UnicodeString& n) { name = n; return *this; }
  1323. /**
  1324. * Sets this to be an opening markup.
  1325. *
  1326. * @return A reference to the builder.
  1327. *
  1328. * @internal ICU 75 technology preview
  1329. * @deprecated This API is for technology preview only.
  1330. */
  1331. Builder& setOpen() { type = UMARKUP_OPEN; return *this; }
  1332. /**
  1333. * Sets this to be an closing markup.
  1334. *
  1335. * @return A reference to the builder.
  1336. *
  1337. * @internal ICU 75 technology preview
  1338. * @deprecated This API is for technology preview only.
  1339. */
  1340. Builder& setClose() { type = UMARKUP_CLOSE; return *this; }
  1341. /**
  1342. * Sets this to be a standalone markup.
  1343. *
  1344. * @return A reference to the builder.
  1345. *
  1346. * @internal ICU 75 technology preview
  1347. * @deprecated This API is for technology preview only.
  1348. */
  1349. Builder& setStandalone() { type = UMARKUP_STANDALONE; return *this; }
  1350. /**
  1351. * Adds a single option.
  1352. *
  1353. * @param key The name of the option.
  1354. * @param value The value (right-hand side) of the option.
  1355. * @param status Input/output error code.
  1356. * @return A reference to the builder.
  1357. *
  1358. * @internal ICU 75 technology preview
  1359. * @deprecated This API is for technology preview only.
  1360. */
  1361. Builder& addOption(const UnicodeString &key, Operand&& value, UErrorCode& status);
  1362. /**
  1363. * Adds a single attribute.
  1364. *
  1365. * @param key The name of the attribute.
  1366. * @param value The value (right-hand side) of the attribute.
  1367. * @param status Input/output error code.
  1368. * @return A reference to the builder.
  1369. *
  1370. * @internal ICU 75 technology preview
  1371. * @deprecated This API is for technology preview only.
  1372. */
  1373. Builder& addAttribute(const UnicodeString &key, Operand&& value, UErrorCode& status);
  1374. /**
  1375. * Constructs a new immutable `Markup` using the name and type
  1376. * and (optionally) options and attributes that were previously set.
  1377. * If `setName()` and at least one of `setOpen()`, `setClose()`, and `setStandalone()`
  1378. * were not previously called,
  1379. * then `status` is set to U_INVALID_STATE_ERROR.
  1380. *
  1381. * The builder object (`this`) can still be used after calling `build()`.
  1382. * The `build()` method is non-const for internal implementation reasons,
  1383. * but is observably const.
  1384. *
  1385. * @param status Input/output error code.
  1386. * @return The new Markup.
  1387. *
  1388. * @internal ICU 75 technology preview
  1389. * @deprecated This API is for technology preview only.
  1390. */
  1391. Markup build(UErrorCode& status);
  1392. /**
  1393. * Default constructor.
  1394. * Returns a Builder with no name, type, options, or attributes set.
  1395. *
  1396. * @param status Input/output error code.
  1397. *
  1398. * @internal ICU 75 technology preview
  1399. * @deprecated This API is for technology preview only.
  1400. */
  1401. Builder(UErrorCode& status);
  1402. /**
  1403. * Destructor.
  1404. *
  1405. * @internal ICU 75 technology preview
  1406. * @deprecated This API is for technology preview only.
  1407. */
  1408. virtual ~Builder();
  1409. Builder(const Builder&) = delete;
  1410. Builder& operator=(const Builder&) = delete;
  1411. Builder(Builder&&) = delete;
  1412. Builder& operator=(Builder&&) = delete;
  1413. }; // class Markup::Builder
  1414. private:
  1415. friend class Builder;
  1416. friend class message2::Serializer;
  1417. UMarkupType type;
  1418. UnicodeString name;
  1419. OptionMap options;
  1420. OptionMap attributes;
  1421. const OptionMap& getOptionsInternal() const { return options; }
  1422. const OptionMap& getAttributesInternal() const { return attributes; }
  1423. Markup(UMarkupType, UnicodeString, OptionMap&&, OptionMap&&);
  1424. }; // class Markup
  1425. /**
  1426. * The `Expression` class corresponds to the `expression` nonterminal in the MessageFormat 2
  1427. * grammar and the `Expression` interface defined in
  1428. * https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model.md#patterns
  1429. *
  1430. * It represents either an operand with no annotation; an annotation with no operand;
  1431. * or an operand annotated with an annotation.
  1432. *
  1433. * `Expression` is immutable, copyable and movable.
  1434. *
  1435. * @internal ICU 75 technology preview
  1436. * @deprecated This API is for technology preview only.
  1437. */
  1438. class U_I18N_API Expression : public UObject {
  1439. public:
  1440. /**
  1441. * Checks if this expression is an annotation
  1442. * with no operand.
  1443. *
  1444. * @return True if and only if the expression has
  1445. * an annotation and has no operand.
  1446. *
  1447. * @internal ICU 75 technology preview
  1448. * @deprecated This API is for technology preview only.
  1449. */
  1450. UBool isStandaloneAnnotation() const;
  1451. /**
  1452. * Checks if this expression has a function
  1453. * annotation (with or without an operand). A reserved
  1454. * sequence is not a function annotation.
  1455. *
  1456. * @return True if and only if the expression has an annotation
  1457. * that is a function.
  1458. *
  1459. * @internal ICU 75 technology preview
  1460. * @deprecated This API is for technology preview only.
  1461. */
  1462. UBool isFunctionCall() const;
  1463. /**
  1464. * Returns true if and only if this expression is
  1465. * annotated with a reserved sequence.
  1466. *
  1467. * @return True if and only if the expression has an
  1468. * annotation that is a reserved sequence,
  1469. *
  1470. * @internal ICU 75 technology preview
  1471. * @deprecated This API is for technology preview only.
  1472. */
  1473. UBool isReserved() const;
  1474. /**
  1475. * Accesses the function or reserved sequence
  1476. * annotating this expression.
  1477. * If !(isFunctionCall() || isReserved()), sets
  1478. * `status` to U_INVALID_STATE_ERROR.
  1479. *
  1480. * @param status Input/output error code.
  1481. * @return A non-owned pointer to the operator of this expression,
  1482. * which does not outlive the expression.
  1483. *
  1484. * @internal ICU 75 technology preview
  1485. * @deprecated This API is for technology preview only.
  1486. */
  1487. const Operator* getOperator(UErrorCode& status) const;
  1488. /**
  1489. * Accesses the operand of this expression.
  1490. *
  1491. * @return A reference to the operand of this expression,
  1492. * which may be the null operand.
  1493. *
  1494. * @internal ICU 75 technology preview
  1495. * @deprecated This API is for technology preview only.
  1496. */
  1497. const Operand& getOperand() const;
  1498. /**
  1499. * Gets the attributes of this expression
  1500. *
  1501. * @return A vector of attributes
  1502. *
  1503. * @internal ICU 75 technology preview
  1504. * @deprecated This API is for technology preview only.
  1505. */
  1506. std::vector<Option> getAttributes() const { return attributes.getOptions(); }
  1507. /**
  1508. * The mutable `Expression::Builder` class allows the operator to be constructed
  1509. * incrementally.
  1510. *
  1511. * Builder is not copyable or movable.
  1512. *
  1513. * @internal ICU 75 technology preview
  1514. * @deprecated This API is for technology preview only.
  1515. */
  1516. class U_I18N_API Builder : public UMemory {
  1517. private:
  1518. friend class Expression;
  1519. bool hasOperand = false;
  1520. bool hasOperator = false;
  1521. Operand rand;
  1522. Operator rator;
  1523. OptionMap::Builder attributes;
  1524. public:
  1525. /**
  1526. * Sets the operand of this expression.
  1527. *
  1528. * @param rAnd The operand to set. Passed by move.
  1529. * @return A reference to the builder.
  1530. *
  1531. * @internal ICU 75 technology preview
  1532. * @deprecated This API is for technology preview only.
  1533. */
  1534. Builder& setOperand(Operand&& rAnd);
  1535. /**
  1536. * Sets the operator of this expression.
  1537. *
  1538. * @param rAtor The operator to set. Passed by move.
  1539. * @return A reference to the builder.
  1540. *
  1541. * @internal ICU 75 technology preview
  1542. * @deprecated This API is for technology preview only.
  1543. */
  1544. Builder& setOperator(Operator&& rAtor);
  1545. /**
  1546. * Adds a single attribute.
  1547. *
  1548. * @param key The name of the attribute.
  1549. * @param value The value (right-hand side) of the attribute.
  1550. * @param status Input/output error code.
  1551. * @return A reference to the builder.
  1552. *
  1553. * @internal ICU 75 technology preview
  1554. * @deprecated This API is for technology preview only.
  1555. */
  1556. Builder& addAttribute(const UnicodeString &key, Operand&& value, UErrorCode& status);
  1557. /**
  1558. * Constructs a new immutable `Expression` using the operand and operator that
  1559. * were previously set. If neither `setOperand()` nor `setOperator()` was
  1560. * previously called, or if `setOperand()` was called with the null operand
  1561. * and `setOperator()` was never called, then `status` is set to
  1562. * U_INVALID_STATE_ERROR.
  1563. *
  1564. * The builder object (`this`) can still be used after calling `build()`.
  1565. * The `build()` method is non-const for internal implementation reasons,
  1566. * but is observably const.
  1567. * @param status Input/output error code.
  1568. * @return The new Expression.
  1569. *
  1570. * @internal ICU 75 technology preview
  1571. * @deprecated This API is for technology preview only.
  1572. */
  1573. Expression build(UErrorCode& status);
  1574. /**
  1575. * Default constructor.
  1576. * Returns a Builder with no operator or operand set.
  1577. *
  1578. * @param status Input/output error code.
  1579. *
  1580. * @internal ICU 75 technology preview
  1581. * @deprecated This API is for technology preview only.
  1582. */
  1583. Builder(UErrorCode& status);
  1584. /**
  1585. * Destructor.
  1586. *
  1587. * @internal ICU 75 technology preview
  1588. * @deprecated This API is for technology preview only.
  1589. */
  1590. virtual ~Builder();
  1591. Builder(const Builder&) = delete;
  1592. Builder& operator=(const Builder&) = delete;
  1593. Builder(Builder&&) = delete;
  1594. Builder& operator=(Builder&&) = delete;
  1595. }; // class Expression::Builder
  1596. /**
  1597. * Non-member swap function.
  1598. * @param e1 will get e2's contents
  1599. * @param e2 will get e1's contents
  1600. *
  1601. * @internal ICU 75 technology preview
  1602. * @deprecated This API is for technology preview only.
  1603. */
  1604. friend inline void swap(Expression& e1, Expression& e2) noexcept {
  1605. using std::swap;
  1606. swap(e1.rator, e2.rator);
  1607. swap(e1.rand, e2.rand);
  1608. swap(e1.attributes, e2.attributes);
  1609. }
  1610. /**
  1611. * Copy constructor.
  1612. *
  1613. * @internal ICU 75 technology preview
  1614. * @deprecated This API is for technology preview only.
  1615. */
  1616. Expression(const Expression& other);
  1617. /**
  1618. * Assignment operator.
  1619. *
  1620. * @internal ICU 75 technology preview
  1621. * @deprecated This API is for technology preview only.
  1622. */
  1623. Expression& operator=(Expression) noexcept;
  1624. /**
  1625. * Default constructor.
  1626. * Puts the Expression into a valid but undefined state.
  1627. *
  1628. * @internal ICU 75 technology preview
  1629. * @deprecated This API is for technology preview only.
  1630. */
  1631. Expression();
  1632. /**
  1633. * Destructor.
  1634. *
  1635. * @internal ICU 75 technology preview
  1636. * @deprecated This API is for technology preview only.
  1637. */
  1638. virtual ~Expression();
  1639. private:
  1640. friend class message2::Serializer;
  1641. /*
  1642. Internally, an expression is represented as the application of an optional operator to an operand.
  1643. The operand is always present; for function calls with no operand, it's represented
  1644. as an operand for which `isNull()` is true.
  1645. Operator | Operand
  1646. --------------------------------
  1647. { |42| :fun opt=value } => (FunctionName=fun, | Literal(quoted=true, contents="42")
  1648. options={opt: value})
  1649. { abcd } => null | Literal(quoted=false, contents="abcd")
  1650. { : fun opt=value } => (FunctionName=fun,
  1651. options={opt: value}) | NullOperand()
  1652. */
  1653. Expression(const Operator &rAtor, const Operand &rAnd, const OptionMap& attrs) : rator(rAtor), rand(rAnd), attributes(attrs) {}
  1654. Expression(const Operand &rAnd, const OptionMap& attrs) : rator(std::nullopt), rand(Operand(rAnd)), attributes(attrs) {}
  1655. Expression(const Operator &rAtor, const OptionMap& attrs) : rator(rAtor), rand(), attributes(attrs) {}
  1656. /* const */ std::optional<Operator> rator;
  1657. /* const */ Operand rand;
  1658. /* const */ OptionMap attributes;
  1659. const OptionMap& getAttributesInternal() const { return attributes; }
  1660. }; // class Expression
  1661. } // namespace data_model
  1662. } // namespace message2
  1663. /// @cond DOXYGEN_IGNORE
  1664. // Export an explicit template instantiation of the LocalPointer that is used as a
  1665. // data member of various MFDataModel classes.
  1666. // (When building DLLs for Windows this is required.)
  1667. // (See measunit_impl.h, datefmt.h, collationiterator.h, erarules.h and others
  1668. // for similar examples.)
  1669. #if U_PF_WINDOWS <= U_PLATFORM && U_PLATFORM <= U_PF_CYGWIN
  1670. template class U_I18N_API LocalPointerBase<message2::data_model::Expression>;
  1671. template class U_I18N_API LocalArray<message2::data_model::Expression>;
  1672. #endif
  1673. /// @endcond
  1674. namespace message2 {
  1675. namespace data_model {
  1676. /**
  1677. * The `UnsupportedStatement` class corresponds to the `reserved-statement` nonterminal in the MessageFormat 2
  1678. * grammar and the `unsupported-statement` type defined in:
  1679. * https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model/message.json#L169
  1680. *
  1681. * It represents a keyword (string) together with an optional
  1682. * `Reserved` annotation and a non-empty list of expressions.
  1683. *
  1684. * `UnsupportedStatement` is immutable, copyable and movable.
  1685. *
  1686. * @internal ICU 75 technology preview
  1687. * @deprecated This API is for technology preview only.
  1688. */
  1689. class U_I18N_API UnsupportedStatement : public UObject {
  1690. public:
  1691. /**
  1692. * Accesses the keyword of this statement.
  1693. *
  1694. * @return A reference to a string.
  1695. *
  1696. * @internal ICU 75 technology preview
  1697. * @deprecated This API is for technology preview only.
  1698. */
  1699. const UnicodeString& getKeyword() const { return keyword; }
  1700. /**
  1701. * Accesses the `reserved-body` of this statement.
  1702. *
  1703. * @param status Input/output error code. Set to U_ILLEGAL_ARGUMENT_ERROR
  1704. * if this unsupported statement has no body.
  1705. * @return A non-owned pointer to a `Reserved` annotation,
  1706. * which is non-null if U_SUCCESS(status).
  1707. *
  1708. * @internal ICU 75 technology preview
  1709. * @deprecated This API is for technology preview only.
  1710. */
  1711. const Reserved* getBody(UErrorCode& status) const;
  1712. /**
  1713. * Accesses the expressions of this statement.
  1714. *
  1715. * @return A vector of Expressions.
  1716. *
  1717. * @internal ICU 75 technology preview
  1718. * @deprecated This API is for technology preview only.
  1719. */
  1720. std::vector<Expression> getExpressions() const {
  1721. if (expressionsLen <= 0 || !expressions.isValid()) {
  1722. // This case should never happen, but we can't use an assertion here
  1723. return {};
  1724. }
  1725. return toStdVector<Expression>(expressions.getAlias(), expressionsLen);
  1726. }
  1727. /**
  1728. * The mutable `UnsupportedStatement::Builder` class allows the statement to be constructed
  1729. * incrementally.
  1730. *
  1731. * Builder is not copyable or movable.
  1732. *
  1733. * @internal ICU 75 technology preview
  1734. * @deprecated This API is for technology preview only.
  1735. */
  1736. class U_I18N_API Builder : public UMemory {
  1737. private:
  1738. friend class UnsupportedStatement;
  1739. friend class message2::Parser;
  1740. UnicodeString keyword;
  1741. std::optional<Reserved> body;
  1742. UVector* expressions; // Vector of expressions;
  1743. // not a LocalPointer for
  1744. // the same reason as in `SelectorKeys::builder`
  1745. public:
  1746. /**
  1747. * Sets the keyword of this statement.
  1748. *
  1749. * @param k The keyword to set.
  1750. * @return A reference to the builder.
  1751. *
  1752. * @internal ICU 75 technology preview
  1753. * @deprecated This API is for technology preview only.
  1754. */
  1755. Builder& setKeyword(const UnicodeString& k);
  1756. /**
  1757. * Sets the body of this statement.
  1758. *
  1759. * @param r The `Reserved` annotation to set as the body. Passed by move.
  1760. * @return A reference to the builder.
  1761. *
  1762. * @internal ICU 75 technology preview
  1763. * @deprecated This API is for technology preview only.
  1764. */
  1765. Builder& setBody(Reserved&& r);
  1766. /**
  1767. * Adds an expression to this statement.
  1768. *
  1769. * @param e The expression to add. Passed by move.
  1770. * @param status Input/output error code.
  1771. * @return A reference to the builder.
  1772. *
  1773. * @internal ICU 75 technology preview
  1774. * @deprecated This API is for technology preview only.
  1775. */
  1776. Builder& addExpression(Expression&& e, UErrorCode& status);
  1777. /**
  1778. * Constructs a new immutable `UnsupportedStatement` using the keyword,
  1779. * body and (if applicable) expressions that were previously set.
  1780. * If `setKeyword()` was never called, then `status` is set to
  1781. * U_INVALID_STATE_ERROR. If `setBody()` was never called, the body is
  1782. * treated as absent (not an error). If `addExpression()` was not called
  1783. * at least once, then `status` is set to U_INVALID_STATE_ERROR.
  1784. *
  1785. * The builder object (`this`) can still be used after calling `build()`.
  1786. * @param status Input/output error code.
  1787. * @return The new UnsupportedStatement
  1788. *
  1789. * @internal ICU 75 technology preview
  1790. * @deprecated This API is for technology preview only.
  1791. */
  1792. UnsupportedStatement build(UErrorCode& status) const;
  1793. /**
  1794. * Default constructor.
  1795. * Returns a Builder with no keyword or body set.
  1796. *
  1797. * @param status Input/output error code.
  1798. *
  1799. * @internal ICU 75 technology preview
  1800. * @deprecated This API is for technology preview only.
  1801. */
  1802. Builder(UErrorCode& status);
  1803. /**
  1804. * Destructor.
  1805. *
  1806. * @internal ICU 75 technology preview
  1807. * @deprecated This API is for technology preview only.
  1808. */
  1809. virtual ~Builder();
  1810. Builder(const Builder&) = delete;
  1811. Builder& operator=(const Builder&) = delete;
  1812. Builder(Builder&&) = delete;
  1813. Builder& operator=(Builder&&) = delete;
  1814. }; // class UnsupportedStatement::Builder
  1815. /**
  1816. * Non-member swap function.
  1817. * @param s1 will get s2's contents
  1818. * @param s2 will get s1's contents
  1819. *
  1820. * @internal ICU 75 technology preview
  1821. * @deprecated This API is for technology preview only.
  1822. */
  1823. friend inline void swap(UnsupportedStatement& s1, UnsupportedStatement& s2) noexcept {
  1824. using std::swap;
  1825. swap(s1.keyword, s2.keyword);
  1826. swap(s1.body, s2.body);
  1827. swap(s1.expressions, s2.expressions);
  1828. swap(s1.expressionsLen, s2.expressionsLen);
  1829. }
  1830. /**
  1831. * Copy constructor.
  1832. *
  1833. * @internal ICU 75 technology preview
  1834. * @deprecated This API is for technology preview only.
  1835. */
  1836. UnsupportedStatement(const UnsupportedStatement& other);
  1837. /**
  1838. * Assignment operator.
  1839. *
  1840. * @internal ICU 75 technology preview
  1841. * @deprecated This API is for technology preview only.
  1842. */
  1843. UnsupportedStatement& operator=(UnsupportedStatement) noexcept;
  1844. /**
  1845. * Default constructor.
  1846. * Puts the UnsupportedStatement into a valid but undefined state.
  1847. *
  1848. * @internal ICU 75 technology preview
  1849. * @deprecated This API is for technology preview only.
  1850. */
  1851. UnsupportedStatement() : expressions(LocalArray<Expression>()) {}
  1852. /**
  1853. * Destructor.
  1854. *
  1855. * @internal ICU 75 technology preview
  1856. * @deprecated This API is for technology preview only.
  1857. */
  1858. virtual ~UnsupportedStatement();
  1859. private:
  1860. friend class message2::Serializer;
  1861. /* const */ UnicodeString keyword;
  1862. /* const */ std::optional<Reserved> body;
  1863. /* const */ LocalArray<Expression> expressions;
  1864. /* const */ int32_t expressionsLen = 0;
  1865. const Expression* getExpressionsInternal() const { return expressions.getAlias(); }
  1866. UnsupportedStatement(const UnicodeString&, const std::optional<Reserved>&, const UVector&, UErrorCode&);
  1867. }; // class UnsupportedStatement
  1868. class Pattern;
  1869. // Despite the comments, `PatternPart` is internal-only
  1870. /**
  1871. * A `PatternPart` is a single element (text or expression) in a `Pattern`.
  1872. * It corresponds to the `body` field of the `Pattern` interface
  1873. * defined in https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model.md#patterns
  1874. *
  1875. * `PatternPart` is immutable, copyable and movable.
  1876. *
  1877. * @internal ICU 75 technology preview
  1878. * @deprecated This API is for technology preview only.
  1879. */
  1880. class PatternPart : public UObject {
  1881. public:
  1882. /**
  1883. * Checks if the part is a text part.
  1884. *
  1885. * @return True if and only if this is a text part.
  1886. *
  1887. * @internal ICU 75 technology preview
  1888. * @deprecated This API is for technology preview only.
  1889. */
  1890. UBool isText() const { return std::holds_alternative<UnicodeString>(piece); }
  1891. /**
  1892. * Checks if the part is a markup part.
  1893. *
  1894. * @return True if and only if this is a markup part.
  1895. *
  1896. * @internal ICU 75 technology preview
  1897. * @deprecated This API is for technology preview only.
  1898. */
  1899. UBool isMarkup() const { return std::holds_alternative<Markup>(piece); }
  1900. /**
  1901. * Checks if the part is an expression part.
  1902. *
  1903. * @return True if and only if this is an expression part.
  1904. *
  1905. * @internal ICU 75 technology preview
  1906. * @deprecated This API is for technology preview only.
  1907. */
  1908. UBool isExpression() const { return std::holds_alternative<Expression>(piece); }
  1909. /**
  1910. * Accesses the expression of the part.
  1911. * Precondition: isExpression()
  1912. *
  1913. * @return A reference to the part's underlying expression.
  1914. *
  1915. * @internal ICU 75 technology preview
  1916. * @deprecated This API is for technology preview only.
  1917. */
  1918. const Expression& contents() const;
  1919. /**
  1920. * Accesses the expression of the part.
  1921. * Precondition: isMarkup()
  1922. *
  1923. * @return A reference to the part's underlying expression.
  1924. *
  1925. * @internal ICU 75 technology preview
  1926. * @deprecated This API is for technology preview only.
  1927. */
  1928. const Markup& asMarkup() const;
  1929. /**
  1930. * Accesses the text contents of the part.
  1931. * Precondition: isText()
  1932. *
  1933. * @return A reference to a string representing the part's text..
  1934. *
  1935. * @internal ICU 75 technology preview
  1936. * @deprecated This API is for technology preview only.
  1937. */
  1938. const UnicodeString& asText() const;
  1939. /**
  1940. * Non-member swap function.
  1941. * @param p1 will get p2's contents
  1942. * @param p2 will get p1's contents
  1943. *
  1944. * @internal ICU 75 technology preview
  1945. * @deprecated This API is for technology preview only.
  1946. */
  1947. friend inline void swap(PatternPart& p1, PatternPart& p2) noexcept {
  1948. using std::swap;
  1949. swap(p1.piece, p2.piece);
  1950. }
  1951. /**
  1952. * Copy constructor.
  1953. *
  1954. * @internal ICU 75 technology preview
  1955. * @deprecated This API is for technology preview only.
  1956. */
  1957. PatternPart(const PatternPart& other);
  1958. /**
  1959. * Assignment operator.
  1960. *
  1961. * @internal ICU 75 technology preview
  1962. * @deprecated This API is for technology preview only.
  1963. */
  1964. PatternPart& operator=(PatternPart) noexcept;
  1965. /**
  1966. * Destructor.
  1967. *
  1968. * @internal ICU 75 technology preview
  1969. * @deprecated This API is for technology preview only.
  1970. */
  1971. virtual ~PatternPart();
  1972. /**
  1973. * Text part constructor. Returns a text pattern part
  1974. * with text `t`.
  1975. *
  1976. * @param t A text string.
  1977. *
  1978. * @internal ICU 75 technology preview
  1979. * @deprecated This API is for technology preview only.
  1980. */
  1981. explicit PatternPart(const UnicodeString& t) : piece(t) {}
  1982. /**
  1983. * Expression part constructor. Returns an Expression pattern
  1984. * part with expression `e`.
  1985. *
  1986. * @param e An Expression.
  1987. *
  1988. * @internal ICU 75 technology preview
  1989. * @deprecated This API is for technology preview only.
  1990. */
  1991. explicit PatternPart(Expression&& e) : piece(e) {}
  1992. /**
  1993. * Markup part constructor. Returns a Markup pattern
  1994. * part with markup `m`
  1995. *
  1996. * @param m A Markup.
  1997. *
  1998. * @internal ICU 75 technology preview
  1999. * @deprecated This API is for technology preview only.
  2000. */
  2001. explicit PatternPart(Markup&& m) : piece(m) {}
  2002. /**
  2003. * Default constructor.
  2004. * Puts the PatternPart into a valid but undefined state.
  2005. *
  2006. * @internal ICU 75 technology preview
  2007. * @deprecated This API is for technology preview only.
  2008. */
  2009. PatternPart() = default;
  2010. private:
  2011. friend class Pattern;
  2012. std::variant<UnicodeString, Expression, Markup> piece;
  2013. }; // class PatternPart
  2014. } // namespace data_model
  2015. } // namespace message2
  2016. /// @cond DOXYGEN_IGNORE
  2017. // Export an explicit template instantiation of the LocalPointer that is used as a
  2018. // data member of various MFDataModel classes.
  2019. // (When building DLLs for Windows this is required.)
  2020. // (See measunit_impl.h, datefmt.h, collationiterator.h, erarules.h and others
  2021. // for similar examples.)
  2022. #if U_PF_WINDOWS <= U_PLATFORM && U_PLATFORM <= U_PF_CYGWIN
  2023. template class U_I18N_API LocalPointerBase<message2::data_model::PatternPart>;
  2024. template class U_I18N_API LocalArray<message2::data_model::PatternPart>;
  2025. template class U_I18N_API LocalPointerBase<message2::data_model::UnsupportedStatement>;
  2026. template class U_I18N_API LocalArray<message2::data_model::UnsupportedStatement>;
  2027. #endif
  2028. /// @endcond
  2029. namespace message2 {
  2030. namespace data_model {
  2031. /**
  2032. * A `Pattern` is a sequence of formattable parts.
  2033. * It corresponds to the `Pattern` interface
  2034. * defined in https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model.md#patterns
  2035. *
  2036. * `Pattern` is immutable, copyable and movable.
  2037. *
  2038. * @internal ICU 75 technology preview
  2039. * @deprecated This API is for technology preview only.
  2040. */
  2041. class U_I18N_API Pattern : public UObject {
  2042. private:
  2043. friend class PatternPart;
  2044. public:
  2045. struct Iterator;
  2046. /**
  2047. * Returns the parts of this pattern
  2048. *
  2049. * @return A forward iterator of variants. Each element is either a string (text part)
  2050. * or an expression part.
  2051. *
  2052. * @internal ICU 75 technology preview
  2053. * @deprecated This API is for technology preview only.
  2054. */
  2055. Iterator begin() const {
  2056. return Iterator(this, 0);
  2057. }
  2058. /**
  2059. * Returns a special value to mark the end of iteration
  2060. *
  2061. * @return A forward iterator of variants. This should only be used for comparisons
  2062. * against an iterator returned by incrementing begin().
  2063. *
  2064. * @internal ICU 75 technology preview
  2065. * @deprecated This API is for technology preview only.
  2066. */
  2067. Iterator end() const {
  2068. return Iterator(this, len);
  2069. }
  2070. /**
  2071. * The mutable `Pattern::Builder` class allows the pattern to be
  2072. * constructed one part at a time.
  2073. *
  2074. * Builder is not copyable or movable.
  2075. *
  2076. * @internal ICU 75 technology preview
  2077. * @deprecated This API is for technology preview only.
  2078. */
  2079. class U_I18N_API Builder : public UMemory {
  2080. private:
  2081. friend class Pattern;
  2082. UVector* parts; // Not a LocalPointer for the same reason as in `SelectorKeys::Builder`
  2083. public:
  2084. /**
  2085. * Adds a single expression part to the pattern.
  2086. *
  2087. * @param part The part to be added (passed by move)
  2088. * @param status Input/output error code.
  2089. * @return A reference to the builder.
  2090. *
  2091. * @internal ICU 75 technology preview
  2092. * @deprecated This API is for technology preview only.
  2093. */
  2094. Builder& add(Expression&& part, UErrorCode& status) noexcept;
  2095. /**
  2096. * Adds a single markup part to the pattern.
  2097. *
  2098. * @param part The part to be added (passed by move)
  2099. * @param status Input/output error code.
  2100. * @return A reference to the builder.
  2101. *
  2102. * @internal ICU 75 technology preview
  2103. * @deprecated This API is for technology preview only.
  2104. */
  2105. Builder& add(Markup&& part, UErrorCode& status) noexcept;
  2106. /**
  2107. * Adds a single text part to the pattern. Copies `part`.
  2108. *
  2109. * @param part The part to be added (passed by move)
  2110. * @param status Input/output error code.
  2111. * @return A reference to the builder.
  2112. *
  2113. * @internal ICU 75 technology preview
  2114. * @deprecated This API is for technology preview only.
  2115. */
  2116. Builder& add(UnicodeString&& part, UErrorCode& status) noexcept;
  2117. /**
  2118. * Constructs a new immutable `Pattern` using the list of parts
  2119. * set with previous `add()` calls.
  2120. *
  2121. * The builder object (`this`) can still be used after calling `build()`.
  2122. *
  2123. * @param status Input/output error code.
  2124. * @return The pattern object
  2125. *
  2126. * @internal ICU 75 technology preview
  2127. * @deprecated This API is for technology preview only.
  2128. */
  2129. Pattern build(UErrorCode& status) const noexcept;
  2130. /**
  2131. * Default constructor.
  2132. * Returns a Builder with an empty sequence of PatternParts.
  2133. *
  2134. * @param status Input/output error code
  2135. *
  2136. * @internal ICU 75 technology preview
  2137. * @deprecated This API is for technology preview only.
  2138. */
  2139. Builder(UErrorCode& status);
  2140. /**
  2141. * Destructor.
  2142. *
  2143. * @internal ICU 75 technology preview
  2144. * @deprecated This API is for technology preview only.
  2145. */
  2146. virtual ~Builder();
  2147. Builder(const Builder&) = delete;
  2148. Builder& operator=(const Builder&) = delete;
  2149. Builder(Builder&&) = delete;
  2150. Builder& operator=(Builder&&) = delete;
  2151. }; // class Pattern::Builder
  2152. /**
  2153. * Default constructor.
  2154. * Puts the Pattern into a valid but undefined state.
  2155. *
  2156. * @internal ICU 75 technology preview
  2157. * @deprecated This API is for technology preview only.
  2158. */
  2159. Pattern() : parts(LocalArray<PatternPart>()) {}
  2160. /**
  2161. * Non-member swap function.
  2162. * @param p1 will get p2's contents
  2163. * @param p2 will get p1's contents
  2164. *
  2165. * @internal ICU 75 technology preview
  2166. * @deprecated This API is for technology preview only.
  2167. */
  2168. friend inline void swap(Pattern& p1, Pattern& p2) noexcept {
  2169. using std::swap;
  2170. swap(p1.bogus, p2.bogus);
  2171. swap(p1.len, p2.len);
  2172. swap(p1.parts, p2.parts);
  2173. }
  2174. /**
  2175. * Copy constructor.
  2176. *
  2177. * @internal ICU 75 technology preview
  2178. * @deprecated This API is for technology preview only.
  2179. */
  2180. Pattern(const Pattern& other);
  2181. /**
  2182. * Assignment operator
  2183. *
  2184. * @internal ICU 75 technology preview
  2185. * @deprecated This API is for technology preview only.
  2186. */
  2187. Pattern& operator=(Pattern) noexcept;
  2188. /**
  2189. * Destructor.
  2190. *
  2191. * @internal ICU 75 technology preview
  2192. * @deprecated This API is for technology preview only.
  2193. */
  2194. virtual ~Pattern();
  2195. /**
  2196. * The `Pattern::Iterator` class provides an iterator over the formattable
  2197. * parts of a pattern.
  2198. *
  2199. * `Pattern::Iterator` is mutable and is not copyable or movable.
  2200. *
  2201. * @internal ICU 75 technology preview
  2202. * @deprecated This API is for technology preview only.
  2203. */
  2204. struct U_I18N_API Iterator {
  2205. private:
  2206. using iterator_category = std::forward_iterator_tag;
  2207. using difference_type = std::ptrdiff_t;
  2208. using value_type = std::variant<UnicodeString, Expression, Markup>;
  2209. using pointer = value_type*;
  2210. using reference = const value_type&;
  2211. friend class Pattern;
  2212. Iterator(const Pattern* p, int32_t i) : pos(i), pat(p) {}
  2213. friend bool operator== (const Iterator& a, const Iterator& b) { return (a.pat == b.pat && a.pos == b.pos); }
  2214. int32_t pos;
  2215. const Pattern* pat;
  2216. public:
  2217. /**
  2218. * Dereference operator (gets the element at the current iterator position)
  2219. *
  2220. * @internal ICU 75 technology preview
  2221. * @deprecated This API is for technology preview only.
  2222. */
  2223. reference operator*() const {
  2224. const PatternPart& part = pat->parts[pos];
  2225. return patternContents(part);
  2226. }
  2227. /**
  2228. * Increment operator (advances to the next iterator position)
  2229. *
  2230. * @internal ICU 75 technology preview
  2231. * @deprecated This API is for technology preview only.
  2232. */
  2233. Iterator operator++() { pos++; return *this; }
  2234. /**
  2235. * Inequality comparison operator (used for comparing an iterator to the result of end())
  2236. *
  2237. * @internal ICU 75 technology preview
  2238. * @deprecated This API is for technology preview only.
  2239. */
  2240. friend bool operator!= (const Iterator& a, const Iterator& b) { return !(a == b); }
  2241. }; // struct Iterator
  2242. private:
  2243. friend class Builder;
  2244. friend class message2::MessageFormatter;
  2245. friend class message2::Serializer;
  2246. // Set to true if a copy constructor fails;
  2247. // needed in order to distinguish an uninitialized
  2248. // Pattern from a 0-length pattern
  2249. bool bogus = false;
  2250. // Possibly-empty array of parts
  2251. int32_t len = 0;
  2252. LocalArray<PatternPart> parts;
  2253. Pattern(const UVector& parts, UErrorCode& status);
  2254. // Helper
  2255. static void initParts(Pattern&, const Pattern&);
  2256. /**
  2257. * Returns the size.
  2258. *
  2259. * @return The number of parts in the pattern.
  2260. *
  2261. * @internal ICU 75 technology preview
  2262. * @deprecated This API is for technology preview only.
  2263. */
  2264. int32_t numParts() const;
  2265. /**
  2266. * Returns the `i`th part in the pattern.
  2267. * Precondition: i < numParts()
  2268. *
  2269. * @param i Index of the part being accessed.
  2270. * @return A reference to the part at index `i`.
  2271. *
  2272. * @internal ICU 75 technology preview
  2273. * @deprecated This API is for technology preview only.
  2274. */
  2275. const PatternPart& getPart(int32_t i) const;
  2276. // Gets around not being able to declare Pattern::Iterator as a friend
  2277. // in PatternPart
  2278. static const std::variant<UnicodeString, Expression, Markup>&
  2279. patternContents(const PatternPart& p) { return p.piece; }
  2280. }; // class Pattern
  2281. /**
  2282. * A `Variant` pairs a list of keys with a pattern
  2283. * It corresponds to the `Variant` interface
  2284. * defined in https://github.com/unicode-org/message-format-wg/tree/main/spec/data-model
  2285. *
  2286. * `Variant` is immutable, copyable and movable.
  2287. *
  2288. * @internal ICU 75 technology preview
  2289. * @deprecated This API is for technology preview only.
  2290. */
  2291. class U_I18N_API Variant : public UObject {
  2292. public:
  2293. /**
  2294. * Accesses the pattern of the variant.
  2295. *
  2296. * @return A reference to the pattern.
  2297. *
  2298. * @internal ICU 75 technology preview
  2299. * @deprecated This API is for technology preview only.
  2300. */
  2301. const Pattern& getPattern() const { return p; }
  2302. /**
  2303. * Accesses the keys of the variant.
  2304. *
  2305. * @return A reference to the keys.
  2306. *
  2307. * @internal ICU 75 technology preview
  2308. * @deprecated This API is for technology preview only.
  2309. */
  2310. const SelectorKeys& getKeys() const { return k; }
  2311. /**
  2312. * Constructor. Returns a variant that formats to `pattern`
  2313. * when `keys` match the selector expressions in the enclosing
  2314. * `match` construct.
  2315. *
  2316. * @param keys A reference to a `SelectorKeys`.
  2317. * @param pattern A pattern (passed by move)
  2318. *
  2319. * @internal ICU 75 technology preview
  2320. * @deprecated This API is for technology preview only.
  2321. */
  2322. Variant(const SelectorKeys& keys, Pattern&& pattern) : k(keys), p(std::move(pattern)) {}
  2323. /**
  2324. * Non-member swap function.
  2325. * @param v1 will get v2's contents
  2326. * @param v2 will get v1's contents
  2327. *
  2328. * @internal ICU 75 technology preview
  2329. * @deprecated This API is for technology preview only.
  2330. */
  2331. friend inline void swap(Variant& v1, Variant& v2) noexcept {
  2332. using std::swap;
  2333. swap(v1.k, v2.k);
  2334. swap(v1.p, v2.p);
  2335. }
  2336. /**
  2337. * Assignment operator
  2338. *
  2339. * @internal ICU 75 technology preview
  2340. * @deprecated This API is for technology preview only.
  2341. */
  2342. Variant& operator=(Variant other) noexcept;
  2343. /**
  2344. * Default constructor.
  2345. * Returns a Variant in a valid but undefined state.
  2346. *
  2347. * @internal ICU 75 technology preview
  2348. * @deprecated This API is for technology preview only.
  2349. */
  2350. Variant() = default;
  2351. /**
  2352. * Copy constructor.
  2353. *
  2354. * @internal ICU 75 technology preview
  2355. * @deprecated This API is for technology preview only.
  2356. */
  2357. Variant(const Variant&);
  2358. /**
  2359. * Destructor.
  2360. *
  2361. * @internal ICU 75 technology preview
  2362. * @deprecated This API is for technology preview only.
  2363. */
  2364. virtual ~Variant();
  2365. private:
  2366. /* const */ SelectorKeys k;
  2367. /* const */ Pattern p;
  2368. }; // class Variant
  2369. } // namespace data_model
  2370. namespace data_model {
  2371. /**
  2372. * A `Binding` pairs a variable name with an expression.
  2373. * It corresponds to the `Declaration` interface
  2374. * defined in https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model.md#messages
  2375. *
  2376. * `Binding` is immutable and copyable. It is not movable.
  2377. *
  2378. * @internal ICU 75 technology preview
  2379. * @deprecated This API is for technology preview only.
  2380. */
  2381. class U_I18N_API Binding : public UObject {
  2382. public:
  2383. /**
  2384. * Accesses the right-hand side of a binding.
  2385. *
  2386. * @return A reference to the expression.
  2387. *
  2388. * @internal ICU 75 technology preview
  2389. * @deprecated This API is for technology preview only.
  2390. */
  2391. const Expression& getValue() const;
  2392. /**
  2393. * Accesses the left-hand side of the binding.
  2394. *
  2395. * @return A reference to the variable name.
  2396. *
  2397. * @internal ICU 75 technology preview
  2398. * @deprecated This API is for technology preview only.
  2399. */
  2400. const VariableName& getVariable() const { return var; }
  2401. /**
  2402. * Constructor for input binding.
  2403. *
  2404. * @param variableName The variable name (left-hand side) of the binding. Passed by move.
  2405. * @param rhs The right-hand side of the input binding. Passed by move.
  2406. * `rhs` must have an operand that is a variable reference to `variableName`.
  2407. * If `rhs` has an operator, it must be a function call.
  2408. * If either of these properties is violated, `errorCode` is set to
  2409. * U_INVALID_STATE_ERROR.
  2410. * @param errorCode Input/output error code
  2411. *
  2412. * @internal ICU 75 technology preview
  2413. * @deprecated This API is for technology preview only.
  2414. */
  2415. static Binding input(UnicodeString&& variableName, Expression&& rhs, UErrorCode& errorCode);
  2416. /**
  2417. * Returns true if and only if this binding represents a local declaration.
  2418. * Otherwise, it's an input declaration.
  2419. *
  2420. * @return True if this binding represents a variable and expression;
  2421. * false if it represents a variable plus an annotation.
  2422. */
  2423. UBool isLocal() const { return local; }
  2424. /**
  2425. * Constructor.
  2426. *
  2427. * @param v A variable name.
  2428. * @param e An expression.
  2429. *
  2430. * @internal ICU 75 technology preview
  2431. * @deprecated This API is for technology preview only.
  2432. */
  2433. Binding(const VariableName& v, Expression&& e) : var(v), expr(std::move(e)), local(true), annotation(nullptr) {}
  2434. /**
  2435. * Non-member swap function.
  2436. * @param b1 will get b2's contents
  2437. * @param b2 will get b1's contents
  2438. *
  2439. * @internal ICU 75 technology preview
  2440. * @deprecated This API is for technology preview only.
  2441. */
  2442. friend inline void swap(Binding& b1, Binding& b2) noexcept {
  2443. using std::swap;
  2444. swap(b1.var, b2.var);
  2445. swap(b1.expr, b2.expr);
  2446. swap(b1.local, b2.local);
  2447. b1.updateAnnotation();
  2448. b2.updateAnnotation();
  2449. }
  2450. /**
  2451. * Copy constructor.
  2452. *
  2453. * @internal ICU 75 technology preview
  2454. * @deprecated This API is for technology preview only.
  2455. */
  2456. Binding(const Binding& other);
  2457. /**
  2458. * Copy assignment operator
  2459. *
  2460. * @internal ICU 75 technology preview
  2461. * @deprecated This API is for technology preview only.
  2462. */
  2463. Binding& operator=(Binding) noexcept;
  2464. /**
  2465. * Default constructor.
  2466. * Puts the Binding into a valid but undefined state.
  2467. *
  2468. * @internal ICU 75 technology preview
  2469. * @deprecated This API is for technology preview only.
  2470. */
  2471. Binding() : local(true) {}
  2472. /**
  2473. * Destructor.
  2474. *
  2475. * @internal ICU 75 technology preview
  2476. * @deprecated This API is for technology preview only.
  2477. */
  2478. virtual ~Binding();
  2479. private:
  2480. friend class message2::Checker;
  2481. friend class message2::MessageFormatter;
  2482. friend class message2::Parser;
  2483. friend class message2::Serializer;
  2484. /* const */ VariableName var;
  2485. /* const */ Expression expr;
  2486. /* const */ bool local;
  2487. // The following field is always nullptr for a local
  2488. // declaration, and possibly nullptr for an .input declaration
  2489. // If non-null, the referent is a member of `expr` so
  2490. // its lifetime is the same as the lifetime of the enclosing Binding
  2491. // (as long as there's no mutation)
  2492. const Callable* annotation = nullptr;
  2493. const OptionMap& getOptionsInternal() const;
  2494. bool hasAnnotation() const { return !local && (annotation != nullptr); }
  2495. void updateAnnotation();
  2496. }; // class Binding
  2497. } // namespace data_model
  2498. } // namespace message2
  2499. /// @cond DOXYGEN_IGNORE
  2500. // Export an explicit template instantiation of the LocalPointer that is used as a
  2501. // data member of various MFDataModel classes.
  2502. // (When building DLLs for Windows this is required.)
  2503. // (See measunit_impl.h, datefmt.h, collationiterator.h, erarules.h and others
  2504. // for similar examples.)
  2505. #if U_PF_WINDOWS <= U_PLATFORM && U_PLATFORM <= U_PF_CYGWIN
  2506. template class U_I18N_API LocalPointerBase<message2::data_model::Variant>;
  2507. template class U_I18N_API LocalPointerBase<message2::data_model::Binding>;
  2508. template class U_I18N_API LocalArray<message2::data_model::Variant>;
  2509. template class U_I18N_API LocalArray<message2::data_model::Binding>;
  2510. #endif
  2511. /// @endcond
  2512. namespace message2 {
  2513. using namespace data_model;
  2514. // Internal only
  2515. class MFDataModel;
  2516. #ifndef U_IN_DOXYGEN
  2517. class Matcher : public UObject {
  2518. public:
  2519. Matcher& operator=(Matcher);
  2520. Matcher(const Matcher&);
  2521. /**
  2522. * Non-member swap function.
  2523. * @param m1 will get m2's contents
  2524. * @param m2 will get m1's contents
  2525. *
  2526. * @internal ICU 75 technology preview
  2527. * @deprecated This API is for technology preview only.
  2528. */
  2529. friend inline void swap(Matcher& m1, Matcher& m2) noexcept {
  2530. using std::swap;
  2531. if (m1.bogus) {
  2532. m2.bogus = true;
  2533. return;
  2534. }
  2535. if (m2.bogus) {
  2536. m1.bogus = true;
  2537. return;
  2538. }
  2539. swap(m1.selectors, m2.selectors);
  2540. swap(m1.numSelectors, m2.numSelectors);
  2541. swap(m1.variants, m2.variants);
  2542. swap(m1.numVariants, m2.numVariants);
  2543. }
  2544. virtual ~Matcher();
  2545. private:
  2546. friend class MFDataModel;
  2547. Matcher(Expression* ss, int32_t ns, Variant* vs, int32_t nv);
  2548. Matcher() {}
  2549. // A Matcher may have numSelectors=0 and numVariants=0
  2550. // (this is a data model error, but it's representable).
  2551. // So we have to keep a separate flag to track failed copies.
  2552. bool bogus = false;
  2553. // The expressions that are being matched on.
  2554. LocalArray<Expression> selectors;
  2555. // The number of selectors
  2556. int32_t numSelectors = 0;
  2557. // The list of `when` clauses (case arms).
  2558. LocalArray<Variant> variants;
  2559. // The number of variants
  2560. int32_t numVariants = 0;
  2561. }; // class Matcher
  2562. #endif
  2563. } // namespace message2
  2564. U_NAMESPACE_END
  2565. /// @cond DOXYGEN_IGNORE
  2566. // Export an explicit template instantiation of the std::variant that is used as a
  2567. // data member of various MFDataModel classes.
  2568. // (When building DLLs for Windows this is required.)
  2569. // (See measunit_impl.h, datefmt.h, collationiterator.h, erarules.h and others
  2570. // for similar examples.)
  2571. #if U_PF_WINDOWS <= U_PLATFORM && U_PLATFORM <= U_PF_CYGWIN
  2572. #if defined(U_REAL_MSVC) && defined(_MSVC_STL_VERSION)
  2573. template class U_I18N_API std::_Variant_storage_<false, icu::message2::Matcher,icu::message2::data_model::Pattern>;
  2574. #endif
  2575. template class U_I18N_API std::variant<icu::message2::Matcher,icu::message2::data_model::Pattern>;
  2576. #endif
  2577. /// @endcond
  2578. U_NAMESPACE_BEGIN
  2579. namespace message2 {
  2580. // -----------------------------------------------------------------------
  2581. // Public MFDataModel class
  2582. /**
  2583. *
  2584. * The `MFDataModel` class describes a parsed representation of the text of a message.
  2585. * This representation is public as higher-level APIs for messages will need to know its public
  2586. * interface: for example, to re-instantiate a parsed message with different values for imported
  2587. variables.
  2588. *
  2589. * The MFDataModel API implements <a target="github"
  2590. href="https://github.com/unicode-org/message-format-wg/blob/main/spec/data-model.md">the
  2591. * specification of the abstract syntax (data model representation)</a> for MessageFormat.
  2592. *
  2593. * `MFDataModel` is immutable, copyable and movable.
  2594. *
  2595. * @internal ICU 75 technology preview
  2596. * @deprecated This API is for technology preview only.
  2597. */
  2598. class U_I18N_API MFDataModel : public UMemory {
  2599. /*
  2600. Classes that represent nodes in the data model are nested inside the
  2601. `MFDataModel` class.
  2602. Classes such as `Expression`, `Pattern` and `VariantMap` are immutable and
  2603. are constructed using the builder pattern.
  2604. Most classes representing nodes have copy constructors. This is because builders
  2605. contain immutable data that must be copied when calling `build()`, since the builder
  2606. could go out of scope before the immutable result of the builder does. Copying is
  2607. also necessary to prevent unexpected mutation if intermediate builders are saved
  2608. and mutated again after calling `build()`.
  2609. The copy constructors perform a deep copy, for example by copying the entire
  2610. list of options for an `Operator` (and copying the entire underlying vector.)
  2611. Some internal fields should be `const`, but are declared as non-`const` to make
  2612. the copy constructor simpler to implement. (These are noted throughout.) In
  2613. other words, those fields are `const` except during the execution of a copy
  2614. constructor.
  2615. On the other hand, intermediate `Builder` methods that return a `Builder&`
  2616. mutate the state of the builder, so in code like:
  2617. Expression::Builder& exprBuilder = Expression::builder()-> setOperand(foo);
  2618. Expression::Builder& exprBuilder2 = exprBuilder.setOperator(bar);
  2619. the call to `setOperator()` would mutate `exprBuilder`, since `exprBuilder`
  2620. and `exprBuilder2` are references to the same object.
  2621. An alternate choice would be to make `build()` destructive, so that copying would
  2622. be unnecessary. Or, both copying and moving variants of `build()` could be
  2623. provided. Copying variants of the intermediate `Builder` methods could be
  2624. provided as well, if this proved useful.
  2625. */
  2626. public:
  2627. /**
  2628. * Accesses the local variable declarations for this data model.
  2629. *
  2630. * @return A vector of bindings for local variables.
  2631. *
  2632. * @internal ICU 75 technology preview
  2633. * @deprecated This API is for technology preview only.
  2634. */
  2635. std::vector<Binding> getLocalVariables() const {
  2636. std::vector<Binding> result;
  2637. if (!bogus) {
  2638. return toStdVector<Binding>(bindings.getAlias(), bindingsLen);
  2639. }
  2640. return {};
  2641. }
  2642. /**
  2643. * Accesses the selectors. Returns an empty vector if this is a pattern message.
  2644. *
  2645. * @return A vector of selectors.
  2646. *
  2647. * @internal ICU 75 technology preview
  2648. * @deprecated This API is for technology preview only.
  2649. */
  2650. const std::vector<Expression> getSelectors() const {
  2651. if (std::holds_alternative<Pattern>(body)) {
  2652. return {};
  2653. }
  2654. const Matcher* match = std::get_if<Matcher>(&body);
  2655. // match must be non-null, given the previous check
  2656. return toStdVector<Expression>(match->selectors.getAlias(), match->numSelectors);
  2657. }
  2658. /**
  2659. * Accesses the variants. Returns an empty vector if this is a pattern message.
  2660. *
  2661. * @return A vector of variants.
  2662. *
  2663. * @internal ICU 75 technology preview
  2664. * @deprecated This API is for technology preview only.
  2665. */
  2666. std::vector<Variant> getVariants() const {
  2667. // Return empty vector if no variants
  2668. if (std::holds_alternative<Pattern>(body)) {
  2669. return {};
  2670. }
  2671. const Matcher* match = std::get_if<Matcher>(&body);
  2672. // match must be non-null, given the previous check
  2673. return toStdVector<Variant>(match->variants.getAlias(), match->numVariants);
  2674. return {};
  2675. }
  2676. /**
  2677. * Accesses the unsupported statements for this data model.
  2678. *
  2679. * @return A vector of unsupported statements.
  2680. *
  2681. * @internal ICU 75 technology preview
  2682. * @deprecated This API is for technology preview only.
  2683. */
  2684. std::vector<UnsupportedStatement> getUnsupportedStatements() const {
  2685. std::vector<UnsupportedStatement> result;
  2686. if (!bogus) {
  2687. return toStdVector<UnsupportedStatement>(unsupportedStatements.getAlias(), unsupportedStatementsLen);
  2688. }
  2689. return {};
  2690. }
  2691. /**
  2692. * Accesses the pattern (in a message without selectors).
  2693. * Returns a reference to an empty pattern if the message has selectors.
  2694. *
  2695. * @return A reference to the pattern.
  2696. *
  2697. * @internal ICU 75 technology preview
  2698. * @deprecated This API is for technology preview only.
  2699. */
  2700. const Pattern& getPattern() const;
  2701. /**
  2702. * The mutable `MFDataModel::Builder` class allows the data model to be
  2703. * constructed incrementally.
  2704. *
  2705. * @internal ICU 75 technology preview
  2706. * @deprecated This API is for technology preview only.
  2707. */
  2708. class U_I18N_API Builder;
  2709. /**
  2710. * Default constructor.
  2711. * Puts the MFDataModel into a valid but undefined state.
  2712. *
  2713. * @internal ICU 75 technology preview
  2714. * @deprecated This API is for technology preview only.
  2715. */
  2716. MFDataModel();
  2717. /**
  2718. * Non-member swap function.
  2719. * @param m1 will get m2's contents
  2720. * @param m2 will get m1's contents
  2721. *
  2722. * @internal ICU 75 technology preview
  2723. * @deprecated This API is for technology preview only.
  2724. */
  2725. friend inline void swap(MFDataModel& m1, MFDataModel& m2) noexcept {
  2726. using std::swap;
  2727. if (m1.bogus) {
  2728. m2.bogus = true;
  2729. return;
  2730. }
  2731. if (m2.bogus) {
  2732. m1.bogus = true;
  2733. return;
  2734. }
  2735. swap(m1.body, m2.body);
  2736. swap(m1.bindings, m2.bindings);
  2737. swap(m1.bindingsLen, m2.bindingsLen);
  2738. swap(m1.unsupportedStatements, m2.unsupportedStatements);
  2739. swap(m1.unsupportedStatementsLen, m2.unsupportedStatementsLen);
  2740. }
  2741. /**
  2742. * Assignment operator
  2743. *
  2744. * @internal ICU 75 technology preview
  2745. * @deprecated This API is for technology preview only.
  2746. */
  2747. MFDataModel& operator=(MFDataModel) noexcept;
  2748. /**
  2749. * Copy constructor.
  2750. *
  2751. * @internal ICU 75 technology preview
  2752. * @deprecated This API is for technology preview only.
  2753. */
  2754. MFDataModel(const MFDataModel& other);
  2755. /**
  2756. * Destructor.
  2757. *
  2758. * @internal ICU 75 technology preview
  2759. * @deprecated This API is for technology preview only.
  2760. */
  2761. virtual ~MFDataModel();
  2762. /**
  2763. * The mutable `MFDataModel::Builder` class allows the data model to be
  2764. * constructed incrementally. Builder is not copyable or movable.
  2765. *
  2766. * @internal ICU 75 technology preview
  2767. * @deprecated This API is for technology preview only.
  2768. */
  2769. class U_I18N_API Builder : public UMemory {
  2770. private:
  2771. friend class MFDataModel;
  2772. void checkDuplicate(const VariableName&, UErrorCode&) const;
  2773. void buildSelectorsMessage(UErrorCode&);
  2774. bool hasPattern = true;
  2775. bool hasSelectors = false;
  2776. Pattern pattern;
  2777. // The following members are not LocalPointers for the same reason as in SelectorKeys::Builder
  2778. UVector* selectors = nullptr;
  2779. UVector* variants = nullptr;
  2780. UVector* bindings = nullptr;
  2781. UVector* unsupportedStatements = nullptr;
  2782. public:
  2783. /**
  2784. * Adds a binding, There must not already be a binding
  2785. * with the same name.
  2786. *
  2787. * @param b The binding. Passed by move.
  2788. * @param status Input/output error code. Set to U_DUPLICATE_DECLARATION_ERROR
  2789. * if `addBinding()` was previously called with a binding
  2790. * with the same variable name as `b`.
  2791. *
  2792. * @internal ICU 75 technology preview
  2793. * @deprecated This API is for technology preview only.
  2794. */
  2795. Builder& addBinding(Binding&& b, UErrorCode& status);
  2796. /**
  2797. * Adds an unsupported statement.
  2798. *
  2799. * @param s The statement. Passed by move.
  2800. * @param status Input/output error code.
  2801. *
  2802. *
  2803. * @internal ICU 75 technology preview
  2804. * @deprecated This API is for technology preview only.
  2805. */
  2806. Builder& addUnsupportedStatement(UnsupportedStatement&& s, UErrorCode& status);
  2807. /**
  2808. * Adds a selector expression. Copies `expression`.
  2809. * If a pattern was previously set, clears the pattern.
  2810. *
  2811. * @param selector Expression to add as a selector. Passed by move.
  2812. * @param errorCode Input/output error code
  2813. * @return A reference to the builder.
  2814. *
  2815. * @internal ICU 75 technology preview
  2816. * @deprecated This API is for technology preview only.
  2817. */
  2818. Builder& addSelector(Expression&& selector, UErrorCode& errorCode) noexcept;
  2819. /**
  2820. * Adds a single variant.
  2821. * If a pattern was previously set using `setPattern()`, clears the pattern.
  2822. *
  2823. * @param keys Keys for the variant. Passed by move.
  2824. * @param pattern Pattern for the variant. Passed by move.
  2825. * @param errorCode Input/output error code
  2826. * @return A reference to the builder.
  2827. *
  2828. * @internal ICU 75 technology preview
  2829. * @deprecated This API is for technology preview only.
  2830. */
  2831. Builder& addVariant(SelectorKeys&& keys, Pattern&& pattern, UErrorCode& errorCode) noexcept;
  2832. /**
  2833. * Sets the body of the message as a pattern.
  2834. * If selectors and/or variants were previously set, clears them.
  2835. *
  2836. * @param pattern Pattern to represent the body of the message.
  2837. * Passed by move.
  2838. * @return A reference to the builder.
  2839. *
  2840. * @internal ICU 75 technology preview
  2841. * @deprecated This API is for technology preview only.
  2842. */
  2843. Builder& setPattern(Pattern&& pattern);
  2844. /**
  2845. * Constructs a new immutable data model.
  2846. * If `setPattern()` has not been called and if `addSelector()` and
  2847. * `addVariant()` were not each called at least once,
  2848. * `status` is set to `U_INVALID_STATE_ERROR`.
  2849. * If `addSelector()` was called and `addVariant()` was never called,
  2850. * or vice versa, then `status` is set to U_INVALID_STATE_ERROR.
  2851. * Otherwise, either a Pattern or Selectors message is constructed
  2852. * based on the pattern that was previously set, or selectors and variants
  2853. * that were previously set.
  2854. *
  2855. * The builder object (`this`) can still be used after calling `build()`.
  2856. *
  2857. * @param status Input/output error code.
  2858. * @return The new MFDataModel
  2859. *
  2860. * @internal ICU 75 technology preview
  2861. * @deprecated This API is for technology preview only.
  2862. */
  2863. MFDataModel build(UErrorCode& status) const noexcept;
  2864. /**
  2865. * Default constructor.
  2866. * Returns a Builder with no pattern or selectors set.
  2867. * Either `setPattern()` or both `addSelector()` and
  2868. * `addVariant()` must be called before calling `build()`
  2869. * on the resulting builder.
  2870. *
  2871. * @param status Input/output error code.
  2872. *
  2873. * @internal ICU 75 technology preview
  2874. * @deprecated This API is for technology preview only.
  2875. */
  2876. Builder(UErrorCode& status);
  2877. /**
  2878. * Destructor.
  2879. *
  2880. * @internal ICU 75 technology preview
  2881. * @deprecated This API is for technology preview only.
  2882. */
  2883. virtual ~Builder();
  2884. Builder(const Builder&) = delete;
  2885. Builder& operator=(const Builder&) = delete;
  2886. Builder(Builder&&) = delete;
  2887. Builder& operator=(Builder&&) = delete;
  2888. }; // class Builder
  2889. private:
  2890. friend class Checker;
  2891. friend class MessageFormatter;
  2892. friend class Serializer;
  2893. Pattern empty; // Provided so that `getPattern()` can return a result
  2894. // if called on a selectors message
  2895. bool hasPattern() const { return std::holds_alternative<Pattern>(body); }
  2896. bool bogus = false; // Set if a copy constructor fails
  2897. // A message body is either a matcher (selector list and variant list),
  2898. // or a single pattern
  2899. std::variant<Matcher, Pattern> body;
  2900. // Bindings for local variables
  2901. /* const */ LocalArray<Binding> bindings;
  2902. int32_t bindingsLen = 0;
  2903. // Unsupported statements
  2904. // (Treated as a type of `declaration` in the data model spec;
  2905. // stored separately for convenience)
  2906. /* const */ LocalArray<UnsupportedStatement> unsupportedStatements;
  2907. int32_t unsupportedStatementsLen = 0;
  2908. const Binding* getLocalVariablesInternal() const;
  2909. const Expression* getSelectorsInternal() const;
  2910. const Variant* getVariantsInternal() const;
  2911. const UnsupportedStatement* getUnsupportedStatementsInternal() const;
  2912. int32_t numSelectors() const {
  2913. const Matcher* matcher = std::get_if<Matcher>(&body);
  2914. return (matcher == nullptr ? 0 : matcher->numSelectors);
  2915. }
  2916. int32_t numVariants() const {
  2917. const Matcher* matcher = std::get_if<Matcher>(&body);
  2918. return (matcher == nullptr ? 0 : matcher->numVariants);
  2919. }
  2920. // Helper
  2921. void initBindings(const Binding*);
  2922. MFDataModel(const Builder& builder, UErrorCode&) noexcept;
  2923. }; // class MFDataModel
  2924. } // namespace message2
  2925. U_NAMESPACE_END
  2926. #endif // U_HIDE_DEPRECATED_API
  2927. #endif /* #if !UCONFIG_NO_MF2 */
  2928. #endif /* #if !UCONFIG_NO_FORMATTING */
  2929. #endif /* U_SHOW_CPLUSPLUS_API */
  2930. #endif // MESSAGEFORMAT_DATA_MODEL_H
  2931. // eof