[ecowatt] Add support for API version 5 (#15953)

A new thing parameter to define the API version has been added.
Its default value is 4 for backward compatibility even if this version
is now deprecated. The documentation explains what to do to switch from
a version to another.

Signed-off-by: Laurent Garnier <lg.hc@free.fr>
This commit is contained in:
lolodomo 2023-11-26 23:34:45 +01:00 committed by GitHub
parent a4da986330
commit 9b55bfba58
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 62 additions and 21 deletions

View File

@ -17,11 +17,16 @@ You have to add the thing manually.
You must create an account and an application on the RTE portal to obtain the OAuth2 credentials required to access the API. You must create an account and an application on the RTE portal to obtain the OAuth2 credentials required to access the API.
1. Open this [page](https://data.rte-france.com/catalog/-/api/consumption/Ecowatt/v4.0), find the "Ecowatt" tile and click on the "Abonnez-vous à l'API" button. 1. Open this [page](https://data.rte-france.com/catalog/-/api/consumption/Ecowatt/v5.0), find the "Ecowatt" tile and click on the "Abonnez-vous à l'API" button.
1. Create an account by following the instructions (you will receive an email to validate your new account). 1. Create an account by following the instructions (you will receive an email to validate your new account).
1. Once logged in, create an application by entering a name (for example "openHAB Integration"), choosing "Web Server" as type, entering any description of your choice and finally clicking on the "Valider" button. 1. Once logged in, create an application by entering a name (for example "openHAB Integration"), choosing "Web Server" as type, entering any description of your choice and finally clicking on the "Valider" button.
1. You will then see your application details, in particular the "ID client" and "ID Secret" information which you will need later to set up your binding thing. 1. You will then see your application details, in particular the "ID client" and "ID Secret" information which you will need later to set up your binding thing.
Note that you are subscribed to a particular version of the API.
When a new version of the API is released, you will have to subscribe to this new version and create a new application.
You will then get new information "ID client" and "ID Secret" and you will have to update your thing configuration in openHAB.
After changing version, you will have to wait for your authentication token to be renewed (max 2 hours) to get a successful response from the API.
## Binding Configuration ## Binding Configuration
There are no overall binding configuration settings that need to be set. There are no overall binding configuration settings that need to be set.
@ -29,10 +34,13 @@ All settings are through thing configuration parameters.
## Thing Configuration ## Thing Configuration
| Name | Type | Description | Required | | Name | Type | Description | Required | Default |
|-----------|---------|-----------------------------------------------------------------------|----------| |------------|---------|---------------------------------------------------------------------------|----------|---------|
| idClient | text | ID client provided with the application you created in the RTE portal | yes | | apiVersion | integer | The version of the Ecowatt tile to which you subscribed in the RTE portal | no | 4 |
| idSecret | text | ID secret provided with the application you created in the RTE portal | yes | | idClient | text | ID client provided with the application you created in the RTE portal | yes | |
| idSecret | text | ID secret provided with the application you created in the RTE portal | yes | |
Take care to select the API version corresponding to the one to which you subscribed in the RTE portal.
## Channels ## Channels
@ -42,14 +50,14 @@ All channels are read-only.
|-------------------|--------|------------------------------------------------------------------| |-------------------|--------|------------------------------------------------------------------|
| todaySignal | Number | The signal relating to the forecast consumption level for today. Values are 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red). | | todaySignal | Number | The signal relating to the forecast consumption level for today. Values are 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red). |
| tomorrowSignal | Number | The signal relating to the forecast consumption level for tomorrow. Values are 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red). | | tomorrowSignal | Number | The signal relating to the forecast consumption level for tomorrow. Values are 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red). |
| currentHourSignal | Number | The signal relating to the forecast consumption level for the current hour. Values are 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red). | | currentHourSignal | Number | The signal relating to the forecast consumption level for the current hour. Values are 0 for normal consumption (green) and carbon-free production, 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red). |
## Full Example ## Full Example
example.things: example.things:
```java ```java
Thing ecowatt:signals:signals "Ecowatt Signals" [ idClient="xxxxx", idSecret="yyyyy"] Thing ecowatt:signals:signals "Ecowatt Signals" [ apiVersion=4, idClient="xxxxx", idSecret="yyyyy"]
``` ```
example.items: example.items:

View File

@ -18,10 +18,12 @@ import org.eclipse.jdt.annotation.NonNullByDefault;
* The {@link EcowattConfiguration} class contains fields mapping thing configuration parameters. * The {@link EcowattConfiguration} class contains fields mapping thing configuration parameters.
* *
* @author Laurent Garnier - Initial contribution * @author Laurent Garnier - Initial contribution
* @author Laurent Garnier - New parameter apiVersion
*/ */
@NonNullByDefault @NonNullByDefault
public class EcowattConfiguration { public class EcowattConfiguration {
public int apiVersion = 4;
public String idClient = ""; public String idClient = "";
public String idSecret = ""; public String idSecret = "";
} }

View File

@ -54,6 +54,7 @@ import org.slf4j.LoggerFactory;
* The {@link EcowattHandler} is responsible for updating the state of the channels * The {@link EcowattHandler} is responsible for updating the state of the channels
* *
* @author Laurent Garnier - Initial contribution * @author Laurent Garnier - Initial contribution
* @author Laurent Garnier - Add support for API version 5
*/ */
@NonNullByDefault @NonNullByDefault
public class EcowattHandler extends BaseThingHandler { public class EcowattHandler extends BaseThingHandler {
@ -100,7 +101,8 @@ public class EcowattHandler extends BaseThingHandler {
updateStatus(ThingStatus.OFFLINE, ThingStatusDetail.CONFIGURATION_ERROR, updateStatus(ThingStatus.OFFLINE, ThingStatusDetail.CONFIGURATION_ERROR,
"@text/offline.config-error-unset-parameters"); "@text/offline.config-error-unset-parameters");
} else { } else {
api = new EcowattRestApi(oAuthFactory, httpClient, thing.getUID().getAsString(), idClient, idSecret); api = new EcowattRestApi(oAuthFactory, httpClient, thing.getUID().getAsString(), idClient, idSecret,
config.apiVersion);
updateStatus(ThingStatus.UNKNOWN); updateStatus(ThingStatus.UNKNOWN);
scheduleNextUpdate(0, true); scheduleNextUpdate(0, true);
} }
@ -264,7 +266,7 @@ public class EcowattHandler extends BaseThingHandler {
int hour = dateTime.withZoneSameInstant(day.getZone()).getHour(); int hour = dateTime.withZoneSameInstant(day.getZone()).getHour();
int value = signals.getHourSignal(hour); int value = signals.getHourSignal(hour);
LoggerFactory.getLogger(EcowattHandler.class).debug("hour {} value {}", hour, value); LoggerFactory.getLogger(EcowattHandler.class).debug("hour {} value {}", hour, value);
if (value >= 1 && value <= 3) { if (value >= 0 && value <= 3) {
return new DecimalType(value); return new DecimalType(value);
} }
} }

View File

@ -58,6 +58,6 @@ public class EcowattDaySignals {
} }
} }
} }
return 0; return -1;
} }
} }

View File

@ -46,23 +46,25 @@ import com.google.gson.JsonSyntaxException;
* The {@link EcowattRestApi} is responsible for handling all communication with the Ecowatt REST API * The {@link EcowattRestApi} is responsible for handling all communication with the Ecowatt REST API
* *
* @author Laurent Garnier - Initial contribution * @author Laurent Garnier - Initial contribution
* @author Laurent Garnier - Add support for different API versions
*/ */
@NonNullByDefault @NonNullByDefault
public class EcowattRestApi { public class EcowattRestApi {
private static final String ECOWATT_API_TOKEN_URL = "https://digital.iservices.rte-france.com/token/oauth/"; private static final String ECOWATT_API_TOKEN_URL = "https://digital.iservices.rte-france.com/token/oauth/";
private static final String ECOWATT_API_GET_SIGNALS_URL = "https://digital.iservices.rte-france.com/open_api/ecowatt/v4/signals"; private static final String ECOWATT_API_GET_SIGNALS_URL = "https://digital.iservices.rte-france.com/open_api/ecowatt/v%d/signals";
private final Logger logger = LoggerFactory.getLogger(EcowattRestApi.class); private final Logger logger = LoggerFactory.getLogger(EcowattRestApi.class);
private final OAuthFactory oAuthFactory; private final OAuthFactory oAuthFactory;
private final HttpClient httpClient; private final HttpClient httpClient;
private final Gson gson; private final Gson gson;
private final String apiUrl;
private OAuthClientService authService; private OAuthClientService authService;
private String authServiceHandle; private String authServiceHandle;
public EcowattRestApi(OAuthFactory oAuthFactory, HttpClient httpClient, String authServiceHandle, String idClient, public EcowattRestApi(OAuthFactory oAuthFactory, HttpClient httpClient, String authServiceHandle, String idClient,
String idSecret) { String idSecret, int apiVersion) {
this.oAuthFactory = oAuthFactory; this.oAuthFactory = oAuthFactory;
this.httpClient = httpClient; this.httpClient = httpClient;
GsonBuilder gsonBuilder = new GsonBuilder(); GsonBuilder gsonBuilder = new GsonBuilder();
@ -73,13 +75,14 @@ public class EcowattRestApi {
this.authService = oAuthFactory.createOAuthClientService(authServiceHandle, ECOWATT_API_TOKEN_URL, null, this.authService = oAuthFactory.createOAuthClientService(authServiceHandle, ECOWATT_API_TOKEN_URL, null,
idClient, idSecret, null, true); idClient, idSecret, null, true);
this.authServiceHandle = authServiceHandle; this.authServiceHandle = authServiceHandle;
this.apiUrl = ECOWATT_API_GET_SIGNALS_URL.formatted(apiVersion);
} }
public EcowattApiResponse getSignals() throws CommunicationException, EcowattApiLimitException { public EcowattApiResponse getSignals() throws CommunicationException, EcowattApiLimitException {
logger.debug("API request signals"); logger.debug("API request {}", apiUrl);
String token = authenticate().getAccessToken(); String token = authenticate().getAccessToken();
final Request request = httpClient.newRequest(ECOWATT_API_GET_SIGNALS_URL).method(HttpMethod.GET) final Request request = httpClient.newRequest(apiUrl).method(HttpMethod.GET)
.header(HttpHeader.AUTHORIZATION, "Bearer " + token).timeout(10, TimeUnit.SECONDS); .header(HttpHeader.AUTHORIZATION, "Bearer " + token).timeout(10, TimeUnit.SECONDS);
ContentResponse response; ContentResponse response;

View File

@ -8,7 +8,7 @@ addon.ecowatt.description = This binding uses the Ecowatt API to expose clear si
thing-type.ecowatt.signals.label = Electricity Forecast thing-type.ecowatt.signals.label = Electricity Forecast
thing-type.ecowatt.signals.description = The French electricity consumption forecasts thing-type.ecowatt.signals.description = The French electricity consumption forecasts
thing-type.ecowatt.signals.channel.currentHourSignal.label = Current Hour Signal thing-type.ecowatt.signals.channel.currentHourSignal.label = Current Hour Signal
thing-type.ecowatt.signals.channel.currentHourSignal.description = The signal relating to the forecast consumption level for the current hour. Values are 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red). thing-type.ecowatt.signals.channel.currentHourSignal.description = The signal relating to the forecast consumption level for the current hour. Values are 0 for normal consumption (green) and carbon-free production, 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red).
thing-type.ecowatt.signals.channel.inThreeDaysSignal.label = In Three Days Signal thing-type.ecowatt.signals.channel.inThreeDaysSignal.label = In Three Days Signal
thing-type.ecowatt.signals.channel.inThreeDaysSignal.description = The signal relating to the forecast consumption level in three days. Values are 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red). thing-type.ecowatt.signals.channel.inThreeDaysSignal.description = The signal relating to the forecast consumption level in three days. Values are 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red).
thing-type.ecowatt.signals.channel.inTwoDaysSignal.label = In Two Days Signal thing-type.ecowatt.signals.channel.inTwoDaysSignal.label = In Two Days Signal
@ -20,6 +20,10 @@ thing-type.ecowatt.signals.channel.tomorrowSignal.description = The signal relat
# thing types config # thing types config
thing-type.config.ecowatt.signals.apiVersion.label = API Version
thing-type.config.ecowatt.signals.apiVersion.description = The version of the Ecowatt tile to which you subscribed in the RTE portal.
thing-type.config.ecowatt.signals.apiVersion.option.4 = V4.0 (deprecated)
thing-type.config.ecowatt.signals.apiVersion.option.5 = V5.0
thing-type.config.ecowatt.signals.idClient.label = ID Client thing-type.config.ecowatt.signals.idClient.label = ID Client
thing-type.config.ecowatt.signals.idClient.description = ID client provided with the application you created in the RTE portal. thing-type.config.ecowatt.signals.idClient.description = ID client provided with the application you created in the RTE portal.
thing-type.config.ecowatt.signals.idSecret.label = ID Secret thing-type.config.ecowatt.signals.idSecret.label = ID Secret
@ -28,7 +32,8 @@ thing-type.config.ecowatt.signals.idSecret.description = ID secret provided with
# channel types # channel types
channel-type.ecowatt.signal.label = Consumption Signal channel-type.ecowatt.signal.label = Consumption Signal
channel-type.ecowatt.signal.description = The signal relating to the forecast consumption level. Values are 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red). channel-type.ecowatt.signal.description = The signal relating to the forecast consumption level. Values are 0 for normal consumption (green) and carbon-free production, 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red).
channel-type.ecowatt.signal.state.option.0 = Green + carbon-free production
channel-type.ecowatt.signal.state.option.1 = Green channel-type.ecowatt.signal.state.option.1 = Green
channel-type.ecowatt.signal.state.option.2 = Orange channel-type.ecowatt.signal.state.option.2 = Orange
channel-type.ecowatt.signal.state.option.3 = Red channel-type.ecowatt.signal.state.option.3 = Red

View File

@ -34,12 +34,22 @@
</channel> </channel>
<channel id="currentHourSignal" typeId="signal"> <channel id="currentHourSignal" typeId="signal">
<label>Current Hour Signal</label> <label>Current Hour Signal</label>
<description>The signal relating to the forecast consumption level for the current hour. Values are 1 for normal <description>The signal relating to the forecast consumption level for the current hour. Values are 0 for normal
consumption (green), 2 for strained electrical system (orange) and 3 for very strained electrical system (red).</description> consumption (green) and carbon-free production, 1 for normal consumption (green), 2 for strained electrical system
(orange) and 3 for very strained electrical system (red).</description>
</channel> </channel>
</channels> </channels>
<config-description> <config-description>
<parameter name="apiVersion" type="integer" required="false">
<label>API Version</label>
<description>The version of the Ecowatt tile to which you subscribed in the RTE portal.</description>
<options>
<option value="4">V4.0 (deprecated)</option>
<option value="5">V5.0</option>
</options>
<default>4</default>
</parameter>
<parameter name="idClient" type="text" required="true"> <parameter name="idClient" type="text" required="true">
<label>ID Client</label> <label>ID Client</label>
<description>ID client provided with the application you created in the RTE portal.</description> <description>ID client provided with the application you created in the RTE portal.</description>
@ -55,10 +65,12 @@
<channel-type id="signal"> <channel-type id="signal">
<item-type>Number</item-type> <item-type>Number</item-type>
<label>Consumption Signal</label> <label>Consumption Signal</label>
<description>The signal relating to the forecast consumption level. Values are 1 for normal consumption (green), 2 for <description>The signal relating to the forecast consumption level. Values are 0 for normal consumption (green) and
strained electrical system (orange) and 3 for very strained electrical system (red).</description> carbon-free production, 1 for normal consumption (green), 2 for strained electrical system (orange) and 3 for very
strained electrical system (red).</description>
<state readOnly="true"> <state readOnly="true">
<options> <options>
<option value="0">Green + carbon-free production</option>
<option value="1">Green</option> <option value="1">Green</option>
<option value="2">Orange</option> <option value="2">Orange</option>
<option value="3">Red</option> <option value="3">Red</option>

View File

@ -42,6 +42,7 @@ import com.google.gson.JsonDeserializer;
@NonNullByDefault @NonNullByDefault
public class EcowattApiResponseTest { public class EcowattApiResponseTest {
private static final DecimalType STATE_ZERO = new DecimalType(0);
private static final DecimalType STATE_ONE = new DecimalType(1); private static final DecimalType STATE_ONE = new DecimalType(1);
private static final DecimalType STATE_TWO = new DecimalType(2); private static final DecimalType STATE_TWO = new DecimalType(2);
private static final DecimalType STATE_THREE = new DecimalType(3); private static final DecimalType STATE_THREE = new DecimalType(3);
@ -104,6 +105,10 @@ public class EcowattApiResponseTest {
State expectedState; State expectedState;
for (int h = 0; h < 24; h++) { for (int h = 0; h < 24; h++) {
switch (h) { switch (h) {
case 2:
case 3:
expectedState = STATE_ZERO;
break;
case 7: case 7:
case 11: case 11:
case 19: case 19:
@ -155,6 +160,10 @@ public class EcowattApiResponseTest {
case 2: case 2:
expectedState = UnDefType.UNDEF; expectedState = UnDefType.UNDEF;
break; break;
case 5:
case 6:
expectedState = STATE_ZERO;
break;
case 10: case 10:
case 14: case 14:
case 22: case 22:

View File

@ -1,4 +1,4 @@
{"signals":[{"GenerationFichier":"2022-09-18T22:00:00+02:00","jour":"2022-09-22T00:00:00+02:00","dvalue":1,"message":"Notre consommation est raisonnable.","values":[{"pas":0,"hvalue":1},{"pas":1,"hvalue":1},{"pas":2,"hvalue":1},{"pas":3,"hvalue":1},{"pas":4,"hvalue":1},{"pas":5,"hvalue":1},{"pas":6,"hvalue":1},{"pas":7,"hvalue":1},{"pas":8,"hvalue":1},{"pas":9,"hvalue":1},{"pas":10,"hvalue":1},{"pas":11,"hvalue":1},{"pas":12,"hvalue":1},{"pas":13,"hvalue":1},{"pas":14,"hvalue":1},{"pas":15,"hvalue":1},{"pas":16,"hvalue":1},{"pas":17,"hvalue":1},{"pas":18,"hvalue":1},{"pas":19,"hvalue":1},{"pas":20,"hvalue":1},{"pas":21,"hvalue":1},{"pas":22,"hvalue":1}]}, {"signals":[{"GenerationFichier":"2022-09-18T22:00:00+02:00","jour":"2022-09-22T00:00:00+02:00","dvalue":1,"message":"Notre consommation est raisonnable.","values":[{"pas":0,"hvalue":1},{"pas":1,"hvalue":1},{"pas":2,"hvalue":1},{"pas":3,"hvalue":1},{"pas":4,"hvalue":1},{"pas":5,"hvalue":1},{"pas":6,"hvalue":1},{"pas":7,"hvalue":1},{"pas":8,"hvalue":1},{"pas":9,"hvalue":1},{"pas":10,"hvalue":1},{"pas":11,"hvalue":1},{"pas":12,"hvalue":1},{"pas":13,"hvalue":1},{"pas":14,"hvalue":1},{"pas":15,"hvalue":1},{"pas":16,"hvalue":1},{"pas":17,"hvalue":1},{"pas":18,"hvalue":1},{"pas":19,"hvalue":1},{"pas":20,"hvalue":1},{"pas":21,"hvalue":1},{"pas":22,"hvalue":1}]},
{"GenerationFichier":"2022-09-18T22:00:00+02:00","jour":"2022-09-20T00:00:00+02:00","dvalue":2,"message":"Notre consommation est raisonnable.","values":[{"pas":0,"hvalue":1},{"pas":1,"hvalue":1},{"pas":2,"hvalue":1},{"pas":3,"hvalue":1},{"pas":4,"hvalue":1},{"pas":5,"hvalue":1},{"pas":6,"hvalue":1},{"pas":7,"hvalue":1},{"pas":8,"hvalue":1},{"pas":9,"hvalue":1},{"pas":10,"hvalue":1},{"pas":11,"hvalue":1},{"pas":12,"hvalue":1},{"pas":13,"hvalue":1},{"pas":14,"hvalue":1},{"pas":15,"hvalue":1},{"pas":16,"hvalue":1},{"pas":17,"hvalue":1},{"pas":18,"hvalue":1},{"pas":19,"hvalue":1},{"pas":20,"hvalue":2},{"pas":21,"hvalue":1},{"pas":22,"hvalue":1},{"pas":23,"hvalue":1}]}, {"GenerationFichier":"2022-09-18T22:00:00+02:00","jour":"2022-09-20T00:00:00+02:00","dvalue":2,"message":"Notre consommation est raisonnable.","values":[{"pas":0,"hvalue":1},{"pas":1,"hvalue":1},{"pas":2,"hvalue":1},{"pas":3,"hvalue":1},{"pas":4,"hvalue":1},{"pas":5,"hvalue":1},{"pas":6,"hvalue":1},{"pas":7,"hvalue":1},{"pas":8,"hvalue":1},{"pas":9,"hvalue":1},{"pas":10,"hvalue":1},{"pas":11,"hvalue":1},{"pas":12,"hvalue":1},{"pas":13,"hvalue":1},{"pas":14,"hvalue":1},{"pas":15,"hvalue":1},{"pas":16,"hvalue":1},{"pas":17,"hvalue":1},{"pas":18,"hvalue":1},{"pas":19,"hvalue":1},{"pas":20,"hvalue":2},{"pas":21,"hvalue":1},{"pas":22,"hvalue":1},{"pas":23,"hvalue":1}]},
{"GenerationFichier":"2022-09-18T22:00:00+02:00","jour":"2022-09-21T00:00:00+02:00","dvalue":1,"message":"Notre consommation est raisonnable.","values":[{"pas":0,"hvalue":1},{"pas":1,"hvalue":1},{"pas":2,"hvalue":1},{"pas":3,"hvalue":1},{"pas":4,"hvalue":1},{"pas":5,"hvalue":1},{"pas":6,"hvalue":1},{"pas":7,"hvalue":1},{"pas":8,"hvalue":1},{"pas":9,"hvalue":1},{"pas":10,"hvalue":1},{"pas":11,"hvalue":1},{"pas":12,"hvalue":1},{"pas":13,"hvalue":1},{"pas":14,"hvalue":1},{"pas":15,"hvalue":1},{"pas":16,"hvalue":1},{"pas":17,"hvalue":1},{"pas":18,"hvalue":1},{"pas":19,"hvalue":1},{"pas":20,"hvalue":1},{"pas":21,"hvalue":1},{"pas":22,"hvalue":1},{"pas":23,"hvalue":1}]}, {"GenerationFichier":"2022-09-18T22:00:00+02:00","jour":"2022-09-21T00:00:00+02:00","dvalue":1,"message":"Notre consommation est raisonnable.","values":[{"pas":0,"hvalue":1},{"pas":1,"hvalue":1},{"pas":2,"hvalue":1},{"pas":3,"hvalue":1},{"pas":4,"hvalue":1},{"pas":5,"hvalue":1},{"pas":6,"hvalue":1},{"pas":7,"hvalue":1},{"pas":8,"hvalue":1},{"pas":9,"hvalue":1},{"pas":10,"hvalue":1},{"pas":11,"hvalue":1},{"pas":12,"hvalue":1},{"pas":13,"hvalue":1},{"pas":14,"hvalue":1},{"pas":15,"hvalue":1},{"pas":16,"hvalue":1},{"pas":17,"hvalue":1},{"pas":18,"hvalue":1},{"pas":19,"hvalue":1},{"pas":20,"hvalue":1},{"pas":21,"hvalue":1},{"pas":22,"hvalue":1},{"pas":23,"hvalue":1}]},
{"GenerationFichier":"2022-09-18T22:00:00+02:00","jour":"2022-09-19T00:00:00+02:00","dvalue":3,"message":"Notre consommation est raisonnable.","values":[{"pas":0,"hvalue":1},{"pas":1,"hvalue":1},{"pas":2,"hvalue":1},{"pas":3,"hvalue":1},{"pas":4,"hvalue":1},{"pas":5,"hvalue":1},{"pas":6,"hvalue":1},{"pas":7,"hvalue":2},{"pas":8,"hvalue":3},{"pas":9,"hvalue":3},{"pas":10,"hvalue":3},{"pas":11,"hvalue":2},{"pas":12,"hvalue":1},{"pas":13,"hvalue":1},{"pas":14,"hvalue":1},{"pas":15,"hvalue":1},{"pas":16,"hvalue":1},{"pas":17,"hvalue":1},{"pas":18,"hvalue":1},{"pas":19,"hvalue":2},{"pas":20,"hvalue":3},{"pas":21,"hvalue":2},{"pas":22,"hvalue":1},{"pas":23,"hvalue":1}]}]} {"GenerationFichier":"2022-09-18T22:00:00+02:00","jour":"2022-09-19T00:00:00+02:00","dvalue":3,"message":"Notre consommation est raisonnable.","values":[{"pas":0,"hvalue":1},{"pas":1,"hvalue":1},{"pas":2,"hvalue":0},{"pas":3,"hvalue":0},{"pas":4,"hvalue":1},{"pas":5,"hvalue":1},{"pas":6,"hvalue":1},{"pas":7,"hvalue":2},{"pas":8,"hvalue":3},{"pas":9,"hvalue":3},{"pas":10,"hvalue":3},{"pas":11,"hvalue":2},{"pas":12,"hvalue":1},{"pas":13,"hvalue":1},{"pas":14,"hvalue":1},{"pas":15,"hvalue":1},{"pas":16,"hvalue":1},{"pas":17,"hvalue":1},{"pas":18,"hvalue":1},{"pas":19,"hvalue":2},{"pas":20,"hvalue":3},{"pas":21,"hvalue":2},{"pas":22,"hvalue":1},{"pas":23,"hvalue":1}]}]}