Why is persistence.lastUpdate() not always working

Hi everyone,

I’m encountering an issue with the persistence.lastUpdate() function not returning the expected result. I have the following setup:

  • Item: Illuminance_Garden_MiFlora1 is persisted, and I can see the data in the persistence store:
ItemId  ItemName
59      Illuminance_Garden_MiFlora1

Time                      Value
2025-01-24 00:00:01.375    115

In my script, I have:

let itemNames = ["Illuminance_Garden_MiFlora1"];
let itemNamesPresence = ["Switch_Garden_MiFlora1_Presence"];

for (let i = 0; i < itemNames.length; i++) {
    var itemName = itemNames[i];  // Item to monitor
    var itemNamePresence = itemNamesPresence[i];
    
    var last10Minute = time.ZonedDateTime.now().minusMinutes(10);
    var lastUpdateTime = items.getItem(itemName).persistence.lastUpdate();

    console.log("Testlastupdate" + lastUpdateTime);
}

However, when I check the logs, I see:

[ab.automation.script.file.miflora.js] - Testlastupdate null

My question: Why is persistence.lastUpdate() returning null in this case? The item Illuminance_Garden_MiFlora1 is correctly persisted, and I can see the timestamp and value in the persistence store.

I also noticed that if I add the following persistence strategy to Illuminance_Garden_MiFlora1:

Illuminance_Garden_MiFlora1: strategy = everyChange, everyMinute, everyDay, restoreOnStartup

then persistence.lastUpdate() works as expected and doesn’t return null.

or reference, my standard persistence rule is:

*: strategy = everyDay, restoreOnStartup

Has anyone encountered a similar issue or knows why this might be happening? I’d appreciate any help!

Thanks in advance!

If your persistence service is rrd4j, you must use everyMinute strategy, otherwise rrd4j does not work properly.

In the current logic, the persistence.lastUpdate() call will return null if the current state of the item is different from the last persisted state. The logic is that there must have been a state update since, but it has not been persisted, so rather than giving a wrong answer, null is given as an answer.

items.getItem(itemName).persistence.persistedState(time.ZonedDateTime.now()) should always give you the answer.

By persisting on everyChange you would avoid the problem in most cases, because every change will be written in persistence. There could still be a timing issue due, if a new state didn’t finish persisting before the lastUpdate() call, so still resulting in null.

This has heavily been debated before. There is a PR to make a getLastStateUpdate method available directly on the item state without requiring persistence. That would allow to revert this implicit assumption in persistence, and would be a better way to get the last update of an item, without relying on persistence.
See Add `getLastStateChange`, `getLastStateUpdate`, and `getLastState` to GenericItem by jimtng · Pull Request #4351 · openhab/openhab-core · GitHub

3 Likes