月別アーカイブ: 2月 2011

PHPとMySQLと文字コードと

 最近の流れとして、文字コードと言えばUTF8って感じが強い(携帯などではSJISもあるけど)
 しかしながら、CentOSや海外から拾ったコンパイル済みPHPの従来型MySQL関数って、コネクト時のクライアントエンコーディングがlatin1になっている。
 この値は、mbstringとか色々変えても変わらず、自前でビルドしないとダメっぽい。
 他方、MySQLサーバではmy.cnfに

[mysqld]
character-set-server=utf8
collation-server=utf8_general_ci

等と入れてやるとUTF8で回るし、個別にデータベースやテーブルを作るときに指定してやることも出来る(現在のMySQLではdefault-character-setは推奨外) コマンドラインのmysqlもmy.cnfに

[mysql]
default-character-set=utf8

とかすれば、UTF8で繋がる。
 それでも、PHPクライアントでmysql_connectして、mysql_client_encodingで引っ張るとlatin1になるし、SHOW VARIABLESクエリの戻り値もクライアントやリザルトはlatin1になってしまう。
 このため、最近のMySQLとPHP(5.2.3以降)の組み合わせではmysql_set_charsetと言う関数を使ってクライアントのエンコーディングを設定してやることが出来る(古いバージョンでは、SET NAMESクエリを発行して変更できるが、サニタイズ関連の動作が期待と異なる事になったり、タイムアウトしたDB接続を自動再接続したときにエンコーディングが元に戻る様だ)
 しかし、実際の所は、このあたりの設定をせずともPHPから処理する限りは、UTF8の文字列を普通にDBに格納して取得も出来てしまう。 これは、エンコーディング設定が同じなら同じ方法で文字列を化けさせているから、化けた文字列を格納しても、取り出し時に逆処理で戻してしまい、外見上は問題なく動作してしまっているのだ。
これをデータベースマネージャなどでテーブル表示すると化け化けの文字列であるから、管理コマンドや、別のアプリケーションからDBを参照したときに問題が起きるし、検索処理や関数などで予想外の動作をする可能性もあるので、エンコーディング設定はしっかり行っておかなければならない。

 my.cnfの[mysqld]でskip-character-set-client-handshakeを設定してやると、サーバの標準キャラクタセットをクライアント値と同期しないので、mbstring.internal_encodingをutf8にしたPHPとutf8設定のMySQLの組み合わせでutf8で格納されて、データベースマネージャなどでもちゃんと表示できるので、この方法を示しているページもあるが、この状態でもmysql_client_encodingはlatin1で、SHOW VARIABLES結果はutf8設定というおかしな状態になるので、これも予想外の動作をする可能性があるわけで、正しく動作させたければ、毎回mysql_set_charsetを実行するか、ソースからPHPをビルドして、標準エンコーディングをutf8にするなどした方が良いと思う。
 また、skip-character-set-client-handshake設定してしまうと、[mysql]のdefault-character-setと整合を取らなくなるので注意が必要(例えば、mysqlをdefault-character-set=ujisで動かしてると、mysqlコマンドで接続した段階ではクライアントがujisで、サーバはutf8クライアントと認識しているのでキャラクタセットの齟齬で文字化けが生じる)

(467)

カテゴリー: LAMP[Linux, Apache, MySQL, PHP], PHP | コメントをどうぞ

PHP設定2

  • PHPのセッション時間設定とか
    php.iniの設定ディレクティブ

    session.cookie_lifetime=秒数

    で、デフォルトのセッションクッキークライアント生存時間を設定している。
    初期値は0で、ブラウザが終了するまで有効。
    しかし、この設定でも長時間放置しておくとセッションが切れることがあるが、これは、サーバ側でセッションファイルが処分されるのが原因で、こちらは

    session.gc_maxlifetime=秒数

    と言うディレクティブで設定されていて、デフォルトが24分なので、これを1日とかに延ばしてしまえばOK。
    上の設定をしてもphpMyAdminが切れるのは、phpMyAdminのconfig.inc.phpの設定

    $cfg[‘LoginCookieValidity’] = ‘秒数‘;

    この値を設定する必要がある。

(178)

カテゴリー: LAMP[Linux, Apache, MySQL, PHP], PHP | コメントをどうぞ

応用コマンド1・PHP設定1

  • 現在のディレクトリ以下で探索語を含むファイルを探す。

find . -type f -print | xargs grep 探索語 /dev/null

  • PHP:DocumentRootより上のファイルのfopenに失敗する。

ウェブアプリがDocumentRootより上にあるファイルを読む場合に、php.iniの設定ディレクティブopen_base_dirに追記しておかないと、fopenがI/O errorになる。 .htaccessでphp_admin_valueで設定しても良い。

open_base_dir = 参照したいディレクトリ
(:区切りで列挙)

(45)

カテゴリー: LAMP[Linux, Apache, MySQL, PHP], PHP | コメントをどうぞ