100 lines
3.4 KiB
PHP
100 lines
3.4 KiB
PHP
<?php
|
|
|
|
declare(strict_types=1);
|
|
|
|
namespace Tests\Support\Imitation;
|
|
|
|
use App\Services\DaData\DaDataException;
|
|
use App\Services\DaData\DaDataPhoneClient;
|
|
use App\Services\DaData\DaDataPhoneResponse;
|
|
|
|
/**
|
|
* Детерминированный фейк DaData-клиента для тестов имитации (Phase 1).
|
|
*
|
|
* Позволяет прогонять каскад LeadRegionResolver без внешних HTTP-вызовов:
|
|
* заранее регистрируем ответы по номеру телефона через stub(), затем
|
|
* биндим этот фейк в контейнер вместо реального DaDataPhoneClient.
|
|
*
|
|
* Использование:
|
|
* $fake = new FakeDaDataPhoneClient();
|
|
* $fake->stub('79990000077', qc: 0, region: 'Москва', provider: 'МТС');
|
|
* app()->instance(DaDataPhoneClient::class, $fake);
|
|
*
|
|
* Task 1 — Phase 1 Portal Client Imitation Harness.
|
|
* Spec: docs/superpowers/specs/2026-06-03-portal-client-imitation-phase1-design.md
|
|
*/
|
|
class FakeDaDataPhoneClient extends DaDataPhoneClient
|
|
{
|
|
/**
|
|
* @var array<string, DaDataPhoneResponse|null> phone => response (null = throw DaDataException)
|
|
*/
|
|
private array $stubs = [];
|
|
|
|
/**
|
|
* Переопределяем конструктор без вызова parent, чтобы не требовать HttpFactory в тестах.
|
|
*/
|
|
public function __construct() {}
|
|
|
|
/**
|
|
* Зарегистрировать детерминированный ответ для номера телефона.
|
|
*
|
|
* @param int $qc Код качества DaData (0=хорошо, 1=не уточнён, 2=мусор, 3=изменён, 7=иностранец)
|
|
*/
|
|
public function stub(
|
|
string $phone,
|
|
int $qc,
|
|
?string $region = null,
|
|
?string $provider = null,
|
|
): self {
|
|
$this->stubs[$phone] = new DaDataPhoneResponse(
|
|
qc: $qc,
|
|
qcConflict: null,
|
|
type: null,
|
|
phone: $phone,
|
|
provider: $provider,
|
|
region: $region,
|
|
city: null,
|
|
timezone: null,
|
|
raw: [
|
|
'qc' => $qc,
|
|
'provider' => $provider,
|
|
'region' => $region,
|
|
'phone' => $phone,
|
|
],
|
|
);
|
|
|
|
return $this;
|
|
}
|
|
|
|
/**
|
|
* Зарегистрировать выброс DaDataException для номера телефона.
|
|
* Используется для тестирования ветки деградации (Россвязь-fallback).
|
|
*/
|
|
public function stubThrows(string $phone): self
|
|
{
|
|
$this->stubs[$phone] = null; // null = throw
|
|
|
|
return $this;
|
|
}
|
|
|
|
/**
|
|
* Возвращает заранее зарегистрированный ответ или бросает DaDataException.
|
|
*
|
|
* @throws DaDataException Если стаб не зарегистрирован или зарегистрирован как throw.
|
|
*/
|
|
public function cleanPhone(string $phone): DaDataPhoneResponse
|
|
{
|
|
if (! array_key_exists($phone, $this->stubs)) {
|
|
throw new DaDataException("FakeDaDataPhoneClient: no stub registered for phone {$phone}");
|
|
}
|
|
|
|
$response = $this->stubs[$phone];
|
|
|
|
if ($response === null) {
|
|
throw new DaDataException("FakeDaDataPhoneClient: stubbed to throw for phone {$phone}");
|
|
}
|
|
|
|
return $response;
|
|
}
|
|
}
|