Workerman/MySQL

注意
このライブラリはもはやメンテナンスされていません。代わりに illuminate/database または topthink/think-orm を使用することをお勧めします。

説明

常駐メモリプログラムは、mysqlを使用する際に頻繁にmysql gone awayエラーに遭遇します。これはプログラムとmysqlの接続が長時間通信されていないため、接続がmysqlサーバーによって切断されるためです。このデータベースクラスはこの問題を解決できます。mysql gone awayエラーが発生した場合、再試行します。

依存の拡張

このmysqlクラスは、pdopdo_mysqlの2つの拡張に依存しています。拡張が不足しているとUndefined class constant 'MYSQL_ATTR_INIT_COMMAND' in ....エラーが発生します。

コマンドラインでphp -mを実行すると、すべてのphp cliにインストールされている拡張をリストします。pdoまたはpdo_mysqlがない場合は、自分でインストールしてください。

centosシステム

PHP5.x

yum install php-pdo
yum install php-mysql

PHP7.x

yum install php70w-pdo_dblib.x86_64
yum install php70w-mysqlnd.x86_64

パッケージ名が見つからない場合は、yum search php mysqlで検索してください。

ubuntu/debianシステム

PHP5.x

apt-get install php5-mysql

PHP7.x

apt-get install php7.0-mysql

パッケージ名が見つからない場合は、apt-cache search php mysqlで検索してください。

上記の方法でインストールできませんか?

上記の方法でインストールできない場合は、workermanマニュアル - 付録 - 拡張インストール - 方法3 ソースコードコンパイルインストールを参照してください。

Workerman/MySQLのインストール

方法1:

composerを使ってインストールできます。コマンドラインで以下のコマンドを実行します(composerのソースは海外にあるため、インストールプロセスが非常に遅い場合があります)。

composer require workerman/mysql

上記のコマンドが成功すると、vendorディレクトリが生成され、その後プロジェクト内でvendor下のautoload.phpを読み込みます。

require_once __DIR__ . '/vendor/autoload.php';

方法2:

ソースコードをダウンロードし、解凍したディレクトリを任意の場所にプロジェクトに配置し、直接ソースファイルをrequireします。

require_once '/your/path/of/mysql-master/src/Connection.php';

注意

onWorkerStartコールバック内でデータベース接続を初期化することを強くお勧めします。Worker::runAll();を実行する前に接続を初期化しないでください。Worker::runAll();を実行する前に初期化された接続は親プロセスに属し、子プロセスはこの接続を継承します。親プロセスと子プロセスが同じデータベース接続を共有するとエラーが発生します。

use Workerman\Worker;
use Workerman\Connection\TcpConnection;
require_once __DIR__ . '/vendor/autoload.php';

$worker = new Worker('websocket://0.0.0.0:8484');
$worker->onWorkerStart = function($worker)
{
    // dbインスタンスをグローバル変数に保存します(特定のクラスの静的メンバーに保存しても良い)
    global $db;
    $db = new \Workerman\MySQL\Connection('host', 'port', 'user', 'password', 'db_name');
};
$worker->onMessage = function(TcpConnection $connection, $data)
{
    // グローバル変数からdbインスタンスを取得します
    global $db;
    // SQLを実行します
    $all_tables = $db->query('show tables');
    $connection->send(json_encode($all_tables));
};
// Workerを実行します
Worker::runAll();

具体的なMySQL/Connectionの使用法

// db接続を初期化します
$db = new \Workerman\MySQL\Connection('host', 'port', 'user', 'password', 'db_name');

// すべてのデータを取得します
$db->select('ID,Sex')->from('Persons')->where('sex= :sex AND ID = :id')->bindValues(array('sex'=>'M', 'id' => 1))->query();
// 等価
$db->select('ID,Sex')->from('Persons')->where("sex= 'M' AND ID = 1")->query();
// 等価
$db->query("SELECT ID,Sex FROM `Persons` WHERE sex='M' AND ID = 1");

// 一行データを取得します
$db->select('ID,Sex')->from('Persons')->where('sex= :sex')->bindValues(array('sex'=>'M'))->row();
// 等価
$db->select('ID,Sex')->from('Persons')->where("sex= 'M' ")->row();
// 等価
$db->row("SELECT ID,Sex FROM `Persons` WHERE sex='M'");

// 一列データを取得します
$db->select('ID')->from('Persons')->where('sex= :sex')->bindValues(array('sex'=>'M'))->column();
// 等価
$db->select('ID')->from('Persons')->where("sex= 'F' ")->column();
// 等価
$db->column("SELECT `ID` FROM `Persons` WHERE sex='M'");

// 単一の値を取得します
$db->select('ID')->from('Persons')->where('sex= :sex')->bindValues(array('sex'=>'M'))->single();
// 等価
$db->select('ID')->from('Persons')->where("sex= 'F' ")->single();
// 等価
$db->single("SELECT ID FROM `Persons` WHERE sex='M'");

// 複雑なクエリ
$db->select('*')->from('table1')->innerJoin('table2','table1.uid = table2.uid')->where('age > :age')->groupBy(array('aid'))->having('foo="foo"')->orderByASC/*orderByDESC*/(array('did'))
->limit(10)->offset(20)->bindValues(array('age' => 13));
// 等価
$db->query('SELECT * FROM `table1` INNER JOIN `table2` ON `table1`.`uid` = `table2`.`uid`
WHERE age > 13 GROUP BY aid HAVING foo="foo" ORDER BY did LIMIT 10 OFFSET 20');

// 挿入
$insert_id = $db->insert('Persons')->cols(array(
    'Firstname'=>'abc',
    'Lastname'=>'efg',
    'Sex'=>'M',
    'Age'=>13))->query();
等価
$insert_id = $db->query("INSERT INTO `Persons` ( `Firstname`,`Lastname`,`Sex`,`Age`)
VALUES ( 'abc', 'efg', 'M', 13)");

// 更新
$row_count = $db->update('Persons')->cols(array('sex'))->where('ID=1')
->bindValue('sex', 'F')->query();
// 等価
$row_count = $db->update('Persons')->cols(array('sex'=>'F'))->where('ID=1')->query();
// 等価
$row_count = $db->query("UPDATE `Persons` SET `sex` = 'F' WHERE ID=1");

// 削除
$row_count = $db->delete('Persons')->where('ID=9')->query();
// 等価
$row_count = $db->query("DELETE FROM `Persons` WHERE ID=9");

// トランザクション
$db->beginTrans();
....
$db->commitTrans(); // または $db->rollBackTrans();