跳转到正文

架构验证

当快照之间的架构发生变化(列被添加、删除或重命名)时,merql 会检测并报告这些差异。架构不匹配不会阻止合并,但会被明确指出,供调用方决定如何处理。

检测

SchemaValidator::validate() 会比较各表在 base、ours 和 theirs 快照中的列集合,并报告:

  • 在 ours 中添加的列(存在于 ours,但不存在于 base)
  • 在 ours 中删除的列(存在于 base,但不存在于 ours)
  • 在 theirs 中添加的列
  • 在 theirs 中删除的列
PHP
use Merql\Merge\ThreeWayMerge;

$merge = new ThreeWayMerge();
$result = $merge->merge($base, $ours, $theirs);

if ($result->hasSchemaMismatches()) {
    foreach ($result->schemaMismatches() as $mismatch) {
        echo $mismatch->getMessage() . "\n";
        // "Schema mismatch on table 'posts': columns added in theirs: subtitle"
    }
}

检测内容

变更 是否检测 备注
添加列 是 按每一侧报告(ours/theirs)
删除列 是 按每一侧报告
列类型变更 否 类型会存储,但不会比较
列重命名 否 会表现为添加列和删除列
主键变更 否 标识在快照时固定

合并期间的行为

当某列存在于一个快照中而不存在于另一个快照时,合并会将缺失的列值视为 null。这意味着:

  • 在 theirs 中添加且值非空的列会显示为 null -> value(接受 theirs 的变更)
  • 在 theirs 中删除的列会显示为 theirs 中所有行均具有 null

合并会继续执行并生成结果。架构不匹配仅提供信息。调用方应在应用之前确认目标数据库架构与合并后的数据相符。

访问不匹配信息

架构不匹配信息可在 ThreeWayMerge 上获取(通过 schemaMismatches()),也可在 MergeResult 上获取(通过 schemaMismatches() 和 hasSchemaMismatches())。这些信息会在 ConflictResolver::resolve() 过程中保留。

PHP
// On the merge result directly
$result->hasSchemaMismatches(); // bool
$result->schemaMismatches();    // list<SchemaException>

// Each mismatch is a SchemaException with a descriptive message
foreach ($result->schemaMismatches() as $e) {
    // $e->getMessage() includes table name and column details
}