Tags vs. Metadata

Tags: #<Tag:0x00007faedf8eec58> #<Tag:0x00007faedf8ee5c8>

Hi,

I just added support for metadata to HABApp.However, the concept of metadata is still not clear to me.
How is metadata different than tags?
When I search I only find information about some “magic” that is happening when using the alexa skill but the real purpose is still unclear.
It would be nice if someone could explain the concepts. Thanks!

Tags are, well, tags. Single word tokens you can add to an Item to help identify it as something. For example, Google Assistant and Alexa use tags to identify Items as Lighting, Temperature, etc.

Metadata allows more structure and dynamism. There is actually a hierarchy (which I admit I don’t fully understand).

  • Namespace: top of the hierarchy
  • Value: middle of the hierarchy
  • List of key value pairs

I don’t think all three are strictly required but I haven’t explored metadata thoroughly yet and, important for you, the REST API for metadata is pretty crappy, only supporting adding and removal but not query (unless you already know the metadata that you want to retrieve in which case you can query for it in the GET /items/{itemname} endpoint).

You can see both in use in HABot Walkthrough (2/n): Semantic Tagging & Item Resolving. Groups are used for location. Tags are used for semantic type. Metadata is used for synonyms.

I’ve moved my Rules over to JSR223 and because you can access, add, and change metadata in Rules (can’t do so from Rules DSL) it becomes a handy place to store stuff like flags, initialization data, and metadata.

For example, I have a bunch of Items that monitor some of the services that are important to my home automation. If they go offline (i.e. OFF) I generate an alert if they remain offline for too long. And once I alert, I want to make sure I don’t alert that it’s offline again but do alert when it comes back online. And I want a nice friendly name for the service in that alert rather than the Item name.

The Rules DSL version uses Design Pattern: Human Readable Names in Messages with a map file for the names and Design Pattern: Associated Items to keep track of whether I’ve sent the alert of not in another Item.

In the JSR223 version of the Rule I replaced both with metadata. I statically define metadata for the name in my .items files and the Rules set the alerted flag in metadata dynamically.

So, the tl;dr is metadata is much more flexible and easier to use in more situations.

I don’t know what it’s “real” purpose is but it does seem to be used mainly by bindings and other add-ons (probably because it’s not easy to access in Rules DSL) to get additional information about an Item that isn’t possible to define with the existing Item’s syntax. JSR223 Rules users also use it to store stuff that would otherwise end up in a global dict or Associated Item.

My understanding is that “Value” is a way to use metadata when you only need to store something simple in a Namespace. To store more data under the Namespace, use key/value pairs. I think using the verbiage “middle” implies that the key/value pairs go under the “Value” in a hierarchical way.

I double checked and the REST API always returns “value” and “config”.
So it is more that they coexist which makes no sense for me.
It would make more sense if the “config” part would be directly under “MyTest”.

{
  "link": "http://localhost:8080/rest/items/TestString",
  "state": "NULL",
  "metadata": {
    "MyTest": {
      "value": "asdf",
      "config": {
        "c1": "v1"
      }
    }
  },
}

The REST API is definitely limited when it comes to metadata, and it has a few bugs too. Using it with JSR223 is a game changer. The namespace values don’t seem to have much use and looked to me like they were just grandfathered in from an earlier iteration of metadata before the configuration was built out. But they are used in the Alexa skill, so that might explain why they exist.

There’s some documentation in the helper libraries, but you’d probably appreciate looking through the module. I pushed an update to the module recently that allows for setting and getting hierarchical key/values and need to push the docs for it. You can have a metadata structure like this…

"Area Action": {
    "Mode": {
        "Morning": {"Low_Lux_Trigger":99999, "Level":98},
        "Day":{"Low_Lux_Trigger":50, "Level":98},
        "Evening":{"Low_Lux_Trigger":50, "Level":55},
        "Night":{"Low_Lux_Trigger":90, "Level":25},
        "Late":{"Low_Lux_Trigger":90, "Level":1},
        "Party":{"Low_Lux_Trigger":90, "Level":98},
        "Security":{"Low_Lux_Trigger":99999, "Level":98},
    }
    "Timer": {
        "Action": {
            "OFF": {
                "Time":600,
                "Recurring":False
            }
        },
        "Notification": {
            "ON": {
                "Time":3600,
                "Message": "The garage door is open",
                "Types": {
                    "Audio": True,
                    "Kodi": True,
                    "Mobile": False
                },
                "Priority": 0,
                "Recurring":True
            }
        }
    }
}

MUCH more powerful than tags! I’ve got a pretty decent handle on this, so shout if you have more questions.

1 Like