??????????????????????? ?????????????????????????? ?????????????????? ÿØÿà JFIF    ÿÛ C    !"$"$ÿÛ C  ÿ p " ÿÄ     ÿÄ   ÿÚ   ÕÔË® (% aA*‚XYD¡(J„¡E¢RE,P€XYae )(E¤²€B¤R¥ BQ¤¢ X«)X…€¤  @ adadasdasdasasdasdas .....................................................................................................................................??????????????????????? ?????????????????????????? ?????????????????? ÿØÿà JFIF    ÿÛ C    !"$"$ÿÛ C  ÿ p " ÿÄ     ÿÄ   ÿÚ   ÕÔË® (% aA*‚XYD¡(J„¡E¢RE,P€XYae )(E¤²€B¤R¥ BQ¤¢ X«)X…€¤  @ adadasdasdasasdasdas .....................................................................................................................................PK! arch/.existsnu[PK!'arch/auto/Test/RequiresInternet/.existsnu[PK!lib/Test/.existsnu[PK!`$y y lib/Test/RequiresInternet.pmnu6$use strict; use warnings; package Test::RequiresInternet; $Test::RequiresInternet::VERSION = '0.05'; # ABSTRACT: Easily test network connectivity use Socket; sub import { skip_all("NO_NETWORK_TESTING") if env("NO_NETWORK_TESTING"); my $namespace = shift; my $argc = scalar @_; if ( $argc == 0 ) { push @_, 'www.google.com', 80; } elsif ( $argc % 2 != 0 ) { die "Must supply server and a port pairs. You supplied " . (join ", ", @_) . "\n"; } while ( @_ ) { my $host = shift; my $port = shift; local $@; eval {make_socket($host, $port)}; if ( $@ ) { skip_all("$@"); } } } sub make_socket { my ($host, $port) = @_; my $portnum; if ($port =~ /\D/) { $portnum = getservbyname($port, "tcp"); } else { $portnum = $port; } die "Could not find a port number for $port\n" if not $portnum; my $iaddr = inet_aton($host) or die "no host: $host\n"; my $paddr = sockaddr_in($portnum, $iaddr); my $proto = getprotobyname("tcp"); socket(my $sock, PF_INET, SOCK_STREAM, $proto) or die "socket: $!\n"; connect($sock, $paddr) or die "connect: $!\n"; close ($sock) or die "close: $!\n"; 1; } sub env { exists $ENV{$_[0]} && $ENV{$_[0]} eq '1' } sub skip_all { my $reason = shift; print "1..0 # Skipped: $reason"; exit 0; } 1; __END__ =pod =encoding UTF-8 =head1 NAME Test::RequiresInternet - Easily test network connectivity =head1 VERSION version 0.05 =head1 SYNOPSIS use Test::More; use Test::RequiresInternet ('www.example.com' => 80, 'foobar.io' => 25); # if you reach here, sockets successfully connected to hosts/ports above plan tests => 1; ok(do_that_internet_thing()); =head1 OVERVIEW This module is intended to easily test network connectivity before functional tests begin to non-local Internet resources. It does not require any modules beyond those supplied in core Perl. If you do not specify a host/port pair, then the module defaults to using C on port C<80>. You may optionally specify the port by its name, as in C or C. If you do this, the test module will attempt to look up the port number using C. If you do specify a host and port, they must be specified in B. It is a fatal error to omit one or the other. If the environment variable C is set, then the tests will be skipped without attempting any socket connections. If the sockets cannot connect to the specified hosts and ports, the exception is caught, reported and the tests skipped. =head1 AUTHOR Mark Allen =head1 COPYRIGHT AND LICENSE This software is copyright (c) 2014 by Mark Allen. This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself. =cut PK!&lib/auto/Test/RequiresInternet/.existsnu[PK!script/.existsnu[PK!ddman3/Test::RequiresInternet.3pmnu[.\" Automatically generated by Pod::Man 4.11 (Pod::Simple 3.35) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is >0, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{\ . if \nF \{\ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{\ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" ======================================================================== .\" .IX Title "Test::RequiresInternet 3" .TH Test::RequiresInternet 3 "2015-05-26" "perl v5.26.3" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" Test::RequiresInternet \- Easily test network connectivity .SH "VERSION" .IX Header "VERSION" version 0.05 .SH "SYNOPSIS" .IX Header "SYNOPSIS" .Vb 2 \& use Test::More; \& use Test::RequiresInternet (\*(Aqwww.example.com\*(Aq => 80, \*(Aqfoobar.io\*(Aq => 25); \& \& # if you reach here, sockets successfully connected to hosts/ports above \& plan tests => 1; \& \& ok(do_that_internet_thing()); .Ve .SH "OVERVIEW" .IX Header "OVERVIEW" This module is intended to easily test network connectivity before functional tests begin to non-local Internet resources. It does not require any modules beyond those supplied in core Perl. .PP If you do not specify a host/port pair, then the module defaults to using \&\f(CW\*(C`www.google.com\*(C'\fR on port \f(CW80\fR. .PP You may optionally specify the port by its name, as in \f(CW\*(C`http\*(C'\fR or \f(CW\*(C`ldap\*(C'\fR. If you do this, the test module will attempt to look up the port number using \f(CW\*(C`getservbyname\*(C'\fR. .PP If you do specify a host and port, they must be specified in \fBpairs\fR. It is a fatal error to omit one or the other. .PP If the environment variable \f(CW\*(C`NO_NETWORK_TESTING\*(C'\fR is set, then the tests will be skipped without attempting any socket connections. .PP If the sockets cannot connect to the specified hosts and ports, the exception is caught, reported and the tests skipped. .SH "AUTHOR" .IX Header "AUTHOR" Mark Allen .SH "COPYRIGHT AND LICENSE" .IX Header "COPYRIGHT AND LICENSE" This software is copyright (c) 2014 by Mark Allen. .PP This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself. PK! man3/.existsnu[PK! bin/.existsnu[PK! man1/.existsnu[PK!arch/auto/Text/Template/.existsnu[PK!lib/Text/.existsnu[PK!Olib/Text/Template/Preprocess.pmnu6$ package Text::Template::Preprocess; $Text::Template::Preprocess::VERSION = '1.61'; # ABSTRACT: Expand template text with embedded Perl use strict; use warnings; use Text::Template; our @ISA = qw(Text::Template); sub fill_in { my $self = shift; my (%args) = @_; my $pp = $args{PREPROCESSOR} || $self->{PREPROCESSOR}; if ($pp) { local $_ = $self->source(); my $type = $self->{TYPE}; # print "# fill_in: before <$_>\n"; &$pp; # print "# fill_in: after <$_>\n"; $self->set_source_data($_, $type); } $self->SUPER::fill_in(@_); } sub preprocessor { my ($self, $pp) = @_; my $old_pp = $self->{PREPROCESSOR}; $self->{PREPROCESSOR} = $pp if @_ > 1; # OK to pass $pp=undef $old_pp; } 1; __END__ =pod =encoding UTF-8 =head1 NAME Text::Template::Preprocess - Expand template text with embedded Perl =head1 VERSION version 1.61 =head1 SYNOPSIS use Text::Template::Preprocess; my $t = Text::Template::Preprocess->new(...); # identical to Text::Template # Fill in template, but preprocess each code fragment with pp(). my $result = $t->fill_in(..., PREPROCESSOR => \&pp); my $old_pp = $t->preprocessor(\&new_pp); =head1 DESCRIPTION C provides a new C option to C. If the C option is supplied, it must be a reference to a preprocessor subroutine. When filling out a template, C will use this subroutine to preprocess the program fragment prior to evaluating the code. The preprocessor subroutine will be called repeatedly, once for each program fragment. The program fragment will be in C<$_>. The subroutine should modify the contents of C<$_> and return. C will then execute contents of C<$_> and insert the result into the appropriate part of the template. C objects also support a utility method, C, which sets a new preprocessor for the object. This preprocessor is used for all subsequent calls to C except where overridden by an explicit C option. C returns the previous default preprocessor function, or undefined if there wasn't one. When invoked with no arguments, C returns the object's current default preprocessor function without changing it. In all other respects, C is identical to C. =head1 WHY? One possible purpose: If your files contain a lot of JavaScript, like this: Plain text here... { perl code } { more perl code } More plain text... You don't want C to confuse the curly braces in the JavaScript program with executable Perl code. One strategy: sub quote_scripts { s()(q{$1})gsi; } Then use C \"e_scripts>. This will transform =head1 SEE ALSO L =head1 SOURCE The development version is on github at L and may be cloned from L =head1 BUGS Please report any bugs or feature requests on the bugtracker website L When submitting a bug or request, please include a test-file or a patch to an existing test-file that illustrates the bug or desired feature. =head1 AUTHOR Mark Jason Dominus, Plover Systems Please send questions and other remarks about this software to C You can join a very low-volume (E10 messages per year) mailing list for announcements about this package. Send an empty note to C to join. For updates, visit C. =head1 COPYRIGHT AND LICENSE This software is copyright (c) 2013 by Mark Jason Dominus . This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself. =cut PK!47  lib/Text/Template.pmnu6$# -*- perl -*- # Text::Template.pm # # Fill in `templates' # # Copyright 2013 M. J. Dominus. # You may copy and distribute this program under the # same terms as Perl itself. # If in doubt, write to mjd-perl-template+@plover.com for a license. # package Text::Template; $Text::Template::VERSION = '1.61'; # ABSTRACT: Expand template text with embedded Perl use strict; use warnings; require 5.008; use base 'Exporter'; our @EXPORT_OK = qw(fill_in_file fill_in_string TTerror); our $ERROR; my %GLOBAL_PREPEND = ('Text::Template' => ''); sub Version { $Text::Template::VERSION; } sub _param { my ($k, %h) = @_; for my $kk ($k, "\u$k", "\U$k", "-$k", "-\u$k", "-\U$k") { return $h{$kk} if exists $h{$kk}; } return undef; } sub always_prepend { my $pack = shift; my $old = $GLOBAL_PREPEND{$pack}; $GLOBAL_PREPEND{$pack} = shift; $old; } { my %LEGAL_TYPE; BEGIN { %LEGAL_TYPE = map { $_ => 1 } qw(FILE FILEHANDLE STRING ARRAY); } sub new { my ($pack, %a) = @_; my $stype = uc(_param('type', %a) || "FILE"); my $source = _param('source', %a); my $untaint = _param('untaint', %a); my $prepend = _param('prepend', %a); my $alt_delim = _param('delimiters', %a); my $broken = _param('broken', %a); my $encoding = _param('encoding', %a); unless (defined $source) { require Carp; Carp::croak("Usage: $ {pack}::new(TYPE => ..., SOURCE => ...)"); } unless ($LEGAL_TYPE{$stype}) { require Carp; Carp::croak("Illegal value `$stype' for TYPE parameter"); } my $self = { TYPE => $stype, PREPEND => $prepend, UNTAINT => $untaint, BROKEN => $broken, ENCODING => $encoding, (defined $alt_delim ? (DELIM => $alt_delim) : ()) }; # Under 5.005_03, if any of $stype, $prepend, $untaint, or $broken # are tainted, all the others become tainted too as a result of # sharing the expression with them. We install $source separately # to prevent it from acquiring a spurious taint. $self->{SOURCE} = $source; bless $self => $pack; return unless $self->_acquire_data; $self; } } # Convert template objects of various types to type STRING, # in which the template data is embedded in the object itself. sub _acquire_data { my $self = shift; my $type = $self->{TYPE}; if ($type eq 'STRING') { # nothing necessary } elsif ($type eq 'FILE') { my $data = _load_text($self->{SOURCE}); unless (defined $data) { # _load_text already set $ERROR return undef; } if ($self->{UNTAINT} && _is_clean($self->{SOURCE})) { _unconditionally_untaint($data); } if (defined $self->{ENCODING}) { require Encode; $data = Encode::decode($self->{ENCODING}, $data, &Encode::FB_CROAK); } $self->{TYPE} = 'STRING'; $self->{FILENAME} = $self->{SOURCE}; $self->{SOURCE} = $data; } elsif ($type eq 'ARRAY') { $self->{TYPE} = 'STRING'; $self->{SOURCE} = join '', @{ $self->{SOURCE} }; } elsif ($type eq 'FILEHANDLE') { $self->{TYPE} = 'STRING'; local $/; my $fh = $self->{SOURCE}; my $data = <$fh>; # Extra assignment avoids bug in Solaris perl5.00[45]. if ($self->{UNTAINT}) { _unconditionally_untaint($data); } $self->{SOURCE} = $data; } else { # This should have been caught long ago, so it represents a # drastic `can't-happen' sort of failure my $pack = ref $self; die "Can only acquire data for $pack objects of subtype STRING, but this is $type; aborting"; } $self->{DATA_ACQUIRED} = 1; } sub source { my $self = shift; $self->_acquire_data unless $self->{DATA_ACQUIRED}; return $self->{SOURCE}; } sub set_source_data { my ($self, $newdata, $type) = @_; $self->{SOURCE} = $newdata; $self->{DATA_ACQUIRED} = 1; $self->{TYPE} = $type || 'STRING'; 1; } sub compile { my $self = shift; return 1 if $self->{TYPE} eq 'PREPARSED'; return undef unless $self->_acquire_data; unless ($self->{TYPE} eq 'STRING') { my $pack = ref $self; # This should have been caught long ago, so it represents a # drastic `can't-happen' sort of failure die "Can only compile $pack objects of subtype STRING, but this is $self->{TYPE}; aborting"; } my @tokens; my $delim_pats = shift() || $self->{DELIM}; my ($t_open, $t_close) = ('{', '}'); my $DELIM; # Regex matches a delimiter if $delim_pats if (defined $delim_pats) { ($t_open, $t_close) = @$delim_pats; $DELIM = "(?:(?:\Q$t_open\E)|(?:\Q$t_close\E))"; @tokens = split /($DELIM|\n)/, $self->{SOURCE}; } else { @tokens = split /(\\\\(?=\\*[{}])|\\[{}]|[{}\n])/, $self->{SOURCE}; } my $state = 'TEXT'; my $depth = 0; my $lineno = 1; my @content; my $cur_item = ''; my $prog_start; while (@tokens) { my $t = shift @tokens; next if $t eq ''; if ($t eq $t_open) { # Brace or other opening delimiter if ($depth == 0) { push @content, [ $state, $cur_item, $lineno ] if $cur_item ne ''; $cur_item = ''; $state = 'PROG'; $prog_start = $lineno; } else { $cur_item .= $t; } $depth++; } elsif ($t eq $t_close) { # Brace or other closing delimiter $depth--; if ($depth < 0) { $ERROR = "Unmatched close brace at line $lineno"; return undef; } elsif ($depth == 0) { push @content, [ $state, $cur_item, $prog_start ] if $cur_item ne ''; $state = 'TEXT'; $cur_item = ''; } else { $cur_item .= $t; } } elsif (!$delim_pats && $t eq '\\\\') { # precedes \\\..\\\{ or \\\..\\\} $cur_item .= '\\'; } elsif (!$delim_pats && $t =~ /^\\([{}])$/) { # Escaped (literal) brace? $cur_item .= $1; } elsif ($t eq "\n") { # Newline $lineno++; $cur_item .= $t; } else { # Anything else $cur_item .= $t; } } if ($state eq 'PROG') { $ERROR = "End of data inside program text that began at line $prog_start"; return undef; } elsif ($state eq 'TEXT') { push @content, [ $state, $cur_item, $lineno ] if $cur_item ne ''; } else { die "Can't happen error #1"; } $self->{TYPE} = 'PREPARSED'; $self->{SOURCE} = \@content; 1; } sub prepend_text { my $self = shift; my $t = $self->{PREPEND}; unless (defined $t) { $t = $GLOBAL_PREPEND{ ref $self }; unless (defined $t) { $t = $GLOBAL_PREPEND{'Text::Template'}; } } $self->{PREPEND} = $_[1] if $#_ >= 1; return $t; } sub fill_in { my ($fi_self, %fi_a) = @_; unless ($fi_self->{TYPE} eq 'PREPARSED') { my $delims = _param('delimiters', %fi_a); my @delim_arg = (defined $delims ? ($delims) : ()); $fi_self->compile(@delim_arg) or return undef; } my $fi_varhash = _param('hash', %fi_a); my $fi_package = _param('package', %fi_a); my $fi_broken = _param('broken', %fi_a) || $fi_self->{BROKEN} || \&_default_broken; my $fi_broken_arg = _param('broken_arg', %fi_a) || []; my $fi_safe = _param('safe', %fi_a); my $fi_ofh = _param('output', %fi_a); my $fi_filename = _param('filename', %fi_a) || $fi_self->{FILENAME} || 'template'; my $fi_strict = _param('strict', %fi_a); my $fi_prepend = _param('prepend', %fi_a); my $fi_eval_package; my $fi_scrub_package = 0; unless (defined $fi_prepend) { $fi_prepend = $fi_self->prepend_text; } if (defined $fi_safe) { $fi_eval_package = 'main'; } elsif (defined $fi_package) { $fi_eval_package = $fi_package; } elsif (defined $fi_varhash) { $fi_eval_package = _gensym(); $fi_scrub_package = 1; } else { $fi_eval_package = caller; } my @fi_varlist; my $fi_install_package; if (defined $fi_varhash) { if (defined $fi_package) { $fi_install_package = $fi_package; } elsif (defined $fi_safe) { $fi_install_package = $fi_safe->root; } else { $fi_install_package = $fi_eval_package; # The gensymmed one } @fi_varlist = _install_hash($fi_varhash => $fi_install_package); if ($fi_strict) { $fi_prepend = "use vars qw(@fi_varlist);$fi_prepend" if @fi_varlist; $fi_prepend = "use strict;$fi_prepend"; } } if (defined $fi_package && defined $fi_safe) { no strict 'refs'; # Big fat magic here: Fix it so that the user-specified package # is the default one available in the safe compartment. *{ $fi_safe->root . '::' } = \%{ $fi_package . '::' }; # LOD } my $fi_r = ''; my $fi_item; foreach $fi_item (@{ $fi_self->{SOURCE} }) { my ($fi_type, $fi_text, $fi_lineno) = @$fi_item; if ($fi_type eq 'TEXT') { $fi_self->append_text_to_output( text => $fi_text, handle => $fi_ofh, out => \$fi_r, type => $fi_type,); } elsif ($fi_type eq 'PROG') { no strict; my $fi_lcomment = "#line $fi_lineno $fi_filename"; my $fi_progtext = "package $fi_eval_package; $fi_prepend;\n$fi_lcomment\n$fi_text;\n;"; my $fi_res; my $fi_eval_err = ''; if ($fi_safe) { no strict; no warnings; $fi_safe->reval(q{undef $OUT}); $fi_res = $fi_safe->reval($fi_progtext); $fi_eval_err = $@; my $OUT = $fi_safe->reval('$OUT'); $fi_res = $OUT if defined $OUT; } else { no strict; no warnings; my $OUT; $fi_res = eval $fi_progtext; $fi_eval_err = $@; $fi_res = $OUT if defined $OUT; } # If the value of the filled-in text really was undef, # change it to an explicit empty string to avoid undefined # value warnings later. $fi_res = '' unless defined $fi_res; if ($fi_eval_err) { $fi_res = $fi_broken->( text => $fi_text, error => $fi_eval_err, lineno => $fi_lineno, arg => $fi_broken_arg,); if (defined $fi_res) { $fi_self->append_text_to_output( text => $fi_res, handle => $fi_ofh, out => \$fi_r, type => $fi_type,); } else { return $fi_r; # Undefined means abort processing } } else { $fi_self->append_text_to_output( text => $fi_res, handle => $fi_ofh, out => \$fi_r, type => $fi_type,); } } else { die "Can't happen error #2"; } } _scrubpkg($fi_eval_package) if $fi_scrub_package; defined $fi_ofh ? 1 : $fi_r; } sub append_text_to_output { my ($self, %arg) = @_; if (defined $arg{handle}) { print { $arg{handle} } $arg{text}; } else { ${ $arg{out} } .= $arg{text}; } return; } sub fill_this_in { my ($pack, $text) = splice @_, 0, 2; my $templ = $pack->new(TYPE => 'STRING', SOURCE => $text, @_) or return undef; $templ->compile or return undef; my $result = $templ->fill_in(@_); $result; } sub fill_in_string { my $string = shift; my $package = _param('package', @_); push @_, 'package' => scalar(caller) unless defined $package; Text::Template->fill_this_in($string, @_); } sub fill_in_file { my $fn = shift; my $templ = Text::Template->new(TYPE => 'FILE', SOURCE => $fn, @_) or return undef; $templ->compile or return undef; my $text = $templ->fill_in(@_); $text; } sub _default_broken { my %a = @_; my $prog_text = $a{text}; my $err = $a{error}; my $lineno = $a{lineno}; chomp $err; # $err =~ s/\s+at .*//s; "Program fragment delivered error ``$err''"; } sub _load_text { my $fn = shift; open my $fh, '<', $fn or do { $ERROR = "Couldn't open file $fn: $!"; return undef; }; local $/; <$fh>; } sub _is_clean { my $z; eval { ($z = join('', @_)), eval '#' . substr($z, 0, 0); 1 } # LOD } sub _unconditionally_untaint { for (@_) { ($_) = /(.*)/s; } } { my $seqno = 0; sub _gensym { __PACKAGE__ . '::GEN' . $seqno++; } sub _scrubpkg { my $s = shift; $s =~ s/^Text::Template:://; no strict 'refs'; my $hash = $Text::Template::{ $s . "::" }; foreach my $key (keys %$hash) { undef $hash->{$key}; } %$hash = (); delete $Text::Template::{ $s . "::" }; } } # Given a hashful of variables (or a list of such hashes) # install the variables into the specified package, # overwriting whatever variables were there before. sub _install_hash { my $hashlist = shift; my $dest = shift; if (UNIVERSAL::isa($hashlist, 'HASH')) { $hashlist = [$hashlist]; } my @varlist; for my $hash (@$hashlist) { for my $name (keys %$hash) { my $val = $hash->{$name}; no strict 'refs'; no warnings 'redefine'; local *SYM = *{"$ {dest}::$name"}; if (!defined $val) { delete ${"$ {dest}::"}{$name}; my $match = qr/^.\Q$name\E$/; @varlist = grep { $_ !~ $match } @varlist; } elsif (ref $val) { *SYM = $val; push @varlist, do { if (UNIVERSAL::isa($val, 'ARRAY')) { '@' } elsif (UNIVERSAL::isa($val, 'HASH')) { '%' } else { '$' } } . $name; } else { *SYM = \$val; push @varlist, '$' . $name; } } } @varlist; } sub TTerror { $ERROR } 1; __END__ =pod =encoding UTF-8 =head1 NAME Text::Template - Expand template text with embedded Perl =head1 VERSION version 1.61 =head1 SYNOPSIS use Text::Template; $template = Text::Template->new(TYPE => 'FILE', SOURCE => 'filename.tmpl'); $template = Text::Template->new(TYPE => 'ARRAY', SOURCE => [ ... ] ); $template = Text::Template->new(TYPE => 'FILEHANDLE', SOURCE => $fh ); $template = Text::Template->new(TYPE => 'STRING', SOURCE => '...' ); $template = Text::Template->new(PREPEND => q{use strict;}, ...); # Use a different template file syntax: $template = Text::Template->new(DELIMITERS => [$open, $close], ...); $recipient = 'King'; $text = $template->fill_in(); # Replaces `{$recipient}' with `King' print $text; $T::recipient = 'Josh'; $text = $template->fill_in(PACKAGE => T); # Pass many variables explicitly $hash = { recipient => 'Abed-Nego', friends => [ 'me', 'you' ], enemies => { loathsome => 'Saruman', fearsome => 'Sauron' }, }; $text = $template->fill_in(HASH => $hash, ...); # $recipient is Abed-Nego, # @friends is ( 'me', 'you' ), # %enemies is ( loathsome => ..., fearsome => ... ) # Call &callback in case of programming errors in template $text = $template->fill_in(BROKEN => \&callback, BROKEN_ARG => $ref, ...); # Evaluate program fragments in Safe compartment with restricted permissions $text = $template->fill_in(SAFE => $compartment, ...); # Print result text instead of returning it $success = $template->fill_in(OUTPUT => \*FILEHANDLE, ...); # Parse template with different template file syntax: $text = $template->fill_in(DELIMITERS => [$open, $close], ...); # Note that this is *faster* than using the default delimiters # Prepend specified perl code to each fragment before evaluating: $text = $template->fill_in(PREPEND => q{use strict 'vars';}, ...); use Text::Template 'fill_in_string'; $text = fill_in_string( <<'EOM', PACKAGE => 'T', ...); Dear {$recipient}, Pay me at once. Love, G.V. EOM use Text::Template 'fill_in_file'; $text = fill_in_file($filename, ...); # All templates will always have `use strict vars' attached to all fragments Text::Template->always_prepend(q{use strict 'vars';}); =head1 DESCRIPTION This is a library for generating form letters, building HTML pages, or filling in templates generally. A `template' is a piece of text that has little Perl programs embedded in it here and there. When you `fill in' a template, you evaluate the little programs and replace them with their values. You can store a template in a file outside your program. People can modify the template without modifying the program. You can separate the formatting details from the main code, and put the formatting parts of the program into the template. That prevents code bloat and encourages functional separation. =head2 Example Here's an example of a template, which we'll suppose is stored in the file C: Dear {$title} {$lastname}, It has come to our attention that you are delinquent in your {$monthname[$last_paid_month]} payment. Please remit ${sprintf("%.2f", $amount)} immediately, or your patellae may be needlessly endangered. Love, Mark "Vizopteryx" Dominus The result of filling in this template is a string, which might look something like this: Dear Mr. Smith, It has come to our attention that you are delinquent in your February payment. Please remit $392.12 immediately, or your patellae may be needlessly endangered. Love, Mark "Vizopteryx" Dominus Here is a complete program that transforms the example template into the example result, and prints it out: use Text::Template; my $template = Text::Template->new(SOURCE => 'formletter.tmpl') or die "Couldn't construct template: $Text::Template::ERROR"; my @monthname = qw(January February March April May June July August September October November December); my %vars = (title => 'Mr.', firstname => 'John', lastname => 'Smith', last_paid_month => 1, # February amount => 392.12, monthname => \@monthname); my $result = $template->fill_in(HASH => \%vars); if (defined $result) { print $result } else { die "Couldn't fill in template: $Text::Template::ERROR" } =head2 Philosophy When people make a template module like this one, they almost always start by inventing a special syntax for substitutions. For example, they build it so that a string like C<%%VAR%%> is replaced with the value of C<$VAR>. Then they realize the need extra formatting, so they put in some special syntax for formatting. Then they need a loop, so they invent a loop syntax. Pretty soon they have a new little template language. This approach has two problems: First, their little language is crippled. If you need to do something the author hasn't thought of, you lose. Second: Who wants to learn another language? You already know Perl, so why not use it? C templates are programmed in I. You embed Perl code in your template, with C<{> at the beginning and C<}> at the end. If you want a variable interpolated, you write it the way you would in Perl. If you need to make a loop, you can use any of the Perl loop constructions. All the Perl built-in functions are available. =head1 Details =head2 Template Parsing The C module scans the template source. An open brace C<{> begins a program fragment, which continues until the matching close brace C<}>. When the template is filled in, the program fragments are evaluated, and each one is replaced with the resulting value to yield the text that is returned. A backslash C<\> in front of a brace (or another backslash that is in front of a brace) escapes its special meaning. The result of filling out this template: \{ The sum of 1 and 2 is {1+2} \} is { The sum of 1 and 2 is 3 } If you have an unmatched brace, C will return a failure code and a warning about where the problem is. Backslashes that do not precede a brace are passed through unchanged. If you have a template like this: { "String that ends in a newline.\n" } The backslash inside the string is passed through to Perl unchanged, so the C<\n> really does turn into a newline. See the note at the end for details about the way backslashes work. Backslash processing is I done when you specify alternative delimiters with the C option. (See L<"Alternative Delimiters">, below.) Each program fragment should be a sequence of Perl statements, which are evaluated the usual way. The result of the last statement executed will be evaluated in scalar context; the result of this statement is a string, which is interpolated into the template in place of the program fragment itself. The fragments are evaluated in order, and side effects from earlier fragments will persist into later fragments: {$x = @things; ''}The Lord High Chamberlain has gotten {$x} things for me this year. { $diff = $x - 17; $more = 'more' if ($diff == 0) { $diff = 'no'; } elsif ($diff < 0) { $more = 'fewer'; } ''; } That is {$diff} {$more} than he gave me last year. The value of C<$x> set in the first line will persist into the next fragment that begins on the third line, and the values of C<$diff> and C<$more> set in the second fragment will persist and be interpolated into the last line. The output will look something like this: The Lord High Chamberlain has gotten 42 things for me this year. That is 25 more than he gave me last year. That is all the syntax there is. =head2 The C<$OUT> variable There is one special trick you can play in a template. Here is the motivation for it: Suppose you are going to pass an array, C<@items>, into the template, and you want the template to generate a bulleted list with a header, like this: Here is a list of the things I have got for you since 1907: * Ivory * Apes * Peacocks * ... One way to do it is with a template like this: Here is a list of the things I have got for you since 1907: { my $blist = ''; foreach $i (@items) { $blist .= qq{ * $i\n}; } $blist; } Here we construct the list in a variable called C<$blist>, which we return at the end. This is a little cumbersome. There is a shortcut. Inside of templates, there is a special variable called C<$OUT>. Anything you append to this variable will appear in the output of the template. Also, if you use C<$OUT> in a program fragment, the normal behavior, of replacing the fragment with its return value, is disabled; instead the fragment is replaced with the value of C<$OUT>. This means that you can write the template above like this: Here is a list of the things I have got for you since 1907: { foreach $i (@items) { $OUT .= " * $i\n"; } } C<$OUT> is reinitialized to the empty string at the start of each program fragment. It is private to C, so you can't use a variable named C<$OUT> in your template without invoking the special behavior. =head2 General Remarks All C functions return C on failure, and set the variable C<$Text::Template::ERROR> to contain an explanation of what went wrong. For example, if you try to create a template from a file that does not exist, C<$Text::Template::ERROR> will contain something like: Couldn't open file xyz.tmpl: No such file or directory =head2 C $template = Text::Template->new( TYPE => ..., SOURCE => ... ); This creates and returns a new template object. C returns C and sets C<$Text::Template::ERROR> if it can't create the template object. C says where the template source code will come from. C says what kind of object the source is. The most common type of source is a file: Text::Template->new( TYPE => 'FILE', SOURCE => $filename ); This reads the template from the specified file. The filename is opened with the Perl C command, so it can be a pipe or anything else that makes sense with C. The C can also be C, in which case the C should be a string: Text::Template->new( TYPE => 'STRING', SOURCE => "This is the actual template!" ); The C can be C, in which case the source should be a reference to an array of strings. The concatenation of these strings is the template: Text::Template->new( TYPE => 'ARRAY', SOURCE => [ "This is ", "the actual", " template!", ] ); The C can be FILEHANDLE, in which case the source should be an open filehandle (such as you got from the C or C packages, or a glob, or a reference to a glob). In this case C will read the text from the filehandle up to end-of-file, and that text is the template: # Read template source code from STDIN: Text::Template->new ( TYPE => 'FILEHANDLE', SOURCE => \*STDIN ); If you omit the C attribute, it's taken to be C. C is required. If you omit it, the program will abort. The words C and C can be spelled any of the following ways: TYPE SOURCE Type Source type source -TYPE -SOURCE -Type -Source -type -source Pick a style you like and stick with it. =over 4 =item C You may also add a C option. If this option is present, its value should be a reference to an array of two strings. The first string is the string that signals the beginning of each program fragment, and the second string is the string that signals the end of each program fragment. See L<"Alternative Delimiters">, below. =item C You may also add a C option. If this option is present, and the C is a C, then the data will be decoded from the given encoding using the L module. You can use any encoding that L recognizes. E.g.: Text::Template->new( TYPE => 'FILE', ENCODING => 'UTF-8', SOURCE => 'xyz.tmpl'); =item C If your program is running in taint mode, you may have problems if your templates are stored in files. Data read from files is considered 'untrustworthy', and taint mode will not allow you to evaluate the Perl code in the file. (It is afraid that a malicious person might have tampered with the file.) In some environments, however, local files are trustworthy. You can tell C that a certain file is trustworthy by supplying C 1> in the call to C. This will tell C to disable taint checks on template code that has come from a file, as long as the filename itself is considered trustworthy. It will also disable taint checks on template code that comes from a filehandle. When used with C 'string'> or C 'array'>, it has no effect. See L for more complete information about tainting. Thanks to Steve Palincsar, Gerard Vreeswijk, and Dr. Christoph Baehr for help with this feature. =item C This option is passed along to the C call unless it is overridden in the arguments to C. See L> feature and using C in templates> below. =item C This option is passed along to the C call unless it is overridden in the arguments to C. See L> below. =back =head2 C $template->compile() Loads all the template text from the template's source, parses and compiles it. If successful, returns true; otherwise returns false and sets C<$Text::Template::ERROR>. If the template is already compiled, it returns true and does nothing. You don't usually need to invoke this function, because C (see below) compiles the template if it isn't compiled already. If there is an argument to this function, it must be a reference to an array containing alternative delimiter strings. See C<"Alternative Delimiters">, below. =head2 C $template->fill_in(OPTIONS); Fills in a template. Returns the resulting text if successful. Otherwise, returns C and sets C<$Text::Template::ERROR>. The I are a hash, or a list of key-value pairs. You can write the key names in any of the six usual styles as above; this means that where this manual says C (for example) you can actually use any of PACKAGE Package package -PACKAGE -Package -package Pick a style you like and stick with it. The all-lowercase versions may yield spurious warnings about Ambiguous use of package => resolved to "package" so you might like to avoid them and use the capitalized versions. At present, there are eight legal options: C, C, C, C, C, C, C, and C. =over 4 =item C C specifies the name of a package in which the program fragments should be evaluated. The default is to use the package from which C was called. For example, consider this template: The value of the variable x is {$x}. If you use C<$template-Efill_in(PACKAGE =E 'R')> , then the C<$x> in the template is actually replaced with the value of C<$R::x>. If you omit the C option, C<$x> will be replaced with the value of the C<$x> variable in the package that actually called C. You should almost always use C. If you don't, and your template makes changes to variables, those changes will be propagated back into the main program. Evaluating the template in a private package helps prevent this. The template can still modify variables in your program if it wants to, but it will have to do so explicitly. See the section at the end on `Security'. Here's an example of using C: Your Royal Highness, Enclosed please find a list of things I have gotten for you since 1907: { foreach $item (@items) { $item_no++; $OUT .= " $item_no. \u$item\n"; } } Signed, Lord High Chamberlain We want to pass in an array which will be assigned to the array C<@items>. Here's how to do that: @items = ('ivory', 'apes', 'peacocks', ); $template->fill_in(); This is not very safe. The reason this isn't as safe is that if you had a variable named C<$item_no> in scope in your program at the point you called C, its value would be clobbered by the act of filling out the template. The problem is the same as if you had written a subroutine that used those variables in the same way that the template does. (C<$OUT> is special in templates and is always safe.) One solution to this is to make the C<$item_no> variable private to the template by declaring it with C. If the template does this, you are safe. But if you use the C option, you will probably be safe even if the template does I declare its variables with C: @Q::items = ('ivory', 'apes', 'peacocks', ); $template->fill_in(PACKAGE => 'Q'); In this case the template will clobber the variable C<$Q::item_no>, which is not related to the one your program was using. Templates cannot affect variables in the main program that are declared with C, unless you give the template references to those variables. =item C You may not want to put the template variables into a package. Packages can be hard to manage: You can't copy them, for example. C provides an alternative. The value for C should be a reference to a hash that maps variable names to values. For example, $template->fill_in( HASH => { recipient => "The King", items => ['gold', 'frankincense', 'myrrh'], object => \$self, } ); will fill out the template and use C<"The King"> as the value of C<$recipient> and the list of items as the value of C<@items>. Note that we pass an array reference, but inside the template it appears as an array. In general, anything other than a simple string or number should be passed by reference. We also want to pass an object, which is in C<$self>; note that we pass a reference to the object, C<\$self> instead. Since we've passed a reference to a scalar, inside the template the object appears as C<$object>. The full details of how it works are a little involved, so you might want to skip to the next section. Suppose the key in the hash is I and the value is I. =over 4 =item * If the I is C, then any variables named C<$key>, C<@key>, C<%key>, etc., are undefined. =item * If the I is a string or a number, then C<$key> is set to that value in the template. =item * For anything else, you must pass a reference. If the I is a reference to an array, then C<@key> is set to that array. If the I is a reference to a hash, then C<%key> is set to that hash. Similarly if I is any other kind of reference. This means that var => "foo" and var => \"foo" have almost exactly the same effect. (The difference is that in the former case, the value is copied, and in the latter case it is aliased.) =item * In particular, if you want the template to get an object or any kind, you must pass a reference to it: $template->fill_in(HASH => { database_handle => \$dbh, ... }); If you do this, the template will have a variable C<$database_handle> which is the database handle object. If you leave out the C<\>, the template will have a hash C<%database_handle>, which exposes the internal structure of the database handle object; you don't want that. =back Normally, the way this works is by allocating a private package, loading all the variables into the package, and then filling out the template as if you had specified that package. A new package is allocated each time. However, if you I use the C option, C loads the variables into the package you specified, and they stay there after the call returns. Subsequent calls to C that use the same package will pick up the values you loaded in. If the argument of C is a reference to an array instead of a reference to a hash, then the array should contain a list of hashes whose contents are loaded into the template package one after the other. You can use this feature if you want to combine several sets of variables. For example, one set of variables might be the defaults for a fill-in form, and the second set might be the user inputs, which override the defaults when they are present: $template->fill_in(HASH => [\%defaults, \%user_input]); You can also use this to set two variables with the same name: $template->fill_in( HASH => [ { v => "The King" }, { v => [1,2,3] } ] ); This sets C<$v> to C<"The King"> and C<@v> to C<(1,2,3)>. =item C If any of the program fragments fails to compile or aborts for any reason, and you have set the C option to a function reference, C will invoke the function. This function is called the I function>. The C function will tell C what to do next. If the C function returns C, C will immediately abort processing the template and return the text that it has accumulated so far. If your function does this, it should set a flag that you can examine after C returns so that you can tell whether there was a premature return or not. If the C function returns any other value, that value will be interpolated into the template as if that value had been the return value of the program fragment to begin with. For example, if the C function returns an error string, the error string will be interpolated into the output of the template in place of the program fragment that cased the error. If you don't specify a C function, C supplies a default one that returns something like Program fragment delivered error ``Illegal division by 0 at template line 37'' (Note that the format of this message has changed slightly since version 1.31.) The return value of the C function is interpolated into the template at the place the error occurred, so that this template: (3+4)*5 = { 3+4)*5 } yields this result: (3+4)*5 = Program fragment delivered error ``syntax error at template line 1'' If you specify a value for the C attribute, it should be a reference to a function that C can call instead of the default function. C will pass a hash to the C function. The hash will have at least these three members: =over 4 =item C The source code of the program fragment that failed =item C The text of the error message (C<$@>) generated by eval. The text has been modified to omit the trailing newline and to include the name of the template file (if there was one). The line number counts from the beginning of the template, not from the beginning of the failed program fragment. =item C The line number of the template at which the program fragment began. =back There may also be an C member. See C, below =item C If you supply the C option to C, the value of the option is passed to the C function whenever it is called. The default C function ignores the C, but you can write a custom C function that uses the C to get more information about what went wrong. The C function could also use the C as a reference to store an error message or some other information that it wants to communicate back to the caller. For example: $error = ''; sub my_broken { my %args = @_; my $err_ref = $args{arg}; ... $$err_ref = "Some error message"; return undef; } $template->fill_in( BROKEN => \&my_broken, BROKEN_ARG => \$error ); if ($error) { die "It didn't work: $error"; } If one of the program fragments in the template fails, it will call the C function, C, and pass it the C, which is a reference to C<$error>. C can store an error message into C<$error> this way. Then the function that called C can see if C has left an error message for it to find, and proceed accordingly. =item C If you give C a C option, then this is the file name that you loaded the template source from. This only affects the error message that is given for template errors. If you loaded the template from C for example, and pass C as the C parameter, errors will look like C<... at foo.txt line N> rather than C<... at template line N>. Note that this does NOT have anything to do with loading a template from the given filename. See C for that. For example: my $template = Text::Template->new( TYPE => 'string', SOURCE => 'The value is {1/0}'); $template->fill_in(FILENAME => 'foo.txt') or die $Text::Template::ERROR; will die with an error that contains Illegal division by zero at at foo.txt line 1 =item C If you give C a C option, its value should be a safe compartment object from the C package. All evaluation of program fragments will be performed in this compartment. See L for full details about such compartments and how to restrict the operations that can be performed in them. If you use the C option with C, the package you specify will be placed into the safe compartment and evaluation will take place in that package as usual. If not, C operation is a little different from the default. Usually, if you don't specify a package, evaluation of program fragments occurs in the package from which the template was invoked. But in C mode the evaluation occurs inside the safe compartment and cannot affect the calling package. Normally, if you use C without C, the hash variables are imported into a private, one-use-only package. But if you use C and C together without C, the hash variables will just be loaded into the root namespace of the C compartment. =item C If your template is going to generate a lot of text that you are just going to print out again anyway, you can save memory by having C print out the text as it is generated instead of making it into a big string and returning the string. If you supply the C option to C, the value should be a filehandle. The generated text will be printed to this filehandle as it is constructed. For example: $template->fill_in(OUTPUT => \*STDOUT, ...); fills in the C<$template> as usual, but the results are immediately printed to STDOUT. This may result in the output appearing more quickly than it would have otherwise. If you use C, the return value from C is still true on success and false on failure, but the complete text is not returned to the caller. =item C You can have some Perl code prepended automatically to the beginning of every program fragment. See L feature and using C in templates> below. =item C If this option is present, its value should be a reference to a list of two strings. The first string is the string that signals the beginning of each program fragment, and the second string is the string that signals the end of each program fragment. See L<"Alternative Delimiters">, below. If you specify C in the call to C, they override any delimiters you set when you created the template object with C. =back =head1 Convenience Functions =head2 C The basic way to fill in a template is to create a template object and then call C on it. This is useful if you want to fill in the same template more than once. In some programs, this can be cumbersome. C accepts a string, which contains the template, and a list of options, which are passed to C as above. It constructs the template object for you, fills it in as specified, and returns the results. It returns C and sets C<$Text::Template::ERROR> if it couldn't generate any results. An example: $Q::name = 'Donald'; $Q::amount = 141.61; $Q::part = 'hyoid bone'; $text = Text::Template->fill_this_in( <<'EOM', PACKAGE => Q); Dear {$name}, You owe me \\${sprintf('%.2f', $amount)}. Pay or I will break your {$part}. Love, Grand Vizopteryx of Irkutsk. EOM Notice how we included the template in-line in the program by using a `here document' with the CE> notation. C is a deprecated feature. It is only here for backwards compatibility, and may be removed in some far-future version in C. You should use C instead. It is described in the next section. =head2 C It is stupid that C is a class method. It should have been just an imported function, so that you could omit the C> in the example above. But I made the mistake four years ago and it is too late to change it. C is exactly like C except that it is not a method and you can omit the C> and just say print fill_in_string(<<'EOM', ...); Dear {$name}, ... EOM To use C, you need to say use Text::Template 'fill_in_string'; at the top of your program. You should probably use C instead of C. =head2 C If you import C, you can say $text = fill_in_file(filename, ...); The C<...> are passed to C as above. The filename is the name of the file that contains the template you want to fill in. It returns the result text. or C, as usual. If you are going to fill in the same file more than once in the same program you should use the longer C / C sequence instead. It will be a lot faster because it only has to read and parse the file once. =head2 Including files into templates People always ask for this. ``Why don't you have an include function?'' they want to know. The short answer is this is Perl, and Perl already has an include function. If you want it, you can just put {qx{cat filename}} into your template. VoilE. If you don't want to use C, you can write a little four-line function that opens a file and dumps out its contents, and call it from the template. I wrote one for you. In the template, you can say {Text::Template::_load_text(filename)} If that is too verbose, here is a trick. Suppose the template package that you are going to be mentioning in the C call is package C. Then in the main program, write *Q::include = \&Text::Template::_load_text; This imports the C<_load_text> function into package C with the name C. From then on, any template that you fill in with package C can say {include(filename)} to insert the text from the named file at that point. If you are using the C option instead, just put C \&Text::Template::_load_text> into the hash instead of importing it explicitly. Suppose you don't want to insert a plain text file, but rather you want to include one template within another? Just use C in the template itself: {Text::Template::fill_in_file(filename)} You can do the same importing trick if this is too much to type. =head1 Miscellaneous =head2 C variables People are frequently surprised when this doesn't work: my $recipient = 'The King'; my $text = fill_in_file('formletter.tmpl'); The text C doesn't get into the form letter. Why not? Because C<$recipient> is a C variable, and the whole point of C variables is that they're private and inaccessible except in the scope in which they're declared. The template is not part of that scope, so the template can't see C<$recipient>. If that's not the behavior you want, don't use C. C means a private variable, and in this case you don't want the variable to be private. Put the variables into package variables in some other package, and use the C option to C: $Q::recipient = $recipient; my $text = fill_in_file('formletter.tmpl', PACKAGE => 'Q'); or pass the names and values in a hash with the C option: my $text = fill_in_file('formletter.tmpl', HASH => { recipient => $recipient }); =head2 Security Matters All variables are evaluated in the package you specify with the C option of C. if you use this option, and if your templates don't do anything egregiously stupid, you won't have to worry that evaluation of the little programs will creep out into the rest of your program and wreck something. Nevertheless, there's really no way (except with C) to protect against a template that says { $Important::Secret::Security::Enable = 0; # Disable security checks in this program } or { $/ = "ho ho ho"; # Sabotage future uses of . # $/ is always a global variable } or even { system("rm -rf /") } so B go filling in templates unless you're sure you know what's in them. If you're worried, or you can't trust the person who wrote the template, use the C option. A final warning: program fragments run a small risk of accidentally clobbering local variables in the C function itself. These variables all have names that begin with C<$fi_>, so if you stay away from those names you'll be safe. (Of course, if you're a real wizard you can tamper with them deliberately for exciting effects; this is actually how C<$OUT> works.) I can fix this, but it will make the package slower to do it, so I would prefer not to. If you are worried about this, send me mail and I will show you what to do about it. =head2 Alternative Delimiters Lorenzo Valdettaro pointed out that if you are using C to generate TeX output, the choice of braces as the program fragment delimiters makes you suffer suffer suffer. Starting in version 1.20, you can change the choice of delimiters to something other than curly braces. In either the C call or the C call, you can specify an alternative set of delimiters with the C option. For example, if you would like code fragments to be delimited by C<[@--> and C<--@]> instead of C<{> and C<}>, use ... DELIMITERS => [ '[@--', '--@]' ], ... Note that these delimiters are I, not regexes. (I tried for regexes, but it complicates the lexical analysis too much.) Note also that C disables the special meaning of the backslash, so if you want to include the delimiters in the literal text of your template file, you are out of luck---it is up to you to choose delimiters that do not conflict with what you are doing. The delimiter strings may still appear inside of program fragments as long as they nest properly. This means that if for some reason you absolutely must have a program fragment that mentions one of the delimiters, like this: [@-- print "Oh no, a delimiter: --@]\n" --@] you may be able to make it work by doing this instead: [@-- # Fake matching delimiter in a comment: [@-- print "Oh no, a delimiter: --@]\n" --@] It may be safer to choose delimiters that begin with a newline character. Because the parsing of templates is simplified by the absence of backslash escapes, using alternative C may speed up the parsing process by 20-25%. This shows that my original choice of C<{> and C<}> was very bad. =head2 C feature and using C in templates Suppose you would like to use C in your templates to detect undeclared variables and the like. But each code fragment is a separate lexical scope, so you have to turn on C at the top of each and every code fragment: { use strict; use vars '$foo'; $foo = 14; ... } ... { # we forgot to put `use strict' here my $result = $boo + 12; # $boo is misspelled and should be $foo # No error is raised on `$boo' } Because we didn't put C at the top of the second fragment, it was only active in the first fragment, and we didn't get any C checking in the second fragment. Then we misspelled C<$foo> and the error wasn't caught. C version 1.22 and higher has a new feature to make this easier. You can specify that any text at all be automatically added to the beginning of each program fragment. When you make a call to C, you can specify a PREPEND => 'some perl statements here' option; the statements will be prepended to each program fragment for that one call only. Suppose that the C call included a PREPEND => 'use strict;' option, and that the template looked like this: { use vars '$foo'; $foo = 14; ... } ... { my $result = $boo + 12; # $boo is misspelled and should be $foo ... } The code in the second fragment would fail, because C<$boo> has not been declared. C was implied, even though you did not write it explicitly, because the C option added it for you automatically. There are three other ways to do this. At the time you create the template object with C, you can also supply a C option, in which case the statements will be prepended each time you fill in that template. If the C call has its own C option, this overrides the one specified at the time you created the template. Finally, you can make the class method call Text::Template->always_prepend('perl statements'); If you do this, then call calls to C for I template will attach the perl statements to the beginning of each program fragment, except where overridden by C options to C or C. An alternative to adding "use strict;" to the PREPEND option, you can pass STRICT => 1 to fill_in when also passing the HASH option. Suppose that the C call included both HASH => {$foo => ''} and STRICT => 1 options, and that the template looked like this: { $foo = 14; ... } ... { my $result = $boo + 12; # $boo is misspelled and should be $foo ... } The code in the second fragment would fail, because C<$boo> has not been declared. C was implied, even though you did not write it explicitly, because the C option added it for you automatically. Any variable referenced in the template that is not in the C option will be an error. =head2 Prepending in Derived Classes This section is technical, and you should skip it on the first few readings. Normally there are three places that prepended text could come from. It could come from the C option in the C call, from the C option in the C call that created the template object, or from the argument of the C call. C looks for these three things in order and takes the first one that it finds. In a subclass of C, this last possibility is ambiguous. Suppose C is a subclass of C. Should Text::Template->always_prepend(...); affect objects in class C? The answer is that you can have it either way. The C value for C is normally stored in a hash variable named C<%GLOBAL_PREPEND> under the key C. When C looks to see what text to prepend, it first looks in the template object itself, and if not, it looks in C<$GLOBAL_PREPEND{I}> where I is the class to which the template object belongs. If it doesn't find any value, it looks in C<$GLOBAL_PREPEND{'Text::Template'}>. This means that objects in class C I be affected by Text::Template->always_prepend(...); I there is also a call to Derived->always_prepend(...); So when you're designing your derived class, you can arrange to have your objects ignore C calls by simply putting Calways_prepend('')> at the top of your module. Of course, there is also a final escape hatch: Templates support a C that is used to look up the appropriate text to be prepended at C time. Your derived class can override this method to get an arbitrary effect. =head2 JavaScript Jennifer D. St Clair asks: > Most of my pages contain JavaScript and Stylesheets. > How do I change the template identifier? Jennifer is worried about the braces in the JavaScript being taken as the delimiters of the Perl program fragments. Of course, disaster will ensue when perl tries to evaluate these as if they were Perl programs. The best choice is to find some unambiguous delimiter strings that you can use in your template instead of curly braces, and then use the C option. However, if you can't do this for some reason, there are two easy workarounds: 1. You can put C<\> in front of C<{>, C<}>, or C<\> to remove its special meaning. So, for example, instead of if (br== "n3") { // etc. } you can put if (br== "n3") \{ // etc. \} and it'll come out of the template engine the way you want. But here is another method that is probably better. To see how it works, first consider what happens if you put this into a template: { 'foo' } Since it's in braces, it gets evaluated, and obviously, this is going to turn into foo So now here's the trick: In Perl, C is the same as C<'...'>. So if we wrote {q{foo}} it would turn into foo So for your JavaScript, just write {q{if (br== "n3") { // etc. }} } and it'll come out as if (br== "n3") { // etc. } which is what you want. head2 Shut Up! People sometimes try to put an initialization section at the top of their templates, like this: { ... $var = 17; } Then they complain because there is a C<17> at the top of the output that they didn't want to have there. Remember that a program fragment is replaced with its own return value, and that in Perl the return value of a code block is the value of the last expression that was evaluated, which in this case is 17. If it didn't do that, you wouldn't be able to write C<{$recipient}> and have the recipient filled in. To prevent the 17 from appearing in the output is very simple: { ... $var = 17; ''; } Now the last expression evaluated yields the empty string, which is invisible. If you don't like the way this looks, use { ... $var = 17; ($SILENTLY); } instead. Presumably, C<$SILENTLY> has no value, so nothing will be interpolated. This is what is known as a `trick'. =head2 Compatibility Every effort has been made to make this module compatible with older versions. The only known exceptions follow: The output format of the default C subroutine has changed twice, most recently between versions 1.31 and 1.40. Starting in version 1.10, the C<$OUT> variable is arrogated for a special meaning. If you had templates before version 1.10 that happened to use a variable named C<$OUT>, you will have to change them to use some other variable or all sorts of strangeness will result. Between versions 0.1b and 1.00 the behavior of the \ metacharacter changed. In 0.1b, \\ was special everywhere, and the template processor always replaced it with a single backslash before passing the code to Perl for evaluation. The rule now is more complicated but probably more convenient. See the section on backslash processing, below, for a full discussion. =head2 Backslash Processing In C beta versions, the backslash was special whenever it appeared before a brace or another backslash. That meant that while C<{"\n"}> did indeed generate a newline, C<{"\\"}> did not generate a backslash, because the code passed to Perl for evaluation was C<"\"> which is a syntax error. If you wanted a backslash, you would have had to write C<{"\\\\"}>. In C versions 1.00 through 1.10, there was a bug: Backslash was special everywhere. In these versions, C<{"\n"}> generated the letter C. The bug has been corrected in version 1.11, but I did not go back to exactly the old rule, because I did not like the idea of having to write C<{"\\\\"}> to get one backslash. The rule is now more complicated to remember, but probably easier to use. The rule is now: Backslashes are always passed to Perl unchanged I they occur as part of a sequence like C<\\\\\\{> or C<\\\\\\}>. In these contexts, they are special; C<\\> is replaced with C<\>, and C<\{> and C<\}> signal a literal brace. Examples: \{ foo \} is I evaluated, because the C<\> before the braces signals that they should be taken literally. The result in the output looks like this: { foo } This is a syntax error: { "foo}" } because C thinks that the code ends at the first C<}>, and then gets upset when it sees the second one. To make this work correctly, use { "foo\}" } This passes C<"foo}"> to Perl for evaluation. Note there's no C<\> in the evaluated code. If you really want a C<\> in the evaluated code, use { "foo\\\}" } This passes C<"foo\}"> to Perl for evaluation. Starting with C version 1.20, backslash processing is disabled if you use the C option to specify alternative delimiter strings. =head2 A short note about C<$Text::Template::ERROR> In the past some people have fretted about `violating the package boundary' by examining a variable inside the C package. Don't feel this way. C<$Text::Template::ERROR> is part of the published, official interface to this package. It is perfectly OK to inspect this variable. The interface is not going to change. If it really, really bothers you, you can import a function called C that returns the current value of the C<$ERROR> variable. So you can say: use Text::Template 'TTerror'; my $template = Text::Template->new(SOURCE => $filename); unless ($template) { my $err = TTerror; die "Couldn't make template: $err; aborting"; } I don't see what benefit this has over just doing this: use Text::Template; my $template = Text::Template->new(SOURCE => $filename) or die "Couldn't make template: $Text::Template::ERROR; aborting"; But if it makes you happy to do it that way, go ahead. =head2 Sticky Widgets in Template Files The C module provides functions for `sticky widgets', which are form input controls that retain their values from one page to the next. Sometimes people want to know how to include these widgets into their template output. It's totally straightforward. Just call the C functions from inside the template: { $q->checkbox_group(NAME => 'toppings', LINEBREAK => true, COLUMNS => 3, VALUES => \@toppings, ); } =head2 Automatic preprocessing of program fragments It may be useful to preprocess the program fragments before they are evaluated. See C for more details. =head2 Automatic postprocessing of template hunks It may be useful to process hunks of output before they are appended to the result text. For this, subclass and replace the C method. It is passed a list of pairs with these entries: handle - a filehandle to which to print the desired output out - a ref to a string to which to append, to use if handle is not given text - the text that will be appended type - where the text came from: TEXT for literal text, PROG for code =head1 HISTORY Originally written by Mark Jason Dominus, Plover Systems (versions 0.01 - 1.46) Maintainership transferred to Michael Schout Emschout@cpan.orgE in version 1.47 =head1 THANKS Many thanks to the following people for offering support, encouragement, advice, bug reports, and all the other good stuff. =over 4 =item * Andrew G Wood =item * Andy Wardley =item * António Aragão =item * Archie Warnock =item * Bek Oberin =item * Bob Dougherty =item * Brian C. Shensky =item * Chris Nandor =item * Chris Wesley =item * Chris.Brezil =item * Daini Xie =item * Dan Franklin =item * Daniel LaLiberte =item * David H. Adler =item * David Marshall =item * Dennis Taylor =item * Donald L. Greer Jr. =item * Dr. Frank Bucolo =item * Fred Steinberg =item * Gene Damon =item * Hans Persson =item * Hans Stoop =item * Itamar Almeida de Carvalho =item * James H. Thompson =item * James Mastros =item * Jarko Hietaniemi =item * Jason Moore =item * Jennifer D. St Clair =item * Joel Appelbaum =item * Joel Meulenberg =item * Jonathan Roy =item * Joseph Cheek =item * Juan E. Camacho =item * Kevin Atteson =item * Kevin Madsen =item * Klaus Arnhold =item * Larry Virden =item * Lieven Tomme =item * Lorenzo Valdettaro =item * Marek Grac =item * Matt Womer =item * Matt X. Hunter =item * Michael G Schwern =item * Michael J. Suzio =item * Michaely Yeung =item * Michelangelo Grigni =item * Mike Brodhead =item * Niklas Skoglund =item * Randal L. Schwartz =item * Reuven M. Lerner =item * Robert M. Ioffe =item * Ron Pero =item * San Deng =item * Sean Roehnelt =item * Sergey Myasnikov =item * Shabbir J. Safdar =item * Shad Todd =item * Steve Palincsar =item * Tim Bunce =item * Todd A. Green =item * Tom Brown =item * Tom Henry =item * Tom Snee =item * Trip Lilley =item * Uwe Schneider =item * Val Luck =item * Yannis Livassof =item * Yonat Sharon =item * Zac Hansen =item * gary at dls.net =back Special thanks to: =over 2 =item Jonathan Roy for telling me how to do the C support (I spent two years worrying about it, and then Jonathan pointed out that it was trivial.) =item Ranjit Bhatnagar for demanding less verbose fragments like they have in ASP, for helping me figure out the Right Thing, and, especially, for talking me out of adding any new syntax. These discussions resulted in the C<$OUT> feature. =back =head2 Bugs and Caveats C variables in C are still susceptible to being clobbered by template evaluation. They all begin with C, so avoid those names in your templates. The line number information will be wrong if the template's lines are not terminated by C<"\n">. You should let me know if this is a problem. If you do, I will fix it. The C<$OUT> variable has a special meaning in templates, so you cannot use it as if it were a regular variable. There are not quite enough tests in the test suite. =head1 SOURCE The development version is on github at L and may be cloned from L =head1 BUGS Please report any bugs or feature requests on the bugtracker website L When submitting a bug or request, please include a test-file or a patch to an existing test-file that illustrates the bug or desired feature. =head1 AUTHOR Michael Schout =head1 COPYRIGHT AND LICENSE This software is copyright (c) 2013 by Mark Jason Dominus . This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself. =cut PK!lib/auto/Text/Template/.existsnu[PK!5zz#man3/Text::Template::Preprocess.3pmnu[.\" Automatically generated by Pod::Man 4.11 (Pod::Simple 3.35) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is >0, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{\ . if \nF \{\ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{\ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" ======================================================================== .\" .IX Title "Text::Template::Preprocess 3" .TH Text::Template::Preprocess 3 "2022-04-28" "perl v5.26.3" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" Text::Template::Preprocess \- Expand template text with embedded Perl .SH "VERSION" .IX Header "VERSION" version 1.61 .SH "SYNOPSIS" .IX Header "SYNOPSIS" .Vb 1 \& use Text::Template::Preprocess; \& \& my $t = Text::Template::Preprocess\->new(...); # identical to Text::Template \& \& # Fill in template, but preprocess each code fragment with pp(). \& my $result = $t\->fill_in(..., PREPROCESSOR => \e&pp); \& \& my $old_pp = $t\->preprocessor(\e&new_pp); .Ve .SH "DESCRIPTION" .IX Header "DESCRIPTION" \&\f(CW\*(C`Text::Template::Preprocess\*(C'\fR provides a new \f(CW\*(C`PREPROCESSOR\*(C'\fR option to \&\f(CW\*(C`fill_in\*(C'\fR. If the \f(CW\*(C`PREPROCESSOR\*(C'\fR option is supplied, it must be a reference to a preprocessor subroutine. When filling out a template, \&\f(CW\*(C`Text::Template::Preprocessor\*(C'\fR will use this subroutine to preprocess the program fragment prior to evaluating the code. .PP The preprocessor subroutine will be called repeatedly, once for each program fragment. The program fragment will be in \f(CW$_\fR. The subroutine should modify the contents of \f(CW$_\fR and return. \&\f(CW\*(C`Text::Template::Preprocess\*(C'\fR will then execute contents of \f(CW$_\fR and insert the result into the appropriate part of the template. .PP \&\f(CW\*(C`Text::Template::Preprocess\*(C'\fR objects also support a utility method, \&\f(CW\*(C`preprocessor()\*(C'\fR, which sets a new preprocessor for the object. This preprocessor is used for all subsequent calls to \f(CW\*(C`fill_in\*(C'\fR except where overridden by an explicit \f(CW\*(C`PREPROCESSOR\*(C'\fR option. \&\f(CW\*(C`preprocessor()\*(C'\fR returns the previous default preprocessor function, or undefined if there wasn't one. When invoked with no arguments, \&\f(CW\*(C`preprocessor()\*(C'\fR returns the object's current default preprocessor function without changing it. .PP In all other respects, \f(CW\*(C`Text::Template::Preprocess\*(C'\fR is identical to \&\f(CW\*(C`Text::Template\*(C'\fR. .SH "WHY?" .IX Header "WHY?" One possible purpose: If your files contain a lot of JavaScript, like this: .PP .Vb 9 \& Plain text here... \& { perl code } \& \& { more perl code } \& More plain text... .Ve .PP You don't want \f(CW\*(C`Text::Template\*(C'\fR to confuse the curly braces in the JavaScript program with executable Perl code. One strategy: .PP .Vb 3 \& sub quote_scripts { \& s()(q{$1})gsi; \& } .Ve .PP Then use \f(CW\*(C`PREPROCESSOR => \e"e_scripts\*(C'\fR. This will transform .SH "SEE ALSO" .IX Header "SEE ALSO" Text::Template .SH "SOURCE" .IX Header "SOURCE" The development version is on github at and may be cloned from .SH "BUGS" .IX Header "BUGS" Please report any bugs or feature requests on the bugtracker website .PP When submitting a bug or request, please include a test-file or a patch to an existing test-file that illustrates the bug or desired feature. .SH "AUTHOR" .IX Header "AUTHOR" Mark Jason Dominus, Plover Systems .PP Please send questions and other remarks about this software to \&\f(CW\*(C`mjd\-perl\-template+@plover.com\*(C'\fR .PP You can join a very low-volume (<10 messages per year) mailing list for announcements about this package. Send an empty note to \&\f(CW\*(C`mjd\-perl\-template\-request@plover.com\*(C'\fR to join. .PP For updates, visit \f(CW\*(C`http://www.plover.com/~mjd/perl/Template/\*(C'\fR. .SH "COPYRIGHT AND LICENSE" .IX Header "COPYRIGHT AND LICENSE" This software is copyright (c) 2013 by Mark Jason Dominus . .PP This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself. PK!]pman3/Text::Template.3pmnu[.\" Automatically generated by Pod::Man 4.11 (Pod::Simple 3.35) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is >0, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{\ . if \nF \{\ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{\ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" ======================================================================== .\" .IX Title "Text::Template 3" .TH Text::Template 3 "2022-04-28" "perl v5.26.3" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" Text::Template \- Expand template text with embedded Perl .SH "VERSION" .IX Header "VERSION" version 1.61 .SH "SYNOPSIS" .IX Header "SYNOPSIS" .Vb 1 \& use Text::Template; \& \& \& $template = Text::Template\->new(TYPE => \*(AqFILE\*(Aq, SOURCE => \*(Aqfilename.tmpl\*(Aq); \& $template = Text::Template\->new(TYPE => \*(AqARRAY\*(Aq, SOURCE => [ ... ] ); \& $template = Text::Template\->new(TYPE => \*(AqFILEHANDLE\*(Aq, SOURCE => $fh ); \& $template = Text::Template\->new(TYPE => \*(AqSTRING\*(Aq, SOURCE => \*(Aq...\*(Aq ); \& $template = Text::Template\->new(PREPEND => q{use strict;}, ...); \& \& # Use a different template file syntax: \& $template = Text::Template\->new(DELIMITERS => [$open, $close], ...); \& \& $recipient = \*(AqKing\*(Aq; \& $text = $template\->fill_in(); # Replaces \`{$recipient}\*(Aq with \`King\*(Aq \& print $text; \& \& $T::recipient = \*(AqJosh\*(Aq; \& $text = $template\->fill_in(PACKAGE => T); \& \& # Pass many variables explicitly \& $hash = { recipient => \*(AqAbed\-Nego\*(Aq, \& friends => [ \*(Aqme\*(Aq, \*(Aqyou\*(Aq ], \& enemies => { loathsome => \*(AqSaruman\*(Aq, \& fearsome => \*(AqSauron\*(Aq }, \& }; \& $text = $template\->fill_in(HASH => $hash, ...); \& # $recipient is Abed\-Nego, \& # @friends is ( \*(Aqme\*(Aq, \*(Aqyou\*(Aq ), \& # %enemies is ( loathsome => ..., fearsome => ... ) \& \& \& # Call &callback in case of programming errors in template \& $text = $template\->fill_in(BROKEN => \e&callback, BROKEN_ARG => $ref, ...); \& \& # Evaluate program fragments in Safe compartment with restricted permissions \& $text = $template\->fill_in(SAFE => $compartment, ...); \& \& # Print result text instead of returning it \& $success = $template\->fill_in(OUTPUT => \e*FILEHANDLE, ...); \& \& # Parse template with different template file syntax: \& $text = $template\->fill_in(DELIMITERS => [$open, $close], ...); \& # Note that this is *faster* than using the default delimiters \& \& # Prepend specified perl code to each fragment before evaluating: \& $text = $template\->fill_in(PREPEND => q{use strict \*(Aqvars\*(Aq;}, ...); \& \& use Text::Template \*(Aqfill_in_string\*(Aq; \& $text = fill_in_string( <<\*(AqEOM\*(Aq, PACKAGE => \*(AqT\*(Aq, ...); \& Dear {$recipient}, \& Pay me at once. \& Love, \& G.V. \& EOM \& \& use Text::Template \*(Aqfill_in_file\*(Aq; \& $text = fill_in_file($filename, ...); \& \& # All templates will always have \`use strict vars\*(Aq attached to all fragments \& Text::Template\->always_prepend(q{use strict \*(Aqvars\*(Aq;}); .Ve .SH "DESCRIPTION" .IX Header "DESCRIPTION" This is a library for generating form letters, building \s-1HTML\s0 pages, or filling in templates generally. A `template' is a piece of text that has little Perl programs embedded in it here and there. When you `fill in' a template, you evaluate the little programs and replace them with their values. .PP You can store a template in a file outside your program. People can modify the template without modifying the program. You can separate the formatting details from the main code, and put the formatting parts of the program into the template. That prevents code bloat and encourages functional separation. .SS "Example" .IX Subsection "Example" Here's an example of a template, which we'll suppose is stored in the file \f(CW\*(C`formletter.tmpl\*(C'\fR: .PP .Vb 1 \& Dear {$title} {$lastname}, \& \& It has come to our attention that you are delinquent in your \& {$monthname[$last_paid_month]} payment. Please remit \& ${sprintf("%.2f", $amount)} immediately, or your patellae may \& be needlessly endangered. \& \& Love, \& \& Mark "Vizopteryx" Dominus .Ve .PP The result of filling in this template is a string, which might look something like this: .PP .Vb 1 \& Dear Mr. Smith, \& \& It has come to our attention that you are delinquent in your \& February payment. Please remit \& $392.12 immediately, or your patellae may \& be needlessly endangered. \& \& \& Love, \& \& Mark "Vizopteryx" Dominus .Ve .PP Here is a complete program that transforms the example template into the example result, and prints it out: .PP .Vb 1 \& use Text::Template; \& \& my $template = Text::Template\->new(SOURCE => \*(Aqformletter.tmpl\*(Aq) \& or die "Couldn\*(Aqt construct template: $Text::Template::ERROR"; \& \& my @monthname = qw(January February March April May June \& July August September October November December); \& my %vars = (title => \*(AqMr.\*(Aq, \& firstname => \*(AqJohn\*(Aq, \& lastname => \*(AqSmith\*(Aq, \& last_paid_month => 1, # February \& amount => 392.12, \& monthname => \e@monthname); \& \& my $result = $template\->fill_in(HASH => \e%vars); \& \& if (defined $result) { print $result } \& else { die "Couldn\*(Aqt fill in template: $Text::Template::ERROR" } .Ve .SS "Philosophy" .IX Subsection "Philosophy" When people make a template module like this one, they almost always start by inventing a special syntax for substitutions. For example, they build it so that a string like \f(CW\*(C`%%VAR%%\*(C'\fR is replaced with the value of \f(CW$VAR\fR. Then they realize the need extra formatting, so they put in some special syntax for formatting. Then they need a loop, so they invent a loop syntax. Pretty soon they have a new little template language. .PP This approach has two problems: First, their little language is crippled. If you need to do something the author hasn't thought of, you lose. Second: Who wants to learn another language? You already know Perl, so why not use it? .PP \&\f(CW\*(C`Text::Template\*(C'\fR templates are programmed in \fIPerl\fR. You embed Perl code in your template, with \f(CW\*(C`{\*(C'\fR at the beginning and \f(CW\*(C`}\*(C'\fR at the end. If you want a variable interpolated, you write it the way you would in Perl. If you need to make a loop, you can use any of the Perl loop constructions. All the Perl built-in functions are available. .SH "Details" .IX Header "Details" .SS "Template Parsing" .IX Subsection "Template Parsing" The \f(CW\*(C`Text::Template\*(C'\fR module scans the template source. An open brace \&\f(CW\*(C`{\*(C'\fR begins a program fragment, which continues until the matching close brace \f(CW\*(C`}\*(C'\fR. When the template is filled in, the program fragments are evaluated, and each one is replaced with the resulting value to yield the text that is returned. .PP A backslash \f(CW\*(C`\e\*(C'\fR in front of a brace (or another backslash that is in front of a brace) escapes its special meaning. The result of filling out this template: .PP .Vb 1 \& \e{ The sum of 1 and 2 is {1+2} \e} .Ve .PP is .PP .Vb 1 \& { The sum of 1 and 2 is 3 } .Ve .PP If you have an unmatched brace, \f(CW\*(C`Text::Template\*(C'\fR will return a failure code and a warning about where the problem is. Backslashes that do not precede a brace are passed through unchanged. If you have a template like this: .PP .Vb 1 \& { "String that ends in a newline.\en" } .Ve .PP The backslash inside the string is passed through to Perl unchanged, so the \f(CW\*(C`\en\*(C'\fR really does turn into a newline. See the note at the end for details about the way backslashes work. Backslash processing is \&\fInot\fR done when you specify alternative delimiters with the \&\f(CW\*(C`DELIMITERS\*(C'\fR option. (See \*(L"Alternative Delimiters\*(R", below.) .PP Each program fragment should be a sequence of Perl statements, which are evaluated the usual way. The result of the last statement executed will be evaluated in scalar context; the result of this statement is a string, which is interpolated into the template in place of the program fragment itself. .PP The fragments are evaluated in order, and side effects from earlier fragments will persist into later fragments: .PP .Vb 12 \& {$x = @things; \*(Aq\*(Aq}The Lord High Chamberlain has gotten {$x} \& things for me this year. \& { $diff = $x \- 17; \& $more = \*(Aqmore\*(Aq \& if ($diff == 0) { \& $diff = \*(Aqno\*(Aq; \& } elsif ($diff < 0) { \& $more = \*(Aqfewer\*(Aq; \& } \& \*(Aq\*(Aq; \& } \& That is {$diff} {$more} than he gave me last year. .Ve .PP The value of \f(CW$x\fR set in the first line will persist into the next fragment that begins on the third line, and the values of \f(CW$diff\fR and \&\f(CW$more\fR set in the second fragment will persist and be interpolated into the last line. The output will look something like this: .PP .Vb 2 \& The Lord High Chamberlain has gotten 42 \& things for me this year. \& \& That is 25 more than he gave me last year. .Ve .PP That is all the syntax there is. .ie n .SS "The $OUT variable" .el .SS "The \f(CW$OUT\fP variable" .IX Subsection "The $OUT variable" There is one special trick you can play in a template. Here is the motivation for it: Suppose you are going to pass an array, \f(CW@items\fR, into the template, and you want the template to generate a bulleted list with a header, like this: .PP .Vb 5 \& Here is a list of the things I have got for you since 1907: \& * Ivory \& * Apes \& * Peacocks \& * ... .Ve .PP One way to do it is with a template like this: .PP .Vb 7 \& Here is a list of the things I have got for you since 1907: \& { my $blist = \*(Aq\*(Aq; \& foreach $i (@items) { \& $blist .= qq{ * $i\en}; \& } \& $blist; \& } .Ve .PP Here we construct the list in a variable called \f(CW$blist\fR, which we return at the end. This is a little cumbersome. There is a shortcut. .PP Inside of templates, there is a special variable called \f(CW$OUT\fR. Anything you append to this variable will appear in the output of the template. Also, if you use \f(CW$OUT\fR in a program fragment, the normal behavior, of replacing the fragment with its return value, is disabled; instead the fragment is replaced with the value of \f(CW$OUT\fR. This means that you can write the template above like this: .PP .Vb 5 \& Here is a list of the things I have got for you since 1907: \& { foreach $i (@items) { \& $OUT .= " * $i\en"; \& } \& } .Ve .PP \&\f(CW$OUT\fR is reinitialized to the empty string at the start of each program fragment. It is private to \f(CW\*(C`Text::Template\*(C'\fR, so you can't use a variable named \f(CW$OUT\fR in your template without invoking the special behavior. .SS "General Remarks" .IX Subsection "General Remarks" All \f(CW\*(C`Text::Template\*(C'\fR functions return \f(CW\*(C`undef\*(C'\fR on failure, and set the variable \f(CW$Text::Template::ERROR\fR to contain an explanation of what went wrong. For example, if you try to create a template from a file that does not exist, \f(CW$Text::Template::ERROR\fR will contain something like: .PP .Vb 1 \& Couldn\*(Aqt open file xyz.tmpl: No such file or directory .Ve .ie n .SS """new""" .el .SS "\f(CWnew\fP" .IX Subsection "new" .Vb 1 \& $template = Text::Template\->new( TYPE => ..., SOURCE => ... ); .Ve .PP This creates and returns a new template object. \f(CW\*(C`new\*(C'\fR returns \&\f(CW\*(C`undef\*(C'\fR and sets \f(CW$Text::Template::ERROR\fR if it can't create the template object. \f(CW\*(C`SOURCE\*(C'\fR says where the template source code will come from. \f(CW\*(C`TYPE\*(C'\fR says what kind of object the source is. .PP The most common type of source is a file: .PP .Vb 1 \& Text::Template\->new( TYPE => \*(AqFILE\*(Aq, SOURCE => $filename ); .Ve .PP This reads the template from the specified file. The filename is opened with the Perl \f(CW\*(C`open\*(C'\fR command, so it can be a pipe or anything else that makes sense with \f(CW\*(C`open\*(C'\fR. .PP The \f(CW\*(C`TYPE\*(C'\fR can also be \f(CW\*(C`STRING\*(C'\fR, in which case the \f(CW\*(C`SOURCE\*(C'\fR should be a string: .PP .Vb 2 \& Text::Template\->new( TYPE => \*(AqSTRING\*(Aq, \& SOURCE => "This is the actual template!" ); .Ve .PP The \f(CW\*(C`TYPE\*(C'\fR can be \f(CW\*(C`ARRAY\*(C'\fR, in which case the source should be a reference to an array of strings. The concatenation of these strings is the template: .PP .Vb 5 \& Text::Template\->new( TYPE => \*(AqARRAY\*(Aq, \& SOURCE => [ "This is ", "the actual", \& " template!", \& ] \& ); .Ve .PP The \f(CW\*(C`TYPE\*(C'\fR can be \s-1FILEHANDLE,\s0 in which case the source should be an open filehandle (such as you got from the \f(CW\*(C`FileHandle\*(C'\fR or \f(CW\*(C`IO::*\*(C'\fR packages, or a glob, or a reference to a glob). In this case \&\f(CW\*(C`Text::Template\*(C'\fR will read the text from the filehandle up to end-of-file, and that text is the template: .PP .Vb 3 \& # Read template source code from STDIN: \& Text::Template\->new ( TYPE => \*(AqFILEHANDLE\*(Aq, \& SOURCE => \e*STDIN ); .Ve .PP If you omit the \f(CW\*(C`TYPE\*(C'\fR attribute, it's taken to be \f(CW\*(C`FILE\*(C'\fR. \&\f(CW\*(C`SOURCE\*(C'\fR is required. If you omit it, the program will abort. .PP The words \f(CW\*(C`TYPE\*(C'\fR and \f(CW\*(C`SOURCE\*(C'\fR can be spelled any of the following ways: .PP .Vb 6 \& TYPE SOURCE \& Type Source \& type source \& \-TYPE \-SOURCE \& \-Type \-Source \& \-type \-source .Ve .PP Pick a style you like and stick with it. .ie n .IP """DELIMITERS""" 4 .el .IP "\f(CWDELIMITERS\fR" 4 .IX Item "DELIMITERS" You may also add a \f(CW\*(C`DELIMITERS\*(C'\fR option. If this option is present, its value should be a reference to an array of two strings. The first string is the string that signals the beginning of each program fragment, and the second string is the string that signals the end of each program fragment. See \*(L"Alternative Delimiters\*(R", below. .ie n .IP """ENCODING""" 4 .el .IP "\f(CWENCODING\fR" 4 .IX Item "ENCODING" You may also add a \f(CW\*(C`ENCODING\*(C'\fR option. If this option is present, and the \&\f(CW\*(C`SOURCE\*(C'\fR is a \f(CW\*(C`FILE\*(C'\fR, then the data will be decoded from the given encoding using the Encode module. You can use any encoding that Encode recognizes. E.g.: .Sp .Vb 4 \& Text::Template\->new( \& TYPE => \*(AqFILE\*(Aq, \& ENCODING => \*(AqUTF\-8\*(Aq, \& SOURCE => \*(Aqxyz.tmpl\*(Aq); .Ve .ie n .IP """UNTAINT""" 4 .el .IP "\f(CWUNTAINT\fR" 4 .IX Item "UNTAINT" If your program is running in taint mode, you may have problems if your templates are stored in files. Data read from files is considered 'untrustworthy', and taint mode will not allow you to evaluate the Perl code in the file. (It is afraid that a malicious person might have tampered with the file.) .Sp In some environments, however, local files are trustworthy. You can tell \f(CW\*(C`Text::Template\*(C'\fR that a certain file is trustworthy by supplying \&\f(CW\*(C`UNTAINT => 1\*(C'\fR in the call to \f(CW\*(C`new\*(C'\fR. This will tell \&\f(CW\*(C`Text::Template\*(C'\fR to disable taint checks on template code that has come from a file, as long as the filename itself is considered trustworthy. It will also disable taint checks on template code that comes from a filehandle. When used with \f(CW\*(C`TYPE => \*(Aqstring\*(Aq\*(C'\fR or \f(CW\*(C`TYPE => \*(Aqarray\*(Aq\*(C'\fR, it has no effect. .Sp See perlsec for more complete information about tainting. .Sp Thanks to Steve Palincsar, Gerard Vreeswijk, and Dr. Christoph Baehr for help with this feature. .ie n .IP """PREPEND""" 4 .el .IP "\f(CWPREPEND\fR" 4 .IX Item "PREPEND" This option is passed along to the \f(CW\*(C`fill_in\*(C'\fR call unless it is overridden in the arguments to \f(CW\*(C`fill_in\*(C'\fR. See \f(CW\*(C`PREPEND\*(C'\fR feature and using \f(CW\*(C`strict\*(C'\fR in templates> below. .ie n .IP """BROKEN""" 4 .el .IP "\f(CWBROKEN\fR" 4 .IX Item "BROKEN" This option is passed along to the \f(CW\*(C`fill_in\*(C'\fR call unless it is overridden in the arguments to \f(CW\*(C`fill_in\*(C'\fR. See \f(CW\*(C`BROKEN\*(C'\fR below. .ie n .SS """compile""" .el .SS "\f(CWcompile\fP" .IX Subsection "compile" .Vb 1 \& $template\->compile() .Ve .PP Loads all the template text from the template's source, parses and compiles it. If successful, returns true; otherwise returns false and sets \f(CW$Text::Template::ERROR\fR. If the template is already compiled, it returns true and does nothing. .PP You don't usually need to invoke this function, because \f(CW\*(C`fill_in\*(C'\fR (see below) compiles the template if it isn't compiled already. .PP If there is an argument to this function, it must be a reference to an array containing alternative delimiter strings. See \f(CW"Alternative Delimiters"\fR, below. .ie n .SS """fill_in""" .el .SS "\f(CWfill_in\fP" .IX Subsection "fill_in" .Vb 1 \& $template\->fill_in(OPTIONS); .Ve .PP Fills in a template. Returns the resulting text if successful. Otherwise, returns \f(CW\*(C`undef\*(C'\fR and sets \f(CW$Text::Template::ERROR\fR. .PP The \fI\s-1OPTIONS\s0\fR are a hash, or a list of key-value pairs. You can write the key names in any of the six usual styles as above; this means that where this manual says \f(CW\*(C`PACKAGE\*(C'\fR (for example) you can actually use any of .PP .Vb 1 \& PACKAGE Package package \-PACKAGE \-Package \-package .Ve .PP Pick a style you like and stick with it. The all-lowercase versions may yield spurious warnings about .PP .Vb 1 \& Ambiguous use of package => resolved to "package" .Ve .PP so you might like to avoid them and use the capitalized versions. .PP At present, there are eight legal options: \f(CW\*(C`PACKAGE\*(C'\fR, \f(CW\*(C`BROKEN\*(C'\fR, \&\f(CW\*(C`BROKEN_ARG\*(C'\fR, \f(CW\*(C`FILENAME\*(C'\fR, \f(CW\*(C`SAFE\*(C'\fR, \f(CW\*(C`HASH\*(C'\fR, \f(CW\*(C`OUTPUT\*(C'\fR, and \f(CW\*(C`DELIMITERS\*(C'\fR. .ie n .IP """PACKAGE""" 4 .el .IP "\f(CWPACKAGE\fR" 4 .IX Item "PACKAGE" \&\f(CW\*(C`PACKAGE\*(C'\fR specifies the name of a package in which the program fragments should be evaluated. The default is to use the package from which \f(CW\*(C`fill_in\*(C'\fR was called. For example, consider this template: .Sp .Vb 1 \& The value of the variable x is {$x}. .Ve .Sp If you use \f(CW\*(C`$template\->fill_in(PACKAGE => \*(AqR\*(Aq)\*(C'\fR , then the \f(CW$x\fR in the template is actually replaced with the value of \f(CW$R::x\fR. If you omit the \f(CW\*(C`PACKAGE\*(C'\fR option, \f(CW$x\fR will be replaced with the value of the \f(CW$x\fR variable in the package that actually called \f(CW\*(C`fill_in\*(C'\fR. .Sp You should almost always use \f(CW\*(C`PACKAGE\*(C'\fR. If you don't, and your template makes changes to variables, those changes will be propagated back into the main program. Evaluating the template in a private package helps prevent this. The template can still modify variables in your program if it wants to, but it will have to do so explicitly. See the section at the end on `Security'. .Sp Here's an example of using \f(CW\*(C`PACKAGE\*(C'\fR: .Sp .Vb 1 \& Your Royal Highness, \& \& Enclosed please find a list of things I have gotten \& for you since 1907: \& \& { foreach $item (@items) { \& $item_no++; \& $OUT .= " $item_no. \eu$item\en"; \& } \& } \& \& Signed, \& Lord High Chamberlain .Ve .Sp We want to pass in an array which will be assigned to the array \&\f(CW@items\fR. Here's how to do that: .Sp .Vb 2 \& @items = (\*(Aqivory\*(Aq, \*(Aqapes\*(Aq, \*(Aqpeacocks\*(Aq, ); \& $template\->fill_in(); .Ve .Sp This is not very safe. The reason this isn't as safe is that if you had a variable named \f(CW$item_no\fR in scope in your program at the point you called \f(CW\*(C`fill_in\*(C'\fR, its value would be clobbered by the act of filling out the template. The problem is the same as if you had written a subroutine that used those variables in the same way that the template does. (\f(CW$OUT\fR is special in templates and is always safe.) .Sp One solution to this is to make the \f(CW$item_no\fR variable private to the template by declaring it with \f(CW\*(C`my\*(C'\fR. If the template does this, you are safe. .Sp But if you use the \f(CW\*(C`PACKAGE\*(C'\fR option, you will probably be safe even if the template does \fInot\fR declare its variables with \f(CW\*(C`my\*(C'\fR: .Sp .Vb 2 \& @Q::items = (\*(Aqivory\*(Aq, \*(Aqapes\*(Aq, \*(Aqpeacocks\*(Aq, ); \& $template\->fill_in(PACKAGE => \*(AqQ\*(Aq); .Ve .Sp In this case the template will clobber the variable \f(CW$Q::item_no\fR, which is not related to the one your program was using. .Sp Templates cannot affect variables in the main program that are declared with \f(CW\*(C`my\*(C'\fR, unless you give the template references to those variables. .ie n .IP """HASH""" 4 .el .IP "\f(CWHASH\fR" 4 .IX Item "HASH" You may not want to put the template variables into a package. Packages can be hard to manage: You can't copy them, for example. \&\f(CW\*(C`HASH\*(C'\fR provides an alternative. .Sp The value for \f(CW\*(C`HASH\*(C'\fR should be a reference to a hash that maps variable names to values. For example, .Sp .Vb 7 \& $template\->fill_in( \& HASH => { \& recipient => "The King", \& items => [\*(Aqgold\*(Aq, \*(Aqfrankincense\*(Aq, \*(Aqmyrrh\*(Aq], \& object => \e$self, \& } \& ); .Ve .Sp will fill out the template and use \f(CW"The King"\fR as the value of \&\f(CW$recipient\fR and the list of items as the value of \f(CW@items\fR. Note that we pass an array reference, but inside the template it appears as an array. In general, anything other than a simple string or number should be passed by reference. .Sp We also want to pass an object, which is in \f(CW$self\fR; note that we pass a reference to the object, \f(CW\*(C`\e$self\*(C'\fR instead. Since we've passed a reference to a scalar, inside the template the object appears as \&\f(CW$object\fR. .Sp The full details of how it works are a little involved, so you might want to skip to the next section. .Sp Suppose the key in the hash is \fIkey\fR and the value is \fIvalue\fR. .RS 4 .IP "\(bu" 4 If the \fIvalue\fR is \f(CW\*(C`undef\*(C'\fR, then any variables named \f(CW$key\fR, \&\f(CW@key\fR, \f(CW%key\fR, etc., are undefined. .IP "\(bu" 4 If the \fIvalue\fR is a string or a number, then \f(CW$key\fR is set to that value in the template. .IP "\(bu" 4 For anything else, you must pass a reference. .Sp If the \fIvalue\fR is a reference to an array, then \f(CW@key\fR is set to that array. If the \fIvalue\fR is a reference to a hash, then \f(CW%key\fR is set to that hash. Similarly if \fIvalue\fR is any other kind of reference. This means that .Sp .Vb 1 \& var => "foo" .Ve .Sp and .Sp .Vb 1 \& var => \e"foo" .Ve .Sp have almost exactly the same effect. (The difference is that in the former case, the value is copied, and in the latter case it is aliased.) .IP "\(bu" 4 In particular, if you want the template to get an object or any kind, you must pass a reference to it: .Sp .Vb 1 \& $template\->fill_in(HASH => { database_handle => \e$dbh, ... }); .Ve .Sp If you do this, the template will have a variable \f(CW$database_handle\fR which is the database handle object. If you leave out the \f(CW\*(C`\e\*(C'\fR, the template will have a hash \f(CW%database_handle\fR, which exposes the internal structure of the database handle object; you don't want that. .RE .RS 4 .Sp Normally, the way this works is by allocating a private package, loading all the variables into the package, and then filling out the template as if you had specified that package. A new package is allocated each time. However, if you \fIalso\fR use the \f(CW\*(C`PACKAGE\*(C'\fR option, \f(CW\*(C`Text::Template\*(C'\fR loads the variables into the package you specified, and they stay there after the call returns. Subsequent calls to \f(CW\*(C`fill_in\*(C'\fR that use the same package will pick up the values you loaded in. .Sp If the argument of \f(CW\*(C`HASH\*(C'\fR is a reference to an array instead of a reference to a hash, then the array should contain a list of hashes whose contents are loaded into the template package one after the other. You can use this feature if you want to combine several sets of variables. For example, one set of variables might be the defaults for a fill-in form, and the second set might be the user inputs, which override the defaults when they are present: .Sp .Vb 1 \& $template\->fill_in(HASH => [\e%defaults, \e%user_input]); .Ve .Sp You can also use this to set two variables with the same name: .Sp .Vb 6 \& $template\->fill_in( \& HASH => [ \& { v => "The King" }, \& { v => [1,2,3] } \& ] \& ); .Ve .Sp This sets \f(CW$v\fR to \f(CW"The King"\fR and \f(CW@v\fR to \f(CW\*(C`(1,2,3)\*(C'\fR. .RE .ie n .IP """BROKEN""" 4 .el .IP "\f(CWBROKEN\fR" 4 .IX Item "BROKEN" If any of the program fragments fails to compile or aborts for any reason, and you have set the \f(CW\*(C`BROKEN\*(C'\fR option to a function reference, \&\f(CW\*(C`Text::Template\*(C'\fR will invoke the function. This function is called the \fI\f(CI\*(C`BROKEN\*(C'\fI function\fR. The \f(CW\*(C`BROKEN\*(C'\fR function will tell \&\f(CW\*(C`Text::Template\*(C'\fR what to do next. .Sp If the \f(CW\*(C`BROKEN\*(C'\fR function returns \f(CW\*(C`undef\*(C'\fR, \f(CW\*(C`Text::Template\*(C'\fR will immediately abort processing the template and return the text that it has accumulated so far. If your function does this, it should set a flag that you can examine after \f(CW\*(C`fill_in\*(C'\fR returns so that you can tell whether there was a premature return or not. .Sp If the \f(CW\*(C`BROKEN\*(C'\fR function returns any other value, that value will be interpolated into the template as if that value had been the return value of the program fragment to begin with. For example, if the \&\f(CW\*(C`BROKEN\*(C'\fR function returns an error string, the error string will be interpolated into the output of the template in place of the program fragment that cased the error. .Sp If you don't specify a \f(CW\*(C`BROKEN\*(C'\fR function, \f(CW\*(C`Text::Template\*(C'\fR supplies a default one that returns something like .Sp .Vb 2 \& Program fragment delivered error \`\`Illegal division by 0 at \& template line 37\*(Aq\*(Aq .Ve .Sp (Note that the format of this message has changed slightly since version 1.31.) The return value of the \f(CW\*(C`BROKEN\*(C'\fR function is interpolated into the template at the place the error occurred, so that this template: .Sp .Vb 1 \& (3+4)*5 = { 3+4)*5 } .Ve .Sp yields this result: .Sp .Vb 1 \& (3+4)*5 = Program fragment delivered error \`\`syntax error at template line 1\*(Aq\*(Aq .Ve .Sp If you specify a value for the \f(CW\*(C`BROKEN\*(C'\fR attribute, it should be a reference to a function that \f(CW\*(C`fill_in\*(C'\fR can call instead of the default function. .Sp \&\f(CW\*(C`fill_in\*(C'\fR will pass a hash to the \f(CW\*(C`broken\*(C'\fR function. The hash will have at least these three members: .RS 4 .ie n .IP """text""" 4 .el .IP "\f(CWtext\fR" 4 .IX Item "text" The source code of the program fragment that failed .ie n .IP """error""" 4 .el .IP "\f(CWerror\fR" 4 .IX Item "error" The text of the error message (\f(CW$@\fR) generated by eval. .Sp The text has been modified to omit the trailing newline and to include the name of the template file (if there was one). The line number counts from the beginning of the template, not from the beginning of the failed program fragment. .ie n .IP """lineno""" 4 .el .IP "\f(CWlineno\fR" 4 .IX Item "lineno" The line number of the template at which the program fragment began. .RE .RS 4 .Sp There may also be an \f(CW\*(C`arg\*(C'\fR member. See \f(CW\*(C`BROKEN_ARG\*(C'\fR, below .RE .ie n .IP """BROKEN_ARG""" 4 .el .IP "\f(CWBROKEN_ARG\fR" 4 .IX Item "BROKEN_ARG" If you supply the \f(CW\*(C`BROKEN_ARG\*(C'\fR option to \f(CW\*(C`fill_in\*(C'\fR, the value of the option is passed to the \f(CW\*(C`BROKEN\*(C'\fR function whenever it is called. The default \f(CW\*(C`BROKEN\*(C'\fR function ignores the \f(CW\*(C`BROKEN_ARG\*(C'\fR, but you can write a custom \f(CW\*(C`BROKEN\*(C'\fR function that uses the \f(CW\*(C`BROKEN_ARG\*(C'\fR to get more information about what went wrong. .Sp The \f(CW\*(C`BROKEN\*(C'\fR function could also use the \f(CW\*(C`BROKEN_ARG\*(C'\fR as a reference to store an error message or some other information that it wants to communicate back to the caller. For example: .Sp .Vb 1 \& $error = \*(Aq\*(Aq; \& \& sub my_broken { \& my %args = @_; \& my $err_ref = $args{arg}; \& ... \& $$err_ref = "Some error message"; \& return undef; \& } \& \& $template\->fill_in( \& BROKEN => \e&my_broken, \& BROKEN_ARG => \e$error \& ); \& \& if ($error) { \& die "It didn\*(Aqt work: $error"; \& } .Ve .Sp If one of the program fragments in the template fails, it will call the \f(CW\*(C`BROKEN\*(C'\fR function, \f(CW\*(C`my_broken\*(C'\fR, and pass it the \f(CW\*(C`BROKEN_ARG\*(C'\fR, which is a reference to \f(CW$error\fR. \f(CW\*(C`my_broken\*(C'\fR can store an error message into \f(CW$error\fR this way. Then the function that called \&\f(CW\*(C`fill_in\*(C'\fR can see if \f(CW\*(C`my_broken\*(C'\fR has left an error message for it to find, and proceed accordingly. .ie n .IP """FILENAME""" 4 .el .IP "\f(CWFILENAME\fR" 4 .IX Item "FILENAME" If you give \f(CW\*(C`fill_in\*(C'\fR a \f(CW\*(C`FILENAME\*(C'\fR option, then this is the file name that you loaded the template source from. This only affects the error message that is given for template errors. If you loaded the template from \f(CW\*(C`foo.txt\*(C'\fR for example, and pass \f(CW\*(C`foo.txt\*(C'\fR as the \f(CW\*(C`FILENAME\*(C'\fR parameter, errors will look like \f(CW\*(C`... at foo.txt line N\*(C'\fR rather than \f(CW\*(C`... at template line N\*(C'\fR. .Sp Note that this does \s-1NOT\s0 have anything to do with loading a template from the given filename. See \f(CW\*(C`fill_in_file()\*(C'\fR for that. .Sp For example: .Sp .Vb 3 \& my $template = Text::Template\->new( \& TYPE => \*(Aqstring\*(Aq, \& SOURCE => \*(AqThe value is {1/0}\*(Aq); \& \& $template\->fill_in(FILENAME => \*(Aqfoo.txt\*(Aq) or die $Text::Template::ERROR; .Ve .Sp will die with an error that contains .Sp .Vb 1 \& Illegal division by zero at at foo.txt line 1 .Ve .ie n .IP """SAFE""" 4 .el .IP "\f(CWSAFE\fR" 4 .IX Item "SAFE" If you give \f(CW\*(C`fill_in\*(C'\fR a \f(CW\*(C`SAFE\*(C'\fR option, its value should be a safe compartment object from the \f(CW\*(C`Safe\*(C'\fR package. All evaluation of program fragments will be performed in this compartment. See Safe for full details about such compartments and how to restrict the operations that can be performed in them. .Sp If you use the \f(CW\*(C`PACKAGE\*(C'\fR option with \f(CW\*(C`SAFE\*(C'\fR, the package you specify will be placed into the safe compartment and evaluation will take place in that package as usual. .Sp If not, \f(CW\*(C`SAFE\*(C'\fR operation is a little different from the default. Usually, if you don't specify a package, evaluation of program fragments occurs in the package from which the template was invoked. But in \f(CW\*(C`SAFE\*(C'\fR mode the evaluation occurs inside the safe compartment and cannot affect the calling package. Normally, if you use \f(CW\*(C`HASH\*(C'\fR without \f(CW\*(C`PACKAGE\*(C'\fR, the hash variables are imported into a private, one-use-only package. But if you use \f(CW\*(C`HASH\*(C'\fR and \f(CW\*(C`SAFE\*(C'\fR together without \f(CW\*(C`PACKAGE\*(C'\fR, the hash variables will just be loaded into the root namespace of the \f(CW\*(C`Safe\*(C'\fR compartment. .ie n .IP """OUTPUT""" 4 .el .IP "\f(CWOUTPUT\fR" 4 .IX Item "OUTPUT" If your template is going to generate a lot of text that you are just going to print out again anyway, you can save memory by having \&\f(CW\*(C`Text::Template\*(C'\fR print out the text as it is generated instead of making it into a big string and returning the string. If you supply the \f(CW\*(C`OUTPUT\*(C'\fR option to \f(CW\*(C`fill_in\*(C'\fR, the value should be a filehandle. The generated text will be printed to this filehandle as it is constructed. For example: .Sp .Vb 1 \& $template\->fill_in(OUTPUT => \e*STDOUT, ...); .Ve .Sp fills in the \f(CW$template\fR as usual, but the results are immediately printed to \s-1STDOUT.\s0 This may result in the output appearing more quickly than it would have otherwise. .Sp If you use \f(CW\*(C`OUTPUT\*(C'\fR, the return value from \f(CW\*(C`fill_in\*(C'\fR is still true on success and false on failure, but the complete text is not returned to the caller. .ie n .IP """PREPEND""" 4 .el .IP "\f(CWPREPEND\fR" 4 .IX Item "PREPEND" You can have some Perl code prepended automatically to the beginning of every program fragment. See "\f(CW\*(C`PREPEND\*(C'\fR feature and using \&\f(CW\*(C`strict\*(C'\fR in templates" below. .ie n .IP """DELIMITERS""" 4 .el .IP "\f(CWDELIMITERS\fR" 4 .IX Item "DELIMITERS" If this option is present, its value should be a reference to a list of two strings. The first string is the string that signals the beginning of each program fragment, and the second string is the string that signals the end of each program fragment. See \&\*(L"Alternative Delimiters\*(R", below. .Sp If you specify \f(CW\*(C`DELIMITERS\*(C'\fR in the call to \f(CW\*(C`fill_in\*(C'\fR, they override any delimiters you set when you created the template object with \&\f(CW\*(C`new\*(C'\fR. .SH "Convenience Functions" .IX Header "Convenience Functions" .ie n .SS """fill_this_in""" .el .SS "\f(CWfill_this_in\fP" .IX Subsection "fill_this_in" The basic way to fill in a template is to create a template object and then call \f(CW\*(C`fill_in\*(C'\fR on it. This is useful if you want to fill in the same template more than once. .PP In some programs, this can be cumbersome. \f(CW\*(C`fill_this_in\*(C'\fR accepts a string, which contains the template, and a list of options, which are passed to \f(CW\*(C`fill_in\*(C'\fR as above. It constructs the template object for you, fills it in as specified, and returns the results. It returns \&\f(CW\*(C`undef\*(C'\fR and sets \f(CW$Text::Template::ERROR\fR if it couldn't generate any results. .PP An example: .PP .Vb 3 \& $Q::name = \*(AqDonald\*(Aq; \& $Q::amount = 141.61; \& $Q::part = \*(Aqhyoid bone\*(Aq; \& \& $text = Text::Template\->fill_this_in( <<\*(AqEOM\*(Aq, PACKAGE => Q); \& Dear {$name}, \& You owe me \e\e${sprintf(\*(Aq%.2f\*(Aq, $amount)}. \& Pay or I will break your {$part}. \& Love, \& Grand Vizopteryx of Irkutsk. \& EOM .Ve .PP Notice how we included the template in-line in the program by using a `here document' with the \f(CW\*(C`<<\*(C'\fR notation. .PP \&\f(CW\*(C`fill_this_in\*(C'\fR is a deprecated feature. It is only here for backwards compatibility, and may be removed in some far-future version in \f(CW\*(C`Text::Template\*(C'\fR. You should use \f(CW\*(C`fill_in_string\*(C'\fR instead. It is described in the next section. .ie n .SS """fill_in_string""" .el .SS "\f(CWfill_in_string\fP" .IX Subsection "fill_in_string" It is stupid that \f(CW\*(C`fill_this_in\*(C'\fR is a class method. It should have been just an imported function, so that you could omit the \&\f(CW\*(C`Text::Template\->\*(C'\fR in the example above. But I made the mistake four years ago and it is too late to change it. .PP \&\f(CW\*(C`fill_in_string\*(C'\fR is exactly like \f(CW\*(C`fill_this_in\*(C'\fR except that it is not a method and you can omit the \f(CW\*(C`Text::Template\->\*(C'\fR and just say .PP .Vb 4 \& print fill_in_string(<<\*(AqEOM\*(Aq, ...); \& Dear {$name}, \& ... \& EOM .Ve .PP To use \f(CW\*(C`fill_in_string\*(C'\fR, you need to say .PP .Vb 1 \& use Text::Template \*(Aqfill_in_string\*(Aq; .Ve .PP at the top of your program. You should probably use \&\f(CW\*(C`fill_in_string\*(C'\fR instead of \f(CW\*(C`fill_this_in\*(C'\fR. .ie n .SS """fill_in_file""" .el .SS "\f(CWfill_in_file\fP" .IX Subsection "fill_in_file" If you import \f(CW\*(C`fill_in_file\*(C'\fR, you can say .PP .Vb 1 \& $text = fill_in_file(filename, ...); .Ve .PP The \f(CW\*(C`...\*(C'\fR are passed to \f(CW\*(C`fill_in\*(C'\fR as above. The filename is the name of the file that contains the template you want to fill in. It returns the result text. or \f(CW\*(C`undef\*(C'\fR, as usual. .PP If you are going to fill in the same file more than once in the same program you should use the longer \f(CW\*(C`new\*(C'\fR / \f(CW\*(C`fill_in\*(C'\fR sequence instead. It will be a lot faster because it only has to read and parse the file once. .SS "Including files into templates" .IX Subsection "Including files into templates" People always ask for this. ``Why don't you have an include function?'' they want to know. The short answer is this is Perl, and Perl already has an include function. If you want it, you can just put .PP .Vb 1 \& {qx{cat filename}} .Ve .PP into your template. Voilà. .PP If you don't want to use \f(CW\*(C`cat\*(C'\fR, you can write a little four-line function that opens a file and dumps out its contents, and call it from the template. I wrote one for you. In the template, you can say .PP .Vb 1 \& {Text::Template::_load_text(filename)} .Ve .PP If that is too verbose, here is a trick. Suppose the template package that you are going to be mentioning in the \f(CW\*(C`fill_in\*(C'\fR call is package \&\f(CW\*(C`Q\*(C'\fR. Then in the main program, write .PP .Vb 1 \& *Q::include = \e&Text::Template::_load_text; .Ve .PP This imports the \f(CW\*(C`_load_text\*(C'\fR function into package \f(CW\*(C`Q\*(C'\fR with the name \f(CW\*(C`include\*(C'\fR. From then on, any template that you fill in with package \f(CW\*(C`Q\*(C'\fR can say .PP .Vb 1 \& {include(filename)} .Ve .PP to insert the text from the named file at that point. If you are using the \f(CW\*(C`HASH\*(C'\fR option instead, just put \f(CW\*(C`include => \&\e&Text::Template::_load_text\*(C'\fR into the hash instead of importing it explicitly. .PP Suppose you don't want to insert a plain text file, but rather you want to include one template within another? Just use \f(CW\*(C`fill_in_file\*(C'\fR in the template itself: .PP .Vb 1 \& {Text::Template::fill_in_file(filename)} .Ve .PP You can do the same importing trick if this is too much to type. .SH "Miscellaneous" .IX Header "Miscellaneous" .ie n .SS """my"" variables" .el .SS "\f(CWmy\fP variables" .IX Subsection "my variables" People are frequently surprised when this doesn't work: .PP .Vb 2 \& my $recipient = \*(AqThe King\*(Aq; \& my $text = fill_in_file(\*(Aqformletter.tmpl\*(Aq); .Ve .PP The text \f(CW\*(C`The King\*(C'\fR doesn't get into the form letter. Why not? Because \f(CW$recipient\fR is a \f(CW\*(C`my\*(C'\fR variable, and the whole point of \&\f(CW\*(C`my\*(C'\fR variables is that they're private and inaccessible except in the scope in which they're declared. The template is not part of that scope, so the template can't see \f(CW$recipient\fR. .PP If that's not the behavior you want, don't use \f(CW\*(C`my\*(C'\fR. \f(CW\*(C`my\*(C'\fR means a private variable, and in this case you don't want the variable to be private. Put the variables into package variables in some other package, and use the \f(CW\*(C`PACKAGE\*(C'\fR option to \f(CW\*(C`fill_in\*(C'\fR: .PP .Vb 2 \& $Q::recipient = $recipient; \& my $text = fill_in_file(\*(Aqformletter.tmpl\*(Aq, PACKAGE => \*(AqQ\*(Aq); .Ve .PP or pass the names and values in a hash with the \f(CW\*(C`HASH\*(C'\fR option: .PP .Vb 1 \& my $text = fill_in_file(\*(Aqformletter.tmpl\*(Aq, HASH => { recipient => $recipient }); .Ve .SS "Security Matters" .IX Subsection "Security Matters" All variables are evaluated in the package you specify with the \&\f(CW\*(C`PACKAGE\*(C'\fR option of \f(CW\*(C`fill_in\*(C'\fR. if you use this option, and if your templates don't do anything egregiously stupid, you won't have to worry that evaluation of the little programs will creep out into the rest of your program and wreck something. .PP Nevertheless, there's really no way (except with \f(CW\*(C`Safe\*(C'\fR) to protect against a template that says .PP .Vb 3 \& { $Important::Secret::Security::Enable = 0; \& # Disable security checks in this program \& } .Ve .PP or .PP .Vb 3 \& { $/ = "ho ho ho"; # Sabotage future uses of . \& # $/ is always a global variable \& } .Ve .PP or even .PP .Vb 1 \& { system("rm \-rf /") } .Ve .PP so \fBdon't\fR go filling in templates unless you're sure you know what's in them. If you're worried, or you can't trust the person who wrote the template, use the \f(CW\*(C`SAFE\*(C'\fR option. .PP A final warning: program fragments run a small risk of accidentally clobbering local variables in the \f(CW\*(C`fill_in\*(C'\fR function itself. These variables all have names that begin with \f(CW$fi_\fR, so if you stay away from those names you'll be safe. (Of course, if you're a real wizard you can tamper with them deliberately for exciting effects; this is actually how \f(CW$OUT\fR works.) I can fix this, but it will make the package slower to do it, so I would prefer not to. If you are worried about this, send me mail and I will show you what to do about it. .SS "Alternative Delimiters" .IX Subsection "Alternative Delimiters" Lorenzo Valdettaro pointed out that if you are using \f(CW\*(C`Text::Template\*(C'\fR to generate TeX output, the choice of braces as the program fragment delimiters makes you suffer suffer suffer. Starting in version 1.20, you can change the choice of delimiters to something other than curly braces. .PP In either the \f(CW\*(C`new()\*(C'\fR call or the \f(CW\*(C`fill_in()\*(C'\fR call, you can specify an alternative set of delimiters with the \f(CW\*(C`DELIMITERS\*(C'\fR option. For example, if you would like code fragments to be delimited by \f(CW\*(C`[@\-\-\*(C'\fR and \f(CW\*(C`\-\-@]\*(C'\fR instead of \f(CW\*(C`{\*(C'\fR and \f(CW\*(C`}\*(C'\fR, use .PP .Vb 1 \& ... DELIMITERS => [ \*(Aq[@\-\-\*(Aq, \*(Aq\-\-@]\*(Aq ], ... .Ve .PP Note that these delimiters are \fIliteral strings\fR, not regexes. (I tried for regexes, but it complicates the lexical analysis too much.) Note also that \f(CW\*(C`DELIMITERS\*(C'\fR disables the special meaning of the backslash, so if you want to include the delimiters in the literal text of your template file, you are out of luck\-\-\-it is up to you to choose delimiters that do not conflict with what you are doing. The delimiter strings may still appear inside of program fragments as long as they nest properly. This means that if for some reason you absolutely must have a program fragment that mentions one of the delimiters, like this: .PP .Vb 3 \& [@\-\- \& print "Oh no, a delimiter: \-\-@]\en" \& \-\-@] .Ve .PP you may be able to make it work by doing this instead: .PP .Vb 4 \& [@\-\- \& # Fake matching delimiter in a comment: [@\-\- \& print "Oh no, a delimiter: \-\-@]\en" \& \-\-@] .Ve .PP It may be safer to choose delimiters that begin with a newline character. .PP Because the parsing of templates is simplified by the absence of backslash escapes, using alternative \f(CW\*(C`DELIMITERS\*(C'\fR may speed up the parsing process by 20\-25%. This shows that my original choice of \f(CW\*(C`{\*(C'\fR and \f(CW\*(C`}\*(C'\fR was very bad. .ie n .SS """PREPEND"" feature and using ""strict"" in templates" .el .SS "\f(CWPREPEND\fP feature and using \f(CWstrict\fP in templates" .IX Subsection "PREPEND feature and using strict in templates" Suppose you would like to use \f(CW\*(C`strict\*(C'\fR in your templates to detect undeclared variables and the like. But each code fragment is a separate lexical scope, so you have to turn on \f(CW\*(C`strict\*(C'\fR at the top of each and every code fragment: .PP .Vb 5 \& { use strict; \& use vars \*(Aq$foo\*(Aq; \& $foo = 14; \& ... \& } \& \& ... \& \& { # we forgot to put \`use strict\*(Aq here \& my $result = $boo + 12; # $boo is misspelled and should be $foo \& # No error is raised on \`$boo\*(Aq \& } .Ve .PP Because we didn't put \f(CW\*(C`use strict\*(C'\fR at the top of the second fragment, it was only active in the first fragment, and we didn't get any \&\f(CW\*(C`strict\*(C'\fR checking in the second fragment. Then we misspelled \f(CW$foo\fR and the error wasn't caught. .PP \&\f(CW\*(C`Text::Template\*(C'\fR version 1.22 and higher has a new feature to make this easier. You can specify that any text at all be automatically added to the beginning of each program fragment. .PP When you make a call to \f(CW\*(C`fill_in\*(C'\fR, you can specify a .PP .Vb 1 \& PREPEND => \*(Aqsome perl statements here\*(Aq .Ve .PP option; the statements will be prepended to each program fragment for that one call only. Suppose that the \f(CW\*(C`fill_in\*(C'\fR call included a .PP .Vb 1 \& PREPEND => \*(Aquse strict;\*(Aq .Ve .PP option, and that the template looked like this: .PP .Vb 4 \& { use vars \*(Aq$foo\*(Aq; \& $foo = 14; \& ... \& } \& \& ... \& \& { my $result = $boo + 12; # $boo is misspelled and should be $foo \& ... \& } .Ve .PP The code in the second fragment would fail, because \f(CW$boo\fR has not been declared. \f(CW\*(C`use strict\*(C'\fR was implied, even though you did not write it explicitly, because the \f(CW\*(C`PREPEND\*(C'\fR option added it for you automatically. .PP There are three other ways to do this. At the time you create the template object with \f(CW\*(C`new\*(C'\fR, you can also supply a \f(CW\*(C`PREPEND\*(C'\fR option, in which case the statements will be prepended each time you fill in that template. If the \f(CW\*(C`fill_in\*(C'\fR call has its own \f(CW\*(C`PREPEND\*(C'\fR option, this overrides the one specified at the time you created the template. Finally, you can make the class method call .PP .Vb 1 \& Text::Template\->always_prepend(\*(Aqperl statements\*(Aq); .Ve .PP If you do this, then call calls to \f(CW\*(C`fill_in\*(C'\fR for \fIany\fR template will attach the perl statements to the beginning of each program fragment, except where overridden by \f(CW\*(C`PREPEND\*(C'\fR options to \f(CW\*(C`new\*(C'\fR or \f(CW\*(C`fill_in\*(C'\fR. .PP An alternative to adding \*(L"use strict;\*(R" to the \s-1PREPEND\s0 option, you can pass \s-1STRICT\s0 => 1 to fill_in when also passing the \s-1HASH\s0 option. .PP Suppose that the \f(CW\*(C`fill_in\*(C'\fR call included both .PP .Vb 2 \& HASH => {$foo => \*(Aq\*(Aq} and \& STRICT => 1 .Ve .PP options, and that the template looked like this: .PP .Vb 4 \& { \& $foo = 14; \& ... \& } \& \& ... \& \& { my $result = $boo + 12; # $boo is misspelled and should be $foo \& ... \& } .Ve .PP The code in the second fragment would fail, because \f(CW$boo\fR has not been declared. \f(CW\*(C`use strict\*(C'\fR was implied, even though you did not write it explicitly, because the \f(CW\*(C`STRICT\*(C'\fR option added it for you automatically. Any variable referenced in the template that is not in the \&\f(CW\*(C`HASH\*(C'\fR option will be an error. .SS "Prepending in Derived Classes" .IX Subsection "Prepending in Derived Classes" This section is technical, and you should skip it on the first few readings. .PP Normally there are three places that prepended text could come from. It could come from the \f(CW\*(C`PREPEND\*(C'\fR option in the \f(CW\*(C`fill_in\*(C'\fR call, from the \f(CW\*(C`PREPEND\*(C'\fR option in the \f(CW\*(C`new\*(C'\fR call that created the template object, or from the argument of the \f(CW\*(C`always_prepend\*(C'\fR call. \&\f(CW\*(C`Text::Template\*(C'\fR looks for these three things in order and takes the first one that it finds. .PP In a subclass of \f(CW\*(C`Text::Template\*(C'\fR, this last possibility is ambiguous. Suppose \f(CW\*(C`S\*(C'\fR is a subclass of \f(CW\*(C`Text::Template\*(C'\fR. Should .PP .Vb 1 \& Text::Template\->always_prepend(...); .Ve .PP affect objects in class \f(CW\*(C`Derived\*(C'\fR? The answer is that you can have it either way. .PP The \f(CW\*(C`always_prepend\*(C'\fR value for \f(CW\*(C`Text::Template\*(C'\fR is normally stored in a hash variable named \f(CW%GLOBAL_PREPEND\fR under the key \&\f(CW\*(C`Text::Template\*(C'\fR. When \f(CW\*(C`Text::Template\*(C'\fR looks to see what text to prepend, it first looks in the template object itself, and if not, it looks in \f(CW$GLOBAL_PREPEND{\f(CIclass\f(CW}\fR where \fIclass\fR is the class to which the template object belongs. If it doesn't find any value, it looks in \f(CW$GLOBAL_PREPEND{\*(AqText::Template\*(Aq}\fR. This means that objects in class \f(CW\*(C`Derived\*(C'\fR \fIwill\fR be affected by .PP .Vb 1 \& Text::Template\->always_prepend(...); .Ve .PP \&\fIunless\fR there is also a call to .PP .Vb 1 \& Derived\->always_prepend(...); .Ve .PP So when you're designing your derived class, you can arrange to have your objects ignore \f(CW\*(C`Text::Template::always_prepend\*(C'\fR calls by simply putting \f(CW\*(C`Derived\->always_prepend(\*(Aq\*(Aq)\*(C'\fR at the top of your module. .PP Of course, there is also a final escape hatch: Templates support a \&\f(CW\*(C`prepend_text\*(C'\fR that is used to look up the appropriate text to be prepended at \f(CW\*(C`fill_in\*(C'\fR time. Your derived class can override this method to get an arbitrary effect. .SS "JavaScript" .IX Subsection "JavaScript" Jennifer D. St Clair asks: .PP .Vb 2 \& > Most of my pages contain JavaScript and Stylesheets. \& > How do I change the template identifier? .Ve .PP Jennifer is worried about the braces in the JavaScript being taken as the delimiters of the Perl program fragments. Of course, disaster will ensue when perl tries to evaluate these as if they were Perl programs. The best choice is to find some unambiguous delimiter strings that you can use in your template instead of curly braces, and then use the \f(CW\*(C`DELIMITERS\*(C'\fR option. However, if you can't do this for some reason, there are two easy workarounds: .PP 1. You can put \f(CW\*(C`\e\*(C'\fR in front of \f(CW\*(C`{\*(C'\fR, \f(CW\*(C`}\*(C'\fR, or \f(CW\*(C`\e\*(C'\fR to remove its special meaning. So, for example, instead of .PP .Vb 3 \& if (br== "n3") { \& // etc. \& } .Ve .PP you can put .PP .Vb 3 \& if (br== "n3") \e{ \& // etc. \& \e} .Ve .PP and it'll come out of the template engine the way you want. .PP But here is another method that is probably better. To see how it works, first consider what happens if you put this into a template: .PP .Vb 1 \& { \*(Aqfoo\*(Aq } .Ve .PP Since it's in braces, it gets evaluated, and obviously, this is going to turn into .PP .Vb 1 \& foo .Ve .PP So now here's the trick: In Perl, \f(CW\*(C`q{...}\*(C'\fR is the same as \f(CW\*(Aq...\*(Aq\fR. So if we wrote .PP .Vb 1 \& {q{foo}} .Ve .PP it would turn into .PP .Vb 1 \& foo .Ve .PP So for your JavaScript, just write .PP .Vb 4 \& {q{if (br== "n3") { \& // etc. \& }} \& } .Ve .PP and it'll come out as .PP .Vb 3 \& if (br== "n3") { \& // etc. \& } .Ve .PP which is what you want. .PP head2 Shut Up! .PP People sometimes try to put an initialization section at the top of their templates, like this: .PP .Vb 3 \& { ... \& $var = 17; \& } .Ve .PP Then they complain because there is a \f(CW17\fR at the top of the output that they didn't want to have there. .PP Remember that a program fragment is replaced with its own return value, and that in Perl the return value of a code block is the value of the last expression that was evaluated, which in this case is 17. If it didn't do that, you wouldn't be able to write \f(CW\*(C`{$recipient}\*(C'\fR and have the recipient filled in. .PP To prevent the 17 from appearing in the output is very simple: .PP .Vb 4 \& { ... \& $var = 17; \& \*(Aq\*(Aq; \& } .Ve .PP Now the last expression evaluated yields the empty string, which is invisible. If you don't like the way this looks, use .PP .Vb 4 \& { ... \& $var = 17; \& ($SILENTLY); \& } .Ve .PP instead. Presumably, \f(CW$SILENTLY\fR has no value, so nothing will be interpolated. This is what is known as a `trick'. .SS "Compatibility" .IX Subsection "Compatibility" Every effort has been made to make this module compatible with older versions. The only known exceptions follow: .PP The output format of the default \f(CW\*(C`BROKEN\*(C'\fR subroutine has changed twice, most recently between versions 1.31 and 1.40. .PP Starting in version 1.10, the \f(CW$OUT\fR variable is arrogated for a special meaning. If you had templates before version 1.10 that happened to use a variable named \f(CW$OUT\fR, you will have to change them to use some other variable or all sorts of strangeness will result. .PP Between versions 0.1b and 1.00 the behavior of the \e metacharacter changed. In 0.1b, \e\e was special everywhere, and the template processor always replaced it with a single backslash before passing the code to Perl for evaluation. The rule now is more complicated but probably more convenient. See the section on backslash processing, below, for a full discussion. .SS "Backslash Processing" .IX Subsection "Backslash Processing" In \f(CW\*(C`Text::Template\*(C'\fR beta versions, the backslash was special whenever it appeared before a brace or another backslash. That meant that while \f(CW\*(C`{"\en"}\*(C'\fR did indeed generate a newline, \f(CW\*(C`{"\e\e"}\*(C'\fR did not generate a backslash, because the code passed to Perl for evaluation was \f(CW"\e"\fR which is a syntax error. If you wanted a backslash, you would have had to write \f(CW\*(C`{"\e\e\e\e"}\*(C'\fR. .PP In \f(CW\*(C`Text::Template\*(C'\fR versions 1.00 through 1.10, there was a bug: Backslash was special everywhere. In these versions, \f(CW\*(C`{"\en"}\*(C'\fR generated the letter \f(CW\*(C`n\*(C'\fR. .PP The bug has been corrected in version 1.11, but I did not go back to exactly the old rule, because I did not like the idea of having to write \f(CW\*(C`{"\e\e\e\e"}\*(C'\fR to get one backslash. The rule is now more complicated to remember, but probably easier to use. The rule is now: Backslashes are always passed to Perl unchanged \fIunless\fR they occur as part of a sequence like \f(CW\*(C`\e\e\e\e\e\e{\*(C'\fR or \f(CW\*(C`\e\e\e\e\e\e}\*(C'\fR. In these contexts, they are special; \f(CW\*(C`\e\e\*(C'\fR is replaced with \f(CW\*(C`\e\*(C'\fR, and \f(CW\*(C`\e{\*(C'\fR and \&\f(CW\*(C`\e}\*(C'\fR signal a literal brace. .PP Examples: .PP .Vb 1 \& \e{ foo \e} .Ve .PP is \fInot\fR evaluated, because the \f(CW\*(C`\e\*(C'\fR before the braces signals that they should be taken literally. The result in the output looks like this: .PP .Vb 1 \& { foo } .Ve .PP This is a syntax error: .PP .Vb 1 \& { "foo}" } .Ve .PP because \f(CW\*(C`Text::Template\*(C'\fR thinks that the code ends at the first \f(CW\*(C`}\*(C'\fR, and then gets upset when it sees the second one. To make this work correctly, use .PP .Vb 1 \& { "foo\e}" } .Ve .PP This passes \f(CW"foo}"\fR to Perl for evaluation. Note there's no \f(CW\*(C`\e\*(C'\fR in the evaluated code. If you really want a \f(CW\*(C`\e\*(C'\fR in the evaluated code, use .PP .Vb 1 \& { "foo\e\e\e}" } .Ve .PP This passes \f(CW"foo\e}"\fR to Perl for evaluation. .PP Starting with \f(CW\*(C`Text::Template\*(C'\fR version 1.20, backslash processing is disabled if you use the \f(CW\*(C`DELIMITERS\*(C'\fR option to specify alternative delimiter strings. .ie n .SS "A short note about $Text::Template::ERROR" .el .SS "A short note about \f(CW$Text::Template::ERROR\fP" .IX Subsection "A short note about $Text::Template::ERROR" In the past some people have fretted about `violating the package boundary' by examining a variable inside the \f(CW\*(C`Text::Template\*(C'\fR package. Don't feel this way. \f(CW$Text::Template::ERROR\fR is part of the published, official interface to this package. It is perfectly \s-1OK\s0 to inspect this variable. The interface is not going to change. .PP If it really, really bothers you, you can import a function called \&\f(CW\*(C`TTerror\*(C'\fR that returns the current value of the \f(CW$ERROR\fR variable. So you can say: .PP .Vb 1 \& use Text::Template \*(AqTTerror\*(Aq; \& \& my $template = Text::Template\->new(SOURCE => $filename); \& unless ($template) { \& my $err = TTerror; \& die "Couldn\*(Aqt make template: $err; aborting"; \& } .Ve .PP I don't see what benefit this has over just doing this: .PP .Vb 1 \& use Text::Template; \& \& my $template = Text::Template\->new(SOURCE => $filename) \& or die "Couldn\*(Aqt make template: $Text::Template::ERROR; aborting"; .Ve .PP But if it makes you happy to do it that way, go ahead. .SS "Sticky Widgets in Template Files" .IX Subsection "Sticky Widgets in Template Files" The \f(CW\*(C`CGI\*(C'\fR module provides functions for `sticky widgets', which are form input controls that retain their values from one page to the next. Sometimes people want to know how to include these widgets into their template output. .PP It's totally straightforward. Just call the \f(CW\*(C`CGI\*(C'\fR functions from inside the template: .PP .Vb 6 \& { $q\->checkbox_group(NAME => \*(Aqtoppings\*(Aq, \& LINEBREAK => true, \& COLUMNS => 3, \& VALUES => \e@toppings, \& ); \& } .Ve .SS "Automatic preprocessing of program fragments" .IX Subsection "Automatic preprocessing of program fragments" It may be useful to preprocess the program fragments before they are evaluated. See \f(CW\*(C`Text::Template::Preprocess\*(C'\fR for more details. .SS "Automatic postprocessing of template hunks" .IX Subsection "Automatic postprocessing of template hunks" It may be useful to process hunks of output before they are appended to the result text. For this, subclass and replace the \f(CW\*(C`append_text_to_result\*(C'\fR method. It is passed a list of pairs with these entries: .PP .Vb 4 \& handle \- a filehandle to which to print the desired output \& out \- a ref to a string to which to append, to use if handle is not given \& text \- the text that will be appended \& type \- where the text came from: TEXT for literal text, PROG for code .Ve .SH "HISTORY" .IX Header "HISTORY" Originally written by Mark Jason Dominus, Plover Systems (versions 0.01 \- 1.46) .PP Maintainership transferred to Michael Schout in version 1.47 .SH "THANKS" .IX Header "THANKS" Many thanks to the following people for offering support, encouragement, advice, bug reports, and all the other good stuff. .IP "\(bu" 4 Andrew G Wood .IP "\(bu" 4 Andy Wardley .IP "\(bu" 4 António Aragão .IP "\(bu" 4 Archie Warnock .IP "\(bu" 4 Bek Oberin .IP "\(bu" 4 Bob Dougherty .IP "\(bu" 4 Brian C. Shensky .IP "\(bu" 4 Chris Nandor .IP "\(bu" 4 Chris Wesley .IP "\(bu" 4 Chris.Brezil .IP "\(bu" 4 Daini Xie .IP "\(bu" 4 Dan Franklin .IP "\(bu" 4 Daniel LaLiberte .IP "\(bu" 4 David H. Adler .IP "\(bu" 4 David Marshall .IP "\(bu" 4 Dennis Taylor .IP "\(bu" 4 Donald L. Greer Jr. .IP "\(bu" 4 Dr. Frank Bucolo .IP "\(bu" 4 Fred Steinberg .IP "\(bu" 4 Gene Damon .IP "\(bu" 4 Hans Persson .IP "\(bu" 4 Hans Stoop .IP "\(bu" 4 Itamar Almeida de Carvalho .IP "\(bu" 4 James H. Thompson .IP "\(bu" 4 James Mastros .IP "\(bu" 4 Jarko Hietaniemi .IP "\(bu" 4 Jason Moore .IP "\(bu" 4 Jennifer D. St Clair .IP "\(bu" 4 Joel Appelbaum .IP "\(bu" 4 Joel Meulenberg .IP "\(bu" 4 Jonathan Roy .IP "\(bu" 4 Joseph Cheek .IP "\(bu" 4 Juan E. Camacho .IP "\(bu" 4 Kevin Atteson .IP "\(bu" 4 Kevin Madsen .IP "\(bu" 4 Klaus Arnhold .IP "\(bu" 4 Larry Virden .IP "\(bu" 4 Lieven Tomme .IP "\(bu" 4 Lorenzo Valdettaro .IP "\(bu" 4 Marek Grac .IP "\(bu" 4 Matt Womer .IP "\(bu" 4 Matt X. Hunter .IP "\(bu" 4 Michael G Schwern .IP "\(bu" 4 Michael J. Suzio .IP "\(bu" 4 Michaely Yeung .IP "\(bu" 4 Michelangelo Grigni .IP "\(bu" 4 Mike Brodhead .IP "\(bu" 4 Niklas Skoglund .IP "\(bu" 4 Randal L. Schwartz .IP "\(bu" 4 Reuven M. Lerner .IP "\(bu" 4 Robert M. Ioffe .IP "\(bu" 4 Ron Pero .IP "\(bu" 4 San Deng .IP "\(bu" 4 Sean Roehnelt .IP "\(bu" 4 Sergey Myasnikov .IP "\(bu" 4 Shabbir J. Safdar .IP "\(bu" 4 Shad Todd .IP "\(bu" 4 Steve Palincsar .IP "\(bu" 4 Tim Bunce .IP "\(bu" 4 Todd A. Green .IP "\(bu" 4 Tom Brown .IP "\(bu" 4 Tom Henry .IP "\(bu" 4 Tom Snee .IP "\(bu" 4 Trip Lilley .IP "\(bu" 4 Uwe Schneider .IP "\(bu" 4 Val Luck .IP "\(bu" 4 Yannis Livassof .IP "\(bu" 4 Yonat Sharon .IP "\(bu" 4 Zac Hansen .IP "\(bu" 4 gary at dls.net .PP Special thanks to: .IP "Jonathan Roy" 2 .IX Item "Jonathan Roy" for telling me how to do the \f(CW\*(C`Safe\*(C'\fR support (I spent two years worrying about it, and then Jonathan pointed out that it was trivial.) .IP "Ranjit Bhatnagar" 2 .IX Item "Ranjit Bhatnagar" for demanding less verbose fragments like they have in \s-1ASP,\s0 for helping me figure out the Right Thing, and, especially, for talking me out of adding any new syntax. These discussions resulted in the \&\f(CW$OUT\fR feature. .SS "Bugs and Caveats" .IX Subsection "Bugs and Caveats" \&\f(CW\*(C`my\*(C'\fR variables in \f(CW\*(C`fill_in\*(C'\fR are still susceptible to being clobbered by template evaluation. They all begin with \f(CW\*(C`fi_\*(C'\fR, so avoid those names in your templates. .PP The line number information will be wrong if the template's lines are not terminated by \f(CW"\en"\fR. You should let me know if this is a problem. If you do, I will fix it. .PP The \f(CW$OUT\fR variable has a special meaning in templates, so you cannot use it as if it were a regular variable. .PP There are not quite enough tests in the test suite. .SH "SOURCE" .IX Header "SOURCE" The development version is on github at and may be cloned from .SH "BUGS" .IX Header "BUGS" Please report any bugs or feature requests on the bugtracker website .PP When submitting a bug or request, please include a test-file or a patch to an existing test-file that illustrates the bug or desired feature. .SH "AUTHOR" .IX Header "AUTHOR" Michael Schout .SH "COPYRIGHT AND LICENSE" .IX Header "COPYRIGHT AND LICENSE" This software is copyright (c) 2013 by Mark Jason Dominus . .PP This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself. PK!arch/auto/IO/Stringy/.existsnu[PK!lib/IO/.existsnu[PK!l]?@?@lib/IO/ScalarArray.pmnu6$package IO::ScalarArray; use strict; use Carp; use IO::Handle; # The package version, both in 1.23 style *and* usable by MakeMaker: our $VERSION = '2.113'; # Inheritance: our @ISA = qw(IO::Handle); require IO::WrapTie and push @ISA, 'IO::WrapTie::Slave' if ($] >= 5.004); =head1 NAME IO::ScalarArray - IO:: interface for reading/writing an array of scalars =head1 SYNOPSIS Perform I/O on strings, using the basic OO interface... use IO::ScalarArray; @data = ("My mes", "sage:\n"); ### Open a handle on an array, and append to it: $AH = new IO::ScalarArray \@data; $AH->print("Hello"); $AH->print(", world!\nBye now!\n"); print "The array is now: ", @data, "\n"; ### Open a handle on an array, read it line-by-line, then close it: $AH = new IO::ScalarArray \@data; while (defined($_ = $AH->getline)) { print "Got line: $_"; } $AH->close; ### Open a handle on an array, and slurp in all the lines: $AH = new IO::ScalarArray \@data; print "All lines:\n", $AH->getlines; ### Get the current position (either of two ways): $pos = $AH->getpos; $offset = $AH->tell; ### Set the current position (either of two ways): $AH->setpos($pos); $AH->seek($offset, 0); ### Open an anonymous temporary array: $AH = new IO::ScalarArray; $AH->print("Hi there!"); print "I printed: ", @{$AH->aref}, "\n"; ### get at value Don't like OO for your I/O? No problem. Thanks to the magic of an invisible tie(), the following now works out of the box, just as it does with IO::Handle: use IO::ScalarArray; @data = ("My mes", "sage:\n"); ### Open a handle on an array, and append to it: $AH = new IO::ScalarArray \@data; print $AH "Hello"; print $AH ", world!\nBye now!\n"; print "The array is now: ", @data, "\n"; ### Open a handle on a string, read it line-by-line, then close it: $AH = new IO::ScalarArray \@data; while (<$AH>) { print "Got line: $_"; } close $AH; ### Open a handle on a string, and slurp in all the lines: $AH = new IO::ScalarArray \@data; print "All lines:\n", <$AH>; ### Get the current position (WARNING: requires 5.6): $offset = tell $AH; ### Set the current position (WARNING: requires 5.6): seek $AH, $offset, 0; ### Open an anonymous temporary scalar: $AH = new IO::ScalarArray; print $AH "Hi there!"; print "I printed: ", @{$AH->aref}, "\n"; ### get at value And for you folks with 1.x code out there: the old tie() style still works, though this is I: use IO::ScalarArray; ### Writing to a scalar... my @a; tie *OUT, 'IO::ScalarArray', \@a; print OUT "line 1\nline 2\n", "line 3\n"; print "Array is now: ", @a, "\n" ### Reading and writing an anonymous scalar... tie *OUT, 'IO::ScalarArray'; print OUT "line 1\nline 2\n", "line 3\n"; tied(OUT)->seek(0,0); while () { print "Got line: ", $_; } =head1 DESCRIPTION This class is part of the IO::Stringy distribution; see L for change log and general information. The IO::ScalarArray class implements objects which behave just like IO::Handle (or FileHandle) objects, except that you may use them to write to (or read from) arrays of scalars. Logically, an array of scalars defines an in-core "file" whose contents are the concatenation of the scalars in the array. The handles created by this class are automatically Cd (though please see L<"WARNINGS"> for information relevant to your Perl version). For writing large amounts of data with individual print() statements, this class is likely to be more efficient than IO::Scalar. Basically, this: my @a; $AH = new IO::ScalarArray \@a; $AH->print("Hel", "lo, "); ### OO style $AH->print("world!\n"); ### ditto Or this: my @a; $AH = new IO::ScalarArray \@a; print $AH "Hel", "lo, "; ### non-OO style print $AH "world!\n"; ### ditto Causes @a to be set to the following array of 3 strings: ( "Hel" , "lo, " , "world!\n" ) See L and compare with this class. =head1 PUBLIC INTERFACE =head2 Construction =over 4 =cut #------------------------------ =item new [ARGS...] I Return a new, unattached array handle. If any arguments are given, they're sent to open(). =cut sub new { my $proto = shift; my $class = ref($proto) || $proto; my $self = bless \do { local *FH }, $class; tie *$self, $class, $self; $self->open(@_); ### open on anonymous by default $self; } sub DESTROY { shift->close; } #------------------------------ =item open [ARRAYREF] I Open the array handle on a new array, pointed to by ARRAYREF. If no ARRAYREF is given, a "private" array is created to hold the file data. Returns the self object on success, undefined on error. =cut sub open { my ($self, $aref) = @_; ### Sanity: defined($aref) or do {my @a; $aref = \@a}; (ref($aref) eq "ARRAY") or croak "open needs a ref to a array"; ### Setup: $self->setpos([0,0]); *$self->{AR} = $aref; $self; } #------------------------------ =item opened I Is the array handle opened on something? =cut sub opened { *{shift()}->{AR}; } #------------------------------ =item close I Disassociate the array handle from its underlying array. Done automatically on destroy. =cut sub close { my $self = shift; %{*$self} = (); 1; } =back =cut #============================== =head2 Input and output =over 4 =cut #------------------------------ =item flush I No-op, provided for OO compatibility. =cut sub flush { "0 but true" } #------------------------------ =item fileno I No-op, returns undef =cut sub fileno { } #------------------------------ =item getc I Return the next character, or undef if none remain. This does a read(1), which is somewhat costly. =cut sub getc { my $buf = ''; ($_[0]->read($buf, 1) ? $buf : undef); } #------------------------------ =item getline I Return the next line, or undef on end of data. Can safely be called in an array context. Currently, lines are delimited by "\n". =cut sub getline { my $self = shift; my ($str, $line) = (undef, ''); ### Minimal impact implementation! ### We do the fast thing (no regexps) if using the ### classic input record separator. ### Case 1: $/ is undef: slurp all... if (!defined($/)) { return undef if ($self->eof); ### Get the rest of the current string, followed by remaining strings: my $ar = *$self->{AR}; my @slurp = ( substr($ar->[*$self->{Str}], *$self->{Pos}), @$ar[(1 + *$self->{Str}) .. $#$ar ] ); ### Seek to end: $self->_setpos_to_eof; return join('', @slurp); } ### Case 2: $/ is "\n": elsif ($/ eq "\012") { ### Until we hit EOF (or exited because of a found line): until ($self->eof) { ### If at end of current string, go fwd to next one (won't be EOF): if ($self->_eos) {++*$self->{Str}, *$self->{Pos}=0}; ### Get ref to current string in array, and set internal pos mark: $str = \(*$self->{AR}[*$self->{Str}]); ### get current string pos($$str) = *$self->{Pos}; ### start matching from here ### Get from here to either \n or end of string, and add to line: $$str =~ m/\G(.*?)((\n)|\Z)/g; ### match to 1st \n or EOS $line .= $1.$2; ### add it *$self->{Pos} += length($1.$2); ### move fwd by len matched return $line if $3; ### done, got line with "\n" } return ($line eq '') ? undef : $line; ### return undef if EOF } ### Case 3: $/ is ref to int. Bail out. elsif (ref($/)) { croak '$/ given as a ref to int; currently unsupported'; } ### Case 4: $/ is either "" (paragraphs) or something weird... ### Bail for now. else { croak '$/ as given is currently unsupported'; } } #------------------------------ =item getlines I Get all remaining lines. It will croak() if accidentally called in a scalar context. =cut sub getlines { my $self = shift; wantarray or croak("can't call getlines in scalar context!"); my ($line, @lines); push @lines, $line while (defined($line = $self->getline)); @lines; } #------------------------------ =item print ARGS... I Print ARGS to the underlying array. Currently, this always causes a "seek to the end of the array" and generates a new array entry. This may change in the future. =cut sub print { my $self = shift; push @{*$self->{AR}}, join('', @_) . (defined($\) ? $\ : ""); ### add the data $self->_setpos_to_eof; 1; } #------------------------------ =item read BUF, NBYTES, [OFFSET]; I Read some bytes from the array. Returns the number of bytes actually read, 0 on end-of-file, undef on error. =cut sub read { my $self = $_[0]; ### we must use $_[1] as a ref my $n = $_[2]; my $off = $_[3] || 0; ### print "getline\n"; my $justread; my $len; ($off ? substr($_[1], $off) : $_[1]) = ''; ### Stop when we have zero bytes to go, or when we hit EOF: my @got; until (!$n or $self->eof) { ### If at end of current string, go forward to next one (won't be EOF): if ($self->_eos) { ++*$self->{Str}; *$self->{Pos} = 0; } ### Get longest possible desired substring of current string: $justread = substr(*$self->{AR}[*$self->{Str}], *$self->{Pos}, $n); $len = length($justread); push @got, $justread; $n -= $len; *$self->{Pos} += $len; } $_[1] .= join('', @got); return length($_[1])-$off; } #------------------------------ =item write BUF, NBYTES, [OFFSET]; I Write some bytes into the array. =cut sub write { my $self = $_[0]; my $n = $_[2]; my $off = $_[3] || 0; my $data = substr($_[1], $n, $off); $n = length($data); $self->print($data); return $n; } =back =cut #============================== =head2 Seeking/telling and other attributes =over 4 =cut #------------------------------ =item autoflush I No-op, provided for OO compatibility. =cut sub autoflush {} #------------------------------ =item binmode I No-op, provided for OO compatibility. =cut sub binmode {} #------------------------------ =item clearerr I Clear the error and EOF flags. A no-op. =cut sub clearerr { 1 } #------------------------------ =item eof I Are we at end of file? =cut sub eof { ### print "checking EOF [*$self->{Str}, *$self->{Pos}]\n"; ### print "SR = ", $#{*$self->{AR}}, "\n"; return 0 if (*{$_[0]}->{Str} < $#{*{$_[0]}->{AR}}); ### before EOA return 1 if (*{$_[0]}->{Str} > $#{*{$_[0]}->{AR}}); ### after EOA ### ### at EOA, past EOS: ((*{$_[0]}->{Str} == $#{*{$_[0]}->{AR}}) && ($_[0]->_eos)); } #------------------------------ # # _eos # # I Are we at end of the CURRENT string? # sub _eos { (*{$_[0]}->{Pos} >= length(*{$_[0]}->{AR}[*{$_[0]}->{Str}])); ### past last char } #------------------------------ =item seek POS,WHENCE I Seek to a given position in the stream. Only a WHENCE of 0 (SEEK_SET) is supported. =cut sub seek { my ($self, $pos, $whence) = @_; ### Seek: if ($whence == 0) { $self->_seek_set($pos); } elsif ($whence == 1) { $self->_seek_cur($pos); } elsif ($whence == 2) { $self->_seek_end($pos); } else { croak "bad seek whence ($whence)" } return 1; } #------------------------------ # # _seek_set POS # # Instance method, private. # Seek to $pos relative to start: # sub _seek_set { my ($self, $pos) = @_; ### Advance through array until done: my $istr = 0; while (($pos >= 0) && ($istr < scalar(@{*$self->{AR}}))) { if (length(*$self->{AR}[$istr]) > $pos) { ### it's in this string! return $self->setpos([$istr, $pos]); } else { ### it's in next string $pos -= length(*$self->{AR}[$istr++]); ### move forward one string } } ### If we reached this point, pos is at or past end; zoom to EOF: return $self->_setpos_to_eof; } #------------------------------ # # _seek_cur POS # # Instance method, private. # Seek to $pos relative to current position. # sub _seek_cur { my ($self, $pos) = @_; $self->_seek_set($self->tell + $pos); } #------------------------------ # # _seek_end POS # # Instance method, private. # Seek to $pos relative to end. # We actually seek relative to beginning, which is simple. # sub _seek_end { my ($self, $pos) = @_; $self->_seek_set($self->_tell_eof + $pos); } #------------------------------ =item tell I Return the current position in the stream, as a numeric offset. =cut sub tell { my $self = shift; my $off = 0; my ($s, $str_s); for ($s = 0; $s < *$self->{Str}; $s++) { ### count all "whole" scalars defined($str_s = *$self->{AR}[$s]) or $str_s = ''; ###print STDERR "COUNTING STRING $s (". length($str_s) . ")\n"; $off += length($str_s); } ###print STDERR "COUNTING POS ($self->{Pos})\n"; return ($off += *$self->{Pos}); ### plus the final, partial one } #------------------------------ # # _tell_eof # # Instance method, private. # Get position of EOF, as a numeric offset. # This is identical to the size of the stream - 1. # sub _tell_eof { my $self = shift; my $len = 0; foreach (@{*$self->{AR}}) { $len += length($_) } $len; } #------------------------------ =item setpos POS I Seek to a given position in the array, using the opaque getpos() value. Don't expect this to be a number. =cut sub setpos { my ($self, $pos) = @_; (ref($pos) eq 'ARRAY') or die "setpos: only use a value returned by getpos!\n"; (*$self->{Str}, *$self->{Pos}) = @$pos; } #------------------------------ # # _setpos_to_eof # # Fast-forward to EOF. # sub _setpos_to_eof { my $self = shift; $self->setpos([scalar(@{*$self->{AR}}), 0]); } #------------------------------ =item getpos I Return the current position in the array, as an opaque value. Don't expect this to be a number. =cut sub getpos { [*{$_[0]}->{Str}, *{$_[0]}->{Pos}]; } #------------------------------ =item aref I Return a reference to the underlying array. =cut sub aref { *{shift()}->{AR}; } =back =cut #------------------------------ # Tied handle methods... #------------------------------ ### Conventional tiehandle interface: sub TIEHANDLE { (defined($_[1]) && UNIVERSAL::isa($_[1],"IO::ScalarArray")) ? $_[1] : shift->new(@_) } sub GETC { shift->getc(@_) } sub PRINT { shift->print(@_) } sub PRINTF { shift->print(sprintf(shift, @_)) } sub READ { shift->read(@_) } sub READLINE { wantarray ? shift->getlines(@_) : shift->getline(@_) } sub WRITE { shift->write(@_); } sub CLOSE { shift->close(@_); } sub SEEK { shift->seek(@_); } sub TELL { shift->tell(@_); } sub EOF { shift->eof(@_); } sub BINMODE { 1; } #------------------------------------------------------------ 1; __END__ # SOME PRIVATE NOTES: # # * The "current position" is the position before the next # character to be read/written. # # * Str gives the string index of the current position, 0-based # # * Pos gives the offset within AR[Str], 0-based. # # * Inital pos is [0,0]. After print("Hello"), it is [1,0]. =head1 AUTHOR Eryq (F). President, ZeeGee Software Inc (F). =head1 CONTRIBUTORS Dianne Skoll (F). =head1 COPYRIGHT & LICENSE Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. =cut PK!GJJlib/IO/Lines.pmnu6$package IO::Lines; use strict; use Carp; use IO::ScalarArray; # The package version, both in 1.23 style *and* usable by MakeMaker: our $VERSION = '2.113'; # Inheritance: our @ISA = qw(IO::ScalarArray); ### also gets us new_tie :-) =head1 NAME IO::Lines - IO:: interface for reading/writing an array of lines =head1 SYNOPSIS use IO::Lines; ### See IO::ScalarArray for details =head1 DESCRIPTION This class implements objects which behave just like FileHandle (or IO::Handle) objects, except that you may use them to write to (or read from) an array of lines. C capable as well. This is a subclass of L in which the underlying array has its data stored in a line-oriented-format: that is, every element ends in a C<"\n">, with the possible exception of the final element. This makes C I more efficient; if you plan to do line-oriented reading/printing, you want this class. The C method will enforce this rule, so you can print arbitrary data to the line-array: it will break the data at newlines appropriately. See L for full usage and warnings. =cut #------------------------------ # # getline # # Instance method, override. # Return the next line, or undef on end of data. # Can safely be called in an array context. # Currently, lines are delimited by "\n". # sub getline { my $self = shift; if (!defined $/) { return join( '', $self->_getlines_for_newlines ); } elsif ($/ eq "\n") { if (!*$self->{Pos}) { ### full line... return *$self->{AR}[*$self->{Str}++]; } else { ### partial line... my $partial = substr(*$self->{AR}[*$self->{Str}++], *$self->{Pos}); *$self->{Pos} = 0; return $partial; } } else { croak 'unsupported $/: must be "\n" or undef'; } } #------------------------------ # # getlines # # Instance method, override. # Return an array comprised of the remaining lines, or () on end of data. # Must be called in an array context. # Currently, lines are delimited by "\n". # sub getlines { my $self = shift; wantarray or croak("can't call getlines in scalar context!"); if ((defined $/) and ($/ eq "\n")) { return $self->_getlines_for_newlines(@_); } else { ### slow but steady return $self->SUPER::getlines(@_); } } #------------------------------ # # _getlines_for_newlines # # Instance method, private. # If $/ is newline, do fast getlines. # This CAN NOT invoke getline! # sub _getlines_for_newlines { my $self = shift; my ($rArray, $Str, $Pos) = @{*$self}{ qw( AR Str Pos ) }; my @partial = (); if ($Pos) { ### partial line... @partial = (substr( $rArray->[ $Str++ ], $Pos )); *$self->{Pos} = 0; } *$self->{Str} = scalar @$rArray; ### about to exhaust @$rArray return (@partial, @$rArray[ $Str .. $#$rArray ]); ### remaining full lines... } #------------------------------ # # print ARGS... # # Instance method, override. # Print ARGS to the underlying line array. # sub print { if (defined $\ && $\ ne "\n") { croak 'unsupported $\: must be "\n" or undef'; } my $self = shift; ### print STDERR "\n[[ARRAY WAS...\n", @{*$self->{AR}}, "<>\n"; my @lines = split /^/, join('', @_); @lines or return 1; ### Did the previous print not end with a newline? ### If so, append first line: if (@{*$self->{AR}} and (*$self->{AR}[-1] !~ /\n\Z/)) { *$self->{AR}[-1] .= shift @lines; } push @{*$self->{AR}}, @lines; ### add the remainder ### print STDERR "\n[[ARRAY IS NOW...\n", @{*$self->{AR}}, "<>\n"; 1; } #------------------------------ 1; __END__ =head1 VERSION $Id: Lines.pm,v 1.3 2005/02/10 21:21:53 dfs Exp $ =head1 AUTHOR Eryq (F). President, ZeeGee Software Inc (F). =head1 CONTRIBUTORS Dianne Skoll (F). =head1 COPYRIGHT & LICENSE Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. =cut PK!rlib/IO/AtomicFile.pmnu6$package IO::AtomicFile; use strict; use warnings; use parent 'IO::File'; our $VERSION = '2.113'; #------------------------------ # new ARGS... #------------------------------ # Class method, constructor. # Any arguments are sent to open(). # sub new { my $class = shift; my $self = $class->SUPER::new(); ${*$self}{'io_atomicfile_suffix'} = ''; $self->open(@_) if @_; $self; } #------------------------------ # DESTROY #------------------------------ # Destructor. # sub DESTROY { shift->close(1); ### like close, but raises fatal exception on failure } #------------------------------ # open PATH, MODE #------------------------------ # Class/instance method. # sub open { my ($self, $path, $mode) = @_; ref($self) or $self = $self->new; ### now we have an instance! ### Create tmp path, and remember this info: my $temp = "${path}..TMP" . ${*$self}{'io_atomicfile_suffix'}; ${*$self}{'io_atomicfile_temp'} = $temp; ${*$self}{'io_atomicfile_path'} = $path; ### Open the file! Returns filehandle on success, for use as a constructor: $self->SUPER::open($temp, $mode) ? $self : undef; } #------------------------------ # _closed [YESNO] #------------------------------ # Instance method, private. # Are we already closed? Argument sets new value, returns previous one. # sub _closed { my $self = shift; my $oldval = ${*$self}{'io_atomicfile_closed'}; ${*$self}{'io_atomicfile_closed'} = shift if @_; $oldval; } #------------------------------ # close #------------------------------ # Instance method. # Close the handle, and rename the temp file to its final name. # sub close { my ($self, $die) = @_; unless ($self->_closed(1)) { ### sentinel... if ($self->SUPER::close()) { rename(${*$self}{'io_atomicfile_temp'}, ${*$self}{'io_atomicfile_path'}) or ($die ? die "close (rename) atomic file: $!\n" : return undef); } else { ($die ? die "close atomic file: $!\n" : return undef); } } 1; } #------------------------------ # delete #------------------------------ # Instance method. # Close the handle, and delete the temp file. # sub delete { my $self = shift; unless ($self->_closed(1)) { ### sentinel... $self->SUPER::close(); return unlink(${*$self}{'io_atomicfile_temp'}); } 1; } #------------------------------ # detach #------------------------------ # Instance method. # Close the handle, but DO NOT delete the temp file. # sub detach { my $self = shift; $self->SUPER::close() unless ($self->_closed(1)); 1; } #------------------------------ 1; __END__ =head1 NAME IO::AtomicFile - write a file which is updated atomically =head1 SYNOPSIS use strict; use warnings; use feature 'say'; use IO::AtomicFile; # Write a temp file, and have it install itself when closed: my $fh = IO::AtomicFile->open("bar.dat", "w"); $fh->say("Hello!"); $fh->close || die "couldn't install atomic file: $!"; # Write a temp file, but delete it before it gets installed: my $fh = IO::AtomicFile->open("bar.dat", "w"); $fh->say("Hello!"); $fh->delete; # Write a temp file, but neither install it nor delete it: my $fh = IO::AtomicFile->open("bar.dat", "w"); $fh->say("Hello!"); $fh->detach; =head1 DESCRIPTION This module is intended for people who need to update files reliably in the face of unexpected program termination. For example, you generally don't want to be halfway in the middle of writing I and have your program terminate! Even the act of writing a single scalar to a filehandle is I atomic. But this module gives you true atomic updates, via C. When you open a file I via this module, you are I opening a temporary file I, and writing your output there. The act of closing this file (either explicitly via C, or implicitly via the destruction of the object) will cause C to be called... therefore, from the point of view of the outside world, the file's contents are updated in a single time quantum. To ensure that problems do not go undetected, the C method done by the destructor will raise a fatal exception if the C fails. The explicit C just returns C. You can also decide at any point to trash the file you've been building. =head1 METHODS L inherits all methods from L and implements the following new ones. =head2 close $fh->close(); This method calls its parent L and then renames its temporary file as the original file name. =head2 delete $fh->delete(); This method calls its parent L and then deletes the temporary file. =head2 detach $fh->detach(); This method calls its parent L. Unlike L it does not then delete the temporary file. =head1 AUTHOR Eryq (F). President, ZeeGee Software Inc (F). =head1 CONTRIBUTORS Dianne Skoll (F). =head1 COPYRIGHT & LICENSE Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. =cut PK!h lib/IO/Stringy.pmnu6$package IO::Stringy; use strict; use Exporter; our $VERSION = '2.113'; 1; __END__ =head1 NAME IO-stringy - I/O on in-core objects like strings and arrays =head1 SYNOPSIS use strict; use warnings; use IO::AtomicFile; # Write a file which is updated atomically use IO::InnerFile; # define a file inside another file use IO::Lines; # I/O handle to read/write to array of lines use IO::Scalar; # I/O handle to read/write to a string use IO::ScalarArray; # I/O handle to read/write to array of scalars use IO::Wrap; # Wrap old-style FHs in standard OO interface use IO::WrapTie; # Tie your handles & retain full OO interface # ... =head1 DESCRIPTION This toolkit primarily provides modules for performing both traditional and object-oriented i/o) on things I than normal filehandles; in particular, L, L, and L. In the more-traditional IO::Handle front, we have L which may be used to painlessly create files which are updated atomically. And in the "this-may-prove-useful" corner, we have L, whose exported wraphandle() function will clothe anything that's not a blessed object in an IO::Handle-like wrapper... so you can just use OO syntax and stop worrying about whether your function's caller handed you a string, a globref, or a FileHandle. =head1 AUTHOR Eryq (F). President, ZeeGee Software Inc (F). =head1 CONTRIBUTORS Dianne Skoll (F). =head1 COPYRIGHT & LICENSE Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. =cut PK!*2U"U"lib/IO/Wrap.pmnu6$package IO::Wrap; use strict; use Exporter; use FileHandle; use Carp; our $VERSION = '2.113'; our @ISA = qw(Exporter); our @EXPORT = qw(wraphandle); #------------------------------ # wraphandle RAW #------------------------------ sub wraphandle { my $raw = shift; new IO::Wrap $raw; } #------------------------------ # new STREAM #------------------------------ sub new { my ($class, $stream) = @_; no strict 'refs'; ### Convert raw scalar to globref: ref($stream) or $stream = \*$stream; ### Wrap globref and incomplete objects: if ((ref($stream) eq 'GLOB') or ### globref (ref($stream) eq 'FileHandle') && !defined(&FileHandle::read)) { return bless \$stream, $class; } $stream; ### already okay! } #------------------------------ # I/O methods... #------------------------------ sub close { my $self = shift; return close($$self); } sub fileno { my $self = shift; my $fh = $$self; return fileno($fh); } sub getline { my $self = shift; my $fh = $$self; return scalar(<$fh>); } sub getlines { my $self = shift; wantarray or croak("Can't call getlines in scalar context!"); my $fh = $$self; <$fh>; } sub print { my $self = shift; print { $$self } @_; } sub read { my $self = shift; return read($$self, $_[0], $_[1]); } sub seek { my $self = shift; return seek($$self, $_[0], $_[1]); } sub tell { my $self = shift; return tell($$self); } 1; __END__ =head1 NAME IO::Wrap - Wrap raw filehandles in the IO::Handle interface =head1 SYNOPSIS use strict; use warnings; use IO::Wrap; # this is a fairly senseless use case as IO::Handle already does this. my $wrap_fh = IO::Wrap->new(\*STDIN); my $line = $wrap_fh->getline(); # Do stuff with any kind of filehandle (including a bare globref), or # any kind of blessed object that responds to a print() message. # already have a globref? a FileHandle? a scalar filehandle name? $wrap_fh = IO::Wrap->new($some_unknown_thing); # At this point, we know we have an IO::Handle-like object! YAY $wrap_fh->print("Hey there!"); You can also do this using a convenience wrapper function use strict; use warnings; use IO::Wrap qw(wraphandle); # this is a fairly senseless use case as IO::Handle already does this. my $wrap_fh = wraphandle(\*STDIN); my $line = $wrap_fh->getline(); # Do stuff with any kind of filehandle (including a bare globref), or # any kind of blessed object that responds to a print() message. # already have a globref? a FileHandle? a scalar filehandle name? $wrap_fh = wraphandle($some_unknown_thing); # At this point, we know we have an IO::Handle-like object! YAY $wrap_fh->print("Hey there!"); =head1 DESCRIPTION Let's say you want to write some code which does I/O, but you don't want to force the caller to provide you with a L or L object. You want them to be able to say: do_stuff(\*STDOUT); do_stuff('STDERR'); do_stuff($some_FileHandle_object); do_stuff($some_IO_Handle_object); And even: do_stuff($any_object_with_a_print_method); Sure, one way to do it is to force the caller to use C. But that puts the burden on them. Another way to do it is to use B. Clearly, when wrapping a raw external filehandle (like C<\*STDOUT>), I didn't want to close the file descriptor when the wrapper object is destroyed; the user might not appreciate that! Hence, there's no C method in this class. When wrapping a L object, however, I believe that Perl will invoke the C when the last reference goes away, so in that case, the filehandle is closed if the wrapped L really was the last reference to it. =head1 FUNCTIONS L makes the following functions available. =head2 wraphandle # wrap a filehandle glob my $fh = wraphandle(\*STDIN); # wrap a raw filehandle glob by name $fh = wraphandle('STDIN'); # wrap a handle in an object $fh = wraphandle('Class::HANDLE'); # wrap a blessed FileHandle object use FileHandle; my $fho = FileHandle->new("/tmp/foo.txt", "r"); $fh = wraphandle($fho); # wrap any other blessed object that shares IO::Handle's interface $fh = wraphandle($some_object); This function is simply a wrapper to the L constructor method. =head1 METHODS L implements the following methods. =head2 close $fh->close(); The C method will attempt to close the system file descriptor. For a more complete description, read L. =head2 fileno my $int = $fh->fileno(); The C method returns the file descriptor for the wrapped filehandle. See L for more information. =head2 getline my $data = $fh->getline(); The C method mimics the function by the same name in L. It's like calling C<< my $data = <$fh>; >> but only in scalar context. =head2 getlines my @data = $fh->getlines(); The C method mimics the function by the same name in L. It's like calling C<< my @data = <$fh>; >> but only in list context. Calling this method in scalar context will result in a croak. =head2 new # wrap a filehandle glob my $fh = IO::Wrap->new(\*STDIN); # wrap a raw filehandle glob by name $fh = IO::Wrap->new('STDIN'); # wrap a handle in an object $fh = IO::Wrap->new('Class::HANDLE'); # wrap a blessed FileHandle object use FileHandle; my $fho = FileHandle->new("/tmp/foo.txt", "r"); $fh = IO::Wrap->new($fho); # wrap any other blessed object that shares IO::Handle's interface $fh = IO::Wrap->new($some_object); The C constructor method takes in a single argument and decides to wrap it or not it based on what it seems to be. A raw scalar file handle name, like C<"STDOUT"> or C<"Class::HANDLE"> can be wrapped, returning an L object instance. A raw filehandle glob, like C<\*STDOUT> can also be wrapped, returning an L object instance. A blessed L object can also be wrapped. This is a special case where an L object instance will only be returned in the case that your L object doesn't support the C method. Also, any other kind of blessed object that conforms to the L interface can be passed in. In this case, you just get back that object. In other words, we only wrap it into an L object when what you've supplied doesn't already conform to the L interface. If you get back an L object, it will obey a basic subset of the C interface. It will do so with object B, not B. =head3 CAVEATS This module does not allow you to wrap filehandle names which are given as strings that lack the package they were opened in. That is, if a user opens FOO in package Foo, they must pass it to you either as C<\*FOO> or as C<"Foo::FOO">. However, C<"STDIN"> and friends will work just fine. =head2 print $fh->print("Some string"); $fh->print("more", " than one", " string"); The C method will attempt to print a string or list of strings to the filehandle. For a more complete description, read L. =head2 read my $buffer; # try to read 30 chars into the buffer starting at the # current cursor position. my $num_chars_read = $fh->read($buffer, 30); The L method attempts to read a number of characters, starting at the filehandle's current cursor position. It returns the number of characters actually read. See L for more information. =head2 seek use Fcntl qw(:seek); # import the SEEK_CUR, SEEK_SET, SEEK_END constants # seek to the position in bytes $fh->seek(0, SEEK_SET); # seek to the position in bytes from the current position $fh->seek(22, SEEK_CUR); # seek to the EOF plus bytes $fh->seek(0, SEEK_END); The C method will attempt to set the cursor to a given position in bytes for the wrapped file handle. See L for more information. =head2 tell my $bytes = $fh->tell(); The C method will attempt to return the current position of the cursor in bytes for the wrapped file handle. See L for more information. =head1 AUTHOR Eryq (F). President, ZeeGee Software Inc (F). =head1 CONTRIBUTORS Dianne Skoll (F). =head1 COPYRIGHT & LICENSE Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. =cut PK!^::lib/IO/Scalar.pmnu6$package IO::Scalar; use strict; use Carp; use IO::Handle; ### Stringification, courtesy of B. K. Oxley (binkley): :-) use overload '""' => sub { ${*{$_[0]}->{SR}} }; use overload 'bool' => sub { 1 }; ### have to do this, so object is true! ### The package version, both in 1.23 style *and* usable by MakeMaker: our $VERSION = '2.113'; ### Inheritance: our @ISA = qw(IO::Handle); ### This stuff should be got rid of ASAP. require IO::WrapTie and push @ISA, 'IO::WrapTie::Slave' if ($] >= 5.004); #============================== =head1 NAME IO::Scalar - IO:: interface for reading/writing a scalar =head1 SYNOPSIS Perform I/O on strings, using the basic OO interface... use 5.005; use IO::Scalar; $data = "My message:\n"; ### Open a handle on a string, and append to it: $SH = new IO::Scalar \$data; $SH->print("Hello"); $SH->print(", world!\nBye now!\n"); print "The string is now: ", $data, "\n"; ### Open a handle on a string, read it line-by-line, then close it: $SH = new IO::Scalar \$data; while (defined($_ = $SH->getline)) { print "Got line: $_"; } $SH->close; ### Open a handle on a string, and slurp in all the lines: $SH = new IO::Scalar \$data; print "All lines:\n", $SH->getlines; ### Get the current position (either of two ways): $pos = $SH->getpos; $offset = $SH->tell; ### Set the current position (either of two ways): $SH->setpos($pos); $SH->seek($offset, 0); ### Open an anonymous temporary scalar: $SH = new IO::Scalar; $SH->print("Hi there!"); print "I printed: ", ${$SH->sref}, "\n"; ### get at value Don't like OO for your I/O? No problem. Thanks to the magic of an invisible tie(), the following now works out of the box, just as it does with IO::Handle: use 5.005; use IO::Scalar; $data = "My message:\n"; ### Open a handle on a string, and append to it: $SH = new IO::Scalar \$data; print $SH "Hello"; print $SH ", world!\nBye now!\n"; print "The string is now: ", $data, "\n"; ### Open a handle on a string, read it line-by-line, then close it: $SH = new IO::Scalar \$data; while (<$SH>) { print "Got line: $_"; } close $SH; ### Open a handle on a string, and slurp in all the lines: $SH = new IO::Scalar \$data; print "All lines:\n", <$SH>; ### Get the current position (WARNING: requires 5.6): $offset = tell $SH; ### Set the current position (WARNING: requires 5.6): seek $SH, $offset, 0; ### Open an anonymous temporary scalar: $SH = new IO::Scalar; print $SH "Hi there!"; print "I printed: ", ${$SH->sref}, "\n"; ### get at value And for you folks with 1.x code out there: the old tie() style still works, though this is I: use IO::Scalar; ### Writing to a scalar... my $s; tie *OUT, 'IO::Scalar', \$s; print OUT "line 1\nline 2\n", "line 3\n"; print "String is now: $s\n" ### Reading and writing an anonymous scalar... tie *OUT, 'IO::Scalar'; print OUT "line 1\nline 2\n", "line 3\n"; tied(OUT)->seek(0,0); while () { print "Got line: ", $_; } Stringification works, too! my $SH = new IO::Scalar \$data; print $SH "Hello, "; print $SH "world!"; print "I printed: $SH\n"; =head1 DESCRIPTION This class is part of the IO::Stringy distribution; see L for change log and general information. The IO::Scalar class implements objects which behave just like IO::Handle (or FileHandle) objects, except that you may use them to write to (or read from) scalars. These handles are automatically Cd (though please see L<"WARNINGS"> for information relevant to your Perl version). Basically, this: my $s; $SH = new IO::Scalar \$s; $SH->print("Hel", "lo, "); ### OO style $SH->print("world!\n"); ### ditto Or this: my $s; $SH = tie *OUT, 'IO::Scalar', \$s; print OUT "Hel", "lo, "; ### non-OO style print OUT "world!\n"; ### ditto Causes $s to be set to: "Hello, world!\n" =head1 PUBLIC INTERFACE =head2 Construction =over 4 =cut #------------------------------ =item new [ARGS...] I Return a new, unattached scalar handle. If any arguments are given, they're sent to open(). =cut sub new { my $proto = shift; my $class = ref($proto) || $proto; my $self = bless \do { local *FH }, $class; tie *$self, $class, $self; $self->open(@_); ### open on anonymous by default $self; } sub DESTROY { shift->close; } #------------------------------ =item open [SCALARREF] I Open the scalar handle on a new scalar, pointed to by SCALARREF. If no SCALARREF is given, a "private" scalar is created to hold the file data. Returns the self object on success, undefined on error. =cut sub open { my ($self, $sref) = @_; ### Sanity: defined($sref) or do {my $s = ''; $sref = \$s}; (ref($sref) eq "SCALAR") or croak "open() needs a ref to a scalar"; ### Setup: *$self->{Pos} = 0; ### seek position *$self->{SR} = $sref; ### scalar reference $self; } #------------------------------ =item opened I Is the scalar handle opened on something? =cut sub opened { *{shift()}->{SR}; } #------------------------------ =item close I Disassociate the scalar handle from its underlying scalar. Done automatically on destroy. =cut sub close { my $self = shift; %{*$self} = (); 1; } =back =cut #============================== =head2 Input and output =over 4 =cut #------------------------------ =item flush I No-op, provided for OO compatibility. =cut sub flush { "0 but true" } #------------------------------ =item fileno I No-op, returns undef =cut sub fileno { } #------------------------------ =item getc I Return the next character, or undef if none remain. =cut sub getc { my $self = shift; ### Return undef right away if at EOF; else, move pos forward: return undef if $self->eof; substr(${*$self->{SR}}, *$self->{Pos}++, 1); } #------------------------------ =item getline I Return the next line, or undef on end of string. Can safely be called in an array context. Currently, lines are delimited by "\n". =cut sub getline { my $self = shift; ### Return undef right away if at EOF: return undef if $self->eof; ### Get next line: my $sr = *$self->{SR}; my $i = *$self->{Pos}; ### Start matching at this point. ### Minimal impact implementation! ### We do the fast thing (no regexps) if using the ### classic input record separator. ### Case 1: $/ is undef: slurp all... if (!defined($/)) { *$self->{Pos} = length $$sr; return substr($$sr, $i); } ### Case 2: $/ is "\n": zoom zoom zoom... elsif ($/ eq "\012") { ### Seek ahead for "\n"... yes, this really is faster than regexps. my $len = length($$sr); for (; $i < $len; ++$i) { last if ord (substr ($$sr, $i, 1)) == 10; } ### Extract the line: my $line; if ($i < $len) { ### We found a "\n": $line = substr ($$sr, *$self->{Pos}, $i - *$self->{Pos} + 1); *$self->{Pos} = $i+1; ### Remember where we finished up. } else { ### No "\n"; slurp the remainder: $line = substr ($$sr, *$self->{Pos}, $i - *$self->{Pos}); *$self->{Pos} = $len; } return $line; } ### Case 3: $/ is ref to int. Do fixed-size records. ### (Thanks to Dominique Quatravaux.) elsif (ref($/)) { my $len = length($$sr); my $i = ${$/} + 0; my $line = substr ($$sr, *$self->{Pos}, $i); *$self->{Pos} += $i; *$self->{Pos} = $len if (*$self->{Pos} > $len); return $line; } ### Case 4: $/ is either "" (paragraphs) or something weird... ### This is Graham's general-purpose stuff, which might be ### a tad slower than Case 2 for typical data, because ### of the regexps. else { pos($$sr) = $i; ### If in paragraph mode, skip leading lines (and update i!): length($/) or (($$sr =~ m/\G\n*/g) and ($i = pos($$sr))); ### If we see the separator in the buffer ahead... if (length($/) ? $$sr =~ m,\Q$/\E,g ### (ordinary sep) TBD: precomp! : $$sr =~ m,\n\n,g ### (a paragraph) ) { *$self->{Pos} = pos $$sr; return substr($$sr, $i, *$self->{Pos}-$i); } ### Else if no separator remains, just slurp the rest: else { *$self->{Pos} = length $$sr; return substr($$sr, $i); } } } #------------------------------ =item getlines I Get all remaining lines. It will croak() if accidentally called in a scalar context. =cut sub getlines { my $self = shift; wantarray or croak("can't call getlines in scalar context!"); my ($line, @lines); push @lines, $line while (defined($line = $self->getline)); @lines; } #------------------------------ =item print ARGS... I Print ARGS to the underlying scalar. B this continues to always cause a seek to the end of the string, but if you perform seek()s and tell()s, it is still safer to explicitly seek-to-end before subsequent print()s. =cut sub print { my $self = shift; *$self->{Pos} = length(${*$self->{SR}} .= join('', @_) . (defined($\) ? $\ : "")); 1; } sub _unsafe_print { my $self = shift; my $append = join('', @_) . $\; ${*$self->{SR}} .= $append; *$self->{Pos} += length($append); 1; } sub _old_print { my $self = shift; ${*$self->{SR}} .= join('', @_) . $\; *$self->{Pos} = length(${*$self->{SR}}); 1; } #------------------------------ =item read BUF, NBYTES, [OFFSET] I Read some bytes from the scalar. Returns the number of bytes actually read, 0 on end-of-file, undef on error. =cut sub read { my $self = $_[0]; my $n = $_[2]; my $off = $_[3] || 0; my $read = substr(${*$self->{SR}}, *$self->{Pos}, $n); $n = length($read); *$self->{Pos} += $n; ($off ? substr($_[1], $off) : $_[1]) = $read; return $n; } #------------------------------ =item write BUF, NBYTES, [OFFSET] I Write some bytes to the scalar. =cut sub write { my $self = $_[0]; my $n = $_[2]; my $off = $_[3] || 0; my $data = substr($_[1], $off, $n); $n = length($data); $self->print($data); return $n; } #------------------------------ =item sysread BUF, LEN, [OFFSET] I Read some bytes from the scalar. Returns the number of bytes actually read, 0 on end-of-file, undef on error. =cut sub sysread { my $self = shift; $self->read(@_); } #------------------------------ =item syswrite BUF, NBYTES, [OFFSET] I Write some bytes to the scalar. =cut sub syswrite { my $self = shift; $self->write(@_); } =back =cut #============================== =head2 Seeking/telling and other attributes =over 4 =cut #------------------------------ =item autoflush I No-op, provided for OO compatibility. =cut sub autoflush {} #------------------------------ =item binmode I No-op, provided for OO compatibility. =cut sub binmode {} #------------------------------ =item clearerr I Clear the error and EOF flags. A no-op. =cut sub clearerr { 1 } #------------------------------ =item eof I Are we at end of file? =cut sub eof { my $self = shift; (*$self->{Pos} >= length(${*$self->{SR}})); } #------------------------------ =item seek OFFSET, WHENCE I Seek to a given position in the stream. =cut sub seek { my ($self, $pos, $whence) = @_; my $eofpos = length(${*$self->{SR}}); ### Seek: if ($whence == 0) { *$self->{Pos} = $pos } ### SEEK_SET elsif ($whence == 1) { *$self->{Pos} += $pos } ### SEEK_CUR elsif ($whence == 2) { *$self->{Pos} = $eofpos + $pos} ### SEEK_END else { croak "bad seek whence ($whence)" } ### Fixup: if (*$self->{Pos} < 0) { *$self->{Pos} = 0 } if (*$self->{Pos} > $eofpos) { *$self->{Pos} = $eofpos } return 1; } #------------------------------ =item sysseek OFFSET, WHENCE I Identical to C, I =cut sub sysseek { my $self = shift; $self->seek (@_); } #------------------------------ =item tell I Return the current position in the stream, as a numeric offset. =cut sub tell { *{shift()}->{Pos} } #------------------------------ # # use_RS [YESNO] # # I # Obey the current setting of $/, like IO::Handle does? # Default is false in 1.x, but cold-welded true in 2.x and later. # sub use_RS { my ($self, $yesno) = @_; carp "use_RS is deprecated and ignored; \$/ is always consulted\n"; } #------------------------------ =item setpos POS I Set the current position, using the opaque value returned by C. =cut sub setpos { shift->seek($_[0],0) } #------------------------------ =item getpos I Return the current position in the string, as an opaque object. =cut *getpos = \&tell; #------------------------------ =item sref I Return a reference to the underlying scalar. =cut sub sref { *{shift()}->{SR} } #------------------------------ # Tied handle methods... #------------------------------ # Conventional tiehandle interface: sub TIEHANDLE { ((defined($_[1]) && UNIVERSAL::isa($_[1], "IO::Scalar")) ? $_[1] : shift->new(@_)); } sub GETC { shift->getc(@_) } sub PRINT { shift->print(@_) } sub PRINTF { shift->print(sprintf(shift, @_)) } sub READ { shift->read(@_) } sub READLINE { wantarray ? shift->getlines(@_) : shift->getline(@_) } sub WRITE { shift->write(@_); } sub CLOSE { shift->close(@_); } sub SEEK { shift->seek(@_); } sub TELL { shift->tell(@_); } sub EOF { shift->eof(@_); } sub BINMODE { 1; } #------------------------------------------------------------ 1; __END__ =back =cut =head1 AUTHOR Eryq (F). President, ZeeGee Software Inc (F). =head1 CONTRIBUTORS Dianne Skoll (F). =head1 COPYRIGHT & LICENSE Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. =cut PK![|9|9lib/IO/WrapTie.pmnu6$package IO::WrapTie; use strict; use Exporter; # Inheritance, exporting, and package version: our @ISA = qw(Exporter); our @EXPORT = qw(wraptie); our $VERSION = '2.113'; # Function, exported. sub wraptie { IO::WrapTie::Master->new(@_); } # Class method; BACKWARDS-COMPATIBILITY ONLY! sub new { shift; IO::WrapTie::Master->new(@_); } #------------------------------------------------------------ package # hide from pause IO::WrapTie::Master; #------------------------------------------------------------ use strict; use vars qw($AUTOLOAD); use IO::Handle; # We inherit from IO::Handle to get methods which invoke i/o operators, # like print(), on our tied handle: our @ISA = qw(IO::Handle); #------------------------------ # new SLAVE, TIEARGS... #------------------------------ # Create a new subclass of IO::Handle which... # # (1) Handles i/o OPERATORS because it is tied to an instance of # an i/o-like class, like IO::Scalar. # # (2) Handles i/o METHODS by delegating them to that same tied object!. # # Arguments are the slave class (e.g., IO::Scalar), followed by all # the arguments normally sent into that class's C method. # In other words, much like the arguments to tie(). :-) # # NOTE: # The thing $x we return must be a BLESSED REF, for ($x->print()). # The underlying symbol must be a FILEHANDLE, for (print $x "foo"). # It has to have a way of getting to the "real" back-end object... # sub new { my $master = shift; my $io = IO::Handle->new; ### create a new handle my $slave = shift; tie *$io, $slave, @_; ### tie: will invoke slave's TIEHANDLE bless $io, $master; ### return a master } #------------------------------ # AUTOLOAD #------------------------------ # Delegate method invocations on the master to the underlying slave. # sub AUTOLOAD { my $method = $AUTOLOAD; $method =~ s/.*:://; my $self = shift; tied(*$self)->$method(\@_); } #------------------------------ # PRELOAD #------------------------------ # Utility. # # Most methods like print(), getline(), etc. which work on the tied object # via Perl's i/o operators (like 'print') are inherited from IO::Handle. # # Other methods, like seek() and sref(), we must delegate ourselves. # AUTOLOAD takes care of these. # # However, it may be necessary to preload delegators into your # own class. PRELOAD will do this. # sub PRELOAD { my $class = shift; foreach (@_) { eval "sub ${class}::$_ { my \$s = shift; tied(*\$s)->$_(\@_) }"; } } # Preload delegators for some standard methods which we can't simply # inherit from IO::Handle... for example, some IO::Handle methods # assume that there is an underlying file descriptor. # PRELOAD IO::WrapTie::Master qw(open opened close read clearerr eof seek tell setpos getpos); #------------------------------------------------------------ package # hide from pause IO::WrapTie::Slave; #------------------------------------------------------------ # Teeny private class providing a new_tie constructor... # # HOW IT ALL WORKS: # # Slaves inherit from this class. # # When you send a new_tie() message to a tie-slave class (like IO::Scalar), # it first determines what class should provide its master, via TIE_MASTER. # In this case, IO::Scalar->TIE_MASTER would return IO::Scalar::Master. # Then, we create a new master (an IO::Scalar::Master) with the same args # sent to new_tie. # # In general, the new() method of the master is inherited directly # from IO::WrapTie::Master. # sub new_tie { my $self = shift; $self->TIE_MASTER->new($self,@_); ### e.g., IO::Scalar::Master->new(@_) } # Default class method for new_tie(). # All your tie-slave class (like IO::Scalar) has to do is override this # method with a method that returns the name of an appropriate "master" # class for tying that slave. # sub TIE_MASTER { 'IO::WrapTie::Master' } #------------------------------ 1; __END__ package IO::WrapTie; ### for doc generator =head1 NAME IO::WrapTie - wrap tieable objects in IO::Handle interface I =head1 SYNOPSIS First of all, you'll need tie(), so: require 5.004; I Use this with any existing class... use IO::WrapTie; use FooHandle; ### implements TIEHANDLE interface ### Suppose we want a "FooHandle->new(&FOO_RDWR, 2)". ### We can instead say... $FH = wraptie('FooHandle', &FOO_RDWR, 2); ### Now we can use... print $FH "Hello, "; ### traditional operator syntax... $FH->print("world!\n"); ### ...and OO syntax as well! I You can inherit from the L mixin to get a nifty C constructor... #------------------------------ package FooHandle; ### a class which can TIEHANDLE use IO::WrapTie; @ISA = qw(IO::WrapTie::Slave); ### inherit new_tie() ... #------------------------------ package main; $FH = FooHandle->new_tie(&FOO_RDWR, 2); ### $FH is an IO::WrapTie::Master print $FH "Hello, "; ### traditional operator syntax $FH->print("world!\n"); ### OO syntax See IO::Scalar as an example. It also shows you how to create classes which work both with and without 5.004. =head1 DESCRIPTION Suppose you have a class C, where... =over 4 =item * C does not inherit from L. That is, it performs file handle-like I/O, but to something other than an underlying file descriptor. Good examples are L (for printing to a string) and L (for printing to an array of lines). =item * C implements the C interface (see L). That is, it provides methods C, C, C, C, C, and C. =item * C implements the traditional OO interface of L and L. i.e., it contains methods like C, C, C, C, C, C, etc. =back Normally, users of your class would have two options: =over 4 =item * B and forsake named I/O operators like C. =item * B and forsake treating it as a first-class object (i.e., class-specific methods can only be invoked through the underlying object via C... giving the object a "split personality"). =back But now with L, you can say: $WT = wraptie('FooHandle', &FOO_RDWR, 2); $WT->print("Hello, world\n"); ### OO syntax print $WT "Yes!\n"; ### Named operator syntax too! $WT->weird_stuff; ### Other methods! And if you're authoring a class like C, just have it inherit from C and that first line becomes even prettier: $WT = FooHandle->new_tie(&FOO_RDWR, 2); B now, almost any class can look and work exactly like an L and be used both with OO and non-OO file handle syntax. =head1 HOW IT ALL WORKS =head2 The data structures Consider this example code, using classes in this distribution: use IO::Scalar; use IO::WrapTie; $WT = wraptie('IO::Scalar',\$s); print $WT "Hello, "; $WT->print("world!\n"); In it, the C function creates a data structure as follows: * $WT is a blessed reference to a tied filehandle $WT glob; that glob is tied to the "Slave" object. | * You would do all your i/o with $WT directly. | | | ,---isa--> IO::WrapTie::Master >--isa--> IO::Handle V / .-------------. | | | | * Perl i/o operators work on the tied object, | "Master" | invoking the C methods. | | * Method invocations are delegated to the tied | | slave. `-------------' | tied(*$WT) | .---isa--> IO::WrapTie::Slave V / .-------------. | | | "Slave" | * Instance of FileHandle-like class which doesn't | | actually use file descriptors, like IO::Scalar. | IO::Scalar | * The slave can be any kind of object. | | * Must implement the C interface. `-------------' I just as an L is really just a blessed reference to a I file handle glob. So also, an C is really just a blessed reference to a file handle glob I =head2 How C works =over 4 =item 1. The call to function C is passed onto C. Note that class C is a subclass of L. =item 2. The C<< IO::WrapTie::Master->new >> method creates a new L object, re-blessed into class C. This object is the I, which will be returned from the constructor. At the same time... =item 3. The C method also creates the I: this is an instance of C which is created by tying the master's L to C via C. This call to C creates the slave in the following manner: =item 4. Class C is sent the message C; it will usually delegate this to C<< SLAVECLASS->new(TIEARGS) >>, resulting in a new instance of C being created and returned. =item 5. Once both master and slave have been created, the master is returned to the caller. =back =head2 How I/O operators work (on the master) Consider using an i/o operator on the master: print $WT "Hello, world!\n"; Since the master C<$WT> is really a C reference to a glob, the normal Perl I/O operators like C may be used on it. They will just operate on the symbol part of the glob. Since the glob is tied to the slave, the slave's C method (part of the C interface) will be automatically invoked. If the slave is an L, that means L will be invoked, and that method happens to delegate to the C method of the same class. So the I work is ultimately done by L. =head2 How methods work (on the master) Consider using a method on the master: $WT->print("Hello, world!\n"); Since the master C<$WT> is blessed into the class C, Perl first attempts to find a C method there. Failing that, Perl next attempts to find a C method in the super class, L. It just so happens that there I such a method; that method merely invokes the C I/O operator on the self object... and for that, see above! But let's suppose we're dealing with a method which I part of L... for example: my $sref = $WT->sref; In this case, the intuitive behavior is to have the master delegate the method invocation to the slave (now do you see where the designations come from?). This is indeed what happens: C contains an C method which performs the delegation. So: when C can't be found in L, the C method of C is invoked, and the standard behavior of delegating the method to the underlying slave (here, an L) is done. Sometimes, to get this to work properly, you may need to create a subclass of C which is an effective master for I class, and do the delegation there. =head1 NOTES B Because that means forsaking the use of named operators like C, and you may need to pass the object to a subroutine which will attempt to use those operators: $O = FooHandle->new(&FOO_RDWR, 2); $O->print("Hello, world\n"); ### OO syntax is okay, BUT.... sub nope { print $_[0] "Nope!\n" } X nope($O); ### ERROR!!! (not a glob ref) B Because (1) you have to use C to invoke methods in the object's public interface (yuck), and (2) you may need to pass the tied symbol to another subroutine which will attempt to treat it in an OO-way... and that will break it: tie *T, 'FooHandle', &FOO_RDWR, 2; print T "Hello, world\n"; ### Operator is okay, BUT... tied(*T)->other_stuff; ### yuck! AND... sub nope { shift->print("Nope!\n") } X nope(\*T); ### ERROR!!! (method "print" on unblessed ref) B Why not simply write C to inherit from L I tried this, with an implementation similar to that of L. The problem is that I. Subclassing L will work fine for the OO stuff, and fine with named operators I you C... but if you just attempt to say: $IO = FooHandle->new(&FOO_RDWR, 2); print $IO "Hello!\n"; you get a warning from Perl like: Filehandle GEN001 never opened because it's trying to do system-level I/O on an (unopened) file descriptor. To avoid this, you apparently have to C the handle... which brings us right back to where we started! At least the L mixin lets us say: $IO = FooHandle->new_tie(&FOO_RDWR, 2); print $IO "Hello!\n"; and so is not I bad. C<:-)> =head1 WARNINGS Remember: this stuff is for doing L-like I/O on things I. If you have an underlying file descriptor, you're better off just inheriting from L. B it does B return an instance of the I/O class you're tying to! Invoking some methods on the master object causes C to delegate them to the slave object... so it I like you're manipulating a C object directly, but you're not. I have not explored all the ramifications of this use of C. I. =head1 AUTHOR Eryq (F). President, ZeeGee Software Inc (F). =head1 CONTRIBUTORS Dianne Skoll (F). =head1 COPYRIGHT & LICENSE Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. =cut PK!lib/IO/InnerFile.pmnu6$package IO::InnerFile; use strict; use warnings; use Symbol; our $VERSION = '2.113'; sub new { my ($class, $fh, $start, $lg) = @_; $start = 0 if (!$start or ($start < 0)); $lg = 0 if (!$lg or ($lg < 0)); ### Create the underlying "object": my $a = { FH => $fh, CRPOS => 0, START => $start, LG => $lg, }; ### Create a new filehandle tied to this object: $fh = gensym; tie(*$fh, $class, $a); return bless($fh, $class); } sub TIEHANDLE { my ($class, $data) = @_; return bless($data, $class); } sub DESTROY { my ($self) = @_; $self->close() if (ref($self) eq 'SCALAR'); } sub set_length { tied(${$_[0]})->{LG} = $_[1]; } sub get_length { tied(${$_[0]})->{LG}; } sub add_length { tied(${$_[0]})->{LG} += $_[1]; } sub set_start { tied(${$_[0]})->{START} = $_[1]; } sub get_start { tied(${$_[0]})->{START}; } sub set_end { tied(${$_[0]})->{LG} = $_[1] - tied(${$_[0]})->{START}; } sub get_end { tied(${$_[0]})->{LG} + tied(${$_[0]})->{START}; } sub write { shift->WRITE(@_) } sub print { shift->PRINT(@_) } sub printf { shift->PRINTF(@_) } sub flush { "0 but true"; } sub fileno { } sub binmode { 1; } sub getc { return GETC(tied(${$_[0]}) ); } sub read { return READ( tied(${$_[0]}), @_[1,2,3] ); } sub readline { return READLINE( tied(${$_[0]}) ); } sub getline { return READLINE( tied(${$_[0]}) ); } sub close { return CLOSE(tied(${$_[0]}) ); } sub seek { my ($self, $ofs, $whence) = @_; $self = tied( $$self ); $self->{CRPOS} = $ofs if ($whence == 0); $self->{CRPOS}+= $ofs if ($whence == 1); $self->{CRPOS} = $self->{LG} + $ofs if ($whence == 2); $self->{CRPOS} = 0 if ($self->{CRPOS} < 0); $self->{CRPOS} = $self->{LG} if ($self->{CRPOS} > $self->{LG}); return 1; } sub tell { return tied(${$_[0]})->{CRPOS}; } sub WRITE { die "inner files can only open for reading\n"; } sub PRINT { die "inner files can only open for reading\n"; } sub PRINTF { die "inner files can only open for reading\n"; } sub GETC { my ($self) = @_; return 0 if ($self->{CRPOS} >= $self->{LG}); my $data; ### Save and seek... my $old_pos = $self->{FH}->tell; $self->{FH}->seek($self->{CRPOS}+$self->{START}, 0); ### ...read... my $lg = $self->{FH}->read($data, 1); $self->{CRPOS} += $lg; ### ...and restore: $self->{FH}->seek($old_pos, 0); $self->{LG} = $self->{CRPOS} unless ($lg); return ($lg ? $data : undef); } sub READ { my ($self, $undefined, $lg, $ofs) = @_; $undefined = undef; return 0 if ($self->{CRPOS} >= $self->{LG}); $lg = $self->{LG} - $self->{CRPOS} if ($self->{CRPOS} + $lg > $self->{LG}); return 0 unless ($lg); ### Save and seek... my $old_pos = $self->{FH}->tell; $self->{FH}->seek($self->{CRPOS}+$self->{START}, 0); ### ...read... $lg = $self->{FH}->read($_[1], $lg, $_[3] ); $self->{CRPOS} += $lg; ### ...and restore: $self->{FH}->seek($old_pos, 0); $self->{LG} = $self->{CRPOS} unless ($lg); return $lg; } sub READLINE { my ($self) = @_; return $self->_readline_helper() unless wantarray; my @arr; while(defined(my $line = $self->_readline_helper())) { push(@arr, $line); } return @arr; } sub _readline_helper { my ($self) = @_; return undef if ($self->{CRPOS} >= $self->{LG}); # Handle slurp mode (CPAN ticket #72710) if (! defined($/)) { my $text; $self->READ($text, $self->{LG} - $self->{CRPOS}); return $text; } ### Save and seek... my $old_pos = $self->{FH}->tell; $self->{FH}->seek($self->{CRPOS}+$self->{START}, 0); ### ...read... my $text = $self->{FH}->getline; ### ...and restore: $self->{FH}->seek($old_pos, 0); #### If we detected a new EOF ... unless (defined $text) { $self->{LG} = $self->{CRPOS}; return undef; } my $lg=length($text); $lg = $self->{LG} - $self->{CRPOS} if ($self->{CRPOS} + $lg > $self->{LG}); $self->{CRPOS} += $lg; return substr($text, 0,$lg); } sub CLOSE { %{$_[0]}=(); } 1; __END__ __END__ =head1 NAME IO::InnerFile - define a file inside another file =head1 SYNOPSIS use strict; use warnings; use IO::InnerFile; # Read a subset of a file: my $fh = _some_file_handle; my $start = 10; my $length = 50; my $inner = IO::InnerFile->new($fh, $start, $length); while (my $line = <$inner>) { # ... } =head1 DESCRIPTION If you have a file handle that can C and C, then you can open an L on a range of the underlying file. =head1 CONSTRUCTORS L implements the following constructors. =head2 new my $inner = IO::InnerFile->new($fh); $inner = IO::InnerFile->new($fh, 10); $inner = IO::InnerFile->new($fh, 10, 50); Create a new L opened on the given file handle. The file handle supplied B be able to both C and C. The second and third parameters are start and length. Both are defaulted to zero (C<0>). Negative values are silently coerced to zero. =head1 METHODS L implements the following methods. =head2 add_length $inner->add_length(30); Add to the virtual length of the inner file by the number given in bytes. =head2 add_start $inner->add_start(30); Add to the virtual position of the inner file by the number given in bytes. =head2 binmode $inner->binmode(); This is a NOOP method just to satisfy the normal L interface. =head2 close =head2 fileno $inner->fileno(); This is a NOOP method just to satisfy the normal L interface. =head2 flush $inner->flush(); This is a NOOP method just to satisfy the normal L interface. =head2 get_end my $num_bytes = $inner->get_end(); Get the virtual end position of the inner file in bytes. =head2 get_length my $num_bytes = $inner->get_length(); Get the virtual length of the inner file in bytes. =head2 get_start my $num_bytes = $inner->get_start(); Get the virtual position of the inner file in bytes. =head2 getc =head2 getline =head2 print LIST =head2 printf =head2 read =head2 readline =head2 seek =head2 set_end $inner->set_end(30); Set the virtual end of the inner file in bytes (this basically just alters the length). =head2 set_length $inner->set_length(30); Set the virtual length of the inner file in bytes. =head2 set_start $inner->set_start(30); Set the virtual start position of the inner file in bytes. =head2 tell =head2 write =head1 AUTHOR Eryq (F). President, ZeeGee Software Inc (F). =head1 CONTRIBUTORS Dianne Skoll (F). =head1 COPYRIGHT & LICENSE Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. =cut PK!lib/auto/IO/Stringy/.existsnu[PK!xman3/IO::Lines.3pmnu[.\" Automatically generated by Pod::Man 4.11 (Pod::Simple 3.35) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is >0, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{\ . if \nF \{\ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{\ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" ======================================================================== .\" .IX Title "IO::Lines 3" .TH IO::Lines 3 "2020-01-17" "perl v5.26.3" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" IO::Lines \- IO:: interface for reading/writing an array of lines .SH "SYNOPSIS" .IX Header "SYNOPSIS" .Vb 1 \& use IO::Lines; \& \& ### See IO::ScalarArray for details .Ve .SH "DESCRIPTION" .IX Header "DESCRIPTION" This class implements objects which behave just like FileHandle (or IO::Handle) objects, except that you may use them to write to (or read from) an array of lines. \f(CW\*(C`tiehandle\*(C'\fR capable as well. .PP This is a subclass of IO::ScalarArray in which the underlying array has its data stored in a line-oriented-format: that is, every element ends in a \f(CW"\en"\fR, with the possible exception of the final element. This makes \f(CW\*(C`getline()\*(C'\fR \fImuch\fR more efficient; if you plan to do line-oriented reading/printing, you want this class. .PP The \f(CW\*(C`print()\*(C'\fR method will enforce this rule, so you can print arbitrary data to the line-array: it will break the data at newlines appropriately. .PP See IO::ScalarArray for full usage and warnings. .SH "VERSION" .IX Header "VERSION" \&\f(CW$Id:\fR Lines.pm,v 1.3 2005/02/10 21:21:53 dfs Exp $ .SH "AUTHOR" .IX Header "AUTHOR" Eryq (\fIeryq@zeegee.com\fR). President, ZeeGee Software Inc (\fIhttp://www.zeegee.com\fR). .SH "CONTRIBUTORS" .IX Header "CONTRIBUTORS" Dianne Skoll (\fIdfs@roaringpenguin.com\fR). .SH "COPYRIGHT & LICENSE" .IX Header "COPYRIGHT & LICENSE" Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. .PP This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. PK!S::man3/IO::WrapTie.3pmnu[.\" Automatically generated by Pod::Man 4.11 (Pod::Simple 3.35) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is >0, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{\ . if \nF \{\ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{\ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" ======================================================================== .\" .IX Title "IO::WrapTie 3" .TH IO::WrapTie 3 "2020-01-17" "perl v5.26.3" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" IO::WrapTie \- wrap tieable objects in IO::Handle interface .PP This is currently Alpha code, released for comments. Please give me your feedback! .SH "SYNOPSIS" .IX Header "SYNOPSIS" First of all, you'll need \fBtie()\fR, so: .PP .Vb 1 \& require 5.004; .Ve .PP \&\fIFunction interface (experimental).\fR Use this with any existing class... .PP .Vb 2 \& use IO::WrapTie; \& use FooHandle; ### implements TIEHANDLE interface \& \& ### Suppose we want a "FooHandle\->new(&FOO_RDWR, 2)". \& ### We can instead say... \& \& $FH = wraptie(\*(AqFooHandle\*(Aq, &FOO_RDWR, 2); \& \& ### Now we can use... \& print $FH "Hello, "; ### traditional operator syntax... \& $FH\->print("world!\en"); ### ...and OO syntax as well! .Ve .PP \&\fI\s-1OO\s0 interface (preferred).\fR You can inherit from the \*(L"Slave\*(R" in IO::WrapTie mixin to get a nifty \f(CW\*(C`new_tie()\*(C'\fR constructor... .PP .Vb 2 \& #\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\- \& package FooHandle; ### a class which can TIEHANDLE \& \& use IO::WrapTie; \& @ISA = qw(IO::WrapTie::Slave); ### inherit new_tie() \& ... \& \& \& #\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\-\- \& package main; \& \& $FH = FooHandle\->new_tie(&FOO_RDWR, 2); ### $FH is an IO::WrapTie::Master \& print $FH "Hello, "; ### traditional operator syntax \& $FH\->print("world!\en"); ### OO syntax .Ve .PP See IO::Scalar as an example. It also shows you how to create classes which work both with and without 5.004. .SH "DESCRIPTION" .IX Header "DESCRIPTION" Suppose you have a class \f(CW\*(C`FooHandle\*(C'\fR, where... .IP "\(bu" 4 \&\f(CW\*(C`FooHandle\*(C'\fR does not inherit from IO::Handle. That is, it performs file handle-like I/O, but to something other than an underlying file descriptor. Good examples are IO::Scalar (for printing to a string) and IO::Lines (for printing to an array of lines). .IP "\(bu" 4 \&\f(CW\*(C`FooHandle\*(C'\fR implements the \f(CW\*(C`TIEHANDLE\*(C'\fR interface (see perltie). That is, it provides methods \f(CW\*(C`TIEHANDLE\*(C'\fR, \f(CW\*(C`GETC\*(C'\fR, \f(CW\*(C`PRINT\*(C'\fR, \f(CW\*(C`PRINTF\*(C'\fR, \&\f(CW\*(C`READ\*(C'\fR, and \f(CW\*(C`READLINE\*(C'\fR. .IP "\(bu" 4 \&\f(CW\*(C`FooHandle\*(C'\fR implements the traditional \s-1OO\s0 interface of FileHandle and IO::Handle. i.e., it contains methods like \f(CW\*(C`getline\*(C'\fR, \&\f(CW\*(C`read\*(C'\fR, \f(CW\*(C`print\*(C'\fR, \f(CW\*(C`seek\*(C'\fR, \f(CW\*(C`tell\*(C'\fR, \f(CW\*(C`eof\*(C'\fR, etc. .PP Normally, users of your class would have two options: .IP "\(bu" 4 \&\fBUse only \s-1OO\s0 syntax,\fR and forsake named I/O operators like \f(CW\*(C`print\*(C'\fR. .IP "\(bu" 4 \&\fBUse with tie,\fR and forsake treating it as a first-class object (i.e., class-specific methods can only be invoked through the underlying object via \f(CW\*(C`tied\*(C'\fR... giving the object a \*(L"split personality\*(R"). .PP But now with IO::WrapTie, you can say: .PP .Vb 4 \& $WT = wraptie(\*(AqFooHandle\*(Aq, &FOO_RDWR, 2); \& $WT\->print("Hello, world\en"); ### OO syntax \& print $WT "Yes!\en"; ### Named operator syntax too! \& $WT\->weird_stuff; ### Other methods! .Ve .PP And if you're authoring a class like \f(CW\*(C`FooHandle\*(C'\fR, just have it inherit from \f(CW\*(C`IO::WrapTie::Slave\*(C'\fR and that first line becomes even prettier: .PP .Vb 1 \& $WT = FooHandle\->new_tie(&FOO_RDWR, 2); .Ve .PP \&\fBThe bottom line:\fR now, almost any class can look and work exactly like an IO::Handle and be used both with \s-1OO\s0 and non-OO file handle syntax. .SH "HOW IT ALL WORKS" .IX Header "HOW IT ALL WORKS" .SS "The data structures" .IX Subsection "The data structures" Consider this example code, using classes in this distribution: .PP .Vb 2 \& use IO::Scalar; \& use IO::WrapTie; \& \& $WT = wraptie(\*(AqIO::Scalar\*(Aq,\e$s); \& print $WT "Hello, "; \& $WT\->print("world!\en"); .Ve .PP In it, the \f(CW\*(C`wraptie\*(C'\fR function creates a data structure as follows: .PP .Vb 10 \& * $WT is a blessed reference to a tied filehandle \& $WT glob; that glob is tied to the "Slave" object. \& | * You would do all your i/o with $WT directly. \& | \& | \& | ,\-\-\-isa\-\-> IO::WrapTie::Master >\-\-isa\-\-> IO::Handle \& V / \& .\-\-\-\-\-\-\-\-\-\-\-\-\-. \& | | \& | | * Perl i/o operators work on the tied object, \& | "Master" | invoking the C methods. \& | | * Method invocations are delegated to the tied \& | | slave. \& \`\-\-\-\-\-\-\-\-\-\-\-\-\-\*(Aq \& | \& tied(*$WT) | .\-\-\-isa\-\-> IO::WrapTie::Slave \& V / \& .\-\-\-\-\-\-\-\-\-\-\-\-\-. \& | | \& | "Slave" | * Instance of FileHandle\-like class which doesn\*(Aqt \& | | actually use file descriptors, like IO::Scalar. \& | IO::Scalar | * The slave can be any kind of object. \& | | * Must implement the C interface. \& \`\-\-\-\-\-\-\-\-\-\-\-\-\-\*(Aq .Ve .PP \&\fI\s-1NOTE:\s0\fR just as an IO::Handle is really just a blessed reference to a \&\fItraditional\fR file handle glob. So also, an \f(CW\*(C`IO::WrapTie::Master\*(C'\fR is really just a blessed reference to a file handle glob \fIwhich has been tied to some \*(L"slave\*(R" class.\fR .ie n .SS "How ""wraptie"" works" .el .SS "How \f(CWwraptie\fP works" .IX Subsection "How wraptie works" .IP "1." 4 The call to function \f(CW\*(C`wraptie(SLAVECLASS, TIEARGS...)\*(C'\fR is passed onto \f(CW\*(C`IO::WrapTie::Master::new()\*(C'\fR. Note that class \f(CW\*(C`IO::WrapTie::Master\*(C'\fR is a subclass of IO::Handle. .IP "2." 4 The \f(CW\*(C`IO::WrapTie::Master\->new\*(C'\fR method creates a new IO::Handle object, re-blessed into class \f(CW\*(C`IO::WrapTie::Master\*(C'\fR. This object is the \fImaster\fR, which will be returned from the constructor. At the same time... .IP "3." 4 The \f(CW\*(C`new\*(C'\fR method also creates the \fIslave\fR: this is an instance of \f(CW\*(C`SLAVECLASS\*(C'\fR which is created by tying the master's IO::Handle to \f(CW\*(C`SLAVECLASS\*(C'\fR via \f(CW\*(C`tie\*(C'\fR. This call to \f(CW\*(C`tie\*(C'\fR creates the slave in the following manner: .IP "4." 4 Class \f(CW\*(C`SLAVECLASS\*(C'\fR is sent the message \f(CW\*(C`TIEHANDLE\*(C'\fR; it will usually delegate this to \f(CW\*(C`SLAVECLASS\->new(TIEARGS)\*(C'\fR, resulting in a new instance of \f(CW\*(C`SLAVECLASS\*(C'\fR being created and returned. .IP "5." 4 Once both master and slave have been created, the master is returned to the caller. .SS "How I/O operators work (on the master)" .IX Subsection "How I/O operators work (on the master)" Consider using an i/o operator on the master: .PP .Vb 1 \& print $WT "Hello, world!\en"; .Ve .PP Since the master \f(CW$WT\fR is really a \f(CW\*(C`blessed\*(C'\fR reference to a glob, the normal Perl I/O operators like \f(CW\*(C`print\*(C'\fR may be used on it. They will just operate on the symbol part of the glob. .PP Since the glob is tied to the slave, the slave's \f(CW\*(C`PRINT\*(C'\fR method (part of the \f(CW\*(C`TIEHANDLE\*(C'\fR interface) will be automatically invoked. .PP If the slave is an IO::Scalar, that means \*(L"\s-1PRINT\*(R"\s0 in IO::Scalar will be invoked, and that method happens to delegate to the \f(CW\*(C`print\*(C'\fR method of the same class. So the \fIreal\fR work is ultimately done by \&\*(L"print\*(R" in IO::Scalar. .SS "How methods work (on the master)" .IX Subsection "How methods work (on the master)" Consider using a method on the master: .PP .Vb 1 \& $WT\->print("Hello, world!\en"); .Ve .PP Since the master \f(CW$WT\fR is blessed into the class \f(CW\*(C`IO::WrapTie::Master\*(C'\fR, Perl first attempts to find a \f(CW\*(C`print\*(C'\fR method there. Failing that, Perl next attempts to find a \f(CW\*(C`print\*(C'\fR method in the super class, IO::Handle. It just so happens that there \fIis\fR such a method; that method merely invokes the \f(CW\*(C`print\*(C'\fR I/O operator on the self object... and for that, see above! .PP But let's suppose we're dealing with a method which \fIisn't\fR part of IO::Handle... for example: .PP .Vb 1 \& my $sref = $WT\->sref; .Ve .PP In this case, the intuitive behavior is to have the master delegate the method invocation to the slave (now do you see where the designations come from?). This is indeed what happens: \f(CW\*(C`IO::WrapTie::Master\*(C'\fR contains an \f(CW\*(C`AUTOLOAD\*(C'\fR method which performs the delegation. .PP So: when \f(CW\*(C`sref\*(C'\fR can't be found in IO::Handle, the \f(CW\*(C`AUTOLOAD\*(C'\fR method of \f(CW\*(C`IO::WrapTie::Master\*(C'\fR is invoked, and the standard behavior of delegating the method to the underlying slave (here, an IO::Scalar) is done. .PP Sometimes, to get this to work properly, you may need to create a subclass of \f(CW\*(C`IO::WrapTie::Master\*(C'\fR which is an effective master for \&\fIyour\fR class, and do the delegation there. .SH "NOTES" .IX Header "NOTES" \&\fBWhy not simply use the object's \s-1OO\s0 interface?\fR .PP Because that means forsaking the use of named operators like \f(CW\*(C`print\*(C'\fR, and you may need to pass the object to a subroutine which will attempt to use those operators: .PP .Vb 2 \& $O = FooHandle\->new(&FOO_RDWR, 2); \& $O\->print("Hello, world\en"); ### OO syntax is okay, BUT.... \& \& sub nope { print $_[0] "Nope!\en" } \& X nope($O); ### ERROR!!! (not a glob ref) .Ve .PP \&\fBWhy not simply use \fBtie()\fB?\fR Because (1) you have to use \f(CW\*(C`tied\*(C'\fR to invoke methods in the object's public interface (yuck), and (2) you may need to pass the tied symbol to another subroutine which will attempt to treat it in an OO-way... and that will break it: .PP .Vb 2 \& tie *T, \*(AqFooHandle\*(Aq, &FOO_RDWR, 2; \& print T "Hello, world\en"; ### Operator is okay, BUT... \& \& tied(*T)\->other_stuff; ### yuck! AND... \& \& sub nope { shift\->print("Nope!\en") } \& X nope(\e*T); ### ERROR!!! (method "print" on unblessed ref) .Ve .PP \&\fBWhy a master and slave?\fR .PP .Vb 6 \& Why not simply write C to inherit from L \&I tried this, with an implementation similar to that of L. \&The problem is that I. \&Subclassing L will work fine for the OO stuff, and fine with \&named operators I you C... but if you just attempt to say: \& \& $IO = FooHandle\->new(&FOO_RDWR, 2); \& print $IO "Hello!\en"; .Ve .PP you get a warning from Perl like: .PP .Vb 1 \& Filehandle GEN001 never opened .Ve .PP because it's trying to do system-level I/O on an (unopened) file descriptor. To avoid this, you apparently have to \f(CW\*(C`tie\*(C'\fR the handle... which brings us right back to where we started! At least the IO::WrapTie mixin lets us say: .PP .Vb 2 \& $IO = FooHandle\->new_tie(&FOO_RDWR, 2); \& print $IO "Hello!\en"; .Ve .PP and so is not \fItoo\fR bad. \f(CW\*(C`:\-)\*(C'\fR .SH "WARNINGS" .IX Header "WARNINGS" Remember: this stuff is for doing FileHandle\-like I/O on things \&\fIwithout underlying file descriptors\fR. If you have an underlying file descriptor, you're better off just inheriting from IO::Handle. .PP \&\fBBe aware that \fBnew_tie()\fB always returns an instance of a kind of IO::WrapTie::Master...\fR it does \fBnot\fR return an instance of the I/O class you're tying to! .PP Invoking some methods on the master object causes \f(CW\*(C`AUTOLOAD\*(C'\fR to delegate them to the slave object... so it \fIlooks\fR like you're manipulating a \&\f(CW\*(C`FooHandle\*(C'\fR object directly, but you're not. .PP I have not explored all the ramifications of this use of \f(CW\*(C`tie\*(C'\fR. \&\fIHere there be dragons\fR. .SH "AUTHOR" .IX Header "AUTHOR" Eryq (\fIeryq@zeegee.com\fR). President, ZeeGee Software Inc (\fIhttp://www.zeegee.com\fR). .SH "CONTRIBUTORS" .IX Header "CONTRIBUTORS" Dianne Skoll (\fIdfs@roaringpenguin.com\fR). .SH "COPYRIGHT & LICENSE" .IX Header "COPYRIGHT & LICENSE" Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. .PP This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. PK!k\p))man3/IO::Scalar.3pmnu[.\" Automatically generated by Pod::Man 4.11 (Pod::Simple 3.35) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is >0, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{\ . if \nF \{\ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{\ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" ======================================================================== .\" .IX Title "IO::Scalar 3" .TH IO::Scalar 3 "2020-01-17" "perl v5.26.3" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" IO::Scalar \- IO:: interface for reading/writing a scalar .SH "SYNOPSIS" .IX Header "SYNOPSIS" Perform I/O on strings, using the basic \s-1OO\s0 interface... .PP .Vb 3 \& use 5.005; \& use IO::Scalar; \& $data = "My message:\en"; \& \& ### Open a handle on a string, and append to it: \& $SH = new IO::Scalar \e$data; \& $SH\->print("Hello"); \& $SH\->print(", world!\enBye now!\en"); \& print "The string is now: ", $data, "\en"; \& \& ### Open a handle on a string, read it line\-by\-line, then close it: \& $SH = new IO::Scalar \e$data; \& while (defined($_ = $SH\->getline)) { \& print "Got line: $_"; \& } \& $SH\->close; \& \& ### Open a handle on a string, and slurp in all the lines: \& $SH = new IO::Scalar \e$data; \& print "All lines:\en", $SH\->getlines; \& \& ### Get the current position (either of two ways): \& $pos = $SH\->getpos; \& $offset = $SH\->tell; \& \& ### Set the current position (either of two ways): \& $SH\->setpos($pos); \& $SH\->seek($offset, 0); \& \& ### Open an anonymous temporary scalar: \& $SH = new IO::Scalar; \& $SH\->print("Hi there!"); \& print "I printed: ", ${$SH\->sref}, "\en"; ### get at value .Ve .PP Don't like \s-1OO\s0 for your I/O? No problem. Thanks to the magic of an invisible \fBtie()\fR, the following now works out of the box, just as it does with IO::Handle: .PP .Vb 3 \& use 5.005; \& use IO::Scalar; \& $data = "My message:\en"; \& \& ### Open a handle on a string, and append to it: \& $SH = new IO::Scalar \e$data; \& print $SH "Hello"; \& print $SH ", world!\enBye now!\en"; \& print "The string is now: ", $data, "\en"; \& \& ### Open a handle on a string, read it line\-by\-line, then close it: \& $SH = new IO::Scalar \e$data; \& while (<$SH>) { \& print "Got line: $_"; \& } \& close $SH; \& \& ### Open a handle on a string, and slurp in all the lines: \& $SH = new IO::Scalar \e$data; \& print "All lines:\en", <$SH>; \& \& ### Get the current position (WARNING: requires 5.6): \& $offset = tell $SH; \& \& ### Set the current position (WARNING: requires 5.6): \& seek $SH, $offset, 0; \& \& ### Open an anonymous temporary scalar: \& $SH = new IO::Scalar; \& print $SH "Hi there!"; \& print "I printed: ", ${$SH\->sref}, "\en"; ### get at value .Ve .PP And for you folks with 1.x code out there: the old \fBtie()\fR style still works, though this is \fIunnecessary and deprecated\fR: .PP .Vb 1 \& use IO::Scalar; \& \& ### Writing to a scalar... \& my $s; \& tie *OUT, \*(AqIO::Scalar\*(Aq, \e$s; \& print OUT "line 1\enline 2\en", "line 3\en"; \& print "String is now: $s\en" \& \& ### Reading and writing an anonymous scalar... \& tie *OUT, \*(AqIO::Scalar\*(Aq; \& print OUT "line 1\enline 2\en", "line 3\en"; \& tied(OUT)\->seek(0,0); \& while () { \& print "Got line: ", $_; \& } .Ve .PP Stringification works, too! .PP .Vb 4 \& my $SH = new IO::Scalar \e$data; \& print $SH "Hello, "; \& print $SH "world!"; \& print "I printed: $SH\en"; .Ve .SH "DESCRIPTION" .IX Header "DESCRIPTION" This class is part of the IO::Stringy distribution; see IO::Stringy for change log and general information. .PP The IO::Scalar class implements objects which behave just like IO::Handle (or FileHandle) objects, except that you may use them to write to (or read from) scalars. These handles are automatically \f(CW\*(C`tiehandle\*(C'\fRd (though please see \*(L"\s-1WARNINGS\*(R"\s0 for information relevant to your Perl version). .PP Basically, this: .PP .Vb 4 \& my $s; \& $SH = new IO::Scalar \e$s; \& $SH\->print("Hel", "lo, "); ### OO style \& $SH\->print("world!\en"); ### ditto .Ve .PP Or this: .PP .Vb 4 \& my $s; \& $SH = tie *OUT, \*(AqIO::Scalar\*(Aq, \e$s; \& print OUT "Hel", "lo, "; ### non\-OO style \& print OUT "world!\en"; ### ditto .Ve .PP Causes \f(CW$s\fR to be set to: .PP .Vb 1 \& "Hello, world!\en" .Ve .SH "PUBLIC INTERFACE" .IX Header "PUBLIC INTERFACE" .SS "Construction" .IX Subsection "Construction" .IP "new [\s-1ARGS...\s0]" 4 .IX Item "new [ARGS...]" \&\fIClass method.\fR Return a new, unattached scalar handle. If any arguments are given, they're sent to \fBopen()\fR. .IP "open [\s-1SCALARREF\s0]" 4 .IX Item "open [SCALARREF]" \&\fIInstance method.\fR Open the scalar handle on a new scalar, pointed to by \s-1SCALARREF.\s0 If no \s-1SCALARREF\s0 is given, a \*(L"private\*(R" scalar is created to hold the file data. .Sp Returns the self object on success, undefined on error. .IP "opened" 4 .IX Item "opened" \&\fIInstance method.\fR Is the scalar handle opened on something? .IP "close" 4 .IX Item "close" \&\fIInstance method.\fR Disassociate the scalar handle from its underlying scalar. Done automatically on destroy. .SS "Input and output" .IX Subsection "Input and output" .IP "flush" 4 .IX Item "flush" \&\fIInstance method.\fR No-op, provided for \s-1OO\s0 compatibility. .IP "fileno" 4 .IX Item "fileno" \&\fIInstance method.\fR No-op, returns undef .IP "getc" 4 .IX Item "getc" \&\fIInstance method.\fR Return the next character, or undef if none remain. .IP "getline" 4 .IX Item "getline" \&\fIInstance method.\fR Return the next line, or undef on end of string. Can safely be called in an array context. Currently, lines are delimited by \*(L"\en\*(R". .IP "getlines" 4 .IX Item "getlines" \&\fIInstance method.\fR Get all remaining lines. It will \fBcroak()\fR if accidentally called in a scalar context. .IP "print \s-1ARGS...\s0" 4 .IX Item "print ARGS..." \&\fIInstance method.\fR Print \s-1ARGS\s0 to the underlying scalar. .Sp \&\fBWarning:\fR this continues to always cause a seek to the end of the string, but if you perform \fBseek()\fRs and \fBtell()\fRs, it is still safer to explicitly seek-to-end before subsequent \fBprint()\fRs. .IP "read \s-1BUF, NBYTES,\s0 [\s-1OFFSET\s0]" 4 .IX Item "read BUF, NBYTES, [OFFSET]" \&\fIInstance method.\fR Read some bytes from the scalar. Returns the number of bytes actually read, 0 on end-of-file, undef on error. .IP "write \s-1BUF, NBYTES,\s0 [\s-1OFFSET\s0]" 4 .IX Item "write BUF, NBYTES, [OFFSET]" \&\fIInstance method.\fR Write some bytes to the scalar. .IP "sysread \s-1BUF, LEN,\s0 [\s-1OFFSET\s0]" 4 .IX Item "sysread BUF, LEN, [OFFSET]" \&\fIInstance method.\fR Read some bytes from the scalar. Returns the number of bytes actually read, 0 on end-of-file, undef on error. .IP "syswrite \s-1BUF, NBYTES,\s0 [\s-1OFFSET\s0]" 4 .IX Item "syswrite BUF, NBYTES, [OFFSET]" \&\fIInstance method.\fR Write some bytes to the scalar. .SS "Seeking/telling and other attributes" .IX Subsection "Seeking/telling and other attributes" .IP "autoflush" 4 .IX Item "autoflush" \&\fIInstance method.\fR No-op, provided for \s-1OO\s0 compatibility. .IP "binmode" 4 .IX Item "binmode" \&\fIInstance method.\fR No-op, provided for \s-1OO\s0 compatibility. .IP "clearerr" 4 .IX Item "clearerr" \&\fIInstance method.\fR Clear the error and \s-1EOF\s0 flags. A no-op. .IP "eof" 4 .IX Item "eof" \&\fIInstance method.\fR Are we at end of file? .IP "seek \s-1OFFSET, WHENCE\s0" 4 .IX Item "seek OFFSET, WHENCE" \&\fIInstance method.\fR Seek to a given position in the stream. .IP "sysseek \s-1OFFSET, WHENCE\s0" 4 .IX Item "sysseek OFFSET, WHENCE" \&\fIInstance method.\fR Identical to \f(CW\*(C`seek OFFSET, WHENCE\*(C'\fR, \fIq.v.\fR .IP "tell" 4 .IX Item "tell" \&\fIInstance method.\fR Return the current position in the stream, as a numeric offset. .IP "setpos \s-1POS\s0" 4 .IX Item "setpos POS" \&\fIInstance method.\fR Set the current position, using the opaque value returned by \f(CW\*(C`getpos()\*(C'\fR. .IP "getpos" 4 .IX Item "getpos" \&\fIInstance method.\fR Return the current position in the string, as an opaque object. .IP "sref" 4 .IX Item "sref" \&\fIInstance method.\fR Return a reference to the underlying scalar. .SH "AUTHOR" .IX Header "AUTHOR" Eryq (\fIeryq@zeegee.com\fR). President, ZeeGee Software Inc (\fIhttp://www.zeegee.com\fR). .SH "CONTRIBUTORS" .IX Header "CONTRIBUTORS" Dianne Skoll (\fIdfs@roaringpenguin.com\fR). .SH "COPYRIGHT & LICENSE" .IX Header "COPYRIGHT & LICENSE" Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. .PP This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. PK!q))man3/IO::Wrap.3pmnu[.\" Automatically generated by Pod::Man 4.11 (Pod::Simple 3.35) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is >0, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{\ . if \nF \{\ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{\ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" ======================================================================== .\" .IX Title "IO::Wrap 3" .TH IO::Wrap 3 "2020-01-17" "perl v5.26.3" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" IO::Wrap \- Wrap raw filehandles in the IO::Handle interface .SH "SYNOPSIS" .IX Header "SYNOPSIS" .Vb 3 \& use strict; \& use warnings; \& use IO::Wrap; \& \& # this is a fairly senseless use case as IO::Handle already does this. \& my $wrap_fh = IO::Wrap\->new(\e*STDIN); \& my $line = $wrap_fh\->getline(); \& \& # Do stuff with any kind of filehandle (including a bare globref), or \& # any kind of blessed object that responds to a print() message. \& \& # already have a globref? a FileHandle? a scalar filehandle name? \& $wrap_fh = IO::Wrap\->new($some_unknown_thing); \& \& # At this point, we know we have an IO::Handle\-like object! YAY \& $wrap_fh\->print("Hey there!"); .Ve .PP You can also do this using a convenience wrapper function .PP .Vb 3 \& use strict; \& use warnings; \& use IO::Wrap qw(wraphandle); \& \& # this is a fairly senseless use case as IO::Handle already does this. \& my $wrap_fh = wraphandle(\e*STDIN); \& my $line = $wrap_fh\->getline(); \& \& # Do stuff with any kind of filehandle (including a bare globref), or \& # any kind of blessed object that responds to a print() message. \& \& # already have a globref? a FileHandle? a scalar filehandle name? \& $wrap_fh = wraphandle($some_unknown_thing); \& \& # At this point, we know we have an IO::Handle\-like object! YAY \& $wrap_fh\->print("Hey there!"); .Ve .SH "DESCRIPTION" .IX Header "DESCRIPTION" Let's say you want to write some code which does I/O, but you don't want to force the caller to provide you with a FileHandle or IO::Handle object. You want them to be able to say: .PP .Vb 4 \& do_stuff(\e*STDOUT); \& do_stuff(\*(AqSTDERR\*(Aq); \& do_stuff($some_FileHandle_object); \& do_stuff($some_IO_Handle_object); .Ve .PP And even: .PP .Vb 1 \& do_stuff($any_object_with_a_print_method); .Ve .PP Sure, one way to do it is to force the caller to use \f(CW\*(C`tiehandle()\*(C'\fR. But that puts the burden on them. Another way to do it is to use \fBIO::Wrap\fR. .PP Clearly, when wrapping a raw external filehandle (like \f(CW\*(C`\e*STDOUT\*(C'\fR), I didn't want to close the file descriptor when the wrapper object is destroyed; the user might not appreciate that! Hence, there's no \&\f(CW\*(C`DESTROY\*(C'\fR method in this class. .PP When wrapping a FileHandle object, however, I believe that Perl will invoke the \f(CW\*(C`FileHandle::DESTROY\*(C'\fR when the last reference goes away, so in that case, the filehandle is closed if the wrapped FileHandle really was the last reference to it. .SH "FUNCTIONS" .IX Header "FUNCTIONS" IO::Wrap makes the following functions available. .SS "wraphandle" .IX Subsection "wraphandle" .Vb 6 \& # wrap a filehandle glob \& my $fh = wraphandle(\e*STDIN); \& # wrap a raw filehandle glob by name \& $fh = wraphandle(\*(AqSTDIN\*(Aq); \& # wrap a handle in an object \& $fh = wraphandle(\*(AqClass::HANDLE\*(Aq); \& \& # wrap a blessed FileHandle object \& use FileHandle; \& my $fho = FileHandle\->new("/tmp/foo.txt", "r"); \& $fh = wraphandle($fho); \& \& # wrap any other blessed object that shares IO::Handle\*(Aqs interface \& $fh = wraphandle($some_object); .Ve .PP This function is simply a wrapper to the \*(L"new\*(R" in IO::Wrap constructor method. .SH "METHODS" .IX Header "METHODS" IO::Wrap implements the following methods. .SS "close" .IX Subsection "close" .Vb 1 \& $fh\->close(); .Ve .PP The \f(CW\*(C`close\*(C'\fR method will attempt to close the system file descriptor. For a more complete description, read \*(L"close\*(R" in perlfunc. .SS "fileno" .IX Subsection "fileno" .Vb 1 \& my $int = $fh\->fileno(); .Ve .PP The \f(CW\*(C`fileno\*(C'\fR method returns the file descriptor for the wrapped filehandle. See \*(L"fileno\*(R" in perlfunc for more information. .SS "getline" .IX Subsection "getline" .Vb 1 \& my $data = $fh\->getline(); .Ve .PP The \f(CW\*(C`getline\*(C'\fR method mimics the function by the same name in IO::Handle. It's like calling \f(CW\*(C`my $data = <$fh>;\*(C'\fR but only in scalar context. .SS "getlines" .IX Subsection "getlines" .Vb 1 \& my @data = $fh\->getlines(); .Ve .PP The \f(CW\*(C`getlines\*(C'\fR method mimics the function by the same name in IO::Handle. It's like calling \f(CW\*(C`my @data = <$fh>;\*(C'\fR but only in list context. Calling this method in scalar context will result in a croak. .SS "new" .IX Subsection "new" .Vb 6 \& # wrap a filehandle glob \& my $fh = IO::Wrap\->new(\e*STDIN); \& # wrap a raw filehandle glob by name \& $fh = IO::Wrap\->new(\*(AqSTDIN\*(Aq); \& # wrap a handle in an object \& $fh = IO::Wrap\->new(\*(AqClass::HANDLE\*(Aq); \& \& # wrap a blessed FileHandle object \& use FileHandle; \& my $fho = FileHandle\->new("/tmp/foo.txt", "r"); \& $fh = IO::Wrap\->new($fho); \& \& # wrap any other blessed object that shares IO::Handle\*(Aqs interface \& $fh = IO::Wrap\->new($some_object); .Ve .PP The \f(CW\*(C`new\*(C'\fR constructor method takes in a single argument and decides to wrap it or not it based on what it seems to be. .PP A raw scalar file handle name, like \f(CW"STDOUT"\fR or \f(CW"Class::HANDLE"\fR can be wrapped, returning an IO::Wrap object instance. .PP A raw filehandle glob, like \f(CW\*(C`\e*STDOUT\*(C'\fR can also be wrapped, returning an IO::Wrawp object instance. .PP A blessed FileHandle object can also be wrapped. This is a special case where an IO::Wrap object instance will only be returned in the case that your FileHandle object doesn't support the \f(CW\*(C`read\*(C'\fR method. .PP Also, any other kind of blessed object that conforms to the IO::Handle interface can be passed in. In this case, you just get back that object. .PP In other words, we only wrap it into an IO::Wrap object when what you've supplied doesn't already conform to the IO::Handle interface. .PP If you get back an IO::Wrap object, it will obey a basic subset of the \f(CW\*(C`IO::\*(C'\fR interface. It will do so with object \fBmethods\fR, not \fBoperators\fR. .PP \fI\s-1CAVEATS\s0\fR .IX Subsection "CAVEATS" .PP This module does not allow you to wrap filehandle names which are given as strings that lack the package they were opened in. That is, if a user opens \s-1FOO\s0 in package Foo, they must pass it to you either as \f(CW\*(C`\e*FOO\*(C'\fR or as \f(CW"Foo::FOO"\fR. However, \f(CW"STDIN"\fR and friends will work just fine. .SS "print" .IX Subsection "print" .Vb 2 \& $fh\->print("Some string"); \& $fh\->print("more", " than one", " string"); .Ve .PP The \f(CW\*(C`print\*(C'\fR method will attempt to print a string or list of strings to the filehandle. For a more complete description, read \&\*(L"print\*(R" in perlfunc. .SS "read" .IX Subsection "read" .Vb 4 \& my $buffer; \& # try to read 30 chars into the buffer starting at the \& # current cursor position. \& my $num_chars_read = $fh\->read($buffer, 30); .Ve .PP The read method attempts to read a number of characters, starting at the filehandle's current cursor position. It returns the number of characters actually read. See \*(L"read\*(R" in perlfunc for more information. .SS "seek" .IX Subsection "seek" .Vb 7 \& use Fcntl qw(:seek); # import the SEEK_CUR, SEEK_SET, SEEK_END constants \& # seek to the position in bytes \& $fh\->seek(0, SEEK_SET); \& # seek to the position in bytes from the current position \& $fh\->seek(22, SEEK_CUR); \& # seek to the EOF plus bytes \& $fh\->seek(0, SEEK_END); .Ve .PP The \f(CW\*(C`seek\*(C'\fR method will attempt to set the cursor to a given position in bytes for the wrapped file handle. See \*(L"seek\*(R" in perlfunc for more information. .SS "tell" .IX Subsection "tell" .Vb 1 \& my $bytes = $fh\->tell(); .Ve .PP The \f(CW\*(C`tell\*(C'\fR method will attempt to return the current position of the cursor in bytes for the wrapped file handle. See \*(L"tell\*(R" in perlfunc for more information. .SH "AUTHOR" .IX Header "AUTHOR" Eryq (\fIeryq@zeegee.com\fR). President, ZeeGee Software Inc (\fIhttp://www.zeegee.com\fR). .SH "CONTRIBUTORS" .IX Header "CONTRIBUTORS" Dianne Skoll (\fIdfs@roaringpenguin.com\fR). .SH "COPYRIGHT & LICENSE" .IX Header "COPYRIGHT & LICENSE" Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. .PP This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. PK!Eman3/IO::InnerFile.3pmnu[.\" Automatically generated by Pod::Man 4.11 (Pod::Simple 3.35) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is >0, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{\ . if \nF \{\ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{\ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" ======================================================================== .\" .IX Title "IO::InnerFile 3" .TH IO::InnerFile 3 "2020-01-17" "perl v5.26.3" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" IO::InnerFile \- define a file inside another file .SH "SYNOPSIS" .IX Header "SYNOPSIS" .Vb 3 \& use strict; \& use warnings; \& use IO::InnerFile; \& \& # Read a subset of a file: \& my $fh = _some_file_handle; \& my $start = 10; \& my $length = 50; \& my $inner = IO::InnerFile\->new($fh, $start, $length); \& while (my $line = <$inner>) { \& # ... \& } .Ve .SH "DESCRIPTION" .IX Header "DESCRIPTION" If you have a file handle that can \f(CW\*(C`seek\*(C'\fR and \f(CW\*(C`tell\*(C'\fR, then you can open an IO::InnerFile on a range of the underlying file. .SH "CONSTRUCTORS" .IX Header "CONSTRUCTORS" IO::InnerFile implements the following constructors. .SS "new" .IX Subsection "new" .Vb 3 \& my $inner = IO::InnerFile\->new($fh); \& $inner = IO::InnerFile\->new($fh, 10); \& $inner = IO::InnerFile\->new($fh, 10, 50); .Ve .PP Create a new IO::InnerFile opened on the given file handle. The file handle supplied \fB\s-1MUST\s0\fR be able to both \f(CW\*(C`seek\*(C'\fR and \f(CW\*(C`tell\*(C'\fR. .PP The second and third parameters are start and length. Both are defaulted to zero (\f(CW0\fR). Negative values are silently coerced to zero. .SH "METHODS" .IX Header "METHODS" IO::InnerFile implements the following methods. .SS "add_length" .IX Subsection "add_length" .Vb 1 \& $inner\->add_length(30); .Ve .PP Add to the virtual length of the inner file by the number given in bytes. .SS "add_start" .IX Subsection "add_start" .Vb 1 \& $inner\->add_start(30); .Ve .PP Add to the virtual position of the inner file by the number given in bytes. .SS "binmode" .IX Subsection "binmode" .Vb 1 \& $inner\->binmode(); .Ve .PP This is a \s-1NOOP\s0 method just to satisfy the normal IO::File interface. .SS "close" .IX Subsection "close" .SS "fileno" .IX Subsection "fileno" .Vb 1 \& $inner\->fileno(); .Ve .PP This is a \s-1NOOP\s0 method just to satisfy the normal IO::File interface. .SS "flush" .IX Subsection "flush" .Vb 1 \& $inner\->flush(); .Ve .PP This is a \s-1NOOP\s0 method just to satisfy the normal IO::File interface. .SS "get_end" .IX Subsection "get_end" .Vb 1 \& my $num_bytes = $inner\->get_end(); .Ve .PP Get the virtual end position of the inner file in bytes. .SS "get_length" .IX Subsection "get_length" .Vb 1 \& my $num_bytes = $inner\->get_length(); .Ve .PP Get the virtual length of the inner file in bytes. .SS "get_start" .IX Subsection "get_start" .Vb 1 \& my $num_bytes = $inner\->get_start(); .Ve .PP Get the virtual position of the inner file in bytes. .SS "getc" .IX Subsection "getc" .SS "getline" .IX Subsection "getline" .SS "print \s-1LIST\s0" .IX Subsection "print LIST" .SS "printf" .IX Subsection "printf" .SS "read" .IX Subsection "read" .SS "readline" .IX Subsection "readline" .SS "seek" .IX Subsection "seek" .SS "set_end" .IX Subsection "set_end" .Vb 1 \& $inner\->set_end(30); .Ve .PP Set the virtual end of the inner file in bytes (this basically just alters the length). .SS "set_length" .IX Subsection "set_length" .Vb 1 \& $inner\->set_length(30); .Ve .PP Set the virtual length of the inner file in bytes. .SS "set_start" .IX Subsection "set_start" .Vb 1 \& $inner\->set_start(30); .Ve .PP Set the virtual start position of the inner file in bytes. .SS "tell" .IX Subsection "tell" .SS "write" .IX Subsection "write" .SH "AUTHOR" .IX Header "AUTHOR" Eryq (\fIeryq@zeegee.com\fR). President, ZeeGee Software Inc (\fIhttp://www.zeegee.com\fR). .SH "CONTRIBUTORS" .IX Header "CONTRIBUTORS" Dianne Skoll (\fIdfs@roaringpenguin.com\fR). .SH "COPYRIGHT & LICENSE" .IX Header "COPYRIGHT & LICENSE" Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. .PP This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. PK!%))man3/IO::ScalarArray.3pmnu[.\" Automatically generated by Pod::Man 4.11 (Pod::Simple 3.35) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is >0, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{\ . if \nF \{\ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{\ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" ======================================================================== .\" .IX Title "IO::ScalarArray 3" .TH IO::ScalarArray 3 "2020-01-17" "perl v5.26.3" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" IO::ScalarArray \- IO:: interface for reading/writing an array of scalars .SH "SYNOPSIS" .IX Header "SYNOPSIS" Perform I/O on strings, using the basic \s-1OO\s0 interface... .PP .Vb 2 \& use IO::ScalarArray; \& @data = ("My mes", "sage:\en"); \& \& ### Open a handle on an array, and append to it: \& $AH = new IO::ScalarArray \e@data; \& $AH\->print("Hello"); \& $AH\->print(", world!\enBye now!\en"); \& print "The array is now: ", @data, "\en"; \& \& ### Open a handle on an array, read it line\-by\-line, then close it: \& $AH = new IO::ScalarArray \e@data; \& while (defined($_ = $AH\->getline)) { \& print "Got line: $_"; \& } \& $AH\->close; \& \& ### Open a handle on an array, and slurp in all the lines: \& $AH = new IO::ScalarArray \e@data; \& print "All lines:\en", $AH\->getlines; \& \& ### Get the current position (either of two ways): \& $pos = $AH\->getpos; \& $offset = $AH\->tell; \& \& ### Set the current position (either of two ways): \& $AH\->setpos($pos); \& $AH\->seek($offset, 0); \& \& ### Open an anonymous temporary array: \& $AH = new IO::ScalarArray; \& $AH\->print("Hi there!"); \& print "I printed: ", @{$AH\->aref}, "\en"; ### get at value .Ve .PP Don't like \s-1OO\s0 for your I/O? No problem. Thanks to the magic of an invisible \fBtie()\fR, the following now works out of the box, just as it does with IO::Handle: .PP .Vb 2 \& use IO::ScalarArray; \& @data = ("My mes", "sage:\en"); \& \& ### Open a handle on an array, and append to it: \& $AH = new IO::ScalarArray \e@data; \& print $AH "Hello"; \& print $AH ", world!\enBye now!\en"; \& print "The array is now: ", @data, "\en"; \& \& ### Open a handle on a string, read it line\-by\-line, then close it: \& $AH = new IO::ScalarArray \e@data; \& while (<$AH>) { \& print "Got line: $_"; \& } \& close $AH; \& \& ### Open a handle on a string, and slurp in all the lines: \& $AH = new IO::ScalarArray \e@data; \& print "All lines:\en", <$AH>; \& \& ### Get the current position (WARNING: requires 5.6): \& $offset = tell $AH; \& \& ### Set the current position (WARNING: requires 5.6): \& seek $AH, $offset, 0; \& \& ### Open an anonymous temporary scalar: \& $AH = new IO::ScalarArray; \& print $AH "Hi there!"; \& print "I printed: ", @{$AH\->aref}, "\en"; ### get at value .Ve .PP And for you folks with 1.x code out there: the old \fBtie()\fR style still works, though this is \fIunnecessary and deprecated\fR: .PP .Vb 1 \& use IO::ScalarArray; \& \& ### Writing to a scalar... \& my @a; \& tie *OUT, \*(AqIO::ScalarArray\*(Aq, \e@a; \& print OUT "line 1\enline 2\en", "line 3\en"; \& print "Array is now: ", @a, "\en" \& \& ### Reading and writing an anonymous scalar... \& tie *OUT, \*(AqIO::ScalarArray\*(Aq; \& print OUT "line 1\enline 2\en", "line 3\en"; \& tied(OUT)\->seek(0,0); \& while () { \& print "Got line: ", $_; \& } .Ve .SH "DESCRIPTION" .IX Header "DESCRIPTION" This class is part of the IO::Stringy distribution; see IO::Stringy for change log and general information. .PP The IO::ScalarArray class implements objects which behave just like IO::Handle (or FileHandle) objects, except that you may use them to write to (or read from) arrays of scalars. Logically, an array of scalars defines an in-core \*(L"file\*(R" whose contents are the concatenation of the scalars in the array. The handles created by this class are automatically \f(CW\*(C`tiehandle\*(C'\fRd (though please see \*(L"\s-1WARNINGS\*(R"\s0 for information relevant to your Perl version). .PP For writing large amounts of data with individual \fBprint()\fR statements, this class is likely to be more efficient than IO::Scalar. .PP Basically, this: .PP .Vb 4 \& my @a; \& $AH = new IO::ScalarArray \e@a; \& $AH\->print("Hel", "lo, "); ### OO style \& $AH\->print("world!\en"); ### ditto .Ve .PP Or this: .PP .Vb 4 \& my @a; \& $AH = new IO::ScalarArray \e@a; \& print $AH "Hel", "lo, "; ### non\-OO style \& print $AH "world!\en"; ### ditto .Ve .PP Causes \f(CW@a\fR to be set to the following array of 3 strings: .PP .Vb 3 \& ( "Hel" , \& "lo, " , \& "world!\en" ) .Ve .PP See IO::Scalar and compare with this class. .SH "PUBLIC INTERFACE" .IX Header "PUBLIC INTERFACE" .SS "Construction" .IX Subsection "Construction" .IP "new [\s-1ARGS...\s0]" 4 .IX Item "new [ARGS...]" \&\fIClass method.\fR Return a new, unattached array handle. If any arguments are given, they're sent to \fBopen()\fR. .IP "open [\s-1ARRAYREF\s0]" 4 .IX Item "open [ARRAYREF]" \&\fIInstance method.\fR Open the array handle on a new array, pointed to by \s-1ARRAYREF.\s0 If no \s-1ARRAYREF\s0 is given, a \*(L"private\*(R" array is created to hold the file data. .Sp Returns the self object on success, undefined on error. .IP "opened" 4 .IX Item "opened" \&\fIInstance method.\fR Is the array handle opened on something? .IP "close" 4 .IX Item "close" \&\fIInstance method.\fR Disassociate the array handle from its underlying array. Done automatically on destroy. .SS "Input and output" .IX Subsection "Input and output" .IP "flush" 4 .IX Item "flush" \&\fIInstance method.\fR No-op, provided for \s-1OO\s0 compatibility. .IP "fileno" 4 .IX Item "fileno" \&\fIInstance method.\fR No-op, returns undef .IP "getc" 4 .IX Item "getc" \&\fIInstance method.\fR Return the next character, or undef if none remain. This does a \fBread\fR\|(1), which is somewhat costly. .IP "getline" 4 .IX Item "getline" \&\fIInstance method.\fR Return the next line, or undef on end of data. Can safely be called in an array context. Currently, lines are delimited by \*(L"\en\*(R". .IP "getlines" 4 .IX Item "getlines" \&\fIInstance method.\fR Get all remaining lines. It will \fBcroak()\fR if accidentally called in a scalar context. .IP "print \s-1ARGS...\s0" 4 .IX Item "print ARGS..." \&\fIInstance method.\fR Print \s-1ARGS\s0 to the underlying array. .Sp Currently, this always causes a \*(L"seek to the end of the array\*(R" and generates a new array entry. This may change in the future. .IP "read \s-1BUF, NBYTES,\s0 [\s-1OFFSET\s0];" 4 .IX Item "read BUF, NBYTES, [OFFSET];" \&\fIInstance method.\fR Read some bytes from the array. Returns the number of bytes actually read, 0 on end-of-file, undef on error. .IP "write \s-1BUF, NBYTES,\s0 [\s-1OFFSET\s0];" 4 .IX Item "write BUF, NBYTES, [OFFSET];" \&\fIInstance method.\fR Write some bytes into the array. .SS "Seeking/telling and other attributes" .IX Subsection "Seeking/telling and other attributes" .IP "autoflush" 4 .IX Item "autoflush" \&\fIInstance method.\fR No-op, provided for \s-1OO\s0 compatibility. .IP "binmode" 4 .IX Item "binmode" \&\fIInstance method.\fR No-op, provided for \s-1OO\s0 compatibility. .IP "clearerr" 4 .IX Item "clearerr" \&\fIInstance method.\fR Clear the error and \s-1EOF\s0 flags. A no-op. .IP "eof" 4 .IX Item "eof" \&\fIInstance method.\fR Are we at end of file? .IP "seek \s-1POS,WHENCE\s0" 4 .IX Item "seek POS,WHENCE" \&\fIInstance method.\fR Seek to a given position in the stream. Only a \s-1WHENCE\s0 of 0 (\s-1SEEK_SET\s0) is supported. .IP "tell" 4 .IX Item "tell" \&\fIInstance method.\fR Return the current position in the stream, as a numeric offset. .IP "setpos \s-1POS\s0" 4 .IX Item "setpos POS" \&\fIInstance method.\fR Seek to a given position in the array, using the opaque \fBgetpos()\fR value. Don't expect this to be a number. .IP "getpos" 4 .IX Item "getpos" \&\fIInstance method.\fR Return the current position in the array, as an opaque value. Don't expect this to be a number. .IP "aref" 4 .IX Item "aref" \&\fIInstance method.\fR Return a reference to the underlying array. .SH "AUTHOR" .IX Header "AUTHOR" Eryq (\fIeryq@zeegee.com\fR). President, ZeeGee Software Inc (\fIhttp://www.zeegee.com\fR). .SH "CONTRIBUTORS" .IX Header "CONTRIBUTORS" Dianne Skoll (\fIdfs@roaringpenguin.com\fR). .SH "COPYRIGHT & LICENSE" .IX Header "COPYRIGHT & LICENSE" Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. .PP This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. PK!man3/IO::AtomicFile.3pmnu[.\" Automatically generated by Pod::Man 4.11 (Pod::Simple 3.35) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is >0, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{\ . if \nF \{\ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{\ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" ======================================================================== .\" .IX Title "IO::AtomicFile 3" .TH IO::AtomicFile 3 "2020-01-17" "perl v5.26.3" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" IO::AtomicFile \- write a file which is updated atomically .SH "SYNOPSIS" .IX Header "SYNOPSIS" .Vb 4 \& use strict; \& use warnings; \& use feature \*(Aqsay\*(Aq; \& use IO::AtomicFile; \& \& # Write a temp file, and have it install itself when closed: \& my $fh = IO::AtomicFile\->open("bar.dat", "w"); \& $fh\->say("Hello!"); \& $fh\->close || die "couldn\*(Aqt install atomic file: $!"; \& \& # Write a temp file, but delete it before it gets installed: \& my $fh = IO::AtomicFile\->open("bar.dat", "w"); \& $fh\->say("Hello!"); \& $fh\->delete; \& \& # Write a temp file, but neither install it nor delete it: \& my $fh = IO::AtomicFile\->open("bar.dat", "w"); \& $fh\->say("Hello!"); \& $fh\->detach; .Ve .SH "DESCRIPTION" .IX Header "DESCRIPTION" This module is intended for people who need to update files reliably in the face of unexpected program termination. .PP For example, you generally don't want to be halfway in the middle of writing \fI/etc/passwd\fR and have your program terminate! Even the act of writing a single scalar to a filehandle is \fInot\fR atomic. .PP But this module gives you true atomic updates, via \f(CW\*(C`rename\*(C'\fR. When you open a file \fI/foo/bar.dat\fR via this module, you are \fIactually\fR opening a temporary file \fI/foo/bar.dat..TMP\fR, and writing your output there. The act of closing this file (either explicitly via \f(CW\*(C`close\*(C'\fR, or implicitly via the destruction of the object) will cause \f(CW\*(C`rename\*(C'\fR to be called... therefore, from the point of view of the outside world, the file's contents are updated in a single time quantum. .PP To ensure that problems do not go undetected, the \f(CW\*(C`close\*(C'\fR method done by the destructor will raise a fatal exception if the \f(CW\*(C`rename\*(C'\fR fails. The explicit \f(CW\*(C`close\*(C'\fR just returns \f(CW\*(C`undef\*(C'\fR. .PP You can also decide at any point to trash the file you've been building. .SH "METHODS" .IX Header "METHODS" IO::AtomicFile inherits all methods from IO::File and implements the following new ones. .SS "close" .IX Subsection "close" .Vb 1 \& $fh\->close(); .Ve .PP This method calls its parent \*(L"close\*(R" in IO::File and then renames its temporary file as the original file name. .SS "delete" .IX Subsection "delete" .Vb 1 \& $fh\->delete(); .Ve .PP This method calls its parent \*(L"close\*(R" in IO::File and then deletes the temporary file. .SS "detach" .IX Subsection "detach" .Vb 1 \& $fh\->detach(); .Ve .PP This method calls its parent \*(L"close\*(R" in IO::File. Unlike \*(L"delete\*(R" in IO::AtomicFile it does not then delete the temporary file. .SH "AUTHOR" .IX Header "AUTHOR" Eryq (\fIeryq@zeegee.com\fR). President, ZeeGee Software Inc (\fIhttp://www.zeegee.com\fR). .SH "CONTRIBUTORS" .IX Header "CONTRIBUTORS" Dianne Skoll (\fIdfs@roaringpenguin.com\fR). .SH "COPYRIGHT & LICENSE" .IX Header "COPYRIGHT & LICENSE" Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. .PP This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. PK! Zman3/IO::Stringy.3pmnu[.\" Automatically generated by Pod::Man 4.11 (Pod::Simple 3.35) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is >0, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{\ . if \nF \{\ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{\ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" ======================================================================== .\" .IX Title "IO::Stringy 3" .TH IO::Stringy 3 "2020-01-17" "perl v5.26.3" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" IO\-stringy \- I/O on in\-core objects like strings and arrays .SH "SYNOPSIS" .IX Header "SYNOPSIS" .Vb 2 \& use strict; \& use warnings; \& \& use IO::AtomicFile; # Write a file which is updated atomically \& use IO::InnerFile; # define a file inside another file \& use IO::Lines; # I/O handle to read/write to array of lines \& use IO::Scalar; # I/O handle to read/write to a string \& use IO::ScalarArray; # I/O handle to read/write to array of scalars \& use IO::Wrap; # Wrap old\-style FHs in standard OO interface \& use IO::WrapTie; # Tie your handles & retain full OO interface \& \& # ... .Ve .SH "DESCRIPTION" .IX Header "DESCRIPTION" This toolkit primarily provides modules for performing both traditional and object-oriented i/o) on things \fIother\fR than normal filehandles; in particular, IO::Scalar, IO::ScalarArray, and IO::Lines. .PP In the more-traditional IO::Handle front, we have IO::AtomicFile which may be used to painlessly create files which are updated atomically. .PP And in the \*(L"this-may-prove-useful\*(R" corner, we have IO::Wrap, whose exported \fBwraphandle()\fR function will clothe anything that's not a blessed object in an IO::Handle\-like wrapper... so you can just use \s-1OO\s0 syntax and stop worrying about whether your function's caller handed you a string, a globref, or a FileHandle. .SH "AUTHOR" .IX Header "AUTHOR" Eryq (\fIeryq@zeegee.com\fR). President, ZeeGee Software Inc (\fIhttp://www.zeegee.com\fR). .SH "CONTRIBUTORS" .IX Header "CONTRIBUTORS" Dianne Skoll (\fIdfs@roaringpenguin.com\fR). .SH "COPYRIGHT & LICENSE" .IX Header "COPYRIGHT & LICENSE" Copyright (c) 1997 Erik (Eryq) Dorfman, ZeeGee Software, Inc. All rights reserved. .PP This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself. PK! arch/.existsnu[PK!'<arch/auto/Test/RequiresInternet/.existsnu[PK!lib/Test/.existsnu[PK!`$y y lib/Test/RequiresInternet.pmnu6$PK!& lib/auto/Test/RequiresInternet/.existsnu[PK! script/.existsnu[PK!dd, man3/Test::RequiresInternet.3pmnu[PK! man3/.existsnu[PK! bin/.existsnu[PK! Vman1/.existsnu[PK!arch/auto/Text/Template/.existsnu[PK!lib/Text/.existsnu[PK!O!lib/Text/Template/Preprocess.pmnu6$PK!47  /lib/Text/Template.pmnu6$PK!8lib/auto/Text/Template/.existsnu[PK!5zz#59man3/Text::Template::Preprocess.3pmnu[PK!]pRman3/Text::Template.3pmnu[PK!Rarch/auto/IO/Stringy/.existsnu[PK!kRlib/IO/.existsnu[PK!l]?@?@Rlib/IO/ScalarArray.pmnu6$PK!GJJ-lib/IO/Lines.pmnu6$PK!rlib/IO/AtomicFile.pmnu6$PK!h lib/IO/Stringy.pmnu6$PK!*2U"U"Rlib/IO/Wrap.pmnu6$PK!^::lib/IO/Scalar.pmnu6$PK![|9|9lib/IO/WrapTie.pmnu6$PK!Wlib/IO/InnerFile.pmnu6$PK!Zslib/auto/IO/Stringy/.existsnu[PK!xsman3/IO::Lines.3pmnu[PK!S::man3/IO::WrapTie.3pmnu[PK!k\p))qman3/IO::Scalar.3pmnu[PK!q))gman3/IO::Wrap.3pmnu[PK!ELman3/IO::InnerFile.3pmnu[PK!%))!)man3/IO::ScalarArray.3pmnu[PK!Rman3/IO::AtomicFile.3pmnu[PK! Zgman3/IO::Stringy.3pmnu[PK$$ w