[SOLVED] Water / Energy consumption Last Month

With great help of many topics on this forum, I managed to calculate the water consumption for:

  • Today so far
  • This week / month / year so far.
    Please find code below.
rule "sumSince Water"
when
  Item CountWater changed or Item Refresh received update
then
  sendCommand(CountWaterDay, CountWater.sumSince(now.withTimeAtStartOfDay()))
  sendCommand(CountWaterWeek, CountWater.sumSince(now.withTimeAtStartOfDay().withDayOfWeek(1)))
  sendCommand(CountWaterMonth, CountWater.sumSince(now.withTimeAtStartOfDay().withDayOfMonth(1)))
  sendCommand(CountWaterYear, CountWater.sumSince(now.withTimeAtStartOfDay().withDayOfYear(1)))
end

I am now looking to get the consumption from previous month.

Here I found a nice piece of code that would somehow fit in my case, but I am struggling to get it in a one-line rule. Is there anyone that can fit this in the sumSince(.....) format?

ZonedId zoneId = ZoneId.of( "America/Montreal" );
YearMonth yearMonthNow = YearMonth.now( zoneId );
YearMonth yearMonthPrevious = yearMonthNow.minusMonths( 1 );
LocalDate firstOfMonth = yearMonthPrevious.atDay( 1 );
LocalDate lastOfMonth = yearMonthPrevious.atEndOfMonth();

Don’t do that, then. There’s no advantage, and going step by step allows you to understand what you’re doing - especially in the future when you come back to a long forgotten rule.

These might help

// 1st day of last calendar month
val startDate = now.minusMonths(1).withDayOfMonth(1).withTimeAtStartOfDay

// last minute of last day of previous month
val stopDate = now.withDayOfMonth(1).withTimeAtStartOfDay.minusMinutes(1)
// its less windy than
// now.minusMonths(1).dayOfMonth().withMaximumValue.getDayOfMonth

Hi @rossko57, thanks again for your help!
I did not succeed to get it work yet, but that is because of my limited knowledge.
I tried to implement your suggestion as follows.

  • Added the declaration of the variables inside the rule.
  • Added the variables inside the sumSince part.
  val startDate = now.minusMonths(1).withDayOfMonth(1).withTimeAtStartOfDay
  // last minute of last day of previous month
  val stopDate = now.withDayOfMonth(1).withTimeAtStartOfDay.minusMinutes(1)
  // its less windy than
  // now.minusMonths(1).dayOfMonth().withMaximumValue.getDayOfMonth

I tried both:

  sendCommand(CountWaterPrevMonth, CountWater.sumSince(now.stopDate.startDate))

and

  sendCommand(CountWaterPrevMonth, CountWater.sumSince(stopDate.startDate))

but not surprisingly the log tells me that “startDate” is not a valid part of the rule.
How can I tell the rule not simply looking to “startDate” but to the declaration that is behind?

2020-11-12 20:18:01.081 [ERROR] [ntime.internal.engine.RuleEngineImpl] - Rule 'sumSince Water': 'startDate' is not a member of 'org.joda.time.DateTime'; line 18, column 56, length 18

Persistence service sumSince() works with one date/time parameter only. One.
It adds values from the target date to “now”.
You cannot use sumSince() to get a sum from date X to date Y.
You can use sumSince() to get a sum from date X to now.
You can use sumSince() to get a sum from date Y to now.
You can then subtract one from the other.
Whether that is any use depends on how your data is stored, but it should work for daily records.

val startDate = now.minusMonths(1).withDayOfMonth(1).withTimeAtStartOfDay
val oldsum = CountWater.sumSince(startDate)
logInfo("test", "Sum since old date " + oldsum.toString)
1 Like

Thanks @rossko57!
I understand your point.
My code now looks as follows and it works!

rule "sumSince Water"
when
  Item CountWater changed or Item Refresh received update
then
  sendCommand(CountWaterDay, CountWater.sumSince(now.withTimeAtStartOfDay()))
  sendCommand(CountWaterWeek, CountWater.sumSince(now.withTimeAtStartOfDay().withDayOfWeek(1)))
  sendCommand(CountWaterMonth, CountWater.sumSince(now.withTimeAtStartOfDay().withDayOfMonth(1)))
  sendCommand(CountWaterYear, CountWater.sumSince(now.withTimeAtStartOfDay().withDayOfYear(1)))

  val startDate = now.minusMonths(1).withDayOfMonth(1).withTimeAtStartOfDay
  val stopDate = now.withDayOfMonth(1).withTimeAtStartOfDay.minusMinutes(1)
  val start = CountWater.sumSince(startDate)
  val stop = CountWater.sumSince(stopDate)
  val prevMonth = start - stop
  logInfo("test", "Sum since old date " + prevMonth.toString)
  sendCommand(CountWaterPrevMonth, prevMonth)
end

I am getting an error in OH3, so replaced with this:
val startDate = now.minusMonths(1).withDayOfMonth(1).withHour(0).withMinute(0).withSecond(0)
Is this correct?
Thanks.