MQTT binding and system state channel types

The openHAB documentation mentions to prefer using system state channel types when possible to define channels on Things. These types seem very useful to me, as they cover many of the common channels a Thing has (like battery-level or signal-strength).

However, these channel types are, it seems, not supported when defining a Generic MQTT Thing. The add-on expects every channel type to come from the mqtt namespace and even throws an exception when it isn’t. This makes me a bit sad, because I have to re-define for example every battery channel on every MQTT Thing with the same properties and have to hope that I don’t make any mistakes for one Thing, which then is configured differently than the other ones.

I am sure that there is a good (technical?) reason for the MQTT binding to not support these channel types, so I’m curious: can someone tell me why it is implemented the way it is and, for example, the following thing definition doesn’t work?

UID: mqtt:topic:AqaraMotionSensor
label: "Zigbee2MQTT: Aqara Motion Sensor"
thingTypeUID: mqtt:topic
configuration:
  availabilityTopic: zigbee2mqtt/AqaraMotionSensor/availability
  payloadNotAvailable: offline
  payloadAvailable: online
bridgeUID: mqtt:broker:Mosquitto
  - id: battery
    channelTypeUID: system:battery-level
    label: Battery
    configuration:
      stateTopic: zigbee2mqtt/AqaraMotionSensorKitchen/temperature

The docs you link to are for developers of add-ons to describe to openHAB core what Things and Channels it provides. It is not docs for something usable by end users. At a minimum you’d need to modify the MQTT binding code and rebuild the add-on to take advantage of anything documented on that page.

The Channel Types supported by the MQTT binding are one of these and only one of these.

I can’t answer the technical specifics except to say that there is not and has never been the concept of end users defining their own Channel types. It’s not just for MQTT though, it’s across all bindings.

system:battery-level is not one of the supported Channel types so that’s not going to work. The Channel types map to the types of Item that the Channel would be linked to. There is no “battery-level” type Item so there is no such Channel type either. You’d use a number Channel for that since it represents a numeric value.

There is no way today to invent your own Channel type in openHAB short of making changes to the actual Java code for a binding, rebuilding and reinstalling with the newly rebuilt add-on with the changes.

Thanks for the details.

I do understand that we’re having a theoretical discussion here and not something that should actually work. Your answer, if I understand correctly (and that would match my expectations), boils down to “this is not a use case the software supports”.

However, talking from a user perspective instead of a technical point of view now: both the MQTT binding documentation you kindly linked and the developer documentation from my post talk about “channel types”. Reading the documentation suggests that the user is in fact defining channels in a Thing (which, from a technical perspective, you actually do: the Thing has additional channels after you’ve done so). I understand that there’s a layer of abstraction between the core “openHAB Thing” and the “MQTT Thing” the user defines, but to me it’s not really logical that you have to stick to the types the add-on itself provides when it seems on the surface that you just plug channels into the Thing, just like an add-on would do itself, and the add-on does have the ability to use the system-defined channel types.

Maybe I’m interpreting this wrong, but I don’t want to define a custom type, I just want to use one that is already available in the system. This is what my whole question boils down to: When an add-on exposes the underlying mechanism of defining Things and channels to the user, why don’t I have the same abilities the add-on has if the system already supports it?

Correct, but not defining the types of those Channels.

All I can suggest is to look at the code for how Things are implemented and perhaps it will become clear. Perhaps it’s important to realize that Channels don’t really exist independently from the Thing and what Channels are available and how those Channels are handled is implemented by the add-on, not core. So where is this code going to come from that actually implements the Channel handling? There is no mechanism for that. The add-on implements this handling code.

From a personal perspective, if you create a type for a thing called “battery-level” but in all respects it has and requires the same properties as a number Channel you really haven’t gained anything except for greatly increasing the complexity.

Because there is Java code required to handle it and that code lives in the add-on. As an end user, you don’t have access to write the Java code to handle that through config. You’d need to modify the source code and rebuild the add-on.

Thank you, Rich, for your detailed explanations. I might actually do as you suggested and and play around with the add-on’s source code a bit. I’m still not totally sure why the system doesn’t work as I would like to image, but I also have never bothered to go into more detail on how the add-on system works, so that might help the most.