From 2c255af1876f0a38bce8044c5529cbacd590554a Mon Sep 17 00:00:00 2001 From: Adam Spiers Date: Mon, 1 Apr 2024 17:00:13 +0100 Subject: [PATCH] t/unstow_orig: split into subtests --- t/unstow_orig.t | 785 +++++++++++++++++++++++++++----------------------------- 1 file changed, 382 insertions(+), 403 deletions(-) rewrite t/unstow_orig.t (89%) diff --git a/t/unstow_orig.t b/t/unstow_orig.t dissimilarity index 89% index e893c56..94f771d 100755 --- a/t/unstow_orig.t +++ b/t/unstow_orig.t @@ -1,403 +1,382 @@ -#!/usr/bin/perl -# -# This file is part of GNU Stow. -# -# GNU Stow is free software: you can redistribute it and/or modify it -# under the terms of the GNU General Public License as published by -# the Free Software Foundation, either version 3 of the License, or -# (at your option) any later version. -# -# GNU Stow is distributed in the hope that it will be useful, but -# WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU -# General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program. If not, see https://www.gnu.org/licenses/. - -# -# Test unstowing packages in compat mode -# - -use strict; -use warnings; - -use File::Spec qw(make_path); -use Test::More tests => 37; -use Test::Output; -use English qw(-no_match_vars); - -use testutil; -use Stow::Util qw(canon_path); - -init_test_dirs(); -cd("$TEST_DIR/target"); - -# Note that each of the following tests use a distinct set of files - -my $stow; -my %conflicts; - -# -# unstow a simple tree minimally -# - -$stow = new_compat_Stow(); - -make_path('../stow/pkg1/bin1'); -make_file('../stow/pkg1/bin1/file1'); -make_link('bin1', '../stow/pkg1/bin1'); - -$stow->plan_unstow('pkg1'); -$stow->process_tasks(); -ok( - $stow->get_conflict_count == 0 && - -f '../stow/pkg1/bin1/file1' && ! -e 'bin1' - => 'unstow a simple tree' -); - -# -# unstow a simple tree from an existing directory -# -$stow = new_compat_Stow(); - -make_path('lib2'); -make_path('../stow/pkg2/lib2'); -make_file('../stow/pkg2/lib2/file2'); -make_link('lib2/file2', '../../stow/pkg2/lib2/file2'); -$stow->plan_unstow('pkg2'); -$stow->process_tasks(); -ok( - $stow->get_conflict_count == 0 && - -f '../stow/pkg2/lib2/file2' && -d 'lib2' - => 'unstow simple tree from a pre-existing directory' -); - -# -# fold tree after unstowing -# -$stow = new_compat_Stow(); - -make_path('bin3'); - -make_path('../stow/pkg3a/bin3'); -make_file('../stow/pkg3a/bin3/file3a'); -make_link('bin3/file3a' => '../../stow/pkg3a/bin3/file3a'); # emulate stow - -make_path('../stow/pkg3b/bin3'); -make_file('../stow/pkg3b/bin3/file3b'); -make_link('bin3/file3b' => '../../stow/pkg3b/bin3/file3b'); # emulate stow -$stow->plan_unstow('pkg3b'); -$stow->process_tasks(); -ok( - $stow->get_conflict_count == 0 && - -l 'bin3' && - readlink('bin3') eq '../stow/pkg3a/bin3' - => 'fold tree after unstowing' -); - -# -# existing link is owned by stow but is invalid so it gets removed anyway -# -$stow = new_compat_Stow(); - -make_path('bin4'); -make_path('../stow/pkg4/bin4'); -make_file('../stow/pkg4/bin4/file4'); -make_invalid_link('bin4/file4', '../../stow/pkg4/bin4/does-not-exist'); - -$stow->plan_unstow('pkg4'); -$stow->process_tasks(); -ok( - $stow->get_conflict_count == 0 && - ! -e 'bin4/file4' - => q(remove invalid link owned by stow) -); - -# -# Existing link is not owned by stow -# -$stow = new_compat_Stow(); - -make_path('../stow/pkg5/bin5'); -make_invalid_link('bin5', '../not-stow'); - -$stow->plan_unstow('pkg5'); -# Unlike the corresponding stow_contents.t test, this doesn't -# cause any conflicts. -# -#like( -# $Conflicts[-1], qr(can't unlink.*not owned by stow) -# => q(existing link not owned by stow) -#); -ok( - -l 'bin5' && readlink('bin5') eq '../not-stow' - => q(existing link not owned by stow) -); - -# -# Target already exists, is owned by stow, but points to a different package -# -$stow = new_compat_Stow(); - -make_path('bin6'); -make_path('../stow/pkg6a/bin6'); -make_file('../stow/pkg6a/bin6/file6'); -make_link('bin6/file6', '../../stow/pkg6a/bin6/file6'); - -make_path('../stow/pkg6b/bin6'); -make_file('../stow/pkg6b/bin6/file6'); - -$stow->plan_unstow('pkg6b'); -ok( - $stow->get_conflict_count == 0 && - -l 'bin6/file6' && - readlink('bin6/file6') eq '../../stow/pkg6a/bin6/file6' - => q(ignore existing link that points to a different package) -); - -# -# Don't unlink anything under the stow directory -# -make_path('stow'); # make out stow dir a subdir of target -$stow = new_compat_Stow(dir => 'stow'); - -# emulate stowing into ourself (bizarre corner case or accident) -make_path('stow/pkg7a/stow/pkg7b'); -make_file('stow/pkg7a/stow/pkg7b/file7b'); -make_link('stow/pkg7b', '../stow/pkg7a/stow/pkg7b'); - -capture_stderr(); -$stow->plan_unstow('pkg7b'); -is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg7b'); -ok( - $stow->get_conflict_count == 0 && - -l 'stow/pkg7b' && - readlink('stow/pkg7b') eq '../stow/pkg7a/stow/pkg7b' - => q(don't unlink any nodes under the stow directory) -); -like($stderr, - qr/WARNING: skipping target which was current stow directory stow/ - => "warn when unstowing from ourself"); -uncapture_stderr(); - -# -# Don't unlink any nodes under another stow directory -# -$stow = new_compat_Stow(dir => 'stow'); - -make_path('stow2'); # make our alternate stow dir a subdir of target -make_file('stow2/.stow'); - -# emulate stowing into ourself (bizarre corner case or accident) -make_path('stow/pkg8a/stow2/pkg8b'); -make_file('stow/pkg8a/stow2/pkg8b/file8b'); -make_link('stow2/pkg8b', '../stow/pkg8a/stow2/pkg8b'); - -capture_stderr(); -$stow->plan_unstow('pkg8a'); -is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg8a'); -ok( - $stow->get_conflict_count == 0 && - -l 'stow2/pkg8b' && - readlink('stow2/pkg8b') eq '../stow/pkg8a/stow2/pkg8b' - => q(don't unlink any nodes under another stow directory) -); -like($stderr, - qr/WARNING: skipping target which was current stow directory stow/ - => "warn when skipping unstowing"); -uncapture_stderr(); - -# -# overriding already stowed documentation -# - -# This will be used by this and subsequent tests -sub check_protected_dirs_skipped { - for my $dir (qw{stow stow2}) { - like($stderr, - qr/WARNING: skipping marked Stow directory $dir/ - => "warn when skipping marked directory $dir"); - } - uncapture_stderr(); -} - -$stow = new_compat_Stow(override => ['man9', 'info9']); -make_file('stow/.stow'); - -make_path('../stow/pkg9a/man9/man1'); -make_file('../stow/pkg9a/man9/man1/file9.1'); -make_path('man9/man1'); -make_link('man9/man1/file9.1' => '../../../stow/pkg9a/man9/man1/file9.1'); # emulate stow - -make_path('../stow/pkg9b/man9/man1'); -make_file('../stow/pkg9b/man9/man1/file9.1'); -capture_stderr(); -$stow->plan_unstow('pkg9b'); -$stow->process_tasks(); -ok( - $stow->get_conflict_count == 0 && - !-l 'man9/man1/file9.1' - => 'overriding existing documentation files' -); -check_protected_dirs_skipped(); - -# -# deferring to already stowed documentation -# -$stow = new_compat_Stow(defer => ['man10', 'info10']); - -make_path('../stow/pkg10a/man10/man1'); -make_file('../stow/pkg10a/man10/man1/file10a.1'); -make_path('man10/man1'); -make_link('man10/man1/file10a.1' => '../../../stow/pkg10a/man10/man1/file10a.1'); - -# need this to block folding -make_path('../stow/pkg10b/man10/man1'); -make_file('../stow/pkg10b/man10/man1/file10b.1'); -make_link('man10/man1/file10b.1' => '../../../stow/pkg10b/man10/man1/file10b.1'); - - -make_path('../stow/pkg10c/man10/man1'); -make_file('../stow/pkg10c/man10/man1/file10a.1'); -capture_stderr(); -$stow->plan_unstow('pkg10c'); -is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg10c'); -ok( - $stow->get_conflict_count == 0 && - readlink('man10/man1/file10a.1') eq '../../../stow/pkg10a/man10/man1/file10a.1' - => 'defer to existing documentation files' -); -check_protected_dirs_skipped(); - -# -# Ignore temp files -# -$stow = new_compat_Stow(ignore => ['~', '\.#.*']); - -make_path('../stow/pkg12/man12/man1'); -make_file('../stow/pkg12/man12/man1/file12.1'); -make_file('../stow/pkg12/man12/man1/file12.1~'); -make_file('../stow/pkg12/man12/man1/.#file12.1'); -make_path('man12/man1'); -make_link('man12/man1/file12.1' => '../../../stow/pkg12/man12/man1/file12.1'); - -capture_stderr(); -$stow->plan_unstow('pkg12'); -$stow->process_tasks(); -ok( - $stow->get_conflict_count == 0 && - !-e 'man12/man1/file12.1' - => 'ignore temp files' -); -check_protected_dirs_skipped(); - -# -# Unstow an already unstowed package -# -$stow = new_compat_Stow(); -capture_stderr(); -$stow->plan_unstow('pkg12'); -is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg12'); -ok( - $stow->get_conflict_count == 0 - => 'unstow already unstowed package pkg12' -); -check_protected_dirs_skipped(); - -# -# Unstow a never stowed package -# - -eval { remove_dir("$TEST_DIR/target"); }; -mkdir("$TEST_DIR/target"); - -$stow = new_compat_Stow(); -capture_stderr(); -$stow->plan_unstow('pkg12'); -is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg12 which was never stowed'); -ok( - $stow->get_conflict_count == 0 - => 'unstow never stowed package pkg12' -); -check_protected_dirs_skipped(); - -# -# Unstowing when target contains a real file shouldn't be an issue. -# -make_file('man12/man1/file12.1'); - -$stow = new_compat_Stow(); -capture_stderr(); -$stow->plan_unstow('pkg12'); -is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg12 for third time'); -%conflicts = $stow->get_conflicts; -ok( - $stow->get_conflict_count == 1 && - $conflicts{unstow}{pkg12}[0] - =~ m!existing target is neither a link nor a directory: man12/man1/file12\.1! - => 'unstow pkg12 for third time' -); -check_protected_dirs_skipped(); - -# -# unstow a simple tree minimally when cwd isn't target -# -cd('../..'); -$stow = new_Stow(dir => "$TEST_DIR/stow", target => "$TEST_DIR/target"); - -make_path("$TEST_DIR/stow/pkg13/bin13"); -make_file("$TEST_DIR/stow/pkg13/bin13/file13"); -make_link("$TEST_DIR/target/bin13", '../stow/pkg13/bin13'); - -$stow->plan_unstow('pkg13'); -$stow->process_tasks(); -ok( - $stow->get_conflict_count == 0 && - -f "$TEST_DIR/stow/pkg13/bin13/file13" && ! -e "$TEST_DIR/target/bin13" - => 'unstow a simple tree' -); - -# -# unstow a simple tree minimally with absolute stow dir when cwd isn't -# target -# -$stow = new_Stow(dir => canon_path("$TEST_DIR/stow"), - target => "$TEST_DIR/target"); - -make_path("$TEST_DIR/stow/pkg14/bin14"); -make_file("$TEST_DIR/stow/pkg14/bin14/file14"); -make_link("$TEST_DIR/target/bin14", '../stow/pkg14/bin14'); - -$stow->plan_unstow('pkg14'); -$stow->process_tasks(); -ok( - $stow->get_conflict_count == 0 && - -f "$TEST_DIR/stow/pkg14/bin14/file14" && ! -e "$TEST_DIR/target/bin14" - => 'unstow a simple tree with absolute stow dir' -); - -# -# unstow a simple tree minimally with absolute stow AND target dirs -# when cwd isn't target -# -$stow = new_Stow(dir => canon_path("$TEST_DIR/stow"), - target => canon_path("$TEST_DIR/target")); - -make_path("$TEST_DIR/stow/pkg15/bin15"); -make_file("$TEST_DIR/stow/pkg15/bin15/file15"); -make_link("$TEST_DIR/target/bin15", '../stow/pkg15/bin15'); - -$stow->plan_unstow('pkg15'); -$stow->process_tasks(); -ok( - $stow->get_conflict_count == 0 && - -f "$TEST_DIR/stow/pkg15/bin15/file15" && ! -e "$TEST_DIR/target/bin15" - => 'unstow a simple tree with absolute stow and target dirs' -); - - -# Todo -# -# Test cleaning up subdirs with --paranoid option - +#!/usr/bin/perl +# +# This file is part of GNU Stow. +# +# GNU Stow is free software: you can redistribute it and/or modify it +# under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# GNU Stow is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see https://www.gnu.org/licenses/. + +# +# Test unstowing packages in compat mode +# + +use strict; +use warnings; + +use File::Spec qw(make_path); +use Test::More tests => 17; +use Test::Output; +use English qw(-no_match_vars); + +use testutil; +use Stow::Util qw(canon_path); + +init_test_dirs(); +cd("$TEST_DIR/target"); + +# Note that each of the following tests use a distinct set of files + +my $stow; +my %conflicts; + +subtest("unstow a simple tree minimally", sub { + plan tests => 3; + my $stow = new_compat_Stow(); + + make_path('../stow/pkg1/bin1'); + make_file('../stow/pkg1/bin1/file1'); + make_link('bin1', '../stow/pkg1/bin1'); + + $stow->plan_unstow('pkg1'); + $stow->process_tasks(); + is($stow->get_conflict_count, 0); + ok(-f '../stow/pkg1/bin1/file1'); + ok(! -e 'bin1' => 'unstow a simple tree'); +}); + +subtest("unstow a simple tree from an existing directory", sub { + plan tests => 3; + my $stow = new_compat_Stow(); + + make_path('lib2'); + make_path('../stow/pkg2/lib2'); + make_file('../stow/pkg2/lib2/file2'); + make_link('lib2/file2', '../../stow/pkg2/lib2/file2'); + $stow->plan_unstow('pkg2'); + $stow->process_tasks(); + is($stow->get_conflict_count, 0); + ok(-f '../stow/pkg2/lib2/file2'); + ok(-d 'lib2' + => 'unstow simple tree from a pre-existing directory' + ); +}); + +subtest("fold tree after unstowing", sub { + plan tests => 3; + my $stow = new_compat_Stow(); + + make_path('bin3'); + + make_path('../stow/pkg3a/bin3'); + make_file('../stow/pkg3a/bin3/file3a'); + make_link('bin3/file3a' => '../../stow/pkg3a/bin3/file3a'); # emulate stow + + make_path('../stow/pkg3b/bin3'); + make_file('../stow/pkg3b/bin3/file3b'); + make_link('bin3/file3b' => '../../stow/pkg3b/bin3/file3b'); # emulate stow + $stow->plan_unstow('pkg3b'); + $stow->process_tasks(); + is($stow->get_conflict_count, 0); + ok(-l 'bin3'); + is(readlink('bin3'), '../stow/pkg3a/bin3' + => 'fold tree after unstowing' + ); +}); + +subtest("existing link is owned by stow but is invalid so it gets removed anyway", sub { + plan tests => 2; + my $stow = new_compat_Stow(); + + make_path('bin4'); + make_path('../stow/pkg4/bin4'); + make_file('../stow/pkg4/bin4/file4'); + make_invalid_link('bin4/file4', '../../stow/pkg4/bin4/does-not-exist'); + + $stow->plan_unstow('pkg4'); + $stow->process_tasks(); + is($stow->get_conflict_count, 0); + ok(! -e 'bin4/file4' + => q(remove invalid link owned by stow) + ); +}); + +subtest("Existing link is not owned by stow", sub { + plan tests => 2; + my $stow = new_compat_Stow(); + + make_path('../stow/pkg5/bin5'); + make_invalid_link('bin5', '../not-stow'); + + $stow->plan_unstow('pkg5'); + # Unlike the corresponding stow_contents.t test, this doesn't + # cause any conflicts. + # + #like( + # $Conflicts[-1], qr(can't unlink.*not owned by stow) + # => q(existing link not owned by stow) + #); + ok(-l 'bin5'); + ok(readlink('bin5') eq '../not-stow' + => q(existing link not owned by stow) + ); +}); + +subtest("Target already exists, is owned by stow, but points to a different package", sub { + plan tests => 3; + my $stow = new_compat_Stow(); + + make_path('bin6'); + make_path('../stow/pkg6a/bin6'); + make_file('../stow/pkg6a/bin6/file6'); + make_link('bin6/file6', '../../stow/pkg6a/bin6/file6'); + + make_path('../stow/pkg6b/bin6'); + make_file('../stow/pkg6b/bin6/file6'); + + $stow->plan_unstow('pkg6b'); + is($stow->get_conflict_count, 0); + ok(-l 'bin6/file6'); + ok( + readlink('bin6/file6') eq '../../stow/pkg6a/bin6/file6' + => q(ignore existing link that points to a different package) + ); +}); + +subtest("Don't unlink anything under the stow directory", sub { + plan tests => 5; + make_path('stow'); # make stow dir a subdir of target + my $stow = new_compat_Stow(dir => 'stow'); + + # emulate stowing into ourself (bizarre corner case or accident) + make_path('stow/pkg7a/stow/pkg7b'); + make_file('stow/pkg7a/stow/pkg7b/file7b'); + make_link('stow/pkg7b', '../stow/pkg7a/stow/pkg7b'); + + capture_stderr(); + $stow->plan_unstow('pkg7b'); + is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg7b'); + is($stow->get_conflict_count, 0); + ok(-l 'stow/pkg7b'); + ok(readlink('stow/pkg7b') eq '../stow/pkg7a/stow/pkg7b' + => q(don't unlink any nodes under the stow directory) + ); + like($stderr, + qr/WARNING: skipping target which was current stow directory stow/ + => "warn when unstowing from ourself"); + uncapture_stderr(); +}); + +subtest("Don't unlink any nodes under another stow directory", sub { + plan tests => 5; + my $stow = new_compat_Stow(dir => 'stow'); + + make_path('stow2'); # make our alternate stow dir a subdir of target + make_file('stow2/.stow'); + + # emulate stowing into ourself (bizarre corner case or accident) + make_path('stow/pkg8a/stow2/pkg8b'); + make_file('stow/pkg8a/stow2/pkg8b/file8b'); + make_link('stow2/pkg8b', '../stow/pkg8a/stow2/pkg8b'); + + capture_stderr(); + $stow->plan_unstow('pkg8a'); + is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg8a'); + is($stow->get_conflict_count, 0); + ok(-l 'stow2/pkg8b'); + ok(readlink('stow2/pkg8b') eq '../stow/pkg8a/stow2/pkg8b' + => q(don't unlink any nodes under another stow directory) + ); + like($stderr, + qr/WARNING: skipping target which was current stow directory stow/ + => "warn when skipping unstowing"); + uncapture_stderr(); +}); + +# This will be used by subsequent tests +sub check_protected_dirs_skipped { + for my $dir (qw{stow stow2}) { + like($stderr, + qr/WARNING: skipping marked Stow directory $dir/ + => "warn when skipping marked directory $dir"); + } + uncapture_stderr(); +} + +subtest("overriding already stowed documentation", sub { + plan tests => 4; + + my $stow = new_compat_Stow(override => ['man9', 'info9']); + make_file('stow/.stow'); + + make_path('../stow/pkg9a/man9/man1'); + make_file('../stow/pkg9a/man9/man1/file9.1'); + make_path('man9/man1'); + make_link('man9/man1/file9.1' => '../../../stow/pkg9a/man9/man1/file9.1'); # emulate stow + + make_path('../stow/pkg9b/man9/man1'); + make_file('../stow/pkg9b/man9/man1/file9.1'); + capture_stderr(); + $stow->plan_unstow('pkg9b'); + $stow->process_tasks(); + is($stow->get_conflict_count, 0); + ok(!-l 'man9/man1/file9.1' + => 'overriding existing documentation files' + ); + check_protected_dirs_skipped(); +}); + +subtest("deferring to already stowed documentation", sub { + plan tests => 5; + my $stow = new_compat_Stow(defer => ['man10', 'info10']); + + make_path('../stow/pkg10a/man10/man1'); + make_file('../stow/pkg10a/man10/man1/file10a.1'); + make_path('man10/man1'); + make_link('man10/man1/file10a.1' => '../../../stow/pkg10a/man10/man1/file10a.1'); + + # need this to block folding + make_path('../stow/pkg10b/man10/man1'); + make_file('../stow/pkg10b/man10/man1/file10b.1'); + make_link('man10/man1/file10b.1' => '../../../stow/pkg10b/man10/man1/file10b.1'); + + make_path('../stow/pkg10c/man10/man1'); + make_file('../stow/pkg10c/man10/man1/file10a.1'); + capture_stderr(); + $stow->plan_unstow('pkg10c'); + is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg10c'); + is($stow->get_conflict_count, 0); + ok(readlink('man10/man1/file10a.1') eq '../../../stow/pkg10a/man10/man1/file10a.1' + => 'defer to existing documentation files' + ); + check_protected_dirs_skipped(); +}); + +subtest("Ignore temp files", sub { + plan tests => 4; + my $stow = new_compat_Stow(ignore => ['~', '\.#.*']); + + make_path('../stow/pkg12/man12/man1'); + make_file('../stow/pkg12/man12/man1/file12.1'); + make_file('../stow/pkg12/man12/man1/file12.1~'); + make_file('../stow/pkg12/man12/man1/.#file12.1'); + make_path('man12/man1'); + make_link('man12/man1/file12.1' => '../../../stow/pkg12/man12/man1/file12.1'); + + capture_stderr(); + $stow->plan_unstow('pkg12'); + $stow->process_tasks(); + is($stow->get_conflict_count, 0); + ok(!-e 'man12/man1/file12.1' => 'ignore temp files'); + check_protected_dirs_skipped(); +}); + +subtest("Unstow an already unstowed package", sub { + plan tests => 4; + my $stow = new_compat_Stow(); + capture_stderr(); + $stow->plan_unstow('pkg12'); + is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg12'); + ok( + $stow->get_conflict_count == 0 + => 'unstow already unstowed package pkg12' + ); + check_protected_dirs_skipped(); +}); + +subtest("Unstow a never stowed package", sub { + plan tests => 4; + + eval { remove_dir("$TEST_DIR/target"); }; + mkdir("$TEST_DIR/target"); + + my $stow = new_compat_Stow(); + capture_stderr(); + $stow->plan_unstow('pkg12'); + is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg12 which was never stowed'); + ok( + $stow->get_conflict_count == 0 + => 'unstow never stowed package pkg12' + ); + check_protected_dirs_skipped(); +}); + +subtest("Unstowing when target contains a real file shouldn't be an issue", sub { + plan tests => 5; + make_file('man12/man1/file12.1'); + + my $stow = new_compat_Stow(); + capture_stderr(); + $stow->plan_unstow('pkg12'); + is($stow->get_tasks, 0, 'no tasks to process when unstowing pkg12 for third time'); + %conflicts = $stow->get_conflicts; + ok($stow->get_conflict_count == 1); + ok($conflicts{unstow}{pkg12}[0] + =~ m!existing target is neither a link nor a directory: man12/man1/file12\.1! + => 'unstow pkg12 for third time' + ); + check_protected_dirs_skipped(); +}); + +subtest("unstow a simple tree minimally when cwd isn't target", sub { + plan tests => 3; + cd('../..'); + my $stow = new_Stow(dir => "$TEST_DIR/stow", target => "$TEST_DIR/target"); + + make_path("$TEST_DIR/stow/pkg13/bin13"); + make_file("$TEST_DIR/stow/pkg13/bin13/file13"); + make_link("$TEST_DIR/target/bin13", '../stow/pkg13/bin13'); + + $stow->plan_unstow('pkg13'); + $stow->process_tasks(); + is($stow->get_conflict_count, 0); + ok(-f "$TEST_DIR/stow/pkg13/bin13/file13"); + ok(! -e "$TEST_DIR/target/bin13" => 'unstow a simple tree'); +}); + +subtest("unstow a simple tree minimally with absolute stow dir when cwd isn't target", sub { + plan tests => 3; + my $stow = new_Stow(dir => canon_path("$TEST_DIR/stow"), + target => "$TEST_DIR/target"); + + make_path("$TEST_DIR/stow/pkg14/bin14"); + make_file("$TEST_DIR/stow/pkg14/bin14/file14"); + make_link("$TEST_DIR/target/bin14", '../stow/pkg14/bin14'); + + $stow->plan_unstow('pkg14'); + $stow->process_tasks(); + is($stow->get_conflict_count, 0); + ok(-f "$TEST_DIR/stow/pkg14/bin14/file14"); + ok(! -e "$TEST_DIR/target/bin14" + => 'unstow a simple tree with absolute stow dir' + ); +}); + +subtest("unstow a simple tree minimally with absolute stow AND target dirs when cwd isn't target", sub { + plan tests => 3; + my $stow = new_Stow(dir => canon_path("$TEST_DIR/stow"), + target => canon_path("$TEST_DIR/target")); + make_path("$TEST_DIR/stow/pkg15/bin15"); + make_file("$TEST_DIR/stow/pkg15/bin15/file15"); + make_link("$TEST_DIR/target/bin15", '../stow/pkg15/bin15'); + + $stow->plan_unstow('pkg15'); + $stow->process_tasks(); + is($stow->get_conflict_count, 0); + ok(-f "$TEST_DIR/stow/pkg15/bin15/file15"); + ok(! -e "$TEST_DIR/target/bin15" + => 'unstow a simple tree with absolute stow and target dirs' + ); +}); + +# subtest("Test cleaning up subdirs with --paranoid option", sub { +# TODO +# }); -- 2.11.4.GIT