rkr / db-sync
用于mysql类似数据库的同步工具
dev-master
2024-04-13 19:37 UTC
Requires
- php: >= 7.4
- ext-json: *
- ext-mbstring: *
- ext-pdo: *
- rkr/php-mysql-query-builder: 0.3.*
Requires (Dev)
- logger/essentials: ^0.2.0
- phpstan/phpstan: >= 0.1
- phpunit/phpunit: ^9.5
This package is auto-updated.
Last update: 2024-09-13 20:33:45 UTC
README
概述
- 从一个PDO连接同步数据到另一个连接。
- 如果数据在两个连接中相等,则不会进行任何更改。
- 数据库中的每个表都必须有一个主键。
- 在目标数据库中检测新或缺失的行基于主键。
- 通过某种散列算法检测更改的行,其中主键之外的所有列值形成一个散列。
- 数据集将以块的形式进行同步,因此表的垂直大小无关紧要。
快速开始
此项目开始是为了有一个工具,可以快速将特定表中的数据拉入本地开发数据库。项目的目标不是拥有某种类型的命令行工具来同步数据库。为此,有像pt-table-sync这样的工具。它更倾向于解决那些难以通过cli界面建模的复杂场景。
重要
此项目不旨在同步两个生产服务器。它旨在从预发布或生产服务器同步一些数据到本地开发机器。
尽管这不是必须的,因为db-sync在任何情况下都不会写入源数据库,但建议在源数据库上使用一个配置为只读的db-user。只是为了明确。
目的是同步数据。表结构应通过迁移脚本来同步,但这超出了本项目范围。
一个从源mariadb 10.2.3+到目标mariadb 10.2.3+的最基本的脚本可能看起来像这样
<?php use Kir\DBSync\DBTable; use Kir\DBSync\PDOWrapper; use Kir\DBSync\DBSyncData; use Kir\DBSync\DBEngines\MariaDBEngine; use Logger\Loggers\ResourceLogger; use Logger\Formatters\TemplateFormatter; require 'vendor/autoload.php'; // Bring your own PSR-Logger. This is from logger/essentials (packagist) $logger = new TemplateFormatter(new ResourceLogger(STDOUT)); $pdoOptions = [PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION, PDO::MYSQL_ATTR_COMPRESS => true]; $sourcePDOConn = new PDO('mysql:host=127.0.0.1;port=3312;dbname=some_db_name;charset=utf8', 'readonly1', null, $pdoOptions); $sourceDBEngine = new MariaDBEngine(new PDOWrapper($sourcePDOConn)); $destPDOConn = new PDO('mysql:host=127.0.0.1;port=3306;dbname=some_db_name;charset=utf8', 'root', null, $pdoOptions); $destDBEngine = new MariaDBEngine(new PDOWrapper($destPDOConn)); $tables = $sourceDBEngine->getTableProvider()->getAllTables(); $tables = array_filter($tables, fn(DBTable $table) => strpos($table->name, 'shop__stats_') !== 0); $syncData = new DBSyncData($logger); foreach($tables as $table) { $logger->info($table->name); try { $syncData->syncTwoTablesFromDifferentConnections($table, $sourceDBEngine, $destDBEngine); } catch (PDOException $e) { $logger->error($e->getMessage()); } }