ホームページ  >  記事  >  データベース  >  php+mysqlで読み書き分離を実現する方法

php+mysqlで読み書き分離を実現する方法

WBOY
WBOY転載
2023-06-03 09:43:581407ブラウズ

PHP は MySQL の読み取りと書き込みの分離を実装しており、次の関数を実装する必要があります:

1. 読み取り操作と書き込み操作を区別します: PHP コードでは、データベース区別するには、読み取り操作と書き込み操作を異なる MySQL インスタンスに配置する必要があります。

異なるアルゴリズムを使用して、読み取りリクエストを複数の MySQL インスタンスに均等に分散するロード バランシング ソリューションを設計する必要があります。

以下、上記の機能の実装方法を詳しく紹介します。

読み取り操作と書き込み操作の分離

MySQL の読み取り操作と書き込み操作の分離を実装するには、MySQL マスター/スレーブ レプリケーション テクノロジのサポートが必要です。 MySQL のマスター/スレーブ レプリケーションでは、すべての書き込み操作はマスター データベースで実行され、読み取り操作のみがスレーブ データベースで実行されます。

PHP コードでは、MySQL の読み取り操作と書き込み操作を区別する必要があります。書き込み操作はメイン ライブラリに送信され、読み取り操作はスレーブ ライブラリに送信されます。

次の 2 つの方法は、特定の実装に使用できます:

1. 接続の手動切り替え: コード内の読み取りおよび書き込み操作の接続を手動で切り替えます。必要に応じて、メイン データベースとスレーブ データベースを異なる MySQL インスタンスに接続し、対応する SQL ステートメントを実行します。

たとえば、次の SQL ステートメントの場合:

SELECT * FROM users WHERE age>18;

次のコードを使用して、読み取り操作の接続を切り替えることができます:

//生成一个读取从库的连接
$slaveConn = mysqli_connect($slaveHost, $slaveUser, $slavePass, $dbName);
mysqli_query($slaveConn, "SET NAMES utf8");

//查询数据
$result = mysqli_query($slaveConn, "SELECT * FROM users WHERE age>18");

同様に、書き込み操作の場合:

INSERT INTO users (name,age,sex) VALUES ('jack',18,'male');

次のコードを使用して書き込み操作の接続を切り替えることができます:

//生成一个写入主库的连接
$masterConn = mysqli_connect($masterHost, $masterUser, $masterPass, $dbName);
mysqli_query($masterConn, "SET NAMES utf8");

//插入数据
$result = mysqli_query($masterConn, "INSERT INTO users (name,age,sex) VALUES ('jack',18,'male')");

上記のコードでは、mysqli_connect 関数を使用してデータベース接続を生成し、mysqli_query メソッドを使用してデータベース接続を操作します。 MySQLデータベース。このうち、$slaveHost、$slaveUser、$slavePassはスレーブライブラリの接続情報、$masterHost、$masterUser、$masterPassはマスターライブラリの接続情報です。

PHP フレームワークの組み込み実装を使用して、読み取り操作と書き込み操作を切り替えることができます。 Yii2 フレームワークでは、次のコードを使用して読み取り操作と書き込み操作を切り替えることができます:

//生成一个读取从库的连接
$slaveConn = Yii::$app->slaveDb->getConnection();

//查询数据
$query = new \yii\db\Query();
$result = $query->from('users')->where(['age' > 18])->all($slaveConn);

同様に、次のコードを使用して書き込み操作を切り替えます:

//生成一个写入主库的连接
$masterConn = Yii::$app->masterDb->getConnection();

//插入数据
$result = Yii::$app->db->createCommand()->insert('users', [
'name' => 'jack',
'age' => 18,
'sex' => 'male'
])->execute($masterConn);

上記のコードでは、 Yii::$app ->slaveDb と Yii::$app->masterDb はどちらも Yii2 フレームワークの組み込みデータベース接続コンポーネントであり、スレーブ ライブラリからの読み取りとマスター ライブラリへの書き込みのメソッドを提供します。

負荷分散戦略

MySQL の読み取りと書き込みの分離を実装する場合、負荷分散は非常に重要な部分です。すべての読み取りリクエストが各スレーブ データベースに均等に分散される場合にのみ、MySQL の読み取りと書き込みの分離の利点を最大限に活用できます。

一般的に使用されるロード バランシング戦略には次のものがあります:

1. ランダム戦略: 読み取りリクエストを各スレーブ データベースにランダムに分散します。

2. ポーリング戦略: 読み取りリクエストを各スレーブ ライブラリに順番に割り当て、それらを周期的に使用します。

3. 可用性優先戦略: 可用性監視方法を使用して、読み取り操作の前に利用可能なスレーブ ライブラリを選択します。

この記事ではポーリング戦略を採用しており、具体的な実装は次のとおりです。

//从库连接信息
$slave1 = array(
'host' => 'slave1.host.com', 
'user' => 'slave1user', 
'pass' => 'slave1pass',
'name' => 'dbname'
);

$slave2 = array(
'host' => 'slave2.host.com', 
'user' => 'slave2user', 
'pass' => 'slave2pass',
'name' => 'dbname'
);

$slave3 = array(
'host' => 'slave3.host.com', 
'user' => 'slave3user', 
'pass' => 'slave3pass',
'name' => 'dbname'
);


//增加从库列表
$slaveList = array($slave1, $slave2, $slave3);


//轮询获取从库连接信息
function getSlaveConn() {
global $slaveList;
static $index = 0;
if ($index >= count($slaveList)) {
    $index = 0;
}
$slave = $slaveList[$index];
$index++;
$conn = mysqli_connect($slave['host'], $slave['user'], $slave['pass'], $slave['name']);
mysqli_query($conn, "SET NAMES utf8");
return $conn;
}

上記のコードでは、$slave1、$slave2、$slave3 がスレーブ ライブラリの接続情報、$slaveList です。スレーブライブラリリストです。 getSlaveConn 関数では、$index はスレーブ ライブラリへの接続数です。接続数がスレーブ ライブラリ リストの長さと等しい場合、$index は 0 にリセットされ、最初のスレーブ ライブラリから接続が再接続されます。スレーブ ライブラリに接続するたびに、mysqli_connect 関数を使用してデータベースに接続します。

上記の実装により、PHP の MySQL の読み書き分離を実現する機能が実装されました。上記のコードを使用して、PHP アプリケーションに MySQL の読み取り/書き込み分離機能を実装し、必要に応じて負荷分散戦略を追加または変更できます。

高い同時実行性と大量のデータの場合、PHP を使用して MySQL の読み取りと書き込みを分離すると、MySQL データベースの読み取りと書き込みのパフォーマンスが効果的に向上し、アプリケーションの応答時間が短縮され、ユーザー エクスペリエンスが向上します。

以上がphp+mysqlで読み書き分離を実現する方法の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事はyisu.comで複製されています。侵害がある場合は、admin@php.cn までご連絡ください。