Files
Enelix-EMS/tests/LadestationAdapterTest.php
T
2026-10-06 11:33:59 +00:00

211 lines
6.5 KiB
PHP

<?php
declare(strict_types=1);
namespace Belevo\EnelixEMS\Tests;
use Belevo\EnelixEMS\LadestationAdapter;
use Belevo\EnelixEMS\LadestationTransport;
use PHPUnit\Framework\TestCase;
final class LadestationAdapterTest extends TestCase
{
/**
* @dataProvider statusFaelle
* @param array<string, string> $konfiguration
* @param array{Rohstatus: int, Istleistung_W: float, Sollstrom_A?: int, Maximalstrom_A?: int, Iststrom_A?: float, Phasenzahl?: int} $erwartet
*/
public function testStatusaufrufUndDekodierungFuerAlleGeraete(
int $geraetetyp,
array $konfiguration,
string $antwort,
string $erwarteteUrl,
array $erwartet
): void {
$aufrufe = [];
$transport = new LadestationTransport(static function (array $anfrage) use (
&$aufrufe,
$antwort
): string {
$aufrufe[] = $anfrage;
return $antwort;
});
$rohstatus = LadestationAdapter::dekodiereStatus(
$geraetetyp,
$transport->statusLesen($geraetetyp, $konfiguration)
);
self::assertSame($erwarteteUrl, $aufrufe[0]['URL']);
self::assertSame('GET', $aufrufe[0]['Methode']);
self::assertSame($erwartet, $rohstatus);
}
/** @return iterable<string, array<mixed>> */
public function statusFaelle(): iterable
{
yield 'go-e alt' => [
LadestationAdapter::GO_E_ALT,
$this->lokaleKonfiguration(),
$this->goEAntwort(2, 1100, [160, 158, 159]),
'http://192.0.2.10/mqtt?payload=',
[
'Rohstatus' => 2,
'Istleistung_W' => 11000.0,
'Sollstrom_A' => 16,
'Maximalstrom_A' => 16,
'Iststrom_A' => 16.0,
'Phasenzahl' => 3,
],
];
yield 'go-e Gemini' => [
LadestationAdapter::GO_E_GEMINI,
$this->lokaleKonfiguration(),
$this->goEAntwort(2, 2300, [9.8, 0, 0]),
'http://192.0.2.10/api/status',
[
'Rohstatus' => 2,
'Istleistung_W' => 2300.0,
'Sollstrom_A' => 16,
'Maximalstrom_A' => 16,
'Iststrom_A' => 9.8,
'Phasenzahl' => 1,
],
];
yield 'Smart-me Pico' => [
LadestationAdapter::SMART_ME_PICO,
$this->picoKonfiguration(),
json_encode([
'State' => 2,
'ActiveChargingPower' => 11.0,
'MaxAllowedChargingCurrent' => 16,
], JSON_THROW_ON_ERROR),
'https://api.smart-me.com/pico/charging/pico-id',
['Rohstatus' => 2, 'Istleistung_W' => 11000.0],
];
}
public function testGoEAusFreigabeWirdAlsNullSollstromDekodiert(): void
{
$daten = json_decode($this->goEAntwort(2, 0, [0, 0, 0]), true, 512, JSON_THROW_ON_ERROR);
$daten['alw'] = false;
$daten['frc'] = 1;
$status = LadestationAdapter::dekodiereStatus(
LadestationAdapter::GO_E_GEMINI,
json_encode($daten, JSON_THROW_ON_ERROR)
);
self::assertSame(0, $status['Sollstrom_A']);
}
/**
* @dataProvider steuerFaelle
* @param array<string, string> $konfiguration
* @param list<array{Methode: string, URL: string}> $erwarteteAufrufe
*/
public function testSteueraufrufeWerdenUeberFakeTransportGeprueft(
int $geraetetyp,
array $konfiguration,
int $strom,
array $erwarteteAufrufe
): void {
$aufrufe = [];
$transport = new LadestationTransport(static function (array $anfrage) use (&$aufrufe): string {
unset($anfrage['Benutzername'], $anfrage['Passwort']);
$aufrufe[] = $anfrage;
return '{}';
});
$transport->ladestromSetzen($geraetetyp, $konfiguration, $strom);
self::assertSame($erwarteteAufrufe, $aufrufe);
}
/** @return iterable<string, array<mixed>> */
public function steuerFaelle(): iterable
{
yield 'go-e alt laden' => [
LadestationAdapter::GO_E_ALT,
$this->lokaleKonfiguration(),
16,
[
['Methode' => 'GET', 'URL' => 'http://192.0.2.10/mqtt?payload=alw=1'],
['Methode' => 'GET', 'URL' => 'http://192.0.2.10/mqtt?payload=amp=16'],
],
];
yield 'go-e Gemini stoppen' => [
LadestationAdapter::GO_E_GEMINI,
$this->lokaleKonfiguration(),
0,
[[
'Methode' => 'GET',
'URL' => 'http://192.0.2.10/api/set?frc=1&sua=false',
]],
];
yield 'Smart-me Pico laden' => [
LadestationAdapter::SMART_ME_PICO,
$this->picoKonfiguration(),
16,
[[
'Methode' => 'POST',
'URL' => 'https://api.smart-me.com/pico/loadmanagementgroup/current/serial-1?current=16000',
]],
];
}
public function testPicoAnfragenVerwendenBasicAuth(): void
{
$anfrage = LadestationAdapter::statusAnfrage(
LadestationAdapter::SMART_ME_PICO,
$this->picoKonfiguration()
);
self::assertSame('api-user', $anfrage['Benutzername']);
self::assertSame(hash('sha256', __FILE__), $anfrage['Passwort']);
}
/** @return array<string, string> */
private function lokaleKonfiguration(): array
{
return [
'Geraeteadresse' => '192.0.2.10',
'GeraeteID' => '',
'Seriennummer' => '',
'Benutzername' => '',
'Passwort' => '',
];
}
/** @return array<string, string> */
private function picoKonfiguration(): array
{
return [
'Geraeteadresse' => '',
'GeraeteID' => 'pico-id',
'Seriennummer' => 'serial-1',
'Benutzername' => 'api-user',
'Passwort' => hash('sha256', __FILE__),
];
}
/** @param list<int|float> $stroeme */
private function goEAntwort(int $status, float $leistung, array $stroeme): string
{
$nrg = array_fill(0, 12, 0);
foreach (array_values($stroeme) as $index => $strom) {
$nrg[4 + $index] = $strom;
}
$nrg[11] = $leistung;
return json_encode([
'car' => $status,
'nrg' => $nrg,
'amp' => 16,
'ama' => 16,
'alw' => true,
'frc' => 2,
], JSON_THROW_ON_ERROR);
}
}