Rule to send a command to an item once every two week

Hey the title said a lot of what I need ! I need something to remind me when i have to take out the trash … If it was every friday it would be easy but it’s every two week ( on friday )

Is it possible to make a rule to send command to an item every two friday ?

Thanks

Take a look into CRON Statements, using that the rule can be triggered at certain times.

I think the simplest way would be something like this:

rule "trash reminder"
when
    Time cron "0 0 7 ? * FRI" //every Friday @ 7 O'clock
then
    if (now.weekOfWeekyear()/2 == int(now.weekOfWeekyear()/2)) { //even weeks
        //do some stuff
    }
    if (now.weekOfWeekyear()/2 != int(now.weekOfWeekyear()/2)) { //uneven weeks
        //do some stuff
    }
end

but be aware that sometimes there is a 53rd week in a year, so sometimes you will have to correct the code.
Another easy way would be to use caldav binding and define an appointment through your preferred calendar…

Could i do something like :

(trashweek is just a dummy switch )

rule "trash reminder"
when
Time cron “0 0 7 ? * FRI” //every Friday @ 7 O’clock
then
if (trashweek == ON){
//do some stuff
postupdate(evenweek, OFF)
}
if (trashweek == OFF){

postupdate(evenweek, ON)
}
end

Should be

...
if(trashweek.state == ON) { //don't forget .state
    evenweek.postUpdate(OFF) //prefer method instead of action!
 }
...

if trashweek is an item. Maybe you ment something like this?

rule "trash reminder"
when
    Time cron "0 0 7 ? * FRI" //every Friday @ 7 O'clock
then
    trashweek.postUpdate(if(trashweek.state == ON) OFF else ON) //toggle state once a week
end

But you will have to ensure the state is correct when starting openHAB.

1 Like

I modified the solution of Udo_Hartmann by calculating with millseconds till 01.01.1970 instead of week number. Replace 1484079952989L (L stands for long, it’s too big for an integer) with the milliseconds timestamp of a day in the past where the event first took place.

rule "trash reminder"
when
Time cron “0 0 7 ? * FRI” //every Friday @ 7 O’clock
then
if((now.getMillis()-1484079952989L)/(8640010007) % 2 == 0) {
logInfo(“Test”, “EVEN WEEK”)
} else {
logInfo(“Test”,“ODD WEEK”)
}
end

Explanation:
Let’s say the litter service came on 1484079952989. Between 1484079952989 and 1484079952989-1+7864001000 (that’s how many milliseconds a week has) the modulo two is zero. Between 1484079952989-1+2786400*1000 it is one. Then again zero and so on.

Yes. :slight_smile:

Only thing to mention: This is not really ODD or EVEN week, because either you do week number calculation like ISO 8601 (week number 1 is the one with the first thursday of the year) or maybe you do it the american way (week number 1 is the one with january 1st).
The former will result in some years with 52 weeks and some years with 53 weeks, the latter will result in "every year has 53 weeks, but some of them aren’t completed."
If a year has 53 weeks, an odd week (53) will be followed by an odd week (1).

However, this is no flaw in question of the “garbage week” :wink:

1 Like

This gives an error to me:

/ cannot be resolved.
The method int(Object) is undefined
/ cannot be resolved.

Can someone help? Thanks…

Please try (now.weekOfWeekyear/2).intValue instead.

Thanks, a lot, that solved one part :slight_smile:

But the current code still returns me a DateTime.property, not a week number as int.

I played around: It must be now.getWeekOfWeekyear(), not now.WeekOfWeekyear(). Is this correct? It gives me a number, not the DateTime.property.

So must it be

if(now.getWeekOfWeekyear()/2 != now.getWeekOfWeekyear()/2.intValue)
{
...
}

?
At least I get no error anymore :slight_smile:

Yes, that’s right. :slight_smile: But I’m pretty sure you have to use () around, as otherwise 2.intValue would be first executed.

So the final term should be

if(now.getWeekOfWeekyear()/2 != (now.getWeekOfWeekyear()/2).intValue)

Maybe you don’t need the empty brackets:

if(now.getWeekOfWeekyear/2 != (now.getWeekOfWeekyear/2).intValue)

Any ideas on what I might be doing wrong?

now.getWeekOfWeekyear gives me 19 as the current week but when I divide it by 2 (with now.getWeekOfWeekyear / 2) I get 9 rather than 9.5.

I tried various calculations see below

21:25:23.166 [INFO ] [g.eclipse.smarthome.model.script.Crib] - now.getWeekOfWeekyear(): 19
21:25:23.173 [INFO ] [g.eclipse.smarthome.model.script.Crib] - now.getWeekOfWeekyear() / 2: 9
21:25:23.180 [INFO ] [g.eclipse.smarthome.model.script.Crib] - now.getWeekOfWeekyear / 2: 9
21:25:23.186 [INFO ] [g.eclipse.smarthome.model.script.Crib] - var int addtest = 1/2 0
21:25:23.193 [INFO ] [g.eclipse.smarthome.model.script.Crib] - 1/2= 0
21:25:23.195 [INFO ] [g.eclipse.smarthome.model.script.Crib] - 3/4= 0
21:25:23.197 [INFO ] [g.eclipse.smarthome.model.script.Crib] - 3.35 + 3.1= 6.45

I’m sure I’m missing something obvious - any help is appreciated

if that’s an integer type to begin with, that makes sense.
You could either convert to a decimal type, or do an integer math trick;
the objective is to determine odd/even, yes?

If ( ((now.getWeekOfWeekyear / 2) * 2) == now.getWeekOfWeekyear ) {
       // it's even

Yes that’s right. Your code works so thanks for that.

Could I ask how I could convert to decimal type. I did try to do that but not successfully

Also if I do 1/2 is it correct that the answer returned is 0?

More than one way I’m sure. Ideas here

In integer maths, yes - 2 goes into into 1 zero times.