bashcov 1.8.1 → 3.0.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5f7a8a7c155fad81c5018015053083c015dbadfec694178e3f5ca40bc2811e93
4
- data.tar.gz: 9adb13322f197aae9963ae90701ff24ed40f9b2473c9410f687c481592dbe387
3
+ metadata.gz: dffc7667dad0e51e2e47f4c4df861d52be6240aff021c7c7771c2e4f8219f862
4
+ data.tar.gz: d720302f22dacf1ac91853301d65ac0a24ac3ff17415fa7fdb42fc1e6b906079
5
5
  SHA512:
6
- metadata.gz: '079bfd802290a486b23cce687c2ee0f5a8f255a82bc1f604b426aa469828009b110aa431ae85d8570c3ccc013d6eb948cbcb0b8a0e3a01f5f94c01dea8edf449'
7
- data.tar.gz: a931f8ba4a96ce8b92f4b977b48e2ee34c3b125b5ecebb2f78662f6f133559814ea748ac4c0ea60d57650239080588fc521098b8c2a260adf9f40e8bde156b4d
6
+ metadata.gz: 284281285d8c60d800753fd0f4ff697d0a5e6faf246a64dfd1509f2cca4f3c6e0f5e91e417e76de2014937b91ada9fee4fcc266ad16dc8d1d106a3912cb6f524
7
+ data.tar.gz: cf79ef6c4e814d112c1255fe9fc59956537b7ad830eda345063395f5c7676895efcdbf7ec899185563e50577df756afb929bf6cb71b9106daeeef93d330dd5a9
data/.build.yml ADDED
@@ -0,0 +1,11 @@
1
+ image: archlinux
2
+ packages:
3
+ - ruby-bundler
4
+ - bash
5
+ sources:
6
+ - https://git.sr.ht/~infertux/bashcov
7
+ tasks:
8
+ - rake: |
9
+ cd bashcov
10
+ bundle install
11
+ bundle exec rake
@@ -0,0 +1,3 @@
1
+ github: infertux
2
+ liberapay: infertux
3
+ patreon: infertux
data/.gitignore ADDED
@@ -0,0 +1,19 @@
1
+ *.swp
2
+ *.gem
3
+ *.rbc
4
+ .bundle
5
+ .config
6
+ .yardoc
7
+ .rbx/
8
+ Gemfile.lock
9
+ InstalledFiles
10
+ _yardoc
11
+ coverage
12
+ doc/
13
+ lib/bundler/man
14
+ pkg
15
+ rdoc
16
+ spec/reports
17
+ test/tmp
18
+ test/version_tmp
19
+ tmp
data/.gitlab-ci.yml ADDED
@@ -0,0 +1,57 @@
1
+ # Official language image. Look for the different tagged releases at:
2
+ # https://hub.docker.com/r/library/ruby/tags/
3
+ image: ruby:latest
4
+
5
+ before_script:
6
+ - ruby -v
7
+ - bundle install -j $(nproc)
8
+ - ./spec/install_bash.sh
9
+ - bash --version
10
+ - id
11
+ - env
12
+
13
+ audit:
14
+ script:
15
+ - bundle exec rake bundle:audit:update
16
+ - bundle exec rake bundle:audit:check
17
+
18
+ build:
19
+ script:
20
+ - bundle exec rake build
21
+ - bundle exec rake build:checksum
22
+ - cat checksums/*
23
+
24
+ cucumber:
25
+ script: bundle exec rake cucumber
26
+
27
+ # Current Bash versions can be found at https://git.savannah.gnu.org/cgit/bash.git
28
+ rspec-bash-5.2:
29
+ variables:
30
+ INSTALL_BASH_VERSION: "5.2"
31
+ script: bundle exec rake spec
32
+
33
+ rspec-bash-5.1:
34
+ variables:
35
+ INSTALL_BASH_VERSION: "5.1"
36
+ script: bundle exec rake spec
37
+
38
+ rspec-bash-5.0:
39
+ variables:
40
+ INSTALL_BASH_VERSION: "5.0"
41
+ script: bundle exec rake spec
42
+
43
+ rspec-bash-4.4:
44
+ variables:
45
+ INSTALL_BASH_VERSION: "4.4"
46
+ script: bundle exec rake spec
47
+
48
+ rspec-bash-4.3:
49
+ variables:
50
+ INSTALL_BASH_VERSION: "4.3"
51
+ script: bundle exec rake spec
52
+
53
+ rubocop:
54
+ script: bundle exec rake rubocop
55
+
56
+ yard:
57
+ script: bundle exec yard stats --list-undoc
data/.rspec ADDED
@@ -0,0 +1,4 @@
1
+ --color
2
+ --format d
3
+ --order random
4
+ --profile
data/.rubocop.yml ADDED
@@ -0,0 +1,55 @@
1
+ require:
2
+ - rubocop-rake
3
+ - rubocop-rspec
4
+
5
+ AllCops:
6
+ TargetRubyVersion: 3.0
7
+ NewCops: enable
8
+
9
+ Metrics:
10
+ Enabled: false
11
+
12
+ Gemspec/DevelopmentDependencies:
13
+ Enabled: false
14
+
15
+ Layout/AccessModifierIndentation:
16
+ EnforcedStyle: outdent
17
+
18
+ Layout/LineLength:
19
+ Enabled: 100
20
+
21
+ Lint/RedundantSplatExpansion:
22
+ Enabled: false
23
+
24
+ RSpec/ExampleLength:
25
+ Enabled: false
26
+
27
+ RSpec/InstanceVariable:
28
+ Enabled: false
29
+
30
+ RSpec/MessageSpies:
31
+ EnforcedStyle: receive
32
+
33
+ RSpec/MultipleExpectations:
34
+ Enabled: false
35
+
36
+ RSpec/NamedSubject:
37
+ Enabled: false
38
+
39
+ RSpec/NestedGroups:
40
+ Enabled: false
41
+
42
+ Style/ParallelAssignment:
43
+ Enabled: false
44
+
45
+ Style/StringLiterals:
46
+ EnforcedStyle: double_quotes
47
+
48
+ Style/SpecialGlobalVars:
49
+ Enabled: false
50
+
51
+ Style/TrailingCommaInArrayLiteral:
52
+ EnforcedStyleForMultiline: comma
53
+
54
+ Style/TrailingCommaInHashLiteral:
55
+ EnforcedStyleForMultiline: comma
data/.simplecov ADDED
@@ -0,0 +1,9 @@
1
+ # frozen_string_literal: true
2
+
3
+ SimpleCov.start do
4
+ minimum_coverage 95
5
+ add_filter "/features/"
6
+ add_filter "/spec/"
7
+ add_filter "/tmp/"
8
+ add_filter "/.git/"
9
+ end
data/CHANGELOG.md CHANGED
@@ -1,7 +1,29 @@
1
- ## Unreleased ([changes](https://github.com/infertux/bashcov/compare/v1.8.1...master))
1
+ ## Unreleased ([changes](https://github.com/infertux/bashcov/compare/v3.0.0...master))
2
2
 
3
3
  * TBD
4
4
 
5
+ ## v3.0.0, 2023-04-10 ([changes](https://github.com/infertux/bashcov/compare/v1.8.2...v3.0.0))
6
+
7
+ * [MISC] New minimum Bash version supported is 4.3
8
+ * [MISC] New minimum Ruby version supported is 3.0
9
+ * [BUGFIX] Running Bashcov as root is now working (especially useful with Docker) although it is not recommended (#31, #43 and #56)
10
+ * [BUGFIX] Fix comments preceded by tabs not filtered out (#68)
11
+ * [BUGFIX] Fix two-line multilines not being treated as related (#67)
12
+ * [BUGFIX] Redefine `BASH_VERSION` when `bash_path` is read from command options (#57)
13
+ * [BUGFIX] Mute output from Bashcov and SimpleCov when requested (#54)
14
+ * [BUGFIX] Correctly handle empty scripts by short-circuiting
15
+ `FieldStream#each` if the reader stream is at end-of-file before
16
+ the start-of-fields pattern is encountered (#41)
17
+ * [FEATURE] Bashcov omits from the coverage results any files that match one
18
+ or more of the filters in `SimpleCov.filters` (#38)
19
+ * [FEATURE] Ensure that files matching the `SimpleCov.tracked_files` glob
20
+ pattern are included in the coverage results, regardless of
21
+ whether `Bashcov.skip_uncovered` is enabled (#38)
22
+
23
+ ## v1.8.2, 2018-03-27 ([changes](https://github.com/infertux/bashcov/compare/v1.8.1...v1.8.2))
24
+
25
+ * [BUGFIX] Fix coverage for complex heredoc constructions (#32)
26
+
5
27
  ## v1.8.1, 2018-03-01 ([changes](https://github.com/infertux/bashcov/compare/v1.8.0...v1.8.1))
6
28
 
7
29
  * [BUGFIX] Fix incorrect coverage for some multiline strings (#35)
data/Gemfile CHANGED
@@ -2,6 +2,6 @@
2
2
 
3
3
  source "https://rubygems.org"
4
4
 
5
- # gem 'simplecov', path: '../simplecov'
5
+ # gem "simplecov", path: "../simplecov"
6
6
 
7
7
  gemspec
data/LICENSE.txt CHANGED
@@ -1,4 +1,4 @@
1
- Copyright (c) 2012-2018 Cédric Félizard
1
+ Copyright (c) 2012-2023 Cédric Félizard
2
2
 
3
3
  MIT License
4
4
 
data/README.md CHANGED
@@ -1,146 +1,65 @@
1
1
  # Bashcov
2
2
 
3
+ [![Funding](https://img.shields.io/liberapay/patrons/infertux.svg?logo=liberapay)](https://liberapay.com/infertux/donate)
4
+ [![Sponsors](https://img.shields.io/liberapay/patrons/infertux)](https://liberapay.com/infertux)
3
5
  [![Gem Version](https://img.shields.io/gem/v/bashcov.svg)](https://rubygems.org/gems/bashcov)
4
- [![Build Status](https://secure.travis-ci.org/infertux/bashcov.png?branch=master)](https://travis-ci.org/infertux/bashcov)
5
- [![Coverage Status](https://coveralls.io/repos/infertux/bashcov/badge.png?branch=master)](https://coveralls.io/r/infertux/bashcov)
6
- [![Dependency Status](https://gemnasium.com/infertux/bashcov.png)](https://gemnasium.com/infertux/bashcov)
6
+ [![Build Status](https://gitlab.com/infertux/bashcov/badges/master/pipeline.svg)](https://gitlab.com/infertux/bashcov/-/pipelines)
7
7
  [![Maintainability](https://api.codeclimate.com/v1/badges/083fdbba795049cd5f06/maintainability)](https://codeclimate.com/github/infertux/bashcov/maintainability)
8
+ [![Inline docs](http://inch-ci.org/github/infertux/bashcov.svg)](http://inch-ci.org/github/infertux/bashcov)
8
9
 
9
- **Code coverage for Bash**
10
-
11
- * [Source Code]
12
- * [Bug Tracker]
13
- * [API Documentation]
14
- * [Changelog]
15
- * [Rubygem]
16
- * [Continuous Integration]
17
- * [Dependencies]
18
- * [SimpleCov]
19
-
20
- [Source Code]: https://github.com/infertux/bashcov "Source Code on Github"
21
- [Bug Tracker]: https://github.com/infertux/bashcov/issues "Bug Tracker on Github"
22
- [API documentation]: http://rubydoc.info/gems/bashcov/frames "API Documentation on Rubydoc"
23
- [Changelog]: https://github.com/infertux/bashcov/blob/master/CHANGELOG.md "Project Changelog"
24
- [Rubygem]: https://rubygems.org/gems/bashcov "Bashcov on Rubygems"
25
- [Continuous Integration]: https://travis-ci.org/infertux/bashcov "Bashcov on Travis-CI"
26
- [Dependencies]: https://gemnasium.com/infertux/bashcov "Bashcov dependencies on Gemnasium"
27
- [Bashcov]: https://github.com/infertux/bashcov
28
- [SimpleCov]: https://github.com/colszowka/simplecov "Bashcov is backed by SimpleCov to generate awesome coverage report"
29
- [Test app demo]: https://infertux.github.com/bashcov/test_app/ "Coverage for the bundled test application"
30
-
31
- You should check out these coverage examples - it's worth a thousand words:
32
-
33
- - [Test app demo]
34
- - [RVM demo](https://infertux.github.com/bashcov/rvm/ "Coverage for RVM")
10
+ Bashcov is a **code coverage analysis tool for Bash**.
11
+
12
+ In most cases, you'll want overall coverage results for your project from
13
+ [shUnit2](https://github.com/kward/shunit2),
14
+ [Bats](https://github.com/bats-core/bats-core),
15
+ [bash_unit](https://github.com/pgrange/bash_unit),
16
+ [assert.sh](https://github.com/lehmannro/assert.sh),
17
+ [bashaspec](https://github.com/d10n/bashaspec),
18
+ etc.
19
+ Bashcov automatically takes care of this by caching and merging results when generating reports,
20
+ so your report includes coverage across your test suites and thereby gives you a better picture of blank spots.
21
+
22
+ It uses the [SimpleCov](https://github.com/colszowka/simplecov) coverage library to generate HTML reports.
23
+ SimpleCov gets installed automatically when you install Bashcov.
24
+
25
+ Here are example coverages generated by Bashcov:
26
+ [test app demo](https://infertux.github.io/bashcov/test_app/ "Coverage for the bundled test application") &
27
+ [RVM demo](https://infertux.github.io/bashcov/rvm/ "Coverage for RVM").
35
28
 
36
29
  ## Installation
37
30
 
38
- `$ gem install bashcov`
31
+ `gem install bashcov`
32
+
33
+ If the `gem` command is unavailable, you need to [install Ruby](https://www.ruby-lang.org/en/documentation/installation/) first.
39
34
 
40
35
  ## Usage
41
36
 
42
- `$ bashcov --help` prints all available options.
43
- Here are some examples:
37
+ `bashcov --help` prints all available options. Here are some examples:
44
38
 
45
- $ bashcov ./script.sh
46
- $ bashcov --skip-uncovered ./script.sh
47
- $ bashcov -- ./script.sh --some --flags
48
- $ bashcov --skip-uncovered -- ./script.sh --some --flags
39
+ bashcov ./script.sh
40
+ bashcov --skip-uncovered ./script.sh
41
+ bashcov -- ./script.sh --some --flags
42
+ bashcov --skip-uncovered -- ./script.sh --some --flags
49
43
 
50
- `script.sh` can be a mere Bash script or typically your CI script.
51
- Bashcov will keep track of all executed scripts.
44
+ `./script.sh` can be a mere Bash script or typically your CI script. Bashcov will keep track of all executed scripts.
52
45
 
53
- Then it will create a directory named `./coverage/` containing nice HTML files.
54
- Open `./coverage/index.html` to browse the coverage report.
46
+ It will create a directory named `./coverage/`, you may open `./coverage/index.html` to browse the coverage report.
55
47
 
56
48
  ### SimpleCov integration
57
49
 
58
- You can take great advantage of [SimpleCov] by adding a `.simplecov` file in
59
- your project's root (like [this](https://github.com/infertux/bashcov/blob/master/spec/test_app/.simplecov)).
60
- See [SimpleCov README](https://github.com/colszowka/simplecov#readme) for more
61
- information.
62
-
63
- #### Controlling the command name
64
-
65
- Bashcov respects all of your `.simplecov` settings save one --
66
- [`SimpleCov.command_name`](http://www.rubydoc.info/gems/simplecov/SimpleCov/Configuration#command_name-instance_method),
67
- which is the tag that SimpleCov attaches to coverage results from a particular
68
- test suite. You can set the value of `SimpleCov.command_name` by using
69
- Bashcov's `--command-name` option, or by assigning a value to the environment
70
- variable `BASHCOV_COMMAND_NAME`. Otherwise, Bashcov will generate a command
71
- name for you based on the name of the currently-executing Bash script and any
72
- arguments passed to it. For example, assuming your Bash lives at `/bin/bash`
73
- and you run the command
74
-
75
- ```
76
- $ bashcov -- ./test_suite.sh --and some --flags
77
- ```
78
-
79
- Bashcov will set `SimpleCov.command_name` to `"/bin/bash ./test_suite.sh --and
80
- some --flags"`. Basing `SimpleCov.command_name` on the executing command helps
81
- to ensure that multiple coverage runs don't [overwrite each other's
82
- results](https://github.com/colszowka/simplecov#test-suite-names) due to
83
- SimpleCov identifying multiple runs by the same tag. The `--command-name` and
84
- `BASHCOV_COMMAND_NAME` knobs are there for you to twiddle in case your test
85
- suite runs the exact same `bashcov` command more than once, in which case the
86
- generated command name will not distinguish each invocation from the others.
87
-
88
- For more info on `SimpleCov.command_name` and its relation to SimpleCov's
89
- result-merging behavior, see the [SimpleCov
90
- README](https://github.com/colszowka/simplecov#merging-results).
91
-
92
- ### Some gory details
93
-
94
- Figuring out where an executing Bash script lives in the file system can be
95
- surprisingly difficult. Bash offers a fair amount of [introspection into its
96
- internals](https://www.gnu.org/software/bash/manual/html_node/Bash-Variables.html),
97
- but the location of the current script has to be inferred from the limited
98
- information available through `BASH_SOURCE`, `PWD`, and `OLDPWD` (and
99
- potentially `DIRSTACK` if you are using `pushd`/`popd`). For this purpose,
100
- Bashcov puts Bash in debug mode and sets up a `PS4` that expands the values of
101
- these variables, reading them on each command that Bash executes. But, given
102
- that:
103
-
104
- * `BASH_SOURCE` is only an absolute path if the script was invoked using an
105
- absolute path,
106
- * the builtins `cd`, `pushd`, and `popd` alter `PWD` and `OLDPWD`, and
107
- * none of these variables are read-only and can therefore be `unset` or
108
- otherwise altered,
109
-
110
- it can be easy to lose track of where we are.
111
-
112
- _"Wait a minute, what about `pwd`, `readlink`, and so on?"_ That would be great,
113
- except that subshells executed as part of expanding the `PS4` can cause Bash to
114
- report [extra executions](https://github.com/infertux/bashcov/commit/4130874e30a05b7ab6ea66fb96a19acaa973c178)
115
- for [certain lines](https://github.com/infertux/bashcov/pull/16). Also,
116
- subshells are slow as the `PS4` is expanded on each and every command when Bash
117
- is in debug mode.
118
-
119
- To deal with these limitations, Bashcov uses the expedient of maintaining two
120
- stacks that track changes to `PWD` and `OLDPWD`. To determine the full path to
121
- the executing script, Bashcov iterates in reverse over the `PWD` stack, testing
122
- for the first `$PWD/$BASH_SOURCE` combination that refers to an existing file.
123
- This heuristic is susceptible to false positives -- under certain combinations
124
- of directory structure, script invocation paths, and working directory changes,
125
- it may yield a path that doesn't refer to the currently-running script.
126
- However, it performs well under the various working directory changes performed
127
- in the [test app demo] and avoids the spurious extra hits caused by using
128
- subshells in the `PS4`.
129
-
130
- One final note on innards: Bash 4.3 fixed a bug in which `PS4` expansion is
131
- truncated to a maximum of 128 characters. On platforms whose Bash version
132
- suffers from this bug, Bashcov uses the ASCII record separator character to
133
- delimit the `PS4` fields, whereas it uses a long random string on Bash 4.3 and
134
- above. When the field delimiter appears in the path of a script under test or
135
- in a command the script executes, Bashcov won't correctly parse the `PS4` and
136
- will abort early with incomplete coverage results.
50
+ You can leverage the underlying library [SimpleCov](https://github.com/colszowka/simplecov)
51
+ by adding a `.simplecov` file in your project's root, like [this](https://github.com/infertux/bashcov/blob/master/spec/test_app/.simplecov).
52
+ See [advanced usage](./USAGE.md) for more information.
137
53
 
138
54
  ## Contributing
139
55
 
140
56
  Bug reports and patches are most welcome.
141
57
  See the [contribution guidelines](https://github.com/infertux/bashcov/blob/master/CONTRIBUTING.md).
142
58
 
59
+ ## Sponsorship
60
+
61
+ Bashcov was [created in 2012](https://github.com/infertux/bashcov/commit/f65e65e5aa3377beb334beee9924136a34a913e8) and it needs your help. I have been maintaining the project for over a decade and keeping it working with new releases of Bash and Ruby takes time. If you use Bashcov professionally, please considerer supporting it on [Liberapay](https://liberapay.com/infertux) through your employer or directly. Thank you for supporting *Free and Open-Source Software*.
62
+
143
63
  ## License
144
64
 
145
65
  MIT
146
-
data/Rakefile CHANGED
@@ -2,8 +2,13 @@
2
2
 
3
3
  require "bundler/gem_tasks"
4
4
 
5
+ require "bundler/audit/task"
6
+ Bundler::Audit::Task.new
7
+
5
8
  require "cucumber/rake/task"
6
- Cucumber::Rake::Task.new
9
+ Cucumber::Rake::Task.new do |t|
10
+ t.cucumber_opts = %w[--publish-quiet]
11
+ end
7
12
 
8
13
  require "rspec/core/rake_task"
9
14
  RSpec::Core::RakeTask.new(:spec) do |t|
@@ -13,4 +18,4 @@ end
13
18
  require "rubocop/rake_task"
14
19
  RuboCop::RakeTask.new
15
20
 
16
- task default: %i[rubocop spec cucumber]
21
+ task default: %i[bundle:audit cucumber spec rubocop]
data/TESTING.md ADDED
@@ -0,0 +1,4 @@
1
+ `bundle exec rake` will run a quick test suite with the current Bash and Ruby version.
2
+
3
+ `./test.sh` will run all [GitLab CI pipelines](https://gitlab.com/infertux/bashcov/-/pipelines) locally.
4
+ You'll need [Docker](https://www.docker.com/) and [GitLab Runner](https://gitlab.com/gitlab-org/gitlab-runner) installed on your machine.
data/USAGE.md ADDED
@@ -0,0 +1,66 @@
1
+ ### Controlling the command name
2
+
3
+ Bashcov respects all of your `.simplecov` settings save one --
4
+ [`SimpleCov.command_name`](http://www.rubydoc.info/gems/simplecov/SimpleCov/Configuration#command_name-instance_method),
5
+ which is the tag that SimpleCov attaches to coverage results from a particular
6
+ test suite. You can set the value of `SimpleCov.command_name` by using
7
+ Bashcov's `--command-name` option, or by assigning a value to the environment
8
+ variable `BASHCOV_COMMAND_NAME`. Otherwise, Bashcov will generate a command
9
+ name for you based on the name of the currently-executing Bash script and any
10
+ arguments passed to it. For example, assuming your Bash lives at `/bin/bash`
11
+ and you run the command
12
+
13
+ ```
14
+ bashcov -- ./test_suite.sh --and some --flags
15
+ ```
16
+
17
+ Bashcov will set `SimpleCov.command_name` to `"/bin/bash ./test_suite.sh --and
18
+ some --flags"`. Basing `SimpleCov.command_name` on the executing command helps
19
+ to ensure that multiple coverage runs don't [overwrite each other's
20
+ results](https://github.com/colszowka/simplecov#test-suite-names) due to
21
+ SimpleCov identifying multiple runs by the same tag. The `--command-name` and
22
+ `BASHCOV_COMMAND_NAME` knobs are there for you to twiddle in case your test
23
+ suite runs the exact same `bashcov` command more than once, in which case the
24
+ generated command name will not distinguish each invocation from the others.
25
+
26
+ For more info on `SimpleCov.command_name` and its relation to SimpleCov's
27
+ result-merging behavior, see the [SimpleCov
28
+ README](https://github.com/colszowka/simplecov#merging-results).
29
+
30
+ ### Some gory details
31
+
32
+ Figuring out where an executing Bash script lives in the file system can be
33
+ surprisingly difficult. Bash offers a fair amount of [introspection into its
34
+ internals](https://www.gnu.org/software/bash/manual/html_node/Bash-Variables.html),
35
+ but the location of the current script has to be inferred from the limited
36
+ information available through `BASH_SOURCE`, `PWD`, and `OLDPWD` (and
37
+ potentially `DIRSTACK` if you are using `pushd`/`popd`). For this purpose,
38
+ Bashcov puts Bash in debug mode and sets up a `PS4` that expands the values of
39
+ these variables, reading them on each command that Bash executes. But, given
40
+ that:
41
+
42
+ * `BASH_SOURCE` is only an absolute path if the script was invoked using an
43
+ absolute path,
44
+ * the builtins `cd`, `pushd`, and `popd` alter `PWD` and `OLDPWD`, and
45
+ * none of these variables are read-only and can therefore be `unset` or
46
+ otherwise altered,
47
+
48
+ it can be easy to lose track of where we are.
49
+
50
+ _"Wait a minute, what about `pwd`, `readlink`, and so on?"_ That would be great,
51
+ except that subshells executed as part of expanding the `PS4` can cause Bash to
52
+ report [extra executions](https://github.com/infertux/bashcov/commit/4130874e30a05b7ab6ea66fb96a19acaa973c178)
53
+ for [certain lines](https://github.com/infertux/bashcov/pull/16). Also,
54
+ subshells are slow as the `PS4` is expanded on each and every command when Bash
55
+ is in debug mode.
56
+
57
+ To deal with these limitations, Bashcov uses the expedient of maintaining two
58
+ stacks that track changes to `PWD` and `OLDPWD`. To determine the full path to
59
+ the executing script, Bashcov iterates in reverse over the `PWD` stack, testing
60
+ for the first `$PWD/$BASH_SOURCE` combination that refers to an existing file.
61
+ This heuristic is susceptible to false positives -- under certain combinations
62
+ of directory structure, script invocation paths, and working directory changes,
63
+ it may yield a path that doesn't refer to the currently-running script.
64
+ However, it performs well under the various working directory changes performed
65
+ in the [test app demo] and avoids the spurious extra hits caused by using
66
+ subshells in the `PS4`.
data/bashcov.gemspec CHANGED
@@ -1,36 +1,42 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- lib = File.expand_path("../lib", __FILE__)
4
- $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
5
- require "bashcov/version"
3
+ require_relative "lib/bashcov/version"
6
4
 
7
- Gem::Specification.new do |gem|
8
- gem.name = "bashcov"
9
- gem.version = Bashcov::VERSION
10
- gem.authors = ["Cédric Félizard"]
11
- gem.email = ["cedric@felizard.fr"]
12
- gem.description = "Code coverage tool for Bash"
13
- gem.summary = gem.description
14
- gem.homepage = "https://github.com/infertux/bashcov"
15
- gem.license = "MIT"
5
+ Gem::Specification.new do |spec|
6
+ spec.name = "bashcov"
7
+ spec.version = Bashcov::VERSION
8
+ spec.authors = ["Cédric Félizard"]
9
+ spec.email = ["cedric@felizard.fr"]
16
10
 
17
- gem.files = `git ls-files -z`.split("\x0").reject do |file|
18
- file.start_with?(".") || file.match(%r{\A(test|spec|features)/})
19
- end
11
+ spec.summary = spec.description
12
+ spec.description = "Code coverage tool for Bash"
13
+ spec.homepage = "https://github.com/infertux/bashcov"
14
+ spec.license = "MIT"
15
+ spec.required_ruby_version = ">= 3.0.0"
20
16
 
21
- gem.executables = gem.files.grep(%r{\Abin/}).map { |f| File.basename(f) }
22
- gem.require_paths = ["lib"]
17
+ spec.metadata["homepage_uri"] = spec.homepage
18
+ spec.metadata["source_code_uri"] = "https://github.com/infertux/bashcov"
19
+ spec.metadata["changelog_uri"] = "https://github.com/infertux/bashcov/blob/master/CHANGELOG.md"
23
20
 
24
- gem.required_ruby_version = ">= 2.3.0"
21
+ # Specify which files should be added to the gem when it is released.
22
+ # The `git ls-files -z` loads the files in the RubyGem that have been added into git.
23
+ spec.files = Dir.chdir(File.expand_path(__dir__)) do
24
+ `git ls-files -z`.split("\x0").reject { |f| f.match(%r{\A(?:test|spec|features)/}) }
25
+ end
26
+ spec.bindir = "exe"
27
+ spec.executables = spec.files.grep(%r{\Aexe/}) { |f| File.basename(f) }
28
+ spec.require_paths = ["lib"]
25
29
 
26
- gem.add_dependency "simplecov", "~> 0.15"
30
+ spec.add_dependency "simplecov", "~> 0.21.2"
27
31
 
28
- gem.add_development_dependency "aruba", "~> 0.14.3"
29
- gem.add_development_dependency "coveralls"
30
- gem.add_development_dependency "cucumber"
31
- gem.add_development_dependency "mutant-rspec"
32
- gem.add_development_dependency "rake"
33
- gem.add_development_dependency "rspec"
34
- gem.add_development_dependency "rubocop"
35
- gem.add_development_dependency "yard"
32
+ spec.add_development_dependency "aruba"
33
+ spec.add_development_dependency "bundler-audit"
34
+ spec.add_development_dependency "cucumber"
35
+ spec.add_development_dependency "rake"
36
+ spec.add_development_dependency "rspec"
37
+ spec.add_development_dependency "rubocop"
38
+ spec.add_development_dependency "rubocop-rake"
39
+ spec.add_development_dependency "rubocop-rspec"
40
+ spec.add_development_dependency "yard"
41
+ spec.metadata["rubygems_mfa_required"] = "true"
36
42
  end
data/bin/bashcov CHANGED
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env ruby
2
2
  # frozen_string_literal: true
3
3
 
4
- lib = File.expand_path("../../lib", __FILE__)
4
+ lib = File.expand_path("../lib", __dir__)
5
5
  $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
6
6
 
7
7
  require "bashcov"
@@ -26,8 +26,18 @@ if SimpleCov.use_merging
26
26
  end
27
27
 
28
28
  SimpleCov.at_exit do
29
- puts "Run completed using #{Bashcov.fullname}"
30
- result.format!
29
+ puts "Run completed using #{Bashcov.fullname}" unless Bashcov.mute
30
+
31
+ begin
32
+ # XXX: suppress output from https://github.com/colszowka/simplecov-html/blob/9ec41504ab139fabfaddfc786dfdab5d6aca0bab/lib/simplecov-html.rb#L25
33
+ # See https://github.com/infertux/bashcov/issues/53
34
+ original_stdout = $stdout
35
+ $stdout = StringIO.new if Bashcov.mute
36
+
37
+ result.format!
38
+ ensure
39
+ $stdout = original_stdout
40
+ end
31
41
  end
32
42
 
33
43
  exit status.exitstatus
@@ -34,7 +34,7 @@ module Bashcov
34
34
  return false unless File.exist?(filename) && File.readable?(filename) \
35
35
  && File.file?(File.realpath(filename))
36
36
 
37
- shellscript_shebang?(filename) || \
37
+ shellscript_shebang?(filename) ||
38
38
  (shellscript_extension?(filename) && shellscript_syntax?(filename))
39
39
  end
40
40
 
@@ -54,10 +54,10 @@ module Bashcov
54
54
 
55
55
  return false unless shebang[0..1] == "#!"
56
56
 
57
- shell, arg = shebang[2..-1].split(/\s+/, 2)
57
+ shell, arg = shebang[2..].split(/\s+/, 2)
58
58
  shell_basename = File.basename(shell)
59
59
 
60
- SHELL_BASENAMES.include?(shell_basename) || \
60
+ SHELL_BASENAMES.include?(shell_basename) ||
61
61
  (OTHER_BASENAMES.include?(shell_basename) && SHELL_BASENAMES.include?(arg))
62
62
  end
63
63