t / t7300-clean.shon commit Merge branch 'dt/untracked-sparse' (a5315dd)
   1#!/bin/sh
   2#
   3# Copyright (c) 2007 Michael Spang
   4#
   5
   6test_description='git clean basic tests'
   7
   8. ./test-lib.sh
   9
  10git config clean.requireForce no
  11
  12test_expect_success 'setup' '
  13
  14        mkdir -p src &&
  15        touch src/part1.c Makefile &&
  16        echo build >.gitignore &&
  17        echo \*.o >>.gitignore &&
  18        git add . &&
  19        git commit -m setup &&
  20        touch src/part2.c README &&
  21        git add .
  22
  23'
  24
  25test_expect_success 'git clean with skip-worktree .gitignore' '
  26        git update-index --skip-worktree .gitignore &&
  27        rm .gitignore &&
  28        mkdir -p build docs &&
  29        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
  30        git clean &&
  31        test -f Makefile &&
  32        test -f README &&
  33        test -f src/part1.c &&
  34        test -f src/part2.c &&
  35        test ! -f a.out &&
  36        test ! -f src/part3.c &&
  37        test -f docs/manual.txt &&
  38        test -f obj.o &&
  39        test -f build/lib.so &&
  40        git update-index --no-skip-worktree .gitignore &&
  41        git checkout .gitignore
  42'
  43
  44test_expect_success 'git clean' '
  45
  46        mkdir -p build docs &&
  47        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
  48        git clean &&
  49        test -f Makefile &&
  50        test -f README &&
  51        test -f src/part1.c &&
  52        test -f src/part2.c &&
  53        test ! -f a.out &&
  54        test ! -f src/part3.c &&
  55        test -f docs/manual.txt &&
  56        test -f obj.o &&
  57        test -f build/lib.so
  58
  59'
  60
  61test_expect_success 'git clean src/' '
  62
  63        mkdir -p build docs &&
  64        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
  65        git clean src/ &&
  66        test -f Makefile &&
  67        test -f README &&
  68        test -f src/part1.c &&
  69        test -f src/part2.c &&
  70        test -f a.out &&
  71        test ! -f src/part3.c &&
  72        test -f docs/manual.txt &&
  73        test -f obj.o &&
  74        test -f build/lib.so
  75
  76'
  77
  78test_expect_success 'git clean src/ src/' '
  79
  80        mkdir -p build docs &&
  81        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
  82        git clean src/ src/ &&
  83        test -f Makefile &&
  84        test -f README &&
  85        test -f src/part1.c &&
  86        test -f src/part2.c &&
  87        test -f a.out &&
  88        test ! -f src/part3.c &&
  89        test -f docs/manual.txt &&
  90        test -f obj.o &&
  91        test -f build/lib.so
  92
  93'
  94
  95test_expect_success 'git clean with prefix' '
  96
  97        mkdir -p build docs src/test &&
  98        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so src/test/1.c &&
  99        (cd src/ && git clean) &&
 100        test -f Makefile &&
 101        test -f README &&
 102        test -f src/part1.c &&
 103        test -f src/part2.c &&
 104        test -f a.out &&
 105        test ! -f src/part3.c &&
 106        test -f src/test/1.c &&
 107        test -f docs/manual.txt &&
 108        test -f obj.o &&
 109        test -f build/lib.so
 110
 111'
 112
 113test_expect_success C_LOCALE_OUTPUT 'git clean with relative prefix' '
 114
 115        mkdir -p build docs &&
 116        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 117        would_clean=$(
 118                cd docs &&
 119                git clean -n ../src |
 120                sed -n -e "s|^Would remove ||p"
 121        ) &&
 122        verbose test "$would_clean" = ../src/part3.c
 123'
 124
 125test_expect_success C_LOCALE_OUTPUT 'git clean with absolute path' '
 126
 127        mkdir -p build docs &&
 128        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 129        would_clean=$(
 130                cd docs &&
 131                git clean -n "$(pwd)/../src" |
 132                sed -n -e "s|^Would remove ||p"
 133        ) &&
 134        verbose test "$would_clean" = ../src/part3.c
 135'
 136
 137test_expect_success 'git clean with out of work tree relative path' '
 138
 139        mkdir -p build docs &&
 140        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 141        (
 142                cd docs &&
 143                test_must_fail git clean -n ../..
 144        )
 145'
 146
 147test_expect_success 'git clean with out of work tree absolute path' '
 148
 149        mkdir -p build docs &&
 150        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 151        dd=$(cd .. && pwd) &&
 152        (
 153                cd docs &&
 154                test_must_fail git clean -n $dd
 155        )
 156'
 157
 158test_expect_success 'git clean -d with prefix and path' '
 159
 160        mkdir -p build docs src/feature &&
 161        touch a.out src/part3.c src/feature/file.c docs/manual.txt obj.o build/lib.so &&
 162        (cd src/ && git clean -d feature/) &&
 163        test -f Makefile &&
 164        test -f README &&
 165        test -f src/part1.c &&
 166        test -f src/part2.c &&
 167        test -f a.out &&
 168        test -f src/part3.c &&
 169        test ! -f src/feature/file.c &&
 170        test -f docs/manual.txt &&
 171        test -f obj.o &&
 172        test -f build/lib.so
 173
 174'
 175
 176test_expect_success SYMLINKS 'git clean symbolic link' '
 177
 178        mkdir -p build docs &&
 179        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 180        ln -s docs/manual.txt src/part4.c &&
 181        git clean &&
 182        test -f Makefile &&
 183        test -f README &&
 184        test -f src/part1.c &&
 185        test -f src/part2.c &&
 186        test ! -f a.out &&
 187        test ! -f src/part3.c &&
 188        test ! -f src/part4.c &&
 189        test -f docs/manual.txt &&
 190        test -f obj.o &&
 191        test -f build/lib.so
 192
 193'
 194
 195test_expect_success 'git clean with wildcard' '
 196
 197        touch a.clean b.clean other.c &&
 198        git clean "*.clean" &&
 199        test -f Makefile &&
 200        test -f README &&
 201        test -f src/part1.c &&
 202        test -f src/part2.c &&
 203        test ! -f a.clean &&
 204        test ! -f b.clean &&
 205        test -f other.c
 206
 207'
 208
 209test_expect_success 'git clean -n' '
 210
 211        mkdir -p build docs &&
 212        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 213        git clean -n &&
 214        test -f Makefile &&
 215        test -f README &&
 216        test -f src/part1.c &&
 217        test -f src/part2.c &&
 218        test -f a.out &&
 219        test -f src/part3.c &&
 220        test -f docs/manual.txt &&
 221        test -f obj.o &&
 222        test -f build/lib.so
 223
 224'
 225
 226test_expect_success 'git clean -d' '
 227
 228        mkdir -p build docs &&
 229        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 230        git clean -d &&
 231        test -f Makefile &&
 232        test -f README &&
 233        test -f src/part1.c &&
 234        test -f src/part2.c &&
 235        test ! -f a.out &&
 236        test ! -f src/part3.c &&
 237        test ! -d docs &&
 238        test -f obj.o &&
 239        test -f build/lib.so
 240
 241'
 242
 243test_expect_success 'git clean -d src/ examples/' '
 244
 245        mkdir -p build docs examples &&
 246        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so examples/1.c &&
 247        git clean -d src/ examples/ &&
 248        test -f Makefile &&
 249        test -f README &&
 250        test -f src/part1.c &&
 251        test -f src/part2.c &&
 252        test -f a.out &&
 253        test ! -f src/part3.c &&
 254        test ! -f examples/1.c &&
 255        test -f docs/manual.txt &&
 256        test -f obj.o &&
 257        test -f build/lib.so
 258
 259'
 260
 261test_expect_success 'git clean -x' '
 262
 263        mkdir -p build docs &&
 264        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 265        git clean -x &&
 266        test -f Makefile &&
 267        test -f README &&
 268        test -f src/part1.c &&
 269        test -f src/part2.c &&
 270        test ! -f a.out &&
 271        test ! -f src/part3.c &&
 272        test -f docs/manual.txt &&
 273        test ! -f obj.o &&
 274        test -f build/lib.so
 275
 276'
 277
 278test_expect_success 'git clean -d -x' '
 279
 280        mkdir -p build docs &&
 281        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 282        git clean -d -x &&
 283        test -f Makefile &&
 284        test -f README &&
 285        test -f src/part1.c &&
 286        test -f src/part2.c &&
 287        test ! -f a.out &&
 288        test ! -f src/part3.c &&
 289        test ! -d docs &&
 290        test ! -f obj.o &&
 291        test ! -d build
 292
 293'
 294
 295test_expect_success 'git clean -d -x with ignored tracked directory' '
 296
 297        mkdir -p build docs &&
 298        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 299        git clean -d -x -e src &&
 300        test -f Makefile &&
 301        test -f README &&
 302        test -f src/part1.c &&
 303        test -f src/part2.c &&
 304        test ! -f a.out &&
 305        test -f src/part3.c &&
 306        test ! -d docs &&
 307        test ! -f obj.o &&
 308        test ! -d build
 309
 310'
 311
 312test_expect_success 'git clean -X' '
 313
 314        mkdir -p build docs &&
 315        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 316        git clean -X &&
 317        test -f Makefile &&
 318        test -f README &&
 319        test -f src/part1.c &&
 320        test -f src/part2.c &&
 321        test -f a.out &&
 322        test -f src/part3.c &&
 323        test -f docs/manual.txt &&
 324        test ! -f obj.o &&
 325        test -f build/lib.so
 326
 327'
 328
 329test_expect_success 'git clean -d -X' '
 330
 331        mkdir -p build docs &&
 332        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 333        git clean -d -X &&
 334        test -f Makefile &&
 335        test -f README &&
 336        test -f src/part1.c &&
 337        test -f src/part2.c &&
 338        test -f a.out &&
 339        test -f src/part3.c &&
 340        test -f docs/manual.txt &&
 341        test ! -f obj.o &&
 342        test ! -d build
 343
 344'
 345
 346test_expect_success 'git clean -d -X with ignored tracked directory' '
 347
 348        mkdir -p build docs &&
 349        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 350        git clean -d -X -e src &&
 351        test -f Makefile &&
 352        test -f README &&
 353        test -f src/part1.c &&
 354        test -f src/part2.c &&
 355        test -f a.out &&
 356        test ! -f src/part3.c &&
 357        test -f docs/manual.txt &&
 358        test ! -f obj.o &&
 359        test ! -d build
 360
 361'
 362
 363test_expect_success 'clean.requireForce defaults to true' '
 364
 365        git config --unset clean.requireForce &&
 366        test_must_fail git clean
 367
 368'
 369
 370test_expect_success 'clean.requireForce' '
 371
 372        git config clean.requireForce true &&
 373        test_must_fail git clean
 374
 375'
 376
 377test_expect_success 'clean.requireForce and -n' '
 378
 379        mkdir -p build docs &&
 380        touch a.out src/part3.c docs/manual.txt obj.o build/lib.so &&
 381        git clean -n &&
 382        test -f Makefile &&
 383        test -f README &&
 384        test -f src/part1.c &&
 385        test -f src/part2.c &&
 386        test -f a.out &&
 387        test -f src/part3.c &&
 388        test -f docs/manual.txt &&
 389        test -f obj.o &&
 390        test -f build/lib.so
 391
 392'
 393
 394test_expect_success 'clean.requireForce and -f' '
 395
 396        git clean -f &&
 397        test -f README &&
 398        test -f src/part1.c &&
 399        test -f src/part2.c &&
 400        test ! -f a.out &&
 401        test ! -f src/part3.c &&
 402        test -f docs/manual.txt &&
 403        test -f obj.o &&
 404        test -f build/lib.so
 405
 406'
 407
 408test_expect_success C_LOCALE_OUTPUT 'core.excludesfile' '
 409
 410        echo excludes >excludes &&
 411        echo included >included &&
 412        git config core.excludesfile excludes &&
 413        output=$(git clean -n excludes included 2>&1) &&
 414        expr "$output" : ".*included" >/dev/null &&
 415        ! expr "$output" : ".*excludes" >/dev/null
 416
 417'
 418
 419test_expect_success SANITY 'removal failure' '
 420
 421        mkdir foo &&
 422        touch foo/bar &&
 423        test_when_finished "chmod 755 foo" &&
 424        (exec <foo/bar &&
 425         chmod 0 foo &&
 426         test_must_fail git clean -f -d)
 427'
 428
 429test_expect_success 'nested git work tree' '
 430        rm -fr foo bar baz &&
 431        mkdir -p foo bar baz/boo &&
 432        (
 433                cd foo &&
 434                git init &&
 435                >hello.world
 436                git add . &&
 437                git commit -a -m nested
 438        ) &&
 439        (
 440                cd bar &&
 441                >goodbye.people
 442        ) &&
 443        (
 444                cd baz/boo &&
 445                git init &&
 446                >deeper.world
 447                git add . &&
 448                git commit -a -m deeply.nested
 449        ) &&
 450        git clean -f -d &&
 451        test -f foo/.git/index &&
 452        test -f foo/hello.world &&
 453        test -f baz/boo/.git/index &&
 454        test -f baz/boo/deeper.world &&
 455        ! test -d bar
 456'
 457
 458test_expect_success 'should clean things that almost look like git but are not' '
 459        rm -fr almost_git almost_bare_git almost_submodule &&
 460        mkdir -p almost_git/.git/objects &&
 461        mkdir -p almost_git/.git/refs &&
 462        cat >almost_git/.git/HEAD <<-\EOF &&
 463        garbage
 464        EOF
 465        cp -r almost_git/.git/ almost_bare_git &&
 466        mkdir almost_submodule/ &&
 467        cat >almost_submodule/.git <<-\EOF &&
 468        garbage
 469        EOF
 470        test_when_finished "rm -rf almost_*" &&
 471        git clean -f -d &&
 472        test_path_is_missing almost_git &&
 473        test_path_is_missing almost_bare_git &&
 474        test_path_is_missing almost_submodule
 475'
 476
 477test_expect_success 'should not clean submodules' '
 478        rm -fr repo to_clean sub1 sub2 &&
 479        mkdir repo to_clean &&
 480        (
 481                cd repo &&
 482                git init &&
 483                test_commit msg hello.world
 484        ) &&
 485        git submodule add ./repo/.git sub1 &&
 486        git commit -m "sub1" &&
 487        git branch before_sub2 &&
 488        git submodule add ./repo/.git sub2 &&
 489        git commit -m "sub2" &&
 490        git checkout before_sub2 &&
 491        >to_clean/should_clean.this &&
 492        git clean -f -d &&
 493        test_path_is_file repo/.git/index &&
 494        test_path_is_file repo/hello.world &&
 495        test_path_is_file sub1/.git &&
 496        test_path_is_file sub1/hello.world &&
 497        test_path_is_file sub2/.git &&
 498        test_path_is_file sub2/hello.world &&
 499        test_path_is_missing to_clean
 500'
 501
 502test_expect_success POSIXPERM 'should avoid cleaning possible submodules' '
 503        rm -fr to_clean possible_sub1 &&
 504        mkdir to_clean possible_sub1 &&
 505        test_when_finished "rm -rf possible_sub*" &&
 506        echo "gitdir: foo" >possible_sub1/.git &&
 507        >possible_sub1/hello.world &&
 508        chmod 0 possible_sub1/.git &&
 509        >to_clean/should_clean.this &&
 510        git clean -f -d &&
 511        test_path_is_file possible_sub1/.git &&
 512        test_path_is_file possible_sub1/hello.world &&
 513        test_path_is_missing to_clean
 514'
 515
 516test_expect_success 'nested (empty) git should be kept' '
 517        rm -fr empty_repo to_clean &&
 518        git init empty_repo &&
 519        mkdir to_clean &&
 520        >to_clean/should_clean.this &&
 521        git clean -f -d &&
 522        test_path_is_file empty_repo/.git/HEAD &&
 523        test_path_is_missing to_clean
 524'
 525
 526test_expect_success 'nested bare repositories should be cleaned' '
 527        rm -fr bare1 bare2 subdir &&
 528        git init --bare bare1 &&
 529        git clone --local --bare . bare2 &&
 530        mkdir subdir &&
 531        cp -r bare2 subdir/bare3 &&
 532        git clean -f -d &&
 533        test_path_is_missing bare1 &&
 534        test_path_is_missing bare2 &&
 535        test_path_is_missing subdir
 536'
 537
 538test_expect_failure 'nested (empty) bare repositories should be cleaned even when in .git' '
 539        rm -fr strange_bare &&
 540        mkdir strange_bare &&
 541        git init --bare strange_bare/.git &&
 542        git clean -f -d &&
 543        test_path_is_missing strange_bare
 544'
 545
 546test_expect_failure 'nested (non-empty) bare repositories should be cleaned even when in .git' '
 547        rm -fr strange_bare &&
 548        mkdir strange_bare &&
 549        git clone --local --bare . strange_bare/.git &&
 550        git clean -f -d &&
 551        test_path_is_missing strange_bare
 552'
 553
 554test_expect_success 'giving path in nested git work tree will remove it' '
 555        rm -fr repo &&
 556        mkdir repo &&
 557        (
 558                cd repo &&
 559                git init &&
 560                mkdir -p bar/baz &&
 561                test_commit msg bar/baz/hello.world
 562        ) &&
 563        git clean -f -d repo/bar/baz &&
 564        test_path_is_file repo/.git/HEAD &&
 565        test_path_is_dir repo/bar/ &&
 566        test_path_is_missing repo/bar/baz
 567'
 568
 569test_expect_success 'giving path to nested .git will not remove it' '
 570        rm -fr repo &&
 571        mkdir repo untracked &&
 572        (
 573                cd repo &&
 574                git init &&
 575                test_commit msg hello.world
 576        ) &&
 577        git clean -f -d repo/.git &&
 578        test_path_is_file repo/.git/HEAD &&
 579        test_path_is_dir repo/.git/refs &&
 580        test_path_is_dir repo/.git/objects &&
 581        test_path_is_dir untracked/
 582'
 583
 584test_expect_success 'giving path to nested .git/ will remove contents' '
 585        rm -fr repo untracked &&
 586        mkdir repo untracked &&
 587        (
 588                cd repo &&
 589                git init &&
 590                test_commit msg hello.world
 591        ) &&
 592        git clean -f -d repo/.git/ &&
 593        test_path_is_dir repo/.git &&
 594        test_dir_is_empty repo/.git &&
 595        test_path_is_dir untracked/
 596'
 597
 598test_expect_success 'force removal of nested git work tree' '
 599        rm -fr foo bar baz &&
 600        mkdir -p foo bar baz/boo &&
 601        (
 602                cd foo &&
 603                git init &&
 604                >hello.world
 605                git add . &&
 606                git commit -a -m nested
 607        ) &&
 608        (
 609                cd bar &&
 610                >goodbye.people
 611        ) &&
 612        (
 613                cd baz/boo &&
 614                git init &&
 615                >deeper.world
 616                git add . &&
 617                git commit -a -m deeply.nested
 618        ) &&
 619        git clean -f -f -d &&
 620        ! test -d foo &&
 621        ! test -d bar &&
 622        ! test -d baz
 623'
 624
 625test_expect_success 'git clean -e' '
 626        rm -fr repo &&
 627        mkdir repo &&
 628        (
 629                cd repo &&
 630                git init &&
 631                touch known 1 2 3 &&
 632                git add known &&
 633                git clean -f -e 1 -e 2 &&
 634                test -e 1 &&
 635                test -e 2 &&
 636                ! (test -e 3) &&
 637                test -e known
 638        )
 639'
 640
 641test_expect_success SANITY 'git clean -d with an unreadable empty directory' '
 642        mkdir foo &&
 643        chmod a= foo &&
 644        git clean -dfx foo &&
 645        ! test -d foo
 646'
 647
 648test_expect_success 'git clean -d respects pathspecs (dir is prefix of pathspec)' '
 649        mkdir -p foo &&
 650        mkdir -p foobar &&
 651        git clean -df foobar &&
 652        test_path_is_dir foo &&
 653        test_path_is_missing foobar
 654'
 655
 656test_expect_success 'git clean -d respects pathspecs (pathspec is prefix of dir)' '
 657        mkdir -p foo &&
 658        mkdir -p foobar &&
 659        git clean -df foo &&
 660        test_path_is_missing foo &&
 661        test_path_is_dir foobar
 662'
 663
 664test_done