[SOLVED] Converting minutes into hour

Tags: #<Tag:0x00007faeda61e780> #<Tag:0x00007faeda61e640> #<Tag:0x00007faeda61e500>

Evening,

I currently display total runtime of a device in minutes in the following item on sitemap.

Number MyDevice3_Time_Day     "Total Runtime Today [%d]"   

If would be nice if I could convert minutes into hours. What`s the best way to achieve it ? Can anyone suggest solution please.

Assuming you don’t want to modify the actual Number state, you could use a JS transform in the Item label [ ] formatting part.

1 Like

I use a javascript transform to that effect:

/*
Javascript transform function to change the number
of minutes of CPU time from the System Info Binding
into a more readable format
eg: 2365 into '1 day 15 hours 25 minutes

The item in the items file is defined as follow:
Number LocalComputer_Cpu_SystemUptime "[JS(CPUTime.js):%s]"
and linked via PaperUI to the System uptime channel
of the System Info Thing
*/

(function(i) {
    if (i == 'NULL') { return i; }
    if (i == '-') { return 'Undefined'; }
    var val = parseInt(i); // The value sent by OH is a string so we parse into an integer
    var days = 0; // Initialise variables
    var hours = 0;
    var minutes = 0;
    if (val >= 1440) { // 1440 minutes in a days
        days = Math.floor(val / 1440); // Number of days
        val = val - (days * 1440); // Remove days from val
    }
    if (val >= 60) { // 60 minutes in an hour
       hours = Math.floor(val /60); // Number of hours
        val = val - (hours * 60); // Remove hours from val
    }
    minutes = Math.floor(val); // Number of minutes

    var stringDays = ''; // Initialse string variables
    var stringHours = '';
    var stringMinutes = '';
    if (days === 1) {
        stringDays = '1 day '; // Only 1 day so no 's'
    } else if (days > 1) {
        stringDays = days + ' days '; // More than 1 day so 's'
    } // If days = 0 then stringDays remains ''

    if (hours === 1) {
        stringHours = '1 hour '; // Only 1 hour so no 's'
    } else if (hours > 1) {
        stringHours = hours + ' hours '; // More than 1 hour so 's'
    } // If hours = 0 then stringHours remains ''

    if (minutes === 1) {
        stringMinutes = '1 minute'; // Only 1 minute so no 's'
    } else if (minutes > 1) {
        stringMinutes = minutes + ' minutes'; // More than 1 minute so 's'
    } // If minutes = 0 then stringMinutes remains ''

    var returnString =  stringDays + stringHours + stringMinutes
    return returnString.trim(); // Removes the extraneous space at the end

})(input)
1 Like

Thank you. Personally I`m not very familiar with transform at the moment, assuming will need to create new transform file or perhaps add to the exist one ?
This is what I can see in transform folder right now. Should I copy this script from above and paste it inside en file ? How would I integrate it with my item then ?

en

No, for each transform you will make a new file. ilename of your choice, the .xxx extension tells thesystem what kind of transform, since there are several.
You might choose minstohours.js for example.

A transform can be shared by many Items that you want to process in the same way.

Thanks for explanation this is really helpful.

So I did created the separate file called minstohours.js

minstohours

I renamed my item definition to

Number MyDevice3_Time_Day     "Total Runtime Today [JS(minstohours.js):%d]"   <line-increase>   (Restore)

Is the restart of OH required at this point ? Still seeing time in minutes at the moment so probably made mistake somewhere along :thinking:

EDIT: I tried restart minute ago but that didnt made any difference. Looking at the log file can see the following info, its complaining about this .js file for some reason.

Caused by: java.io.FileNotFoundException: /etc/openhab2/transform/minstohours.js (No such file or directory)
	at java.io.FileInputStream.open0(Native Method) ~[?:?]
	at java.io.FileInputStream.open(FileInputStream.java:195) ~[?:?]
	at java.io.FileInputStream.<init>(FileInputStream.java:138) ~[?:?]
	at java.io.FileInputStream.<init>(FileInputStream.java:93) ~[?:?]
	at org.eclipse.smarthome.transform.javascript.internal.JavaScriptTransformationService.transform(JavaScriptTransformationService.java:70) ~[?:?]

That doesn’t seem to be looking in the same place as your screenshot. I don’t know openhabian to say what is up.

The “type” column is showing “MAP file”, instead of “JS file” or “Javascript file”. Could you have a hidden extension giving it the wrong file name?

2 Likes

Good spot - indeed there is incorrect file extension. I will amend configs it as soon I get back home later this evening.

This javascript from @vzorglub works well, problem solved many thanks.

Evening All,

I have recently upgraded to OH 2.4. Looking in the log file I can see many warnings related to my javascript transform function converting minutes into hours/days.

2019-07-02 23:31:46.068 [WARN ] [rest.core.item.EnrichedItemDTOMapper] - Failed transforming the state '85.0' on item 'MyDevice4_Time_Day' with pattern 'JS(minstohours.js):%d': Cannot format state '85.0' to format '%d'
2019-07-02 23:31:46.079 [WARN ] [rest.core.item.EnrichedItemDTOMapper] - Failed transforming the state '240.0' on item 'MyDevice1_Time_Day' with pattern 'JS(minstohours.js):%d': Cannot format state '240.0' to format '%d'
2019-07-02 23:31:46.090 [WARN ] [rest.core.item.EnrichedItemDTOMapper] - Failed transforming the state '0' on item 'MyDevice5_Time_Active' with pattern 'JS(minstohours.js):%d': Cannot format state '0' to format '%d'
2019-07-02 23:31:46.093 [WARN ] [rest.core.item.EnrichedItemDTOMapper] - Failed transforming the state '85.0' on item 'MyDevice2_Time_Day' with pattern 'JS(minstohours.js):%d': Cannot format state '85.0' to format '%d'
2019-07-02 23:31:46.096 [WARN ] [rest.core.item.EnrichedItemDTOMapper] - Failed transforming the state '11.0' on item 'MyDevice5_Time_Day' with pattern 'JS(minstohours.js):%d': Cannot format state '11.0' to format '%d'
2019-07-02 23:31:46.106 [WARN ] [rest.core.item.EnrichedItemDTOMapper] - Failed transforming the state '240.0' on item 'MyDevice1_Time_Day' with pattern 'JS(minstohours.js):%d': Cannot format state '240.0' to format '%d'
2019-07-02 23:31:46.153 [WARN ] [rest.core.item.EnrichedItemDTOMapper] - Failed transforming the state '0' on item 'MyDevice5_Time_Active' with pattern 'JS(minstohours.js):%d': Cannot format state '0' to format '%d'
2019-07-02 23:31:46.170 [WARN ] [rest.core.item.EnrichedItemDTOMapper] - Failed transforming the state '11.0' on item 'MyDevice5_Time_Day' with pattern 'JS(minstohours.js):%d': Cannot format state '11.0' to format '%d'
2019-07-02 23:31:46.200 [WARN ] [rest.core.item.EnrichedItemDTOMapper] - Failed transforming the state '240.0' on item 'MyDevice1_Time_Day' with pattern 'JS(minstohours.js):%d': Cannot format state '240.0' to format '%d'
2019-07-02 23:31:46.209 [WARN ] [rest.core.item.EnrichedItemDTOMapper] - Failed transforming the state '0' on item 'MyDevice5_Time_Active' with pattern 'JS(minstohours.js):%d': Cannot format state '0' to format '%d'
2019-07-02 23:31:46.213 [WARN ] [rest.core.item.EnrichedItemDTOMapper] - Failed transforming the state '11.0' on item 'MyDevice5_Time_Day' with pattern 'JS(minstohours.js):%d': Cannot format state '11.0' to format '%d'

I can see that things has changed in new OH version, so was expecting some teething problems at the start. Would you be able to tell me if I need to changing anything on my script to get it working as I can`t figured that out yet.

The output of a JS transform is always a string. I don’t know why it used to work with format %d and now does not, but try %s instead.

@rossko57 changed output to string and working again. No sure either why it used to work with format %d :+1:

I’ve only just realised that your JS returns something like "2 hours 10 minutes", which certainly is a string and won’t format nicely using %d for decimal number.

I was worrying it was some regression bug, but in fact it’s an enhancement to report instead of failing silently. Luckily it just passes the whole string along despite failure, I guess.