Support both tzinfo v1 and v2 alongwith non-half hour offsets. (#8880)
Merge pull request 8880
This commit is contained in:
parent
956701f96c
commit
9c9cf3e82b
2
Gemfile
2
Gemfile
|
@ -86,7 +86,7 @@ group :jekyll_optional_dependencies do
|
||||||
# Windows and JRuby does not include zoneinfo files, so bundle the tzinfo-data gem
|
# Windows and JRuby does not include zoneinfo files, so bundle the tzinfo-data gem
|
||||||
# and associated library
|
# and associated library
|
||||||
platforms :jruby, :mswin, :mingw, :x64_mingw do
|
platforms :jruby, :mswin, :mingw, :x64_mingw do
|
||||||
gem "tzinfo", "~> 1.2"
|
gem "tzinfo", ENV["TZINFO_VERSION"] if ENV["TZINFO_VERSION"]
|
||||||
gem "tzinfo-data"
|
gem "tzinfo-data"
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
12
appveyor.yml
12
appveyor.yml
|
@ -13,6 +13,12 @@ build: off
|
||||||
environment:
|
environment:
|
||||||
BUNDLE_WITHOUT: "benchmark:development"
|
BUNDLE_WITHOUT: "benchmark:development"
|
||||||
matrix:
|
matrix:
|
||||||
|
- RUBY_FOLDER_VER: "26"
|
||||||
|
TZINFO_VERSION: "~> 1.2"
|
||||||
|
TEST_SUITE: "test"
|
||||||
|
- RUBY_FOLDER_VER: "26"
|
||||||
|
TZINFO_VERSION: "~> 2.0"
|
||||||
|
TEST_SUITE: "test"
|
||||||
- RUBY_FOLDER_VER: "26"
|
- RUBY_FOLDER_VER: "26"
|
||||||
TEST_SUITE: "test"
|
TEST_SUITE: "test"
|
||||||
- RUBY_FOLDER_VER: "26"
|
- RUBY_FOLDER_VER: "26"
|
||||||
|
@ -21,6 +27,12 @@ environment:
|
||||||
TEST_SUITE: "profile-docs"
|
TEST_SUITE: "profile-docs"
|
||||||
- RUBY_FOLDER_VER: "26"
|
- RUBY_FOLDER_VER: "26"
|
||||||
TEST_SUITE: "memprof"
|
TEST_SUITE: "memprof"
|
||||||
|
- RUBY_FOLDER_VER: "26"
|
||||||
|
TZINFO_VERSION: "~> 1.2"
|
||||||
|
TEST_SUITE: "cucumber"
|
||||||
|
- RUBY_FOLDER_VER: "26"
|
||||||
|
TZINFO_VERSION: "~> 2.0"
|
||||||
|
TEST_SUITE: "cucumber"
|
||||||
- RUBY_FOLDER_VER: "26"
|
- RUBY_FOLDER_VER: "26"
|
||||||
TEST_SUITE: "cucumber"
|
TEST_SUITE: "cucumber"
|
||||||
|
|
||||||
|
|
|
@ -121,22 +121,14 @@ While 'new' blogs created with Jekyll v3.4 and greater, will have the following
|
||||||
sites *will* have to update their `Gemfile` (and installed gems) to enable development on Windows:
|
sites *will* have to update their `Gemfile` (and installed gems) to enable development on Windows:
|
||||||
|
|
||||||
```ruby
|
```ruby
|
||||||
# Windows does not include zoneinfo files, so bundle the tzinfo-data gem
|
# Windows and JRuby does not include zoneinfo files, so bundle the tzinfo-data gem
|
||||||
gem 'tzinfo-data', platforms: [:mingw, :mswin, :x64_mingw, :jruby]
|
# and associated library.
|
||||||
|
platforms :mingw, :x64_mingw, :mswin, :jruby do
|
||||||
|
gem "tzinfo", ">= 1", "< 3"
|
||||||
|
gem "tzinfo-data"
|
||||||
|
end
|
||||||
```
|
```
|
||||||
|
|
||||||
<div class="note warning">
|
|
||||||
<h5>TZInfo 2.0 incompatibility</h5>
|
|
||||||
<p>
|
|
||||||
Version 2.0 of the TZInfo library has introduced a change in how timezone offsets are calculated.
|
|
||||||
This will result in incorrect date and time for your posts when the site is built with Jekyll 3.x on Windows.
|
|
||||||
</p>
|
|
||||||
<p>
|
|
||||||
We therefore recommend that you lock the Timezone library to version 1.2 and above by listing
|
|
||||||
<code>gem 'tzinfo', '~> 1.2'</code> in your <code>Gemfile</code>.
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
## Auto Regeneration
|
## Auto Regeneration
|
||||||
|
|
||||||
Jekyll uses the `listen` gem to watch for changes when the `--watch` switch is specified during a build or serve.
|
Jekyll uses the `listen` gem to watch for changes when the `--watch` switch is specified during a build or serve.
|
||||||
|
|
|
@ -291,6 +291,28 @@ Feature: Site configuration
|
||||||
And I should see "Post Layout: <p>content for entry1.</p>\n built at 2013-04-09T09:22:00-10:00" in "_site/2013/04/09/entry1.html"
|
And I should see "Post Layout: <p>content for entry1.</p>\n built at 2013-04-09T09:22:00-10:00" in "_site/2013/04/09/entry1.html"
|
||||||
And I should see "Post Layout: <p>content for entry2.</p>\n built at 2013-04-09T13:14:00-10:00" in "_site/2013/04/09/entry2.html"
|
And I should see "Post Layout: <p>content for entry2.</p>\n built at 2013-04-09T13:14:00-10:00" in "_site/2013/04/09/entry2.html"
|
||||||
|
|
||||||
|
Scenario: Generate proper dates with explicitly set timezone (using non-half hour offset )
|
||||||
|
Given I have a _layouts directory
|
||||||
|
And I have a page layout that contains "Page Layout: {{ site.posts.size }}"
|
||||||
|
And I have a post layout that contains "Post Layout: {{ content }} built at {{ page.date | date_to_xmlschema }}"
|
||||||
|
And I have an "index.html" page with layout "page" that contains "site index page"
|
||||||
|
And I have a configuration file with:
|
||||||
|
| key | value |
|
||||||
|
| timezone | Australia/Eucla |
|
||||||
|
And I have a _posts directory
|
||||||
|
And I have the following posts:
|
||||||
|
| title | date | layout | content |
|
||||||
|
| entry1 | 2013-04-09 23:22 +0400 | post | content for entry1. |
|
||||||
|
| entry2 | 2013-04-10 03:14 +0400 | post | content for entry2. |
|
||||||
|
When I run jekyll build
|
||||||
|
Then I should get a zero exit status
|
||||||
|
And the _site directory should exist
|
||||||
|
And I should see "Page Layout: 2" in "_site/index.html"
|
||||||
|
And the "_site/2013/04/10/entry1.html" file should exist
|
||||||
|
And the "_site/2013/04/10/entry2.html" file should exist
|
||||||
|
And I should see "Post Layout: <p>content for entry1.</p>\n built at 2013-04-10T04:07:00\+08:45" in "_site/2013/04/10/entry1.html"
|
||||||
|
And I should see "Post Layout: <p>content for entry2.</p>\n built at 2013-04-10T07:59:00\+08:45" in "_site/2013/04/10/entry2.html"
|
||||||
|
|
||||||
Scenario: Limit the number of posts generated by most recent date
|
Scenario: Limit the number of posts generated by most recent date
|
||||||
Given I have a _posts directory
|
Given I have a _posts directory
|
||||||
And I have a configuration file with:
|
And I have a configuration file with:
|
||||||
|
|
|
@ -92,7 +92,7 @@ module Jekyll
|
||||||
# Windows and JRuby does not include zoneinfo files, so bundle the tzinfo-data gem
|
# Windows and JRuby does not include zoneinfo files, so bundle the tzinfo-data gem
|
||||||
# and associated library.
|
# and associated library.
|
||||||
platforms :mingw, :x64_mingw, :mswin, :jruby do
|
platforms :mingw, :x64_mingw, :mswin, :jruby do
|
||||||
gem "tzinfo", "~> 1.2"
|
gem "tzinfo", ">= 1", "< 3"
|
||||||
gem "tzinfo-data"
|
gem "tzinfo-data"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -11,64 +11,35 @@ module Jekyll
|
||||||
# timezone - the IANA Time Zone specified in "_config.yml"
|
# timezone - the IANA Time Zone specified in "_config.yml"
|
||||||
#
|
#
|
||||||
# Returns a string that ultimately re-defines ENV["TZ"] in Windows
|
# Returns a string that ultimately re-defines ENV["TZ"] in Windows
|
||||||
def calculate(timezone)
|
def calculate(timezone, now = Time.now)
|
||||||
External.require_with_graceful_fail("tzinfo") unless defined?(TZInfo)
|
External.require_with_graceful_fail("tzinfo") unless defined?(TZInfo)
|
||||||
tz = TZInfo::Timezone.get(timezone)
|
tz = TZInfo::Timezone.get(timezone)
|
||||||
difference = Time.now.to_i - tz.now.to_i
|
|
||||||
|
#
|
||||||
|
# Use period_for_utc and utc_total_offset instead of
|
||||||
|
# period_for and observed_utc_offset for compatibility with tzinfo v1.
|
||||||
|
offset = tz.period_for_utc(now.getutc).utc_total_offset
|
||||||
|
|
||||||
#
|
#
|
||||||
# POSIX style definition reverses the offset sign.
|
# POSIX style definition reverses the offset sign.
|
||||||
# e.g. Eastern Standard Time (EST) that is 5Hrs. to the 'west' of Prime Meridian
|
# e.g. Eastern Standard Time (EST) that is 5Hrs. to the 'west' of Prime Meridian
|
||||||
# is denoted as:
|
# is denoted as:
|
||||||
# EST+5 (or) EST+05:00
|
# EST+5 (or) EST+05:00
|
||||||
# Reference: http://www.gnu.org/software/libc/manual/html_node/TZ-Variable.html
|
# Reference: http://www.gnu.org/software/libc/manual/html_node/TZ-Variable.html
|
||||||
sign = difference.negative? ? "-" : "+"
|
sign = offset.positive? ? "-" : "+"
|
||||||
offset = sign == "-" ? "+" : "-" unless difference.zero?
|
|
||||||
#
|
|
||||||
# convert the difference (in seconds) to hours, as a rational number, and perform
|
|
||||||
# a modulo operation on it.
|
|
||||||
modulo = modulo_of(rational_hour(difference))
|
|
||||||
#
|
|
||||||
# Format the hour as a two-digit number.
|
|
||||||
# Establish the minutes based on modulo expression.
|
|
||||||
hh = format("%<hour>02d", :hour => absolute_hour(difference).ceil)
|
|
||||||
mm = modulo.zero? ? "00" : "30"
|
|
||||||
|
|
||||||
Jekyll.logger.debug "Timezone:", "#{timezone} #{offset}#{hh}:#{mm}"
|
rational_hours = offset.abs.to_r / 3600
|
||||||
|
hours = rational_hours.to_i
|
||||||
|
minutes = ((rational_hours - hours) * 60).to_i
|
||||||
|
|
||||||
|
#
|
||||||
|
# Format the hours and minutes as two-digit numbers.
|
||||||
|
time = format("%<hours>02d:%<minutes>02d", :hours => hours, :minutes => minutes)
|
||||||
|
|
||||||
|
Jekyll.logger.debug "Timezone:", "#{timezone} #{sign}#{time}"
|
||||||
#
|
#
|
||||||
# Note: The 3-letter-word below doesn't have a particular significance.
|
# Note: The 3-letter-word below doesn't have a particular significance.
|
||||||
"WTZ#{sign}#{hh}:#{mm}"
|
"WTZ#{sign}#{time}"
|
||||||
end
|
|
||||||
|
|
||||||
private
|
|
||||||
|
|
||||||
# Private: Convert given seconds to an hour as a rational number.
|
|
||||||
#
|
|
||||||
# seconds - supplied as an integer, it is converted to a rational number.
|
|
||||||
# 3600 - no. of seconds in an hour.
|
|
||||||
#
|
|
||||||
# Returns a rational number.
|
|
||||||
def rational_hour(seconds)
|
|
||||||
seconds.to_r / 3600
|
|
||||||
end
|
|
||||||
|
|
||||||
# Private: Convert given seconds to an hour as an absolute number.
|
|
||||||
#
|
|
||||||
# seconds - supplied as an integer, it is converted to its absolute.
|
|
||||||
# 3600 - no. of seconds in an hour.
|
|
||||||
#
|
|
||||||
# Returns an integer.
|
|
||||||
def absolute_hour(seconds)
|
|
||||||
seconds.abs / 3600
|
|
||||||
end
|
|
||||||
|
|
||||||
# Private: Perform a modulo operation on a given fraction.
|
|
||||||
#
|
|
||||||
# fraction - supplied as a rational number, its numerator is divided
|
|
||||||
# by its denominator and the remainder returned.
|
|
||||||
#
|
|
||||||
# Returns an integer.
|
|
||||||
def modulo_of(fraction)
|
|
||||||
fraction.numerator % fraction.denominator
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -0,0 +1,31 @@
|
||||||
|
# frozen_string_literal: true
|
||||||
|
|
||||||
|
require "helper"
|
||||||
|
|
||||||
|
class TestWinTz < JekyllUnitTest
|
||||||
|
[["America/New_York", "WTZ+05:00"], ["Europe/Paris", "WTZ-01:00"]].each do |tz, expected|
|
||||||
|
should "use base offset in winter for #{tz}" do
|
||||||
|
result = Jekyll::Utils::WinTZ.calculate(tz, Time.utc(2021, 1, 1))
|
||||||
|
assert_equal expected, result
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
[["America/New_York", "WTZ+04:00"], ["Europe/Paris", "WTZ-02:00"]].each do |tz, expected|
|
||||||
|
should "apply DST in summer for #{tz}" do
|
||||||
|
result = Jekyll::Utils::WinTZ.calculate(tz, Time.utc(2021, 7, 1))
|
||||||
|
assert_equal expected, result
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
[["Australia/Eucla", "WTZ-08:45"], ["Pacific/Marquesas", "WTZ+09:30"]].each do |tz, expected|
|
||||||
|
should "handle non zero minutes for #{tz}" do
|
||||||
|
result = Jekyll::Utils::WinTZ.calculate(tz, Time.utc(2021, 1, 1))
|
||||||
|
assert_equal expected, result
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
should "return zero for UTC" do
|
||||||
|
result = Jekyll::Utils::WinTZ.calculate("UTC")
|
||||||
|
assert_equal "WTZ+00:00", result
|
||||||
|
end
|
||||||
|
end
|
Loading…
Reference in New Issue