From a5344a3940f292d8d4f8907f92a54bf726b87e44 Mon Sep 17 00:00:00 2001 From: patrick brisbin Date: Fri, 23 Aug 2013 14:31:32 -0400 Subject: An integration test suite This test suite uses cram to run integration tests through `/bin/sh`. The tests are all high-level acceptance tests; they should work regardless of the implemention code. To run them, you must first install cram: sudo pip install cram Then the `check` target will run them: make check Failure output should be printed clearly to stdout, but in general: full test output is in `test/test-suite.log` and output specific to a test named `foo.t` is in `foo.t.log`. Tests are now encouraged in `CONTRIBUTING.md` as part of the normal pull request process. This is a TAP-enabled test suite. --- .gitignore | 7 +++++++ CONTRIBUTING.md | 37 +++++++++++++++++++++++++++++----- Makefile.am | 2 +- README.md | 2 +- configure.ac | 2 +- test/Makefile.am | 20 +++++++++++++++++++ test/helper.sh | 34 +++++++++++++++++++++++++++++++ test/lsrc-dotfiles-dirs.t | 13 ++++++++++++ test/lsrc-excludes.t | 20 +++++++++++++++++++ test/lsrc-hostname.t | 13 ++++++++++++ test/lsrc-sigils.t | 16 +++++++++++++++ test/lsrc-tags.t | 14 +++++++++++++ test/lsrc-usage.t | 7 +++++++ test/lsrc.t | 14 +++++++++++++ test/mkrc-alternate-dotfiles-dir.t | 10 ++++++++++ test/mkrc-copy-file.t | 15 ++++++++++++++ test/mkrc-host-file.t | 9 +++++++++ test/mkrc-simple-output.t | 41 ++++++++++++++++++++++++++++++++++++++ test/mkrc-tagged-file.t | 9 +++++++++ test/mkrc-usage.t | 14 +++++++++++++ test/rcrc-custom.t | 16 +++++++++++++++ test/rcrc.t | 16 +++++++++++++++ test/rcup-link-files.t | 15 ++++++++++++++ test/rcup-usage.t | 7 +++++++ 24 files changed, 345 insertions(+), 8 deletions(-) create mode 100644 test/Makefile.am create mode 100644 test/helper.sh create mode 100644 test/lsrc-dotfiles-dirs.t create mode 100644 test/lsrc-excludes.t create mode 100644 test/lsrc-hostname.t create mode 100644 test/lsrc-sigils.t create mode 100644 test/lsrc-tags.t create mode 100644 test/lsrc-usage.t create mode 100644 test/lsrc.t create mode 100644 test/mkrc-alternate-dotfiles-dir.t create mode 100644 test/mkrc-copy-file.t create mode 100644 test/mkrc-host-file.t create mode 100644 test/mkrc-simple-output.t create mode 100644 test/mkrc-tagged-file.t create mode 100644 test/mkrc-usage.t create mode 100644 test/rcrc-custom.t create mode 100644 test/rcrc.t create mode 100644 test/rcup-link-files.t create mode 100644 test/rcup-usage.t diff --git a/.gitignore b/.gitignore index d7d26c6..91c5a2c 100644 --- a/.gitignore +++ b/.gitignore @@ -33,5 +33,12 @@ release-arch deb-build rcm-* +# Files generated for or during testing +test-driver +*.t.err +*.t.trs +*.t.log +test/test-suite.log + # Other generated files man/rcm.7 diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index fcf9da1..478dd56 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -4,18 +4,15 @@ Contributing Overview -------- -- We do not currently have a test suite. - Update `NEWS.md.in`. - Update `.mailmap`. +- Write a test covering your feature or fix. +- Ensure existing and new tests are passing. - Submit a pull request on GitHub. Explanation ----------- -Since we do not yet have a test suite, you should make sure to install -and try your patch in a various scenarios. We will also entertain a -contribution with a test case. - Consider updating `NEWS.md.in`. The topmost section is for the upcoming release. Bugfixes should be marked with `BUGFIX`. Small things (typos, code style) should be grouped but with multiple authors (`Documentation @@ -25,7 +22,37 @@ We use your name and email address as produced by `git-shortlog(1)`. You can change how this is formatted by modifying `.mailmap`. More details on that file can be found in the git [Documentation/mailmap.txt][mailmap]. +Our test suite is new, and therefore it is not yet mandatory to include +tests with pull requests. However, you must ensure that the existing +test suite passes with any changes you make. Also, any attempts to add +or extend tests will increase the chances of your pull request being +merged. + Submit a pull request using GitHub. If there is a relevant bug, mention it in the commit message (`Fixes #42.`). [mailmap]: https://github.com/git/git/blob/6a907786af835ac15962be53f1492f2 + +Testing +----- + +The test suite uses [cram][]. It is an integration suite, meaning the +programs are exercised from the outside and assertions are made only on +their output or effects. + +All tests can be run like so: + + $ make check + +Individual tests can be run like so: + + $ env TESTS=lsrc-dotfiles-dirs.t make -e check + +If you intend to write a new test: + +1. Add your test at `test/subcommand-something-meaningful.t`. +2. Add the relative name to the `TESTS` variable in `test/Makefile.am`. +3. Source `test/helper.sh` as the first line of your test. +4. When in doubt, use existing tests as a guide. + +[cram]: https://bitheap.org/cram/ diff --git a/Makefile.am b/Makefile.am index 1f881ef..2525776 100644 --- a/Makefile.am +++ b/Makefile.am @@ -1,5 +1,5 @@ AUTOMAKE_OPTIONS = foreign -SUBDIRS = man share bin +SUBDIRS = man share bin test EXTRA_DIST = LICENSE README.md NEWS.md .PHONY: release \ diff --git a/README.md b/README.md index 4eaf7e9..d585823 100644 --- a/README.md +++ b/README.md @@ -60,7 +60,7 @@ Programs Support ------- -Pull requests welcome; see `CONTRIBUTING.MD`. +Pull requests welcome; see `CONTRIBUTING.md`. License ------- diff --git a/configure.ac b/configure.ac index 5212051..2f1707a 100644 --- a/configure.ac +++ b/configure.ac @@ -23,4 +23,4 @@ AC_SUBST([SHELL]) # Checks for library functions. AM_EXTRA_RECURSIVE_TARGETS([release_build_man_html release_push_man_html release_clean_man_html]) -AC_OUTPUT(Makefile bin/Makefile man/Makefile share/Makefile share/rcm.sh NEWS.md bin/lsrc bin/mkrc bin/rcdn bin/rcup) +AC_OUTPUT(Makefile bin/Makefile man/Makefile share/Makefile test/Makefile share/rcm.sh NEWS.md bin/lsrc bin/mkrc bin/rcdn bin/rcup) diff --git a/test/Makefile.am b/test/Makefile.am new file mode 100644 index 0000000..9cbc6b2 --- /dev/null +++ b/test/Makefile.am @@ -0,0 +1,20 @@ +TESTS = \ + lsrc-dotfiles-dirs.t \ + lsrc-excludes.t \ + lsrc-hostname.t \ + lsrc-sigils.t \ + lsrc.t \ + lsrc-tags.t \ + lsrc-usage.t \ + mkrc-alternate-dotfiles-dir.t \ + mkrc-copy-file.t \ + mkrc-host-file.t \ + mkrc-simple-output.t \ + mkrc-tagged-file.t \ + mkrc-usage.t \ + rcrc-custom.t \ + rcrc.t \ + rcup-link-files.t \ + rcup-usage.t + +LOG_COMPILER = cram diff --git a/test/helper.sh b/test/helper.sh new file mode 100644 index 0000000..539e270 --- /dev/null +++ b/test/helper.sh @@ -0,0 +1,34 @@ +for bin in lsrc mkrc rcup rcdn; do + chmod +x "$TESTDIR/../bin"/$bin +done + +export HOME="$PWD" +export PATH="$TESTDIR/../bin:$PATH" +export RCRC="$HOME/.rcrc" +export RCM_LIB="$TESTDIR/../share" + +mkdir .dotfiles + +assert() { + local msg="$1"; shift + + test "$@" || echo "Failed assertion: $msg" + + return 0 +} + +refute() { + local msg="$1"; shift + + test "$@" && echo "Failed assertion: $msg" + + return 0 +} + +assert_linked() { + local from="$1" to="$2" + local resolved="$(readlink -f "$from")" + + assert "$from should be a symlink" -h "$from" + assert "$from should resolve to $to, resolved to $resolved" "$resolved" = "$to" +} diff --git a/test/lsrc-dotfiles-dirs.t b/test/lsrc-dotfiles-dirs.t new file mode 100644 index 0000000..e7769c0 --- /dev/null +++ b/test/lsrc-dotfiles-dirs.t @@ -0,0 +1,13 @@ + $ . "$TESTDIR/helper.sh" + +Should include all the dotfiles + + $ touch .dotfiles/example + > mkdir .second-dotfiles/ + > touch .second-dotfiles/s-example + > mkdir .third-dotfiles/ + > touch .third-dotfiles/t-example + + $ lsrc -d .second-dotfiles -d .third-dotfiles + /*/.s-example:/*/.second-dotfiles/s-example (glob) + /*/.t-example:/*/.third-dotfiles/t-example (glob) diff --git a/test/lsrc-excludes.t b/test/lsrc-excludes.t new file mode 100644 index 0000000..de63840 --- /dev/null +++ b/test/lsrc-excludes.t @@ -0,0 +1,20 @@ + $ . "$TESTDIR/helper.sh" + +Should exclude items with -x + + $ touch .dotfiles/example + > touch .dotfiles/excluded + + $ lsrc -x excluded + /*/.example:/*/.dotfiles/example (glob) + +Should accept directory:file syntax + + $ mkdir .other-dotfiles + > touch .other-dotfiles/included + > touch .other-dotfiles/excluded + + $ lsrc -d .dotfiles -d .other-dotfiles -x other-dotfiles:excluded + /*/.example:/*/.dotfiles/example (glob) + /*/.excluded:/*/.dotfiles/excluded (glob) + /*/.included:/*/.other-dotfiles/included (glob) diff --git a/test/lsrc-hostname.t b/test/lsrc-hostname.t new file mode 100644 index 0000000..9170c74 --- /dev/null +++ b/test/lsrc-hostname.t @@ -0,0 +1,13 @@ + $ . "$TESTDIR/helper.sh" + +Should include entries that match hostname + + $ touch .dotfiles/example + > mkdir .dotfiles/host-$(hostname) + > touch .dotfiles/host-$(hostname)/h-example + > mkdir .dotfiles/host-not-hostname + > touch .dotfiles/host-not-hostname/nh-example + + $ lsrc + /*/.example:/*/.dotfiles/example (glob) + /*/.h-example:/*/.dotfiles/host-*/h-example (glob) diff --git a/test/lsrc-sigils.t b/test/lsrc-sigils.t new file mode 100644 index 0000000..98573b2 --- /dev/null +++ b/test/lsrc-sigils.t @@ -0,0 +1,16 @@ + $ . "$TESTDIR/helper.sh" + +Should print @ for links + + $ touch .dotfiles/example + + $ lsrc -F + /*/.example:/*/.dotfiles/example:@ (glob) + +Should print X for files in COPY_ALWAYS + + $ touch .dotfiles/copy + + $ COPY_ALWAYS=copy lsrc -F + /*/.copy:/*/.dotfiles/copy:X (glob) + /*/.example:/*/.dotfiles/example:@ (glob) diff --git a/test/lsrc-tags.t b/test/lsrc-tags.t new file mode 100644 index 0000000..97f77db --- /dev/null +++ b/test/lsrc-tags.t @@ -0,0 +1,14 @@ + $ . "$TESTDIR/helper.sh" + +Should include entries that match passed tags + + $ touch .dotfiles/example + > mkdir .dotfiles/tag-foo + > touch .dotfiles/tag-foo/f-example + > mkdir .dotfiles/tag-bar + > touch .dotfiles/tag-bar/b-example + + $ lsrc -t foo -t bar + /*/.example:/*/.dotfiles/example (glob) + /*/.f-example:/*/.dotfiles/tag-foo/f-example (glob) + /*/.b-example:/*/.dotfiles/tag-bar/b-example (glob) diff --git a/test/lsrc-usage.t b/test/lsrc-usage.t new file mode 100644 index 0000000..70a3bd8 --- /dev/null +++ b/test/lsrc-usage.t @@ -0,0 +1,7 @@ + $ . "$TESTDIR/helper.sh" + +-h should output usage information and exit 0 + + $ lsrc -h + Usage: lsrc [-FVqvh] [-I EXCL_PAT] [-x EXCL_PAT] [-N EXCL_PAT ] [-t TAG] [-d DOT_DIR] + see lsrc(1) and rcm(5) for more details diff --git a/test/lsrc.t b/test/lsrc.t new file mode 100644 index 0000000..e28a3a8 --- /dev/null +++ b/test/lsrc.t @@ -0,0 +1,14 @@ + $ . "$TESTDIR/helper.sh" + +Should list the contents of ~/.dotfiles + + $ touch .dotfiles/example + > mkdir .dotfiles/nested + > touch .dotfiles/nested/example + > mkdir .dotfiles/nested/deeply + > touch .dotfiles/nested/deeply/example + + $ lsrc + /*/.example:/*/.dotfiles/example (glob) + /*/.nested/deeply/example:/*/.dotfiles/nested/deeply/example (glob) + /*/.nested/example:/*/.dotfiles/nested/example (glob) diff --git a/test/mkrc-alternate-dotfiles-dir.t b/test/mkrc-alternate-dotfiles-dir.t new file mode 100644 index 0000000..8346214 --- /dev/null +++ b/test/mkrc-alternate-dotfiles-dir.t @@ -0,0 +1,10 @@ + $ . "$TESTDIR/helper.sh" + > mkdir .other-dotfiles + +Passing -d should specify alternate dotfiles location + + $ touch .example + + $ mkrc -d .other-dotfiles .example >/dev/null + + $ assert_linked "$HOME/.example" "$HOME/.other-dotfiles/example" diff --git a/test/mkrc-copy-file.t b/test/mkrc-copy-file.t new file mode 100644 index 0000000..45e63d3 --- /dev/null +++ b/test/mkrc-copy-file.t @@ -0,0 +1,15 @@ + $ . "$TESTDIR/helper.sh" + +Passing -C should copy the file + + $ echo 'Content' > .example + + $ mkrc -C .example >/dev/null + + $ refute "should not be a symlink" -h $HOME/.example + + $ cat $HOME/.example + Content + + $ cat $HOME/.dotfiles/example + Content diff --git a/test/mkrc-host-file.t b/test/mkrc-host-file.t new file mode 100644 index 0000000..3f13c6c --- /dev/null +++ b/test/mkrc-host-file.t @@ -0,0 +1,9 @@ + $ . "$TESTDIR/helper.sh" + +Passing -o should put it in a host + + $ touch .example + + $ mkrc -o .example >/dev/null + + $ assert_linked "$HOME/.example" "$HOME/.dotfiles/host-$(hostname)/example" diff --git a/test/mkrc-simple-output.t b/test/mkrc-simple-output.t new file mode 100644 index 0000000..884da01 --- /dev/null +++ b/test/mkrc-simple-output.t @@ -0,0 +1,41 @@ + $ . "$TESTDIR/helper.sh" + +Making an rc file should move it into dotfiles and create a symlink + + $ touch .example + + $ mkrc -v .example + Moving... + '.example' -> '*/.dotfiles/example' (glob) + Linking... + '*/.dotfiles/example' -> '*/.example' (glob) + + $ assert_linked "$HOME/.example" "$HOME/.dotfiles/example" + +Making an rc file in a sub-directory should create the directories then +create a symlink + + $ mkdir .nested + > touch .nested/example + + $ mkrc -v .nested/example + Moving... + '.nested/example' -> '*/.dotfiles/nested/example' (glob) + Linking... + '*/.dotfiles/nested/example' -> '*/.nested/example' (glob) + + $ assert_linked "$HOME/.nested/example" "$HOME/.dotfiles/nested/example" + +Making an rc file in a deeply nested sub-directory should create all of +the required directories then create a symlink + + $ mkdir .nested/deeply + > touch .nested/deeply/example + + $ mkrc -v .nested/deeply/example + Moving... + '.nested/deeply/example' -> '*/.dotfiles/nested/deeply/example' (glob) + Linking... + '*/.dotfiles/nested/deeply/example' -> '*/.nested/deeply/example' (glob) + + $ assert_linked "$HOME/.nested/deeply/example" "$HOME/.dotfiles/nested/deeply/example" diff --git a/test/mkrc-tagged-file.t b/test/mkrc-tagged-file.t new file mode 100644 index 0000000..2f8e710 --- /dev/null +++ b/test/mkrc-tagged-file.t @@ -0,0 +1,9 @@ + $ . "$TESTDIR/helper.sh" + +Passing -t should put it in a tag + + $ touch .example + + $ mkrc -t foo .example >/dev/null + + $ assert_linked "$HOME/.example" "$HOME/.dotfiles/tag-foo/example" diff --git a/test/mkrc-usage.t b/test/mkrc-usage.t new file mode 100644 index 0000000..c9ede8d --- /dev/null +++ b/test/mkrc-usage.t @@ -0,0 +1,14 @@ + $ . "$TESTDIR/helper.sh" + +no arguments should output usage information and exit 1 + + $ mkrc + Usage: mkrc [-hvqo] [-t TAG] [-d DIR] FILES ... + see mkrc(1) and rcm(5) for more details + [1] + +-h should output usage information and exit 0 + + $ mkrc -h + Usage: mkrc [-hvqo] [-t TAG] [-d DIR] FILES ... + see mkrc(1) and rcm(5) for more details diff --git a/test/rcrc-custom.t b/test/rcrc-custom.t new file mode 100644 index 0000000..ef9b8fa --- /dev/null +++ b/test/rcrc-custom.t @@ -0,0 +1,16 @@ + $ . "$TESTDIR/helper.sh" + +mkrc should accept -r for a custom rcrc + + $ touch .example + > mkdir .other-dotfiles + + $ echo 'DOTFILES_DIRS="$HOME/.other-dotfiles"' > alt-rcrc + + $ RCRC=./alt-rcrc mkrc -v .example + Moving... + '.example' -> '*/.other-dotfiles/example' (glob) + Linking... + '*/.other-dotfiles/example' -> '*/.example' (glob) + + $ assert_linked "$HOME/.example" "$HOME/.other-dotfiles/example" diff --git a/test/rcrc.t b/test/rcrc.t new file mode 100644 index 0000000..54fc022 --- /dev/null +++ b/test/rcrc.t @@ -0,0 +1,16 @@ + $ . "$TESTDIR/helper.sh" + +Information should be read from ~/.rcrc by default + + $ touch .example + > mkdir .other-dotfiles + + $ echo 'DOTFILES_DIRS="$HOME/.other-dotfiles"' > $HOME/.rcrc + + $ mkrc -v .example + Moving... + '.example' -> '*/.other-dotfiles/example' (glob) + Linking... + '*/.other-dotfiles/example' -> '*/.example' (glob) + + $ assert_linked "$HOME/.example" "$HOME/.other-dotfiles/example" diff --git a/test/rcup-link-files.t b/test/rcup-link-files.t new file mode 100644 index 0000000..9a3e273 --- /dev/null +++ b/test/rcup-link-files.t @@ -0,0 +1,15 @@ + $ . "$TESTDIR/helper.sh" + +Should create symlinks for files and directories + + $ touch .dotfiles/example + > mkdir .dotfiles/nested/ + > touch .dotfiles/nested/example + > mkdir .dotfiles/nested/deeply + > touch .dotfiles/nested/deeply/example + + $ rcup >/dev/null + + $ assert_linked "$HOME/.example" "$HOME/.dotfiles/example" + $ assert_linked "$HOME/.nested/example" "$HOME/.dotfiles/nested/example" + $ assert_linked "$HOME/.nested/deeply/example" "$HOME/.dotfiles/nested/deeply/example" diff --git a/test/rcup-usage.t b/test/rcup-usage.t new file mode 100644 index 0000000..c5b798f --- /dev/null +++ b/test/rcup-usage.t @@ -0,0 +1,7 @@ + $ . "$TESTDIR/helper.sh" + +-h should output usage information and exit 0 + + $ rcup -h + Usage: rcup [-CVqvfhikK] [-I EXCL_PAT] [-x EXCL_PAT] [-t TAG] [-d DOT_DIR] + see rcup(1) and rcm(5) for more details -- cgit v1.2.3