Étape 1 complete: V2C Trydan nymea plugin (Modbus TCP, status Partial).
Plugin (IntegrationPluginV2c):
- discoverThings: delegates to V2cTcpDiscovery, maps results to
ThingDescriptors; createMethod "user" bypasses discovery.
- setupThing: registers a NetworkDeviceMonitor (IP tracking on DHCP
renewal), creates TrydanModbusTcpMaster, wires reachableChanged →
initialize() → state update on initializationFinished(), then starts
periodic polls on a 30s PluginTimer.
- updateThingStates: ChargeState 0/1/2 → pluggedIn/charging;
power = (PauseState==0 AND Lock==0) per evcc trydan.go Enabled().
- handleDynamicConflict: if Dynamic==1 (V2C internal PV optimizer),
write PauseDynamic=1 to suppress it. NEVER write Dynamic=0 (silences
ChargePower telemetry). Writes only on state transition to minimize
flash wear. cf. github.com/evcc-io/evcc/issues/28047.
- Action "power": writes PauseState then Lock (always in mirror), then
fire-and-forgets PauseDynamic if Dynamic==1. Action handlers filter
writeCompleted by register address to avoid reacting to concurrent
background writes.
- Action "maxChargingCurrent": clamps to [minIntensity, maxIntensity],
writes Intensity. Below 6A → pause instead of invalid setpoint.
JSON (integrationpluginv2c.json):
- ThingClass "trydan" implementing evcharger + connectable + networkdevice.
- settingsTypes: suspendInternalOptimizer (bool, default true) — allows
the user to disable Dynamic conflict management if they want the V2C
PID to remain active alongside the HEMS.
- State "chargeEnergy" exposed as diagnostic only (NOT sessionEnergy) —
firmware reliability on this register is unvalidated; cf. evcc #28047.
Build (v2c.pro):
- MODBUS_CONNECTIONS intentionally empty: the modbus-tool code generator
assumes non-overlapping block reads; leaving it empty skips generation
while still linking nymea-modbus via the PKGCONFIG in modbus.pri.
VendorId 56c3e7bb… is new (no existing V2C vendor in the repo).
PluginId f0692725… is new (generated for this plugin).
PORTING_STATUS_modbus.md documents register sources, the 4 items that
require validation on real hardware, and the "no beta matrix" constraint.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
188 lines
8.2 KiB
JSON
188 lines
8.2 KiB
JSON
{
|
|
"name": "V2C",
|
|
"displayName": "V2C Trydan",
|
|
"id": "f0692725-650a-47c3-a673-172f077768f1",
|
|
"paramTypes": [],
|
|
"vendors": [
|
|
{
|
|
"id": "56c3e7bb-2db8-4002-b799-9e21530e6fb9",
|
|
"name": "v2c",
|
|
"displayName": "V2C",
|
|
"thingClasses": [
|
|
{
|
|
"id": "b2a12873-4d11-444e-a4ad-914907491eb4",
|
|
"name": "trydan",
|
|
"displayName": "Trydan",
|
|
"interfaces": [
|
|
"evcharger",
|
|
"connectable",
|
|
"networkdevice"
|
|
],
|
|
"createMethods": [
|
|
"discovery",
|
|
"user"
|
|
],
|
|
"discoveryType": "weak",
|
|
"paramTypes": [
|
|
{
|
|
"id": "2fe17a54-b24b-4868-ae99-36a4627e6827",
|
|
"name": "macAddress",
|
|
"displayName": "MAC address",
|
|
"type": "QString",
|
|
"inputType": "MacAddress",
|
|
"defaultValue": "",
|
|
"readOnly": true
|
|
},
|
|
{
|
|
"id": "c0cdfa64-7054-4486-809e-3b7f257a3aab",
|
|
"name": "address",
|
|
"displayName": "Host address",
|
|
"type": "QString",
|
|
"inputType": "IPv4Address",
|
|
"defaultValue": ""
|
|
},
|
|
{
|
|
"id": "bd9987a4-4c45-49c8-ab67-8c80705ec109",
|
|
"name": "hostName",
|
|
"displayName": "Host name",
|
|
"type": "QString",
|
|
"inputType": "TextLine",
|
|
"defaultValue": ""
|
|
},
|
|
{
|
|
"id": "d096bfe1-5861-456f-915c-f1f2c65b03b3",
|
|
"name": "port",
|
|
"displayName": "Modbus TCP port",
|
|
"type": "uint",
|
|
"defaultValue": 502
|
|
}
|
|
],
|
|
"settingsTypes": [
|
|
{
|
|
"id": "a47f20bd-dfdc-4827-ab7d-05d7819f316e",
|
|
"name": "suspendInternalOptimizer",
|
|
"displayName": "Suspend internal V2C optimizer when HEMS takes control",
|
|
"type": "bool",
|
|
"defaultValue": true
|
|
}
|
|
],
|
|
"stateTypes": [
|
|
{
|
|
"id": "47054399-82fb-4e12-9bb6-9ae3e4fd4f78",
|
|
"name": "connected",
|
|
"displayName": "Connected",
|
|
"type": "bool",
|
|
"defaultValue": false,
|
|
"cached": false
|
|
},
|
|
{
|
|
"id": "f38c313c-47cc-4791-8a8f-64c1af852af6",
|
|
"name": "pluggedIn",
|
|
"displayName": "Plugged in",
|
|
"type": "bool",
|
|
"defaultValue": false,
|
|
"cached": false
|
|
},
|
|
{
|
|
"id": "6d003e09-d30d-4a1c-9e2d-9e838b61dc5d",
|
|
"name": "charging",
|
|
"displayName": "Charging",
|
|
"type": "bool",
|
|
"defaultValue": false,
|
|
"cached": false
|
|
},
|
|
{
|
|
"id": "eb3253a2-7518-4e76-9c06-1bb133d5037d",
|
|
"name": "power",
|
|
"displayName": "Charging enabled",
|
|
"displayNameAction": "Set charging enabled",
|
|
"type": "bool",
|
|
"defaultValue": true,
|
|
"writable": true
|
|
},
|
|
{
|
|
"id": "deb8826d-4f91-42b8-89cf-16feb6425e0e",
|
|
"name": "maxChargingCurrent",
|
|
"displayName": "Maximum charging current",
|
|
"displayNameAction": "Set maximum charging current",
|
|
"type": "double",
|
|
"unit": "Ampere",
|
|
"minValue": 6,
|
|
"maxValue": 32,
|
|
"stepSize": 1,
|
|
"defaultValue": 16,
|
|
"writable": true
|
|
},
|
|
{
|
|
"id": "2570c0d7-f9a5-4e24-9242-6d79253004ec",
|
|
"name": "currentPower",
|
|
"displayName": "Charging power",
|
|
"type": "double",
|
|
"unit": "Watt",
|
|
"defaultValue": 0,
|
|
"cached": false
|
|
},
|
|
{
|
|
"id": "d11a392f-387d-4f10-9050-e25198d2c584",
|
|
"name": "housePower",
|
|
"displayName": "House power (CT clamp)",
|
|
"type": "double",
|
|
"unit": "Watt",
|
|
"defaultValue": 0,
|
|
"cached": false
|
|
},
|
|
{
|
|
"id": "37e706fb-fa3c-484a-b776-b50aa5de5c61",
|
|
"name": "solarPower",
|
|
"displayName": "Solar power (PV seen by charger)",
|
|
"type": "double",
|
|
"unit": "Watt",
|
|
"defaultValue": 0,
|
|
"cached": false
|
|
},
|
|
{
|
|
"id": "9a9e6afb-a641-409f-9705-c16776db3a29",
|
|
"name": "slaveError",
|
|
"displayName": "Charger error code",
|
|
"type": "uint",
|
|
"defaultValue": 0
|
|
},
|
|
{
|
|
"id": "fe616e45-39cb-4be3-8426-9d27c7a64f06",
|
|
"name": "chargeEnergy",
|
|
"displayName": "Session energy (diagnostic)",
|
|
"type": "double",
|
|
"unit": "KiloWattHour",
|
|
"defaultValue": 0
|
|
},
|
|
{
|
|
"id": "71773194-ebd3-4ded-893c-14bfef9b1854",
|
|
"name": "intensity",
|
|
"displayName": "Current charging current",
|
|
"type": "double",
|
|
"unit": "Ampere",
|
|
"defaultValue": 0,
|
|
"cached": false
|
|
},
|
|
{
|
|
"id": "3c86495b-74da-440e-98a5-825678e35c1a",
|
|
"name": "conflictDetected",
|
|
"displayName": "Internal V2C optimizer active",
|
|
"type": "bool",
|
|
"defaultValue": false
|
|
},
|
|
{
|
|
"id": "006dd018-9c6a-4a4e-a7b2-eb965d27ca92",
|
|
"name": "optimizerSuspended",
|
|
"displayName": "Internal optimizer suspended by HEMS",
|
|
"type": "bool",
|
|
"defaultValue": false
|
|
}
|
|
],
|
|
"actionTypes": []
|
|
}
|
|
]
|
|
}
|
|
]
|
|
}
|