この章では、PHPおよびOracle Database環境でのグローバル・アプリケーションの開発について説明します。グローバルなインターネット・アプリケーションの開発およびデプロイに関連付けられている基本的なタスク(ロケール認識の開発、ユーザー選択言語でのHTMLコンテンツの構築、ユーザーのロケールの表記規則に従ったデータの表示など)について説明します。
様々なロケールをサポートするグローバル・インターネット・アプリケーションを構築するには、適切な開発の実施が必要です。ロケールは、各国語とその言語が使用されている地域を指します。アプリケーション自体がユーザーのロケール・プリファレンスを認識し、ユーザーが考えているとおりの表記規則に従ってコンテンツを表示できる必要があります。正しい日付書式や数値書式など、該当するロケールの特性を使用してデータを表示することが重要です。Oracle Databaseは完全に国際化されており、グローバル・アプリケーションを開発およびデプロイするためのグローバル・プラットフォームを提供します。
この章のトピックは、次のとおりです。
グローバル・アプリケーションを構築するための最初のステップは、PHPエンジンとOracleデータベース間の接続を正しく設定することです。これにより、すべての層にわたるデータの整合性が保証されます。ほとんどのインターネット・ベースの標準では、文字エンコーディングとしてUnicodeがサポートされています。この章では、データ交換のキャラクタ・セットとしてUnicodeを使用することに焦点を絞って説明します。
PHPはオラクル社のC言語OCIインタフェースと、OCIおよびPHPに適用されるルールを使用します。Oracleロケールの動作(OCIアプリケーションで使用されるクライアント・キャラクタ・セットを含む)は、NLS_LANG
環境変数で定義します。この環境変数の形式は次のとおりです。
<language>_<territory>.<character set>
たとえば、Unicodeでアプリケーションを実行するブラジル国内のポルトガル語ユーザーの場合、NLS_LANG
は次のように設定されます。
BRAZILIAN PORTUGUESE_BRAZIL.AL32UTF8
言語および地域の設定によって、Oracle日付書式、エラー・メッセージ言語、ソート順序に使用されるルールなどのOracleの動作が制御されます。キャラクタ・セットAL32UTF8は、UTF-8のOracle名です。
NLS_LANG
環境変数の詳細は、Oracle Databaseのインストレーション・ガイドを参照してください。
Oracle LinuxのApacheにPHPをインストールするときに、/etc/sysconfig/httpd
でNLS_LANG
を設定できます。
export NLS_LANG='BRAZILIAN PORTUGUESE_BRAZIL.AL32UTF8'
この変更を実装するには、Webリスナーを再起動する必要があります。
PHPは、ISO-8859-1キャラクタ・セットで動作するように設計されています。それ以外のキャラクタ・セット(特にマルチバイト・キャラクタ・セット)を処理する場合は、一連のマルチバイト文字列関数を使用できます。これらの機能を有効にするには、PHPのmbstring
拡張モジュールを有効にする必要があります。
アプリケーション・コードでmb_strlen()
などの関数を使用して、文字列内の文字数を計算する必要があります。これによって、文字列内のバイト数を戻すstrlen()
とは異なる値が戻される場合があります。
mbstring拡張モジュールを有効にし、Webサーバーを再起動すると、いくつかの構成オプションを使用できるようになります。mbstring.func_overload
をOverload設定のいずれかに設定して、標準のPHP文字列関数の動作を変更できます。
詳細は、PHPのmbstringに関する次のリファレンス・マニュアルを参照してください。
ICUライブラリをラップするPHP intl
拡張モジュールもまた、文字列の操作用として広く使用されています。次を参照してください。
グローバル環境のアプリケーションでは、ロケール・プリファレンスが異なるユーザーに対応する必要があります。ユーザーの優先ロケールを決定した後は、そのロケールの言語でHTMLコンテンツを構築し、そのロケールの表記規則に従います。
ユーザーのロケールを決定する一般的な方法として、ブラウザのデフォルトのISOロケール設定を使用する方法があります。通常、ブラウザは、Accept Language HTTPヘッダーでHTTPサーバーにそのロケール・プリファレンス設定を送信します。Accept Language HTTPヘッダーがNULLの場合は、使用可能なロケール・プリファレンス情報がなく、事前定義のデフォルトのロケールにフォールバックされます。
次のPHPコードは、$_SERVER
サーバー変数を使用して、Accept Language HTTPヘッダーからISOロケールを取り出します。
$s = $_SERVER["HTTP_ACCEPT_LANGUAGE"]
ユーザーのロケール・プリファレンスを決定すると、日付、時間、通貨の書式などのロケール依存の関数をコールして、ロケールの表記規則に従ってHTMLページを書式設定できます。
様々なプログラミング環境で実装されるグローバル・アプリケーションを構築する場合は、異なる環境間でユーザー・ロケール設定を同期できるようにする必要があります。たとえば、PL/SQLプロシージャをコールするPHPアプリケーションでは、PL/SQLプロシージャをコールする前に、ISOロケールを対応するNLS_LANGUAGE
値およびNLS_TERRITORY
値にマップし、ユーザーのロケールに合わせてパラメータ値を変更する必要があります。PL/SQL UTL_I18Nパッケージには、ISOロケールとOracleロケール間でマップできるマッピング関数が含まれています。
表14-1に、よく使用されるロケールをISO環境およびOracle環境に定義する方法を示します。
表 14-1: ISO、SQL、PL/SQLの各プログラミング環境でのロケールの表現
ロケール | ロケールID | NLS_LANGUAGE | NLS_TERRITORY |
---|---|---|---|
中国語(中華人民共和国) |
zh-CN |
SIMPLIFIED CHINESE |
CHINA |
中国語(台湾) |
zh-TW |
TRADITIONAL CHINESE |
TAIWAN |
英語(アメリカ合衆国) |
en-US |
AMERICAN |
AMERICA |
英語(イギリス) |
en-GB |
ENGLISH |
UNITED KINGDOM |
フランス語(カナダ) |
fr-CA |
CANADIAN FRENCH |
CANADA |
フランス語(フランス) |
fr-FR |
FRENCH |
FRANCE |
ドイツ語 |
de |
GERMAN |
GERMANY |
イタリア語 |
it |
ITALIAN |
ITALY |
日本語 |
ja |
JAPANESE |
JAPAN |
韓国語 |
ko |
KOREAN |
KOREA |
ポルトガル語(ブラジル) |
pt-BR |
BRAZILIAN PORTUGUESE |
BRAZIL |
ポルトガル語 |
pt |
PORTUGUESE |
PORTUGAL |
スペイン語 |
es |
SPANISH |
SPAIN |
HTMLページのエンコーディングは、ブラウザおよびインターネット・アプリケーションに関する重要な情報です。ページ・エンコーディングは、インターネット・アプリケーションがサービスを提供するロケールに使用されるキャラクタ・セットです。ブラウザは、正しいフォントおよびキャラクタ・セットのマッピング表を使用してHTMLページを表示できるように、ページ・エンコーディングを認識している必要があります。インターネット・アプリケーションは、HTMLフォームに入力されたデータを処理できるように、HTMLページ・エンコーディングを認識している必要があります。
ロケールごとに異なるネイティブ・エンコーディングを使用するのではなく、すべてのページ・エンコードでUTF-8(Unicodeエンコーディング)を使用することをお薦めします。このエンコーディングを使用すると、グローバル・アプリケーションのコーディングを簡略化できるのみでなく、単一ページに多言語コンテンツを配置できます。
HTMLページのエンコーディングをHTTPヘッダーまたはHTMLページ・ヘッダーに指定できます。
HTMLページ・エンコーディングをHTTPヘッダーに指定するには、HTTP仕様にContent-Type HTTPヘッダーを含めます。このヘッダーで、コンテンツ・タイプおよびキャラクタ・セットを指定します。Content-Type HTTPヘッダーの形式は次のとおりです。
Content-Type: text/html; charset=utf-8
charsetパラメータで、HTMLページのエンコーディングを指定します。charsetパラメータに指定可能な値は、ブラウザでサポートされている文字エンコーディングのIANA名です。
この方法は、主に静的なHTMLページに使用します。HTMLページ・エンコーディングをHTMLページ・ヘッダーに指定するには、文字エンコーディングを次のようにHTMLヘッダーに指定します。
<meta http-equiv="Content-Type" content="text/html;charset=utf-8">
charsetパラメータで、HTMLページのエンコーディングを指定します。Content-Type HTTPの場合と同様に、charsetパラメータに指定可能な値は、ブラウザでサポートされている文字エンコーディングのIANA名です。
ユーザー・インタフェースをユーザーのローカル言語で使用できるようにすることは、アプリケーションのグローバル化の基本的なタスクです。HTMLページのコンテンツの翻訳可能なソースは、次のカテゴリに分類されます。
アプリケーション・コードに含まれているテキスト文字列
静的なHTMLファイル、イメージ・ファイル、およびCSSなどのテンプレート・ファイル
データベースに格納された動的データ
PHPアプリケーション・ロジック内の翻訳可能な文字列を外部化して、そのテキストを簡単に翻訳できるようにする必要があります。これらのテキスト・メッセージは、翻訳対象データのタイプおよびボリュームに応じて、フラット・ファイルまたはデータベース表に格納できます。
HTMLファイルなどの静的ファイルは簡単に翻訳できます。これらのファイルを翻訳するときは、UTF-8をファイル・エンコーディングとして、対応する言語に翻訳する必要があります。翻訳したファイルの言語を区別するには、静的ファイルを言語ごとに異なるディレクトリにステージングするか、または異なるファイル名でステージングします。
アプリケーションのデータは、ユーザーが考えているとおりに表示される必要があります。そうでない場合、データの意味が誤って解釈される可能性があります。たとえば、12/11/05という日付は、アメリカ合衆国では2005年12月11日を意味するのに対して、イギリスでは2005年11月12日を意味します。ユーザーの数値書式および通貨書式にも同様の違いが存在します。たとえば、.という記号はアメリカ合衆国では小数点セパレータですが、ドイツでは千単位セパレータです。
各言語に独自のソート・ルールがあります。アルファベットの文字の順序に従う言語、文字の画数に従う言語、単語の発音に従う言語などがあります。ユーザーが慣れている言語順序でソートされていないデータを表示すると、情報の検索が難しくなり、時間がかかることがあります。
アプリケーションのロジックおよびデータベースから取得されるデータ量によっては、アプリケーション・レベルではなくデータベース・レベルでデータを書式設定する方が適切な場合があります。Oracle Databaseには、ユーザーのロケール・プリファレンスがわかっている場合にデータの表示を調整するのに役立つ機能が多く用意されています。以降の項では、SQLでのロケール依存の操作の例を示します。
Oracle Databaseの日付表示書式には、標準の日付、短い日付、長い日付の3種類があります。次の例では、アメリカ合衆国およびブラジルのポルトガル語ユーザーでの短い日付書式と長い日付書式の違いを示します。
SQL> alter session set nls_territory=america nls_language=american; Session altered. SQL> select employee_id EmpID, 2 substr(first_name,1,1)││'.'││last_name "EmpName", 3 to_char(hire_date,'DS') "Hiredate", 4 to_char(hire_date,'DL') "Long HireDate" 5 from employees 6* where employee_id <105; EMPID EmpName Hiredate Long HireDate ---------- --------------------------- ---------- ----------------------------- 100 S.King 06/17/1987 Wednesday, June 17, 1987 101 N.Kochhar 09/21/1989 Thursday, September 21, 1989 102 L.De Haan 01/13/1993 Wednesday, January 13, 1993 103 A.Hunold 01/03/1990 Wednesday, January 3, 1990 104 B.Ernst 05/21/1991 Tuesday, May 21, 1991
SQL> alter session set nls_language = 'BRAZILIAN PORTUGUESE' nls_territory = 'BRAZIL'; Sessão alterada. SQL> select employee_id EmpID, 2 substr(first_name,1,1)││'.'││last_name "EmpName", 3 to_char(hire_date,'DS') "Hiredate", 4 to_char(hire_date,'DL') "Long HireDate" 5 from employees 6* where employee_id <105; EMPID EmpName Hiredate Long HireDate ----- -------- --------- ------------------------------- 100 S.King 17/6/2003 terça-feira, 17 de junho de 2003 101 N.Kochhar 21/9/2005 quarta-feira, 21 de setembro de 2005 102 L.De Haan 13/1/2001 sábado, 13 de janeiro de 2001 103 A.Hunold 3/1/2006 terça-feira, 3 de janeiro de 2006 104 B.Ernst 21/5/2007 segunda-feira, 21 de maio de 2007
次の例では、アメリカ合衆国とブラジルのポルトガル語ユーザーでの小数点文字およびグループ・セパレータの違いを示します。
SQL> alter session set nls_territory=america; Session altered. SQL> select employee_id EmpID, 2 substr(first_name,1,1)││'.'││last_name "EmpName", 3 to_char(salary, '99G999D99') "Salary" 4 from employees 5* where employee_id <105 EMPID EmpName Salary ---------- --------------------------- ---------- 100 S.King 24,000.00 101 N.Kochhar 17,000.00 102 L.De Haan 17,000.00 103 A.Hunold 9,000.00 104 B.Ernst 6,000.00 SQL> alter session set nls_territory=brazil; Session altered. SQL> select employee_id EmpID, 2 substr(first_name,1,1)││'.'││last_name "EmpName", 3 to_char(salary, '99G999D99') "Salary" 4 from employees 5* where employee_id <105 EMPID EmpName Salary ---------- --------------------------- ---------- 100 S.King 24.000,00 101 N.Kochhar 17.000,00 102 L.De Haan 17.000,00 103 A.Hunold 9.000,00 104 B.Ernst 6.000,00
注意: Oracleで使用されている小数点セパレータおよび千単位セパレータがそれぞれ'.'と','でない場合、返されたデータ値で計算を実行したときにPHPエラーが発生します。これは、PHPではセパレータをPHP形式で解析できない場合に、数字を含んだ文字列変数を整数または浮動小数の変数に正しく変換できないためです。この問題を回避するには、次を使用して書式を明示的に設定します。alter session set nls_numeric_characters = '.,' |
スペイン語では、伝統的にch、llおよびñが一意の文字として扱われ、それぞれc、lおよびnの後に順序付けられます。次の例では、ChenとChungという従業員名にスペイン語のソートを使用した場合の結果を示します。
SQL> alter session set nls_sort=binary; Session altered. SQL> select employee_id EmpID, 2 last_name "Last Name" 3 from employees 4 where last_name like 'C%' 5* order by last_name EMPID Last Name ---------- ------------------------- 187 Cabrio 148 Cambrault 154 Cambrault 110 Chen 188 Chung 119 Colmenares 6 rows selected. SQL> alter session set nls_sort=spanish_m; Session altered. SQL> select employee_id EmpID, 2 last_name "Last Name" 3 from employees 4 where last_name like 'C%' 5* order by last_name EMPID Last Name ---------- ------------------------- 187 Cabrio 148 Cambrault 154 Cambrault 119 Colmenares 110 Chen 188 Chung 6 rows selected.
NLS_LANGUAGE
パラメータは、データベースから戻されるデータベース・エラー・メッセージの言語も制御します。SQL文を発行する前にこのパラメータを設定すると、言語固有のデータベース・エラー・メッセージがアプリケーションに戻されるようになります。
次のサーバー・メッセージを考えてみます。
ORA-00942: table or view does not exist
NLS_LANGUAGE
パラメータをBRAZILIAN PORTUGUESE
に設定すると、このサーバー・メッセージは次のように表示されます。
ORA-00942: a tabela ou view não existe
Oracle Databaseのグローバリゼーション・サポート機能の詳細は、『Oracle Database Express Edition 2日で開発者ガイド』のグローバル環境での作業に関する項を参照してください。