File-Slurp-9999.32/0000755000175000017500000000000013676754374014474 5ustar cwhitenercwhitenerFile-Slurp-9999.32/MANIFEST.SKIP0000644000175000017500000000017313676215364016362 0ustar cwhitenercwhitener^\.git ^blib/ ^experiment/ ^slurp_talk/ TODO Makefile$ \.bak$ ^extras/ pm_to_blib \.lock$ ^cover_db/ ^File-Slurp ^MYMETA\. File-Slurp-9999.32/t/0000755000175000017500000000000013676754373014736 5ustar cwhitenercwhitenerFile-Slurp-9999.32/t/01-error_read_dir.t0000644000175000017500000000507513355535337020321 0ustar cwhitenercwhiteneruse strict; use warnings; use File::Basename (); use File::Spec (); use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib'); use FileSlurpTest qw(temp_file_path trap_function); use File::Slurp qw(read_dir); use Test::More; plan tests => 18; # possible failure points: # 1. Can't open dir due to bad path/permissions/whatever # - easily simulated by asking the read_dir function to open a dir that # doesn't exist, and is nested far enough in a path that it can't be # created. /tmp exists, but opening /tmp/fake/path/whatever/dir will fail # 2. Can't open dir because it's a file # - create a file, try to read_dir on it. # each of the above cases should be tested in all three failure modes: # 1. quiet (no warnings, exceptions, or content) # 2. carp (warnings, no exceptions, no content) # 3. croak (an exception, no warnings, no content) # read_dir on bad path { my $file = temp_file_path('gimme a nonexistent path'); my ($res, $warn, $err) = trap_function(\&read_dir, $file, err_mode => 'quiet'); ok(!$warn, 'read_dir: bad path, quiet - no warn!'); ok(!$err, 'read_dir: bad path, quiet - no exception!'); ok(!$res, 'read_dir: bad path, quiet - no content!'); ($res, $warn, $err) = trap_function(\&read_dir, $file, err_mode => 'carp'); ok($warn, 'read_dir: bad path, carp - got warn!'); ok(!$err, 'read_dir: bad path, carp - no exception!'); ok(!$res, 'read_dir: bad path, carp - no content!'); ($res, $warn, $err) = trap_function(\&read_dir, $file, err_mode => 'croak'); ok(!$warn, 'read_dir: bad path, croak - no warn!'); ok($err, 'read_dir: bad path, croak - got exception!'); ok(!$res, 'read_dir: bad path, croak - no content!'); } # read_dir on file { my $file = temp_file_path(); File::Slurp::write_file($file, 'junk'); my ($res, $warn, $err) = trap_function(\&read_dir, $file, err_mode => 'quiet'); ok(!$warn, 'read_dir: not dir, quiet - no warn!'); ok(!$err, 'read_dir: not dir, quiet - no exception!'); ok(!$res, 'read_dir: not dir, quiet - no content!'); ($res, $warn, $err) = trap_function(\&read_dir, $file, err_mode => 'carp'); ok($warn, 'read_dir: not dir, carp - got warn!'); ok(!$err, 'read_dir: not dir, carp - no exception!'); ok(!$res, 'read_dir: not dir, carp - no content!'); ($res, $warn, $err) = trap_function(\&read_dir, $file, err_mode => 'croak'); ok(!$warn, 'read_dir: not dir, croak - no warn!'); ok($err, 'read_dir: not dir, croak - got exception!'); ok(!$res, 'read_dir: not dir, croak - no content!'); unlink $file; } File-Slurp-9999.32/t/01-error_write_file.t0000644000175000017500000003102613440747315020670 0ustar cwhitenercwhiteneruse strict; use warnings; use File::Basename (); use File::Spec (); use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib'); use FileSlurpTestOverride qw(trap_function_override_core); use FileSlurpTest qw(temp_file_path trap_function); # all of these names are synonyms use File::Slurp qw(wf write_file overwrite_file append_file); use Test::More; plan tests => 108; # possible failure points: # 1. Can't open file due to bad path/permissions/whatever # 2. Can't write to file due to bad permissions/whatever # also, if in atomic write mode # 1. Can't create new file "filename.$$" due to permissions/etc. # - We can't simulate this, unfortunately # 2. Can't rename "filename.$$" to "filename" for whatever reason. # each of the above cases should be tested in all three failure modes: # 1. quiet (no warnings, exceptions, or content) # 2. carp (warnings, no exceptions, no content) # 3. croak (an exception, no warnings, no content) # Simulate a bad open { my $file = temp_file_path('gimme a nonexistent path'); # first, write_file my ($res, $warn, $err) = trap_function(\&write_file, $file, {err_mode => 'quiet'}, 'junk'); ok(!$warn, 'write_file: open error, quiet - no warn!'); ok(!$err, 'write_file: open error, quiet - no exception!'); ok(!$res, 'write_file: open error, quiet - no content!'); ($res, $warn, $err) = trap_function(\&write_file, $file, {err_mode => 'carp'}, 'junk'); ok($warn, 'write_file: open error, carp - got warn!'); ok(!$err, 'write_file: open error, carp - no exception!'); ok(!$res, 'write_file: open error, carp - no content!'); ($res, $warn, $err) = trap_function(\&write_file, $file, {err_mode => 'croak'}, 'junk'); ok(!$warn, 'write_file: open error, croak - no warn!'); ok($err, 'write_file: open error, croak - got exception!'); ok(!$res, 'write_file: open error, croak - no content!'); # the wf synonym ($res, $warn, $err) = trap_function(\&wf, $file, {err_mode => 'quiet'}, 'junk'); ok(!$warn, 'wf: open error, quiet - no warn!'); ok(!$err, 'wf: open error, quiet - no exception!'); ok(!$res, 'wf: open error, quiet - no content!'); ($res, $warn, $err) = trap_function(\&wf, $file, {err_mode => 'carp'}, 'junk'); ok($warn, 'wf: open error, carp - got warn!'); ok(!$err, 'wf: open error, carp - no exception!'); ok(!$res, 'wf: open error, carp - no content!'); ($res, $warn, $err) = trap_function(\&wf, $file, {err_mode => 'croak'}, 'junk'); ok(!$warn, 'wf: open error, croak - no warn!'); ok($err, 'wf: open error, croak - got exception!'); ok(!$res, 'wf: open error, croak - no content!'); # the overwrite_file synonym ($res, $warn, $err) = trap_function(\&overwrite_file, $file, {err_mode => 'quiet'}, 'junk'); ok(!$warn, 'overwrite_file: open error, quiet - no warn!'); ok(!$err, 'overwrite_file: open error, quiet - no exception!'); ok(!$res, 'overwrite_file: open error, quiet - no content!'); ($res, $warn, $err) = trap_function(\&overwrite_file, $file, {err_mode => 'carp'}, 'junk'); ok($warn, 'overwrite_file: open error, carp - got warn!'); ok(!$err, 'overwrite_file: open error, carp - no exception!'); ok(!$res, 'overwrite_file: open error, carp - no content!'); ($res, $warn, $err) = trap_function(\&overwrite_file, $file, {err_mode => 'croak'}, 'junk'); ok(!$warn, 'overwrite_file: open error, croak - no warn!'); ok($err, 'overwrite_file: open error, croak - got exception!'); ok(!$res, 'overwrite_file: open error, croak - no content!'); # the append_file pseudo-synonym (adds the atomic => 1 option) ($res, $warn, $err) = trap_function(\&append_file, $file, {err_mode => 'quiet'}, 'junk'); ok(!$warn, 'append_file: open error, quiet - no warn!'); ok(!$err, 'append_file: open error, quiet - no exception!'); ok(!$res, 'append_file: open error, quiet - no content!'); ($res, $warn, $err) = trap_function(\&append_file, $file, {err_mode => 'carp'}, 'junk'); ok($warn, 'append_file: open error, carp - got warn!'); ok(!$err, 'append_file: open error, carp - no exception!'); ok(!$res, 'append_file: open error, carp - no content!'); ($res, $warn, $err) = trap_function(\&append_file, $file, {err_mode => 'croak'}, 'junk'); ok(!$warn, 'append_file: open error, croak - no warn!'); ok($err, 'append_file: open error, croak - got exception!'); ok(!$res, 'append_file: open error, croak - no content!'); } # Simulate a bad write # we do this by causing CORE::syswrite to fail by overriding it SKIP: { skip "Skip these tests because mocking write failures can't happen", 36; my $file = temp_file_path(); # good filename, can open # write_file first my ($res, $warn, $err) = trap_function_override_core('syswrite', \&write_file, $file, {err_mode => 'quiet'}, 'junk'); ok(!$warn, 'write_file: write error, quiet - no warn!'); ok(!$err, 'write_file: write error, quiet - no exception!'); ok(!$res, 'write_file: write error, quiet - no content!'); ($res, $warn, $err) = trap_function_override_core('syswrite', \&write_file, $file, {err_mode => 'carp'}, 'junk'); ok($warn, 'write_file: write error, carp - got warn!'); ok(!$err, 'write_file: write error, carp - no exception!'); ok(!$res, 'write_file: write error, carp - no content!'); ($res, $warn, $err) = trap_function_override_core('syswrite', \&write_file, $file, {err_mode => 'croak'}, 'junk'); ok(!$warn, 'write_file: write error, croak - no warn!'); ok($err, 'write_file: write error, croak - got exception!'); ok(!$res, 'write_file: write error, croak - no content!'); # now the wf synonym ($res, $warn, $err) = trap_function_override_core('syswrite', \&wf, $file, {err_mode => 'quiet'}, 'junk'); ok(!$warn, 'wf: write error, quiet - no warn!'); ok(!$err, 'wf: write error, quiet - no exception!'); ok(!$res, 'wf: write error, quiet - no content!'); ($res, $warn, $err) = trap_function_override_core('syswrite', \&wf, $file, {err_mode => 'carp'}, 'junk'); ok($warn, 'wf: write error, carp - got warn!'); ok(!$err, 'wf: write error, carp - no exception!'); ok(!$res, 'wf: write error, carp - no content!'); ($res, $warn, $err) = trap_function_override_core('syswrite', \&wf, $file, {err_mode => 'croak'}, 'junk'); ok(!$warn, 'wf: write error, croak - no warn!'); ok($err, 'wf: write error, croak - got exception!'); ok(!$res, 'wf: write error, croak - no content!'); # now the overwrite_file synonym ($res, $warn, $err) = trap_function_override_core('syswrite', \&overwrite_file, $file, {err_mode => 'quiet'}, 'junk'); ok(!$warn, 'overwrite_file: write error, quiet - no warn!'); ok(!$err, 'overwrite_file: write error, quiet - no exception!'); ok(!$res, 'overwrite_file: write error, quiet - no content!'); ($res, $warn, $err) = trap_function_override_core('syswrite', \&overwrite_file, $file, {err_mode => 'carp'}, 'junk'); ok($warn, 'overwrite_file: write error, carp - got warn!'); ok(!$err, 'overwrite_file: write error, carp - no exception!'); ok(!$res, 'overwrite_file: write error, carp - no content!'); ($res, $warn, $err) = trap_function_override_core('syswrite', \&overwrite_file, $file, {err_mode => 'croak'}, 'junk'); ok(!$warn, 'overwrite_file: write error, croak - no warn!'); ok($err, 'overwrite_file: write error, croak - got exception!'); ok(!$res, 'overwrite_file: write error, croak - no content!'); # the append_file pseudo-synonym (adds the atomic => 1 option) ($res, $warn, $err) = trap_function_override_core('syswrite', \&append_file, $file, {err_mode => 'quiet'}, 'junk'); ok(!$warn, 'append_file: write error, quiet - no warn!'); ok(!$err, 'append_file: write error, quiet - no exception!'); ok(!$res, 'append_file: write error, quiet - no content!'); ($res, $warn, $err) = trap_function_override_core('syswrite', \&append_file, $file, {err_mode => 'carp'}, 'junk'); ok($warn, 'append_file: write error, carp - got warn!'); ok(!$err, 'append_file: write error, carp - no exception!'); ok(!$res, 'append_file: write error, carp - no content!'); ($res, $warn, $err) = trap_function_override_core('syswrite', \&append_file, $file, {err_mode => 'croak'}, 'junk'); ok(!$warn, 'append_file: write error, croak - no warn!'); ok($err, 'append_file: write error, croak - got exception!'); ok(!$res, 'append_file: write error, croak - no content!'); unlink $file, "$file.$$"; }; # Simulate a bad rename when in atomic mode. # we do this by causing CORE::rename to fail by overriding it { my $file = temp_file_path(); # good filename, can open # write_file first my ($res, $warn, $err) = trap_function_override_core('rename', \&write_file, $file, {atomic => 1, err_mode => 'quiet'}, 'junk'); ok(!$warn, 'write_file: rename error, quiet - no warn!'); ok(!$err, 'write_file: rename error, quiet - no exception!'); ok(!$res, 'write_file: rename error, quiet - no content!'); ($res, $warn, $err) = trap_function_override_core('rename', \&write_file, $file, {atomic => 1, err_mode => 'carp'}, 'junk'); ok($warn, 'write_file: rename error, carp - got warn!'); ok(!$err, 'write_file: rename error, carp - no exception!'); ok(!$res, 'write_file: rename error, carp - no content!'); ($res, $warn, $err) = trap_function_override_core('rename', \&write_file, $file, {atomic => 1, err_mode => 'croak'}, 'junk'); ok(!$warn, 'write_file: rename error, croak - no warn!'); ok($err, 'write_file: rename error, croak - got exception!'); ok(!$res, 'write_file: rename error, croak - no content!'); unlink "$file.$$"; # now the wf synonym ($res, $warn, $err) = trap_function_override_core('rename', \&wf, $file, {atomic => 1, err_mode => 'quiet'}, 'junk'); ok(!$warn, 'wf: rename error, quiet - no warn!'); ok(!$err, 'wf: rename error, quiet - no exception!'); ok(!$res, 'wf: rename error, quiet - no content!'); ($res, $warn, $err) = trap_function_override_core('rename', \&wf, $file, {atomic => 1, err_mode => 'carp'}, 'junk'); ok($warn, 'wf: rename error, carp - got warn!'); ok(!$err, 'wf: rename error, carp - no exception!'); ok(!$res, 'wf: rename error, carp - no content!'); ($res, $warn, $err) = trap_function_override_core('rename', \&wf, $file, {atomic => 1, err_mode => 'croak'}, 'junk'); ok(!$warn, 'wf: rename error, croak - no warn!'); ok($err, 'wf: rename error, croak - got exception!'); ok(!$res, 'wf: rename error, croak - no content!'); unlink "$file.$$"; # now the overwrite_file synonym ($res, $warn, $err) = trap_function_override_core('rename', \&overwrite_file, $file, {atomic => 1, err_mode => 'quiet'}, 'junk'); ok(!$warn, 'overwrite_file: rename error, quiet - no warn!'); ok(!$err, 'overwrite_file: rename error, quiet - no exception!'); ok(!$res, 'overwrite_file: rename error, quiet - no content!'); ($res, $warn, $err) = trap_function_override_core('rename', \&overwrite_file, $file, {atomic => 1, err_mode => 'carp'}, 'junk'); ok($warn, 'overwrite_file: rename error, carp - got warn!'); ok(!$err, 'overwrite_file: rename error, carp - no exception!'); ok(!$res, 'overwrite_file: rename error, carp - no content!'); ($res, $warn, $err) = trap_function_override_core('rename', \&overwrite_file, $file, {atomic => 1, err_mode => 'croak'}, 'junk'); ok(!$warn, 'overwrite_file: rename error, croak - no warn!'); ok($err, 'overwrite_file: rename error, croak - got exception!'); ok(!$res, 'overwrite_file: rename error, croak - no content!'); unlink "$file.$$"; # the append_file pseudo-synonym (adds the append => 1 option) ($res, $warn, $err) = trap_function_override_core('rename', \&append_file, $file, {atomic => 1, err_mode => 'quiet'}, 'junk'); ok(!$warn, 'append_file: rename error, quiet - no warn!'); ok(!$err, 'append_file: rename error, quiet - no exception!'); ok(!$res, 'append_file: rename error, quiet - no content!'); ($res, $warn, $err) = trap_function_override_core('rename', \&append_file, $file, {atomic => 1, err_mode => 'carp'}, 'junk'); ok($warn, 'append_file: rename error, carp - got warn!'); ok(!$err, 'append_file: rename error, carp - no exception!'); ok(!$res, 'append_file: rename error, carp - no content!'); ($res, $warn, $err) = trap_function_override_core('rename', \&append_file, $file, {atomic => 1, err_mode => 'croak'}, 'junk'); ok(!$warn, 'append_file: rename error, croak - no warn!'); ok($err, 'append_file: rename error, croak - got exception!'); ok(!$res, 'append_file: rename error, croak - no content!'); unlink $file, "$file.$$"; } File-Slurp-9999.32/t/original.t0000644000175000017500000000330513356734371016717 0ustar cwhitenercwhiteneruse strict; use warnings; use File::Spec (); use File::Slurp; use File::Temp qw(tempfile); use Test::More; plan(tests => 8); # older EUMMs turn this on. We don't want to emit warnings. # also, some of our CORE function overrides emit warnings. Silence those. local $^W; my (undef, $tmp) = tempfile('tempXXXXX', DIR => File::Spec->tmpdir, OPEN => 0); my $short = <catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib'); use FileSlurpTest qw(temp_file_path trap_function); use File::Slurp qw(write_file prepend_file read_file); use Test::More ; plan tests => 32; my $existing_data = <
1,bar=>2}, $prepend_data);
    ok($res, 'prepend_file: add line, invalid opts: got response!');
    ok(!$warn, 'prepend_file: add line, invalid opts: no warnings!');
    ok(!$err, 'prepend_file: add line, invalid opts: no exceptions!');
    my $data = read_file($file);
    is($data, $prepend_data.$existing_data, 'prepend_file: add line, invalid opts: contents match');
    unlink $file;
}
{
    my $file = temp_file_path();
    write_file($file, $existing_data);
    my $prepend_data = "line 0\n";
    my ($res, $warn, $err) = trap_function(\&prepend_file, $file, {foo=>1,bar=>2,binmode=>':raw'}, $prepend_data);
    ok($res, 'prepend_file: add line, invalid opts, binmode: got response!');
    # this should get fixed
    SKIP: {
        skip "Binmode is bad news bears with sysread on Perl 5.30+", 1;
        ok(!$warn, 'prepend_file: add line, invalid opts, binmode: no warnings!');
    }
    ok(!$err, 'prepend_file: add line, invalid opts, binmode: no exceptions!');
    my $data = read_file($file);
    is($data, $prepend_data.$existing_data, 'prepend_file: add line, invalid opts, binmode: contents match');
    unlink $file;
}
{
    my $file = temp_file_path();
    write_file($file, $existing_data);
    my $prepend_data = "line 0\n";
    my ($res, $warn, $err) = trap_function(\&prepend_file, $file, {foo=>1,bar=>2,err_mode=>'quiet'}, $prepend_data);
    ok($res, 'prepend_file: add line, invalid opts, err_mode quiet: got response!');
    ok(!$warn, 'prepend_file: add line, invalid opts, err_mode quiet: no warnings!');
    ok(!$err, 'prepend_file: add line, invalid opts, err_mode quiet: no exceptions!');
    my $data = read_file($file);
    is($data, $prepend_data.$existing_data, 'prepend_file: add line, invalid opts, err_mode quiet: contents match');
    unlink $file;
}
{
    my $file = temp_file_path();
    write_file($file, $existing_data);
    my $prepend_data = "line 0\n";
    my ($res, $warn, $err) = trap_function(\&prepend_file, $file, \$prepend_data);
    ok($res, 'prepend_file: add line, scalar ref: got response!');
    ok(!$warn, 'prepend_file: add line, scalar ref: no warnings!');
    ok(!$err, 'prepend_file: add line, scalar ref: no exceptions!');
    my $data = read_file($file);
    is($data, $prepend_data.$existing_data, 'prepend_file: add line, scalar ref: contents match');
    unlink $file;
}
File-Slurp-9999.32/t/01-error_prepend_file.t0000644000175000017500000001212713440747315021174 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTestOverride qw(trap_function_override_core);
use FileSlurpTest qw(temp_file_path trap_function);

use File::Slurp qw(prepend_file);
use Test::More;

plan tests => 27;

# older EUMMs turn this on. We don't want to emit warnings.
# also, some of our CORE function overrides emit warnings. Silence those.
local $^W;

# prepend_file reads in a file, edits the contents, writes the new file
# atomically to "foo.$$" then renames "foo.$$" to the original "foo"
# this leaves many failure steps to tend to

# step 1: read in the file. error simulated by asking it to read-in a
# nonexistent file
{
    # this one intentionally doesn't exist on a couple of paths. can't be created.
    my $file = temp_file_path('gimme a nonexistent path');
    my ($res, $warn, $err) = trap_function(\&prepend_file, $file, {err_mode => 'quiet'}, 'junk');
    ok(!$warn, 'prepend_file: read: err_mode opt quiet - no warn!');
    ok(!$err, 'prepend_file: read: err_mode opt quiet - no exception!');
    ok(!$res, 'prepend_file: read: err_mode opt quiet - no content!');
    ($res, $warn, $err) = trap_function(\&prepend_file, $file, {err_mode => 'carp'}, 'junk');
    like($warn, qr/read_file/, 'prepend_file: read: err_mode opt carp - got warn!');
    ok(!$err, 'prepend_file: read: err_mode opt carp - no exception!');
    ok(!$res, 'prepend_file: read: err_mode opt carp - no content!');
    ($res, $warn, $err) = trap_function(\&prepend_file, $file, {err_mode => 'croak'}, 'junk');
    ok(!$warn, 'prepend_file: read: err_mode opt croak - no warn!');
    like($err, qr/read_file/, 'prepend_file: read: err_mode opt croak - got exception!');
    ok(!$res, 'prepend_file: read: err_mode opt croak - no content!');
}

# step 2: Allow step 1 to pass, then write out the newly altered contents to a
# a file called "foo.$$". This write will fail by simulating a problem with
# CORE::GLOBAL::syswrite
SKIP: {
    skip "Skip these tests because mocking write failures can't happen", 9;
    # go ahead and setup an initial file so that it can be read during the test
    my $file = temp_file_path();
    File::Slurp::write_file($file, '');

    # step 1 will pass here, but step 2 will fail due to our simulation
    # overriding CORE::syswrite simulates a failure in writing to a file
    my ($res, $warn, $err) = trap_function_override_core('syswrite', \&prepend_file, $file, {err_mode => 'quiet'}, '');
    ok(!$warn, 'prepend_file: write: err_mode opt quiet - no warning!');
    ok(!$err, 'prepend_file: write: err_mode opt quiet - no exception!');
    ok(!$res, 'prepend_file: write: err_mode opt quiet - no content!');
    unlink "$file.$$";
    ($res, $warn, $err) = trap_function_override_core('syswrite', \&prepend_file, $file, {err_mode => 'carp'}, '');
    like($warn, qr/write_file/, 'prepend_file: write: err_mode opt carp - got warning!');
    ok(!$err, 'prepend_file: write: err_mode opt carp - no exception!');
    ok(!$res, 'prepend_file: write: err_mode opt carp - no content!');
    unlink "$file.$$";
    ($res, $warn, $err) = trap_function_override_core('syswrite', \&prepend_file, $file, {err_mode => 'croak'}, '');
    ok(!$warn, 'prepend_file: write: err_mode opt croak - no warning!');
    like($err, qr/write_file/, 'prepend_file: write: err_mode opt croak - got exception!');
    ok(!$res, 'prepend_file: write: err_mode opt croak - no content!');
    unlink "$file.$$";
    # cleanup
    unlink $file;
};

# step 3: Allow steps 1 and 2 to pass, then rename the new file called "foo.$$"
# to the original "foo". This rename will fail by simulating a problem with
# CORE::GLOBAL::rename
{
    # go ahead and setup an initial file so that it can be read during the test
    my $file = temp_file_path();
    File::Slurp::write_file($file, '');

    # step 1 will pass here, but step 2 will fail due to our simulation
    # overriding CORE::syswrite simulates a failure in writing to a file
    my ($res, $warn, $err) = trap_function_override_core('rename', \&prepend_file, $file, {err_mode => 'quiet'}, '');
    ok(!$warn, 'prepend_file: rename: err_mode opt quiet - no warning!');
    ok(!$err, 'prepend_file: rename: err_mode opt quiet - no exception!');
    ok(!$res, 'prepend_file: rename: err_mode opt quiet - no content!');
    unlink "$file.$$";
    ($res, $warn, $err) = trap_function_override_core('rename', \&prepend_file, $file, {err_mode => 'carp'}, '');
    like($warn, qr/write_file/, 'prepend_file: rename: err_mode opt carp - got warning!');
    ok(!$err, 'prepend_file: rename: err_mode opt carp - no exception!');
    ok(!$res, 'prepend_file: rename: err_mode opt carp - no content!');
    unlink "$file.$$";
    ($res, $warn, $err) = trap_function_override_core('rename', \&prepend_file, $file, {err_mode => 'croak'}, '');
    ok(!$warn, 'prepend_file: rename: err_mode opt croak - no warning!');
    like($err, qr/write_file/, 'prepend_file: rename: err_mode opt croak - got exception!');
    ok(!$res, 'prepend_file: rename: err_mode opt croak - no content!');
    unlink "$file.$$";
    # cleanup
    unlink $file;
}
File-Slurp-9999.32/t/perms.t0000644000175000017500000000503513361246675016244 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use IO::Handle ();
use Fcntl qw(:DEFAULT);
use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');

use FileSlurpTest qw(temp_file_path trap_function);
use File::Slurp;
use Test::More;

plan tests => 12;

{
    umask 0;
    my $file = temp_file_path();
    # the above file name isn't yet created

    # create with sysopen
    sysopen my $fh, $file, O_WRONLY | O_TRUNC | O_CREAT, 0666 or die $!;
    $fh->print("whatever");
    $fh->close();
    my $mode = _mode($file);
    unlink $file;

    # create it again with write_file
    my ($res, $warn, $err) = trap_function(\&write_file, $file, "whatever");
    ok($res, 'write_file: plain write - got a response');
    ok(!$warn, 'write_file: plain write - no warnings!');
    ok(!$err, 'write_file: plain write - no exceptions!');

    # check that the permissions match both ways
    is(_mode($file), $mode, 'write_file: plain write - default perms');
    unlink $file;
}

{
    umask 027; # test this with another umask
    my $file = temp_file_path();
    # the above file name isn't yet created

    # create with sysopen
    sysopen my $fh, $file, O_WRONLY | O_TRUNC | O_CREAT, 0666 or die $!;
    $fh->print("whatever");
    $fh->close();
    my $mode = _mode($file);
    unlink $file;

    # create it again with write_file
    my ($res, $warn, $err) = trap_function(\&write_file, $file, "whatever");
    ok($res, 'write_file: plain write - got a response');
    ok(!$warn, 'write_file: plain write - no warnings!');
    ok(!$err, 'write_file: plain write - no exceptions!');

    # check that the permissions match both ways
    is(_mode( $file ), $mode, 'write_file: plain write - default perms');
    unlink $file;
}

{
    umask 027;
    my $file = temp_file_path();
    # the above file name isn't yet created

    # create with sysopen
    sysopen my $fh, $file, O_WRONLY | O_TRUNC | O_CREAT, 0777 or die $!;
    $fh->print("whatever");
    $fh->close();
    my $mode = _mode($file);
    unlink $file;

    # create it again with write_file with permissions passed
    my ($res, $warn, $err) = trap_function(\&write_file, $file, {perms => 0777}, "whatever");
    ok($res, 'write_file: perms opt - got a response');
    ok(!$warn, 'write_file: perms opt - no warnings!');
    ok(!$err, 'write_file: perms opt - no exceptions!');

    # check that the permissions match both ways
    is(_mode($file), $mode, 'write_file: perms opt - got perms');
    unlink $file;
}

exit;

sub _mode {
    return 07777 & (stat $_[0])[2];
}
File-Slurp-9999.32/t/stringify.t0000644000175000017500000000167113363077605017133 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Spec ();
use File::Slurp;
use File::Temp qw(tempfile);
use IO::Handle ();
use Test::More;

# older EUMMs turn this on. We don't want to emit warnings.
# also, some of our CORE function overrides emit warnings. Silence those.
local $^W;

# this code creates the object which has a stringified path
{
    package FileObject;
    use Exporter qw(import);
    use overload
        q[""] => \&stringify,
        fallback => 1;

    sub new { bless { path => $_[1] }, $_[0] }

    sub stringify { $_[0]->{path} }
}

plan tests => 3 ;

my (undef, $path) = tempfile('tempXXXXX', DIR => File::Spec->tmpdir, OPEN => 0);
my $data = "random junk\n";

# create an object with an overloaded path
my $obj = FileObject->new($path);

isa_ok($obj, 'FileObject');
is("$obj", $path, "object stringifies to path");

write_file($obj, $data);
my $read = read_file($obj);
is($data, $read, 'read_file of stringified object');

unlink $path;
File-Slurp-9999.32/t/read_dir.t0000644000175000017500000000357713363077605016675 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path);

use File::Slurp qw(read_dir write_file);
use Test::More;

plan tests => 9;

# try to honor possible tempdirs
my $test_dir = temp_file_path(); # a good temporary filename

mkdir( $test_dir, 0700) || die "mkdir $test_dir: $!";
my @dir_entries = read_dir($test_dir);
ok(@dir_entries == 0, 'empty dir');

@dir_entries = read_dir($test_dir, keep_dot_dot => 1);
ok(@dir_entries == 2, 'empty dir with . ..');

@dir_entries = read_dir($test_dir, {keep_dot_dot => 1});
ok(@dir_entries == 2, 'empty dir with . .. - args ref');

write_file(File::Spec->catfile($test_dir, 'x'), "foo\n");
@dir_entries = read_dir($test_dir);
ok(@dir_entries == 1, 'dir with 1 file');
is($dir_entries[0], 'x', 'dir with file x');


my $file_cnt = 23;
my @expected_entries = sort('x', 1 .. $file_cnt);

for my $file (1 .. $file_cnt) {
    write_file(File::Spec->catfile($test_dir, $file), "foo\n");
}

@dir_entries = read_dir($test_dir);
@dir_entries = sort @dir_entries;

is_deeply(\@dir_entries, \@expected_entries, "dir with $file_cnt files");

my $dir_entries_ref = read_dir($test_dir);
@{$dir_entries_ref} = sort @{$dir_entries_ref};

is_deeply($dir_entries_ref, \@expected_entries, "dir in array ref");

my @prefixed_entries;
@prefixed_entries = read_dir( $test_dir, { prefix => 1 } ) ;
is_deeply(
    [ sort @prefixed_entries ],
    [ map File::Spec->catfile($test_dir, $_), @dir_entries ],
	'prefix option in hash ref'
);

@prefixed_entries = read_dir( $test_dir, prefix => 1 ) ;
is_deeply(
    [ sort @prefixed_entries ],
    [ map File::Spec->catfile($test_dir, $_), @dir_entries ],
	'prefix option as key-value pair'
);

# clean up

unlink map File::Spec->catfile($test_dir, $_), @dir_entries;
rmdir($test_dir) || die "rmdir $test_dir: $!";
File-Slurp-9999.32/t/newline.t0000644000175000017500000000217513365742141016552 0ustar  cwhitenercwhiteneruse strict;
use warnings;
use IO::Handle ();

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path);

use File::Slurp qw(read_file write_file);

use Test::More;
plan tests => 2;

my $data = "\r\n\r\n\r\n" ;
my $file_name = temp_file_path();

stdio_write_file($file_name, $data);
my $slurped_data = read_file($file_name);

my $stdio_slurped_data = stdio_read_file( $file_name ) ;


print 'data ', unpack( 'H*', $data), "\n",
'slurp ', unpack('H*',  $slurped_data), "\n",
'stdio slurp ', unpack('H*',  $stdio_slurped_data), "\n";

is($data, $slurped_data, 'slurp');

write_file($file_name, $data);
$slurped_data = stdio_read_file($file_name);

is($data, $slurped_data, 'spew');
unlink $file_name;

sub stdio_write_file {
    my ($file_name, $data) = @_;
    open (my $fh, '>', $file_name) || die "Couldn't create $file_name: $!";
    $fh->print($data);
}

sub stdio_read_file {
    my ($file_name) = @_;
    open (my $fh, '<', $file_name ) || die "Couldn't open $file_name: $!";
    local $/;
    my $data = <$fh>;
    return $data;
}
File-Slurp-9999.32/t/tainted.t0000644000175000017500000000306213536562567016551 0ustar  cwhitenercwhitener#!perl -T

use strict;
use warnings;
use IO::Handle ();
use File::Basename ();
use File::Spec ();
use Scalar::Util qw(tainted);
use Test::More;

BEGIN {
    plan skip_all => 'Taint was always terrible. Just stop it already.';
    exit;
    # Taint mode is the devil. THE DEVIL I SAY
    unshift @INC, File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib') =~ /^(.*)$/;
    # Why on earth do we keep on with Taint mode?!? I hate all the things
}

use FileSlurpTest qw(temp_file_path trap_function trap_function_list_context);
use File::Slurp qw(read_file);

plan tests => 9;

my $path = temp_file_path();
my $data = "random junk\nline2";

# write something to that file
open(my $fh, ">", $path) or die "can't write to '$path': $!";
$fh->print($data);
$fh->close();

# read the file using File::Slurp in scalar context
my ($res, $warn, $err) = trap_function(\&read_file, $path);
ok(!$warn, "read_file: taint on - no warnings");
ok(!$err, "read_file: taint on - no exceptions");
ok($res, "read_file: taint on - got content");
ok(tainted($res), "read_file: taint on - got tainted content");

# read the file using File::Slurp in list context
my $aref;
($aref, $warn, $err) = trap_function_list_context(\&read_file, $path);
ok(!$warn, "read_file: list context, taint on - no warnings");
ok(!$err, "read_file: list context, taint on - no exceptions");
ok(@{$aref}, "read_file: list context, taint on - got content");
ok(tainted($aref->[0]), "read_file: list context, taint on - got tainted content");

is(join('', @{$aref}), $res, "list eq scalar");

unlink $path;
File-Slurp-9999.32/t/file_object.t0000644000175000017500000000367113363077605017364 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path trap_function);
use File::Slurp qw(read_file write_file);
use Scalar::Util qw(blessed);
use Test::More ;

plan tests => 12;

# the following mimics the parts from Path::Class causing
# problems with File::Slurp
{
    package FileObject;
    use strict;
    use warnings;
    use overload
        q[""] => \&stringify, fallback => 1;

    sub new {
        return bless { path => $_[1] }, $_[0]
    }

    sub stringify {
        return $_[0]->{path}
    }
}

my $path = temp_file_path();
my $data = "random junk\n";

# create an object
my $obj = FileObject->new($path);
isa_ok($obj, 'FileObject');
is("$obj", $path, "check that the object correctly stringifies");
ok(!($obj && ref($obj) && blessed($obj) && $obj->isa('GLOB')), "FileObject isn't a glob");
ok(!($obj && ref($obj) && blessed($obj) && $obj->isa('IO')), "FileObject isn't an IO");

my $io = IO::Handle->new();
isa_ok($io, 'IO::Handle');
ok($io && ref($io) && blessed($io) && $io->isa('GLOB'), "IO::Handle is a glob");
ok(!($io && ref($io) && blessed($io) && $io->isa('IO')), "IO::Handle isn't an IO");

SKIP: {
    open(FH, '<', $0) or skip 3, "Can't open $0: $!";
    my $fh = *FH{IO};
    my $glob = *FH{GLOB};
    ok($fh && ref($fh) && blessed($fh) && $fh->isa('IO'), '$fh is an IO');
    ok(!($glob && ref($glob) && blessed($glob) && $glob->isa('GLOB')), '$glob is an GLOB');
}

SKIP: {
    # write something to that file
    open(FILE, '>', "$obj") or skip 4, "can't write to '$path': $!";
    print FILE $data;
    close(FILE);

    # pass it to read_file()
    my ($res, $warn, $err) = trap_function(\&read_file, $obj);
    is($res, $data, "read_file: file object: right content");
    ok(!$warn, "read_file: file object: no warnings!");
    ok(!$err, "read_file: file object: no exceptions!");
}

unlink $path;
File-Slurp-9999.32/t/01-error_edit_file_lines.t0000644000175000017500000000431313355535337021660 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path trap_function);

# both of these names are synonyms
use File::Slurp qw(efl edit_file_lines);
use Test::More;

plan tests => 18;

# this one intentionally doesn't exist on a couple of paths. can't be created.
my $file = temp_file_path('gimme a nonexistent path');

# edit_file_lines errors
{
    my ($res, $warn, $err) = trap_function(\&edit_file_lines, sub { s/foo/bar/g }, $file, {err_mode => 'quiet'});
    ok(!$warn, 'edit_file_lines: err_mode opt quiet - no warn!');
    ok(!$err, 'edit_file_lines: err_mode opt quiet - no exception!');
    ok(!$res, 'edit_file_lines: err_mode opt quiet - no content!');
    ($res, $warn, $err) = trap_function(\&edit_file_lines, sub { s/foo/bar/g }, $file, {err_mode => 'carp'});
    ok($warn, 'edit_file_lines: err_mode opt carp - got warn!');
    ok(!$err, 'edit_file_lines: err_mode opt carp - no exception!');
    ok(!$res, 'edit_file_lines: err_mode opt carp - no content!');
    ($res, $warn, $err) = trap_function(\&edit_file_lines, sub { s/foo/bar/g }, $file, {err_mode => 'croak'});
    ok(!$warn, 'edit_file_lines: err_mode opt croak - no warn!');
    ok($err, 'edit_file_lines: err_mode opt croak - got exception!');
    ok(!$res, 'edit_file_lines: err_mode opt croak - no content!');
}

# efl errors
{
    my ($res, $warn, $err) = trap_function(\&efl, sub { s/foo/bar/g }, $file, {err_mode => 'quiet'});
    ok(!$warn, 'efl: err_mode opt quiet - no warn!');
    ok(!$err, 'efl: err_mode opt quiet - no exception!');
    ok(!$res, 'efl: err_mode opt quiet - no content!');
    ($res, $warn, $err) = trap_function(\&efl, sub { s/foo/bar/g }, $file, {err_mode => 'carp'});
    ok($warn, 'efl: err_mode opt carp - got warn!');
    ok(!$err, 'efl: err_mode opt carp - no exception!');
    ok(!$res, 'efl: err_mode opt carp - no content!');
    ($res, $warn, $err) = trap_function(\&efl, sub { s/foo/bar/g }, $file, {err_mode => 'croak'});
    ok(!$warn, 'efl: err_mode opt croak - no warn!');
    ok($err, 'efl: err_mode opt croak - got exception!');
    ok(!$res, 'efl: err_mode opt croak - no content!');
}
File-Slurp-9999.32/t/large.t0000644000175000017500000001214613366460674016213 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use Carp ;
use File::Spec ();
use File::Slurp;
use File::Temp qw(tempfile);
use Test::More;

# older EUMMs turn this on. We don't want to emit warnings.
# also, some of our CORE function overrides emit warnings. Silence those.
local $^W;

my @text_data = (
    [],
    [ 'a' x 8 ],
    [ ("\n") x 5 ],
    [ map( "aaaaaaaa\n", 1 .. 3 ) ],
    [ map( "aaaaaaaa\n", 1 .. 3 ), 'aaaaaaaa' ],
    [ map ( 'a' x 100 . "\n", 1 .. 1024 ) ],
    [ map ( 'a' x 100 . "\n", 1 .. 1024 ), 'a' x 100 ],
    [ map ( 'a' x 1024 . "\n", 1 .. 1024 ) ],
    [ map ( 'a' x 1024 . "\n", 1 .. 1024 ), 'a' x 10240 ],
    [],
);

my @bin_sizes = (1000, 1024 * 1024);
my @bin_stuff = ("\012", "\015", "\012\015", "\015\012", map {chr $_} (0 .. 32) ) ;
my @bin_data;
foreach my $size (@bin_sizes) {
    my $data = '';
    while (length($data) < $size) {
        $data .= $bin_stuff[ rand @bin_stuff ];
    }
    push @bin_data, $data;
}

plan(tests => 17 * @text_data + 8 * @bin_data);

my (undef, $file) = tempfile('tempXXXXX', DIR => File::Spec->tmpdir, OPEN => 0);

foreach my $data (@text_data) {
    test_text_slurp($data);
}
foreach my $data (@bin_data) {
    test_bin_slurp($data);
}

unlink $file;

exit;

sub test_text_slurp {
    my ($data_ref) = @_;

    my @data_lines = @{$data_ref};
    my $data_text = join('', @data_lines);
    my $data_length = length($data_text);

    # write_file returns 1 for success or undef on error
    # diag("Data Text: ".$data_text);

    { # write then read - regular string
        my $res = write_file($file, $data_text);
        ok($res, "write_file - $data_length");
        my $text = read_file($file);
        is($text, $data_text, "read_file: scalar context - $data_length");
    }

    { # write and read - from scalar ref
        my $res = write_file($file, \$data_text);
        ok($res, "write_file - ref arg - $data_length");
        my $text = read_file($file);
        is($text, $data_text, "read_file: scalar context - $data_length");
    }

    { # write and read using buf_ref and scalar_ref options
        my $res = write_file($file, {buf_ref => \$data_text});
        ok($res, "write_file - buf ref opt - $data_length");
        my $text = read_file($file);
        is($text, $data_text, "read_file: scalar context - $data_length");
        my $text_ref = read_file($file, scalar_ref => 1);
        is(${$text_ref}, $data_text, "read_file: scalar_ref opt - $data_length");
        read_file($file, buf_ref => \my $buffer);
        is($buffer, $data_text, "read_file - buf_ref opt - $data_length");
    }

    { # write and read - from array ref
        my $res = write_file($file, \@data_lines);
        ok($res, "write_file - list ref arg - $data_length");
        my $text = read_file($file);
        is($text, $data_text, "read_file: scalar context - $data_length");
        my @array = read_file($file);
        is_deeply(\@array, \@data_lines, "read_file: list context - $data_length");
        my $array_ref = read_file($file, array_ref => 1);
        is_deeply($array_ref, \@data_lines, "read_file: scalar context with array_ref opt - $data_length");
        ($array_ref) = read_file($file, {array_ref => 1});
        is_deeply($array_ref, \@data_lines, "read_file: list context with array_ref opt - $data_length");
    }

    { # write and read - with append option
        my $res = write_file($file, {append => 1}, $data_text);
        ok($res, "write_file - append opt - $data_length");
        my $text = read_file($file);
        is($text, $data_text x 2, "read_file: scalar context - $data_length");
    }

    { # append and read
        my $res = append_file($file, $data_text );
        ok($res, "append_file - $data_length");
        my $text = read_file($file);
        is($text, $data_text x 3, "read_file: scalar context - $data_length");
    }
}

sub test_bin_slurp {
    my ($data) = @_;

    my $data_length = length($data);

    { # write and read - binmode :raw opt
        my $res = write_file($file, {binmode => ':raw'}, $data);
        ok($res, "write_file - binmode opt - $data_length");
        my $bin = read_file($file, binmode => ':raw');
        is($bin, $data, "read_file: scalar context binmode opt - $data_length");
        my $bin_ref = read_file($file, scalar_ref => 1, binmode => ':raw');
        is(${$bin_ref}, $data, "read_file: scalar w/ scalar_ref, binmode opts - $data_length");
        read_file($file, buf_ref => \(my $buffer), binmode => ':raw');
        is($buffer,$data, "read_file: buf_ref, binmode opts - $data_length");
    }

    { # write and read - append with binmode :raw opt
        my $res = write_file($file, {append => 1, binmode => ':raw'}, $data);
        ok($res, "write_file - append and binmode opt - $data_length");
        my $bin = read_file($file, 'binmode' => ':raw');
        is($bin, $data x 2, "read_file: scalar context binmode opt - $data_length");
    }

    { # append and write - binmode :raw opt
        my $res = append_file($file, {binmode => ':raw'}, $data);
        ok($res, "append_file - binmode opt - $data_length");
        my $bin = read_file( $file, binmode => ':raw');
        is($bin, $data x 3, "read_file: scalar context binmode opt - $data_length");
    }
}
File-Slurp-9999.32/t/paragraph.t0000644000175000017500000000255313363077605017062 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path);

use File::Slurp qw(read_file write_file);
use Test::More;


my $file = temp_file_path();

my @text_data = (
	[],
	[ 'a' x 8 ],
	[ "\n" x 5 ],
	[ map( "aaaaaaaa\n\n", 1 .. 3 ) ],
	[ map( "aaaaaaaa\n\n", 1 .. 3 ), 'aaaaaaaa' ],
 	[ map( "aaaaaaaa" . ( "\n"  x (2 + rand 3) ), 1 .. 100 ) ],
 	[ map( "aaaaaaaa" . ( "\n"  x (2 + rand 3) ), 1 .. 100 ), 'aaaaaaaa' ],
	[],
) ;

plan( tests => 3 * @text_data ) ;

#print "# text slurp\n" ;

foreach my $data ( @text_data ) {

	test_text_slurp( $data ) ;
}


unlink $file ;

exit ;

sub test_text_slurp {

	my( $data_ref ) = @_ ;

	my @data_lines = @{$data_ref} ;
	my $data_text = join( '', @data_lines ) ;

	local( $/ ) = '' ;

	my $err = write_file( $file, $data_text ) ;
	ok( $err, 'write_file - ' . length $data_text ) ;


	my @array = read_file( $file ) ;
	ok( eq_array( \@array, \@data_lines ),
			'array read_file - ' . length $data_text ) ;

	print "READ:\n", map( "[$_]\n", @array ),
		 "EXP:\n", map( "[$_]\n", @data_lines )
			unless eq_array( \@array, \@data_lines ) ;

 	my $array_ref = read_file( $file, array_ref => 1 ) ;
	ok( eq_array( $array_ref, \@data_lines ),
 			'array ref read_file - ' . length $data_text ) ;

	return ;
}
File-Slurp-9999.32/t/01-error_read_file.t0000644000175000017500000001444413355535337020462 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path trap_function trap_function_list_context);

# all three of these names are synonyms
use File::Slurp qw(rf slurp read_file);
use Test::More;

plan tests => 54;

# possible failure points:
# 1. Can't open file due to bad path/permissions/whatever
#    - easily simulated by asking the read_file function to open a file that
#      doesn't exist, and is nested far enough in a path that it can't be
#      created. /tmp exists, but opening /tmp/fake/path/whatever/file will fail

# each of the above cases should be tested in all three failure modes:
# 1. quiet (no warnings, exceptions, or content)
# 2. carp (warnings, no exceptions, no content) - has a problem in list context
# 3. croak (an exception, no warnings, no content)

# each of those scenarios should also be tested in list context (ugh, wantarray)

my $file = temp_file_path('gimme a nonexistent path');

# read_file errors
{
    my ($res, $warn, $err) = trap_function(\&read_file, $file, err_mode => 'quiet');
    ok(!$warn, 'read_file: bad path, quiet - no warn!');
    ok(!$err, 'read_file: bad path, quiet - no exception!');
    ok(!$res, 'read_file: bad path, quiet - no content!');
    ($res, $warn, $err) = trap_function(\&read_file, $file, err_mode => 'carp');
    ok($warn, 'read_file: bad path, carp - got warn!');
    ok(!$err, 'read_file: bad path, carp - no exception!');
    ok(!$res, 'read_file: bad path, carp - no content!');
    ($res, $warn, $err) = trap_function(\&read_file, $file, err_mode => 'croak');
    ok(!$warn, 'read_file: bad path, croak - no warn!');
    ok($err, 'read_file: bad path, croak - got exception!');
    ok(!$res, 'read_file: bad path, croak - no content!');

    # same thing in list context
    ($res, $warn, $err) = trap_function_list_context(\&read_file, $file, err_mode => 'quiet');
    ok(!$warn, 'read_file: bad path, list context, quiet - no warn!');
    ok(!$err, 'read_file: bad path, list context, quiet - no exception!');
    ok(!@{$res}, 'read_file: bad path, list context, quiet - no content!');
    ($res, $warn, $err) = trap_function_list_context(\&read_file, $file, err_mode => 'carp');
    ok($warn, 'read_file: bad path, list context, carp - got warn!');
    ok(!$err, 'read_file: bad path, list context, carp - no exception!');
    # I hate this decision to dump undef on the list. WHY OH WHY?!?!?!?!?!?!
    ok(@{$res}==1 && !defined($res->[0]), 'read_file: bad path, list context, carp - no content!');
    ($res, $warn, $err) = trap_function_list_context(\&read_file, $file, err_mode => 'croak');
    ok(!$warn, 'read_file: bad path, list context, croak - no warn!');
    ok($err, 'read_file: bad path, list context, croak - got exception!');
    ok(!@{$res}, 'read_file: bad path, list context, croak - no content!');
}

# rf errors
{
    my ($res, $warn, $err) = trap_function(\&rf, $file, err_mode => 'quiet');
    ok(!$warn, 'rf: bad path, quiet - no warn!');
    ok(!$err, 'rf: bad path, quiet - no exception!');
    ok(!$res, 'rf: bad path, quiet - no content!');
    ($res, $warn, $err) = trap_function(\&rf, $file, err_mode => 'carp');
    ok($warn, 'rf: bad path, carp - got warn!');
    ok(!$err, 'rf: bad path, carp - no exception!');
    ok(!$res, 'rf: bad path, carp - no content!');
    ($res, $warn, $err) = trap_function(\&rf, $file, err_mode => 'croak');
    ok(!$warn, 'rf: bad path, croak - no warn!');
    ok($err, 'rf: bad path, croak - got exception!');
    ok(!$res, 'rf: bad path, croak - no content!');

    # same thing in list context
    ($res, $warn, $err) = trap_function_list_context(\&rf, $file, err_mode => 'quiet');
    ok(!$warn, 'rf: bad path, list context, quiet - no warn!');
    ok(!$err, 'rf: bad path, list context, quiet - no exception!');
    ok(!@{$res}, 'rf: bad path, list context, quiet - no content!');
    ($res, $warn, $err) = trap_function_list_context(\&rf, $file, err_mode => 'carp');
    ok($warn, 'rf: bad path, list context, carp - got warn!');
    ok(!$err, 'rf: bad path, list context, carp - no exception!');
    # I hate this decision to dump undef on the list. WHY OH WHY?!?!?!?!?!?!
    ok(@{$res}==1 && !defined($res->[0]), 'rf: bad path, list context, carp - no content!');
    ($res, $warn, $err) = trap_function_list_context(\&rf, $file, err_mode => 'croak');
    ok(!$warn, 'rf: bad path, list context, croak - no warn!');
    ok($err, 'rf: bad path, list context, croak - got exception!');
    ok(!@{$res}, 'rf: bad path, list context, croak - no content!');
}

# slurp errors
{
    my ($res, $warn, $err) = trap_function(\&slurp, $file, err_mode => 'quiet');
    ok(!$warn, 'slurp: bad path, quiet - no warn!');
    ok(!$err, 'slurp: bad path, quiet - no exception!');
    ok(!$res, 'slurp: bad path, quiet - no content!');
    ($res, $warn, $err) = trap_function(\&slurp, $file, err_mode => 'carp');
    ok($warn, 'slurp: bad path, carp - got warn!');
    ok(!$err, 'slurp: bad path, carp - no exception!');
    ok(!$res, 'slurp: bad path, carp - no content!');
    ($res, $warn, $err) = trap_function(\&slurp, $file, err_mode => 'croak');
    ok(!$warn, 'slurp: bad path, croak - no warn!');
    ok($err, 'slurp: bad path, croak - got exception!');
    ok(!$res, 'slurp: bad path, croak - no content!');

    # same thing in list context
    ($res, $warn, $err) = trap_function_list_context(\&slurp, $file, err_mode => 'quiet');
    ok(!$warn, 'slurp: bad path, list context, quiet - no warn!');
    ok(!$err, 'slurp: bad path, list context, quiet - no exception!');
    ok(!@{$res}, 'slurp: bad path, list context, quiet - no content!');
    ($res, $warn, $err) = trap_function_list_context(\&slurp, $file, err_mode => 'carp');
    ok($warn, 'slurp: bad path, list context, carp - got warn!');
    ok(!$err, 'slurp: bad path, list context, carp - no exception!');
    # I hate this decision to dump undef on the list. WHY OH WHY?!?!?!?!?!?!
    ok(@{$res}==1 && !defined($res->[0]), 'slurp: bad path, list context, carp - no content!');
    ($res, $warn, $err) = trap_function_list_context(\&slurp, $file, err_mode => 'croak');
    ok(!$warn, 'slurp: bad path, list context, croak - no warn!');
    ok($err, 'slurp: bad path, list context, croak - got exception!');
    ok(!@{$res}, 'slurp: bad path, list context, croak - no content!');
}
File-Slurp-9999.32/t/no_clobber.t0000644000175000017500000000202713363077605017215 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path trap_function);

use File::Slurp;
use Test::More;

plan(tests => 6);

my $file = temp_file_path();

my $data = <1}, $data);
    ok($res, 'write_file: no_clobber opt - new file');
    ok(!$warn, 'write_file: no_clobber opt - new file - no warnings!');
    ok(!$err, 'write_file: no_clobber opt - new file - no exceptions!');
}

{
    my ($res, $warn, $err) = trap_function(\&write_file, $file, {no_clobber=>1, err_mode=>'quiet'}, $data);
    ok(!$res, 'write_file: no_clobber, err_mode quiet opts - existing file - no added content');
    ok(!$warn, 'write_file: no_clobber, err_mode quiet opts - existing file - no warnings!');
    ok(!$err, 'write_file: no_clobber, err_mode quiet opts - existing file - no exceptions!');
}

unlink $file ;
File-Slurp-9999.32/t/data_section.t0000644000175000017500000000256413363077605017554 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Spec ();
use File::Slurp;
use File::Temp qw(tempfile);
use IO::Handle ();
use POSIX qw( :fcntl_h ) ;
use Test::More;

plan tests => 9;

# get the current position (BYTES)_
my $data_seek = tell(\*DATA);
ok($data_seek, 'tell: find position of __DATA__');

# get the baseline to test against
my @data_lines = ;
ok(@data_lines, 'readfile<>: list context, joined - grabbed __DATA__');
my $data_text = join '', @data_lines;
ok($data_text, 'Got a good baseline text');

# seek back to that inital BYTES position
my $seek = seek(\*DATA, $data_seek, 0) || die "seek $!" ;
ok($seek, 'seek: Move back to original __DATA__ position');

# first slurp in the text
my $slurp_text = read_file(\*DATA);
ok($slurp_text, 'read_file: scalar context - grabbed __DATA__');
is($slurp_text, $data_text, 'scalar read matches baseline');

# seek back to that inital BYTES position
$seek = seek(\*DATA, $data_seek, 0) || die "seek $!" ;
ok($seek, 'seek: Move back to original __DATA__ position');

# first slurp in the lines
my @slurp_lines = read_file(\*DATA);
ok(@slurp_lines, 'read_file: list context - grabbed __DATA__');
is_deeply(\@slurp_lines, \@data_lines, 'list read matches baseline');

exit();

__DATA__
line one
second line
more lines
still more

enough lines

we can't test long handle slurps from DATA since i would have to type
too much stuff

so we will stop here
File-Slurp-9999.32/t/stdin.t0000644000175000017500000000075413363077605016237 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');

use File::Slurp qw(read_file write_file);
use Test::More;

plan tests => 6;

my $data = < 1;

use ExtUtils::MakeMaker;
use File::Spec;

# from $version::LAX
my $lax_version_re =
    qr/(?: undef | (?: (?:[0-9]+) (?: \. | (?:\.[0-9]+) (?:_[0-9]+)? )?
            |
            (?:\.[0-9]+) (?:_[0-9]+)?
        ) | (?:
            v (?:[0-9]+) (?: (?:\.[0-9]+)+ (?:_[0-9]+)? )?
            |
            (?:[0-9]+)? (?:\.[0-9]+){2,} (?:_[0-9]+)?
        )
    )/x;

# hide optional CPAN::Meta modules from prereq scanner
# and check if they are available
my $cpan_meta = "CPAN::Meta";
my $cpan_meta_pre = "CPAN::Meta::Prereqs";
my $HAS_CPAN_META = eval "require $cpan_meta; $cpan_meta->VERSION('2.120900')" && eval "require $cpan_meta_pre"; ## no critic

# Verify requirements?
my $DO_VERIFY_PREREQS = 1;

sub _max {
    my $max = shift;
    $max = ( $_ > $max ) ? $_ : $max for @_;
    return $max;
}

sub _merge_prereqs {
    my ($collector, $prereqs) = @_;

    # CPAN::Meta::Prereqs object
    if (ref $collector eq $cpan_meta_pre) {
        return $collector->with_merged_prereqs(
            CPAN::Meta::Prereqs->new( $prereqs )
        );
    }

    # Raw hashrefs
    for my $phase ( keys %$prereqs ) {
        for my $type ( keys %{ $prereqs->{$phase} } ) {
            for my $module ( keys %{ $prereqs->{$phase}{$type} } ) {
                $collector->{$phase}{$type}{$module} = $prereqs->{$phase}{$type}{$module};
            }
        }
    }

    return $collector;
}

my @include = qw(

);

my @exclude = qw(

);

# Add static prereqs to the included modules list
my $static_prereqs = do './t/00-report-prereqs.dd';

# Merge all prereqs (either with ::Prereqs or a hashref)
my $full_prereqs = _merge_prereqs(
    ( $HAS_CPAN_META ? $cpan_meta_pre->new : {} ),
    $static_prereqs
);

# Add dynamic prereqs to the included modules list (if we can)
my ($source) = grep { -f } 'MYMETA.json', 'MYMETA.yml';
my $cpan_meta_error;
if ( $source && $HAS_CPAN_META
    && (my $meta = eval { CPAN::Meta->load_file($source) } )
) {
    $full_prereqs = _merge_prereqs($full_prereqs, $meta->prereqs);
}
else {
    $cpan_meta_error = $@;    # capture error from CPAN::Meta->load_file($source)
    $source = 'static metadata';
}

my @full_reports;
my @dep_errors;
my $req_hash = $HAS_CPAN_META ? $full_prereqs->as_string_hash : $full_prereqs;

# Add static includes into a fake section
for my $mod (@include) {
    $req_hash->{other}{modules}{$mod} = 0;
}

for my $phase ( qw(configure build test runtime develop other) ) {
    next unless $req_hash->{$phase};
    next if ($phase eq 'develop' and not $ENV{AUTHOR_TESTING});

    for my $type ( qw(requires recommends suggests conflicts modules) ) {
        next unless $req_hash->{$phase}{$type};

        my $title = ucfirst($phase).' '.ucfirst($type);
        my @reports = [qw/Module Want Have/];

        for my $mod ( sort keys %{ $req_hash->{$phase}{$type} } ) {
            next if $mod eq 'perl';
            next if grep { $_ eq $mod } @exclude;

            my $file = $mod;
            $file =~ s{::}{/}g;
            $file .= ".pm";
            my ($prefix) = grep { -e File::Spec->catfile($_, $file) } @INC;

            my $want = $req_hash->{$phase}{$type}{$mod};
            $want = "undef" unless defined $want;
            $want = "any" if !$want && $want == 0;

            my $req_string = $want eq 'any' ? 'any version required' : "version '$want' required";

            if ($prefix) {
                my $have = MM->parse_version( File::Spec->catfile($prefix, $file) );
                $have = "undef" unless defined $have;
                push @reports, [$mod, $want, $have];

                if ( $DO_VERIFY_PREREQS && $HAS_CPAN_META && $type eq 'requires' ) {
                    if ( $have !~ /\A$lax_version_re\z/ ) {
                        push @dep_errors, "$mod version '$have' cannot be parsed ($req_string)";
                    }
                    elsif ( ! $full_prereqs->requirements_for( $phase, $type )->accepts_module( $mod => $have ) ) {
                        push @dep_errors, "$mod version '$have' is not in required range '$want'";
                    }
                }
            }
            else {
                push @reports, [$mod, $want, "missing"];

                if ( $DO_VERIFY_PREREQS && $type eq 'requires' ) {
                    push @dep_errors, "$mod is not installed ($req_string)";
                }
            }
        }

        if ( @reports ) {
            push @full_reports, "=== $title ===\n\n";

            my $ml = _max( map { length $_->[0] } @reports );
            my $wl = _max( map { length $_->[1] } @reports );
            my $hl = _max( map { length $_->[2] } @reports );

            if ($type eq 'modules') {
                splice @reports, 1, 0, ["-" x $ml, "", "-" x $hl];
                push @full_reports, map { sprintf("    %*s %*s\n", -$ml, $_->[0], $hl, $_->[2]) } @reports;
            }
            else {
                splice @reports, 1, 0, ["-" x $ml, "-" x $wl, "-" x $hl];
                push @full_reports, map { sprintf("    %*s %*s %*s\n", -$ml, $_->[0], $wl, $_->[1], $hl, $_->[2]) } @reports;
            }

            push @full_reports, "\n";
        }
    }
}

if ( @full_reports ) {
    diag "\nVersions for all modules listed in $source (including optional ones):\n\n", @full_reports;
}

if ( $cpan_meta_error || @dep_errors ) {
    diag "\n*** WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING ***\n";
}

if ( $cpan_meta_error ) {
    my ($orig_source) = grep { -f } 'MYMETA.json', 'MYMETA.yml';
    diag "\nCPAN::Meta->load_file('$orig_source') failed with: $cpan_meta_error\n";
}

if ( @dep_errors ) {
    diag join("\n",
        "\nThe following REQUIRED prerequisites were not satisfied:\n",
        @dep_errors,
        "\n"
    );
}

pass;

# vim: ts=4 sts=4 sw=4 et:
File-Slurp-9999.32/t/inode.t0000644000175000017500000000157013363077605016211 0ustar  cwhitenercwhiteneruse strict;
use warnings;
use IO::Handle ();

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path);

use File::Slurp qw(read_file write_file);

use Test::More;
BEGIN {
    if ($^O eq 'MSWin32') {
        plan skip_all => 'skip inode test on windows';
        exit;
    }
}
plan tests => 2;

my $data = < 1}, $data);
$inode_num2 = (stat $file)[1];

#print "I1 $inode_num I2 $inode_num2\n" ;

isnt($inode_num, $inode_num2, 'different inode');

unlink $file;
unlink "$file.$$";
File-Slurp-9999.32/t/write_file_win32.t0000644000175000017500000000127613363077605020271 0ustar  cwhitenercwhiteneruse strict;
use warnings;
use IO::Handle ();

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');

use FileSlurpTest qw(temp_file_path trap_function);

use File::Slurp qw(write_file read_file);
use Test::More ;

plan tests => 1;

sub simple_write_file {
    open my $fh, ">", $_[0] or die "Couldn't open $_[0] for write: $!";
    $fh->print($_[1]);
}

sub newline_size {
    my ($code) = @_;

    my $file = temp_file_path();

    local $\ = '';
    $code->($file, "\n" x 3);

    my $size = -s $file;

    unlink $file;

    return $size;
}

is(newline_size(\&write_file), newline_size(\&simple_write_file), 'newline');
File-Slurp-9999.32/t/error.t0000644000175000017500000001135313440747315016242 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTestOverride qw(trap_function_override_core);
use FileSlurpTest qw(temp_file_path trap_function);

use File::Slurp qw( :all prepend_file edit_file );
use Test::More;

plan tests => 30;

my $is_win32 = $^O =~ /cygwin|win32/i ;
# older EUMMs turn this on. We don't want to emit warnings.
# also, some of our CORE function overrides emit warnings. Silence those.
local $^W;

# write_file open error - no sysopen
{
    my $file = temp_file_path('gimme a bad one');
    my ($res, $warn, $err) = trap_function_override_core('sysopen', \&write_file, $file);
    ok(!$warn, 'write_file: open error, no sysopen - no warning!');
    like($err, qr/open/, 'write_file: open error, no sysopen - got exception!');
    ok(!$res, 'write_file: open error, no sysopen - no content!');

}
# write_file write error - no syswrite
SKIP: {
    skip "Skip these tests because mocking write failures can't happen", 3;
    my $file = temp_file_path();
    my ($res, $warn, $err) = trap_function_override_core('syswrite', \&write_file, $file, '');
    ok(!$warn, 'write_file: write error, no syswrite - no warning!');
    like($err, qr/write/, 'write_file: write error, no syswrite - got exception!');
    ok(!$res, 'write_file: write error, no syswrite - no content!');
    unlink $file;
};
# atomic rename error
SKIP: {
    skip "Atomic rename on Win32 is useless", 3 if $is_win32;
    my $file = temp_file_path();
    my ($res, $warn, $err) = trap_function_override_core('rename', \&write_file, $file, {atomic => 1}, '');
    ok(!$warn, 'write_file: atomic rename error, no rename - no warning!');
    like($err, qr/rename/, 'write_file: atomic renamed error, no rename - got exception!');
    ok(!$res, 'write_file: atomic rename error, no rename - no content!');
    unlink $file;
    unlink "$file.$$";
}
# read_dir opendir error
{
    my $file = temp_file_path('gimme a bad one');
    my ($res, $warn, $err) = trap_function(\&read_dir, $file);
    ok(!$warn, 'read_dir: opendir error - no warning!');
    like($err, qr/open/, 'read_dir: opendir error - got exception!');
    ok(!$res, 'read_dir: opendir error - no content!');
}
# prepend_file read error
{
    my $file = temp_file_path('gimme a bad one');
    my ($res, $warn, $err) = trap_function(\&prepend_file, $file);
    ok(!$warn, 'prepend_file: read error - no warning!');
    like($err, qr/read_file/, 'prepend_file: read error - got exception!');
    ok(!$res, 'prepend_file: read error - no content!');
}
# prepend_file write error
SKIP: {
    skip "Skip these tests because mocking write failures can't happen", 3;
    my $file = temp_file_path();
    write_file($file, '');
    my ($res, $warn, $err) = trap_function_override_core('syswrite', \&prepend_file, $file, '');
    ok(!$warn, 'prepend_file: opendir error - no warning!');
    like($err, qr/write_file/, 'prepend_file: opendir error - got exception!');
    ok(!$res, 'prepend_file: opendir error - no content!');
    unlink $file;
    unlink "$file.$$";
};
# edit_file read error
{
    my $file = temp_file_path();
    my ($res, $warn, $err) = trap_function(\&edit_file, sub {}, $file);
    ok(!$warn, 'edit_file: read error - no warning!');
    like($err, qr/read_file/, 'edit_file: read error - got exception!');
    ok(!$res, 'edit_file: read error - no content!');
    unlink $file;
}
# edit_file write error
SKIP: {
    skip "Skip these tests because mocking write failures can't happen", 3;
    my $file = temp_file_path();
    write_file($file, '');
    my ($res, $warn, $err) = trap_function_override_core('syswrite', \&edit_file, sub {}, $file);
    ok(!$warn, 'edit_file: write error - no warning!');
    like($err, qr/write_file/, 'edit_file: write error - got exception!');
    ok(!$res, 'edit_file: write error - no content!');
    unlink $file;
    unlink "$file.$$";
};
# edit_file_lines read error
{
    my $file = temp_file_path();
    my ($res, $warn, $err) = trap_function(\&edit_file_lines, sub {}, $file);
    ok(!$warn, 'edit_file_lines: read error - no warning!');
    like($err, qr/read_file/, 'edit_file_lines: read error - got exception!');
    ok(!$res, 'edit_file_lines: read error - no content!');
    unlink $file;
}
# edit_file write error
SKIP: {
    skip "Skip these tests because mocking write failures can't happen", 3;
    my $file = temp_file_path();
    write_file($file, '');
    my ($res, $warn, $err) = trap_function_override_core('syswrite', \&edit_file_lines, sub {}, $file);
    ok(!$warn, 'edit_file_lines: write error - no warning!');
    like($err, qr/write_file/, 'edit_file_lines: write error - got exception!');
    ok(!$res, 'edit_file_lines: write error - no content!');
    unlink $file;
    unlink "$file.$$";
};
File-Slurp-9999.32/t/data_glob.t0000644000175000017500000000307313371166240017020 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(trap_function);
use File::Slurp qw(read_file);

# a package with a __DATA__ section
use FSGlobby ();

use Scalar::Util qw(blessed);
use Symbol qw(qualify qualify_to_ref);
use Test::More;

plan tests => 10;

my $obj = FSGlobby->new();
ok(defined $obj, "Constructor returned defined object");
isa_ok( $obj, 'FSGlobby');

my $symbolname = qualify("DATA", blessed $obj);
is($symbolname, 'FSGlobby::DATA', "Symbol::qualify(): Got expected symbol name");

my $glob = qualify_to_ref("DATA", blessed $obj);
is(ref($glob), 'GLOB', "Symbol::qualify_to_ref():  Got a glob");

my @lines = read_file($glob, {chomp => 1});
my $expected_lines = 8;
is(scalar @lines, $expected_lines, "Got $expected_lines lines in file");
is($lines[0], 'File:', "Got expected first line");
is($lines[$expected_lines - 1], 'Last-Updated:', "Got expected last line");
my %lines_seen;
map { $lines_seen{$_}++ } @lines;
is($lines_seen{$lines[0]}, 1, "First line seen exactly once");
is($lines_seen{$lines[$expected_lines - 1]}, 1, "Last line seen exactly once");

# read a second time
# this test exists as yet another regression prevention test because certain
# modules like CPAN::Index::API make use of what should be considered a bug
# where sysread was in use, not altering tell and the __DATA__ cursor was good
# for another read.
my @second_lines = read_file($glob, {chomp => 1});
is_deeply(\@second_lines, \@lines, 'multiple reads the same');
File-Slurp-9999.32/t/lib/0000755000175000017500000000000013676754373015504 5ustar  cwhitenercwhitenerFile-Slurp-9999.32/t/lib/FileSlurpTest.pm0000644000175000017500000000275613356734371020610 0ustar  cwhitenercwhitenerpackage FileSlurpTest;

use strict;
use warnings;
use Exporter qw(import);
use IO::Handle ();
use File::Spec ();
use File::Temp qw(tempfile);

use File::Slurp ();

our @EXPORT_OK = qw(
    IS_WSL temp_file_path trap_function trap_function_list_context
);

sub IS_WSL() {
  if ($^O eq 'linux') {
    require POSIX;
    return 1 if (POSIX::uname())[2] =~ /windows/i;
  }
}

sub temp_file_path {
    my ($pick_nonsense_path) = @_;

    # older EUMMs turn this on. We don't want to emit warnings.
    # also, some of our CORE function overrides emit warnings. Silence those.
    local $^W;

    my $file;
    if ($pick_nonsense_path) {
        $file = File::Spec->catfile(File::Spec->tmpdir, 'super', 'bad', 'file-slurp', 'path');
    }
    else {
        (undef, $file) = tempfile('tempXXXXX', DIR => File::Spec->tmpdir, OPEN => 0);
    }
    return $file;
}

sub trap_function {
    my ($function, @args) = @_;
    my $res;
    my $warn;
    my $err = do { # catch
        local $@;
        local $SIG{__WARN__} = sub {$warn = join '', @_};
        eval { # try
            $res = $function->(@args);
            1;
        };
        $@;
    };
    return ($res, $warn, $err);
}

sub trap_function_list_context {
    my ($function, @args) = @_;
    my @res;
    my $warn;
    my $err = do { # catch
        local $@;
        local $SIG{__WARN__} = sub {$warn = join '', @_};
        eval { # try
            @res = $function->(@args);
            1;
        };
        $@;
    };
    return (\@res, $warn, $err);
}

1;
File-Slurp-9999.32/t/lib/FileSlurpTestOverride.pm0000644000175000017500000000276413367600703022300 0ustar  cwhitenercwhitenerpackage FileSlurpTestOverride;

use Exporter qw(import);

# older EUMMs turn this on. We don't want to emit warnings.
# also, some of our CORE function overrides emit warnings. Silence those.
local $^W;

BEGIN {
    *CORE::GLOBAL::rename = sub($$) { my ($o, $n) = @_; CORE::rename($o, $n) };
    # we only use the 4-arg version of syswrite
    *CORE::GLOBAL::syswrite = sub($$;$$) { my ($h, $buff, $l, $o) = @_; return CORE::syswrite($h, $buff, $l, $o); };
    # We use the 3 and 4-arg form of sysread.
    *CORE::GLOBAL::sysread = sub($$$;$) { my( $h, $b, $s, $o ) = @_; CORE::sysread $h, $b, $s, $o };
            # sub($$$;$) { my( $h, $b, $s, $o ) = @_; CORE::sysread $h, $b, $s, $o } ;
    # We use the 3 and 4-arg form of sysopen
    *CORE::GLOBAL::sysopen = sub($$$;$) { my( $h, $n, $m, $p ) = @_; CORE::sysopen $h, $n, $m, $p };
    # sub(*$$;$) {
    #     my ($h, $n, $m, $p) = @_;
    #     return CORE::sysopen($h, $n, $m, $p) if defined $p;
    #     CORE::sysopen($h, $n, $m);
    # };
}


our @EXPORT_OK = qw(
    trap_function_override_core
);

sub trap_function_override_core {
    my ($core, $function, @args) = @_;

    my $res;
    my $warn;
    my $err = do { # catch
        no strict 'refs';
        no warnings;
        local $^W;
        local $@;
        local $SIG{__WARN__} = sub {$warn = join '', @_};
        local *{"CORE::GLOBAL::$core"} = sub {};
        eval { # try
            $res = $function->(@args);
            1;
        };
        $@;
    };

    return ($res, $warn, $err);
}

1;
File-Slurp-9999.32/t/lib/FSGlobby.pm0000644000175000017500000000026613371162021017464 0ustar  cwhitenercwhitenerpackage FSGlobby;

sub new {
    my $class = shift;
    return bless {}, $class;
}

1;

__DATA__
File:
URL:
Description:
Columns:
Intended-For:
Written-By:
Line-Count:
Last-Updated:
File-Slurp-9999.32/t/handle.t0000644000175000017500000000170713676214155016350 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Slurp qw(read_file write_file);

use IO::Handle ();
use Socket;
use Symbol;
use Test::More;

my @pipe_data = (
    '',
    'abc',
    'abc' x 100,
    'abc' x 1000,
);

plan tests => scalar(@pipe_data);

foreach my $data ( @pipe_data ) {
    my $size = length( $data );
    my $read_fh = gensym;
    my $write_fh = gensym;
    my $value;
    my $error;
    { # catch block
        local $@;
        $error = $@ || 'Error' unless eval {
            $value = socketpair($read_fh, $write_fh, AF_UNIX, SOCK_STREAM, PF_UNSPEC);
            1;
        }; # try
    }
    SKIP: {
        skip "Can't use socketpair", 1 unless $value;
        if (fork()) {
            $write_fh->close();
            my $res = read_file($read_fh);
            is($res, $data, "read_file: socketpair of $size bytes");
        }
        else {
            $read_fh->close();
            write_file($write_fh, $data);
            exit();
        }
    };
}
File-Slurp-9999.32/t/append_null.t0000644000175000017500000000106513440747315017411 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path trap_function);

use File::Slurp;
use Test::More;

plan(tests => 3);

my $file = temp_file_path();
my $data = <catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path trap_function);

use File::Slurp qw(read_file write_file edit_file);
use Test::More;

plan tests => 20;

my $file = 'edit_file';
my $existing_data = <1,bar=>2});
    ok($res, 'edit_file: edit line, invalid options: got response!');
    ok(!$warn, 'edit_file: edit line, invalid options: no warnings!');
    ok(!$err, 'edit_file: edit line, invalid options: no exceptions!');
    my $expected = join("\n", ('line 1000', 'line 2000', 'more', ''));
    is(read_file($file), $expected, 'edit_file: edit line, invalid options: contents are right');
    unlink $file;
}
{
    my $file = temp_file_path();
    write_file($file, $existing_data);
    my ($res, $warn, $err) = trap_function(\&edit_file, sub {s/([0-9])/${1}000/g}, $file, {foo=>1,bar=>2, binmode=>':raw'});
    ok($res, 'edit_file: edit line, invalid options, binmode: got response!');
    # this should get fixed
    SKIP: {
        skip "Binmode is bad news bears with sysread on Perl 5.30+", 1;
        ok(!$warn, 'edit_file: edit line, invalid options, binmode: no warnings!');
    }
    ok(!$err, 'edit_file: edit line, invalid options, binmode: no exceptions!');
    my $expected = join("\n", ('line 1000', 'line 2000', 'more', ''));
    is(read_file($file), $expected, 'edit_file: edit line, invalid options, binmode: contents are right');
    unlink $file;
}
{
    my $file = temp_file_path();
    write_file($file, $existing_data);
    my ($res, $warn, $err) = trap_function(\&edit_file, sub {s/([0-9])/${1}000/g}, $file, {foo=>1,bar=>2, err_mode=>'quiet'});
    ok($res, 'edit_file: edit line, invalid options, err_mode: got response!');
    ok(!$warn, 'edit_file: edit line, invalid options, err_mode: no warnings!');
    ok(!$err, 'edit_file: edit line, invalid options, err_mode: no exceptions!');
    my $expected = join("\n", ('line 1000', 'line 2000', 'more', ''));
    is(read_file($file), $expected, 'edit_file: edit line, invalid options, err_mode: contents are right');
    unlink $file;
}
File-Slurp-9999.32/t/pseudo.t0000644000175000017500000000101613355535337016407 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path);

use File::Slurp qw(read_file);
use Test::More;

plan tests => 1;

my $proc_file = "/proc/$$/auxv";

SKIP: {
    skip "Can't find pseudo file: $proc_file", 1 unless -r $proc_file;
    my $data_do = do{ local( @ARGV, $/ ) = $proc_file; <> };
    my $data_slurp = read_file($proc_file);
    is($data_do, $data_slurp, 'pseudo');
}
File-Slurp-9999.32/t/01-error_edit_file.t0000644000175000017500000000415113355535337020466 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path trap_function);

# both of these names are synonyms
use File::Slurp qw(ef edit_file);
use Test::More;

plan tests => 18;

# this one intentionally doesn't exist on a couple of paths. can't be created.
my $file = temp_file_path('gimme a nonexistent path');

# edit_file errors
{
    my ($res, $warn, $err) = trap_function(\&edit_file, sub { s/foo/bar/g }, $file, {err_mode => 'quiet'});
    ok(!$warn, 'edit_file: err_mode opt quiet - no warn!');
    ok(!$err, 'edit_file: err_mode opt quiet - no exception!');
    ok(!$res, 'edit_file: err_mode opt quiet - no content!');
    ($res, $warn, $err) = trap_function(\&edit_file, sub { s/foo/bar/g }, $file, {err_mode => 'carp'});
    ok($warn, 'edit_file: err_mode opt carp - got warn!');
    ok(!$err, 'edit_file: err_mode opt carp - no exception!');
    ok(!$res, 'edit_file: err_mode opt carp - no content!');
    ($res, $warn, $err) = trap_function(\&edit_file, sub { s/foo/bar/g }, $file, {err_mode => 'croak'});
    ok(!$warn, 'edit_file: err_mode opt croak - no warn!');
    ok($err, 'edit_file: err_mode opt croak - got exception!');
    ok(!$res, 'edit_file: err_mode opt croak - no content!');
}

# ef errors
{
    my ($res, $warn, $err) = trap_function(\&ef, sub { s/foo/bar/g }, $file, {err_mode => 'quiet'});
    ok(!$warn, 'ef: err_mode opt quiet - no warn!');
    ok(!$err, 'ef: err_mode opt quiet - no exception!');
    ok(!$res, 'ef: err_mode opt quiet - no content!');
    ($res, $warn, $err) = trap_function(\&ef, sub { s/foo/bar/g }, $file, {err_mode => 'carp'});
    ok($warn, 'ef: err_mode opt carp - got warn!');
    ok(!$err, 'ef: err_mode opt carp - no exception!');
    ok(!$res, 'ef: err_mode opt carp - no content!');
    ($res, $warn, $err) = trap_function(\&ef, sub { s/foo/bar/g }, $file, {err_mode => 'croak'});
    ok(!$warn, 'ef: err_mode opt croak - no warn!');
    ok($err, 'ef: err_mode opt croak - got exception!');
    ok(!$res, 'ef: err_mode opt croak - no content!');
}
File-Slurp-9999.32/t/slurp.t0000644000175000017500000000070413363077605016256 0ustar  cwhitenercwhiteneruse strict;
use warnings;

use File::Basename ();
use File::Spec ();
use lib File::Spec->catdir(File::Spec->rel2abs(File::Basename::dirname(__FILE__)), 'lib');
use FileSlurpTest qw(temp_file_path);

use File::Slurp qw(slurp write_file);
use Test::More;

plan tests => 1;

my $data = < 'Older Perl lacking unicode support' if $] < 5.008001;
}

# older EUMMs turn this on. We don't want to emit warnings.
# also, some of our CORE function overrides emit warnings. Silence those.
local $^W;


plan tests => 4;

my $suf = 'utf8';
my $mode = ":$suf";

# euro symbol with \r\n or \n
my $orig_text = "\x{20ac}\n";
my $win_text = "\x{20ac}\015\012";
my $expected_text = $^O eq 'MSWin32' ? $win_text : $orig_text;
my $unicode_length = length $orig_text;

my (undef, $control_file) = tempfile('ctrlXXXXX', DIR => File::Spec->tmpdir, OPEN => 0);
my (undef, $slurp_file) = tempfile('slurpXXXXX', DIR => File::Spec->tmpdir, OPEN => 0);

{ # print to the control file
    open(my $fh, ">$mode", $control_file) or
        die "cannot create control unicode file '$control_file' $!";
    $fh->print($orig_text);
}

my $slurp_utf = read_file( $control_file, binmode => $mode);
is($slurp_utf, $expected_text, "read_file of $mode file");

my $res = write_file($slurp_file, {binmode => $mode}, $orig_text);
ok($res, "write_file: binmode opt");

my $read_length;
{ # read the slurp file
    open(my $fh, "<$mode", $slurp_file) or
        die "cannot open slurp test file '$slurp_file' $!";
    my $read_length = read($fh, my $utf_text, $unicode_length);
    $fh->close();
    is($read_length, $unicode_length, "read lengths match");
    is($utf_text, $orig_text, "write_file of $mode file");
}
unlink($control_file, $slurp_file);
File-Slurp-9999.32/META.yml0000664000175000017500000000242713676754373015753 0ustar  cwhitenercwhitener---
abstract: 'Simple and Efficient Reading/Writing/Modifying of Complete Files'
author:
  - 'Uri Guttman '
build_requires:
  Carp: '0'
  Exporter: '5.57'
  ExtUtils::MakeMaker: '0'
  Fcntl: '0'
  File::Basename: '0'
  File::Spec: '3.01'
  File::Temp: '0'
  IO::Handle: '0'
  POSIX: '0'
  Scalar::Util: '1.00'
  Socket: '0'
  Symbol: '0'
  Test::More: '0'
  overload: '0'
  strict: '0'
  warnings: '0'
configure_requires:
  ExtUtils::MakeMaker: '0'
dynamic_config: 0
generated_by: 'ExtUtils::MakeMaker version 7.44, CPAN::Meta::Converter version 2.150010'
license: perl
meta-spec:
  url: http://module-build.sourceforge.net/META-spec-v1.4.html
  version: '1.4'
name: File-Slurp
no_index:
  directory:
    - t
    - inc
    - xt
requires:
  B: '0'
  Carp: '0'
  Errno: '0'
  Exporter: '5.57'
  Fcntl: '0'
  File::Basename: '0'
  File::Spec: '3.01'
  File::Temp: '0'
  IO::Handle: '0'
  POSIX: '0'
  strict: '0'
  warnings: '0'
resources:
  repository: https://github.com/perhunter/slurp.git
version: '9999.32'
x_contributors:
  - 'Aristotle Pagaltzis '
  - 'Chase Whitener '
  - 'Dan Book '
  - 'Graham Knop '
  - 'James E Keenan '
x_serialization_backend: 'CPAN::Meta::YAML version 0.018'
File-Slurp-9999.32/xt/0000755000175000017500000000000013676754373015126 5ustar  cwhitenercwhitenerFile-Slurp-9999.32/xt/author/0000755000175000017500000000000013676754373016430 5ustar  cwhitenercwhitenerFile-Slurp-9999.32/xt/author/eol.t0000644000175000017500000000172313355535337017366 0ustar  cwhitenercwhiteneruse strict;
use warnings;

# this test was generated with Dist::Zilla::Plugin::Test::EOL 0.19

use Test::More 0.88;
use Test::EOL;

my @files = (
    'lib/File/Slurp.pm',
    't/00-report-prereqs.t',
    't/01-error_edit_file.t',
    't/01-error_edit_file_lines.t',
    't/01-error_prepend_file.t',
    't/01-error_read_dir.t',
    't/01-error_read_file.t',
    't/01-error_write_file.t',
    't/append_null.t',
    't/binmode.t',
    't/data_section.t',
    't/edit_file.t',
    't/error.t',
    't/file_object.t',
    't/handle.t',
    't/inode.t',
    't/large.t',
    't/lib/FileSlurpTest.pm',
    't/lib/FileSlurpTestOverride.pm',
    't/newline.t',
    't/no_clobber.t',
    't/original.t',
    't/paragraph.t',
    't/perms.t',
    't/prepend_file.t',
    't/pseudo.t',
    't/read_dir.t',
    't/slurp.t',
    't/stdin.t',
    't/stringify.t',
    't/tainted.t',
    't/write_file_win32.t',
);

eol_unix_ok($_, { trailing_whitespace => 1 }) foreach @files;
done_testing;
File-Slurp-9999.32/xt/author/pod_coverage.t0000644000175000017500000000031513357526202021231 0ustar  cwhitenercwhitener#!/usr/local/bin/perl

use Test::More;

eval 'use Test::Pod::Coverage 1.04';
plan skip_all =>
	'Test::Pod::Coverage 1.04 required for testing POD coverage' if $@;

all_pod_coverage_ok({ trustme => [], });
File-Slurp-9999.32/xt/author/test-version.t0000644000175000017500000000063713353273047021247 0ustar  cwhitenercwhiteneruse strict;
use warnings;
use Test::More;

# generated by Dist::Zilla::Plugin::Test::Version 1.09
use Test::Version;

my @imports = qw( version_all_ok );

my $params = {
    is_strict      => 0,
    has_version    => 1,
    multiple       => 0,

};

push @imports, $params
    if version->parse( $Test::Version::VERSION ) >= version->parse('1.002');

Test::Version->import(@imports);

version_all_ok;
done_testing;
File-Slurp-9999.32/xt/author/00-compile.t0000644000175000017500000000254013353273047020445 0ustar  cwhitenercwhiteneruse 5.006;
use strict;
use warnings;

# this test was generated with Dist::Zilla::Plugin::Test::Compile 2.058

use Test::More;

plan tests => 2;

my @module_files = (
    'File/Slurp.pm'
);



# no fake home requested

my @switches = (
    -d 'blib' ? '-Mblib' : '-Ilib',
);

use File::Spec;
use IPC::Open3;
use IO::Handle;

open my $stdin, '<', File::Spec->devnull or die "can't open devnull: $!";

my @warnings;
for my $lib (@module_files)
{
    # see L
    my $stderr = IO::Handle->new;

    diag('Running: ', join(', ', map { my $str = $_; $str =~ s/'/\\'/g; q{'} . $str . q{'} }
            $^X, @switches, '-e', "require q[$lib]"))
        if $ENV{PERL_COMPILE_TEST_DEBUG};

    my $pid = open3($stdin, '>&STDERR', $stderr, $^X, @switches, '-e', "require q[$lib]");
    binmode $stderr, ':crlf' if $^O eq 'MSWin32';
    my @_warnings = <$stderr>;
    waitpid($pid, 0);
    is($?, 0, "$lib loaded ok");

    shift @_warnings if @_warnings and $_warnings[0] =~ /^Using .*\bblib/
        and not eval { +require blib; blib->VERSION('1.01') };

    if (@_warnings)
    {
        warn @_warnings;
        push @warnings, @_warnings;
    }
}



is(scalar(@warnings), 0, 'no warnings found')
    or diag 'got warnings: ', ( Test::More->can('explain') ? Test::More::explain(\@warnings) : join("\n", '', @warnings) );
File-Slurp-9999.32/xt/author/pod-spell.t0000644000175000017500000000044613357005305020474 0ustar  cwhitenercwhiteneruse strict;
use warnings;
use Test::More;

# generated by Dist::Zilla::Plugin::Test::PodSpelling 2.007005
use Test::Spelling 0.12;
use Pod::Wordlist;

set_spell_cmd('aspell list');
add_stopwords();
all_pod_files_spelling_ok( qw( bin lib ) );
__DATA__
Guttman
dir
stemsystems
rf
wf
ef
efl
File-Slurp-9999.32/xt/author/pod-syntax.t0000644000175000017500000000025213353273047020704 0ustar  cwhitenercwhitener#!perl
# This file was automatically generated by Dist::Zilla::Plugin::PodSyntaxTests.
use strict; use warnings;
use Test::More;
use Test::Pod 1.41;

all_pod_files_ok();
File-Slurp-9999.32/META.json0000664000175000017500000000433113676754374016120 0ustar  cwhitenercwhitener{
   "abstract" : "Simple and Efficient Reading/Writing/Modifying of Complete Files",
   "author" : [
      "Uri Guttman "
   ],
   "dynamic_config" : 0,
   "generated_by" : "ExtUtils::MakeMaker version 7.44, CPAN::Meta::Converter version 2.150010",
   "license" : [
      "perl_5"
   ],
   "meta-spec" : {
      "url" : "http://search.cpan.org/perldoc?CPAN::Meta::Spec",
      "version" : 2
   },
   "name" : "File-Slurp",
   "no_index" : {
      "directory" : [
         "t",
         "inc",
         "xt"
      ]
   },
   "prereqs" : {
      "build" : {
         "requires" : {
            "ExtUtils::MakeMaker" : "0"
         }
      },
      "configure" : {
         "requires" : {
            "ExtUtils::MakeMaker" : "0"
         }
      },
      "runtime" : {
         "requires" : {
            "B" : "0",
            "Carp" : "0",
            "Errno" : "0",
            "Exporter" : "5.57",
            "Fcntl" : "0",
            "File::Basename" : "0",
            "File::Spec" : "3.01",
            "File::Temp" : "0",
            "IO::Handle" : "0",
            "POSIX" : "0",
            "strict" : "0",
            "warnings" : "0"
         }
      },
      "test" : {
         "requires" : {
            "Carp" : "0",
            "Exporter" : "5.57",
            "Fcntl" : "0",
            "File::Basename" : "0",
            "File::Spec" : "3.01",
            "File::Temp" : "0",
            "IO::Handle" : "0",
            "POSIX" : "0",
            "Scalar::Util" : "1.00",
            "Socket" : "0",
            "Symbol" : "0",
            "Test::More" : "0",
            "overload" : "0",
            "strict" : "0",
            "warnings" : "0"
         }
      }
   },
   "release_status" : "stable",
   "resources" : {
      "repository" : {
         "type" : "git",
         "url" : "https://github.com/perhunter/slurp.git",
         "web" : "https://github.com/perhunter/slurp"
      }
   },
   "version" : "9999.32",
   "x_contributors" : [
      "Aristotle Pagaltzis ",
      "Chase Whitener ",
      "Dan Book ",
      "Graham Knop ",
      "James E Keenan "
   ],
   "x_serialization_backend" : "JSON::PP version 4.04"
}
File-Slurp-9999.32/.mailmap0000644000175000017500000000054513241411005016062 0ustar  cwhitenercwhitener# https://www.kernel.org/pub/software/scm/git/docs/git-shortlog.html#_mapping_authors
Chase Whitener  
Chase Whitener  
Uri Guttman  
Uri Guttman  
Uri Guttman  
File-Slurp-9999.32/Makefile.PL0000644000175000017500000000530213440747315016430 0ustar  cwhitenercwhiteneruse strict;
use warnings;
use ExtUtils::MakeMaker;
use 5.006;

# See lib/ExtUtils/MakeMaker.pm for details of how to influence
# the contents of the Makefile that is written.

my %BuildReqs = (
    "ExtUtils::MakeMaker" => 0,
);
my %ConfigReqs = (
    "ExtUtils::MakeMaker" => 0,
);
my %DevReqs = (
    "Test::Pod" => 0,
    "Test::Pod::Coverage" => 0,
    "Test::Spelling" => 0,
    "Test::Version" => 0,
);
my %TestReqs = (
    "overload" => 0,
    "strict" => 0,
    "warnings" => 0,
    "Carp" => 0,
    'Exporter' => '5.57',
    'Fcntl' => 0,
    "File::Basename" => 0,
    "File::Spec" => '3.01',
    "File::Temp" => 0,
    "IO::Handle" => 0,
    "POSIX" => 0,
    "Scalar::Util" => '1.00', # had tainted()
    "Socket" => 0,
    "Symbol" => 0,
    "Test::More" => 0,
);
my %prereqs = (
    'B' => 0,
    'Carp' => 0,
    'Exporter' => '5.57',
    'Errno' => 0,
    'Fcntl' => 0,
    "File::Basename" => 0,
    "File::Spec" => '3.01',
    "File::Temp" => 0,
    "IO::Handle" => 0,
    'POSIX' => 0,
    "strict" => 0,
    "warnings" => 0,
);

my %WriteMakefileArgs = (
    'NAME' => 'File::Slurp',
    "DISTNAME" => "File-Slurp",
    'LICENSE' => 'perl_5',
    'AUTHOR' => 'Uri Guttman ',
    'VERSION_FROM' => 'lib/File/Slurp.pm',
    'ABSTRACT_FROM' => 'lib/File/Slurp.pm',
    'META_MERGE' => {
        'dynamic_config' => 0,
        'meta-spec' => {version => 2},
        'no_index' => {directory => ['xt']},
        'resources' => {
            repository => {
                type => 'git',
                url  => 'https://github.com/perhunter/slurp.git',
                web  => 'https://github.com/perhunter/slurp',
            },
        },
        'x_contributors' => [
            'Aristotle Pagaltzis ',
            'Chase Whitener ',
            'Dan Book ',
            'Graham Knop ',
            'James E Keenan ',
        ],
    },
    "BUILD_REQUIRES" => \%BuildReqs,
    "CONFIGURE_REQUIRES" => \%ConfigReqs,
    "TEST_REQUIRES" => \%TestReqs,
    "PREREQ_PM" => \%prereqs,
    "test" => {
        "TESTS" => "t/*.t",
    },
);

unless ( eval { ExtUtils::MakeMaker->VERSION('6.63_03') } ) {
    my %fallback = (%prereqs, %TestReqs, %BuildReqs);
    delete $WriteMakefileArgs{TEST_REQUIRES};
    delete $WriteMakefileArgs{BUILD_REQUIRES};
    $WriteMakefileArgs{PREREQ_PM} = \%fallback;
}

delete $WriteMakefileArgs{CONFIGURE_REQUIRES}
  unless eval { ExtUtils::MakeMaker->VERSION('6.52') };

delete $WriteMakefileArgs{META_MERGE}
  unless eval { ExtUtils::MakeMaker->VERSION('6.46') };

delete $WriteMakefileArgs{LICENSE}
  unless eval { ExtUtils::MakeMaker->VERSION('6.31') };

WriteMakefile(%WriteMakefileArgs);
File-Slurp-9999.32/MANIFEST0000644000175000017500000000157313676754374015633 0ustar  cwhitenercwhitener.mailmap
Changes
lib/File/Slurp.pm
Makefile.PL
MANIFEST
MANIFEST.SKIP
META.json			Module meta-data (added by MakeMaker)
README.md
t/00-report-prereqs.t
t/01-error_edit_file.t
t/01-error_edit_file_lines.t
t/01-error_prepend_file.t
t/01-error_read_dir.t
t/01-error_read_file.t
t/01-error_write_file.t
t/append_null.t
t/binmode.t
t/data_glob.t
t/data_section.t
t/edit_file.t
t/error.t
t/file_object.t
t/handle.t
t/inode.t
t/large.t
t/lib/FileSlurpTest.pm
t/lib/FileSlurpTestOverride.pm
t/lib/FSGlobby.pm
t/newline.t
t/no_clobber.t
t/original.t
t/paragraph.t
t/perms.t
t/prepend_file.t
t/pseudo.t
t/read_dir.t
t/slurp.t
t/stdin.t
t/stringify.t
t/tainted.t
t/write_file_win32.t
xt/author/00-compile.t
xt/author/eol.t
xt/author/pod-spell.t
xt/author/pod-syntax.t
xt/author/pod_coverage.t
xt/author/test-version.t
META.yml                                 Module YAML meta-data (added by MakeMaker)
File-Slurp-9999.32/lib/0000755000175000017500000000000013676754373015241 5ustar  cwhitenercwhitenerFile-Slurp-9999.32/lib/File/0000755000175000017500000000000013676754373016120 5ustar  cwhitenercwhitenerFile-Slurp-9999.32/lib/File/Slurp.pm0000644000175000017500000007476513676215256017576 0ustar  cwhitenercwhitenerpackage File::Slurp;

use strict;
use warnings ;

our $VERSION = '9999.32';
$VERSION = eval $VERSION;

use Carp ;
use Exporter qw(import);
use Fcntl qw( :DEFAULT ) ;
use File::Basename ();
use File::Spec;
use File::Temp qw(tempfile);
use IO::Handle ();
use POSIX qw( :fcntl_h ) ;
use Errno ;

my @std_export = qw(
	read_file
	write_file
	overwrite_file
	append_file
	read_dir
) ;

my @edit_export = qw(
	edit_file
	edit_file_lines
) ;

my @abbrev_export = qw(
	rf
	wf
	ef
	efl
) ;

our @EXPORT_OK = (
	@edit_export,
	@abbrev_export,
	qw(
		slurp
		prepend_file
	),
) ;

our %EXPORT_TAGS = (
	'all'	=> [ @std_export, @edit_export, @abbrev_export, @EXPORT_OK ],
	'edit'	=> [ @edit_export ],
	'std'	=> [ @std_export ],
	'abr'	=> [ @abbrev_export ],
) ;

our @EXPORT = @std_export ;

my $max_fast_slurp_size = 1024 * 100 ;

my $is_win32 = $^O =~ /win32/i ;

*slurp = \&read_file ;
*rf = \&read_file ;

sub read_file {
	my $file_name = shift;
	my $opts = (ref $_[0] eq 'HASH') ? shift : {@_};
	# options we care about:
	# array_ref binmode blk_size buf_ref chomp err_mode scalar_ref

	# let's see if we have a stringified object before doing anything else
	# We then only have to deal with when we are given a file handle/globref
	if (ref($file_name)) {
		my $ref_result = _check_ref($file_name, $opts);
		if (ref($ref_result)) {
			@_ = ($opts, $ref_result);
			goto &_error;
		}
		$file_name = $ref_result if $ref_result;
		# we have now stringified $file_name if possible. if it's still a ref
		# then we probably have a file handle
	}

	my $fh;
	if (ref($file_name)) {
		$fh = $file_name;
	}
	else {
		# to keep with the old ways, read in :raw by default
		unless (open $fh, "<:raw", $file_name) {
			@_ = ($opts, "read_file '$file_name' - open: $!");
			goto &_error;
		}
		# even though we set raw, let binmode take place here (busted)
		if (my $bm = $opts->{binmode}) {
			binmode $fh, $bm;
		}
	}

	# we are now sure to have an open file handle. Let's slurp it in the same
	# way that File::Slurper does.
	my $buf;
	my $buf_ref = $opts->{buf_ref} || \$buf;
	${$buf_ref} = '';
	my $blk_size = $opts->{blk_size} || 1024 * 1024;
	if (my $size = -f $fh && -s _) {
		$blk_size = $size if $size < $blk_size;
		my ($pos, $read) = 0;
		do {
			unless(defined($read = read $fh, ${$buf_ref}, $blk_size, $pos)) {
				@_ = ($opts, "read_file '$file_name' - read: $!");
				goto &_error;
			}
			$pos += $read;
		} while ($read && $pos < $size);
	}
	else {
		${$buf_ref} = do { local $/; <$fh> };
	}
	seek($fh, $opts->{_data_tell}, SEEK_SET) if $opts->{_is_data} && $opts->{_data_tell};

	# line endings if we're on Windows
	${$buf_ref} =~ s/\015\012/\012/g if ${$buf_ref} && $is_win32 && !$opts->{binmode};

	# we now have a buffer filled with the file content. Figure out how to
	# return it to the user
	my $want_array = wantarray; # let's only ask for this once
	if ($want_array || $opts->{array_ref}) {
		use re 'taint';
		my $sep = $/;
		$sep = '\n\n+' if defined $sep && $sep eq '';
		# split the buffered content into lines
		my @lines = length(${$buf_ref}) ?
			${$buf_ref} =~ /(.*?$sep|.+)/sg : ();
		chomp @lines if $opts->{chomp};
		return \@lines if $opts->{array_ref};
		return @lines;
	}
	return $buf_ref if $opts->{scalar_ref};
	# if the function was called in scalar context, return the contents
	return ${$buf_ref} if defined $want_array;
	# if we were called in void context, return nothing
	return;
}

# errors in this sub are returned as scalar refs
# a normal IO/GLOB handle is an empty return
# an overloaded object returns its stringified as a scalarfilename

sub _check_ref {

	my( $handle, $opts ) = @_ ;

# check if we are reading from a handle (GLOB or IO object)

	if ( eval { $handle->isa( 'GLOB' ) || $handle->isa( 'IO' ) } ) {

# we have a handle. deal with seeking to it if it is DATA

		my $err = _seek_data_handle( $handle, $opts ) ;

# return the error string if any

		return \$err if $err ;

# we have good handle
		return ;
	}

	eval { require overload } ;

# return an error if we can't load the overload pragma
# or if the object isn't overloaded

	return \"Bad handle '$handle' is not a GLOB or IO object or overloaded"
		 if $@ || !overload::Overloaded( $handle ) ;

# must be overloaded so return its stringified value

	return "$handle" ;
}

sub _seek_data_handle {

	my( $handle, $opts ) = @_ ;
	# store some meta-data about the __DATA__ file handle
	$opts->{_is_data} = 0;
	$opts->{_data_tell} = 0;

# DEEP DARK MAGIC. this checks the UNTAINT IO flag of a
# glob/handle. only the DATA handle is untainted (since it is from
# trusted data in the source file). this allows us to test if this is
# the DATA handle and then to do a sysseek to make sure it gets
# slurped correctly. on some systems, the buffered i/o pointer is not
# left at the same place as the fd pointer. this sysseek makes them
# the same so slurping with sysread will work.

	eval{ require B } ;

	if ( $@ ) {

		return <IO->IoFLAGS & 16 ) {

		# we now know we have the data handle. Let's store its original
		# location in the file so that we can put it back after the read.
		# this is only done for Bugwards-compatibility in some dists such as
		# CPAN::Index::API that made use of the oddity where sysread was in use
		# before
		$opts->{_is_data} = 1;
		$opts->{_data_tell} = tell($handle);
# set the seek position to the current tell.

		# unless( sysseek( $handle, tell( $handle ), SEEK_SET ) ) {
		# 	return "read_file '$handle' - sysseek: $!" ;
		# }
	}

# seek was successful, return no error string

	return ;
}

*wf = \&write_file ;

sub write_file {
	my $file_name = shift;
	my $opts = (ref $_[0] eq 'HASH') ? shift : {};
	# options we care about:
	# append atomic binmode buf_ref err_mode no_clobber perms

	my $fh;
	my $no_truncate = 0;
	my $orig_filename;
	# let's see if we have a stringified object or some sort of handle
	# or globref before doing anything else
	if (ref($file_name)) {
		my $ref_result = _check_ref($file_name, $opts);
		if (ref($ref_result)) {
			# some error happened while checking for a ref
			@_ = ($opts, $ref_result);
			goto &_error;
		}
		if ($ref_result) {
			# we have now stringified $file_name from the overloaded obj
			$file_name = $ref_result;
		}
		else {
			# we now have a proper handle ref
			# make sure we don't call truncate on it
			$fh = $file_name;
			$no_truncate = 1;
			# can't do atomic or permissions on a file handle
			delete $opts->{atomic};
			delete $opts->{perms};
		}
	}

	# open the file for writing if we were given a filename
	unless ($fh) {
		$orig_filename = $file_name;
		my $perms = defined($opts->{perms}) ? $opts->{perms} : 0666;
		# set the mode for the sysopen
		my $mode = O_WRONLY | O_CREAT;
		$mode |= O_APPEND if $opts->{append};
		$mode |= O_EXCL if $opts->{no_clobber};
		if ($opts->{atomic}) {
			# in an atomic write, we must open a new file in the same directory
			# as the original to account for ACLs. We must also set the new file
			# to the same permissions as the original unless overridden by the
			# caller's request to set a specified permission set.
			my $dir = File::Spec->rel2abs(File::Basename::dirname($file_name));
			if (!defined($opts->{perms}) && -e $file_name && -f _) {
				$perms = 07777 & (stat $file_name)[2];
			}
			# we must ensure we're using a good temporary filename (doesn't already
			# exist). This is slower, but safer.
			{
				local $^W = 0; # AYFKM
				(undef, $file_name) = tempfile('.tempXXXXX', DIR => $dir, OPEN => 0);
			}
		}
		$fh = local *FH;
		unless (sysopen($fh, $file_name, $mode, $perms)) {
			@_ = ($opts, "write_file '$file_name' - sysopen: $!");
			goto &_error;
		}
	}
	# we now have an open file handle as well as data to write to that handle
	if (my $binmode = $opts->{binmode}) {
		binmode($fh, $binmode);
	}

	# get the data to print to the file
	# get the buffer ref - it depends on how the data is passed in
	# after this if/else $buf_ref will have a scalar ref to the data
	my $buf_ref;
	my $data_is_ref = 0;
	if (ref($opts->{buf_ref}) eq 'SCALAR') {
		# a scalar ref passed in %opts has the data
		# note that the data was passed by ref
		$buf_ref = $opts->{buf_ref};
		$data_is_ref = 1;
	}
	elsif (ref($_[0]) eq 'SCALAR') {
		# the first value in @_ is the scalar ref to the data
		# note that the data was passed by ref
		$buf_ref = shift;
		$data_is_ref = 1;
	}
	elsif (ref($_[0]) eq 'ARRAY') {
		# the first value in @_ is the array ref to the data so join it.
		${$buf_ref} = join '', @{$_[0]};
	}
	else {
		# good old @_ has all the data so join it.
		${$buf_ref} = join '', @_;
	}

	# seek and print
	seek($fh, 0, SEEK_END) if $opts->{append};
	print {$fh} ${$buf_ref};
	truncate($fh, tell($fh)) unless $no_truncate;
	close($fh);

	if ($opts->{atomic} && !rename($file_name, $orig_filename)) {
		@_ = ($opts, "write_file '$file_name' - rename: $!");
		goto &_error;
	}

	return 1;
}

# this is for backwards compatibility with the previous File::Slurp module.
# write_file always overwrites an existing file
*overwrite_file = \&write_file ;

# the current write_file has an append mode so we use that. this
# supports the same API with an optional second argument which is a
# hash ref of options.

sub append_file {

# get the optional opts hash ref
	my $opts = $_[1] ;
	if ( ref $opts eq 'HASH' ) {

# we were passed an opts ref so just mark the append mode

		$opts->{append} = 1 ;
	}
	else {

# no opts hash so insert one with the append mode

		splice( @_, 1, 0, { append => 1 } ) ;
	}

# magic goto the main write_file sub. this overlays the sub without touching
# the stack or @_

	goto &write_file
}

# prepend data to the beginning of a file

sub prepend_file {

	my $file_name = shift ;

#print "FILE $file_name\n" ;

	my $opts = ( ref $_[0] eq 'HASH' ) ? shift : {} ;

# delete unsupported options

	my @bad_opts =
		grep $_ ne 'err_mode' && $_ ne 'binmode', keys %{$opts} ;

	delete @{$opts}{@bad_opts} ;

	my $prepend_data = shift ;
	$prepend_data = '' unless defined $prepend_data ;
	$prepend_data = ${$prepend_data} if ref $prepend_data eq 'SCALAR' ;

#print "PRE [$prepend_data]\n" ;

	my $err_mode = delete $opts->{err_mode} ;
	$opts->{ err_mode } = 'croak' ;
	$opts->{ scalar_ref } = 1 ;

	my $existing_data = eval { read_file( $file_name, $opts ) } ;

	if ( $@ ) {

		@_ = ( { err_mode => $err_mode },
			"prepend_file '$file_name' - read_file: $!" ) ;
		goto &_error ;
	}

#print "EXIST [$$existing_data]\n" ;

	$opts->{atomic} = 1 ;
	my $write_result =
		eval { write_file( $file_name, $opts,
		       $prepend_data, $$existing_data ) ;
	} ;

	if ( $@ ) {

		@_ = ( { err_mode => $err_mode },
			"prepend_file '$file_name' - write_file: $!" ) ;
		goto &_error ;
	}

	return $write_result ;
}

# edit a file as a scalar in $_

*ef = \&edit_file ;

sub edit_file(&$;$) {

	my( $edit_code, $file_name, $opts ) = @_ ;
	$opts = {} unless ref $opts eq 'HASH' ;

# 	my $edit_code = shift ;
# 	my $file_name = shift ;
# 	my $opts = ( ref $_[0] eq 'HASH' ) ? shift : {} ;

#print "FILE $file_name\n" ;

# delete unsupported options

	my @bad_opts =
		grep $_ ne 'err_mode' && $_ ne 'binmode', keys %{$opts} ;

	delete @{$opts}{@bad_opts} ;

# keep the user err_mode and force croaking on internal errors

	my $err_mode = delete $opts->{err_mode} ;
	$opts->{ err_mode } = 'croak' ;

# get a scalar ref for speed and slurp the file into a scalar

	$opts->{ scalar_ref } = 1 ;
	my $existing_data = eval { read_file( $file_name, $opts ) } ;

	if ( $@ ) {

		@_ = ( { err_mode => $err_mode },
			"edit_file '$file_name' - read_file: $!" ) ;
		goto &_error ;
	}

#print "EXIST [$$existing_data]\n" ;

	my( $edited_data ) = map { $edit_code->(); $_ } $$existing_data ;

	$opts->{atomic} = 1 ;
	my $write_result =
		eval { write_file( $file_name, $opts, $edited_data ) } ;

	if ( $@ ) {

		@_ = ( { err_mode => $err_mode },
			"edit_file '$file_name' - write_file: $!" ) ;
		goto &_error ;
	}

	return $write_result ;
}

*efl = \&edit_file_lines ;

sub edit_file_lines(&$;$) {

	my( $edit_code, $file_name, $opts ) = @_ ;
	$opts = {} unless ref $opts eq 'HASH' ;

# 	my $edit_code = shift ;
# 	my $file_name = shift ;
# 	my $opts = ( ref $_[0] eq 'HASH' ) ? shift : {} ;

#print "FILE $file_name\n" ;

# delete unsupported options

	my @bad_opts =
		grep $_ ne 'err_mode' && $_ ne 'binmode', keys %{$opts} ;

	delete @{$opts}{@bad_opts} ;

# keep the user err_mode and force croaking on internal errors

	my $err_mode = delete $opts->{err_mode} ;
	$opts->{ err_mode } = 'croak' ;

# get an array ref for speed and slurp the file into lines

	$opts->{ array_ref } = 1 ;
	my $existing_data = eval { read_file( $file_name, $opts ) } ;

	if ( $@ ) {

		@_ = ( { err_mode => $err_mode },
			"edit_file_lines '$file_name' - read_file: $!" ) ;
		goto &_error ;
	}

#print "EXIST [$$existing_data]\n" ;

	my @edited_data = map { $edit_code->(); $_ } @$existing_data ;

	$opts->{atomic} = 1 ;
	my $write_result =
		eval { write_file( $file_name, $opts, @edited_data ) } ;

	if ( $@ ) {

		@_ = ( { err_mode => $err_mode },
			"edit_file_lines '$file_name' - write_file: $!" ) ;
		goto &_error ;
	}

	return $write_result ;
}

# basic wrapper around opendir/readdir

sub read_dir {

	my $dir = shift ;
	my $opts = ( ref $_[0] eq 'HASH' ) ? shift : { @_ } ;

# this handle will be destroyed upon return

	local(*DIRH);

# open the dir and handle any errors

	unless ( opendir( DIRH, $dir ) ) {

		@_ = ( $opts, "read_dir '$dir' - opendir: $!" ) ;
		goto &_error ;
	}

	my @dir_entries = readdir(DIRH) ;

	@dir_entries = grep( $_ ne "." && $_ ne "..", @dir_entries )
		unless $opts->{'keep_dot_dot'} ;

	if ( $opts->{'prefix'} ) {

		$_ = File::Spec->catfile($dir, $_) for @dir_entries;
	}

	return @dir_entries if wantarray ;
	return \@dir_entries ;
}

# error handling section
#
# all the error handling uses magic goto so the caller will get the
# error message as if from their code and not this module. if we just
# did a call on the error code, the carp/croak would report it from
# this module since the error sub is one level down on the call stack
# from read_file/write_file/read_dir.


my %err_func = (
	'carp'	=> \&carp,
	'croak'	=> \&croak,
) ;

sub _error {

	my( $opts, $err_msg ) = @_ ;

# get the error function to use

 	my $func = $err_func{ $opts->{'err_mode'} || 'croak' } ;

# if we didn't find it in our error function hash, they must have set
# it to quiet and we don't do anything.

	return unless $func ;

# call the carp/croak function

	$func->($err_msg) if $func ;

# return a hard undef (in list context this will be a single value of
# undef which is not a legal in-band value)

	return undef ;
}

1;
__END__

=head1 NAME

File::Slurp - Simple and Efficient Reading/Writing/Modifying of Complete Files

=head1 SYNOPSIS

  use File::Slurp;

  # read in a whole file into a scalar
  my $text = read_file('/path/file');

  # read in a whole file into an array of lines
  my @lines = read_file('/path/file');

  # write out a whole file from a scalar
  write_file('/path/file', $text);

  # write out a whole file from an array of lines
  write_file('/path/file', @lines);

  # Here is a simple and fast way to load and save a simple config file
  # made of key=value lines.
  my %conf = read_file('/path/file') =~ /^(\w+)=(.*)$/mg;
  write_file('/path/file', {atomic => 1}, map "$_=$conf{$_}\n", keys %conf);

  # insert text at the beginning of a file
  prepend_file('/path/file', $text);

  # in-place edit to replace all 'foo' with 'bar' in file
  edit_file { s/foo/bar/g } '/path/file';

  # in-place edit to delete all lines with 'foo' from file
  edit_file_lines sub { $_ = '' if /foo/ }, '/path/file';

  # read in a whole directory of file names (skipping . and ..)
  my @files = read_dir('/path/to/dir');

=head1 DESCRIPTION

This module provides subs that allow you to read or write entire files
with one simple call. They are designed to be simple to use, have
flexible ways to pass in or get the file contents and to be very
efficient. There is also a sub to read in all the files in a
directory.

=head2 WARNING - PENDING DOOM

Although you technically I, do NOT use this module to work on file handles,
pipes, sockets, standard IO, or the C handle. These are
features implemented long ago that just really shouldn't be abused here.

Be warned: this activity will lead to inaccurate encoding/decoding of data.

All further mentions of actions on the above have been removed from this
documentation and that feature set will likely be deprecated in the future.

In other words, if you don't have a filename to pass, consider using the
standard C<< do { local $/; <$fh> } >>, or
L/L for working with C<__DATA__>.

=head1 FUNCTIONS

L implements the following functions.

=head2 append_file

	use File::Slurp qw(append_file write_file);
	my $res = append_file('/path/file', "Some text");
	# same as
	my $res = write_file('/path/file', {append => 1}, "Some text");

The C function is simply a synonym for the
L function, but ensures that the C option is
set.

=head2 edit_file

	use File::Slurp qw(edit_file);
	# perl -0777 -pi -e 's/foo/bar/g' /path/file
	edit_file { s/foo/bar/g } '/path/file';
	edit_file sub { s/foo/bar/g }, '/path/file';
	sub replace_foo { s/foo/bar/g }
	edit_file \&replace_foo, '/path/file';

The C function reads in a file into C<$_>, executes a code block that
should modify C<$_>, and then writes C<$_> back to the file. The C
function reads in the entire file and calls the code block one time. It is
equivalent to the C<-pi> command line options of Perl but you can call it from
inside your program and not have to fork out a process.

The first argument to C is a code block or a code reference. The
code block is not followed by a comma (as with C and C) but a code
reference is followed by a comma.

The next argument is the filename.

The next argument(s) is either a hash reference or a flattened hash,
C<< key => value >> pairs. The options are passed through to the
L function. All options are described there.
Only the C and C options are supported. The call to
L has the C option set so you will always
have a consistent file.

=head2 edit_file_lines

	use File::Slurp qw(edit_file_lines);
	# perl -pi -e '$_ = "" if /foo/' /path/file
	edit_file_lines { $_ = '' if /foo/ } '/path/file';
	edit_file_lines sub { $_ = '' if /foo/ }, '/path/file';
	sub delete_foo { $_ = '' if /foo/ }
	edit_file \&delete_foo, '/path/file';

The C function reads each line of a file into C<$_>, and
executes a code block that should modify C<$_>. It will then write C<$_> back
to the file. It is equivalent to the C<-pi> command line options of Perl but
you can call it from inside your program and not have to fork out a process.

The first argument to C is a code block or a code reference.
The code block is not followed by a comma (as with C and C) but a
code reference is followed by a comma.

The next argument is the filename.

The next argument(s) is either a hash reference or a flattened hash,
C<< key => value >> pairs. The options are passed through to the
L function. All options are described there.
Only the C and C options are supported. The call to
L has the C option set so you will always
have a consistent file.

=head2 ef

	use File::Slurp qw(ef);
	# perl -0777 -pi -e 's/foo/bar/g' /path/file
	ef { s/foo/bar/g } '/path/file';
	ef sub { s/foo/bar/g }, '/path/file';
	sub replace_foo { s/foo/bar/g }
	ef \&replace_foo, '/path/file';

The C function is simply a synonym for the L
function.

=head2 efl

	use File::Slurp qw(efl);
	# perl -pi -e '$_ = "" if /foo/' /path/file
	efl { $_ = '' if /foo/ } '/path/file';
	efl sub { $_ = '' if /foo/ }, '/path/file';
	sub delete_foo { $_ = '' if /foo/ }
	efl \&delete_foo, '/path/file';

The C function is simply a synonym for the L
function.

=head2 overwrite_file

	use File::Slurp qw(overwrite_file);
	my $res = overwrite_file('/path/file', "Some text");

The C function is simply a synonym for the
L function.

=head2 prepend_file

	use File::Slurp qw(prepend_file);
	prepend_file('/path/file', $header);
	prepend_file('/path/file', \@lines);
	prepend_file('/path/file', { binmode => ':raw'}, $bin_data);

	# equivalent to:
	use File::Slurp qw(read_file write_file);
	my $content = read_file('/path/file');
	my $new_content = "hahahaha";
	write_file('/path/file', $new_content . $content);

The C function is the opposite of L as
it writes new contents to the beginning of the file instead of the end. It is a
combination of L and L. It
works by first using C to slurp in the file and then calling
C with the new data and the existing file data.

The first argument to C is the filename.

The next argument(s) is either a hash reference or a flattened hash,
C<< key => value >> pairs. The options are passed through to the
L function. All options are described there.

Only the C and C options are supported. The
C call has the C option set so you will always have
a consistent file.

=head2 read_dir

	use File::Slurp qw(read_dir);
	my @files = read_dir('/path/to/dir');
	# all files, even the dots
	my @files = read_dir('/path/to/dir', keep_dot_dot => 1);
	# keep the full file path
	my @paths = read_dir('/path/to/dir', prefix => 1);
	# scalar context
	my $files_ref = read_dir('/path/to/dir');

This function returns a list of the filenames in the supplied directory. In
list context, an array is returned, in scalar context, an array reference is
returned.

The first argument is the path to the directory to read.

The next argument(s) is either a hash reference or a flattened hash,
C<< key => value >> pairs. The following options are available:

=over

=item

err_mode

The C option has three possible values: C, C, or the
default, C. In C mode, all errors will be silent. In C mode,
all errors will be emitted as warnings. And, in C mode, all errors will
be emitted as exceptions. Take a look at L or
L to see how to catch exceptions.

=item

keep_dot_dot

The C option is a boolean option, defaulted to false (C<0>).
Setting this option to true (C<1>) will also return the C<.> and C<..> files
that are removed from the file list by default.

=item

prefix

The C option is a boolean option, defaulted to false (C<0>).
Setting this option to true (C<1>) add the directory as a prefix to the file.
The directory and the filename are joined using C<< File::Spec->catfile() >> to
ensure the proper directory separator is used for your OS. See L.

=back

=head2 read_file

	use File::Slurp qw(read_file);
	my $text = read_file('/path/file');
	my $bin = read_file('/path/file', { binmode => ':raw' });
	my @lines = read_file('/path/file');
	my $lines_ref = read_file('/path/file', array_ref => 1);
	my $lines_ref = [ read_file('/path/file') ];

	# or we can read into a buffer:
	my $buffer;
	read_file('/path/file', buf_ref => \$buffer);

	# or we can set the block size for the read
	my $text_ref = read_file('/path/file', blk_size => 10_000_000, array_ref => 1);

	# or we can get a scalar reference
	my $text_ref = read_file('/path/file', scalar_ref => 1);

This function reads in an entire file and returns its contents to the
caller. In scalar context it returns the entire file as a single
scalar. In list context it will return a list of lines (using the
current value of C<$/> as the separator, including support for paragraph
mode when it is set to C<''>).

The first argument is the path to the file to be slurped in.

The next argument(s) is either a hash reference or a flattened hash,
C<< key => value >> pairs. The following options are available:

=over

=item

array_ref

The C option is a boolean option, defaulted to false (C<0>). Setting
this option to true (C<1>) will only have relevance if the C function
is called in scalar context. When true, the C function will return
a reference to an array of the lines in the file.

=item

binmode

The C option is a string option, defaulted to empty (C<''>). If you
set the C option, then its value is passed to a call to C on
the opened handle. You can use this to set the file to be read in binary mode,
utf8, etc. See C for more.

=item

blk_size

You can use this option to set the block size used when slurping from
an already open handle (like C<\*STDIN>). It defaults to 1MB.

=item

buf_ref

The C option can be used in conjunction with any of the other options.
You can use this option to pass in a scalar reference and the slurped
file contents will be stored in the scalar. This saves an extra copy of
the slurped file and can lower RAM usage vs returning the file. It is
usually the fastest way to read a file into a scalar.

=item

chomp

The C option is a boolean option, defaulted to false (C<0>). Setting
this option to true (C<1>) will cause each line to have its contents Ced.
This option works in list context or in scalar context with the C
option.

=item

err_mode

The C option has three possible values: C, C, or the
default, C. In C mode, all errors will be silent. In C mode,
all errors will be emitted as warnings. And, in C mode, all errors will
be emitted as exceptions. Take a look at L or
L to see how to catch exceptions.

=item

scalar_ref

The C option is a boolean option, defaulted to false (C<0>). It only
has meaning in scalar context. The return value will be a scalar reference to a
string which is the contents of the slurped file. This will usually be faster
than returning the plain scalar. It will also save memory as it will not make a
copy of the file to return.

=back

=head2 rf

	use File::Slurp qw(rf);
	my $text = rf('/path/file');

The C function is simply a synonym for the L
function.

=head2 slurp

	use File::Slurp qw(slurp);
	my $text = slurp('/path/file');

The C function is simply a synonym for the L
function.

=head2 wf

	use File::Slurp qw(wf);
	my $res = wf('/path/file', "Some text");


The C function is simply a synonym for the
L function.

=head2 write_file

	use File::Slurp qw(write_file);
	write_file('/path/file', @data);
	write_file('/path/file', {append => 1}, @data);
	write_file('/path/file', {binmode => ':raw'}, $buffer);
	write_file('/path/file', \$buffer);
	write_file('/path/file', $buffer);
	write_file('/path/file', \@lines);
	write_file('/path/file', @lines);

	# binmode
	write_file('/path/file', {binmode => ':raw'}, @data);
	write_file('/path/file', {binmode => ':utf8'}, $utf_text);

	# buffered
	write_file('/path/file', {buf_ref => \$buffer});
	write_file('/path/file', \$buffer);
	write_file('/path/file', $buffer);

	# append
	write_file('/path/file', {append => 1}, @data);

	# no clobbering
	write_file('/path/file', {no_clobber => 1}, @data);

This function writes out an entire file in one call. By default C
returns C<1> upon successfully writing the file or C if it encountered
an error. You can change how errors are handled with the C option.

The first argument to C is the filename.

The next argument(s) is either a hash reference or a flattened hash,
C<< key => value >> pairs. The following options are available:

=over

=item

append

The C option is a boolean option, defaulted to false (C<0>). Setting
this option to true (C<1>) will cause the data to be be written at the end of
the current file. Internally this sets the C mode flag C.

The L function sets this option by default.

=item

atomic

The C option is a boolean option, defaulted to false (C<0>). Setting
this option to true (C<1>) will cause the file to be be written to in an
atomic fashion. A temporary file name is created using L.
After the file is closed it is renamed to the original file name
(and C is an atomic operation on most OSes). If the program using
this were to crash in the middle of this, then the temporary file could
be left behind.

=item

binmode

The C option is a string option, defaulted to empty (C<''>). If you
set the C option, then its value is passed to a call to C on
the opened handle. You can use this to set the file to be read in binary mode,
utf8, etc. See C for more.

=item

buf_ref

The C option is used to pass in a scalar reference which has the
data to be written. If this is set then any data arguments (including
the scalar reference shortcut) in C<@_> will be ignored.

=item

err_mode

The C option has three possible values: C, C, or the
default, C. In C mode, all errors will be silent. In C mode,
all errors will be emitted as warnings. And, in C mode, all errors will
be emitted as exceptions. Take a look at L or
L to see how to catch exceptions.


=item

no_clobber

The C option is a boolean option, defaulted to false (C<0>). Setting
this option to true (C<1>) will ensure an that existing file will not be
overwritten.

=item

perms

The C option sets the permissions of newly-created files. This value
is modified by your process's C and defaults to C<0666> (same as
C).

NOTE: this option is new as of File::Slurp version 9999.14.

=back

=head1 EXPORT

These are exported by default or with

	use File::Slurp qw(:std);
	# read_file write_file overwrite_file append_file read_dir

These are exported with

	use File::Slurp qw(:edit);
	# edit_file edit_file_lines

You can get all subs in the module exported with

	use File::Slurp qw(:all);

=head1 SEE ALSO

=over

=item *

L - Provides a straightforward set of functions for the most
common tasks of reading/writing text and binary files.

=item *

L - Lightweight and comprehensive file handling, including simple
methods for reading, writing, and editing text and binary files.

=item *

L - Similar to Path::Tiny for the L toolkit, always works in
bytes.

=back

=head1 AUTHOR

Uri Guttman, >

=head1 COPYRIGHT & LICENSE

Copyright (c) 2003 Uri Guttman. All rights reserved.

This program is free software; you can redistribute it and/or modify it
under the same terms as Perl itself.

=cut
File-Slurp-9999.32/Changes0000644000175000017500000003055013676753360015764 0ustar  cwhitenercwhitenerRevision history File::Slurp

9999.32     2020-06-30
    - Re-release after fixing MANIFEST

9999.31     2020-06-28
    - Remove TravisCI and AppVeyor
    - Test using GitHub Actions/workflows on Windows, Mac, and Linux
    - Add See Also section to the docs. (PR#24 Thanks, Dan Book)
    - Add file existence and size checks (RT 132900 - Thanks, Bao Haojun)

9999.30     2020-03-09
    - Altered the atomic version of write_file to use temporary files that
      are also hidden files. (RT #132064)

9999.29     2019-11-27
    - Correct some documentation errors where copy-paste had us saying
      File::Spec rather than File::Slurp. (RT 131097 - Thanks, Mike)
    - Reduce the size of the tests in t/handle.t to be nicer to CPAN
      Testers.

9999.28     2019-04-05
    - Stop testing with Taint mode. Taint was a terrible practice that should
      have never ever ever been a thing.

9999.27     2019-04-05
    - Update the documentation on the atomic write. We no longer use the pid
      and I neglected to update the documentation as such. (RT #129029)
    - Localize $^W to stop File::Temp from warning the user when the -w flag
      is on while we're grabbing a temporary file name. (RT #129029)

9999.26     2019-02-13
    - Reduce the size of handle.t to prevent failures on systems with limits set
    - Skip all tests in the suite that relied on overriding syswrite to test
      failure mechanisms as CORE::print cannot be overridden.
    - Refactor write_file to use print rather than syswrite.
      - When performing an atomic write, make sure we find a good temporary file
        so that we don't accidentally overwrite a file that may already exist in
        the working directory.
      - Stop re-working the line endings on write_file when on Windows as the use
        of print now allows layers to provide that functionality.
    - Add File::Basename, File::Spec, File::Temp, and IO::Handle to the runtime
      prereqs. These were already testing prereqs and are core.
    - Perl 5.30 compliance is complete at this point.

9999.25     2018-11-16
    - The previous release contained nothing but a documentation update. That
      updated documentation errantly mentioned pseudo-files. Pseudo-files
      are perfectly fine to use with File::Slurp.
    - Add regression test for GLOB refs being slurped in. Thank you, James Keenan!
      https://github.com/perhunter/slurp/pull/17#issuecomment-437174592
    - Refactor read_file to use open and read rather than sysopen and sysread.
    - Add a bugwards compatible feature to keep track of the cursor when
      dealing with the DATA handle (https://github.com/perhunter/slurp/pull/17)
    - Fix a typo in the docs.

9999.24     2018-10-29
    - Document the clear downfalls of using file handles of any kind rather
      than just the file's path string.

9999.23     2018-10-20
    - Fix an error on the test rewrites with a bad value for binmode
    - Create a 00-report-prereqs.dd to ease testing on 5.6
    - Bump requirement for File::Spec to 3.01 as Cwd was shipped separately
      before and the one that came with 5.6 had Taint issues.
    - Cleaned up the Change log to make all dates uniform

9999.22     2018-10-15
    - Update the SYNOPSIS documentation. (Graham Knop)
    - Fix some EUMM metadata depending on version. (Dan Book)
    - Fix Windows path concatenation on read_dir. (James Keenan)
    - Document each function with proper POD heads and re-order in alphabetical
    - Dump the POD to GH markdown for a README.md
    - Remove the README file
    - Remove some work-arounds for older Perls < 5.6
    - Do not inherit from Exporter (requires Exporter 5.57)
    - Fix perms.t to run on all platforms (Aristotle Pagaltzis, Linda Walsh
      via RT #92401)
    - Clean up handle.t (we no longer use the -w flag anywhere)

9999.21    2018-10-08
    - Unset $^W in a few strategic places to silence warnings when Test::Harness
      or ExtUtils::MakeMaker turn them on. (Thanks, Graham Knop).
    - Got rid of a few MYMETA leftovers in the MANIFEST
    - Add Git repository info to the Makefile
    - Add a contributor's list for display on metacpan

9999.20_02     2018-10-04  (TRIAL)
    - Update TravisCI tests to show coverage.
    - Update all remaining test files
    - Get rid of assumption of . in @INC in tests
    - Remove t/TestDriver.pm
    - Add t/lib/FileSlurpTest.pm
    - Make sure all tests use a properly acquired temp file
    - Clean up prereqs a bit further
    - Document all failure cases in the 01-error* tests.
    - Moved the CORE:: function overrides to their own test class to only be
      included when overriding is necessary

9999.20_01     2018-09-27  (TRIAL)
    - Fixed spelling mistakes in POD (RT #85251)
    - Fixed a typo in an example (RTs #72116, #80279)
    - Remove doc mentions of Perl < 5.006 as that's required.
    - Fix POD coverage tests by adding a few more ignored functions
    - Added t/edit_file.t (James Keenan)
    - Move the POD tests to xt/author
    - Update t/append_null.t
    - Update t/binmode.t
    - Update t/data_list.t
    - Update t/data_scalar.t
    - Update t/error_mode.t
    - Update t/large.t
    - Update t/original.t
    - Update t/stringify.t
    - Added t/00-report-prereqs.t
    - Added more xt/author tests
    - Fix all trailing whitespace in accordance with xt/author/eol.t
    - Updated the Makefile.PL to get all of the prereqs in there.
    - Add CI testing via TravisCI and AppVeyor

9999.19      2011-Jun-7
    - Fixed use line in t/edit_file.t to import :edit first (paul)
    - read_file and write_file work even when interrupted by signals
      this includes a test for read_file interrupt (Andrew Danforth)
    - Fixed bugs in the config synopsis example

9999.18      2011-May-13
    - Added :std and :edit export tags
    - Cleaned up EXPORT vars
    - Documented importing edit_file and edit_file_lines
    - Fixed some pod spelling

9999.17      2011-04-27
    - Requiring Perl 5.6.2 (first time older Perls were dropped)
      This is because of use of the re 'taint' pragma
    - Added major new features: edit_file and edit_file_lines
    - Speed up of tainted slurp with return of lines
    - Added chomp option to read_file
    - Added prefix option to read_dir
    - Fixed optimization of reading small files.

9999.16   2011-04-13
    - Added support for read_file options to be a hash reference.
    - Added support for read_dir options to be a hash reference.
    - Added new feature prepend_file
    - Fixed bug with array_ref in list context. was introduced by .15/.14
      Thanks to Norbert Gruener
    - Cleaned up some pod

9999.15   2011-03-24
    - Fixed error.t test so it works when run as root
    - Removed skip lines from error.t
    - Fixed pod about binmode option to reflect changes in .14

9999.14      2011-03-20
    - Added LICENCE (same as perl) to POD
    - Added special faster code to slurp in small text files which
      is a common case
    - Rewrote the extras/slurp_bench.pl script. It has a full
      legend, better CLI options, size is selectable, benchmark
      entries have more consistant names and it compares the new
      fast slurp for small files to the general slurp code.
      Thanks to Mark Friendlich
    - Cleaned up pod
    - Added more Synopsis examples
    - Added t/error.t to actually test error conditions. Previous
      error.t was renamed to error_mode.t which better reflects its
      tests.
    - t/error.t uses a new test driver module. this may get used by
      other tests in the future.
    - Fixed check for SEEK_SET and other constant subs being defined
    - Added support for binmode other than :raw and binmode.t test
      Thanks to Martin J. Evans, Peter Edwards, Bryce Nesbitt
    - Added support for perms option in write_file and perms.t test
      Thanks to Peter Corlett and Paul Miller
    - Added check to the rename call in atomic mode. Tested in error.t.
      Thanks to Daniel Scott Sterling
    - Added POD to state that using scalar_ref or buf_ref will be faster
      and save memory due to not making a copy (Peter Edwards)
    - read_file in list mode keeps data tainted (Sébastien Aperghis-Tramoni)
    - read_file checks for an overloaded object to get the file
      name. (Sébastien Aperghis-Tramoni)

9999.13   2006-10-10
    - Refactored the extras/slurp_bench.pl script. It has options,
      a key the benchmarks, help and more benchmarks.
    - Reordered changes so recent entries are first
    - Added error check on atomic rename and test for it. Thanks to Daniel
      Scott Sterling

9999.12   2006-02-2
    - Fixed bug on windows with classic slurping and File::Slurp not
      agreeing on newline conversion.
    - Added t/newline.t test to check for that fix.
    - When passing text data by scalar reference to write_file under
      windows, the buffer is copied so the newline conversion won't
      modify the caller's data.
    - Thanks to Johan Lodin  for a test script which
      I modified into t/newline.t

9999.11   2005-01-20
    - Quick release to remove code that forced the faked SEEK_*
      values to be used. Showed up when tested on OSX which doesn't
      need that backport.

9999.10   2005-01-19
    - t/*.t modules don't use Fcntl.pm
    - using POSIX qw( :fcntl_h ) instead of Fcntl qw( :seek ) for
      backwards compatiblity to 5.00503
    - added conditional definitions of SEEK_* and O_* subs as they are not
      defined in perl 5.004
    - File::Slurp now runs on perl 5.004 and newer (see BUGS section)
      All of the above thanks to Smylers ,
      Piers Kent  and
      John Alden 
    - Added pod.t and pod_coverage.t tests. This is to pass all
      the CPANTS tests.

9999.09  2005-04-19
    - t/original.t and read_dir.t no longer search for tempdirs. they just
      use the current dir which should be in the build directory
    - t/readdir.t renamed to read_dir.t for consistancy
    - write_file return values are docuemented
      Thanks to Adam Kennedy 
    - added no_clobber option to write_file and t/no_clobber.t test for it
      Thanks to 
    - fixed bug when appending a null string to a file which then
      truncates it. seems to be an odd way for linux and OS X to
      handle O_APPEND mode on sysopen. they don't seek to the end of
      the file so it gets truncated. fixed by adding a seek to the
      end if in append mode.n
      Thanks to Chris Dolan 

9999.08  2005-04-16
    - read_dir returns an array ref in scalar context
    - read_dir keeps . and .. if keep_dot_dot option is set.
      Thanks to John Alden 
    - slurp() is an optional exported alias to read_file
      Thanks to Damian Conway 

9999.07  2005-01-25
    - Slurping in pseudo files (as in /proc) which show a size of 0
      but actually have data works. This seems to be the case on
      linux but on Solaris those files show their proper size.
      Thanks to Juerd Waalboer 

9999.06  2004-09-20
    - Slurping the DATA handle now works without the workaround.
      tests are in t/data_scalar.t and t/data_list.t
    - Paragraph mode in read_file is supported. As with <> when $/
      (input record separator) is set to '', then the input file is
      split on multiple newlines (/\n\n+/).
      Thanks to Geoffrey Leach 

9999.05  2004-02-24
    - skip handle tests where socketpair is not supported (pre 5.8
      on windows) Thanks to Mike Arms 

9999.04  2004-02-23
    - fixed DATA handle bug in t/handle.t (not seen on most OS's) Thanks to
      James Willmore 

9999.03  2003-12-22
    - fixed DATA handle bugs in t/handle.t on osx (should be fixed
      on BSD as well)
    - added more comments to code

9999.02  2003-12-17
    - skip DATA test in handle.t on OSX (bug in perl with sysread on DATA)
    - changed checking if file handle from fileno to ref
      from Randal Schwartz 
    - added support for atomic spewing
    - added new test stdin.t for the fileno/ref change
    - added new test inode.t to test atomic spewing

9999.01  2003-09-01
    - original version; created by h2xs 1.21 with options -AX -n File::FastSlurp
File-Slurp-9999.32/README.md0000644000175000017500000004365013676214265015751 0ustar  cwhitenercwhitener# NAME

File::Slurp - Simple and Efficient Reading/Writing/Modifying of Complete Files

# SYNOPSIS

```perl
use File::Slurp;

# read in a whole file into a scalar
my $text = read_file('/path/file');

# read in a whole file into an array of lines
my @lines = read_file('/path/file');

# write out a whole file from a scalar
write_file('/path/file', $text);

# write out a whole file from an array of lines
write_file('/path/file', @lines);

# Here is a simple and fast way to load and save a simple config file
# made of key=value lines.
my %conf = read_file('/path/file') =~ /^(\w+)=(.*)$/mg;
write_file('/path/file', {atomic => 1}, map "$_=$conf{$_}\n", keys %conf);

# insert text at the beginning of a file
prepend_file('/path/file', $text);

# in-place edit to replace all 'foo' with 'bar' in file
edit_file { s/foo/bar/g } '/path/file';

# in-place edit to delete all lines with 'foo' from file
edit_file_lines sub { $_ = '' if /foo/ }, '/path/file';

# read in a whole directory of file names (skipping . and ..)
my @files = read_dir('/path/to/dir');
```

# DESCRIPTION

This module provides subs that allow you to read or write entire files
with one simple call. They are designed to be simple to use, have
flexible ways to pass in or get the file contents and to be very
efficient. There is also a sub to read in all the files in a
directory.

## WARNING - PENDING DOOM

Although you technically _can_, do NOT use this module to work on file handles,
pipes, sockets, standard IO, or the `DATA` handle. These are
features implemented long ago that just really shouldn't be abused here.

Be warned: this activity will lead to inaccurate encoding/decoding of data.

All further mentions of actions on the above have been removed from this
documentation and that feature set will likely be deprecated in the future.

In other words, if you don't have a filename to pass, consider using the
standard `do { local $/; <$fh> }`, or
[Data::Section](https://metacpan.org/pod/Data%3A%3ASection)/[Data::Section::Simple](https://metacpan.org/pod/Data%3A%3ASection%3A%3ASimple) for working with `__DATA__`.

# FUNCTIONS

[File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp) implements the following functions.

## append\_file

```perl
    use File::Slurp qw(append_file write_file);
    my $res = append_file('/path/file', "Some text");
    # same as
    my $res = write_file('/path/file', {append => 1}, "Some text");
```

The `append_file` function is simply a synonym for the
["write\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#write_file) function, but ensures that the `append` option is
set.

## edit\_file

```perl
    use File::Slurp qw(edit_file);
    # perl -0777 -pi -e 's/foo/bar/g' /path/file
    edit_file { s/foo/bar/g } '/path/file';
    edit_file sub { s/foo/bar/g }, '/path/file';
    sub replace_foo { s/foo/bar/g }
    edit_file \&replace_foo, '/path/file';
```

The `edit_file` function reads in a file into `$_`, executes a code block that
should modify `$_`, and then writes `$_` back to the file. The `edit_file`
function reads in the entire file and calls the code block one time. It is
equivalent to the `-pi` command line options of Perl but you can call it from
inside your program and not have to fork out a process.

The first argument to `edit_file` is a code block or a code reference. The
code block is not followed by a comma (as with `grep` and `map`) but a code
reference is followed by a comma.

The next argument is the filename.

The next argument(s) is either a hash reference or a flattened hash,
`key => value` pairs. The options are passed through to the
["write\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#write_file) function. All options are described there.
Only the `binmode` and `err_mode` options are supported. The call to
["write\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#write_file) has the `atomic` option set so you will always
have a consistent file.

## edit\_file\_lines

```perl
    use File::Slurp qw(edit_file_lines);
    # perl -pi -e '$_ = "" if /foo/' /path/file
    edit_file_lines { $_ = '' if /foo/ } '/path/file';
    edit_file_lines sub { $_ = '' if /foo/ }, '/path/file';
    sub delete_foo { $_ = '' if /foo/ }
    edit_file \&delete_foo, '/path/file';
```

The `edit_file_lines` function reads each line of a file into `$_`, and
executes a code block that should modify `$_`. It will then write `$_` back
to the file. It is equivalent to the `-pi` command line options of Perl but
you can call it from inside your program and not have to fork out a process.

The first argument to `edit_file_lines` is a code block or a code reference.
The code block is not followed by a comma (as with `grep` and `map`) but a
code reference is followed by a comma.

The next argument is the filename.

The next argument(s) is either a hash reference or a flattened hash,
`key => value` pairs. The options are passed through to the
["write\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#write_file) function. All options are described there.
Only the `binmode` and `err_mode` options are supported. The call to
["write\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#write_file) has the `atomic` option set so you will always
have a consistent file.

## ef

```perl
    use File::Slurp qw(ef);
    # perl -0777 -pi -e 's/foo/bar/g' /path/file
    ef { s/foo/bar/g } '/path/file';
    ef sub { s/foo/bar/g }, '/path/file';
    sub replace_foo { s/foo/bar/g }
    ef \&replace_foo, '/path/file';
```

The `ef` function is simply a synonym for the ["edit\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#edit_file)
function.

## efl

```perl
    use File::Slurp qw(efl);
    # perl -pi -e '$_ = "" if /foo/' /path/file
    efl { $_ = '' if /foo/ } '/path/file';
    efl sub { $_ = '' if /foo/ }, '/path/file';
    sub delete_foo { $_ = '' if /foo/ }
    efl \&delete_foo, '/path/file';
```

The `efl` function is simply a synonym for the ["edit\_file\_lines" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#edit_file_lines)
function.

## overwrite\_file

```perl
    use File::Slurp qw(overwrite_file);
    my $res = overwrite_file('/path/file', "Some text");
```

The `overwrite_file` function is simply a synonym for the
["write\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#write_file) function.

## prepend\_file

```perl
    use File::Slurp qw(prepend_file);
    prepend_file('/path/file', $header);
    prepend_file('/path/file', \@lines);
    prepend_file('/path/file', { binmode => ':raw'}, $bin_data);

    # equivalent to:
    use File::Slurp qw(read_file write_file);
    my $content = read_file('/path/file');
    my $new_content = "hahahaha";
    write_file('/path/file', $new_content . $content);
```

The `prepend_file` function is the opposite of ["append\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#append_file) as
it writes new contents to the beginning of the file instead of the end. It is a
combination of ["read\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#read_file) and ["write\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#write_file). It
works by first using `read_file` to slurp in the file and then calling
`write_file` with the new data and the existing file data.

The first argument to `prepend_file` is the filename.

The next argument(s) is either a hash reference or a flattened hash,
`key => value` pairs. The options are passed through to the
["write\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#write_file) function. All options are described there.

Only the `binmode` and `err_mode` options are supported. The
`write_file` call has the `atomic` option set so you will always have
a consistent file.

## read\_dir

```perl
    use File::Slurp qw(read_dir);
    my @files = read_dir('/path/to/dir');
    # all files, even the dots
    my @files = read_dir('/path/to/dir', keep_dot_dot => 1);
    # keep the full file path
    my @paths = read_dir('/path/to/dir', prefix => 1);
    # scalar context
    my $files_ref = read_dir('/path/to/dir');
```

This function returns a list of the filenames in the supplied directory. In
list context, an array is returned, in scalar context, an array reference is
returned.

The first argument is the path to the directory to read.

The next argument(s) is either a hash reference or a flattened hash,
`key => value` pairs. The following options are available:

- err\_mode

    The `err_mode` option has three possible values: `quiet`, `carp`, or the
    default, `croak`. In `quiet` mode, all errors will be silent. In `carp` mode,
    all errors will be emitted as warnings. And, in `croak` mode, all errors will
    be emitted as exceptions. Take a look at [Try::Tiny](https://metacpan.org/pod/Try%3A%3ATiny) or
    [Syntax::Keyword::Try](https://metacpan.org/pod/Syntax%3A%3AKeyword%3A%3ATry) to see how to catch exceptions.

- keep\_dot\_dot

    The `keep_dot_dot` option is a boolean option, defaulted to false (`0`).
    Setting this option to true (`1`) will also return the `.` and `..` files
    that are removed from the file list by default.

- prefix

    The `prefix` option is a boolean option, defaulted to false (`0`).
    Setting this option to true (`1`) add the directory as a prefix to the file.
    The directory and the filename are joined using `File::Spec->catfile()` to
    ensure the proper directory separator is used for your OS. See [File::Spec](https://metacpan.org/pod/File%3A%3ASpec).

## read\_file

```perl
    use File::Slurp qw(read_file);
    my $text = read_file('/path/file');
    my $bin = read_file('/path/file', { binmode => ':raw' });
    my @lines = read_file('/path/file');
    my $lines_ref = read_file('/path/file', array_ref => 1);
    my $lines_ref = [ read_file('/path/file') ];

    # or we can read into a buffer:
    my $buffer;
    read_file('/path/file', buf_ref => \$buffer);

    # or we can set the block size for the read
    my $text_ref = read_file('/path/file', blk_size => 10_000_000, array_ref => 1);

    # or we can get a scalar reference
    my $text_ref = read_file('/path/file', scalar_ref => 1);
```

This function reads in an entire file and returns its contents to the
caller. In scalar context it returns the entire file as a single
scalar. In list context it will return a list of lines (using the
current value of `$/` as the separator, including support for paragraph
mode when it is set to `''`).

The first argument is the path to the file to be slurped in.

The next argument(s) is either a hash reference or a flattened hash,
`key => value` pairs. The following options are available:

- array\_ref

    The `array_ref` option is a boolean option, defaulted to false (`0`). Setting
    this option to true (`1`) will only have relevance if the `read_file` function
    is called in scalar context. When true, the `read_file` function will return
    a reference to an array of the lines in the file.

- binmode

    The `binmode` option is a string option, defaulted to empty (`''`). If you
    set the `binmode` option, then its value is passed to a call to `binmode` on
    the opened handle. You can use this to set the file to be read in binary mode,
    utf8, etc. See `perldoc -f binmode` for more.

- blk\_size

    You can use this option to set the block size used when slurping from
    an already open handle (like `\*STDIN`). It defaults to 1MB.

- buf\_ref

    The `buf_ref` option can be used in conjunction with any of the other options.
    You can use this option to pass in a scalar reference and the slurped
    file contents will be stored in the scalar. This saves an extra copy of
    the slurped file and can lower RAM usage vs returning the file. It is
    usually the fastest way to read a file into a scalar.

- chomp

    The `chomp` option is a boolean option, defaulted to false (`0`). Setting
    this option to true (`1`) will cause each line to have its contents `chomp`ed.
    This option works in list context or in scalar context with the `array_ref`
    option.

- err\_mode

    The `err_mode` option has three possible values: `quiet`, `carp`, or the
    default, `croak`. In `quiet` mode, all errors will be silent. In `carp` mode,
    all errors will be emitted as warnings. And, in `croak` mode, all errors will
    be emitted as exceptions. Take a look at [Try::Tiny](https://metacpan.org/pod/Try%3A%3ATiny) or
    [Syntax::Keyword::Try](https://metacpan.org/pod/Syntax%3A%3AKeyword%3A%3ATry) to see how to catch exceptions.

- scalar\_ref

    The `scalar_ref` option is a boolean option, defaulted to false (`0`). It only
    has meaning in scalar context. The return value will be a scalar reference to a
    string which is the contents of the slurped file. This will usually be faster
    than returning the plain scalar. It will also save memory as it will not make a
    copy of the file to return.

## rf

```perl
    use File::Slurp qw(rf);
    my $text = rf('/path/file');
```

The `rf` function is simply a synonym for the ["read\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#read_file)
function.

## slurp

```perl
    use File::Slurp qw(slurp);
    my $text = slurp('/path/file');
```

The `slurp` function is simply a synonym for the ["read\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#read_file)
function.

## wf

```perl
    use File::Slurp qw(wf);
    my $res = wf('/path/file', "Some text");
```

The `wf` function is simply a synonym for the
["write\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#write_file) function.

## write\_file

```perl
    use File::Slurp qw(write_file);
    write_file('/path/file', @data);
    write_file('/path/file', {append => 1}, @data);
    write_file('/path/file', {binmode => ':raw'}, $buffer);
    write_file('/path/file', \$buffer);
    write_file('/path/file', $buffer);
    write_file('/path/file', \@lines);
    write_file('/path/file', @lines);

    # binmode
    write_file('/path/file', {binmode => ':raw'}, @data);
    write_file('/path/file', {binmode => ':utf8'}, $utf_text);

    # buffered
    write_file('/path/file', {buf_ref => \$buffer});
    write_file('/path/file', \$buffer);
    write_file('/path/file', $buffer);

    # append
    write_file('/path/file', {append => 1}, @data);

    # no clobbering
    write_file('/path/file', {no_clobber => 1}, @data);
```

This function writes out an entire file in one call. By default `write_file`
returns `1` upon successfully writing the file or `undef` if it encountered
an error. You can change how errors are handled with the `err_mode` option.

The first argument to `write_file` is the filename.

The next argument(s) is either a hash reference or a flattened hash,
`key => value` pairs. The following options are available:

- append

    The `append` option is a boolean option, defaulted to false (`0`). Setting
    this option to true (`1`) will cause the data to be be written at the end of
    the current file. Internally this sets the `sysopen` mode flag `O_APPEND`.

    The ["append\_file" in File::Slurp](https://metacpan.org/pod/File%3A%3ASlurp#append_file) function sets this option by default.

- atomic

    The `atomic` option is a boolean option, defaulted to false (`0`). Setting
    this option to true (`1`) will cause the file to be be written to in an
    atomic fashion. A temporary file name is created using ["tempfile" in File::Temp](https://metacpan.org/pod/File%3A%3ATemp#tempfile).
    After the file is closed it is renamed to the original file name
    (and `rename` is an atomic operation on most OSes). If the program using
    this were to crash in the middle of this, then the temporary file could
    be left behind.

- binmode

    The `binmode` option is a string option, defaulted to empty (`''`). If you
    set the `binmode` option, then its value is passed to a call to `binmode` on
    the opened handle. You can use this to set the file to be read in binary mode,
    utf8, etc. See `perldoc -f binmode` for more.

- buf\_ref

    The `buf_ref` option is used to pass in a scalar reference which has the
    data to be written. If this is set then any data arguments (including
    the scalar reference shortcut) in `@_` will be ignored.

- err\_mode

    The `err_mode` option has three possible values: `quiet`, `carp`, or the
    default, `croak`. In `quiet` mode, all errors will be silent. In `carp` mode,
    all errors will be emitted as warnings. And, in `croak` mode, all errors will
    be emitted as exceptions. Take a look at [Try::Tiny](https://metacpan.org/pod/Try%3A%3ATiny) or
    [Syntax::Keyword::Try](https://metacpan.org/pod/Syntax%3A%3AKeyword%3A%3ATry) to see how to catch exceptions.

- no\_clobber

    The `no_clobber` option is a boolean option, defaulted to false (`0`). Setting
    this option to true (`1`) will ensure an that existing file will not be
    overwritten.

- perms

    The `perms` option sets the permissions of newly-created files. This value
    is modified by your process's `umask` and defaults to `0666` (same as
    `sysopen`).

    NOTE: this option is new as of File::Slurp version 9999.14.

# EXPORT

These are exported by default or with

```perl
    use File::Slurp qw(:std);
    # read_file write_file overwrite_file append_file read_dir
```

These are exported with

```perl
    use File::Slurp qw(:edit);
    # edit_file edit_file_lines
```

You can get all subs in the module exported with

```perl
    use File::Slurp qw(:all);
```

# SEE ALSO

- [File::Slurper](https://metacpan.org/pod/File%3A%3ASlurper) - Provides a straightforward set of functions for the most
common tasks of reading/writing text and binary files.
- [Path::Tiny](https://metacpan.org/pod/Path%3A%3ATiny) - Lightweight and comprehensive file handling, including simple
methods for reading, writing, and editing text and binary files.
- [Mojo::File](https://metacpan.org/pod/Mojo%3A%3AFile) - Similar to Path::Tiny for the [Mojo](https://metacpan.org/pod/Mojo) toolkit, always works in
bytes.

# AUTHOR

Uri Guttman, <`uri@stemsystems.com`>

# COPYRIGHT & LICENSE

Copyright (c) 2003 Uri Guttman. All rights reserved.

This program is free software; you can redistribute it and/or modify it
under the same terms as Perl itself.