İçeriğe geç

Test Stratejisi

merql, oracle tabanlı bir test modeli kullanır. Her test senaryosu bilinen bir girdi kümesi (üç veritabanı durumu) ve belirlenimci bir beklenen sonuç (oracle) tanımlar; ardından gerçek birleştirme çıktısını bu beklentiyle karşılaştırır. 32 senaryo; temiz birleştirmeleri, çakışmaları, kimlik çözümlemeyi, veri türlerini, ölçeği ve uç durumları kapsar.

Kabuk
# Run the full verification suite.
./bin/verify-all

Bu sayfadaki komutlar, merql deposunun bir çalışma kopyasında composer install sonrasında çalıştırılır. bin/ içindeki geliştirme betikleri, scenarios/ külliyatı ve testler Composer paketinin parçası değildir. Geliştirme bağımlılıkları PHP 8.4 veya üzerini gerektiren PHPUnit 13'ü içerir; kütüphanenin kendisi PHP 8.2'de çalışsa da.

Oracle tabanlı testler

Üç yönlü veritabanı birleştirmesi yapan mevcut bir referans aracı olmadığından oracle, harici bir araç tarafından üretilmek yerine bilinen girdilerden hesaplanır. Her senaryonun mantık yoluyla doğrulanabilen belirlenimci bir beklenen sonucu vardır:

  1. Kurulum -- bilinen içeriklerle üç veritabanı durumu (base, ours, theirs) oluşturun.
  2. Oracle -- bilinen girdilerden beklenen birleştirme sonucunu hesaplayın.
  3. Gerçek sonuç -- merql ile üç durum üzerinde birleştirmeyi çalıştırın.
  4. Karşılaştırma -- gerçek sonuç, beklenen sonuçla tam olarak eşleşmelidir.
Kod
Known inputs (base, ours, theirs)
         |                    |
    Deterministic          merql merge
    computation
         |                    |
    Expected result       Actual result
         |                    |
         -----> Compare <-----
                  |
            Pass or Fail

Testleri çalıştırma

Tam doğrulama

verify-all betiği son kontroldür. Statik analizi, kodlama standartlarını, PHPUnit testlerini ve oracle regresyon paketini çalıştırır:

Kabuk
./bin/verify-all

Herhangi bir çalışma tamamlanmış sayılmadan önce bu kontroller geçmelidir.

Oracle regresyon paketi

32 senaryonun tümünü çalıştırın:

Kabuk
./bin/test-regression

Tek bir kategoriyi çalıştırın:

Kabuk
./bin/test-regression --category clean
./bin/test-regression --category conflict
./bin/test-regression --category identity

Kategoriler, scenarios/ altındaki dizin adlarıdır: clean, conflict, identity, types, scale ve edge. Bilinmeyen bir kategori No scenarios found çıktısını verir ve başarıyla çıkar. Birden fazla kategoriyi çalıştırmak için --category yinelenebilir.

Betik --jobs seçeneğini de kabul eder ancak değeri yok sayıp senaryoları sırayla çalıştırır (#5).

En az çıktıyla çalıştırın (yalnızca başarılı/başarısız):

Kabuk
./bin/test-regression --fast

Tek senaryo

Tam işlem hattı üzerinden tek bir senaryoyu test edin:

Kabuk
./bin/test-scenario column-level-clean

Tek tek oracle adımları

Kabuk
./bin/oracle column-level-clean    # Compute expected result
./bin/actual column-level-clean    # Run merql, capture output
./bin/compare column-level-clean   # Diff oracle vs actual

Birim testleri

Kabuk
composer test:unit         # Isolated component tests
composer test:integration  # Integration tests (SQLite, plus MySQL when configured)
composer test              # All PHPUnit suites
composer test:oracle       # Oracle regression corpus (bin/test-regression)
composer verify            # analyse + cs + test + test:oracle

composer test yalnızca PHPUnit çalıştırır. oracle PHPUnit paketi, senaryo çalıştırıcı sınıflarını barındıran ancak test vakası içermeyen tests/Oracle konumunu kullanır; bu nedenle 32 senaryo yalnızca composer test:oracle, composer verify veya ./bin/verify-all aracılığıyla çalıştırılır.

MERQL_MYSQL_HOST, MERQL_MYSQL_DATABASE ve MERQL_MYSQL_USER (isteğe bağlı olarak MERQL_MYSQL_PASSWORD ve MERQL_MYSQL_PORT ile birlikte) bir test veritabanını göstermedikçe MySQL entegrasyon testleri atlanır.

Kod kalitesi

Kabuk
composer cs            # PSR-12 coding standards check
composer cs:fix        # Auto-fix coding standards
composer analyse       # PHPStan level 10 static analysis

Senaryo kategorileri

clean (8 senaryo)

Çakışma içermeyen temiz birleştirmeler. İki taraf da veriyi değiştirebilir, ancak aynı satırın aynı sütununu asla değiştirmez.

Senaryo Testler
insert-only-theirs Theirs satır ekledi, ours değiştirmedi.
update-only-theirs Theirs satırları güncelledi, ours değiştirmedi.
delete-only-theirs Theirs satırları sildi, ours değiştirmedi.
insert-only-ours Ours satır ekledi, theirs değiştirmedi.
mixed-no-overlap İki taraf da farklı tabloları veya satırları değiştirdi.
both-same-change İki taraf da aynı değişiklikleri yaptı (çakışma yok).
column-level-clean İki taraf da aynı satırda farklı sütunları değiştirdi.
multi-table Birden fazla tabloda yapılan değişiklikler.

conflict (6 senaryo)

Çakışma oluşturması gereken senaryolar.

Senaryo Testler
both-update-same-column İki taraf da aynı sütunu farklı değerlere değiştirdi.
update-vs-delete Bir taraf aynı satırı güncelledi, diğeri sildi.
delete-vs-update Güncelleme-silme işleminin tersi.
both-insert-same-pk İki taraf da aynı birincil anahtara sahip satır ekledi.
multiple-conflicts Tek bir birleştirmede birden fazla çakışma.
partial-conflict Bazı sütunlar çakışırken diğerleri sorunsuz birleşir.

identity (4 senaryo)

Satır kimliğinin uç durumları.

Senaryo Testler
auto-increment Yeni satırların dallar arasında farklı kimlikleri vardır.
natural-key Birincil anahtar yerine benzersiz sütunlara göre eşleştirme.
composite-key Çok sütunlu birincil anahtar.
no-key Birincil anahtarı olmayan tablo (içerik özeti yedeği).

types (6 senaryo)

Tüm sütun türlerinde veri türü işleme.

Senaryo Testler
text-columns VARCHAR, TEXT, LONGTEXT değerleri.
numeric-columns INT, DECIMAL, FLOAT değerleri.
date-columns DATE, DATETIME, TIMESTAMP değerleri.
json-columns JSON sütun birleştirmesi.
blob-columns İkili veri.
null-handling NULL'dan değere, değerden NULL'a geçişler.

scale (4 senaryo)

Yük altındaki performans.

Senaryo Testler
1k-rows 1,000 satır.
10k-rows 10,000 satır.
100k-rows 100,000 satır.
wide-table 50+ sütunlu tablo.

edge (4 senaryo)

Uç durumlar ve sınır koşulları.

Senaryo Testler
empty-changeset Bir veya iki tarafta da değişiklik yok.
schema-mismatch Anlık görüntüler arasında sütun ekleme veya kaldırma.
encoding UTF-8, emoji ve özel karakterler.
large-text Çok büyük TEXT/LONGTEXT değerleri.

Senaryo yapısı

Her senaryo, scenario.json yapılandırma dosyasını içeren scenarios/<category>/<name>/ altında bir dizindir:

JSON
{
    "name": "column-level-clean",
    "category": "clean",
    "description": "Both sides modify same row but different columns",
    "tables": ["test_posts"],
    "expectations": {
        "conflicts": 0,
        "operations": 3,
        "changeset_match": "exact",
        "merge_match": "exact",
        "sql_match": "semantic"
    }
}

Çakışma senaryolarında beklenen çakışmalar ayrıntılı olarak belirtilir:

JSON
{
    "expectations": {
        "conflicts": 1,
        "conflict_details": [
            {
                "table": "test_posts",
                "primary_key": {"id": 42},
                "column": "title",
                "ours_value": "Welcome",
                "theirs_value": "Greetings"
            }
        ]
    }
}

ScenarioRunner işlem hattı

ScenarioRunner::run() tek bir senaryoyu düzenler:

  1. OracleCapture::compute(), senaryonun JSON verilerinden üç anlık görüntü oluşturur ve birleştirmeyi çalıştırır.
  2. ScenarioComparator::compare(), birleştirme sonucunu scenario.json içindeki beklenen değerlerle karşılaştırır.
  3. Başarılı/başarısız sonucunu ve hata mesajlarının listesini döndürür.
PHP
use Merql\Tests\Oracle\ScenarioRunner;

$result = ScenarioRunner::run($scenario);
// ['name' => 'column-level-clean', 'pass' => true, 'failures' => []]

ScenarioRunner::runAll() her senaryoyu sırayla çalıştırır:

PHP
$results = ScenarioRunner::runAll($scenarios);

Yeni senaryo ekleme

  1. Bir dizin oluşturun: scenarios/<category>/<name>/.
  2. Senaryo meta verilerini ve beklentileri içeren scenario.json dosyasını oluşturun.
  3. JSON yapılandırmasında üç veritabanı durumunu tanımlayın: base verileri, ours değişiklikleri, theirs değişiklikleri.
  4. Senaryoyu çalıştırın: ./bin/test-scenario <name>.
  5. Paketin tamamını doğrulayın: ./bin/verify-all.

Kod kalitesi standartları

merql şu standartları uygular:

  • PHPStan düzey 10 -- taban istisnaları olmadan sıkı statik analiz.
  • PSR-12 -- kodlama standartları phpcs tarafından denetlenir.
  • Oracle regresyonu -- 32 senaryonun tümü geçmelidir.
  • Birim testleri -- her bileşen için yalıtılmış testler.

verify-all betiği dört kontrolün tümünü sırayla çalıştırır. Kısmi onay kabul edilmez.

Sürekli entegrasyon

CI; kodlama standartlarını, PHPStan, composer test, MySQL 8.4'e karşı mysqli kullanan entegrasyon paketini, birleştirme temel işlemlerinin kapsamını ve composer audit öğesini main deposuna yapılan her gönderimde ve çekme isteğinde çalıştırır. Oracle regresyon külliyatını (#6) çalıştırmaz; bu nedenle bir değişikliğe güvenmeden önce yerel olarak composer test:oracle veya ./bin/verify-all çalıştırın.