diff --git a/bundles/org.openhab.binding.kostalinverter/README.md b/bundles/org.openhab.binding.kostalinverter/README.md index 5e1d19225..c2cabb09a 100644 --- a/bundles/org.openhab.binding.kostalinverter/README.md +++ b/bundles/org.openhab.binding.kostalinverter/README.md @@ -291,7 +291,7 @@ String SolarStatus "Solar status [%s]" { channel="kostalinverter:kostal demo.items: ``` -Number:Power GridOutputPower "PV Output Power" { channel="kostalinverter:piko1020:mypiko1020:gridOutputPower" } +Number:Power GridOutputPower "Grid Output Power" { channel="kostalinverter:piko1020:mypiko1020:gridOutputPower" } Number:Energy YieldDaySecondGen "PV Output Power Day" { channel="kostalinverter:piko1020:mypiko1020:yieldDaySecondGen" } Number:Energy YieldTotalSecondGen "PV Output Power Total" { channel="kostalinverter:piko1020:mypiko1020:yieldTotalSecondgen" } Number:Dimensionless OperatingStatus "Operating Status" { channel="kostalinverter:piko1020:mypiko1020:operatingStatus" } diff --git a/bundles/org.openhab.binding.kostalinverter/src/main/java/org/openhab/binding/kostalinverter/internal/secondgeneration/SecondGenerationHandler.java b/bundles/org.openhab.binding.kostalinverter/src/main/java/org/openhab/binding/kostalinverter/internal/secondgeneration/SecondGenerationHandler.java index 3b873b811..771f424b9 100644 --- a/bundles/org.openhab.binding.kostalinverter/src/main/java/org/openhab/binding/kostalinverter/internal/secondgeneration/SecondGenerationHandler.java +++ b/bundles/org.openhab.binding.kostalinverter/src/main/java/org/openhab/binding/kostalinverter/internal/secondgeneration/SecondGenerationHandler.java @@ -187,147 +187,142 @@ public class SecondGenerationHandler extends BaseThingHandler { } private void refresh() { - try { - // Build posts for dxsEntries part - String dxsEntriesCall = inverterConfig.url + "/api/dxs.json?dxsEntries=" + channelConfigs.get(0).dxsEntries; - for (int i = 1; i < channelConfigs.size(); i++) { - dxsEntriesCall += ("&dxsEntries=" + channelConfigs.get(i).dxsEntries); - } - String jsonDxsEntriesResponse = callURL(dxsEntriesCall, httpClient); - SecondGenerationDxsEntriesContainerDTO dxsEntriesContainer = gson.fromJson(jsonDxsEntriesResponse, - SecondGenerationDxsEntriesContainerDTO.class); + // Build posts for dxsEntries part + String dxsEntriesCall = inverterConfig.url + "/api/dxs.json?dxsEntries=" + channelConfigs.get(0).dxsEntries; + for (int i = 1; i < channelConfigs.size(); i++) { + dxsEntriesCall += ("&dxsEntries=" + channelConfigs.get(i).dxsEntries); + } + String jsonDxsEntriesResponse = callURL(dxsEntriesCall, httpClient); + SecondGenerationDxsEntriesContainerDTO dxsEntriesContainer = gson.fromJson(jsonDxsEntriesResponse, + SecondGenerationDxsEntriesContainerDTO.class); - String[] channelPosts = new String[23]; - int channelPostsCounter = 0; - for (SecondGenerationDxsEntries dxsentries : dxsEntriesContainer.dxsEntries) { - channelPosts[channelPostsCounter] = dxsentries.getName(); - channelPostsCounter++; - } - channelPostsTemp = List.of(channelPosts); + String[] channelPosts = new String[23]; + int channelPostsCounter = 0; + for (SecondGenerationDxsEntries dxsentries : dxsEntriesContainer.dxsEntries) { + channelPosts[channelPostsCounter] = dxsentries.getName(); + channelPostsCounter++; + } + channelPostsTemp = List.of(channelPosts); - // Build posts for dxsEntriesExt part - String dxsEntriesCallExt = inverterConfig.url + "/api/dxs.json?dxsEntries=" - + channelConfigsExt.get(0).dxsEntries; - for (int i = 1; i < channelConfigs.size(); i++) { - dxsEntriesCallExt += ("&dxsEntries=" + channelConfigsExt.get(i).dxsEntries); - } - String jsonDxsEntriesResponseExt = callURL(dxsEntriesCallExt, httpClient); - SecondGenerationDxsEntriesContainerDTO dxsEntriesContainerExt = gson.fromJson(jsonDxsEntriesResponseExt, - SecondGenerationDxsEntriesContainerDTO.class); - String[] channelPostsExt = new String[23]; - int channelPostsCounterExt = 0; - for (SecondGenerationDxsEntries dxsentriesExt : dxsEntriesContainerExt.dxsEntries) { - channelPostsExt[channelPostsCounterExt] = dxsentriesExt.getName(); - channelPostsCounterExt++; - } - channelPostsTempExt = List.of(channelPostsExt); + // Build posts for dxsEntriesExt part + String dxsEntriesCallExt = inverterConfig.url + "/api/dxs.json?dxsEntries=" + + channelConfigsExt.get(0).dxsEntries; + for (int i = 1; i < channelConfigs.size(); i++) { + dxsEntriesCallExt += ("&dxsEntries=" + channelConfigsExt.get(i).dxsEntries); + } + String jsonDxsEntriesResponseExt = callURL(dxsEntriesCallExt, httpClient); + SecondGenerationDxsEntriesContainerDTO dxsEntriesContainerExt = gson.fromJson(jsonDxsEntriesResponseExt, + SecondGenerationDxsEntriesContainerDTO.class); + String[] channelPostsExt = new String[23]; + int channelPostsCounterExt = 0; + for (SecondGenerationDxsEntries dxsentriesExt : dxsEntriesContainerExt.dxsEntries) { + channelPostsExt[channelPostsCounterExt] = dxsentriesExt.getName(); + channelPostsCounterExt++; + } + channelPostsTempExt = List.of(channelPostsExt); - // Build posts for dxsEntriesExtExt part - String dxsEntriesCallExtExt = inverterConfig.url + "/api/dxs.json?dxsEntries=" - + channelConfigsExtExt.get(0).dxsEntries; - for (int i = 1; i < channelConfigsExtExt.size(); i++) { - dxsEntriesCallExtExt += ("&dxsEntries=" + channelConfigsExtExt.get(i).dxsEntries); - } - String jsonDxsEntriesResponseExtExt = callURL(dxsEntriesCallExtExt, httpClient); - SecondGenerationDxsEntriesContainerDTO dxsEntriesContainerExtExt = gson - .fromJson(jsonDxsEntriesResponseExtExt, SecondGenerationDxsEntriesContainerDTO.class); - String[] channelPostsExtExt = new String[3]; - int channelPostsCounterExtExt = 0; - for (SecondGenerationDxsEntries dxsentriesExtExt : dxsEntriesContainerExtExt.dxsEntries) { - channelPostsExtExt[channelPostsCounterExtExt] = dxsentriesExtExt.getName(); - channelPostsCounterExtExt++; - } - channelPostsTempExtExt = List.of(channelPostsExtExt); + // Build posts for dxsEntriesExtExt part + String dxsEntriesCallExtExt = inverterConfig.url + "/api/dxs.json?dxsEntries=" + + channelConfigsExtExt.get(0).dxsEntries; + for (int i = 1; i < channelConfigsExtExt.size(); i++) { + dxsEntriesCallExtExt += ("&dxsEntries=" + channelConfigsExtExt.get(i).dxsEntries); + } + String jsonDxsEntriesResponseExtExt = callURL(dxsEntriesCallExtExt, httpClient); + SecondGenerationDxsEntriesContainerDTO dxsEntriesContainerExtExt = gson.fromJson(jsonDxsEntriesResponseExtExt, + SecondGenerationDxsEntriesContainerDTO.class); + String[] channelPostsExtExt = new String[3]; + int channelPostsCounterExtExt = 0; + for (SecondGenerationDxsEntries dxsentriesExtExt : dxsEntriesContainerExtExt.dxsEntries) { + channelPostsExtExt[channelPostsCounterExtExt] = dxsentriesExtExt.getName(); + channelPostsCounterExtExt++; + } + channelPostsTempExtExt = List.of(channelPostsExtExt); - // Concatenate posts for all parts except configurable channels - channelPostsTempAll = combinePostsLists(channelPostsTemp, channelPostsTempExt, channelPostsTempExtExt); - String[] channelPostsTempAll1 = channelPostsTempAll.toArray(new String[0]); + // Concatenate posts for all parts except configurable channels + channelPostsTempAll = combinePostsLists(channelPostsTemp, channelPostsTempExt, channelPostsTempExtExt); + String[] channelPostsTempAll1 = channelPostsTempAll.toArray(new String[0]); - // Build posts for dxsEntriesConfigureable part - String[] channelPostsConfigurable = new String[5]; - if (inverterConfig.hasBattery) { - String dxsEntriesCallConfigurable = inverterConfig.url + "/api/dxs.json?dxsEntries=" - + channelConfigsConfigurable.get(0).dxsEntries; - for (int i = 1; i < channelConfigsConfigurable.size(); i++) { - dxsEntriesCallConfigurable += ("&dxsEntries=" + channelConfigsConfigurable.get(i).dxsEntries); + // Build posts for dxsEntriesConfigureable part + String[] channelPostsConfigurable = new String[5]; + if (inverterConfig.hasBattery) { + String dxsEntriesCallConfigurable = inverterConfig.url + "/api/dxs.json?dxsEntries=" + + channelConfigsConfigurable.get(0).dxsEntries; + for (int i = 1; i < channelConfigsConfigurable.size(); i++) { + dxsEntriesCallConfigurable += ("&dxsEntries=" + channelConfigsConfigurable.get(i).dxsEntries); + } + String jsonDxsEntriesResponseConfigurable = callURL(dxsEntriesCallConfigurable, httpClient); + SecondGenerationDxsEntriesContainerDTO dxsEntriesContainerConfigurable = gson + .fromJson(jsonDxsEntriesResponseConfigurable, SecondGenerationDxsEntriesContainerDTO.class); + int channelPostsCounterConfigurable = 0; + for (SecondGenerationDxsEntries dxsentriesConfigurable : dxsEntriesContainerConfigurable.dxsEntries) { + channelPostsConfigurable[channelPostsCounterConfigurable] = dxsentriesConfigurable.getName(); + channelPostsCounterConfigurable++; + } + } + + // Create and update actual values for non-configurable channels + if (!inverterConfig.hasBattery) { + channelConfigsAll = combineChannelConfigLists(channelConfigs, channelConfigsExt, channelConfigsExtExt); + int channelValuesCounterAll = 0; + for (SecondGenerationChannelConfiguration cConfig : channelConfigsAll) { + String channel = cConfig.id; + updateState(channel, getState(channelPostsTempAll1[channelValuesCounterAll], cConfig.unit)); + channelValuesCounterAll++; + } + } + // Create and update actual values for all channels + if (inverterConfig.hasBattery) { + // Part for updating non-configurable channels + channelConfigsAll = combineChannelConfigLists(channelConfigs, channelConfigsExt, channelConfigsExtExt); + // Update the non-configurable channels + int channelValuesCounterAll = 0; + for (SecondGenerationChannelConfiguration cConfig : channelConfigsAll) { + String channel = cConfig.id; + updateState(channel, getState(channelPostsTempAll1[channelValuesCounterAll], cConfig.unit)); + channelValuesCounterAll++; + } + + // Part for updating configurable channels + int channelValuesCounterConfigurable = 0; + for (SecondGenerationChannelConfiguration cConfig : channelConfigsConfigurable) { + String channel = cConfig.id; + String value = channelPostsConfigurable[channelValuesCounterConfigurable]; + int dxsEntriesCheckCounter = 3; + if (cConfig.dxsEntries.equals("33556484")) { + dxsEntriesCheckCounter = 1; } - String jsonDxsEntriesResponseConfigurable = callURL(dxsEntriesCallConfigurable, httpClient); - SecondGenerationDxsEntriesContainerDTO dxsEntriesContainerConfigurable = gson - .fromJson(jsonDxsEntriesResponseConfigurable, SecondGenerationDxsEntriesContainerDTO.class); - int channelPostsCounterConfigurable = 0; - for (SecondGenerationDxsEntries dxsentriesConfigurable : dxsEntriesContainerConfigurable.dxsEntries) { - channelPostsConfigurable[channelPostsCounterConfigurable] = dxsentriesConfigurable.getName(); - channelPostsCounterConfigurable++; + if (cConfig.dxsEntries.equals("33556482")) { + dxsEntriesCheckCounter = 2; + } + switch (dxsEntriesCheckCounter) { + case 1: + if ("false".equals(value)) { + updateState(channel, OnOffType.OFF); + } + if ("true".equals(value)) { + updateState(channel, OnOffType.ON); + } + channelValuesCounterConfigurable++; + break; + case 2: + if ("false".equals(value)) { + State stateFalse = new StringType("0"); + updateState(channel, stateFalse); + } + if ("true".equals(value)) { + State stateTrue = new StringType("1"); + updateState(channel, stateTrue); + } + channelValuesCounterConfigurable++; + break; + case 3: + State stateOther = getState(channelPostsConfigurable[channelValuesCounterConfigurable], + cConfig.unit); + updateState(channel, stateOther); + channelValuesCounterConfigurable++; + break; } } - - // Create and update actual values for non-configurable channels - if (!inverterConfig.hasBattery) { - channelConfigsAll = combineChannelConfigLists(channelConfigs, channelConfigsExt, channelConfigsExtExt); - int channelValuesCounterAll = 0; - for (SecondGenerationChannelConfiguration cConfig : channelConfigsAll) { - String channel = cConfig.id; - updateState(channel, getState(channelPostsTempAll1[channelValuesCounterAll], cConfig.unit)); - channelValuesCounterAll++; - } - } - // Create and update actual values for all channels - if (inverterConfig.hasBattery) { - // Part for updating non-configurable channels - channelConfigsAll = combineChannelConfigLists(channelConfigs, channelConfigsExt, channelConfigsExtExt); - // Update the non-configurable channels - int channelValuesCounterAll = 0; - for (SecondGenerationChannelConfiguration cConfig : channelConfigsAll) { - String channel = cConfig.id; - updateState(channel, getState(channelPostsTempAll1[channelValuesCounterAll], cConfig.unit)); - channelValuesCounterAll++; - } - - // Part for updating configurable channels - int channelValuesCounterConfigurable = 0; - for (SecondGenerationChannelConfiguration cConfig : channelConfigsConfigurable) { - String channel = cConfig.id; - String value = channelPostsConfigurable[channelValuesCounterConfigurable]; - int dxsEntriesCheckCounter = 3; - if (cConfig.dxsEntries.equals("33556484")) { - dxsEntriesCheckCounter = 1; - } - if (cConfig.dxsEntries.equals("33556482")) { - dxsEntriesCheckCounter = 2; - } - switch (dxsEntriesCheckCounter) { - case 1: - if ("false".equals(value)) { - updateState(channel, OnOffType.OFF); - } - if ("true".equals(value)) { - updateState(channel, OnOffType.ON); - } - channelValuesCounterConfigurable++; - break; - case 2: - if ("false".equals(value)) { - State stateFalse = new StringType("0"); - updateState(channel, stateFalse); - } - if ("true".equals(value)) { - State stateTrue = new StringType("1"); - updateState(channel, stateTrue); - } - channelValuesCounterConfigurable++; - break; - case 3: - State stateOther = getState(channelPostsConfigurable[channelValuesCounterConfigurable], - cConfig.unit); - updateState(channel, stateOther); - channelValuesCounterConfigurable++; - break; - } - } - } - } catch (final RuntimeException e) { - logger.debug("Updating inverter status failed: ", e); - updateStatus(ThingStatus.OFFLINE, ThingStatusDetail.COMMUNICATION_ERROR, e.getMessage()); } } @@ -338,7 +333,10 @@ public class SecondGenerationHandler extends BaseThingHandler { try { SecondGenerationConfigurationHandler.executeConfigurationChanges(httpClientHandleCommand, url, username, password, dxsEntriesConf, valueConfiguration); - } catch (InterruptedException | ExecutionException | TimeoutException | NoSuchAlgorithmException e) { + } catch (InterruptedException e) { + Thread.currentThread().interrupt(); + logger.debug("Connection to inverter interrupted during configuration"); + } catch (ExecutionException | TimeoutException | NoSuchAlgorithmException e) { logger.debug("Connection to inverter disturbed during configuration"); } } @@ -347,8 +345,11 @@ public class SecondGenerationHandler extends BaseThingHandler { private final String callURL(String dxsEntriesCall, HttpClient httpClient) { String jsonDxsResponse = ""; try { - jsonDxsResponse = httpClient.GET(dxsEntriesCall).getContentAsString(); - } catch (InterruptedException | ExecutionException | TimeoutException e2) { + jsonDxsResponse = httpClient.GET(dxsEntriesCall).getContentAsString().replace("null", "0.000000"); + } catch (InterruptedException e2) { + Thread.currentThread().interrupt(); + logger.debug("Connection to inverter interrupted during scrape"); + } catch (ExecutionException | TimeoutException e2) { logger.debug("Connection to inverter disturbed during scrape"); } return jsonDxsResponse;