1

MSSQL2005 データベースにアクセスし、そこからデータを読み取り、結果をメールで送信する php スクリプトがあります。

一部の列名とフィールド自体の両方に特殊文字が含まれています。

ブラウザー (Web サーバー iis) を介してスクリプトにアクセスすると、クエリが正しく実行され、メールの内容が (対象ユーザーに対して) 正しくエンコードされます。ただし、コンソールから php を実行すると、クエリが失敗します (列名に特殊文字が含まれているため)。クエリ内の特殊文字を chr() の呼び出しと latin-1 の文字コードに置き換えると、クエリは正しく実行されますが、結果も latin-1 でエンコードされるため、メールに正しく表示されません。PHP/MSSQL ドライバー/… が 2 つのシナリオで異なるエンコーディングを使用しているのはなぜですか? それを回避する方法はありますか?

ご存じのように、SQLAgent (または taskmanager など) を使用してスクリプトをスケジュールしたいので、コンソールが必要です。

4

3 に答える 3

2

データベースにある文字の種類によっては、コンソールの制限である可能性があります。コンソールに入力chcpすると、アクティブなコード ページが表示されます。これは、拡張 ASCII とも呼ばれるCP437のようなものかもしれません。UTF8 のように、このコード ページ以外の文字を使用すると、問題が発生する可能性があります。現在アクティブなコード ページを変更するには、chcp 65001UTF8 に切り替えるように入力します。

すべてのフォントが拡張文字をサポートしているわけではないため、必要な文字に応じて、デフォルトのラスター フォントを Lucida コンソールに変更することもできます (コマンド プロンプト ウィンドウのタイトル、プロパティ、フォントを右クリックします)。

すでに述べたように、PHP の Unicode サポートは理想的ではありませんが、適切に配置されたutf8_decodeの関数呼び出しを使用して、PHP5 でそれを行うことができます。文字エンコーディングの秘訣は、使用しているすべてのツールの現在のエンコーディングが何であるかをよく理解することです: データベース、データベース接続、PHP 変数の現在のバイト数、コンソール画面への出力、メール本文のエンコーディング、メール クライアント、等々...

特殊文字を含むすべてのものについては、現代では UTF8 のようなものが推奨されることがよくあります。途中ですべてが UTF8 に設定されていることを確認し、必要な場合にのみ変換してください。

于 2008-12-13T03:08:54.710 に答える
1

PHP 文字列について覚えておくべきことは、それらがバイトのストリームであることです。(何をしていても) 正しい文字セットでデータを取得したい場合は、ある種の関数またはフィルターを使用して明示的にこれを行う必要があります。どれもかなり低レベルです。

設定によっては、データベース内の文字列の内部文字セットを知る必要がある場合がありますが、少なくとも、データベースが PHP に送信している文字セットを知る必要があります (覚えておいてください、PHP にとっては単なるストリームだからです)。のバイト)。

次に、ターゲットの文字セットを知る必要があります (そして、場合によってはそれを指定する必要があります)。たとえば、データベースから utf-8 を取得しているが、latin-1 を送信したい (したがって、「Content-transfer-encoding」としてエンコードされた base64 または q-printable) とします。

$send_string = base64_encode(utf8_decode($database_string));

もちろん、この場合、すべての utf-8 文字が latin-1 文字セットに存在することを知っておく必要があり、実際には base64 は必要ないでしょう (残念ながら、PHP には優れた q-printable エンコーディング関数がありません)。 、不思議なことに、それはデコード用です)、そして utf-8 <=> latin-1 について話していない場合は、代わりに mbstring 関数を取り出したいと思うでしょう。

コンソールに関しては、コンソールから特殊文字を入力するときに PHP が何を取得しているかを知る必要があります。これは、おそらくシェルや PHP の設定に依存します。しかし、PHP は文字列をバイト バイト バイトとしてしか認識しないことを覚えておいてください。

于 2008-12-13T01:14:08.187 に答える
1

英語以外の世界に対する PHP の貧弱なサポートはよく知られています。基本的な ASCII 領域外の文字を含むデータベースを使用したことはありませんが、明らかに、すでに回避策があり、それと一緒に暮らす必要があるようです。

1. すべての特殊文字とそれに相当する CHR を含む配列を作成する 2. 配列を foreach し、クエリで str_replace を実行する

しかし、クエリがハードコーディングされている場合は、問題ないと思います。また、最新の PHP、少なくとも 4.4.x を使用していることを確認してください。これは修正された変更が常にありますが、4.xx のリリース ノートをざっと読んだところ、問題に関連するものは何も見つかりません。

于 2008-12-03T22:42:07.417 に答える