Skip to main content

OpenADR 3.0 VEN

Enrols GEM as a Virtual End Node on an OpenADR 3.0 demand-response program. 3.0 replaced the 2.0b XML ceremony with a REST/JSON API secured by OAuth2 client credentials, and it is the profile new utility programs are written against.

The driver owns the connection only. Event interpretation, load curtailment, restore and history are shared with the OpenADR 2.0b driver — see the OpenADR console for everything on that side.

Prerequisites

  • Enrolment with the utility or Energy Services Provider, which supplies:
    • the VTN base URL, including the version path (e.g. https://vtn.example.com/openadr3/3.0.0)
    • an OAuth2 client_id and client_secret
    • the clientName registered for this site, and the program id(s) to follow
  • Some programs additionally require a client certificate. Both mTLS and OAuth2 can be used together.
  • Outbound HTTPS from the controller to the VTN. Webhook push additionally needs the VTN to reach the controller, which most installs cannot offer — polling is the default and needs no inbound path.

Setup steps

  1. System → Devices → Add Device, choose OpenADR 3.0 VEN (key openadr3).
  2. Set base_url, client_id and client_secret.
  3. Set ven_name to the clientName the program registered for this site. An event targeted at a name that does not match is skipped — the Monitor tab shows the targets so they can be compared directly.
  4. Optionally set program_ids to restrict which programs are followed. Empty follows every program the VTN offers.
  5. Configure the response on the console's Response tab: curtailable resources for kW-targeted shedding, and/or level-mapped macros.

Or add it from Integrations → OpenADR, which walks the same steps and then opens the console against the new VEN.

Attribute reference

ScopeAttributeDirectionNotes
devicebase_urlrequired3.0 API root including the version path.
deviceclient_idoptionalOAuth2 client id. Omit only if the VTN authenticates purely with mTLS.
deviceclient_secretoptional, secureOAuth2 client secret.
devicetoken_urloptionalDefaults to <base_url>/auth/token.
deviceoauth_scopeoptionalOnly if the program requires a scope.
deviceven_nameoptionalVEN clientName. Defaults to the device name.
deviceven_idread-onlyAssigned by the VTN on registration.
deviceprogram_idsoptionalComma-separated. Empty follows every program.
devicepoll_intervaloptionalMilliseconds between polls. Default 60000, floored at 5000.
devicepush_enabledoptionalSubscribe to VTN webhook push. Polling continues either way.
devicepush_callback_urloptionalExternally reachable URL for push delivery.
deviceclient_cert / client_keyoptional, securePEM material for VTNs requiring mTLS.
deviceca_certoptionalPEM CA chain used to verify the VTN.
deviceallow_insecureoptionalDisables TLS verification. Lab VTNs only.
deviceresponse_modeoptionalauto (default), resources, macro, both.
deviceprice_thresholdsoptionalMaps a PRICE payload onto shed levels.
devicerestore_spread_msoptionalWindow over which curtailed load is returned. Default 120000.
devicetelemetry_enabledoptionalMeasure and report readings to the VTN. Off by default.
devicetelemetry_sample_msoptionalHow often readings are taken. Default 30000, floored at 5000.
devicereport_interval_msoptionalSubmit telemetry on this cadence even with no event running. Empty reports only when an event asks.
devicereport_granularity_msoptionalInterval length for standing reports. Default 900000.
deviceshed_macro_id, restore_macro_id, event_level_1..3_macro_idoptionalLevel-mapped macros.
deviceevent_statusread-onlyidle or active.
devicelast_event_id, last_signal_levelread-onlyMost recent event and the level in force.
devicedr_directiveread-onlyNormalized reading of what the site is being asked to do.
deviceopted_outread-onlyTracking events but not acting on them.
devicedr_active_eventsread-onlyPersisted event and curtailment state. Managed by the driver.
zonedr_event_activeread-only1 while an event is active.
zonedr_signal_levelread-onlyLevel in force.
zonedr_event_idread-onlyCurrent event id.

Zones do not need an address — assigning one to the VEN simply gives it the DR attributes above.

Commands

CommandDescription
registerCreate or refresh this VEN's record on the VTN.
pollFetch events now.
opt_in / opt_outResume or suspend automatic load control.
get_programsPrograms the VTN offers.
get_eventsEvents currently tracked.
get_statusConnection, registration and event state.
get_response_statusCurtailable capacity and the current shed plan.
get_traceRecent protocol exchanges.
subscribe_pushCreate a webhook subscription for event push.
get_telemetryStreams, report obligations and latest readings.
send_reportsSend any due telemetry reports now.

Telemetry (reports)

With telemetry_enabled on, the driver registers its measurable resources under /vens/{id}/resources (so a program can target one piece of equipment) and POSTs REPORT objects to /reports.

Values are converted to 3.0's settlement units — watts become KW, watt-hours become KWH. Site-level readings report under the reserved AGGREGATED_REPORT resource name; a metered curtailable resource reports under its own name.

A failed POST is retried rather than skipped past, so a transient VTN outage does not leave a settlement gap.

Payload types

The driver classifies the 3.0 event payload vocabulary and acts only on what it recognizes:

Payload typeRead as
SIMPLE, LEVELshed level
PRICE, EXPORT_PRICE, IMPORT_PRICEprice — drives load only with price_thresholds configured
LOAD_CONTROLpercentage reduction
LOAD_DISPATCH, DISPATCH_SETPOINT, IMPORT_CAPACITY_LIMIT, IMPORT_CAPACITY_SUBSCRIPTION, IMPORT_CAPACITY_RESERVATION, EXPORT_CAPACITY_LIMIT, EXPORT_CAPACITY_SUBSCRIPTIONkW target
CONTROL_SETPOINT, CHARGE_STATE_SETPOINTsetpoint
ALERT_GRID_EMERGENCY, ALERT_BLACK_START, ALERT_POSSIBLE_OUTAGEshed level
anything elserecorded and displayed, never acted on

Known quirks

  • Event versioning uses modificationDateTime, since 3.0 has no modification number. A VTN that does not update that field when an event is edited will not have its edits applied.
  • Event targeting is strict. An event with no targets is program-wide and applies. An event carrying only target types GEM does not recognize is treated as not ours — shedding on another VEN's event is worse than missing one, and a skipped event is visible in the console while a wrong shed is a comfort complaint.
  • Webhook push is best-effort. When a subscription cannot be created the driver logs it and stays on polling rather than failing the connection.
  • Events far outside the window are dropped before decoding — more than 7 days ahead or 6 hours behind. A VTN carrying a season of history is not re-decoded on every poll.
  • Reporting obligations come from events. 3.0 has no METADATA negotiation: an event's reportDescriptors create the obligation, so it can change with every event received. For data between events, set report_interval_ms.
  • Only report payload types GEM can actually produce are answeredUSAGE, DEMAND, READING, BASELINE, OPERATING_STATE. A descriptor asking for anything else is skipped rather than answered with a wrong quantity.

Troubleshooting

SymptomCheck
Token request fails with HTTP 401client_id / client_secret are wrong, or the VTN expects a scope — set oauth_scope to whatever the program documents.
Connected but no events ever arriveConfirm program_ids matches a real program id. The Monitor tab shows the raw /events response; an empty array with HTTP 200 means the VTN has nothing scheduled for this VEN.
Events listed but nothing happensOpen the event in the console — the audit trail records the reason. Common causes are a PRICE-only event with no price_thresholds, a level-0 event, the VEN being opted out, or every resource sitting below its min_level.
Shed falls short of the requested kWThe Response tab shows available capacity against the target, and the shortfall is written to the event audit trail. Add resources or correct their nominal_kw.
Telemetry enabled but nothing is sentNo event has asked for a report and no standing interval is set. Set report_interval_ms for a continuous feed; the Telemetry tab shows every active obligation.
Reports rejected by the VTNThe Monitor tab holds the exact POST body and the rejection. Check that the programID matches and that the resources were registered.
Duplicate VEN records on the VTNThe driver looks for its own clientName before creating one. If duplicates already exist from an earlier tool, remove them at the VTN — a duplicate silently stops receiving targeted events.