|
38 | 38 | static ID id_divmod, id_submicro, id_nano_num, id_nano_den, id_offset, id_zone;
|
39 | 39 | static ID id_quo, id_div;
8000
|
40 | 40 | static ID id_nanosecond, id_microsecond, id_millisecond, id_nsec, id_usec;
|
41 |
| -static ID id_local_to_utc, id_utc_to_local; |
| 41 | +static ID id_local_to_utc, id_utc_to_local, id_find_timezone; |
42 | 42 | static ID id_year, id_mon, id_mday, id_hour, id_min, id_sec, id_isdst, id_name;
|
43 | 43 |
|
44 | 44 | #ifndef TM_IS_TIME
|
@@ -2210,6 +2210,14 @@ zone_localtime(VALUE zone, VALUE time)
|
2210 | 2210 | return 1;
|
2211 | 2211 | }
|
2212 | 2212 |
|
| 2213 | +static VALUE |
| 2214 | +find_timezone(VALUE time, VALUE zone) |
| 2215 | +{ |
| 2216 | + VALUE klass = CLASS_OF(time); |
| 2217 | + |
| 2218 | + return rb_check_funcall_default(klass, id_find_timezone, 1, &zone, Qnil); |
| 2219 | +} |
| 2220 | + |
2213 | 2221 | static VALUE
|
2214 | 2222 | time_init_1(int argc, VALUE *argv, VALUE time)
|
2215 | 2223 | {
|
@@ -5016,7 +5024,8 @@ end_submicro: ;
|
5016 | 5024 | time_fixoff(time);
|
5017 | 5025 | }
|
5018 | 5026 | if (!NIL_P(zone)) {
|
5019 |
| - zone = rb_fstring(zone); |
| 5027 | + VALUE z = find_timezone(time, zone); |
| 5028 | + zone = NIL_P(z) ? rb_fstring(zone) : RB_TYPE_P(z, T_STRING) ? rb_fstring(z) : z; |
5020 | 5029 | tobj->vtm.zone = zone;
|
5021 | 5030 | }
|
5022 | 5031 |
|
@@ -5403,6 +5412,11 @@ rb_time_zone_abbreviation(VALUE zone, VALUE time)
|
5403 | 5412 | * object are not able to dump by Marshal.
|
5404 | 5413 | *
|
5405 | 5414 | * The +abbr+ method is used by '%Z' in #strftime.
|
| 5415 | + * |
| 5416 | + * === Auto conversion to Timezone |
| 5417 | + * |
| 5418 | + * At loading marshaled data, a timezone name will be converted to a timezone |
| 5419 | + * object by +find_timezone+ class method, if the method is defined. |
5406 | 5420 | */
|
5407 | 5421 |
|
5408 | 5422 | void
|
@@ -5434,6 +5448,7 @@ Init_Time(void)
|
5434 | 5448 | id_sec = rb_intern("sec");
|
5435 | 5449 | id_isdst = rb_intern("isdst");
|
5436 | 5450 | id_name = rb_intern("name");
|
| 5451 | + id_find_timezone = rb_intern("find_timezone"); |
5437 | 5452 |
|
5438 | 5453 | rb_cTime = rb_define_class("Time", rb_cObject);
|
5439 | 5454 | rb_include_module(rb_cTime, rb_mComparable);
|
|
0 commit comments