Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Missing timezone in metadata date can lead to wrong date in url #1069

Closed
zwippie opened this issue May 9, 2013 · 36 comments
Closed

Missing timezone in metadata date can lead to wrong date in url #1069

zwippie opened this issue May 9, 2013 · 36 comments
Milestone

Comments

@zwippie
Copy link

zwippie commented May 9, 2013

Starting with a fresh new Jekyll site with no modifications, I noticed that the first auto-generated post got the wrong page date when served. It looks like a missing timezone in the posts metadata can lead to the generated url being one day off when the time is close enough to midnight.

Metadata of file /_posts/2013-05-09/welcome-to-jekyll.markdown:


---
layout: post
title:  "Welcome to Jekyll!"
date:   2013-05-09 22:39:53
categories: jekyll update

---

This leads to the post having url /jekyll/update/2013/05/10/welcome-to-jekyll.html, which can be explained by me being in a timezone with offset +0200.

The url I expected to see was /jekyll/update/2013/05/09/welcome-to-jekyll.html.

Changing or removing the time part of the metadata (or adding timezone info) fixes the problem as expected, but it left me puzzled for a moment.

@zachgersh
Copy link

by chance, what is your system timezone set to?

@parkr
Copy link
Member

parkr commented May 10, 2013

He says it's "+0200" above, which is my timezone as well. Central European.

@zachgersh
Copy link

Didn't you add specification of timezone to support just this issue?

@parkr
Copy link
Member

parkr commented May 10, 2013

Yes, but there's an edgecase: if you don't specify the timezone when making posts and pages, it assumes it's UTC, I guess.

@zwippie
Copy link
Author

zwippie commented May 10, 2013

I'm sorry, I should have added that bit of information: System timezone in /etc/timezone is Europe/Amsterdam. To my best knowledge, Ruby uses that info. Also, adding the timezone to the config file did not change the situation. So what parkr says seems to be the case: the time/date is converted to UTC where it probably should not.

@parkr
Copy link
Member

parkr commented May 10, 2013

i will look into this more, probably something i'd want to make into the gh pages release //cc @benbalter

@zachgersh
Copy link

So @parkr and I took a look at this and there seems to be nothing wrong with how the time / date are parsed (it always ends up in your local timezone).

I am not sure how your url would have rolled over like that. We checked to make sure the time didn't default to UTC or have any wonkiness.

Doesn't seem to be anything wrong at present with it.

@zwippie
Copy link
Author

zwippie commented May 12, 2013

@zachgersh I agree with you that no strange things seem to happen in ie. post.rb when it comes to parsing and formatting dates. If no one else experiences this one-day-off error then I guess there is something wrong on my side.

For the sake of completeness:

Linux Debian 6 kernel 2.6.32-5-amd64
rvm 1.15.7
ruby 1.9.3p194
Jekyll 1.01

@zachgersh
Copy link

Well, I don't want to claim it is not there just because I didn't experience it 😄

The only thing I could possibly think of is daylight savings having something to do with it but that feels like a stretch.

Just out of curiosity can you double check in your IRB that your offset is what you expect it to be from Ruby?

@zachgersh
Copy link

I think we can close this for now @parkr.

@zwippie please reopen if you stumble across this and have new info.

@parkr parkr closed this as completed May 13, 2013
@allxiao
Copy link

allxiao commented Aug 2, 2013

I've experienced this issue on my first taste of Jekyll today.
The default timezone of my Mac OS X system is set to CST (+0800).

➜  ~  date
Fri Aug  2 17:29:51 CST 2013

The generated example post (by jekyll new blog) have metadata as followed:

---
layout: post
title:  "Welcome to Jekyll!"
date:   2013-07-30 17:57:28
categories: jekyll update
---

And after running jekyll serve, the URL for the post is

http://localhost:4000/jekyll/update/2013/07/31/welcome-to-jekyll.html

If I edit the date of the post in metadata to 2013-07-30 17:57:28+0800, everything works fine.

It seems that Jekyll parses the date in metadata with default timezone set to UTC (if no timezone info is specified in the date string), but then generates the link according to the system default timezone.

It would be better either 1) to generate system timezone aware date string in metadata when running jekyll new blog or 2) to parse the date in metadata with default timezone set to system timezone.

Thanks~

@parkr
Copy link
Member

parkr commented Aug 5, 2013

Adding the timezone is a great idea! We also want to create generators which create new posts - we'll add it there as well.

@parkr
Copy link
Member

parkr commented Aug 6, 2013

Rel: #1148.

@makkes
Copy link

makkes commented Sep 3, 2013

Having to add the timezone to the date metadata is pretty awful. Why do I have to specify it in _config.yml, then? Why not just assume every date without a specified timezone to have the one specified in _config.yml?

@parkr
Copy link
Member

parkr commented Sep 4, 2013

We can't make that assumption :( What if we provided a generator like in #1148?

@robkorv
Copy link

robkorv commented Oct 7, 2013

Hmm, breaking my head over this ;)
What I would expect is that it doesn't convert the time at all. Only when I explicitly tell jekyll that it should.

When I use date : 2013-08-04 22:14:12 on my machine it shouldn't convert it to 2013-08-05 00:14:12, because I'm on UTC+2.

I'm reading above that this shouldn't happen, is there something I'm missing?

@fugalh
Copy link

fugalh commented Dec 8, 2013

I found that a bunch of my dates were off after an import even though it had given timezones. Changing date: YYYY-MM-DD HH:MM:ss.sssssss -08:00 to date: 'YYYY-MM-DD HH:MM:ss.sssssss -08:00' (note the quotes) corrected it. So try quotes and see if that makes things less confusing. sed -i "s/^date: \(2.*\)$/date: '\1'/" _posts/*

Not sure if this is illegal yaml, a yaml parsing problem, or something after

@gregRV
Copy link

gregRV commented Aug 18, 2014

Very helpful, thanks for posting @zwippie

dnozay added a commit to dnozay/dnozay.github.io that referenced this issue Nov 5, 2014
@13protons
Copy link

I'm experiencing this as an issue too, and it definitely feels broken. I'd only expect the output of the date filter to match UTC if I were, in fact, on UTC +0000. I didn't notice this when working just with dates, but it was immediately apparent when trying to work with hours.

IRB tells me I have my time set correctly

2.2.0 :001 > Time.now
 => 2015-03-06 11:57:35 -0500 

_config.yml has the timezone set correctly:

timezone: America/Detroit
markdown: kramdown
encoding: utf-8
...

Post front matter has a dates array in local time

dates:
  - start: 2015-3-23 18:00:00
    end: 2015-3-23 21:00:00
  - start: 2015-3-25 18:00:00
    end: 2015-3-25 21:00:00

No funky tricks in the date rendering:

{% for date in event.dates %}
  <li>{{ date.start | date: '%b %d, %Y  %l:%M %P' }} - {{ date.end | date: ' %l:%M %P' }}</li>
{% endfor %}

And the rendered HTML shows times in UTC. ( that should be 6pm (18:00) - 9pm(21:00), rather than 2pm and 5pm respectively ).

Mar 23, 2015 2:00 pm - 5:00 pm
Mar 25, 2015 2:00 pm - 5:00 pm

Miraculously, jekyll does correctly calculate daylight savings time by only rending the UTC time as -0400 instead of the usual -0500 for my part of the world.

ps - jekyll 2.5.3

@13protons
Copy link

Update: setting my timezone to Africa/El_Aaiun in _config.yml in the meantime to avoid adding the offset to each date in each post. Apparently that will give me the same DST rules as US Eastern time, and output my times as expected.

@parkr
Copy link
Member

parkr commented Mar 6, 2015

@alanguir This behaviour is per safe_yaml and Time.parse when you give us a string. We set the TZ variable before these methods are executed, but if you have no offset, Ruby has no way to know what that time should be so it just forgets about it and assigns it to UTC at all times (IIRC). Going back and adding offsets is highly recommended. It can be a pain, but it's important, otherwise you have over 24 times in one (one per timezone), so there's no way to know what exact moment in time you're looking for.

@13protons
Copy link

@parkr I understand how this could cause unexpected results if I'm writing my times assuming UTC +5, and jekyll has a build script that runs when I deploy on a heroku server living in UTC +8, but why ignore the explicit timezone setting in the config file? That seems like a perfectly good way to know what the time should be.

What is the timezone config option used for if not helping jekyll parse dates at build time?

@parkr
Copy link
Member

parkr commented Mar 7, 2015

What is the timezone config option used for if not helping jekyll parse dates at build time?

All it does is set $TZ in your Ruby environment. If you have no timezone data, it doesn't add anything in (it doesn't default to your local timezone). It makes me sad. I wrote a blog post about this sort of thing (though not this exact thing). Timezones in Ruby aren't great.

Think of it like excluded bits of data without a default.

@willnorris
Copy link
Contributor

yep, I ran into the crappy support for timezones in Ruby when I switched to Jekyll too. In my case, I very specifically want to preserve the timezone of when a post was written, and display that on my site (for example, compare by-lines here vs here). For me, that additional bit of data is meaningful.

I do this by ensuring that I always specify dates as strings in my frontmatter (otherwise the yaml module will "helpfully" parse them as Time objects), and then use a custom jekyll plugin to parse the post date as a DateTime, which preserve timezone information. Not sure if that is helpful to others in this thread, but just wanted to point out one way I've worked around ruby's TZ shortcomings.

@parkr
Copy link
Member

parkr commented Mar 7, 2015

@willnorris Do you see a bugfix path for safe_yaml or Jekyll in this regard?

@willnorris
Copy link
Contributor

@parkr I've never actually looked closely at what safe_yaml does before, but now this does make sense: date.rb. It parses dates as DateTime, but then converts them to Time and always returns the value in local time. In my opinion, this is totally the wrong thing to do since (if I'm correctly understanding how time is handled in ruby) you're throwing away any TZ data that was there. I imagine having safe_yaml return the DateTime object would be a pretty major breaking change for them and not realistic. The only thing Jekyll could do is basically what I'm doing... if a date is specified as a string, then you could additionally parse it as a DateTime and preserve the TZ info that way.

@parkr
Copy link
Member

parkr commented Mar 7, 2015

It parses dates as DateTime, but then converts them to Time and always returns the value in local time. In my opinion, this is totally the wrong thing to do since (if I'm correctly understanding how time is handled in ruby) you're throwing away any TZ data that was there.

So they fixed this in Ruby 2.2.0, which broke Jekyll's expectations that it'd be in your local timezone (that's what my blog post is about).

I imagine having safe_yaml return the DateTime object would be a pretty major breaking change for them and not realistic.

@dtao, how would you feel about this?

if a date is specified as a string, then you could additionally parse it as a DateTime and preserve the TZ info that way.

Right now we use Time.parse – should we switch to using DateTime.parse?

@willnorris
Copy link
Contributor

It parses dates as DateTime, but then converts them to Time and always returns the value in local time. In my opinion, this is totally the wrong thing to do since (if I'm correctly understanding how time is handled in ruby) you're throwing away any TZ data that was there.

So they fixed this in Ruby 2.2.0, which broke Jekyll's expectations that it'd be in your local timezone (that's what my blog post is about).

Oh, interesting.. so I somehow missed that. So now this means that ruby 2.2 is preserving the TZ information correctly, but now it's Jekyll that is throwing it away by always calling localtime 😞 I know that this is how Jekyll has always worked historically and perhaps has some assumptions built in for this, but it still makes me sad because we're throwing away the data. If a post date is specified without TZ information, then sure treat it as localtime. But if an author has taken the effort to specify the TZ in the post date, then it seems very unfortunate that we don't respect and preserve that.

if a date is specified as a string, then you could additionally parse it as a DateTime and preserve the TZ info that way.

Right now we use Time.parse – should we switch to using DateTime.parse?

Maybe? I'm not sure where else Time and DateTime differ and what problems this could potentially introduce. I seem to recall that some of our date-related liquid filters choked on a DateTime, but don't remember fully.

@pathawks
Copy link
Member

pathawks commented Mar 7, 2015

But if an author has taken the effort to specify the TZ in the post date, then it seems very unfortunate that we don't respect and preserve that.

👍 This has also often bothered me.

@13protons
Copy link

To solve my specific issue, I wrote a tiny Jekyll filter that will apply your local timezone offset to a custom front matter date. Be careful when using with something like a heroku deploy script - I haven't tested there, although tzinfo is explicitly setting the timezone based on Jekyll config:

https://gist.github.com/alanguir/72c6d22d95f3ed80a511

@sumdog
Copy link

sumdog commented May 12, 2015

I just started using Jeykll and just noticed this. I have converted posts from a legacy/proprietary system where each post had a date and a time (but no timezone). Everything was a full day off (My localtime is set to Australia/Melbourne).

I feel like if I don't specify a timezone, than those are the dates/times I want to use when displaying to the user. They really shouldn't go through any conversion at all. (and even if I do specify a timezone...there should really only be a conversion if the _config.yml has a different timezone). We're talking about static content here; not content that changes depending on the connecting browser.

There should be an option to disable any timezone alteration entirely, although judging from the comments, I'm not sure if that's entirely possibly if this is depending on the underlying YAML engine.

@envygeeks
Copy link
Contributor

This is more than likely a problem with the object we use rather than the way we use the object, DateTime sucks when an explicit timezone isn't supplied and if I remember we are using DateTime objects?

@jaypinho
Copy link

Just ran into the same problem here as well.

Posted something at 1:22 AM New York time (UTC - 4 hours) and put in the data without time zone as '2015-05-22 01:22:00' (assuming it would show up correctly since I have 'timezone: America/New_York' in my _config.yml file), but the URL slug and the post date both show up as the day before. This doesn't seem like the type of behavior you'd expect by default.

davep added a commit to davep/davep.github.com that referenced this issue Jun 18, 2015
Also noticed that Jekyll has some issues with timezones. cf
jekyll/jekyll#1069
@chemoish
Copy link

Trying to follow years of timezone posts,,, It would be nice to be able to specify a time and have the timezone modify that time appropriately on compilation.

2017-02-12 14:30:00 + America/Los_Angeles = 2017-02-12 14:30:00 -0800
2017-04-02 14:30:00 + America/Los_Angeles = 2017-04-02 14:30:00 -0700

/shrug

e28eta added a commit to e28eta/e28eta.github.io that referenced this issue Feb 3, 2017
Setting the _config timezone didn't solve the issue. Maybe I should add
timezone to all dates in all posts, but I'm going to try this first.
I'm not concerned about capturing the local time (I think).

Possibly related: jekyll/jekyll#1069
cardoe added a commit to applewoodhoa/applewoodhoa.github.io that referenced this issue Nov 3, 2018
Following jekyll/jekyll#1069 to attempt to fix
the incorrect dates
@scottdorman
Copy link

This issue seems to still exist. Look at https://scottdorman.github.io/2015/05/29/introducing-jquery-gotop/ https://scottdorman.github.io/2015/05/28/introducing-jquery-gotop/as an example. The date portion of the link gets set to 2015/05/29 even though the front matter has date: '2015-05-28 23:23:39.00000000 -05:00' and my _config.yml has timezone: America/New_York. I have tried the front matter date in several variations and none of them seem to make any difference.

This issue affects a bunch of pages for me and also has an impact on some automatic redirection logic I have set up since the date portions of the links don't match up.

If there's something I need to change, I'm all for changing it but it seems like this is an issue with how Jekyll is parsing the date front matter variable to generate the URL. If the date has timezone information provided (which mine does) it should always use that timezone.

Interestingly enough, as I was writing this I decided to try setting the date to the corresponding UTC time (2015-05-29 03:23:39) which still had no effect. However, when I set the date back to the original and removed the time zone portion, it was generated with the correct date in the URL. This behavior seems widly inconsistent, as other pages seem to work just fine with the time zone in the date (as a string) (see https://github.com/scottdorman/scottdorman.github.io/blob/master/_posts/2018/2018-08-18-saving-bootstrap-component-state.md as an example). It seems like where things start to go wrong is when the time approaches that roll-over period in UTC (so, for my time zone any dates earlier than 19:00:00 generate with the correct date and anything after would appear to generate with the wrong date).

@ashmaroli
Copy link
Member

@scottdorman This is a very old ticket.
Please open a new ticket providing us with the relevant information about the issue and your Jekyll environment.

@jekyll jekyll locked and limited conversation to collaborators Feb 26, 2019
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests