| File-Assets documentation | Contained in the File-Assets distribution. |
my $asset = File::Asset->new(base => $base, path => "/static/assets.css");
$asset = $assets->include("/static/assets.css"); # Or, like this, usually.
print "The rank for asset at ", $asset->uri, " is ", $asset->rank, "\n";
print "The file for the asset is ", $asset->file, "\n";
A File::Asset object represents an asset existing in both URI-space and file-space (on disk). The asset is usually a .js (JavaScript) or .css (CSS) file.
Creates a new File::Asset. You probably don't want to use this, create a File::Assets object and use $assets->include instead.
Returns a URI object represting the uri for $asset
Returns a Path::Class::File object represting the file for $asset
Returns the path of $asset
Returns a SCALAR reference to the content contained in $asset->file
Writes <content>, which should be a SCALAR reference, to the file located at $asset->file
If the parent directory for $asset->file does not exist yet, this method will create it first
Returns a hex digest for the content of $asset
Returns the unique key for the $asset. Usually the path/filename of the $asset, but for content-based assets returns a value based off of $asset->digest
Hide $asset (mark it as hidden). That is, don't include $asset during export
Returns whether $asset is inline (should be embedded into the document) or external.
If an argument is given, then it will set whether $asset is inline or not (1 for inline, 0 for external).
| File-Assets documentation | Contained in the File-Assets distribution. |
package File::Assets::Asset; use warnings; use strict; use File::Assets::Util; use File::Assets::Carp; use File::Assets::Asset::Content; use XML::Tiny; use IO::Scalar; use Object::Tiny qw/type rank attributes hidden rsc outside/; use Scalar::Util qw/blessed/;
sub _html_parse ($) { XML::Tiny::parsefile(IO::Scalar->new(shift)); } sub new { my $self = bless {}, shift; my $asset = @_ == 1 && ref $_[0] eq "HASH" ? shift : { @_ }; my $content = delete $asset->{content}; $content = ref $content eq "SCALAR" ? $$content : $content; if (defined $content && $content =~ m/^\s*</) { # Looks like tagged content (<script> or <style>) my $tag = _html_parse \$content; croak "Unable to parse $content" unless $tag && $tag->[0]; $tag = $tag->[0]; my $type = delete $tag->{attrib}->{type}; if (! $type) { if ($tag->{name} =~ m/^script$/i) { $type = "js" } elsif ($tag->{name} =~ m/^style$/i) { $type = "css" } } $asset->{type} = $type unless defined $asset->{type}; while (my ($name, $value) = each %{ $tag->{attrib} }) { $asset->{$name} = $value unless exists $asset->{$name}; } $content = $tag->{content}->[0]->{content}; $content = "" unless defined $content; } my ($path, $rsc, $base, $type) = delete @$asset{qw/path rsc base type/}; if (defined $type) { my $_type = $type; $type = File::Assets::Util->parse_type($_type) or croak "Don't understand type ($_type) for this asset"; } if ($rsc) { croak "Don't have a type for this asset" unless $type; $self->{rsc} = $rsc; $self->{type} = $type; croak "Can't also specify content and ", $self->rsc->file if defined $content; } elsif ($path && $path =~ m/^https?:\/\// || (blessed $path && $path->isa("URI"))) { my $uri = $self->{uri} = URI->new($path); $self->{type} = $type || do { File::Assets::Util->parse_type($uri->path) or croak "Unable to determine type of $uri"; }; $self->{outside} = 1; } elsif ($base && $path) { if ($path =~ m/^\//) { $self->{rsc} = $base->clone($path); } else { $self->{rsc} = $base->child($path); } croak "Can't also specify content and ", $self->rsc->file if defined $content; $self->{type} = $type || File::Assets::Util->parse_type($path) or croak "Don't know type for asset ($path)"; } elsif (defined $content) { croak "Don't have a type for this asset" unless $type; $self->{type} = $type; $self->{digest} = File::Assets::Util->digest->add($content)->hexdigest; $self->{content} = \$content; } else { croak "Don't know what to do"; } my $rank = $self->{rank} = delete $asset->{rank} || 0; croak "Don't understand rank ($rank)" if $rank && $rank =~ m/[^\d\+\-\.]/; $self->{cache} = delete $asset->{cache}; $self->{inline} = exists $asset->{inline} ? (delete $asset->{inline} ? 1 : 0) : $self->{content} ? 1 : 0; $self->{attributes} = { %$asset }; # The rest goes here! return $self; }
sub uri { my $self = shift; return $self->{uri} unless $self->{rsc}; return ($self->{uri} ||= $self->rsc->uri)->clone; }
sub file { my $self = shift; return unless $self->{rsc}; return $self->{file} ||= $self->rsc->file; }
sub path { my $self = shift; return unless $self->{rsc}; return $self->{path} ||= $self->rsc->path; }
sub content { my $self = shift; return $self->{content} || $self->_content->content; }
sub write { my $self = shift; my $content = shift; my $file = $self->file; my $dir = $file->parent; $dir->mkpath unless -d $dir; $file->openw->print($$content); }
# NOTE: $asset->digest used to return a unique signature for the asset (based off the filename), but this has changed to # now return the actual hex digest of the content of $asset sub digest { my $self = shift; return $self->{digest} || $self->_content->digest; } sub content_digest { my $self = shift; carp "File::Assets::Asset::content_digest is DEPRECATED (use ::digest instead)"; return $self->digest; } sub mtime { return 0; carp "File::Assets::Asset::mtime is DEPRECATED"; } sub file_mtime { my $self = shift; return 0 unless $self->file; return $self->_content->file_mtime; } sub file_size { my $self = shift; return 0 unless $self->file; return $self->_content->file_size; } sub content_mtime { my $self = shift; return 0 unless $self->file; return $self->_content->content_mtime; } sub content_size { my $self = shift; return length ${ $self->{content} } unless $self->file; return $self->_content->content_size; } sub refresh { my $self = shift; return 0 unless $self->file; return $self->_content->refresh; } sub stale { my $self = shift; return 0 unless $self->file; return $self->_content->stale; } sub _content { my $self = shift; return $self->{_content} ||= do { if (my $cache = $self->{cache}) { $cache->content($self->file); } else { File::Assets::Asset::Content->new($self->file); } }; }
sub key { my $self = shift; return $self->path || $self->uri || ($self->{key} ||= '%' . $self->digest); }
sub hide { shift->{hidden} = 1; }
sub inline { my $self = shift; $self->{inline} = shift() ? 1 : 0 if @_; return $self->{inline}; } 1; __END__ # elsif (0 && $base && $content) { # Nonsense scenario? # croak "Don't have a type for this asset" unless $type; # my $path = File::Assets::Util->build_asset_path(undef, type => $type, digest => $self->digest); # $self->{rsc} = $base->child($path); # $self->{type} = $type; # }