busser-bats 0.6.0 → 0.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.github/workflows/publish.yml +22 -0
- data/.gitignore +0 -1
- data/.release-please-manifest.json +1 -1
- data/.rubocop.yml +1 -4
- data/CHANGELOG.md +11 -0
- data/CONTRIBUTING.md +86 -0
- data/Gemfile +7 -5
- data/README.md +100 -28
- data/Rakefile +42 -15
- data/config/features/support/env.rb +0 -5
- data/features/support/env.rb +0 -12
- data/features/test_command.feature +31 -31
- data/lib/busser/bats/version.rb +3 -1
- data/lib/busser/runner_plugin/bats.rb +27 -3
- data/spec/busser/runner_plugin/bats_spec.rb +41 -0
- data/spec/spec_helper.rb +2 -0
- data/vendor/bats/LICENSE.md +53 -0
- data/vendor/bats/README.md +84 -242
- data/vendor/bats/VERSION.txt +1 -1
- data/vendor/bats/bin/bats +75 -0
- data/vendor/bats/install.sh +20 -28
- data/vendor/bats/lib/bats-core/common.bash +278 -0
- data/vendor/bats/lib/bats-core/formatter.bash +151 -0
- data/vendor/bats/lib/bats-core/preprocessing.bash +19 -0
- data/vendor/bats/lib/bats-core/semaphore.bash +113 -0
- data/vendor/bats/lib/bats-core/test_functions.bash +539 -0
- data/vendor/bats/lib/bats-core/tracing.bash +425 -0
- data/vendor/bats/lib/bats-core/validator.bash +37 -0
- data/vendor/bats/lib/bats-core/warnings.bash +44 -0
- data/vendor/bats/libexec/bats-core/bats +549 -0
- data/vendor/bats/libexec/bats-core/bats-exec-file +402 -0
- data/vendor/bats/libexec/bats-core/bats-exec-suite +342 -0
- data/vendor/bats/libexec/bats-core/bats-exec-test +383 -0
- data/vendor/bats/libexec/bats-core/bats-format-cat +6 -0
- data/vendor/bats/libexec/bats-core/bats-format-junit +293 -0
- data/vendor/bats/libexec/bats-core/bats-format-pretty +360 -0
- data/vendor/bats/libexec/bats-core/bats-format-tap +55 -0
- data/vendor/bats/libexec/bats-core/bats-format-tap13 +89 -0
- data/vendor/bats/libexec/bats-core/bats-gather-tests +402 -0
- data/vendor/bats/libexec/bats-core/bats-preprocess +118 -0
- data/vendor/bats/man/Makefile +16 -3
- data/vendor/bats/man/bats.1 +100 -58
- data/vendor/bats/man/bats.1.ronn +102 -12
- data/vendor/bats/man/bats.7 +205 -83
- data/vendor/bats/man/bats.7.ronn +262 -14
- data/vendor/bats/uninstall.sh +63 -0
- metadata +25 -6
- data/.tool-versions +0 -1
- data/vendor/bats/.gitattributes +0 -3
- data/vendor/bats/.travis.yml +0 -5
- data/vendor/bats/LICENSE +0 -20
- data/vendor/bats/bin/bats +0 -1
- data/vendor/bats/package.json +0 -9
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 50827f7c53a1bce1a7ddc9bda08aacd3d7a2388fefc183b7bdc3cbdd23bac07f
|
|
4
|
+
data.tar.gz: 3a22e249cc415c99bdfd3f922b0a4d13665f267eb14216f2c1d226f76354ade3
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: c00aef02c07f8518d484107f04165d2e320cc0a822c36b7e74350795c84ce5e3b7d7a221cf75e0e679a9623995db2f2ee44a058b729a73a73442b8a56c38855f
|
|
7
|
+
data.tar.gz: 65749c81f7d399d2a2ce2c64eda0bc3235c815e7e1a7c6a2b0beef4756d8db414589140cdfc8df02d00da757d426eaf2f61bbcf3ab0c2cdb0f122401d96593fd
|
|
@@ -43,3 +43,25 @@ jobs:
|
|
|
43
43
|
uses: actionshub/publish-gem-to-rubygems@f9126f7a2d36a4fd31a13e78fde5fbdcc4b7b251 # v2.0.6
|
|
44
44
|
with:
|
|
45
45
|
token: ${{ secrets.RUBYGEMS_API_KEY }}
|
|
46
|
+
|
|
47
|
+
# actionshub/publish-gem-to-rubygems logs a rejected push and still exits
|
|
48
|
+
# 0, so a release that never reached RubyGems shows up as a green job.
|
|
49
|
+
# Ask RubyGems directly instead of trusting the step. The v2 endpoint is
|
|
50
|
+
# 404 until the exact version is indexed, so -f turns "not there" into a
|
|
51
|
+
# non-zero exit rather than a substring match on `gem list` output.
|
|
52
|
+
- name: Verify the release reached RubyGems
|
|
53
|
+
if: ${{ steps.release.outputs.release_created }}
|
|
54
|
+
env:
|
|
55
|
+
VERSION: ${{ steps.release.outputs.version }}
|
|
56
|
+
run: |
|
|
57
|
+
set -euo pipefail
|
|
58
|
+
name="$(basename "$(ls ./*.gemspec)" .gemspec)"
|
|
59
|
+
for _ in $(seq 1 12); do
|
|
60
|
+
if curl -fsS -o /dev/null "https://rubygems.org/api/v2/rubygems/${name}/versions/${VERSION}.json"; then
|
|
61
|
+
echo "${name} ${VERSION} is on RubyGems"
|
|
62
|
+
exit 0
|
|
63
|
+
fi
|
|
64
|
+
sleep 15
|
|
65
|
+
done
|
|
66
|
+
echo "::error::${name} ${VERSION} never reached RubyGems. A permissions failure in the push step above does not fail that step -- read its log."
|
|
67
|
+
exit 1
|
data/.gitignore
CHANGED
data/.rubocop.yml
CHANGED
data/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,16 @@
|
|
|
1
1
|
# busser-bats Changelog
|
|
2
2
|
|
|
3
|
+
## [0.7.0](https://github.com/test-kitchen/busser-bats/compare/v0.6.0...v0.7.0) (2026-08-28)
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
### ⚠ BREAKING CHANGES
|
|
7
|
+
|
|
8
|
+
* the vendored bats goes from 0.4.0 to 1.14.0. Suites relying on bats 0.4 behaviour may need updating; see the bats-core changelog.
|
|
9
|
+
|
|
10
|
+
### Features
|
|
11
|
+
|
|
12
|
+
* vendor bats-core instead of the archived sstephenson/bats ([#59](https://github.com/test-kitchen/busser-bats/issues/59)) ([377240c](https://github.com/test-kitchen/busser-bats/commit/377240cbf04dee7bdec158fc306bbc5a7e7fe509))
|
|
13
|
+
|
|
3
14
|
## [0.6.0](https://github.com/test-kitchen/busser-bats/compare/v0.5.0...v0.6.0) (2026-08-28)
|
|
4
15
|
|
|
5
16
|
|
data/CONTRIBUTING.md
ADDED
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
# Contributing to busser-bats
|
|
2
|
+
|
|
3
|
+
Thanks for taking the time to contribute. This document covers how to get the
|
|
4
|
+
project running locally, how to check your work before opening a pull request,
|
|
5
|
+
and the commit convention releases depend on.
|
|
6
|
+
|
|
7
|
+
## Getting set up
|
|
8
|
+
|
|
9
|
+
This plugin requires **Ruby 3.2 or newer**. Clone the repository and install the
|
|
10
|
+
development dependencies:
|
|
11
|
+
|
|
12
|
+
```bash
|
|
13
|
+
git clone https://github.com/test-kitchen/busser-bats.git
|
|
14
|
+
cd busser-bats
|
|
15
|
+
bundle install
|
|
16
|
+
```
|
|
17
|
+
|
|
18
|
+
## Running the tests
|
|
19
|
+
|
|
20
|
+
`rake` runs the whole suite:
|
|
21
|
+
|
|
22
|
+
```bash
|
|
23
|
+
bundle exec rake test
|
|
24
|
+
```
|
|
25
|
+
|
|
26
|
+
The tests are [cucumber](https://cucumber.io) features in `features/`. They
|
|
27
|
+
drive the real `busser` executable through
|
|
28
|
+
[aruba](https://github.com/cucumber/aruba) rather than calling the plugin's
|
|
29
|
+
classes, so they cover it end to end: install the plugin into a throwaway
|
|
30
|
+
Busser root, write a suite, run it, and check what came out. The step
|
|
31
|
+
definitions they use are published by busser itself, in `lib/busser/cucumber.rb`.
|
|
32
|
+
|
|
33
|
+
## Linting
|
|
34
|
+
|
|
35
|
+
CI runs three linters, all of which you can run locally:
|
|
36
|
+
|
|
37
|
+
```bash
|
|
38
|
+
bundle exec cookstyle --chefstyle # Ruby
|
|
39
|
+
yamllint --strict . # YAML
|
|
40
|
+
markdownlint-cli2 "**/*.md" "!**/CHANGELOG*.md"
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
## Commit messages
|
|
44
|
+
|
|
45
|
+
This project uses [Conventional Commits](https://www.conventionalcommits.org).
|
|
46
|
+
Releases are automated, and the commit subject on `main` is what decides the
|
|
47
|
+
next version number and what appears in the changelog.
|
|
48
|
+
|
|
49
|
+
Pull requests are **squash merged, so the pull request title becomes that
|
|
50
|
+
subject**. A CI check enforces the format on the title; the individual commits
|
|
51
|
+
on your branch are not checked.
|
|
52
|
+
|
|
53
|
+
| Prefix | Effect on the next release |
|
|
54
|
+
| --- | --- |
|
|
55
|
+
| `fix:` | Patch version bump |
|
|
56
|
+
| `feat:` | Minor version bump |
|
|
57
|
+
| `feat!:`, or a `BREAKING CHANGE:` footer | Minor bump, until this gem reaches 1.0 |
|
|
58
|
+
| `chore:`, `docs:`, `ci:`, `test:`, `refactor:` | No release |
|
|
59
|
+
|
|
60
|
+
For example:
|
|
61
|
+
|
|
62
|
+
```text
|
|
63
|
+
fix: install the plugin into GEM_HOME rather than the bundle
|
|
64
|
+
feat: support a Gemfile alongside the suite
|
|
65
|
+
ci: pin the shared workflow to a release
|
|
66
|
+
```
|
|
67
|
+
|
|
68
|
+
## Opening a pull request
|
|
69
|
+
|
|
70
|
+
1. Fork the repository and create a branch for your change.
|
|
71
|
+
2. Add or update tests. A bug fix should come with a test that fails without it.
|
|
72
|
+
3. Run `bundle exec rake test` and the linters above.
|
|
73
|
+
4. Open a pull request with a Conventional Commits title.
|
|
74
|
+
|
|
75
|
+
## Releases
|
|
76
|
+
|
|
77
|
+
Releases are handled by
|
|
78
|
+
[release-please](https://github.com/googleapis/release-please). It watches
|
|
79
|
+
commits landing on `main` and keeps a release pull request open with the next
|
|
80
|
+
version number and the accumulated changelog. Merging that pull request tags the
|
|
81
|
+
release and publishes the gem to RubyGems and GitHub Packages.
|
|
82
|
+
|
|
83
|
+
Maintainers do not bump `lib/busser/bats/version.rb` or edit
|
|
84
|
+
`CHANGELOG.md` by hand; release-please owns both files. This gem is still pre-1.0, so
|
|
85
|
+
`bump-minor-pre-major` is set and a breaking change takes the minor rather than
|
|
86
|
+
graduating it to 1.0.
|
data/Gemfile
CHANGED
|
@@ -3,16 +3,18 @@ source "https://rubygems.org"
|
|
|
3
3
|
gemspec
|
|
4
4
|
|
|
5
5
|
group :cookstyle do
|
|
6
|
-
gem "cookstyle", ">= 9.0
|
|
6
|
+
gem "cookstyle", ">= 9.0"
|
|
7
7
|
end
|
|
8
8
|
|
|
9
9
|
group :test do
|
|
10
|
-
gem "aruba", ">= 2.
|
|
11
|
-
gem "base64" # cucumber needs it; not a default gem on Ruby 4.0
|
|
10
|
+
gem "aruba", ">= 2.4"
|
|
11
|
+
gem "base64", ">= 0.3" # cucumber needs it; not a default gem on Ruby 4.0
|
|
12
12
|
gem "cucumber", ">= 11.1"
|
|
13
|
-
gem "
|
|
13
|
+
gem "minitest", ">= 6.0"
|
|
14
|
+
gem "mocha", ">= 2.7"
|
|
15
|
+
gem "rake", ">= 13.4"
|
|
14
16
|
end
|
|
15
17
|
|
|
16
18
|
group :development do
|
|
17
|
-
gem "
|
|
19
|
+
gem "yard", ">= 0.9.37"
|
|
18
20
|
end
|
data/README.md
CHANGED
|
@@ -1,50 +1,122 @@
|
|
|
1
|
-
#
|
|
1
|
+
# busser-bats
|
|
2
2
|
|
|
3
|
-
[](
|
|
3
|
+
[](https://badge.fury.io/rb/busser-bats)
|
|
4
4
|
|
|
5
|
-
A Busser runner plugin
|
|
5
|
+
A [Busser](https://github.com/test-kitchen/busser) runner plugin that runs
|
|
6
|
+
[Bats](https://github.com/bats-core/bats-core) test files.
|
|
7
|
+
|
|
8
|
+
Bats is a TAP-producing test harness for bash. This plugin vendors a copy of it,
|
|
9
|
+
installs that copy onto the machine under test during postinstall, and then runs
|
|
10
|
+
it against the suite's `bats` directory — so the machine under test needs
|
|
11
|
+
nothing beyond bash.
|
|
12
|
+
|
|
13
|
+
The vendored copy is [bats-core](https://github.com/bats-core/bats-core), which
|
|
14
|
+
is the maintained fork; `vendor/bats/VERSION.txt` records the exact release.
|
|
15
|
+
`rake bats:vendor` refreshes it, and `BATS_VERSION` selects a different tag.
|
|
6
16
|
|
|
7
17
|
## Status
|
|
8
18
|
|
|
9
|
-
This software project is no longer under active development as it has no active
|
|
19
|
+
This software project is no longer under active development as it has no active
|
|
20
|
+
maintainers. The software may continue to work for some or all use cases, but
|
|
21
|
+
issues filed in GitHub will most likely not be triaged. If a new maintainer is
|
|
22
|
+
interested in working on this project please come chat with us in #test-kitchen
|
|
23
|
+
on Chef Community Slack.
|
|
24
|
+
|
|
25
|
+
## Requirements
|
|
26
|
+
|
|
27
|
+
Ruby 3.2 or newer, and busser 0.9.0 or newer.
|
|
28
|
+
|
|
29
|
+
## Installation
|
|
10
30
|
|
|
11
|
-
|
|
31
|
+
Busser installs the plugin for you when Test Kitchen runs the suite, so there is
|
|
32
|
+
usually nothing to do. To install it by hand:
|
|
12
33
|
|
|
13
|
-
|
|
34
|
+
```bash
|
|
35
|
+
busser plugin install busser-bats
|
|
36
|
+
```
|
|
14
37
|
|
|
15
38
|
## Usage
|
|
16
39
|
|
|
17
|
-
|
|
40
|
+
Put your `.bats` files in the `bats` directory of a suite:
|
|
18
41
|
|
|
19
|
-
|
|
42
|
+
```text
|
|
43
|
+
test
|
|
44
|
+
`-- integration
|
|
45
|
+
`-- default # suite name
|
|
46
|
+
`-- bats
|
|
47
|
+
`-- default.bats
|
|
48
|
+
```
|
|
20
49
|
|
|
21
|
-
|
|
22
|
-
|
|
50
|
+
The whole directory is handed to `bats`, which picks up every `*.bats` file in
|
|
51
|
+
it. A test is a `@test` block, and it passes when every command in it succeeds:
|
|
23
52
|
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
53
|
+
```bash
|
|
54
|
+
@test "foobar.txt was created" {
|
|
55
|
+
run cat /usr/local/foobar.txt
|
|
56
|
+
[ "$status" -eq 0 ]
|
|
57
|
+
[ "$output" = "hello" ]
|
|
58
|
+
}
|
|
59
|
+
```
|
|
27
60
|
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
3. Commit your changes (`git commit -am 'Added some feature'`)
|
|
31
|
-
4. Push to the branch (`git push origin my-new-feature`)
|
|
32
|
-
5. Create new Pull Request
|
|
61
|
+
See the [Bats documentation](https://bats-core.readthedocs.io) for the full
|
|
62
|
+
assertion and helper vocabulary.
|
|
33
63
|
|
|
34
|
-
|
|
64
|
+
Test Kitchen picks the plugin up from the suite directory name — no verifier
|
|
65
|
+
configuration is needed beyond the default busser verifier.
|
|
35
66
|
|
|
36
|
-
|
|
67
|
+
## Using it with Test Kitchen
|
|
37
68
|
|
|
38
|
-
|
|
69
|
+
This is how most people run it, and it needs no Busser commands of your own.
|
|
70
|
+
Select the verifier in `kitchen.yml`:
|
|
71
|
+
|
|
72
|
+
```yaml
|
|
73
|
+
verifier:
|
|
74
|
+
name: busser
|
|
75
|
+
|
|
76
|
+
suites:
|
|
77
|
+
- name: default
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
Then put your tests in a `bats` directory inside the suite:
|
|
39
81
|
|
|
40
|
-
|
|
82
|
+
```text
|
|
83
|
+
test/integration/default/bats/default.bats
|
|
84
|
+
```
|
|
41
85
|
|
|
42
|
-
|
|
86
|
+
`kitchen verify` installs Busser and this plugin on the instance and runs them.
|
|
87
|
+
The directory name is what selects this plugin -- there is nothing else to
|
|
88
|
+
configure.
|
|
89
|
+
|
|
90
|
+
## When nothing runs
|
|
91
|
+
|
|
92
|
+
If the suite files do not match what this plugin looks for, the run prints one
|
|
93
|
+
line and **exits `0`**:
|
|
94
|
+
|
|
95
|
+
```text
|
|
96
|
+
-----> Running bats test suite
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
No tests ran, and nothing said so. Work through these in order:
|
|
100
|
+
|
|
101
|
+
1. **Is the directory named `bats`?** That name alone selects this plugin.
|
|
102
|
+
`batss/`, `tests/` or anything else is not picked up.
|
|
103
|
+
2. **Do the filenames match?** Every `*.bats` file in the directory is run
|
|
104
|
+
-- `smoke.sh` is *not* picked up.
|
|
105
|
+
3. **Is the plugin installed?** `busser plugin list` shows what is available.
|
|
106
|
+
4. **Is `BUSSER_ROOT` what you think?** `busser suite path` prints where suites
|
|
107
|
+
are actually being looked for.
|
|
108
|
+
|
|
109
|
+
## Contributing
|
|
110
|
+
|
|
111
|
+
Bug reports and pull requests are welcome. See
|
|
112
|
+
[CONTRIBUTING.md](CONTRIBUTING.md) for how to set up the project, run the test
|
|
113
|
+
suite, and format your commits.
|
|
114
|
+
|
|
115
|
+
## License
|
|
43
116
|
|
|
117
|
+
Apache License 2.0. See [LICENSE](LICENSE).
|
|
44
118
|
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
[license]: https://github.com/fnichol/busser-bats/blob/master/LICENSE
|
|
48
|
-
[repo]: https://github.com/fnichol/busser-bats
|
|
119
|
+
The vendored copy of Bats is released under an MIT-style license, copyright Sam
|
|
120
|
+
Stephenson and the bats-core contributors.
|
|
49
121
|
|
|
50
|
-
[
|
|
122
|
+
Originally created by [Fletcher Nichol](https://github.com/fnichol).
|
data/Rakefile
CHANGED
|
@@ -1,12 +1,17 @@
|
|
|
1
1
|
require "bundler/gem_tasks"
|
|
2
|
-
require "open-uri"
|
|
3
|
-
|
|
4
2
|
namespace :bats do
|
|
5
|
-
|
|
6
|
-
|
|
3
|
+
# bats moved. sstephenson/bats was archived in 2016 at v0.4.0; bats-core is
|
|
4
|
+
# the maintained fork and where every release since has come from.
|
|
5
|
+
version = ENV.fetch("BATS_VERSION", "v1.14.0")
|
|
6
|
+
url = "https://github.com/bats-core/bats-core/archive/refs/tags/#{version}.tar.gz"
|
|
7
7
|
tarball = "tmp/bats-#{version}.tar.gz"
|
|
8
8
|
vendor = "vendor/bats"
|
|
9
9
|
|
|
10
|
+
# install.sh needs bin, libexec, lib and the two man pages. Everything else in
|
|
11
|
+
# the tarball -- the test suite, the docs site, Docker and CI scaffolding --
|
|
12
|
+
# is weight in a gem that gets copied onto every machine under test.
|
|
13
|
+
keep = %w{bin libexec lib man install.sh uninstall.sh LICENSE.md README.md}
|
|
14
|
+
|
|
10
15
|
desc "Vendors bats #{version} source code into gem codebase"
|
|
11
16
|
task vendor: "#{vendor}/VERSION.txt"
|
|
12
17
|
|
|
@@ -14,19 +19,16 @@ namespace :bats do
|
|
|
14
19
|
directory vendor
|
|
15
20
|
|
|
16
21
|
file tarball => File.dirname(tarball) do |t|
|
|
17
|
-
|
|
18
|
-
dst = open(t.name, "wb")
|
|
19
|
-
IO.copy_stream(src, dst)
|
|
20
|
-
ensure
|
|
21
|
-
src.close
|
|
22
|
-
dst.close
|
|
22
|
+
sh "curl", "--fail", "--silent", "--location", url, "--output", t.name
|
|
23
23
|
end
|
|
24
24
|
|
|
25
25
|
file "#{vendor}/VERSION.txt" => [vendor, tarball] do |t|
|
|
26
26
|
abs_tarball = File.expand_path(tarball)
|
|
27
|
-
Dir.chdir(vendor)
|
|
28
|
-
|
|
29
|
-
|
|
27
|
+
Dir.chdir(vendor) do
|
|
28
|
+
sh "tar", "xzf", abs_tarball, "--strip-components=1"
|
|
29
|
+
(Dir.glob("*", File::FNM_DOTMATCH) - [".", "..", *keep]).each { |f| rm_rf(f) }
|
|
30
|
+
end
|
|
31
|
+
File.write(t.name, "#{url}\n")
|
|
30
32
|
end
|
|
31
33
|
|
|
32
34
|
desc "Clean up a vendored bats in preparation for a new vendored version"
|
|
@@ -35,12 +37,37 @@ namespace :bats do
|
|
|
35
37
|
end
|
|
36
38
|
end
|
|
37
39
|
|
|
40
|
+
require "rake/testtask"
|
|
41
|
+
Rake::TestTask.new(:unit) do |t|
|
|
42
|
+
t.libs.push "lib"
|
|
43
|
+
t.test_files = FileList["spec/**/*_spec.rb"]
|
|
44
|
+
t.verbose = true
|
|
45
|
+
end
|
|
46
|
+
|
|
38
47
|
require "cucumber/rake/task"
|
|
39
48
|
Cucumber::Rake::Task.new(:features) do |t|
|
|
40
|
-
t.cucumber_opts = ["features", "
|
|
49
|
+
t.cucumber_opts = ["features", "--format progress", "--fail-fast"]
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
# yard lives in the :development group, which CI omits when it runs the tests.
|
|
53
|
+
# Requiring it unconditionally would make `rake test` fail there, so the real
|
|
54
|
+
# task is only defined when yard is installed and a stub explains its absence
|
|
55
|
+
# otherwise. Nothing in CI gates on documentation.
|
|
56
|
+
begin
|
|
57
|
+
require "yard"
|
|
58
|
+
|
|
59
|
+
YARD::Rake::YardocTask.new(:doc) do |t|
|
|
60
|
+
t.files = ["lib/**/*.rb"]
|
|
61
|
+
t.options = ["--output-dir", "doc", "--markup", "markdown"]
|
|
62
|
+
end
|
|
63
|
+
rescue LoadError
|
|
64
|
+
desc "Generate YARD documentation (install the development group first)"
|
|
65
|
+
task :doc do
|
|
66
|
+
abort "yard is not available. Run `bundle install --with development` first."
|
|
67
|
+
end
|
|
41
68
|
end
|
|
42
69
|
|
|
43
70
|
desc "Run all test suites"
|
|
44
|
-
task test:
|
|
71
|
+
task test: %i{unit features}
|
|
45
72
|
|
|
46
73
|
task default: %i{test}
|
data/features/support/env.rb
CHANGED
|
@@ -1,21 +1,9 @@
|
|
|
1
1
|
require "aruba/cucumber"
|
|
2
2
|
require "busser/cucumber"
|
|
3
3
|
|
|
4
|
-
if ENV["COVERAGE"]
|
|
5
|
-
require "simplecov"
|
|
6
|
-
SimpleCov.command_name "features"
|
|
7
|
-
end
|
|
8
|
-
|
|
9
4
|
# aruba 2 dropped @aruba_timeout_seconds; setting it in a Before hook is a
|
|
10
5
|
# no-op, which quietly left these commands on aruba's 15 second default.
|
|
11
6
|
# Installing a plugin and its gems into a cold sandbox does not always fit.
|
|
12
7
|
Aruba.configure do |config|
|
|
13
8
|
config.exit_timeout = 60
|
|
14
9
|
end
|
|
15
|
-
|
|
16
|
-
After do |s|
|
|
17
|
-
# Tell Cucumber to quit after this scenario is done - if it failed.
|
|
18
|
-
# This is useful to inspect the 'tmp/aruba' directory before any other
|
|
19
|
-
# steps are executed and clear it out.
|
|
20
|
-
Cucumber.wants_to_quit = true if s.failed?
|
|
21
|
-
end
|
|
@@ -8,37 +8,37 @@ Feature: Test command
|
|
|
8
8
|
When I successfully run `busser plugin install busser-bats --force-postinstall`
|
|
9
9
|
Given a suite directory named "bats"
|
|
10
10
|
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
11
|
+
Scenario: A passing test suite
|
|
12
|
+
Given a file in suite "bats" named "default.bats" with:
|
|
13
|
+
"""
|
|
14
|
+
@test "runs something" {
|
|
15
|
+
run echo "hello"
|
|
16
|
+
[ "$status" -eq 0 ]
|
|
17
|
+
[ "$output" == "hello" ]
|
|
18
|
+
}
|
|
19
19
|
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
20
|
+
"""
|
|
21
|
+
When I run `busser test bats`
|
|
22
|
+
Then the output should contain:
|
|
23
|
+
"""
|
|
24
|
+
1..1
|
|
25
|
+
ok 1 runs something
|
|
26
|
+
"""
|
|
27
|
+
And the exit status should be 0
|
|
28
28
|
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
29
|
+
Scenario: A failing test suite
|
|
30
|
+
Given a file in suite "bats" named "default.bats" with:
|
|
31
|
+
"""
|
|
32
|
+
@test "fails something" {
|
|
33
|
+
run which uhoh-whatzit-called
|
|
34
|
+
[ "$status" -eq 0 ]
|
|
35
|
+
}
|
|
36
36
|
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
37
|
+
"""
|
|
38
|
+
When I run `busser test bats`
|
|
39
|
+
Then the output should contain:
|
|
40
|
+
"""
|
|
41
|
+
1..1
|
|
42
|
+
not ok 1 fails something
|
|
43
|
+
"""
|
|
44
|
+
And the exit status should not be 0
|
data/lib/busser/bats/version.rb
CHANGED
|
@@ -16,6 +16,7 @@
|
|
|
16
16
|
# limitations under the License.
|
|
17
17
|
|
|
18
18
|
require "pathname" unless defined?(Pathname)
|
|
19
|
+
require "shellwords" unless defined?(Shellwords)
|
|
19
20
|
|
|
20
21
|
require "busser/runner_plugin"
|
|
21
22
|
|
|
@@ -25,14 +26,37 @@ require "busser/runner_plugin"
|
|
|
25
26
|
#
|
|
26
27
|
class Busser::RunnerPlugin::Bats < Busser::RunnerPlugin::Base
|
|
27
28
|
|
|
29
|
+
# Installs the vendored bats onto the machine under test. Runs once, when
|
|
30
|
+
# Busser installs this plugin.
|
|
31
|
+
#
|
|
32
|
+
# bats 0.4 shipped bin/bats as a symlink that the tarball did not preserve,
|
|
33
|
+
# so this used to recreate it by hand before running install.sh. bats-core
|
|
34
|
+
# ships bin/bats as a real file, and recreating the link would replace it
|
|
35
|
+
# with one pointing at libexec/bats, which does not exist in bats-core --
|
|
36
|
+
# its executables live in libexec/bats-core.
|
|
28
37
|
postinstall do
|
|
29
38
|
inside(Pathname.new(__FILE__).dirname.join("../../../vendor/bats")) do
|
|
30
|
-
|
|
31
|
-
run!(%{./install.sh #{vendor_path("bats")}})
|
|
39
|
+
run!(%{./install.sh #{Shellwords.escape(vendor_path("bats").to_s)}})
|
|
32
40
|
end
|
|
33
41
|
end
|
|
34
42
|
|
|
43
|
+
# Builds the bats invocation.
|
|
44
|
+
#
|
|
45
|
+
# Both paths are quoted: the Busser root is user supplied through
|
|
46
|
+
# BUSSER_ROOT, and an unquoted path containing a space would be split into
|
|
47
|
+
# two arguments by the shell and silently run the wrong thing.
|
|
48
|
+
#
|
|
49
|
+
# @param bats_bin [String, Pathname] the vendored bats executable
|
|
50
|
+
# @param suite [String, Pathname] the suite directory holding the .bats files
|
|
51
|
+
# @return [String] the command to run
|
|
52
|
+
def self.command_for(bats_bin, suite)
|
|
53
|
+
%{#{Shellwords.escape(bats_bin.to_s)} #{Shellwords.escape(suite.to_s)}}
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
# Runs the suite's .bats files through the vendored bats.
|
|
57
|
+
#
|
|
58
|
+
# @return [void]
|
|
35
59
|
def test
|
|
36
|
-
run!(
|
|
60
|
+
run!(self.class.command_for(vendor_path("bats").join("bin/bats"), suite_path("bats")))
|
|
37
61
|
end
|
|
38
62
|
end
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
require_relative "../../spec_helper"
|
|
2
|
+
|
|
3
|
+
require "shellwords"
|
|
4
|
+
require "busser/runner_plugin/bats"
|
|
5
|
+
|
|
6
|
+
describe Busser::RunnerPlugin::Bats do
|
|
7
|
+
describe ".command_for" do
|
|
8
|
+
it "puts the bats binary first and the suite second" do
|
|
9
|
+
cmd = Busser::RunnerPlugin::Bats.command_for("/opt/busser/vendor/bats/bin/bats",
|
|
10
|
+
"/opt/busser/suites/bats")
|
|
11
|
+
|
|
12
|
+
_(cmd).must_equal "/opt/busser/vendor/bats/bin/bats /opt/busser/suites/bats"
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
# BUSSER_ROOT is user supplied, and Windows-style or otherwise spaced paths
|
|
16
|
+
# do turn up. Unquoted, the shell would split the path and bats would be
|
|
17
|
+
# handed arguments nobody intended.
|
|
18
|
+
it "quotes a path containing spaces" do
|
|
19
|
+
cmd = Busser::RunnerPlugin::Bats.command_for("/opt/busser/bin/bats",
|
|
20
|
+
"/tmp/my tests/suites/bats")
|
|
21
|
+
|
|
22
|
+
# Shellwords.split is what a shell would do with this string, so this
|
|
23
|
+
# asserts the shell sees exactly two arguments rather than three.
|
|
24
|
+
_(Shellwords.split(cmd)).must_equal ["/opt/busser/bin/bats", "/tmp/my tests/suites/bats"]
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
it "neutralises shell metacharacters in a path" do
|
|
28
|
+
cmd = Busser::RunnerPlugin::Bats.command_for("/opt/busser/bin/bats",
|
|
29
|
+
"/tmp/a;rm -rf x/bats")
|
|
30
|
+
|
|
31
|
+
_(Shellwords.split(cmd)).must_equal ["/opt/busser/bin/bats", "/tmp/a;rm -rf x/bats"]
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
it "accepts Pathname arguments" do
|
|
35
|
+
cmd = Busser::RunnerPlugin::Bats.command_for(Pathname.new("/a/bats"),
|
|
36
|
+
Pathname.new("/b/suites/bats"))
|
|
37
|
+
|
|
38
|
+
_(cmd).must_equal "/a/bats /b/suites/bats"
|
|
39
|
+
end
|
|
40
|
+
end
|
|
41
|
+
end
|
data/spec/spec_helper.rb
ADDED