Mojolicious-Plugin-AssetPack

 view release on metacpan or  search on metacpan

lib/Mojolicious/Plugin/AssetPack/Asset.pm  view on Meta::CPAN

package Mojolicious::Plugin::AssetPack::Asset;
use Mojo::Base -base;

use Mojo::Asset::Memory;
use Mojo::URL;
use Mojo::File;
use Mojolicious::Plugin::AssetPack::Util qw(diag has_ro DEBUG);

my %TAG_TEMPLATE;
$TAG_TEMPLATE{css} = [qw(link rel stylesheet href)];
$TAG_TEMPLATE{ico} = [qw(link rel icon href)];
$TAG_TEMPLATE{js}  = [qw(script src)];
$TAG_TEMPLATE{$_}  = [qw(img src)]    for qw(gif jpg jpeg png svg);
$TAG_TEMPLATE{$_}  = [qw(source src)] for qw(mp3 mp4 ogg ogv webm);

has checksum => sub { Mojolicious::Plugin::AssetPack::Util::checksum(shift->content) };
has format   => sub {
  my $self = shift;
  my $name = $self->url =~ /^https?:/ ? Mojo::URL->new($self->url)->path->[-1] : (split m!(\\|/)!, $self->url)[-1];

  return $name =~ /\.(\w+)$/ ? lc $1 : '';
};

has minified => sub { shift->url =~ /\bmin\b/ ? 1 : 0 };
has renderer => undef;
has tag_for  => sub { \&_default_tag_for };

has _asset => sub {
  my $self = shift;
  return $self->content(delete $self->{content})->_asset      if $self->{content};
  return Mojo::Asset::File->new(path => delete $self->{path}) if $self->{path};
  return Mojo::Asset::Memory->new;
};

has_ro name => sub {
  my $self = shift;
  my $name;

  if ($self->url =~ /^https?:/) {
    my $url = Mojo::URL->new($self->url);
    my $qs  = $url->query->to_string;
    $name = $url->path->[-1];
    $qs   =~ s!\W!_!g;
    $name =~ s!\.\w+$!!;
    $name .= "_$qs" if $qs;
  }
  else {
    $name = (split m!(\\|/)!, $self->url)[-1];
    $name =~ s!\.\w+$!!;
  }

  return $name;
};

has_ro 'url';

sub asset {
  my $self  = shift;
  my $orig  = $self->_asset;
  my $clone = $orig->new;

  if ($orig->is_file) {
    $clone->cleanup(0)->path($orig->path);
  }
  else {
    $clone->auto_upgrade(0)->mtime($orig->mtime)->add_chunk($orig->slurp);
  }

  return $clone;
}

sub content {
  my $self = shift;
  return $self->_asset->slurp unless @_;
  return $self->_asset($_[0]->_asset) if UNIVERSAL::isa($_[0], __PACKAGE__);
  return $self->_asset($_[0])         if UNIVERSAL::isa($_[0], 'Mojo::Asset');
  return $self->_asset(Mojo::Asset::Memory->new->add_chunk($_[0]));
}

sub path {
  my $self = shift;
  return $self->_asset(Mojo::Asset::File->new(path => $_[0])) if $_[0];
  return Mojo::File->new($self->_asset->path)                 if $self->_asset->isa('Mojo::Asset::File');
  return undef;
}

sub size { $_[0]->_asset->size }

sub url_for { $_[1]->url_for(assetpack => $_[0]->TO_JSON); }

sub _default_tag_for {
  my ($asset, $c, $args, @attrs) = @_;
  my $url      = $asset->url_for($c);
  my @template = @{$TAG_TEMPLATE{$asset->format} || $TAG_TEMPLATE{css}};
  splice @template, 1, 0, type => $c->app->types->type($asset->format) if $template[0] eq 'source';
  return $c->tag(@template, Mojo::URL->new("$args->{base_url}$url"), @attrs);
}

sub FROM_JSON {
  my ($self, $attrs) = @_;
  $self->$_($attrs->{$_}) for grep { defined $attrs->{$_} } qw(checksum format minified);
  $self;
}

sub TO_JSON {
  return {map { ($_ => $_[0]->$_) } qw(checksum format minified name url)};
}



( run in 0.329 second using v1.01-cache-2.11-cpan-71847e10f99 )