The EPIC Time Conversion and Manipulation Thread!

Just wanted to say thanks for this thread, @finity. I find myself referring to it frequently. Maybe you should consider creating a version of it to put somewhere in the HA docs.

2 Likes

Thanks for the kind words.

If I get the time maybe I’ll give your suggestion a try.

1 Like

sorry, need some guidance please.
Im in the UK (So UTC+1 at the moment) and i have an attribute in my sensor thats showing as UTC.
So it shows as being 00:05 when it was actually 01:05

{{ states.vacuum.rover.attributes.clean_start }}
value = 2019-07-27 00:00:05

how do i change this value to add 60mintues to it, or is there more of a global setting that would automatically pass the correct value into the source data?

You need the sensor to include the time zone in the string then it will display correctly. Anything without an explicit time zone definition is treated as being in local time so the best solution is to ensure the sensor includes the TZ.

Hi, I’m trying to build an if-then test to get something done only when now() is not inside a specific time interval of the day. This is my most recent, but still failed attempt:

{%- set t1 = as_timestamp(now())| timestamp_custom('%H:%M') %}
{% if strptime(t1, '%H:%M') < strptime('09:30', '%H:%M') and
      strptime(t1, '%H:%M') > strptime('12:30', '%H:%M') %}
  Do_Something
{%- endif %}

Can you help me out?

I think it’s not the time manipulation that isn’t working. It’s the logic.

you will never have a time now that is both before 09:30 and after 12:30 at the same time.

I think for how you describe the desired result that you will need to change the “and” to an “or”.

That way if now is before 09:30 it will be true or if now is after 12:30 it will be true but not in between.

You are of course absolutely right. Funny how I got stuck in my own mind-loop. I should have thought of that. Anyway, I solved it by using if not :wink:
But still, it puzzles me that I had to use a temporary varible (t1) in order to get HA to tolerate the syntax.

Yeah, I’m no expert at any of this. I spent the better part of 3 or 4 days working on the content of the first posts here to try to understand it. TBH, I still have to go back to my notes when working with the more complex stuff.

but technically I don’t think have to use a variable. You could just substitute the stuff after the “set t1 =” part into everywhere you have t1 in the rest of the template. but that would get really messy. it’s cleaner to use that variable.

and also to make it a bit simpler you didn’t have to convert now to a timestamp. You could have gone straight to a string then when you use strptime it would convert the string to a time object for the comparison:

{%- set t1 = now().strftime('%H:%M') %}
{% if strptime(t1, '%H:%M') < strptime('09:30', '%H:%M') or
      strptime(t1, '%H:%M') > strptime('12:30', '%H:%M') %}
  Do_Something
{%- endif %}

Interesting. But I tried to substitute everything after the “set t1=” directly into the if statement, but HA complained about token irregularities and what not.
I must say that I do find these things overly complex. And finding documentation without presumption that your are already a python or java programmer with 10 years experience, makes it even harder. Take for instance the strftime and strptime operators (I don’t even know if calling them operators is correct?), I assume that someone “made” up these two words with something logical in mind. So probably str means string, and time is of course obvious, but the letter ‘f’ and ‘p’ stuck in between there? What do those mean? It would have been nice to know. it makes it easier to remember if you know what meaning or words these letters represent… just a sigh :roll_eyes:
Anyway, thanks for your suggestion. I’ll try it later.For now, at least, it works as-is.

You definitely have to make sure the sysntax is right with no missing (), {} or quotes.

here it is without the t1 and it is working in the template editor:

as far as the p & f I really don’t know where they came from but it helps me remember which is which using strftime = “string from time” and strptime = not string from time :slightly_smiling_face: so it’s “time from string”.

That’s a good one :slightly_smiling_face:
Thank you so much for your assistance. However, sometimes I do not understand the do’s and dont’s of the template editor. It fails on this one:

{% as_timestamp(now())| timestamp_custom('%H:%M') %}

saying that as_timestamp is invalid, although we know it is valid. I was expecting the above to yield the current time as output.

It fails because you aren’t giving it a directive. the {% …%} requires you tell it to do something. Like set, if-else, etc.

this will not give an error but it won’t output anything to the screen:

{% set t = as_timestamp(now())| timestamp_custom(’%H:%M’) %}

it is just internally setting the variable t to the value of (as_timestamp(now())| timestamp_custom(’%H:%M’) )

if you just want to show an output of what’s happening inside the brackets you use the {{…}} notation.

so if you change the above to this:

{{ as_timestamp(now())| timestamp_custom('%H:%M') }}

it should work

Thank you so much. You’ve yet again solved one of the great syntax mysteries.
( I wonder what pleasure the creator had in making things so complex and completely unlogical) :shushing_face:

Who ? you mean balloob ? :rofl:

finity: could you have a look at “Chicken Eggs!” ??? - I think it needs your time wizzardry skills and I think I’m going to have to read this thread twice a day and practice for a month to get my head round this.
I don’t think it needs Phil’s “Sun Enhancement” just subtract one time from another, subtract a few more hours and then output as minutes.

I have no idea what that is. Is it another thread here?

And to clarify I’m not “wizard”. I barely figure this stuff out on my best day without looking at my notes and playing around in the template editor.

In the land of the blind, the one eyed man is king.

Yeah, it’s a thread

1 Like

Ok, I’ve put my two cents in there now.

Also I’m not sure that you noticed but I made the first posts able to be fully copied into the template editor so you can copy them over and play with them to get different results.

In milliseconds - 1544817447000 (which is another can of worms).

Yes, the time stated should be the local time and the bit on the end simply tells you the relationship of that time string to UTC.

Coming a bit late to this but the best way I found of visualizing this, is to think of time & date as a number. Wherever you are on the globe, everyone is at the same instantaneous number - the UNIX timestamp - UTC.

The number (or TZ) on the end of the string representation, tells you what that number string is relative to UTC (or GMT or Zulu time) where a minus is behind (midday is later) and plus is ahead (midday is earlier) than if you were on UTC.

So if your timezone is -5, you are 5 hours behind so when UTC is 19:00, local time to you is 14:00 but in ISO format that is 14:00-05:00 not 19:00-05:00

Without a timezone, the time & date string is always assumed to be local.

image

from Date Time Converter Online - DenCode

HTH

BTW great tutorial on time and HA!

1 Like

Great explanation!

Would anyone have a way of explaining how to use the input_datetime component for comparison?

Specifically just the has_date: false/has_time: true usage.

When trying to use the timestamp attribute in this configuration, it only produces the number of seconds from midnight of the current day when used in templates which doesn’t play well with as_timestamp’s use of the Unix starting point.

I’m trying to use the time entry at the input_datetime component in the frontend to trigger an action everyday at that time.

unfortunately because of the nature of the timestamp you won’t be able to use as_timestamp() with an input_datetime that doesn’t have the date part.

As far as I know…

You would have to figure out a way to add the date to it. But if you are going to that trouble it would be easier to just use an input_datetime that has both date and time and be done with it.

However, if I understand your use case you should just be able to use the state of the time-only input_datetime and do a compare to the starting time as a string.

Something like (using one of my time only entities):

trigger:
  - platform: template
    value_template: >
      {{ states('input_datetime.cpap_ind_start_time') == '09:53:27' }}

ex