SemVer-V2-Strict

 view release on metacpan or  search on metacpan

lib/SemVer/V2/Strict.pm  view on Meta::CPAN

package SemVer::V2::Strict;
use strict;
use warnings;
use utf8;
our $VERSION = '0.17';

use constant PRE_RELEASE_FORMAT    => qr/(?:-(?<pre_release>[a-zA-Z0-9.\-]+))?/;
use constant BUILD_METADATA_FORMAT => qr/(?:\+(?<build_metadata>[a-zA-Z0-9.\-]+))?/;
use constant VERSION_FORMAT        =>
    qr/(?<major>[0-9]+)(?:\.(?<minor>[0-9]+))?(?:\.(?<patch>[0-9]+))?@{[PRE_RELEASE_FORMAT]}@{[BUILD_METADATA_FORMAT]}/;

use List::Util qw/min max/;
use Scalar::Util qw/looks_like_number/;

use overload (
    q{""}    => \&as_string,
    q{<=>}   => \&_cmp,
    fallback => 1,
);

sub major          { shift->{major} }
sub minor          { shift->{minor} }
sub patch          { shift->{patch} }
sub pre_release    { shift->{pre_release} }
sub build_metadata { shift->{build_metadata} }

sub new {
    my $class = shift;
    my $self  = bless {} => $class;

    $self->_init_by_version_numbers     if @_ == 0;
    $self->_init_by_version_string(@_)  if @_ == 1;
    $self->_init_by_version_numbers(@_) if @_ >= 2;

    return $self;
}

sub _init_by_version_string {
    my ($self, $version) = @_;

    die 'Invalid format' unless $version =~ qr/^@{[VERSION_FORMAT]}$/;

    $self->{major}          = $+{major};
    $self->{minor}          = $+{minor} // 0;
    $self->{patch}          = $+{patch} // 0;
    $self->{pre_release}    = $+{pre_release};
    $self->{build_metadata} = $+{build_metadata};
}

sub _init_by_version_numbers {
    my ($self, $major, $minor, $patch, $pre_release, $build_metadata) = @_;

    $self->{major}          = $major // 0;
    $self->{minor}          = $minor // 0;
    $self->{patch}          = $patch // 0;
    $self->{pre_release}    = $pre_release;
    $self->{build_metadata} = $build_metadata;
}

sub clean {
    my ($class, $version) = @_;

    $version =~ s/^\s*(.*?)\s*$/$1/; # trim
    $version =~ s/^[=v]+//;

    return eval { $class->new($version)->as_string };
}

sub sort {
    my ($class, @versions) = @_;
    return sort { $class->new($a) <=> $class->new($b) } @versions;
}

sub as_string {
    my $self = shift;

    my $string = $self->major.'.'.$self->minor.'.'.$self->patch;
    $string .= '-'.$self->pre_release    if $self->pre_release;
    $string .= '+'.$self->build_metadata if $self->build_metadata;

    return $string;
}

sub _cmp {
    my ($self, $other) = @_;

    return $self->major <=> $other->major if $self->major != $other->major;
    return $self->minor <=> $other->minor if $self->minor != $other->minor;
    return $self->patch <=> $other->patch if $self->patch != $other->patch;

 view all matches for this distribution
 view release on metacpan -  search on metacpan

( run in 1.250 second using v1.00-cache-2.02-grep-82fe00e-cpan-9f2165ba459b )