forked from OpenEMS/openems
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Improvements to App-Manager (OpenEMS#1813)
Co-authored-by: Michael Grill <59126309+michaelgrill@users.noreply.github.com>
- Loading branch information
1 parent
b1d60d5
commit 8a1eebb
Showing
87 changed files
with
9,924 additions
and
519 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
131 changes: 131 additions & 0 deletions
131
io.openems.edge.core/src/io/openems/edge/app/api/ModbusTcpApiReadOnly.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,131 @@ | ||
package io.openems.edge.app.api; | ||
|
||
import java.util.EnumMap; | ||
import java.util.List; | ||
import java.util.Map; | ||
import java.util.TreeMap; | ||
|
||
import org.osgi.service.cm.ConfigurationAdmin; | ||
import org.osgi.service.component.ComponentContext; | ||
import org.osgi.service.component.annotations.Activate; | ||
import org.osgi.service.component.annotations.Reference; | ||
|
||
import com.google.common.collect.Lists; | ||
import com.google.gson.JsonElement; | ||
|
||
import io.openems.common.exceptions.OpenemsError.OpenemsNamedException; | ||
import io.openems.common.function.ThrowingBiFunction; | ||
import io.openems.common.types.EdgeConfig; | ||
import io.openems.common.utils.JsonUtils; | ||
import io.openems.edge.app.api.ModbusTcpApiReadOnly.Property; | ||
import io.openems.edge.common.component.ComponentManager; | ||
import io.openems.edge.core.appmanager.AbstractOpenemsApp; | ||
import io.openems.edge.core.appmanager.AppAssistant; | ||
import io.openems.edge.core.appmanager.AppConfiguration; | ||
import io.openems.edge.core.appmanager.AppDescriptor; | ||
import io.openems.edge.core.appmanager.ComponentUtil; | ||
import io.openems.edge.core.appmanager.ConfigurationTarget; | ||
import io.openems.edge.core.appmanager.OpenemsApp; | ||
import io.openems.edge.core.appmanager.OpenemsAppCardinality; | ||
import io.openems.edge.core.appmanager.OpenemsAppCategory; | ||
import io.openems.edge.core.appmanager.validator.CheckAppsNotInstalled; | ||
import io.openems.edge.core.appmanager.validator.Validator; | ||
import io.openems.edge.core.appmanager.validator.Validator.Builder; | ||
|
||
/** | ||
* Describes a App for ReadOnly Modbus/TCP Api. | ||
* | ||
* <pre> | ||
{ | ||
"appId":"App.Api.ModbusTcp.ReadOnly", | ||
"alias":"Modbus/TCP-Api Read-Only", | ||
"instanceId": UUID, | ||
"image": base64, | ||
"properties":{ | ||
"CONTROLLER_ID": "ctrlApiModbusTcp0" | ||
}, | ||
"appDescriptor": { | ||
"websiteUrl": <a href= | ||
"https://docs.fenecon.de/de/_/latest/fems/apis.html#_fems_app_modbustcp_api_lesend">https://docs.fenecon.de/de/_/latest/fems/apis.html#_fems_app_modbustcp_api_lesend</a> | ||
} | ||
} | ||
* </pre> | ||
*/ | ||
@org.osgi.service.component.annotations.Component(name = "App.Api.ModbusTcp.ReadOnly") | ||
public class ModbusTcpApiReadOnly extends AbstractOpenemsApp<Property> implements OpenemsApp { | ||
|
||
public static enum Property { | ||
// Components | ||
CONTROLLER_ID; | ||
} | ||
|
||
@Activate | ||
public ModbusTcpApiReadOnly(@Reference ComponentManager componentManager, ComponentContext context, | ||
@Reference ConfigurationAdmin cm, @Reference ComponentUtil componentUtil) { | ||
super(componentManager, context, cm, componentUtil); | ||
} | ||
|
||
@Override | ||
public AppAssistant getAppAssistant() { | ||
return AppAssistant.create(this.getName()) // | ||
.build(); | ||
} | ||
|
||
@Override | ||
public AppDescriptor getAppDescriptor() { | ||
return AppDescriptor.create() // | ||
.build(); | ||
} | ||
|
||
@Override | ||
public OpenemsAppCategory[] getCategorys() { | ||
return new OpenemsAppCategory[] { OpenemsAppCategory.API }; | ||
} | ||
|
||
@Override | ||
public String getImage() { | ||
return OpenemsApp.FALLBACK_IMAGE; | ||
} | ||
|
||
@Override | ||
public String getName() { | ||
return "Modbus/TCP-Api Read-Only"; | ||
} | ||
|
||
@Override | ||
public OpenemsAppCardinality getCardinality() { | ||
return OpenemsAppCardinality.SINGLE; | ||
} | ||
|
||
@Override | ||
protected ThrowingBiFunction<ConfigurationTarget, EnumMap<Property, JsonElement>, AppConfiguration, OpenemsNamedException> appConfigurationFactory() { | ||
return (t, p) -> { | ||
|
||
var controllerId = this.getId(t, p, Property.CONTROLLER_ID, "ctrlApiModbusTcp0"); | ||
|
||
List<EdgeConfig.Component> components = Lists.newArrayList(// | ||
new EdgeConfig.Component(controllerId, this.getName(), "Controller.Api.ModbusTcp.ReadOnly", | ||
JsonUtils.buildJsonObject() // | ||
.build())); | ||
|
||
return new AppConfiguration(components); | ||
}; | ||
} | ||
|
||
@Override | ||
public Builder getValidateBuilder() { | ||
return Validator.create() // | ||
.setInstallableCheckableNames(new Validator.MapBuilder<>(new TreeMap<String, Map<String, ?>>()) // | ||
.put(CheckAppsNotInstalled.COMPONENT_NAME, // | ||
new Validator.MapBuilder<>(new TreeMap<String, Object>()) // | ||
.put("appIds", new String[] { "App.Api.ModbusTcp.ReadWrite" }) // | ||
.build()) | ||
.build()); | ||
} | ||
|
||
@Override | ||
protected Class<Property> getPropertyClass() { | ||
return Property.class; | ||
} | ||
|
||
} |
178 changes: 178 additions & 0 deletions
178
io.openems.edge.core/src/io/openems/edge/app/api/ModbusTcpApiReadWrite.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,178 @@ | ||
package io.openems.edge.app.api; | ||
|
||
import java.util.EnumMap; | ||
import java.util.List; | ||
import java.util.Map; | ||
import java.util.TreeMap; | ||
|
||
import org.osgi.service.cm.ConfigurationAdmin; | ||
import org.osgi.service.component.ComponentContext; | ||
import org.osgi.service.component.annotations.Activate; | ||
import org.osgi.service.component.annotations.Reference; | ||
|
||
import com.google.common.collect.Lists; | ||
import com.google.gson.JsonElement; | ||
|
||
import io.openems.common.exceptions.OpenemsError.OpenemsNamedException; | ||
import io.openems.common.function.ThrowingBiFunction; | ||
import io.openems.common.types.EdgeConfig; | ||
import io.openems.common.utils.EnumUtils; | ||
import io.openems.common.utils.JsonUtils; | ||
import io.openems.edge.app.api.ModbusTcpApiReadWrite.Property; | ||
import io.openems.edge.common.component.ComponentManager; | ||
import io.openems.edge.common.component.OpenemsComponent; | ||
import io.openems.edge.core.appmanager.AbstractOpenemsApp; | ||
import io.openems.edge.core.appmanager.AppAssistant; | ||
import io.openems.edge.core.appmanager.AppConfiguration; | ||
import io.openems.edge.core.appmanager.AppDescriptor; | ||
import io.openems.edge.core.appmanager.ComponentUtil; | ||
import io.openems.edge.core.appmanager.ConfigurationTarget; | ||
import io.openems.edge.core.appmanager.JsonFormlyUtil; | ||
import io.openems.edge.core.appmanager.JsonFormlyUtil.InputBuilder.Type; | ||
import io.openems.edge.core.appmanager.OpenemsApp; | ||
import io.openems.edge.core.appmanager.OpenemsAppCardinality; | ||
import io.openems.edge.core.appmanager.OpenemsAppCategory; | ||
import io.openems.edge.core.appmanager.validator.CheckAppsNotInstalled; | ||
import io.openems.edge.core.appmanager.validator.CheckNoComponentInstalledOfFactoryId; | ||
import io.openems.edge.core.appmanager.validator.Validator; | ||
import io.openems.edge.core.appmanager.validator.Validator.Builder; | ||
|
||
/** | ||
* Describes a App for ReadWrite Modbus/TCP Api. | ||
* | ||
* <pre> | ||
{ | ||
"appId":"App.Api.ModbusTcp.ReadWrite", | ||
"alias":"Modbus/TCP-Api Read-Write", | ||
"instanceId": UUID, | ||
"image": base64, | ||
"properties":{ | ||
"CONTROLLER_ID": "ctrlApiModbusTcp0", | ||
"API_TIMEOUT": 60, | ||
"COMPONENT_IDS": ["_sum", ...] | ||
}, | ||
"appDescriptor": { | ||
"websiteUrl": <a href= | ||
"https://fenecon.de/fems-2-2/fems-app-modbus-tcp-schreibzugriff-2/">https://fenecon.de/fems-2-2/fems-app-modbus-tcp-schreibzugriff-2/</a> | ||
} | ||
} | ||
* </pre> | ||
*/ | ||
@org.osgi.service.component.annotations.Component(name = "App.Api.ModbusTcp.ReadWrite") | ||
public class ModbusTcpApiReadWrite extends AbstractOpenemsApp<Property> implements OpenemsApp { | ||
|
||
public static enum Property { | ||
// Components | ||
CONTROLLER_ID, // | ||
// User-Values | ||
API_TIMEOUT, // | ||
COMPONENT_IDS; | ||
} | ||
|
||
@Activate | ||
public ModbusTcpApiReadWrite(@Reference ComponentManager componentManager, ComponentContext context, | ||
@Reference ConfigurationAdmin cm, @Reference ComponentUtil componentUtil) { | ||
super(componentManager, context, cm, componentUtil); | ||
} | ||
|
||
@Override | ||
public AppAssistant getAppAssistant() { | ||
return AppAssistant.create(this.getName()) // | ||
.fields(JsonUtils.buildJsonArray() // | ||
.add(JsonFormlyUtil.buildInput(Property.API_TIMEOUT) // | ||
.setLabel("Api-Timeout") // | ||
.setDescription("Sets the timeout in seconds for updates on Channels set by this Api.") | ||
.setDefaultValue(60) // | ||
.isRequired(true) // | ||
.setInputType(Type.NUMBER) // | ||
.setMin(30) // | ||
.setMax(120) // | ||
.build()) | ||
.add(JsonFormlyUtil.buildSelect(Property.COMPONENT_IDS) // | ||
.isMulti(true) // | ||
.isRequired(true) // | ||
.setLabel("Component-IDs") // | ||
.setDescription("Components that should be made available via Modbus.") | ||
.setOptions(this.componentManager.getAllComponents(), t -> t.id() + ": " + t.alias(), | ||
OpenemsComponent::id) | ||
.setDefaultValue("_sum") // | ||
.build()) | ||
.build()) | ||
.build(); | ||
} | ||
|
||
@Override | ||
public AppDescriptor getAppDescriptor() { | ||
return AppDescriptor.create() // | ||
.build(); | ||
} | ||
|
||
@Override | ||
public OpenemsAppCategory[] getCategorys() { | ||
return new OpenemsAppCategory[] { OpenemsAppCategory.API }; | ||
} | ||
|
||
@Override | ||
public String getImage() { | ||
return OpenemsApp.FALLBACK_IMAGE; | ||
} | ||
|
||
@Override | ||
public String getName() { | ||
return "Modbus/TCP-Api Read-Write"; | ||
} | ||
|
||
@Override | ||
public OpenemsAppCardinality getCardinality() { | ||
return OpenemsAppCardinality.SINGLE; | ||
} | ||
|
||
@Override | ||
protected ThrowingBiFunction<ConfigurationTarget, EnumMap<Property, JsonElement>, AppConfiguration, OpenemsNamedException> appConfigurationFactory() { | ||
return (t, p) -> { | ||
|
||
var controllerId = this.getId(t, p, Property.CONTROLLER_ID, "ctrlApiModbusTcp0"); | ||
var apiTimeout = EnumUtils.getAsInt(p, Property.API_TIMEOUT); | ||
var controllerIds = EnumUtils.getAsJsonArray(p, Property.COMPONENT_IDS); | ||
|
||
// remove self if selected | ||
for (var i = 0; i < controllerIds.size(); i++) { | ||
if (controllerIds.get(i).getAsString().equals(controllerId)) { | ||
controllerIds.remove(i); | ||
break; | ||
} | ||
} | ||
|
||
List<EdgeConfig.Component> components = Lists.newArrayList(// | ||
new EdgeConfig.Component(controllerId, this.getName(), "Controller.Api.ModbusTcp.ReadWrite", | ||
JsonUtils.buildJsonObject() // | ||
.addProperty("apiTimeout", apiTimeout) // | ||
.add("component.ids", controllerIds).build())); | ||
|
||
return new AppConfiguration(components); | ||
}; | ||
} | ||
|
||
@Override | ||
public Builder getValidateBuilder() { | ||
return Validator.create() // | ||
.setInstallableCheckableNames(new Validator.MapBuilder<>(new TreeMap<String, Map<String, ?>>()) // | ||
.put(CheckAppsNotInstalled.COMPONENT_NAME, // | ||
new Validator.MapBuilder<>(new TreeMap<String, Object>()) // | ||
.put("appIds", new String[] { "App.Api.ModbusTcp.ReadOnly" }) // | ||
.build()) | ||
// TODO remove this if the free apps get created via App-Manager and an actual | ||
// app instance gets created | ||
.put(CheckNoComponentInstalledOfFactoryId.COMPONENT_NAME, // | ||
new Validator.MapBuilder<>(new TreeMap<String, Object>()) // | ||
.put("factorieId", "Controller.Api.ModbusTcp.ReadOnly") // | ||
.build()) | ||
.build()); | ||
} | ||
|
||
@Override | ||
protected Class<Property> getPropertyClass() { | ||
return Property.class; | ||
} | ||
|
||
} |
Oops, something went wrong.