DateTime

 view release on metacpan or  search on metacpan

lib/DateTime.pm  view on Meta::CPAN

                . " be subtracted from a $class object." );
    }
}

sub add {
    my $self = shift;

    return $self->add_duration( $self->_duration_object_from_args(@_) );
}

sub subtract {
    my $self = shift;

    my %eom;
    if ( @_ % 2 == 0 ) {
        my %p = @_;

        $eom{end_of_month} = delete $p{end_of_month}
            if exists $p{end_of_month};
    }

    my $dur = $self->_duration_object_from_args(@_)->inverse(%eom);

    return $self->add_duration($dur);
}

# Syntactic sugar for add and subtract: use a duration object if it's
# supplied, otherwise build a new one from the arguments.

sub _duration_object_from_args {
    my $self = shift;

    return $_[0]
        if @_ == 1 && blessed( $_[0] ) && $_[0]->isa( $self->duration_class );

    return $self->duration_class->new(@_);
}

sub subtract_duration { return $_[0]->add_duration( $_[1]->inverse ) }

{
    my $validator = validation_for(
        name             => '_check_add_duration_params',
        name_is_optional => 1,
        params           => [
            { type => t('Duration') },
        ],
    );

    ## no critic (Subroutines::ProhibitExcessComplexity)
    sub add_duration {
        my $self = shift;
        my ($dur) = $validator->(@_);

        # simple optimization
        return $self if $dur->is_zero;

        my %deltas = $dur->deltas;

        # This bit isn't quite right since DateTime::Infinite::Future -
        # infinite duration should NaN
        for my $val ( values %deltas ) {
            my $inf;
            if ( $val == INFINITY ) {
                $inf = DateTime::Infinite::Future->new;
            }
            elsif ( $val == NEG_INFINITY ) {
                $inf = DateTime::Infinite::Past->new;
            }

            if ($inf) {
                %$self = %$inf;
                bless $self, ref $inf;

                return $self;
            }
        }

        return $self if $self->is_infinite;

        my %orig = %{$self};
        try {
            $self->_add_duration($dur);
        }
        catch {
            %{$self} = %orig;
            die $_;
        };
    }
}

sub _add_duration {
    my $self = shift;
    my $dur  = shift;

    my %deltas = $dur->deltas;

    if ( $deltas{days} ) {
        $self->{local_rd_days} += $deltas{days};

        $self->{utc_year} += int( $deltas{days} / 365 ) + 1;
    }

    if ( $deltas{months} ) {

        # For preserve mode, if it is the last day of the month, make
        # it the 0th day of the following month (which then will
        # normalize back to the last day of the new month).
        my ( $y, $m, $d ) = (
              $dur->is_preserve_mode
            ? $self->_rd2ymd( $self->{local_rd_days} + 1 )
            : $self->_rd2ymd( $self->{local_rd_days} )
        );

        $d -= 1 if $dur->is_preserve_mode;

        if ( !$dur->is_wrap_mode && $d > 28 ) {

            # find the rd for the last day of our target month
            $self->{local_rd_days}
                = $self->_ymd2rd( $y, $m + $deltas{months} + 1, 0 );

lib/DateTime.pm  view on Meta::CPAN


You can enable a git pre-commit hook for linting by running F<./git/setup.pl>.

Note that linting will be checked in CI, and it's okay to submit a PR which
fails the linting check, but it's extra nice to fix these yourself.

=head1 THE DATETIME PROJECT ECOSYSTEM

This module is part of a larger ecosystem of modules in the DateTime family.

=head2 L<DateTime::Set>

The L<DateTime::Set> module represents sets (including recurrences) of
datetimes. Many modules return sets or recurrences.

=head2 Format Modules

The various format modules exist to parse and format datetimes. For example,
L<DateTime::Format::HTTP> parses dates according to the RFC 1123 format:

    my $datetime
        = DateTime::Format::HTTP->parse_datetime(
        'Thu Feb  3 17:03:55 GMT 1994');

    print DateTime::Format::HTTP->format_datetime($datetime);

Most format modules are suitable for use as a C<formatter> with a DateTime
object.

All format modules start with
L<DateTime::Format::|https://metacpan.org/search?q=datetime%3A%3Aformat>.

=head2 Calendar Modules

There are a number of modules on CPAN that implement non-Gregorian calendars,
such as the Chinese, Mayan, and Julian calendars.

All calendar modules start with
L<DateTime::Calendar::|https://metacpan.org/search?q=datetime%3A%3Acalendar>.

=head2 Event Modules

There are a number of modules that calculate the dates for events, such as
Easter, Sunrise, etc.

All event modules start with
L<DateTime::Event::|https://metacpan.org/search?q=datetime%3A%3Aevent>.

=head2 Others

There are many other modules that work with DateTime, including modules in the
L<DateTimeX namespace|https://metacpan.org/search?q=datetimex> namespace, as
well as others.

See L<MetaCPAN|https://metacpan.org/search?q=datetime> for more modules.

=head1 KNOWN BUGS

The tests in F<20infinite.t> seem to fail on some machines, particularly on
Win32. This appears to be related to Perl's internal handling of IEEE infinity
and NaN, and seems to be highly platform/compiler/phase of moon dependent.

If you don't plan to use infinite datetimes you can probably ignore this. This
will be fixed (perhaps) in future versions.

=head1 SEE ALSO

L<A Date with Perl|http://presentations.houseabsolute.com/a-date-with-perl/> -
a talk I've given at a few YAPCs.

L<datetime@perl.org mailing list|http://lists.perl.org/list/datetime.html>

=head1 SUPPORT

Bugs may be submitted at L<https://github.com/houseabsolute/DateTime.pm/issues>.

There is a mailing list available for users of this distribution,
L<mailto:datetime@perl.org>.

=head1 SOURCE

The source code repository for DateTime can be found at L<https://github.com/houseabsolute/DateTime.pm>.

=head1 DONATIONS

If you'd like to thank me for the work I've done on this module, please
consider making a "donation" to me via PayPal. I spend a lot of free time
creating free software, and would appreciate any support you'd care to offer.

Please note that B<I am not suggesting that you must do this> in order for me
to continue working on this particular software. I will continue to do so,
inasmuch as I have in the past, for as long as it interests me.

Similarly, a donation made in this way will probably not make me work on this
software much more, unless I get so many donations that I can consider working
on free software full time (let's all have a chuckle at that together).

To donate, log into PayPal and send money to autarch@urth.org, or use the
button at L<https://houseabsolute.com/foss-donations/>.

=head1 AUTHOR

Dave Rolsky <autarch@urth.org>

=head1 CONTRIBUTORS

=for stopwords Ben Bennett Christian Hansen Daisuke Maki Dan Book Stewart David Dyck E. Wheeler Precious Doug Bell Flávio Soibelmann Glock Gianni Ceccarelli Gregory Oschwald Hauke D Iain Truskett James Raspass Jason McIntosh Joshua Hoblitt Karen Eth...

=over 4

=item *

Ben Bennett <fiji@limey.net>

=item *

Christian Hansen <chansen@cpan.org>

=item *

Daisuke Maki <dmaki@cpan.org>



( run in 1.852 second using v1.01-cache-2.11-cpan-39bf76dae61 )