- PR -

Windows-31JとShift_JIS

投稿者投稿内容
アックリー
会議室デビュー日: 2005/06/28
投稿数: 6
投稿日時: 2005-06-28 11:33
みなさま、はじめまして。

サイト1:ページエンコードがShift_JIS
 RedHatLinux 9
 JDK 1.4.2_03
 Tomcat 4.1.30
 PostgreSQL 7.3.3

サイト2:ページエンコードがWindows-31J
 RedHatLinux 9
 JDK 1.4.2_03
 Tomcat 4.1.30
 PostgreSQL 7.3.3

という二つのサイトがあります。

ちなみに、サイト1と2はユーザが情報を入力できるサイトなのですが、困ったことにサイト1で入力されたらそれをサイト2にも表示させろとの指示が下り、構築にあたりました。

サイト1で入力があった場合、それをBASE64でエンコードして、サイト2のサーブレットに飛ばして、requestを取得し、BASE64でデコード後に値を取得しデータベースに格納しています。

そこで、非常に困った問題がおきました。サイト1からサイト2へデータを投げて、データベースに格納するまでは何とかできたのですが、サイト2でサイト1から登録されたデータを表示させると「ー」や「〜」などの文字が見事に「?」に化けてしまいます。

サイト2にテストページを用意して、ページエンコードをShift_JISにすると、↑の文字化けはなおったのですが、今度はサイト2で登録されている「ー」が文字化けを起こしました。
// 当然だと思いますが・・・。


ページエンコードがShift_JISのページから、ページエンコードがWindows-31Jのページへ文字化けすることなく登録する方法などがあれば、教えていただけたらと思います。

舌足らずで大変もうしわけございませんが、ご教授よろしくお願いします。
スフレ
ぬし
会議室デビュー日: 2005/05/27
投稿数: 281
お住まい・勤務地: 東京
投稿日時: 2005-06-28 12:46
何をbase64エンコードして送ったんでしょうか?
アックリー
会議室デビュー日: 2005/06/28
投稿数: 6
投稿日時: 2005-06-28 13:24
スフレさま、ご返信いただきありがとうございます。
また情報が足りず大変もうしわけございませんでした。

> 何をbase64エンコードして送ったんでしょうか?
フォームに入力された文字です。
<input type="text" name="name" value"">
String s = request.getParameter("name");
byte[] bytes = Base64.encodeBase64(s.getBytes());
String encoded = new String(bytes);
というような感じです。

ちなみに、Base64は
Jakarta commonsのCodecパッケージを使用しております。

これを
URLConnectionで
setDoOutput(true);
にし、POSTでサイト2のサーブレットへ送っています。

ちなみに、PostgreSQLに実行されたSQL文をログに残すように設定し、確認してみたところ
「〜」と入力したものが「&#12316;」として残っていました・・・。
// ↑プレビューしたところ、うまく出ませんでした(涙)

よろしくお願いします。
スフレ
ぬし
会議室デビュー日: 2005/05/27
投稿数: 281
お住まい・勤務地: 東京
投稿日時: 2005-06-28 14:22
s.getBytes() のところで、「プラットフォームデフォルトの符号化方式のバイト列」になってますね。
ここで、s.getBytes("Windows-31J") として、受け取り側でも base64 のデコード結果を new String(decoded, "Windows-31J") としてみるとどうでしょう。
甕星
ぬし
会議室デビュー日: 2003/03/07
投稿数: 1185
お住まい・勤務地: 湖の見える丘の上
投稿日時: 2005-06-28 14:56
Unicode<->ShiftJISのコードマッピングを行う時のテーブルが、プラットフォームによって異なるのは有名な話です。MySQLのコードページが何になっているのか知りませんが、
Web(SJIS)→Tomcat→Java(Unicode)→MySQL(?)の過程と、MySQL(?)→Java(Unicode)→Tomcat→Web(Windows-31J, SJIS)の過程で用いている変換テーブルが違っているのでしょう。
'〜'を別の適当な文字にエスケープして、データベースに格納するのもお手軽な対策かと思います。
#Microsoftの実装が変なだけだと言う話もありますが
アックリー
会議室デビュー日: 2005/06/28
投稿数: 6
投稿日時: 2005-06-28 14:57
スフレさん、またまたご返信いただきありがとうございます。m(_|_)m

> s.getBytes("Windows-31J") として、受け取り側でも base64 のデコード結果を new String(decoded, "Windows-31J") としてみるとどうでしょう。
スフレさんの言われたとおりにしてみると、不思議な現象が起こりました。
例えば、サイト1で
「ーーーーーーー〜〜〜〜〜〜〜〜〜〜あああ」
と入力します。
すると、サイト2では
「ーーーーーーー??????????あああ」
というように、「ー」は化けなくなったのですが「〜」が化けてしまいます。

PostgreSQLのINSERTログを見ても、「ーーーーーーー??????????あああ」と出ています。
デコードは
String str = reques.getParameter("name");
byte[] bytes = str.getBytes();
s_decoded = new String(Base64.decodeBase64(bytes), "Windows-31J");
このような感じで行っています。

ご教授いただけると幸いです。
アックリー
会議室デビュー日: 2005/06/28
投稿数: 6
投稿日時: 2005-06-28 15:27
甕星さん、ご助言いただきありがとうございます。m(_|_)m

> MySQLのコードページが何になっているのか知りませんが、
すみません。申し遅れました。m(_|_)m
PostgreSQLのデータベース文字コードはUnicodeです。

> '〜'を別の適当な文字にエスケープして、データベースに格納するのもお手軽な対策かと思います。
なるほどなるほど。
ということは、'ー'などの化ける文字は全部、エスケープしてあげる必要があるということですよね。(^_^
uk
ぬし
会議室デビュー日: 2003/05/20
投稿数: 1155
お住まい・勤務地: 東京都
投稿日時: 2005-06-28 17:46
引用:

アックリーさんの書き込み (2005-06-28 13:24) より:
String s = request.getParameter("name");
byte[] bytes = Base64.encodeBase64(s.getBytes());
String encoded = new String(bytes);


POSTで送るのであれば、こんな面倒なことをしなくても普通の文字列として送り、受け側の
サーブレット側でリクエストに適切なエンコーディングで設定すればよいと思うのですが、
このような実装にしているのは何か理由があるのですか?

スキルアップ/キャリアアップ(JOB@IT)