1 chuck 1.1 <!doctype html public "-//w3c//dtd html 4.0 transitional//en">
2 <html>
3 <head>
4 <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
|
5 chuck 1.4 <meta name="GENERATOR" content="Mozilla/4.78 [en] (X11; U; Linux 2.4.7-10 i686) [Netscape]">
|
6 chuck 1.1 </head>
7 <body text="#000000" bgcolor="#FFFFFF" link="#0000EF" vlink="#55188A" alink="#FF0000">
8
9 <center><font size=+4>Globalization HOWTO</font>
10 <p>Release: Pegasus 2.3
11 <p>Author: Chuck Carmack (carmack@us.ibm.com)
|
12 chuck 1.2 <p>July 28, 2003</center>
|
13 chuck 1.1
14 <p><br>
15 <h2>
16 1.0 Introduction</h2>
17
18 <p><br>As part of the Pegasus 2.3 release, functions were added for globalization
19 support. Globalization involves two major aspects: internationalization
20 and localization.
21 <br>
22 <p>Internationalization is the process of writing a program that is locale-neutral.
23 In other words, the program should be able to run in any locale without
24 change. There are several categories in a locale, including the language
25 of message strings, date format, time format, etc. For release 2.3,
26 the Pegasus server is concerned with the language of the message strings
27 it returns to its clients.
28 <br>
29 <p>To support internationalization, a program is designed to do the following:
30 <br>
31 <blockquote>
32 <li>
33 Support character sets that can represent customer data in any language.
34 chuck 1.1 Typically, the program supports some variation of Unicode for internal
35 data. There is usually some conversion between the supported character
36 sets for external data, and the internal character set. Since Unicode
37 covers all characters, and usually has converters on the platform, it is
38 a good choice for the 'normalized' internal character set.
39 The most 'interoperable' solution for external data is to support UTF-8
40 (eg. network and file system data). The internal data is usually
41 UTF-16 (or UCS-2, but that is deprecated).</li>
42
43 <br>
44 <li>
45 Extract locale-sensitive resources, such as message strings, from the code
46 to external resource files. Typically, the resources are loaded based
47 on the locale requested by the end-user, and returned to the end-user for
48 display.</li>
49 </blockquote>
50
51 <p><br>Localization is the process of customizing a software product to
52 support particular locales. For example, a product that is internationalized
53 might want to only localize for certain countries. This would mean
54 that the localized resources (eg. message files) would only be translated
55 chuck 1.1 and shipped for the countries that the product supports. Since the
56 code for the product is locale-neutral, it will be easy to drop in new
57 translations as more countries are supported.
58 <br>
59 <p>The Pegasus 2.3 release added support for globalization. At a
60 high-level, the following additions were made to Pegasus 2.3:
61 <br>
62 <ul>
63 <li>
64 Support UTF-8 for external data.</li>
65
66 <br>
67 <ul>
68 <li>
69 The CIM-XML documents contained in the HTTP messages</li>
70
71 <li>
|
72 chuck 1.4 The files in the repository</li>
73
74 <li>
75 Note: Pegasus 2.3 does NOT support UTF-8 in the MOF files</li>
76
77 <br> </ul>
|
78 chuck 1.1
79 <li>
80 Support UTF-16 for internal data.</li>
81
82 <br>
83 <li>
84 Extract the hardcoded messages from the Pegasus code into message files.
85 An API was added to load messages from the message files.</li>
86
87 <br>
88 <li>
89 APIs were added for clients to associate a language with the CIM objects
90 they are sending to Pegasus. Also, APIs were added for clients to
91 determine the language of the error message or CIM object that Pegasus
92 returns.</li>
93
94 <br>
95 <li>
96 APIs were added for providers to determine the language of CIM objects
97 sent by the client. Also, APIs were added for providers to associate
98 a language with the CIM object, or error message, they return to the client.</li>
99 chuck 1.1 </ul>
100
101 <p><br>Please refer to PEPs 56 and 58 for details about the globalization
|
102 chuck 1.2 design in Pegasus 2.3.
|
103 chuck 1.1 <br>
104 <p>This document provides a HOWTO guide to be used by developers to globalize
105 code that is being added to Pegasus. The audience for this document
106 are:
107 <br>
108 <ul>
109 <li>
110 Provider developers - both CMPI and C++</li>
111
112 <li>
113 Client developers</li>
114
115 <li>
116 Pegasus developers</li>
117 </ul>
118
119 <p><br>The quickest way to approach this document is to read the General
120 section, and then the developer section that relates to what you are doing.
121 <br>
122 <h2>
123 2.0 General</h2>
124 chuck 1.1
125 <h3>
126 2.1 Unicode Support</h3>
127
128 <p><br>Pegasus 2.3 supports Unicode throughout the processing of requests.
129 External data to Pegasus is encoded in UTF-8. Internal data is encoded
130 in UTF-16.
131 <br>
|
132 chuck 1.4 <p>UTF-8 support for external data includes the CIM-XML messages passed
133 over the network, and the repository files. Note: UTF-8 support
134 was NOT added to the MOF Compiler for MOF files in release 2.3.
135 For the CIM-XML messages, Pegasus follows section 4.8 of the <a href="http://www.dmtf.org/standards/documents/WBEM/DSP200.html">CIM-HTTP
|
136 chuck 1.1 specification</a> Specifically, Pegasus supports the
137 "utf-8" setting for the charset parameter of the Content-Type header and
138 the XML encoding attribute. If no charset is specified, the 7-bit
|
139 chuck 1.4 ASCII is assumed.
|
140 chuck 1.1 <br>
141 <p>The internal support of UTF-16 is encapsulated in the Pegasus String
142 class. This class has been updated to contain UTF-16 characters.
143 Specifically, the Char16 objects inside the String contain UTF-16 characters.
144 Note: a UTF-16 surrogate pair is contained in two consecutive Char16 objects.
145 To keep backwards compatibilty, the methods on the String class have not
146 changed. New methods have been added as needed. The following
147 describes this in more detail:
148 <ul>
149 <li>
150 The Pegasus 2.2 methods that take a char *, or return char *, are unchanged.
151 Code written to Pegasus 2.2 may have expected to store 8-bit ASCII (ISO-8859-1)
152 characters into String. These methods will convert the input to UTF-16
153 from 8-bit ASCII. (This is simple because UTF-16 is a superset of
154 8-bit ASCII - simply need to prepend '\0' to each char). The Pegasus
155 2.2 methods that return char data will attempt to convert from the UTF-16
156 internal representation to 8-bit ASCII. Characters that cannot be
157 converted will be replaced with a substitution character.</li>
158
159 <br>
160 <li>
161 chuck 1.1 All methods that take or return Char16 data are unchanged. The String
162 class now supports UTF-16 data in Char16, although surrogate pairs will
163 require two consecutive Char16 objects. The String class does NO
164 checking for unmatched surrogate pairs.</li>
165
166 <br>
167 <li>
168 New methods have been added to take and return UTF-8 data. The String
169 class will convert between UTF-8 and the UTF-16 internal representation
170 as needed. These new methods will use char * parameters, but will
171 be clearly labelled as UTF-8 methods.</li>
172
173 <br> </ul>
174 PROGRAMMING NOTE: Putting EBCDIC data into the String class is dangerous.
175 The String class is designed for UTF-16, which is a superset of 8-bit ASCII.
176 Any String object containing EBCDIC data will not work if it is used by
177 Pegasus to read or write data from external sources, such as the network
178 or repository files. In other words, any String containing EBCDIC
179 data should not leave the code using it.
180 <br>
181 <br>
182 chuck 1.1 <h3>
183 2.2 Localization Support</h3>
184
185 <h4>
186 2.2.1 Language Headers</h4>
187
188 <p><br>Pegasus 2.3 supports clients and providers that wish to localize.
189 There are two areas to be localized: <a href="http://www.dmtf.org/standards/documents/WBEM/DSP201.html#SecERROR">ERROR</a>
190 elements in the CIM-XML; and <a href="http://www.dmtf.org/standards/documents/WBEM/DSP201.html#SecObjectDefinitionElements">Object
191 Definition</a> elements in the CIM-XML. Clients can request
192 the server to return error messages and CIM objects in a set of languages
193 of their choosing. Clients can also tag a language to the CIM objects
194 they are sending to the server. Providers and the server can return
195 error messages and CIM objects that are tagged with one of languages
196 requested by the client.
197 <br>
198 <p>The localization design is based on section 4.8 of the <a href="http://www.dmtf.org/standards/documents/WBEM/DSP200.html">CIM-HTTP
199 specification</a> , which refers to <a href="http://www.ietf.org/rfc/rfc2616.txt?number=2616">RFC
200 2616</a>. The method used to tag a language to the CIM-XML is through
201 the Accept-Language and Content-Language HTTP headers. These headers
202 are basically lists of language tags. An HTTP request can contain
203 chuck 1.1 an Accept-Language header, which indicates the list of preferred languages
204 that the client wants in the response. This list can be prioritized
205 by using the quality numbers. An HTTP request or response can contain
206 a Content-Language header, which indicates the language(s) of the content
207 in the message. In the Pegasus case, this would be the CIM-XML.
208 Note that the Content-Language header is a list of language tags.
209 This allows the content of an HTTP message to contain more than one translation.
210 However, in the Pegasus case, there is only one CIM-XML document in the
211 HTTP message, and thus one translation.
212 <br>
213 <p>CIM clients may use the Accept-Language HTTP header to specify the languages
214 they wish to be returned in the CIM response message. CIM clients
215 may also use the Content-Language header to tag the language of any CIM
216 objects they are sending to the server in the CIM request message.
217 The server, and providers, should attempt to return error messages and
218 CIM objects in one of the accept languages requested by the client.
219 The server and providers should set the Content-Language header in the
220 CIM response message to indicate which of the requested languages they
221 are returning.
222 <br>
223 <p>NOTE: Localization support was not added for the MOF files and
224 chuck 1.1 repository in Pegasus 2.3. The #pragma locale, #pragma instancelocale,
225 and translatable qualifier flavor are not supported in the Pegasus 2.3
226 MOF compiler. From the client perspective, classes, qualifiers, and
|
227 chuck 1.2 instances stored in the repository are not tagged with a language.
|
228 chuck 1.1 The Accept-Language and Content-Language headers will be ignored for repository
229 operations. However, since the repository will support UTF-8,
230 characters for any language may be stored there.
231 <br>
232 <p>NOTE: Since the Content-Language header applies to the entire
233 HTTP message, it applies to the entire CIM-XML document. This includes
234 all the objects in the document, including enumerated objects, and all
235 the values in the objects. This is a limitation that will remain
236 until the CIM standard has been updated to support language tags tied to
237 individual CIM values. From the client perspective, it is possible
238 for Pegasus to send a CIM response with NO Content-Language, even if the
239 client had sent Accept-Language. This can happen if Pegasus
240 does not know the language of the response. An example is a request
241 that was sent to a Pegasus 2.2 provider. Another example is an enumerated
242 response where each provider returned a different language. Please
243 refer to PEP58 for details on these provider scenarios.
244 <br>
245 <p>Pegasus 2.3 has added classes for the localization support. There
246 are new classes called AcceptLanguages and ContentLanguages that encapsulate
247 the Accept-Language and Content-Language headers, respectively. These
248 classes are basically containers of AcceptLanguageElement and ContentLanguageElement,
249 chuck 1.1 where a language element represents one language tag. The AcceptLanguages
250 class will keep the AcceptLanguageElement's prioritized based on quality,
251 according to RFC 2616.
252 <br>
253 <p>AcceptLanguages and ContentLanguages are the objects used by code throughout
254 the request/response processing, from the client to the server to the providers
255 and back. The server handles the creation of these objects from the
256 HTTP headers. Code at each point in the process will have access
257 to these objects.
258 <br>
259 <p>Please refer to the following files for details on the new Pegasus classes.
260 <br>
261 <ul>
262 <li>
263 pegasus/src/Pegasus/Common/AcceptLanguages.h</li>
264
265 <li>
266 pegasus/src/Pegasus/Common/AcceptLanguageElement.h</li>
267
268 <li>
269 pegasus/src/Pegasus/Common/ContentLanguages.h</li>
270 chuck 1.1
271 <li>
272 pegasus/src/Pegasus/Common/ContentLanguageElement.h</li>
273
274 <li>
275 pegasus/src/Pegasus/Common/LanguageElementContainer.h</li>
276
277 <li>
278 pegasus/src/Pegasus/Common/LanguageElement.h</li>
279 </ul>
280
281 <p><br>See the sections below for details on how to write clients and providers
282 to use these classes.
283 <br>
284 <br>
285 <h4>
|
286 chuck 1.2 2.2.2 Message Bundles</h4>
|
287 chuck 1.1
288 <p><br>One of the goals of globalization for Pegasus 2.3 is the extraction
|
289 chuck 1.2 of hardcoded messages into translated message files, loading translated
290 messages from those files, and returning those messages to the client.
291 The topics to be discussed here are: how to create message files,
292 how to compile message files, and how to load messages into Pegasus.
|
293 chuck 1.1 <br>
294 <p>At the time of writing, the message loading function in Pegasus 2.3
295 used the International Components for Unicode (<a href="http://oss.software.ibm.com/icu">ICU)</a>
296 libraries. This is expected to be the future direction for Pegasus.
297 <a href="http://oss.software.ibm.com/icu">ICU
298 </a>uses
299 a resource bundle format for their message files. In order
300 to load the messages, ICU requires that the resource bundles are compiled
301 into a binary form (.res file) using their genrb tool.
302 <br>
|
303 chuck 1.3 <p>Platform Maintainers Note: Please refer to PEP 58 for information
|
304 chuck 1.2 about how to build Pegasus to use the ICU libraries.
305 <br>
|
306 chuck 1.1 <p>The documentation for ICU resource bundles is in the <a href="http://oss.software.ibm.com/icu/userguide/ResourceManagement.html">Resource
307 Management</a> section of the <a href="http://oss.software.ibm.com/icu/userguide/">ICU
308 User Guide</a> . This section will tell you how to
|
309 chuck 1.2 <br>create and organize your resource bundles for different languages.
|
310 chuck 1.1 Note: your resource bundles should be organized in a tree structure
311 similiar to the one shown in the Resource Management section, including
|
312 chuck 1.2 the empty bundles in the tree. It is recommended that you ship a
313 root resource bundle to be used as the fallback in case the client requests
|
314 chuck 1.4 a language that you are not supporting. The Pegasus make files are
315 set up to automatically create and compile a root resource bundle for you.
316 For Pegasus 2.3, the make will use your "en" bundle, upper case all the
317 messages, and then put the uppercased messages into the root bundle.
318 The uppercasing of the messages is necessary to create a "fallback" root
319 bundle that contains invariant characters across all EBCIC and ASCII codepages.
320 <br>
321 <p>NOTE: When creating your resource bundles, the name of the table
322 resource should contain the package name. For example,
323 if you have a bundle with a package name of "xyz", then the "en" bundle
324 should start like this:
325 <p>xyz_en:table {
326 <br>..... messages here
327 <br>
328 }
329 <br>
330 <p><i>not</i> like this:
331 <p>en:table {
332 <br>..... messages here
333 <br>
334 }
335 chuck 1.4 <p>This is different than some of the examples in the <a href="http://oss.software.ibm.com/icu/userguide/ResourceManagement.html">Resource
336 Management</a> section, but is needed because the -p option is not used
337 on genrb by the make files.
|
338 chuck 1.1 <br>
339 <p>NOTE: Pegasus 2.3 only supports simple string resources in the
340 ICU resource bundles. String resources may only be loaded by key.
341 Tables, arrays, and other complex resource types, are not supported.
342 <br>
|
343 chuck 1.2 <p>In order to compile your resource bundles, support has been added to
344 the Pegasus make files to run genrb. A new make target, "messages",
345 has been added that will call genrb and put the compiled bundles (.res)
346 in a directory of your choosing. An example of ICU resource bundles
347 and the make files to compile them are located in:
348 <br>
349 <ul>
350 <li>
351 pegasus/src/Providers/sample/LocalizedProvider/Makefile (just causes the
352 make to recurse to the msg sub-directory)</li>
353
354 <li>
355 pegasus/src/Providers/sample/LocalizedProvider/msg/Makefile (compiles the
356 bundles in the msg/ directory)</li>
357
358 <li>
359 pegasus/src/Providers/sample/LocalizedProvider/msg/*.txt (the resource
360 bundles to compile, using the recommended ICU language tree structure)</li>
361 </ul>
362
363 <p><br>NOTE: At the time of writing, only the Linux make files have
364 chuck 1.2 been updated to compile ICU resource bundles.
365 <br>
366 <p>It is important to place the compiled resource bundles in a directory
367 where your code can find them . The make files above compile the
368 resource bundles into $PEGASUS_HOME/msg/provider/localizedProvider.
369 The code that loads these messages uses the MessageLoader class (next section)
370 to load messages from this directory.
371 <br>
372 <br>
373 <h4>
374 2.2.3 Message Loading</h4>
375
376 <p><br>Code that needs to load a message in Pegasus does not call ICU directly.
|
377 chuck 1.1 Two message loading classes were added for Pegasus 2.3: MessageLoader
378 and MessageLoaderParms. These classes are abstractions designed to
|
379 chuck 1.2 hide of the actual loader used (but note that at the time of writing, only
380 ICU is supported). The MessageLoader is used to load a message
381 using a list of preferrred languages. The parameters to MessageLoader
382 are encapsulated in a MessageLoaderParms object.
383 <br>
384 <p>The MessageLoader is the place where the Accept-Language header, Content-Language
385 header, and the ICU resource bundles, join up. The MessageLoader
386 class is designed to receive an AcceptLanguages object, and a set of parameters
387 indicating the bundle base-name and message ID to use. The AcceptLanguages
388 object contains the list of requested languages sent by the client.
389 The MessageLoader searches for the message in the set of bundles named
390 with the base-name, using the AcceptLanguages for the list of specific
391 translated bundles to search. The MessageLoader returns the message
392 that it found, along with a ContentLanguages object indicating the language
393 of the message. The ContentLanguages object should be used to indicate
394 the language of the response sent back to the client.
|
395 chuck 1.1 <br>
396 <p>The MessageLoaderParms object contains the parameters to load the message.
397 There are many parameters, but many can be allowed to default. Here
398 is a description of the parameters:
399 <br>
400 <br>
401 <table BORDER COLS=3 WIDTH="100%" NOSAVE >
402 <tr>
403 <td>String msg_id; </td>
404
405 <td>Input.
406 <br>Required.</td>
407
408 <td>Message ID of the message to load from the resource bundle.
409 This is the key that ICU will use to load the message.</td>
410 </tr>
411
412 <tr>
413 <td>String default_msg;</td>
414
415 <td>Input.
416 chuck 1.1 <br>Required</td>
417
|
418 chuck 1.2 <td>Message to return if the no message can be loaded for msg_id from any
|
419 chuck 1.1 resource bundle. Note: The args parameters below are substituted
420 into this string.
421 <br>Note: For the args into this string, use the Pegasus '$'
422 form, as described in pegasus/src/Pegasus/Common/Formatter.h. Don't
423 use the ICU substitution format for the default message string.</td>
424 </tr>
425
426 <tr>
427 <td>String msg_src_path; </td>
428
429 <td>Input.
430 <br>Optional
431 <br>Default: $PEGASUS_HOME/msg/pegasus/pegasusServer</td>
432
433 <td>Path to the root resource bundle file which contains the msg_id.
|
434 chuck 1.2 <br>Note: Only specify the path down to the bundle base-name. Do
435 not append a language tag, such as "_root" or "_en". Do not append
436 a file extension.
437 <br>Note: relative paths start at $PEGASUS_HOME/msg.
438 <br>Note: defaults to the bundle containing the Pegasus server messages.</td>
|
439 chuck 1.1 </tr>
440
441 <tr>
442 <td>AcceptLanguages acceptlanguages;</td>
443
444 <td>Input.
445 <br>Optional
446 <br>Default: AcceptLanguages::EMPTY</td>
447
448 <td>Contains the list of preferred languages, in priority order.
449 This is combined with msg_src_path to determine which resource bundles
|
450 chuck 1.2 to search for for the msg_id. If not empty, overrides useThreadLocale
|
451 chuck 1.1 and useProcessLocale.</td>
452 </tr>
453
454 <tr>
455 <td>ContentLanguages contentlanguages;</td>
456
457 <td>Output</td>
458
459 <td>Contains the language that MessageLoader found for the msg_id. </td>
460 </tr>
461
462 <tr>
463 <td>Boolean useProcessLocale;</td>
464
465 <td>Input
466 <br>Optional
467 <br>Default = false</td>
468
469 <td>If true, MessageLoader will use the default locale of the process.
470 If true, overrides useThreadLocale.</td>
471 </tr>
472 chuck 1.1
473 <tr>
474 <td>Boolean useThreadLocale;</td>
475
476 <td>Input
477 <br>Optional
478 <br>Default = <font color="#FF0000">true</font></td>
479
|
480 chuck 1.2 <td>If true, MessageLoader will use the AcceptLanguages set by Pegasus
481 into the caller's Thread. See the Note below for details. </td>
|
482 chuck 1.1 </tr>
483
484 <tr>
485 <td>Boolean useICUfallback</td>
486
487 <td>Input
488 <br>Optional
489 <br>Default = false</td>
490
491 <td>If true, use ICU's fallback mechnism to search more general resource
492 bundles if the msg_id cannot be found. Note: the recommended setting
493 is false if you are using an AcceptLanguages from a CIM client. The
494 Accept-Languages HTTP header from the client contains the fallback specifications.</td>
495 </tr>
496
497 <tr>
498 <td>Formatter::Arg arg0;
499 <br> Formatter::Arg arg1;
500 <br> Formatter::Arg arg2;
501 <br> Formatter::Arg arg3;
502 <br> Formatter::Arg arg4;
503 chuck 1.1 <br> Formatter::Arg arg5;
504 <br> Formatter::Arg arg6;
505 <br> Formatter::Arg arg7;
506 <br> Formatter::Arg arg8;
507 <br> Formatter::Arg arg9;</td>
508
509 <td>Input
510 <br>Optional
511 <br>Default: Formatter::Arg( ) // empty arg</td>
512
513 <td>These are the substitution variables, using the Pegasus Formatter::Arg
514 class.</td>
515 </tr>
516 </table>
517
|
518 chuck 1.2 <p>Notes:
519 <br>
520 <p>The "useThreadLocale" parameter defaults to true. This flag indicates
521 to use the AcceptLanguages object set by Pegasus into the Pegasus Thread
522 in which the caller's code is running. This AcceptLanguages object
523 reflects the languages requested by the client. This is useful for
524 code that may not have access to the AcceptLanguages from the client.
525 Pegasus sets this AcceptLanguages object into the Thread of providers and
526 internal Pegasus code. For this reason, it is recommended that provider
527 and internal Pegasus code use the "useThreadLocale" flag instead of explicity
528 passing in an AcceptLanguages object. See the Provider Developer
529 and Pegasus Developer sections for details.
530 <br>
531 <p>The "useProcessLocale" flag can be used to tell MessageLoader to use
532 the default locale of the process, as determined by ICU. This is
533 useful for situations where the caller is not localizing for a client request.
534 The caller may itself be a client (eg. cimconfig), or may need to log messages
535 to the system log in the locale of the Pegasus server process. See
536 the CLI Messages and Logger Messages sections below.
537 <br>
538 <p>"Master switch"
539 chuck 1.2 <br>The MessageLoader class has a public static Boolean variable called
540 _useProcessLocale that may be used to override all the AcceptLanguages
541 and useThreadLocale settings in the MessageLoaderParms objects passed in.
542 This is useful for CLI code (eg cimconfig) that needs to localize its messages
543 based on the locale of its process, which refects the locale set by the
544 user running the CLI (eg. $LANG on Unix). The CLI code may call Pegasus
545 APIs that are coded to use the Thread's AcceptLanguages, which will not
546 be set in this case. The _useProcessLocale static variable tells
547 the MessageLoader to ignore the AcceptLanguages, useThreadLocale, and useProcessLocale
548 settings in MessageLoaderParms that it gets. The MessageLoader will
549 use the default process locale, as determined by ICU, in this case.
550 <br>
551 <p><i>Important Note:</i> The MessageLoader defaults to <i>not </i>use
552 the "fallback" mechanism described in the ICU Resource Management section.
553 This is because the Accept-Language header itself describes the fallback
554 that the client wants. However, the MessageLoader does "fallback"
555 to the root resource bundle if none of the languages in AcceptLanguages
556 can be found. If the root resource bundle cannot be found, then the
557 default_msg is returned. The "useICUFallback" flag can be set to
558 have MessageLoader use ICU fallback on all message load attempts.
559 However, usage of this flag for client requests may lead to incorrect results.
560 chuck 1.2 For example, a client sets Accept-Language to french, german, and spanish,
561 in that order, but there is no french resource bundle. A call to
562 MessageLoader with useICUfallback == true would cause the root resource
563 bundle string to be returned on the attempt to load from the french bundle.
564 But the client requested german to be the fallback after french.
565 <br>
|
566 chuck 1.1 <p>Please refer to the following files for details on the new Pegasus classes.
567 <br>
568 <ul>
569 <li>
570 pegasus/src/Pegasus/Common/MessageLoader.h</li>
571 </ul>
572
573 <h4>
|
574 chuck 1.2 2.2.4 Message Loading Example</h4>
575
576 <p><br>The following example shows how a message may be loaded using the
577 classes described above. Note: this a generic example. Each
578 of the developer sections below have 'real-life' examples that are better
579 suited to each type of code.
|
580 chuck 1.1 <p>// Build an AcceptLanguages with some language elements
581 <br>AcceptLanguages acceptLangs;
582 <br>acceptLangs.add(AcceptLanguageElement("fr", 0.5));
583 <br>acceptLangs.add(AcceptLanguageElement("de", 0.8));
584 <br>acceptLangs.add(AcceptLanguageElement("es", 0.4));
585 <p>// Construct a MessageLoaderParms
586 <br>MessageLoaderParms parms("msgID", "default message");
587 <br>parms. msg_src_path = "/my_msg_dir/my_bundle";
588 <br>parms.acceptlanguages = acceptLangs;
589 <p>// Note: If you have args, set them into MessageLoaderParms
590 <p>// Load the localized String
591 <br>String localizedMsg = MessageLoader::getMessage(parms);
592 <br>
593 <br>
594 <h4>
595 2.2.4 Message Writing Guidelines</h4>
596
597 <p><br>Here are some basic rules for writing messages:
598 <br>
599 <ul>
600 <li>
601 chuck 1.1 If you want to claim that you are globalized, no hardcoded messages!</li>
602
603 <li>
604 Avoid combining messages in the code from other messages. When you
605 do this you are assuming that you know the grammar for every language.</li>
606
607 <li>
608 String substitutions into messages are generally untranslated, ie. not
609 loaded from the resource bundle. Example: a file name.</li>
610
611 <li>
612 Avoid jargon, humour, and cultural idioms. Use full sentences.
613 Have your messages reviewed by your globalization team. Your messages
614 need to make sense to the translators, and ultimately the customer.</li>
615
616 <li>
617 <b>TODO </b>- find a good message writing guide to link to</li>
618 </ul>
619
|
620 chuck 1.2 <h4>
621 2.2.5 Localized Exceptions</h4>
622
623 <p><br>The base Exception class, and derived classes, have been updated
624 to support localization. Constructors have been added that take a
625 MessageLoaderParms object. These constructors will use the MessageLoaderParms
626 object to call the MessageLoader to load the localized exception message.
627 The localized message is saved in the Exception. The ContentLanguages
628 object returned by MessageLoader is also saved in the Exception.
629 This indicates the language of the message. The ContentLanguages
630 object is used later to set the Content-Language header in the HTTP message
631 to the client.
632 <br>
633 <p>The old Exception constructors that take a String will remain.
634 These should be used in cases where the code throwing the exception is
635 not localized, or the String is not localized (for example, a file name).
636 Also, there are several exceptions in Pegasus where the String parameter
637 is meant to be a non-localized substitution in a localized message owned
638 by the Exception (see InternalException.h, ClassNotResolved for an example).
639 The old constructors for these have been kept.
640 <br>
641 chuck 1.2 <br>
|
642 chuck 1.1 <h2>
643 3.0 Provider Developers</h2>
644
645 <h3>
646 3.1 Design Issues</h3>
647
648 <p><br>Providers that wish to globalize should consider the following in
649 their design:
650 <br>
651 <ul>
652 <li>
653 Are there localized string properties that need to be supported?
654 If so, then the client will use Accept-Language to request specific languages
655 for these properties. If the properties are read-only, use MessageLoader
656 to load the localized strings for the properties.</li>
657
658 <li>
659 If you have a localized read/write string property, then the client will
660 use Content-Language to set the property with an associated language.
661 The client will expect to be able to retrieve the property in that same
662 language later (using Accept-Language).</li>
663 chuck 1.1
664 <li>
665 Note: only the string property types in CIM are candidates for localization.
666 The other types, including datetime, are locale-neutral.</li>
667
668 <li>
669 Are there error messages that need to returned to the client in different
670 languages? The client will use Accept-Language to request specific
671 languages for the error messages.</li>
672
673 <li>
674 What resource bundle translations, if any, will be shipped with the provider?</li>
675
676 <li>
677 Do any codepage conversions need to be done between the UTF-16 characters
678 in the String objects and the codepage of data stored on the system?
679 This is a concern for EBCDIC platforms. All EBCDIC data needs to
680 be converted to at least 7-bit ASCII before it is passed into the String
681 object.</li>
682 </ul>
683
684 chuck 1.1 <p><br>To help providers handle the situations described above, Pegasus
685 2.3 will pass the Accept-Language received from the client to the provider.
686 The provider should load strings from its resource bundle based on the
687 client's Accept-Language. The client's Accept-Language is passed
688 to the provider in two ways:
689 <br>
690 <ul>
691 <li>
692 Pegasus will set the Accept-Language from the client into the thread in
693 which the provider is running. By using the useThreadLocale setting
694 in MessageLoaderParms, providers can easily load strings using the client's
695 requested Accept-Language. The provider does not need to know what
696 the Accept-Language is. This is the recommended method to load messages
697 based on the client's request.</li>
698
699 <br>
700 <li>
701 The OperationContext will contain an AcceptLanguages object that has the
702 Accept-Language requested by the client. The provider can use this
703 AcceptLanguages object to load strings with MessageLoader.</li>
704 </ul>
705 chuck 1.1
706 <p><br>The OperationContext will also contain a ContentLanguages object
707 that is set from the Content-Language in the client request. This
708 is the language of the CIM objects being passed to the provider on that
709 request. A localized provider should store the content language along
710 with the data from the CIM objects. This will allow the client to
711 use Accept-Language later to retreive the data in that language.
712 <br>
713 <p>The provider should indicate the language of CIM objects it is returning
714 by calling setLanguage( ) on the ResponseHandler. This will be used
715 to set the Content-Language in the CIM response message sent back to the
716 client. If setLanguage( ) is not called, then no Content-Language
717 will be returned to the client. setLanguage( ) should only be called
718 once per response.
719 <br>
720 <h3>
721 3.2 Sample Code</h3>
722
723 <p><br>The following sample code shows a localized getInstance( ) where
724 the instance returned is localized based on the Accept-Language of the
725 client request. Note that this example also throws a localized exception.
726 chuck 1.1 <br>
727 <p>void LocalizedProvider::getInstance(
728 <br> const OperationContext & context,
729 <br> const CIMObjectPath & instanceReference,
730 <br> const Boolean includeQualifiers,
731 <br> const Boolean includeClassOrigin,
732 <br> const CIMPropertyList & propertyList,
733 <br> InstanceResponseHandler & handler)
734 <br>{
735 <br> // convert a potential fully qualified reference
736 into a local reference
737 <br> // (class name and keys only).
738 <br> CIMObjectPath localReference = CIMObjectPath(
739 <br> String(),
740 <br> String(),
741 <br> instanceReference.getClassName(),
742 <br> instanceReference.getKeyBindings());
743 <p> // begin processing the request
744 <br> handler.processing();
745 <p> // Find the instance to be returned.
746 <br> Uint32 i;
747 chuck 1.1 <br> Uint32 n = _instances.size();
748 <br> for (i = 0; i < n; i++)
749 <br> {
750 <br> if(localReference
751 == _instanceNames[i])
752 <br> {
753 <br>
754 // We found the instance to return
755 <p>
756 // Build the parameters for loading the localized string property.
757 <br>
758 // We are going to let the message loader parameters default to use the
759 <br>
760 // AcceptLanguages that Pegasus set into our thread.
761 <br>
762 // (this equals the AcceptLanguages requested by the client)
763 <br>
764 // Note: This parms object could be constructed once and
765 <br>
766 // reused.
767 <br>
768 chuck 1.1 MessageLoaderParms parms("myMsgID", "myDefaultString");
769 <br>
770 parms.msg_src_path = "/myprovider/msg/myResourceBundle";
771 <p>
772 // Load the string for the localized property from the resource bundle
773 <br>
774 String localizedString = MessageLoader::getMessage(parms);
775 <p>
776 // Remove the old property from the instance to be returned
777 <br>
778 Uint32 index = instances[i].findProperty("myProperty");
779 <br>
780 if (index != PEG_NOT_FOUND)
781 <br>
782 {
783 <br>
784 _instances[i].removeProperty(index);
785 <br>
786 }
787 <p>
788 // Add the localized string property to the instance
789 chuck 1.1 <br>
790 instances[i].addProperty(CIMProperty("myProperty", localizedString));
791 <p>
792 // The MessageLoader set the contentlanguages member
793 <br>
794 // of parms to the language that it found for the message.
795 <br>
796 ContentLanguages rtnLangs = parms.contentlanguages;
797 <p>
798 // We need to tag the instance we are returning with the
799 <br>
800 // the content language.
801 <br>
802 handler.setLanguages(rtnLangs);
803 <p>
804 // deliver requested instance
805 <br>
806 handler.deliver(_instances[i]);
807 <p>
808 break;
809 <br>
810 chuck 1.1 } // end if
811 <br> }
812 // end for
813 <p> // throw an exception if
814 the instance wasn't found
815 <br> if (i == n)
816 <br> {
817 <br>
818 // Build the parameters for loading the localized error message.
819 <br>
820 // We are going to let the message loader parameters default to use the
821 <br>
822 // AcceptLanguages that Pegasus set into our thread.
823 <br>
824 // (this equals the AcceptLanguages requested by the client)
825 <br>
826 // Note: This parms object could be constructed once and
827 <br>
828 // reused.
829 <br>
830 MessageLoaderParms errParms("myErrorMsgID", "myErrorDefaultString");
831 chuck 1.1 <br>
832 errParms.msg_src_path = "/myprovider/msg/myResourceBundle";
833 <p>
834 // Note: the exception calls MessageLoader::getMessage( )
835 <br>
836 // Note: no need to call handler.setLanguages( ) in this case
837 <br>
838 throw CIMObjectNotFoundException(errParms);
839 <br> }
840 <br>
841 <p> // complete processing the
842 request
843 <br> handler.complete();
844 <br>}
845 <br>
846 <p>NOTE: A sample provider has been written that fully demonstates the
847 design issues described above. This provider is located at:
848 <br>
849 <ul>
850 <li>
851 pegasus/src/Providers/sample/LocalizedProvider/</li>
852 chuck 1.1 </ul>
853
854 <p><br>This sample provider also demonstrates how some of the special issues
855 can be handled. The special issues are caused by having a read/only
856 localized property and a read/write localized property. What happens
857 if the client sets the read/write property with a Content-Language that
858 is not one of the supported languages for the read/only property?
859 This provider allows the client to set any language into the read/write
860 property, and get that property back in the same language. This becomes
861 an issue when the client does a getInstance( ) later, because the Content-Language
862 on the returned instance applies to all the properties. A related
863 issue is what to return for Content-Language when the client does enumerateInstances,
864 but the instances have different languages. Recall that Content-Language
865 applies to the entire response (a limitation in the CIM specification).
866 <br>
867 <p>NOTE: Indication Providers have other special considerations for
868 language support. Please refer to PEP58.
869 <br>
870 <p>NOTE: The CMPI interface has been updated for language support.
871 Please refer to the CMPI documentation for details.
872 <br>
873 chuck 1.1 <p>NOTE: SPECIAL ISSUES FOR OS/400 PROVIDERS:
874 <ul>
875 <li>
876 Convert between UTF-16 in the String objects and EBCDIC system data as
877 needed. The converters in Pegasus/Common/OS400ConvertChar.h may be
878 used to convert between EBCDIC CCSID 37 and ASCII CCSID 819 (a subset of
879 UTF-16).</li>
880
881 <li>
882 The Pegasus program, and all bound service programs, will run in
883 a UTF-8 locale even though the job CCSID is 37. The C-runtime library
884 (printf, fopen, isalpha, strcmp, etc) will expect UTF-8, or at least 7-bit
885 ASCII, characters.</li>
886
887 <li>
888 Consideration should be given to the codepage for the compiled string literals.
889 Use #pragma convert as needed. But, remember that the C-runtime will
890 expect UTF-8.</li>
891
892 <li>
893 For more details, refer to "Unicode support" in chapter 3 of the <u>ILE
894 chuck 1.1 C/C++ for iSeries Run-Time Functions, Version 5</u> publication for V5R3
895 (SC41-5607-02). The Pegasus string literals will be compiled with
896 the UTF-8 compile switch described in this section. OS/400 provider
897 developers should strongly consider using the same compile switch for their
898 string literals. This would allow the literals to match the UTF-8
899 encoding expected by the C-runtime.</li>
900 </ul>
901
902 <h2>
903 4. 0 Client Developers</h2>
904
905 <p><br>Methods have been added to CIMClient to set the Accept-Language
906 and Content-Language on the request, and retrieve Content-Language on the
|
907 chuck 1.2 response. The language tags in the Accept-Language header must meet
908 the ISO-639 and ISO-3166 standards.
|
909 chuck 1.1 <br>
910 <p>Please refer to
911 <br>
912 <ul>
913 <li>
914 pegasus/src/Pegasus/Client/CIMClient.h</li>
915
916 <br> </ul>
917 for the new methods on CIMClient.
918 <br>
919 <p>Here is a code fragment that uses the new methods on CIMClient
920 <p> //
921 <br> // Get a localized instance in French
922 <br> //
923 <p> // Language priority is martian, pig-latin, and french.
924 We should
925 <br> // get french back, even though its the lowest priority
926 <br> AcceptLanguages acceptLangs;
927 <br> acceptLangs.add(AcceptLanguageElement("x-martian"));
928 <br> acceptLangs.add(AcceptLanguageElement("fr", 0.1));
929 <br> acceptLangs.add(AcceptLanguageElement("x-pig-latin", 0.4));
930 chuck 1.1 <p> // Set the requested languages into the CIMClient
931 <br> client.setRequestAcceptLanguages(acceptLangs);
932 <p> // Get the instance
933 <br> CIMInstance instance = client.getInstance(
934 <br> NAMESPACE,
935 <br> cimNInstances[0].buildPath(sampleClass),
936 <br> localOnly,
937 <br> includeQualifiers,
938 <br> includeClassOrigin);
939 <p> // Get the string property that should be french
940 <br> String returnedString;
941 <br> instance.getProperty (
942 <br> instance.findProperty("myProp")).
943 <br>
944 getValue().
945 <br>
946 get(returnedString);
947 <p> // Check that we got back french
948 <br> ContentLanguages CL_FR("fr");
949 <br> String expectedFRString = "oui";
950 <br> PEGASUS_ASSERT(CL_FR == client.getResponseContentLanguages());
951 chuck 1.1 <br> PEGASUS_ASSERT(expectedFRString == returnedString);
952 <p> //
953 <br> // Create an instance in French
954 <br> //
955 <p> String oui = "Oui";
956 <br> CIMInstance frInstance(CLASSNAME);
957 <br> frInstance.addProperty(CIMProperty(
958 <br>
959 CIMName("myProp"),
960 <br>
961 oui));
962 <p> CIMObjectPath frInstanceName = frInstance.buildPath(sampleClass);
963 <p> client.setRequestContentLanguages(CL_FR);
964 <p> client.createInstance(NAMESPACE, frInstance);
965 <br>
966 <br>
967 <br>
968 <p>Also, refer to
969 <ul>
970 <li>
971 pegasus/src/Clients/g11ntest/</li>
972 chuck 1.1 </ul>
973 for more examples of a client that uses Accept-Language and Content-Language.
974 <br>
975 <p>NOTE: Consideration should be given for converting the UTF-16
976 characters in the String objects passed over the CIMClient interface to
977 a platform codepage. This is especially needed for EBCDIC platforms.
978 See the Provider developer section for details of the EBCDIC considerations.
979 <br>
|
980 chuck 1.2 <br>
981 <h3>
982 4.1 Default Process Locale</h3>
983
984 <p><br>A method has been added to CIMClient to set the Accept-Language
985 for the requests based on the default locale of the process, as determined
986 by ICU. If ICU is installed on the client system then CIMClient will
987 set the Accept-Language from the default ICU process locale. If ICU
988 is not installed then the caller is required to set an AcceptLanguages
989 into CIMClient that meets the ISO-639 and IS0-3166 standards. Note:
990 this is useful for local clients, such as the Pegasus CLIs, where ICU would
991 be installed on both the client and server sides.
992 <br>
|
993 chuck 1.1 <br>
994 <h2>
995 5. 0 Pegasus Developers</h2>
996
997 <p><br>The design for Pegasus releases beyond 2.3 is to avoid using hardcoded
998 messages. All new messages should be loaded from a Pegasus resource
999 bundle. This section describes the process to follow if you are creating
1000 a new message. The process depends on where you are in the code.
1001 <br>
1002 <br>
1003 <h3>
1004 <b>5.1 Pegasus Resource Bundles</b></h3>
1005
1006 <p><br>Place any new Pegasus messages into one of the following resource
1007 bundles:
1008 <br>
1009 <ul>
1010 <li>
|
1011 chuck 1.3 pegasus/src/Pegasus/msg/Server/pegasusServer_*.txt for server and
1012 MOF compiler (cimmof, cimmofl) messages</li>
|
1013 chuck 1.1
1014 <li>
|
1015 chuck 1.3 pegasus/src/Pegasus/msg/CLI/pegasusCLI_*.txt for all CLI messages (except
|
1016 chuck 1.4 the MOF compiler)</li>
|
1017 chuck 1.1 </ul>
|
1018 chuck 1.2
1019 <p><br>The make messages target will compile these resource bundles.
1020 <p>Note: As described above, the resource bundle path in MessageLoaderParms
|
1021 chuck 1.1 defaults to the server resource bundle. For CLI messages, you will
1022 need to specify the bundle for your CLI.
1023 <br>
1024 <h3>
1025 5.2 Server Messages</h3>
1026
1027 <p><br>For messages returned from one of the services in the Pegasus server
1028 (eg. CIMOperationRequestDispatcher, or ProviderManagerService), the goal
1029 is to make it easy for any code in the call chain to throw an exception
1030 with a localized error string. The code throwing the exception will
1031 not need to know the Accept-Language that the client requested. To
1032 understand how this works, some design points need to described:
1033 <br>
1034 <p><b>Server Design Points:</b>
1035 <br>
1036 <p>The CIMMessage object has been expanded to include an AcceptLanguages
1037 object and a ContentLanguages object. For CIMRequestMessage, these
1038 objects contain the Accept-Language and Content-Language headers that were
1039 built from the client request. For CIMResponseMessage, the ContentLanguages
1040 object is used to build the Content-Language header associated with the
1041 CIM <i>objects </i>in the response message. The AcceptLanguages object
1042 chuck 1.1 in the CIMResponseMessage is ignored.
1043 <br>
1044 <p>The localization of the cimException object in the CIMResponseMessage
1045 is handled separately from the CIM objects. The message string in
1046 the cimException object is assumed to have been localized by the time it
1047 is built into the XML. For this reason, the localization of the exception
1048 is the responsibility of the code throwing the exception. (The goal
1049 of the design is to make that easy - see below). The ContentLanguages
1050 object in the CIMResponseMessage has NO relation to this exception.
1051 The cimException object keeps its own localization information once it
1052 is created.
1053 <br>
1054 <p>To enable exceptions to be localized, the ability was added to set a
1055 global language for all the code running from a Pegasus Thread object.
1056 The top level code for a Thread can set a global AcceptLanguages object
|
1057 chuck 1.2 that can be accessed by all the low-level functions that it calls.
1058 This will allow an exception thrown by the low-level function to be localized
1059 based on this global AcceptLanguages object. Note: This applies
1060 only to Threads that are managed by a ThreadPool.
|
1061 chuck 1.1 <br>
1062 <p>Each service in the request path of the Pegasus server sets the AcceptLanguages
1063 into its Thread from the AcceptLanguages in the CIMRequestMessage object
1064 that it dequeues. This sets the global langauge for all the functions
1065 in the same thread that are called below handleEnqueue. <i>If you
1066 are writing a new service that processes requests, or discover a request
1067 service that was missed, please do this. </i> The CIMOperationRequestDispatcher
1068 service is an example.
1069 <br>
1070 <p><b>How to Throw a Localized Exception from Server code:</b>
1071 <br>
1072 <p>With all that background, here is how code running in a Pegasus service
1073 can throw a localized exception:
1074 <br>This example assumes that the top-level code in the service had set
|
1075 chuck 1.2 the global thread AcceptLanguages beforehand. As described above,
1076 every service in Pegasus should do that. The code here may be buried
1077 several layers deep in the call chain, but does not need to know the AcceptLanguage
1078 of the current client request.
|
1079 chuck 1.1 <p>// First, construct a MessageLoaderParms
1080 <br>//
1081 <br>// Notes:
1082 <br>// 1) The errorMessageID must be in the Pegasus server resource
1083 bundle.
1084 <br>// 2) The default message is the old "hardcoded" message.
1085 <br>// 3) The MessageLoaderParms will default to use the Pegasus
1086 server resource bundle
|
1087 chuck 1.2 <br>// 4) The MessageLoaderParms will default to use the AcceptLanguages
1088 set into the current Thread. Don't change this!
|
1089 chuck 1.1 <br>// 5) You might need to set the arguments for the message into
1090 the MessageLoaderParms
1091 <br>MessageLoaderParms parms("errorMessageID", "default message");
1092 <p>// Second, throw the Exception
1093 <br>// Note: this applies to all the derived classes from Exception, including
1094 the CIMException's
1095 <br>throw new Exception(parms);
1096 <br>
1097 <p>NOTE: If you are throwing an Exception with un-localized data,
1098 use the constructor that takes a String. An example of this would
1099 be an Exception where you are passing in a file name. Most of the
1100 "non-CIM" exceptions defined in Exception.h and InternalException.h take
1101 un-localized data.
1102 <br>
|
1103 chuck 1.2 <p><b>The Exception Macros</b>
1104 <br>
1105 <p>There are many spots in the server code that use the PEGASUS_CIM_EXCEPTION
1106 macro to throw a TraceableCIMException. The use of this macro in
1107 the code like the following example presented a design problem:
1108 <p>....
1109 <br>} catch (Exception & e)
1110 <br>{
1111 <br> throw PEGASUS_CIM_EXCEPTION(CIM_ERR_FAILED, e.getMessage());
1112 <br>}
1113 <br>
1114 <p>This type of code would have lost the ContentLanguages saved in "e",
1115 so that the Content-Language would not be set in HTTP response to the client.
1116 <br>
1117 <p>For Pegasus 2.3, these types of macro calls can stay. The TraceableCIMException
1118 constructed by the macro will "re-localize". That is, the "CIM" part
1119 of the message (the part based on the error code) will be localized at
1120 throw time, and the ContentLanguages re-established. A key is to
1121 avoid a "language mismatch" problem between the CIM part of the message
1122 and the extra part of the message. The design point here is that
1123 all internal exceptions thrown by Pegasus code are localized using the
1124 chuck 1.2 global AcceptLanguages of the Thread...see above.
1125 <br>
1126 <p>In the future, it will be safer and more maintainable to use of the
1127 new "localized" flavors of the macro. For example:
1128 <br>
1129 <p>When the message from a caught Exception needs to be become the
1130 extra message in a thrown CIMException:
1131 <p>....
1132 <br>} catch (Exception & e)
1133 <br>{
1134 <br> throw PEGASUS_CIM_EXCEPTION_LANG(e.getContentLanguages(
1135 ),
1136 <br>
1137 CIM_ERR_FAILED,
1138 <br>
1139 e.getMessage( ));
1140 <br>}
1141 <br>
1142 <p>This guarantees that the ContentLanguages in "e" is copied to the newly
1143 created TraceableCIMException.
1144 <br>
1145 chuck 1.2 <p>In the case where the extra message for the CIMException is determined
1146 by the throwing code:
1147 <br>
1148 <p>throw PEGASUS_CIM_EXCEPTION_L(CIM_ERR_FAILED,
1149 <br>
1150 MessageLoaderParms("Repository.CIMRepository.COMPACT_FAILED", "compact
1151 failed"));
1152 <br>
1153 <p>(example from CIMRepository.cpp)
1154 <br>This uses a MessageLoaderParms object to localize the extra message
1155 in the newly created TraceableCIMException.
|
1156 chuck 1.1 <br>
1157 <h3>
1158 5.2 Logger Messages</h3>
1159
1160 <p><br>New methods have been added to Logger to take a message ID of a
1161 message to be loaded from the Pegasus server resource bundle. The
|
1162 chuck 1.2 caller is only required to pass in the message ID, the old "hardcoded"
|
1163 chuck 1.1 message, and the args. The Logger will use MessageLoader to load
1164 the message in the locale of the Pegasus server <i>process</i>, using the
|
1165 chuck 1.2 hardcoded message as the default string. Please refer to pegasus/src/Pegasus/Logger.h.
1166 <p>Note: Messages sent to the "logs", whether the system logs or
1167 the Pegasus log file, are converted to UTF-8 before being sent.
|
1168 chuck 1.1 <br>
1169 <h3>
1170 5.3 CLI Messages</h3>
1171
|
1172 chuck 1.2 <p><br>The goal for messages returned by the Pegasus CLIs is to localize
1173 in the locale of the user running the CLI. This should be automatic
1174 -- the user should not be required to tell the CLI what the locale is.
1175 For the CLIs that are CIM clients (cimconfing, cimprovider) there are two
1176 sets of messages to localize -- messages generated in the CLI process
1177 itself, and messages returned from the Pegasus server . For CLIs
1178 that are directly linked into Pegasus (cimmofl), all the messages are generated
1179 in the CLI's process, but the CLI may call Pegasus APIs that are coded
1180 to localize based on a client's requested languages.
1181 <br>
1182 <p>Code in the client side of the client/server CLIs (eg. cimconfig, cimmof),
1183 or in directly linked CLIs (cimmofl), should use the _useProcessLocale
1184 "master switch" described in the Message Loading section. This will
1185 cause all messages, including exceptions thrown by Pegasus APIs,
1186 to be loaded in the locale based on the environment in which the program
1187 is running. This locale can be set by the user before running the
1188 program.
1189 <br>
1190 <p>Code in the client side of the client/server CLIs need to send an Accept-Language
1191 to the Pegasus server that reflects the default locale of the CLI's process.
1192 See the Client Developer section for details.
|
1193 chuck 1.1 <br>
|
1194 chuck 1.2 <p>An example of these considerations can be seen in the source code for
1195 cimconfig.
|
1196 chuck 1.1 <br>
1197 <p>
1198 <hr>
1199 <p><i>Copyright (c) 2003 BMC Software; Hewlett-Packard Development Company,
1200 L.P.; IBM Corp.; The Open Group</i>
1201 <p><i>Permission is hereby granted, free of charge, to any person obtaining
1202 a copy of this software and associated documentation files (the "Software"),
1203 to deal in the Software without restriction, including without limitation
1204 the rights to use, copy, modify, merge, publish, distribute, sublicense,
1205 and/or sell copies of the Software, and to permit persons to whom the Software
1206 is furnished to do so, subject to the following conditions:</i>
1207 <p><i>THE ABOVE COPYRIGHT NOTICE AND THIS PERMISSION NOTICE SHALL BE INCLUDED
1208 IN ALL COPIES OR SUBSTANTIAL PORTIONS OF THE SOFTWARE. THE SOFTWARE IS
1209 PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
1210 INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
1211 FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS
1212 OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
1213 WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
1214 OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
1215 SOFTWARE.</i>
1216 <br>
1217 chuck 1.1 <br>
1218 </body>
1219 </html>
|