On 3.0 ? what post you use for this ?
I tried several but each time I have errors, javascript even bug for the “Hello World”.
thanks in advance
On 3.0 ? what post you use for this ?
I tried several but each time I have errors, javascript even bug for the “Hello World”.
thanks in advance
What do you mean by what post?
To install jython I used this procedure, python script works, on the other hand javascript, bug all the time, I tried several times the procedure but without success, if you succeeded maybe you have a link describing it, I must obviously missing something
I would like to order the javascript files on my test server 3.0.
thanks in advance
I didn’t install anything else. Mine is just a plain install of OH3.
I have these bindings: MQTT,mail,Astro.
I have no DSL rules and only ECMAScript (JavaScript).
My set up is very simple.
Start a new post for this, instead of adding on to a tutorial about something else,it’ll work out better.
Thank you rossko57, this is what will do it will indeed be clearer
hi @ubeaut all good?
I am trying to setup the simplest way to notify me when batteries are low (RPIs). I saw you post and “copy pasted it” (but i dont know exactly what i am doing.
i copied your java script code into one of my rules, renamed the group to my own and (for now) disabled the email rule because I have no idea how to make it work - do i need to setup something to be able to send emails via javascript code?
Cna i change somehow the item display name from the label of the item to the “officia” name of the device? (all levels are battery level so i would need to rename them all)
I can send dsl rule - cloud driven notifications to my phone/app but I dont know if htis is doable with Javascirpt? it is it? any pointers?
thanks in advance!
To get the email to work you have to install the mail binding.
If you have copied the code then it should just work. It’s nothing special.
Put the code you have done here in this thread and then someone can see what you have done.
@ubeaut - aha mail binding. now i know! (obvious ok! )
I think that the mail binding will have to wait. I found an other way around it and was a little lucky i guess with the testing. here is my working javascript code with Notifications on the openhab app (needs cloud setup) - Group all batteries are in is called Batteries
configuration: {}
triggers:
- id: "1"
configuration:
time: 17:30
type: timer.TimeOfDayTrigger
conditions: []
actions:
- inputs: {}
id: "2"
configuration:
type: application/javascript
script: >
var logger =
Java.type('org.slf4j.LoggerFactory').getLogger('org.openhab.rule.' +
ctx.ruleUID);
var ArrayList = Java.type('java.util.ArrayList'); var NotificationAction = org.openhab.io.openhabcloud.NotificationAction;
battcheckList = new ArrayList();
/*
This will check the percentage of battery left and if it is low then push notify
Add the items to check into Batteries group
*/
var whatitis = "";
var percenttocheck = 15;
ir.getItem("Batteries").members
.stream()
.filter(function(batt) {return batt.state.intValue() <= percenttocheck; } )
.forEach(function(batt) { whatitis = whatitis + batt.name +": "+ batt.state +"%" + "\r\n"; } );
if(whatitis != ""){
battcheckList.add(whatitis);
logger.info('\r\nBattery low: \r\n' + whatitis );
}
//If something in the array then send an email
if(battcheckList.length !== 0){
message = "Low Batτερυ: " +battcheckList + " Percentage below " +percenttocheck;
NotificationAction.sendNotification("XXX@gmail.com", message);
logger.info('\r\nArray list: \r\n' + battcheckList );
}
type: script.ScriptAction
To test it change
percenttocheck to 115
That way it will log to the log file.
By the way if you want the name you gave the item then change:
batt.name
to
batt.label
P.S Did this work for you?
@ubeaut @alexkarageorgis thank you very much for this rule. Just what I was looking for. Works perfectly.
hello everyone. Bringing this back to life as my old Java code stopped working in the new openhab 4.+. I am assuming the new Java version doesnt like my code.
could someone understand what is wrong with this code under the new java?
var logger = Java.type('org.slf4j.LoggerFactory').getLogger('org.openhab.rule.' + ctx.ruleUID);
var ArrayList = Java.type('java.util.ArrayList'); var NotificationAction = org.openhab.io.openhabcloud.NotificationAction;
battcheckList = new ArrayList();
/*
This will check the percentage of battery left and if it is low then push notify
Add the items to check into Batteries group
*/
var whatitis = "";
var percenttocheck = 15;
ir.getItem("Batteries").members
.stream()
.filter(function(batt) {return batt.state.intValue() <= percenttocheck; } )
.forEach(function(batt) { whatitis = whatitis + batt.name +": "+ batt.state +"%" + "\r\n"; } );
if(whatitis != ""){
battcheckList.add(whatitis);
logger.info('\r\nBattery low: \r\n' + whatitis );
}
//If something in the array then send an email
if(battcheckList.length !== 0){
message = "Low Battery: " +battcheckList + " Percentage below " +percenttocheck;
NotificationAction.sendNotification("XXXXX@gmail.com", message);
logger.info('\r\nArray list: \r\n' + battcheckList );
}
See below the error
2023-11-13 11:44:09.486 [ERROR] [b.automation.script.javascript.stack] - Failed to **execute** script:
org.graalvm.polyglot.PolyglotException: ReferenceError: "ir" is not defined
at <js>.:program(<eval>:14) ~[?:?]
at org.graalvm.polyglot.Context.eval(Context.java:399) ~[?:?]
at com.oracle.truffle.js.scriptengine.GraalJSScriptEngine.eval(GraalJSScriptEngine.java:458) ~[?:?]
at com.oracle.truffle.js.scriptengine.GraalJSScriptEngine.eval(GraalJSScriptEngine.java:426) ~[?:?]
at javax.script.AbstractScriptEngine.eval(AbstractScriptEngine.java:262) ~[java.scripting:?]
at org.openhab.automation.jsscripting.internal.scriptengine.DelegatingScriptEngineWithInvocableAndAutocloseable.eval(DelegatingScriptEngineWithInvocableAndAutocloseable.java:53) ~[?:?]
at org.openhab.automation.jsscripting.internal.scriptengine.InvocationInterceptingScriptEngineWithInvocableAndAutoCloseable.eval(InvocationInterceptingScriptEngineWithInvocableAndAutoCloseable.java:78) ~[?:?]
at org.openhab.automation.jsscripting.internal.scriptengine.DelegatingScriptEngineWithInvocableAndAutocloseable.eval(DelegatingScriptEngineWithInvocableAndAutocloseable.java:53) ~[?:?]
at org.openhab.automation.jsscripting.internal.scriptengine.InvocationInterceptingScriptEngineWithInvocableAndAutoCloseable.eval(InvocationInterceptingScriptEngineWithInvocableAndAutoCloseable.java:78) ~[?:?]
at org.openhab.core.automation.module.script.internal.handler.ScriptActionHandler.lambda$0(ScriptActionHandler.java:71) ~[?:?]
at java.util.Optional.ifPresent(Optional.java:178) ~[?:?]
at org.openhab.core.automation.module.script.internal.handler.ScriptActionHandler.execute(ScriptActionHandler.java:68) ~[?:?]
at org.openhab.core.automation.internal.RuleEngineImpl.executeActions(RuleEngineImpl.java:1188) ~[?:?]
at org.openhab.core.automation.internal.RuleEngineImpl.runNow(RuleEngineImpl.java:1039) ~[?:?]
at org.openhab.core.automation.rest.internal.RuleResource.runNow(RuleResource.java:381) ~[?:?]
at org.openhab.core.automation.rest.internal.RuleResource.runNow(RuleResource.java:398) ~[?:?]
at jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[?:?]
at jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77) ~[?:?]
at jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[?:?]
at java.lang.reflect.Method.invoke(Method.java:568) ~[?:?]
at org.apache.cxf.service.invoker.AbstractInvoker.performInvocation(AbstractInvoker.java:179) ~[bundleFile:3.4.5]
at org.apache.cxf.service.invoker.AbstractInvoker.invoke(AbstractInvoker.java:96) ~[bundleFile:3.4.5]
at org.apache.cxf.jaxrs.JAXRSInvoker.invoke(JAXRSInvoker.java:201) ~[bundleFile:3.4.5]
at org.apache.cxf.jaxrs.JAXRSInvoker.invoke(JAXRSInvoker.java:104) ~[bundleFile:3.4.5]
at org.apache.cxf.interceptor.ServiceInvokerInterceptor$1.run(ServiceInvokerInterceptor.java:59) ~[bundleFile:3.4.5]
at org.apache.cxf.interceptor.ServiceInvokerInterceptor.handleMessage(ServiceInvokerInterceptor.java:96) ~[bundleFile:3.4.5]
at org.apache.cxf.phase.PhaseInterceptorChain.doIntercept(PhaseInterceptorChain.java:308) ~[bundleFile:3.4.5]
at org.apache.cxf.transport.ChainInitiationObserver.onMessage(ChainInitiationObserver.java:121) ~[bundleFile:3.4.5]
at org.apache.cxf.transport.http.AbstractHTTPDestination.invoke(AbstractHTTPDestination.java:265) ~[bundleFile:3.4.5]
at org.apache.cxf.transport.servlet.ServletController.invokeDestination(ServletController.java:234) ~[bundleFile:3.4.5]
at org.apache.cxf.transport.servlet.ServletController.invoke(ServletController.java:208) ~[bundleFile:3.4.5]
at org.apache.cxf.transport.servlet.ServletController.invoke(ServletController.java:160) ~[bundleFile:3.4.5]
at org.apache.cxf.transport.servlet.CXFNonSpringServlet.invoke(CXFNonSpringServlet.java:225) ~[bundleFile:3.4.5]
at org.apache.cxf.transport.servlet.AbstractHTTPServlet.handleRequest(AbstractHTTPServlet.java:298) ~[bundleFile:3.4.5]
at org.apache.cxf.transport.servlet.AbstractHTTPServlet.doPost(AbstractHTTPServlet.java:217) ~[bundleFile:3.4.5]
at javax.servlet.http.HttpServlet.service(HttpServlet.java:517) ~[bundleFile:4.0.4]
at org.apache.cxf.transport.servlet.AbstractHTTPServlet.service(AbstractHTTPServlet.java:273) ~[bundleFile:3.4.5]
at org.ops4j.pax.web.service.spi.servlet.OsgiInitializedServlet.service(OsgiInitializedServlet.java:102) ~[bundleFile:?]
at org.eclipse.jetty.servlet.ServletHolder.handle(ServletHolder.java:799) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.servlet.ServletHandler$ChainEnd.doFilter(ServletHandler.java:1656) ~[bundleFile:9.4.50.v20221201]
at org.ops4j.pax.web.service.spi.servlet.OsgiFilterChain.doFilter(OsgiFilterChain.java:100) ~[bundleFile:?]
at org.ops4j.pax.web.service.jetty.internal.PaxWebServletHandler.doHandle(PaxWebServletHandler.java:310) ~[bundleFile:?]
at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:143) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.security.SecurityHandler.handle(SecurityHandler.java:600) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:127) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.handler.ScopedHandler.nextHandle(ScopedHandler.java:235) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.session.SessionHandler.doHandle(SessionHandler.java:1624) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.handler.ScopedHandler.nextHandle(ScopedHandler.java:233) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1440) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.handler.ScopedHandler.nextScope(ScopedHandler.java:188) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:505) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.session.SessionHandler.doScope(SessionHandler.java:1594) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.handler.ScopedHandler.nextScope(ScopedHandler.java:186) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandler.java:1355) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:141) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.handler.ContextHandlerCollection.handle(ContextHandlerCollection.java:234) ~[bundleFile:9.4.50.v20221201]
at org.ops4j.pax.web.service.jetty.internal.PrioritizedHandlerCollection.handle(PrioritizedHandlerCollection.java:96) ~[bundleFile:?]
at org.eclipse.jetty.server.handler.gzip.GzipHandler.handle(GzipHandler.java:722) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:127) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.Server.handle(Server.java:516) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.HttpChannel.lambda$handle$1(HttpChannel.java:487) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.HttpChannel.dispatch(HttpChannel.java:732) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.HttpChannel.handle(HttpChannel.java:479) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.server.HttpConnection.onFillable(HttpConnection.java:277) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.io.AbstractConnection$ReadCallback.succeeded(AbstractConnection.java:311) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.io.FillInterest.fillable(FillInterest.java:105) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.io.ChannelEndPoint$1.run(ChannelEndPoint.java:104) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.util.thread.strategy.EatWhatYouKill.runTask(EatWhatYouKill.java:338) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.util.thread.strategy.EatWhatYouKill.doProduce(EatWhatYouKill.java:315) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.util.thread.strategy.EatWhatYouKill.tryProduce(EatWhatYouKill.java:173) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.util.thread.strategy.EatWhatYouKill.run(EatWhatYouKill.java:131) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.util.thread.ReservedThreadExecutor$ReservedThread.run(ReservedThreadExecutor.java:409) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.util.thread.QueuedThreadPool.runJob(QueuedThreadPool.java:883) ~[bundleFile:9.4.50.v20221201]
at org.eclipse.jetty.util.thread.QueuedThreadPool$Runner.run(QueuedThreadPool.java:1034) ~[bundleFile:9.4.50.v20221201]
at java.lang.Thread.run(Thread.java:833) ~[?:?]
2023-11-13 11:44:09.506 [ERROR] [internal.handler.ScriptActionHandler] - Script execution of rule with UID 'b0be2cd840' failed: org.graalvm.polyglot.PolyglotException: ReferenceError: "ir" is not defined
This is what I did for OH4:
var datetoday = new Date();
var numberofweek = datetoday.getDay();
/*
This will check the percentage of battery left and if it is low then email
Add the items to check into gBatterycheck group
*/
//DAILY REPORT
var percenttocheck = 15;
var heading="Openhab daily low sensor battery report"
//WEEKLY REPORT
//Only do on Sundays (numberofweek is 0)
if (numberofweek == 0){
var percenttocheck = 100;
var heading="Openhab weekly sensor battery report"
}
var email_message = "";
var i;
var sendmail="";
var i_list = items.getItem("gBatterycheck").members;
for (var i_index in i_list) {
i = i_list[i_index];
if(i.state <= percenttocheck){sendmail="YES"
// console.info('Test',i.label,i.state);
email_message = email_message + i.label + " " + i.state + "%" + "\r\n";
}
}
if(sendmail=="YES"){
message = "<H2>Sensor battery report <br>" +email_message +"</H2>" + "Percentage check was set at " +percenttocheck;
actions.get("mail", "mail:smtp:a514b96247").sendHtmlMail("you@gmail.com", heading, message );
console.info(email_message);
}
I have implemented this way:
var whatitis = "";
var percenttocheck = 15;
items.getItem("Batteries").members
.filter(function(batt) {return batt.state == percenttocheck ; } )
.forEach(function(batt) { whatitis = whatitis + " " + batt.label + " "; } );
if (whatitis != "") {
battcheckList.add(whatitis);
}
hey michaeljoos - i copy pasted and it works now something with the IR part of my own didnt work. from a logic perspective you use == vs <= which is my implementation. basically you run so that you get an alert when it become 15 right? but what happens if for some reason a battery drops more than than one unit? wont you miss the alert?
Did you try the code I posted?
I run it once a day.
It will send an email if the battery is less than or equal to 15% and on Sunday it sends a list of all the batteries in the battery group.
It is for OH4 which is what you said you are using.
hi Greg,
thanks for sending it through. I went through it. however your code is email based and i prefer the notification element offered by my code (it sends an alert to the openhab app) - so i just adjusted my own with the part offered by michaeljoos
just playing with the logs now to wrap up.
Ok, thanks for the reply.
You can put your notification in the code below instead of using email.
Anyway if it works for you that is good.
For future readers of this thread, there is a rule template on the marketplace that handles this use case.
configuration: {}
triggers: []
conditions: []
actions:
- inputs: {}
id: "1"
configuration:
type: application/javascript;version=ECMAScript-2021
script: >
var {alerting} = require('rlk_personal');
var logger = log('Low Battery');
alerting.sendAlert('The following batteries are below 10%: ' + this.threshItemLabels, logger);
type: script.ScriptAction
Parameter | Purpose | Value |
---|---|---|
Triggering Group | Group with all the battery level Items | AllBatteries |
Threshold State | The threshold value to compare against, if the value is < this the alert rule is called. The rule handles UoM | 15 % |
Comparison Operator | If Item State <operator> Threshold is true, the alert rule is called. |
< |
Alert Rule | UID of the rule created in step 2. | battery_alert |
Do Not Disturb | Do not call the alert rule between these two times, wait until the end of the time period. This prevents alerts from being sent over night. | Start: 22:00 , End: 08:00 |
Rate Limit | Do not call the alert rule more often than this. For example, don’t alert more than once every eight hours. | PT8H |
All the other properties are left at the defaults.
This rule template is pretty handy. I use it to send an alert when a door is left open too long, when a battery goes low and needs to be replaced soon, a sensor stops reporting, a service goes offline, and as a motion sensor timer.