wareki 1.1.0 → 2.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/ChangeLog +66 -0
- data/README.md +46 -8
- data/lib/wareki/calendar.rb +90 -0
- data/lib/wareki/calendar_def.rb +253 -1431
- data/lib/wareki/common.rb +24 -5
- data/lib/wareki/date.rb +144 -67
- data/lib/wareki/era_def.rb +16 -13
- data/lib/wareki/std_ext.rb +55 -7
- data/lib/wareki/utils.rb +99 -32
- data/lib/wareki/version.rb +1 -1
- metadata +11 -52
data/lib/wareki/common.rb
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
|
-
require 'wareki/
|
|
3
|
+
require 'wareki/calendar'
|
|
4
4
|
require 'wareki/era_def'
|
|
5
5
|
require 'date'
|
|
6
6
|
# Wareki module common constants definitions
|
|
@@ -9,8 +9,9 @@ module Wareki
|
|
|
9
9
|
GREGORIAN_START_YEAR = 1873
|
|
10
10
|
IMPERIAL_START = 1_480_041 # Date.new(-660, 2, 11, Date::GREGORIAN).jd
|
|
11
11
|
IMPERIAL_START_YEAR = -660
|
|
12
|
+
WESTERN_ERA_NAMES = ['', '西暦', '紀元前'].freeze
|
|
13
|
+
IMPERIAL_ERA_NAMES = %w(皇紀 神武天皇即位紀元).freeze
|
|
12
14
|
DATE_INFINITY = ::Date.new(280_000_000, 12, 31) # Use 280000000 for jruby limitation...
|
|
13
|
-
YEAR_BY_NUM = Hash[*YEAR_DEFS.map { |y| [y.year, y] }.flatten].freeze
|
|
14
15
|
KANJI_VARIANTS = {
|
|
15
16
|
'宝' => '寳',
|
|
16
17
|
'霊' => '靈',
|
|
@@ -42,8 +43,8 @@ module Wareki
|
|
|
42
43
|
NORMALIZE_KANJI_VARIANTS_HASH = KANJI_VARIANTS.each_with_object({}) { |(n, s), h| s.each_char { |c| h[c] = n } }
|
|
43
44
|
NORMALIZE_KANJI_VARIANTS = ->(str) { str.gsub(NORMALIZE_KANJI_VARIANTS_REGEX, NORMALIZE_KANJI_VARIANTS_HASH) }
|
|
44
45
|
ERA_BY_NAME = Hash[*(ERA_NORTH_DEFS + ERA_DEFS).flat_map { |g| [g.name, g] }]
|
|
45
|
-
ERA_BY_NAME['皇紀'] = ERA_BY_NAME['神武天皇即位紀元'] = Era.new('皇紀', -660, 1_480_041, DATE_INFINITY.jd)
|
|
46
|
-
ERA_BY_NAME['西暦'] = ERA_BY_NAME[''] = Era.new('西暦', 1, 1_721_424, DATE_INFINITY.jd)
|
|
46
|
+
ERA_BY_NAME['皇紀'] = ERA_BY_NAME['神武天皇即位紀元'] = Era.new('皇紀', -660, 1_480_041, DATE_INFINITY.jd).freeze
|
|
47
|
+
ERA_BY_NAME['西暦'] = ERA_BY_NAME[''] = Era.new('西暦', 1, 1_721_424, DATE_INFINITY.jd).freeze
|
|
47
48
|
ERA_BY_NAME.default_proc = ->(hash, key) { hash.fetch(SQUARE_ERAS[key] || NORMALIZE_KANJI_VARIANTS[key], nil) }
|
|
48
49
|
ERA_BY_NAME.freeze
|
|
49
50
|
ERA_REGEX = Regexp.new(
|
|
@@ -58,17 +59,35 @@ module Wareki
|
|
|
58
59
|
(?:(?<era_name>紀元前|#{ERA_REGEX})?
|
|
59
60
|
(?:(?<year>[元#{NUM_CHARS}]+)年))?
|
|
60
61
|
(?:(?<is_leap>閏|潤|うるう)?
|
|
61
|
-
(?:(?<month>[正#{NUM_CHARS}]+)
|
|
62
|
+
(?:(?<month>[正#{NUM_CHARS}]+)(?<is_leap_post>['’])?月 |
|
|
62
63
|
(?<alt_month>#{ALT_MONTH_NAME.join('|')})))?
|
|
63
64
|
(?:(?<day>[元朔晦#{NUM_CHARS}]+)日|元旦)?
|
|
64
65
|
}x.freeze
|
|
66
|
+
# REGEX が空でないマッチを返すには 年/月/日/元旦 か、「月」を含まない
|
|
67
|
+
# 月の別名 (弥生・師走) のいずれかが必要。それ以外は素の Date.parse に
|
|
68
|
+
# 直行させて monkey patch のオーバーヘッドを避ける。
|
|
69
|
+
PARSE_QUICK_FILTER = /[年月日]|元旦|弥生|師走/.freeze
|
|
70
|
+
TIME_REGEX = %r{
|
|
71
|
+
(?<noon>正午) |
|
|
72
|
+
(?:(?<ampm>午前|午後)[[:space:]]*)?
|
|
73
|
+
(?<hour>[#{NUM_CHARS}]+)[[:space:]]*時
|
|
74
|
+
(?:[[:space:]]*
|
|
75
|
+
(?:(?<half>半) |
|
|
76
|
+
(?<min>[#{NUM_CHARS}]+)[[:space:]]*分
|
|
77
|
+
(?:[[:space:]]*(?<sec>[#{NUM_CHARS}]+)[[:space:]]*秒)?))?
|
|
78
|
+
}x.freeze
|
|
79
|
+
# TIME_REGEX が非空マッチしうるのは「時」か「正午」を含む文字列のみ
|
|
80
|
+
TIME_PARSE_QUICK_FILTER = /時|正午/.freeze
|
|
65
81
|
|
|
66
82
|
class UnsupportedDateRange < StandardError; end
|
|
83
|
+
class InvalidDate < ArgumentError; end
|
|
67
84
|
|
|
68
85
|
module_function
|
|
69
86
|
|
|
70
87
|
def parse_to_date(str, start = ::Date::ITALY)
|
|
71
88
|
Date.parse(str).to_date(start)
|
|
89
|
+
rescue InvalidDate
|
|
90
|
+
raise
|
|
72
91
|
rescue ArgumentError
|
|
73
92
|
::Date.parse(str, true, start)
|
|
74
93
|
end
|
data/lib/wareki/date.rb
CHANGED
|
@@ -8,33 +8,25 @@ require 'wareki/kansuji'
|
|
|
8
8
|
module Wareki
|
|
9
9
|
# Wareki date handling class, main implementation.
|
|
10
10
|
class Date
|
|
11
|
-
|
|
11
|
+
include Comparable
|
|
12
|
+
|
|
13
|
+
attr_reader :year, :month, :day, :era_year, :era_name
|
|
12
14
|
|
|
13
15
|
def self.today
|
|
14
16
|
jd(::Date.today.jd)
|
|
15
17
|
end
|
|
16
18
|
|
|
17
|
-
def self._check_invalid_date(era, year, month, day)
|
|
18
|
-
month == 12 or return true
|
|
19
|
-
day > 2 or return true
|
|
20
|
-
(era == '明治' && year == 5 ||
|
|
21
|
-
%w(皇紀 神武天皇即位紀元).member?(era) &&
|
|
22
|
-
year == GREGORIAN_START_YEAR - IMPERIAL_START_YEAR - 1) and
|
|
23
|
-
return false
|
|
24
|
-
true
|
|
25
|
-
end
|
|
26
|
-
|
|
27
19
|
def self._parse(str)
|
|
28
20
|
str = str.to_s.gsub(/[[:space:]]/, '')
|
|
29
21
|
match = REGEX.match(str)
|
|
30
|
-
match && !match[0].empty? or
|
|
22
|
+
(match && !match[0].empty?) or
|
|
31
23
|
raise ArgumentError, "Invaild Date: #{str}"
|
|
32
24
|
era = match[:era_name]
|
|
33
25
|
if (era.nil? || era == '') && match[:year].nil?
|
|
34
26
|
year = Date.today.year
|
|
35
27
|
else
|
|
36
|
-
|
|
37
|
-
|
|
28
|
+
year = Utils.k2i(match[:year])
|
|
29
|
+
year > 0 or raise ArgumentError, "Invalid year: #{str}"
|
|
38
30
|
end
|
|
39
31
|
month = day = 1
|
|
40
32
|
|
|
@@ -48,20 +40,20 @@ module Wareki
|
|
|
48
40
|
end
|
|
49
41
|
|
|
50
42
|
month > 12 || month < 1 and
|
|
51
|
-
raise
|
|
43
|
+
raise InvalidDate, "invalid date (month out of range): #{str}"
|
|
44
|
+
|
|
45
|
+
is_leap = !!(match[:is_leap] || match[:is_leap_post])
|
|
52
46
|
|
|
53
47
|
if match[:day]
|
|
54
48
|
if match[:day] == '晦'
|
|
55
|
-
|
|
49
|
+
civil_year = Utils.era_year_to_civil(era, year)
|
|
50
|
+
day = Utils.last_day_of_era_month(era, civil_year, month, is_leap)
|
|
56
51
|
else
|
|
57
52
|
day = Utils.k2i(match[:day])
|
|
58
53
|
end
|
|
59
54
|
end
|
|
60
55
|
|
|
61
|
-
|
|
62
|
-
raise ArgumentError, "Invaild Date: #{str}"
|
|
63
|
-
|
|
64
|
-
{era: era, year: year, month: month, day: day, is_leap: !!match[:is_leap]}
|
|
56
|
+
{era: era, year: year, month: month, day: day, is_leap: is_leap}
|
|
65
57
|
end
|
|
66
58
|
|
|
67
59
|
def self.parse(str)
|
|
@@ -87,23 +79,13 @@ module Wareki
|
|
|
87
79
|
end
|
|
88
80
|
|
|
89
81
|
def initialize(era_name, era_year, month = 1, day = 1, is_leap_month = false)
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
82
|
+
@era_name = era_name.to_s
|
|
83
|
+
@era_year = era_year
|
|
93
84
|
@month = month
|
|
94
85
|
@day = day
|
|
95
86
|
@is_leap_month = is_leap_month
|
|
96
|
-
@
|
|
97
|
-
|
|
98
|
-
if era_name.to_s == '' || era_name == '西暦'
|
|
99
|
-
@year = @era_year
|
|
100
|
-
elsif era_name.to_s == '紀元前'
|
|
101
|
-
@year = -@era_year
|
|
102
|
-
elsif %w(皇紀 神武天皇即位紀元).include? era_name
|
|
103
|
-
@year = era_year + IMPERIAL_START_YEAR
|
|
104
|
-
else
|
|
105
|
-
@year = ERA_BY_NAME[era_name].year + era_year - 1
|
|
106
|
-
end
|
|
87
|
+
@year = Utils.era_year_to_civil(@era_name, @era_year)
|
|
88
|
+
_validate_date!
|
|
107
89
|
end
|
|
108
90
|
|
|
109
91
|
def imperial_year
|
|
@@ -111,7 +93,7 @@ module Wareki
|
|
|
111
93
|
end
|
|
112
94
|
|
|
113
95
|
def imperial_year=(v)
|
|
114
|
-
|
|
96
|
+
self.year = v + IMPERIAL_START_YEAR
|
|
115
97
|
end
|
|
116
98
|
|
|
117
99
|
def leap_month?
|
|
@@ -119,36 +101,92 @@ module Wareki
|
|
|
119
101
|
end
|
|
120
102
|
|
|
121
103
|
def leap_month=(v)
|
|
104
|
+
@jd = nil
|
|
122
105
|
@is_leap_month = v
|
|
123
106
|
end
|
|
124
107
|
|
|
108
|
+
def year=(v)
|
|
109
|
+
era_year = Utils.civil_to_era_year(@era_name, v)
|
|
110
|
+
@jd = nil
|
|
111
|
+
@year = v
|
|
112
|
+
@era_year = era_year
|
|
113
|
+
end
|
|
114
|
+
|
|
115
|
+
def month=(v)
|
|
116
|
+
@jd = nil
|
|
117
|
+
@month = v
|
|
118
|
+
end
|
|
119
|
+
|
|
120
|
+
def day=(v)
|
|
121
|
+
@jd = nil
|
|
122
|
+
@day = v
|
|
123
|
+
end
|
|
124
|
+
|
|
125
|
+
def era_year=(v)
|
|
126
|
+
year = Utils.era_year_to_civil(@era_name, v)
|
|
127
|
+
@jd = nil
|
|
128
|
+
@era_year = v
|
|
129
|
+
@year = year
|
|
130
|
+
end
|
|
131
|
+
|
|
132
|
+
def era_name=(v)
|
|
133
|
+
era_name = v.to_s
|
|
134
|
+
year = Utils.era_year_to_civil(era_name, @era_year)
|
|
135
|
+
@jd = nil
|
|
136
|
+
@era_name = era_name
|
|
137
|
+
@year = year
|
|
138
|
+
end
|
|
139
|
+
|
|
125
140
|
def __set_jd(v)
|
|
126
141
|
@jd = v
|
|
127
142
|
end
|
|
128
143
|
|
|
129
144
|
def month_index
|
|
130
145
|
return month - 1 if
|
|
131
|
-
|
|
146
|
+
WESTERN_ERA_NAMES.include?(@era_name) || @year >= GREGORIAN_START_YEAR
|
|
132
147
|
|
|
133
|
-
|
|
148
|
+
Calendar.covers_year?(@year) or
|
|
134
149
|
raise UnsupportedDateRange, "Cannot get year info of #{inspect}"
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
150
|
+
Calendar.month_index(@year, month, leap_month?)
|
|
151
|
+
end
|
|
152
|
+
|
|
153
|
+
def last_day_of_month
|
|
154
|
+
Utils.last_day_of_era_month(@era_name, @year, month, leap_month?)
|
|
155
|
+
end
|
|
156
|
+
|
|
157
|
+
def _validate_date!
|
|
158
|
+
(month.is_a?(Integer) && month >= 1 && month <= 12) or
|
|
159
|
+
raise InvalidDate, "invalid date (month out of range): #{inspect}"
|
|
160
|
+
(day.is_a?(Integer) && day >= 1) or
|
|
161
|
+
raise InvalidDate, "invalid date (day out of range): #{inspect}"
|
|
162
|
+
if !WESTERN_ERA_NAMES.include?(@era_name) && @year < GREGORIAN_START_YEAR
|
|
163
|
+
# 暦テーブル外の年は従来どおり jd 変換時の UnsupportedDateRange に委ねる
|
|
164
|
+
Calendar.covers_year?(@year) or return
|
|
165
|
+
!leap_month? || Calendar.leap_month(@year) == month or
|
|
166
|
+
raise InvalidDate, "invalid date (no leap month): #{inspect}"
|
|
167
|
+
day <= Calendar.last_day_of_month(@year, month, leap_month?) or
|
|
168
|
+
raise InvalidDate, "invalid date (day out of range): #{inspect}"
|
|
169
|
+
else
|
|
170
|
+
leap_month? and
|
|
171
|
+
raise InvalidDate, "invalid date (no leap month): #{inspect}"
|
|
172
|
+
day <= last_day_of_month or
|
|
173
|
+
raise InvalidDate, "invalid date (day out of range): #{inspect}"
|
|
174
|
+
end
|
|
138
175
|
end
|
|
139
176
|
|
|
140
177
|
def jd
|
|
141
178
|
@jd and return @jd
|
|
142
179
|
|
|
143
|
-
|
|
180
|
+
_validate_date!
|
|
181
|
+
WESTERN_ERA_NAMES.include?(@era_name) and
|
|
144
182
|
return @jd = ::Date.new(@year, month, day, ::Date::ITALY).jd
|
|
145
183
|
|
|
146
184
|
@year >= GREGORIAN_START_YEAR and
|
|
147
185
|
return @jd = ::Date.new(@year, month, day, ::Date::GREGORIAN).jd
|
|
148
186
|
|
|
149
|
-
|
|
187
|
+
@jd = Calendar.to_jd(@year, month, day, leap_month?) or
|
|
150
188
|
raise UnsupportedDateRange, "Cannot convert to jd #{inspect}"
|
|
151
|
-
@jd
|
|
189
|
+
@jd
|
|
152
190
|
end
|
|
153
191
|
|
|
154
192
|
def to_date(start = ::Date::ITALY)
|
|
@@ -159,61 +197,72 @@ module Wareki
|
|
|
159
197
|
to_date.to_time
|
|
160
198
|
end
|
|
161
199
|
|
|
200
|
+
FORMAT_DIRECTIVE_REGEX = /%J(-|[_0]{0,2}[0-9]*|)([fFyYegGoOiImMsSlLdD][kK]?)/.freeze
|
|
201
|
+
FORMAT_EXPANSION_REGEX = /(?<!%)(?:%%)*\K#{FORMAT_DIRECTIVE_REGEX}/.freeze
|
|
202
|
+
|
|
203
|
+
def expand_wareki_format(format_str)
|
|
204
|
+
format_str.to_str.gsub(FORMAT_EXPANSION_REGEX) { format($2, $1) || $& }
|
|
205
|
+
end
|
|
206
|
+
|
|
162
207
|
def strftime(format_str = '%JF')
|
|
163
|
-
ret = format_str
|
|
208
|
+
ret = expand_wareki_format(format_str)
|
|
164
209
|
ret.index('%') or return ret
|
|
165
210
|
d = to_date
|
|
166
211
|
d.respond_to?(:_wareki_strftime_orig) ? d._wareki_strftime_orig(ret) : d.strftime(ret)
|
|
167
212
|
end
|
|
168
213
|
|
|
169
|
-
def
|
|
214
|
+
def _number_format(opt)
|
|
215
|
+
Utils.number_format(opt)
|
|
216
|
+
end
|
|
217
|
+
|
|
218
|
+
def format(key, opt = '')
|
|
170
219
|
case key.to_sym
|
|
171
220
|
when :e then era_name
|
|
172
|
-
when :g then era_name.to_s == '' ? '' : era_year
|
|
221
|
+
when :g then era_name.to_s == '' ? '' : Kernel.format(_number_format(opt), era_year)
|
|
173
222
|
when :G then era_name.to_s == '' ? '' : Utils.i2z(era_year)
|
|
174
|
-
when :Gk then era_name.to_s == '' ? '' :
|
|
223
|
+
when :Gk then era_name.to_s == '' ? '' : Utils.to_simple_kan(era_year)
|
|
175
224
|
when :GK
|
|
176
225
|
if era_name.to_s == ''
|
|
177
226
|
''
|
|
178
227
|
elsif era_year == 1
|
|
179
228
|
'元'
|
|
180
229
|
else
|
|
181
|
-
|
|
230
|
+
Utils.to_simple_kan(era_year)
|
|
182
231
|
end
|
|
183
232
|
when :o then year
|
|
184
233
|
when :O then Utils.i2z(year)
|
|
185
|
-
when :Ok then
|
|
234
|
+
when :Ok then Utils.to_simple_kan(year)
|
|
186
235
|
when :i then imperial_year
|
|
187
236
|
when :I then Utils.i2z(imperial_year)
|
|
188
|
-
when :Ik then
|
|
189
|
-
when :s then month
|
|
237
|
+
when :Ik then Utils.to_simple_kan(imperial_year)
|
|
238
|
+
when :s then Kernel.format(_number_format(opt), month)
|
|
190
239
|
when :S then Utils.i2z(month)
|
|
191
|
-
when :Sk then
|
|
240
|
+
when :Sk then Utils.to_simple_kan(month)
|
|
192
241
|
when :SK then Utils.alt_month_name(month)
|
|
193
242
|
when :l then leap_month? ? "'" : ''
|
|
194
243
|
when :L then leap_month? ? '’' : ''
|
|
195
244
|
when :Lk then leap_month? ? '閏' : ''
|
|
196
|
-
when :d then day
|
|
245
|
+
when :d then Kernel.format(_number_format(opt), day)
|
|
197
246
|
when :D then Utils.i2z(day)
|
|
198
|
-
when :Dk then
|
|
247
|
+
when :Dk then Utils.to_simple_kan(day)
|
|
199
248
|
when :DK
|
|
200
249
|
if month == 1 && !leap_month? && day == 1
|
|
201
250
|
'元'
|
|
202
251
|
elsif day == 1
|
|
203
252
|
'朔'
|
|
204
|
-
elsif day ==
|
|
253
|
+
elsif day == last_day_of_month
|
|
205
254
|
'晦'
|
|
206
255
|
else
|
|
207
|
-
|
|
256
|
+
Utils.to_simple_kan(day)
|
|
208
257
|
end
|
|
209
|
-
when :m then "#{format(:s)}#{format(:l)}"
|
|
258
|
+
when :m then "#{format(:s, opt)}#{format(:l)}"
|
|
210
259
|
when :M then "#{format(:Lk)}#{format(:S)}"
|
|
211
260
|
when :Mk then "#{format(:Lk)}#{format(:Sk)}"
|
|
212
|
-
when :y then "#{format(:e)}#{format(:g)}"
|
|
261
|
+
when :y then "#{format(:e)}#{format(:g, opt)}"
|
|
213
262
|
when :Y then "#{format(:e)}#{format(:G)}"
|
|
214
263
|
when :Yk then "#{format(:e)}#{format(:Gk)}"
|
|
215
264
|
when :YK then "#{format(:e)}#{format(:GK)}"
|
|
216
|
-
when :f then "#{format(:e)}#{format(:g)}年#{format(:s)}#{format(:l)}月#{format(:d)}日"
|
|
265
|
+
when :f then "#{format(:e)}#{format(:g, opt)}年#{format(:s, opt)}#{format(:l)}月#{format(:d, opt)}日"
|
|
217
266
|
when :F then "#{format(:e)}#{format(:GK)}年#{format(:Lk)}#{format(:Sk)}月#{format(:Dk)}日"
|
|
218
267
|
end
|
|
219
268
|
end
|
|
@@ -239,20 +288,48 @@ module Wareki
|
|
|
239
288
|
true
|
|
240
289
|
end
|
|
241
290
|
|
|
291
|
+
def hash
|
|
292
|
+
[self.class, @era_name, @era_year, @year, @month, @day, leap_month?].hash
|
|
293
|
+
end
|
|
294
|
+
|
|
295
|
+
def <=>(other)
|
|
296
|
+
ojd = _jd_if_date_like(other)
|
|
297
|
+
ojd = other if ojd.nil? && other.is_a?(Numeric)
|
|
298
|
+
ojd.nil? and return nil
|
|
299
|
+
jd <=> ojd
|
|
300
|
+
end
|
|
301
|
+
|
|
302
|
+
def succ
|
|
303
|
+
self + 1
|
|
304
|
+
end
|
|
305
|
+
|
|
242
306
|
def -(other)
|
|
243
|
-
|
|
307
|
+
n = _to_days(other)
|
|
308
|
+
n.nil? or return self.class.jd(jd - n)
|
|
309
|
+
ojd = _jd_if_date_like(other)
|
|
310
|
+
ojd and return jd - ojd
|
|
311
|
+
raise TypeError, "Cannot subtract #{other.inspect} from Wareki::Date"
|
|
244
312
|
end
|
|
245
313
|
|
|
246
314
|
def +(other)
|
|
247
|
-
|
|
315
|
+
n = _to_days(other)
|
|
316
|
+
n.nil? and raise TypeError, "Cannot add #{other.inspect} to Wareki::Date"
|
|
317
|
+
self.class.jd(jd + n)
|
|
248
318
|
end
|
|
249
319
|
|
|
250
|
-
def
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
other
|
|
320
|
+
def _to_days(other)
|
|
321
|
+
# rubocop:disable Style/ClassEqualityComparison
|
|
322
|
+
return other.in_days if other.class.name == 'ActiveSupport::Duration'
|
|
323
|
+
# rubocop:enable Style/ClassEqualityComparison
|
|
324
|
+
|
|
325
|
+
other.is_a?(Numeric) ? other : nil
|
|
326
|
+
end
|
|
327
|
+
|
|
328
|
+
def _jd_if_date_like(other)
|
|
329
|
+
return other.jd if other.respond_to?(:jd)
|
|
330
|
+
|
|
331
|
+
other.respond_to?(:to_date) && !other.is_a?(Numeric) and other = other.to_date
|
|
332
|
+
other.respond_to?(:jd) ? other.jd : nil
|
|
256
333
|
end
|
|
257
334
|
end
|
|
258
335
|
end
|
data/lib/wareki/era_def.rb
CHANGED
|
@@ -1,12 +1,15 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
# coding: utf-8
|
|
3
|
+
|
|
4
|
+
# Generated by build-util/gen-era-def.rb from manakai data-locale era-defs.json.
|
|
5
|
+
# Do not edit this file directly.
|
|
3
6
|
module Wareki
|
|
4
7
|
DAY_MAX = 1684383730585466947585
|
|
5
8
|
Era = Struct.new(:name, :year, :start, :end)
|
|
6
9
|
ERA_DEFS = [
|
|
7
10
|
Era.new("大化", 645, 1956842, 1958551),
|
|
8
|
-
Era.new("白雉", 650, 1958551,
|
|
9
|
-
Era.new("朱鳥", 686, 1971845,
|
|
11
|
+
Era.new("白雉", 650, 1958551, 1960339),
|
|
12
|
+
Era.new("朱鳥", 686, 1971845, 1972033),
|
|
10
13
|
Era.new("大宝", 701, 1977221, 1978361),
|
|
11
14
|
Era.new("慶雲", 704, 1978361, 1979692),
|
|
12
15
|
Era.new("和銅", 708, 1979692, 1982487),
|
|
@@ -163,9 +166,9 @@ module Wareki
|
|
|
163
166
|
Era.new("建武", 1334, 2208365, 2209133),
|
|
164
167
|
Era.new("延元", 1336, 2209133, 2210638),
|
|
165
168
|
Era.new("興国", 1340, 2210638, 2213069),
|
|
166
|
-
Era.new("正平", 1346, 2213069,
|
|
167
|
-
Era.new("建徳", 1370,
|
|
168
|
-
Era.new("文中", 1372,
|
|
169
|
+
Era.new("正平", 1346, 2213069, 2221512),
|
|
170
|
+
Era.new("建徳", 1370, 2221512, 2222332),
|
|
171
|
+
Era.new("文中", 1372, 2222332, 2223453),
|
|
169
172
|
Era.new("天授", 1375, 2223453, 2225533),
|
|
170
173
|
Era.new("弘和", 1381, 2225533, 2226702),
|
|
171
174
|
Era.new("元中", 1384, 2226702, 2229809),
|
|
@@ -252,11 +255,11 @@ module Wareki
|
|
|
252
255
|
Era.new("昭和", 1926, 2424875, 2447534),
|
|
253
256
|
Era.new("平成", 1989, 2447535, 2458604),
|
|
254
257
|
Era.new("令和", 2019, 2458605, DAY_MAX),
|
|
255
|
-
].freeze
|
|
258
|
+
].each(&:freeze).freeze
|
|
256
259
|
ERA_NORTH_DEFS = [
|
|
257
260
|
Era.new("大化", 645, 1956842, 1958551),
|
|
258
|
-
Era.new("白雉", 650, 1958551,
|
|
259
|
-
Era.new("朱鳥", 686, 1971845,
|
|
261
|
+
Era.new("白雉", 650, 1958551, 1960339),
|
|
262
|
+
Era.new("朱鳥", 686, 1971845, 1972033),
|
|
260
263
|
Era.new("大宝", 701, 1977221, 1978361),
|
|
261
264
|
Era.new("慶雲", 704, 1978361, 1979692),
|
|
262
265
|
Era.new("和銅", 708, 1979692, 1982487),
|
|
@@ -407,15 +410,15 @@ module Wareki
|
|
|
407
410
|
Era.new("元亨", 1321, 2203634, 2205008),
|
|
408
411
|
Era.new("正中", 1324, 2205008, 2205527),
|
|
409
412
|
Era.new("嘉暦", 1326, 2205527, 2206740),
|
|
410
|
-
Era.new("元徳", 1329, 2206740,
|
|
413
|
+
Era.new("元徳", 1329, 2206740, 2207714),
|
|
411
414
|
Era.new("元弘", 1331, 2207459, 2208365),
|
|
412
415
|
Era.new("正慶", 1332, 2207714, 2208124),
|
|
413
416
|
Era.new("建武", 1334, 2208365, 2210046),
|
|
414
417
|
Era.new("延元", 1336, 2209133, 2210638),
|
|
415
418
|
Era.new("興国", 1340, 2210638, 2213069),
|
|
416
|
-
Era.new("正平", 1346, 2213069,
|
|
417
|
-
Era.new("建徳", 1370,
|
|
418
|
-
Era.new("文中", 1372,
|
|
419
|
+
Era.new("正平", 1346, 2213069, 2221512),
|
|
420
|
+
Era.new("建徳", 1370, 2221512, 2222332),
|
|
421
|
+
Era.new("文中", 1372, 2222332, 2223453),
|
|
419
422
|
Era.new("天授", 1375, 2223453, 2225533),
|
|
420
423
|
Era.new("弘和", 1381, 2225533, 2226702),
|
|
421
424
|
Era.new("元中", 1384, 2226702, 2229809),
|
|
@@ -502,5 +505,5 @@ module Wareki
|
|
|
502
505
|
Era.new("昭和", 1926, 2424875, 2447534),
|
|
503
506
|
Era.new("平成", 1989, 2447535, 2458604),
|
|
504
507
|
Era.new("令和", 2019, 2458605, DAY_MAX),
|
|
505
|
-
].freeze
|
|
508
|
+
].each(&:freeze).freeze
|
|
506
509
|
end
|
data/lib/wareki/std_ext.rb
CHANGED
|
@@ -5,8 +5,26 @@ require 'wareki/date'
|
|
|
5
5
|
module Wareki
|
|
6
6
|
# :nodoc:
|
|
7
7
|
module StdExt
|
|
8
|
+
module_function
|
|
9
|
+
|
|
10
|
+
def wareki_directive?(format)
|
|
11
|
+
!!(format.to_str =~ Wareki::Date::FORMAT_EXPANSION_REGEX)
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
def wareki_time_directive?(format)
|
|
15
|
+
!!(format.to_str =~ Wareki::Utils::TIME_FORMAT_EXPANSION_REGEX)
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
# %JT 時刻トークンと %J 日付トークンの両方を展開した文字列を返す
|
|
19
|
+
def expand_all_wareki_formats(format, datetime)
|
|
20
|
+
ret = format
|
|
21
|
+
ret = Wareki::Utils.expand_time_format(ret, datetime) if wareki_time_directive?(ret)
|
|
22
|
+
ret = datetime.to_wareki_date.expand_wareki_format(ret) if wareki_directive?(ret)
|
|
23
|
+
ret
|
|
24
|
+
end
|
|
8
25
|
end
|
|
9
26
|
end
|
|
27
|
+
|
|
10
28
|
# :nodoc:
|
|
11
29
|
class Date
|
|
12
30
|
JAPAN = Wareki::GREGORIAN_START
|
|
@@ -17,29 +35,59 @@ class Date
|
|
|
17
35
|
|
|
18
36
|
alias _wareki_strftime_orig strftime
|
|
19
37
|
def strftime(format = '%F')
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
_wareki_strftime_orig(format)
|
|
24
|
-
end
|
|
38
|
+
return _wareki_strftime_orig(format) unless Wareki::StdExt.wareki_directive?(format)
|
|
39
|
+
|
|
40
|
+
_wareki_strftime_orig(to_wareki_date.expand_wareki_format(format))
|
|
25
41
|
end
|
|
26
42
|
|
|
27
43
|
class << self
|
|
28
44
|
alias _wareki_parse_orig parse
|
|
29
45
|
def parse(str = '-4712-01-01', comp = true, start = ::Date::ITALY)
|
|
46
|
+
return ::Date._wareki_parse_orig(str, comp, start) if str.to_s.ascii_only?
|
|
47
|
+
|
|
48
|
+
str = Wareki::Utils.normalize_time(str)
|
|
49
|
+
str.to_s =~ Wareki::PARSE_QUICK_FILTER or
|
|
50
|
+
return ::Date._wareki_parse_orig(str, comp, start)
|
|
30
51
|
Wareki::Date.parse(str).to_date(start)
|
|
31
|
-
rescue
|
|
52
|
+
rescue Wareki::InvalidDate
|
|
53
|
+
raise
|
|
54
|
+
rescue ArgumentError
|
|
32
55
|
::Date._wareki_parse_orig(str, comp, start)
|
|
33
56
|
end
|
|
34
57
|
|
|
35
58
|
alias _wareki__parse_orig _parse
|
|
36
59
|
def _parse(str, comp = true)
|
|
60
|
+
return ::Date._wareki__parse_orig(str, comp) if str.to_s.ascii_only?
|
|
61
|
+
|
|
62
|
+
str = Wareki::Utils.normalize_time(str)
|
|
63
|
+
str.to_s =~ Wareki::PARSE_QUICK_FILTER or
|
|
64
|
+
return ::Date._wareki__parse_orig(str, comp)
|
|
37
65
|
di = Wareki::Date._parse(str)
|
|
38
66
|
wdate = Wareki::Date.new(di[:era], di[:year], di[:month], di[:day], di[:is_leap])
|
|
39
|
-
rescue ArgumentError
|
|
67
|
+
rescue ArgumentError
|
|
40
68
|
::Date._wareki__parse_orig(str, comp)
|
|
41
69
|
else
|
|
42
70
|
::Date._wareki__parse_orig(str.sub(Wareki::REGEX, wdate.strftime('%F ')), comp)
|
|
43
71
|
end
|
|
44
72
|
end
|
|
45
73
|
end
|
|
74
|
+
|
|
75
|
+
# :nodoc:
|
|
76
|
+
class DateTime
|
|
77
|
+
alias _wareki_strftime_orig strftime
|
|
78
|
+
def strftime(format = '%FT%T%:z')
|
|
79
|
+
_wareki_strftime_orig(Wareki::StdExt.expand_all_wareki_formats(format, self))
|
|
80
|
+
end
|
|
81
|
+
end
|
|
82
|
+
|
|
83
|
+
# :nodoc:
|
|
84
|
+
class Time
|
|
85
|
+
def to_wareki_date
|
|
86
|
+
Wareki::Date.jd(to_date.jd)
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
alias _wareki_strftime_orig strftime
|
|
90
|
+
def strftime(format)
|
|
91
|
+
_wareki_strftime_orig(Wareki::StdExt.expand_all_wareki_formats(format, self))
|
|
92
|
+
end
|
|
93
|
+
end
|