Shelly Modul generisch erweitern
Tests / test (push) Successful in 46s

This commit is contained in:
dh
2026-09-17 10:19:56 +00:00
parent 4cbec75d56
commit 1baa63f23e
7 changed files with 1006 additions and 309 deletions
+117
View File
@@ -0,0 +1,117 @@
<?php
declare(strict_types=1);
namespace Belevo\EnelixUtils\Tests;
use PHPUnit\Framework\TestCase;
require_once __DIR__ . '/../ShellyModul/libs/ShellyParser.php';
final class ShellyParserTest extends TestCase
{
public function testCustomAndNestedTopicPrefixesAreRecognized(): void
{
self::assertSame(
['deviceTopic' => 'symcon', 'kind' => 'rpc', 'component' => null],
\ShellyParser::parseTopic('symcon/events/rpc')
);
self::assertSame(
['deviceTopic' => 'building/floor/device-1', 'kind' => 'component_status', 'component' => 'pm1:0'],
\ShellyParser::parseTopic('building/floor/device-1/status/pm1:0')
);
}
public function testNotifyStatusIsFlattenedWithoutKnowingTheDeviceModel(): void
{
$points = \ShellyParser::pointsFromRpc([
'src' => 'custom-source',
'method' => 'NotifyStatus',
'params' => [
'switch:0' => [
'output' => true,
'apower' => 12.4,
'aenergy' => ['total' => 42.5, 'by_minute' => [1, 2, 3]],
],
'humidity:0' => ['rh' => 56.2],
],
]);
self::assertContains(['component' => 'switch:0', 'path' => 'output', 'value' => true], $points);
self::assertContains(['component' => 'switch:0', 'path' => 'apower', 'value' => 12.4], $points);
self::assertContains(['component' => 'switch:0', 'path' => 'aenergy.total', 'value' => 42.5], $points);
self::assertContains(['component' => 'switch:0', 'path' => 'aenergy.by_minute', 'value' => '[1,2,3]'], $points);
self::assertContains(['component' => 'humidity:0', 'path' => 'rh', 'value' => 56.2], $points);
}
public function testGroupsSeparateOutputsMetersAndSensors(): void
{
self::assertSame('switches', \ShellyParser::groupForPoint('switch:0', 'output'));
self::assertSame('power', \ShellyParser::groupForPoint('switch:0', 'apower'));
self::assertSame('energy', \ShellyParser::groupForPoint('emdata:0', 'a_total_act_energy'));
self::assertSame('humidity', \ShellyParser::groupForPoint('humidity:0', 'rh'));
self::assertSame('covers', \ShellyParser::groupForPoint('cover:0', 'current_pos'));
self::assertSame('other', \ShellyParser::groupForPoint('future:7', 'new_value'));
}
public function testNotifyEventsAreMappedToTheirComponent(): void
{
$points = \ShellyParser::pointsFromRpc([
'method' => 'NotifyEvent',
'params' => [
'events' => [[
'component' => 'input:0',
'event' => 'single_push',
'ts' => 123.5,
]],
],
]);
self::assertContains(
['component' => 'input:0', 'path' => 'event.event', 'value' => 'single_push'],
$points
);
}
public function testNumericMeasurementsUseFloatVariables(): void
{
self::assertSame(2, \ShellyParser::variableType(0, 'apower'));
self::assertSame(1, \ShellyParser::variableType(123, 'uptime'));
self::assertSame(1, \ShellyParser::variableType(123.5, 'ts'));
self::assertSame(0, \ShellyParser::variableType(true, 'output'));
self::assertSame(3, \ShellyParser::variableType('open', 'state'));
}
public function testConfigurationOffersAllDataPointGroups(): void
{
$json = file_get_contents(__DIR__ . '/../ShellyModul/form.json');
self::assertNotFalse($json);
$form = json_decode($json, true, 512, JSON_THROW_ON_ERROR);
$encoded = json_encode($form, JSON_THROW_ON_ERROR);
foreach ([
'CreateOnline',
'CreateDeviceInfo',
'CreateInputs',
'CreateSwitches',
'CreateCovers',
'CreateLights',
'CreatePower',
'CreateVoltage',
'CreateCurrent',
'CreateEnergy',
'CreateFrequency',
'CreatePowerFactor',
'CreateMeterDetails',
'CreateTemperature',
'CreateHumidity',
'CreateIlluminance',
'CreateBattery',
'CreateEnvironment',
'CreateSystem',
'CreateOther',
] as $property) {
self::assertStringContainsString($property, $encoded);
}
}
}