package org.jruby.ext.date;
import org.joda.time.DateTime;
import org.jruby.*;
import org.jruby.anno.JRubyMethod;
import org.jruby.runtime.ThreadContext;
import org.jruby.runtime.builtin.IRubyObject;
import static org.jruby.ext.date.DateUtils.*;
import static org.jruby.ext.date.RubyDate.*;
public abstract class TimeExt {
private TimeExt() { }
static void load(Ruby runtime) {
runtime.getTime().defineAnnotatedMethods(TimeExt.class);
}
@JRubyMethod
public static RubyTime to_time(IRubyObject self) { return (RubyTime) self; }
@JRubyMethod(name = "to_date")
public static RubyDate to_date(ThreadContext context, IRubyObject self) {
final DateTime dt = ((RubyTime) self).getDateTime();
long jd = civil_to_jd(dt.getYear(), dt.getMonthOfYear(), dt.getDayOfMonth(), GREGORIAN);
return new RubyDate(context, getDate(context.runtime), jd_to_ajd(context, jd), CHRONO_ITALY_UTC, 0);
}
@JRubyMethod(name = "to_datetime")
public static RubyDateTime to_datetime(ThreadContext context, IRubyObject self) {
final RubyTime time = (RubyTime) self;
DateTime dt = ((RubyTime) self).getDateTime();
long subMillisNum = 0, subMillisDen = 1;
if (time.getNSec() != 0) {
IRubyObject subMillis = RubyRational.newRationalCanonicalize(context, time.getNSec(), 1_000_000);
if (subMillis instanceof RubyRational) {
subMillisNum = ((RubyRational) subMillis).getNumerator().getLongValue();
subMillisDen = ((RubyRational) subMillis).getDenominator().getLongValue();
}
else {
subMillisNum = ((RubyInteger) subMillis).getLongValue();
}
}
final int off = dt.getZone().getOffset(dt.getMillis()) / 1000;
int year = dt.getYear(); if (year <= 0) year--;
if (year == 1582) {
return calcAjdFromCivil(context, dt, off, subMillisNum, subMillisDen);
}
dt = new DateTime(
year, dt.getMonthOfYear(), dt.getDayOfMonth(),
dt.getHourOfDay(), dt.getMinuteOfHour(), dt.getSecondOfMinute(),
dt.getMillisOfSecond(), getChronology(context, ITALY, dt.getZone())
);
return new RubyDateTime(context.runtime, getDateTime(context.runtime), dt, off, ITALY, subMillisNum, subMillisDen);
}
private static RubyDateTime calcAjdFromCivil(ThreadContext context, final DateTime dt, final int off,
final long subMillisNum, final long subMillisDen) {
final Ruby runtime = context.runtime;
long jd = civil_to_jd(dt.getYear(), dt.getMonthOfYear(), dt.getDayOfMonth(), ITALY);
RubyNumeric fr = timeToDayFraction(context, dt.getHourOfDay(), dt.getMinuteOfHour(), dt.getSecondOfMinute());
final RubyNumeric ajd = jd_to_ajd(context, jd, fr, off);
RubyDateTime dateTime = new RubyDateTime(context, getDateTime(runtime), ajd, off, ITALY);
dateTime.dt = dateTime.dt.withMillisOfSecond(dt.getMillisOfSecond());
dateTime.subMillisNum = subMillisNum; dateTime.subMillisDen = subMillisDen;
return dateTime;
}
}