rundoc 2.0.0 → 3.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (53) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +10 -7
  3. data/CHANGELOG.md +15 -0
  4. data/CONTRIBUTING.md +25 -0
  5. data/README.md +35 -48
  6. data/Rakefile +5 -1
  7. data/bin/rundoc +4 -17
  8. data/lib/rundoc/cli.rb +207 -49
  9. data/lib/rundoc/cli_argument_parser.rb +140 -0
  10. data/lib/rundoc/code_command/bash.rb +8 -1
  11. data/lib/rundoc/code_command/rundoc/depend_on.rb +1 -24
  12. data/lib/rundoc/code_command/rundoc/require.rb +13 -7
  13. data/lib/rundoc/code_command/website/driver.rb +7 -5
  14. data/lib/rundoc/code_command/website/navigate.rb +1 -1
  15. data/lib/rundoc/code_command/website/screenshot.rb +7 -2
  16. data/lib/rundoc/code_command/website/visit.rb +1 -1
  17. data/lib/rundoc/code_section.rb +4 -6
  18. data/lib/rundoc/context/after_build.rb +14 -0
  19. data/lib/rundoc/context/execution.rb +22 -0
  20. data/lib/rundoc/parser.rb +9 -5
  21. data/lib/rundoc/version.rb +1 -1
  22. data/lib/rundoc.rb +13 -5
  23. data/rundoc.gemspec +1 -0
  24. data/test/fixtures/cnb/ruby/download.md +22 -0
  25. data/test/fixtures/cnb/ruby/image_structure.md +34 -0
  26. data/test/fixtures/cnb/ruby/intro.md +5 -0
  27. data/test/fixtures/cnb/ruby/multiple_langs.md +43 -0
  28. data/test/fixtures/cnb/ruby/rundoc.md +48 -0
  29. data/test/fixtures/cnb/ruby/what_is_pack_build.md +18 -0
  30. data/test/fixtures/cnb/shared/call_to_action.md +11 -0
  31. data/test/fixtures/cnb/shared/configure_builder.md +23 -0
  32. data/test/fixtures/cnb/shared/install_pack.md +14 -0
  33. data/test/fixtures/cnb/shared/pack_build.md +20 -0
  34. data/test/fixtures/cnb/shared/procfile.md +13 -0
  35. data/test/fixtures/cnb/shared/use_the_image.md +52 -0
  36. data/test/fixtures/cnb/shared/what_is_a_builder.md +18 -0
  37. data/test/fixtures/rails_4/rundoc.md +5 -7
  38. data/test/fixtures/rails_5/rundoc.md +1 -1
  39. data/test/fixtures/rails_6/rundoc.md +2 -2
  40. data/test/fixtures/rails_7/rundoc.md +2 -3
  41. data/test/fixtures/simple_git/rundoc.md +13 -0
  42. data/test/integration/after_build_test.rb +62 -0
  43. data/test/integration/print_test.rb +9 -9
  44. data/test/integration/require_test.rb +63 -0
  45. data/test/integration/website_test.rb +35 -0
  46. data/test/rundoc/cli_argument_parser_test.rb +118 -0
  47. data/test/rundoc/code_section_test.rb +40 -8
  48. data/test/rundoc/parser_test.rb +3 -3
  49. data/test/rundoc/peg_parser_test.rb +6 -6
  50. data/test/rundoc/regex_test.rb +22 -0
  51. data/test/system/exe_cli_test.rb +231 -0
  52. data/test/test_helper.rb +74 -1
  53. metadata +40 -3
@@ -0,0 +1,14 @@
1
+ ## Install the pack CLI
2
+
3
+ We assume you have [docker installed](https://docs.docker.com/engine/install/) and a working copy [of git](https://github.com/git-guides/install-git). Next, you will need to install the CLI tool for building CNBs, [pack CLI](https://buildpacks.io/docs/for-platform-operators/how-to/integrate-ci/pack/). If you're on a Mac you can install it via Homebrew:
4
+
5
+ ```
6
+ :::-> print.text
7
+ $ brew install buildpacks/tap/pack
8
+ ```
9
+
10
+ Ensure that `pack` is installed correctly:
11
+
12
+ ```
13
+ :::>> $ pack --version
14
+ ```
@@ -0,0 +1,20 @@
1
+ ## Build the application image with the pack CLI
2
+
3
+ Now build an image named `my-image-name` by executing the heroku builder against the application by running the
4
+ `pack build` command:
5
+
6
+ ```
7
+ $ pack build my-image-name --path .
8
+ :::-- $ docker rmi -f my-image-name
9
+ :::-- $ pack build my-image-name --path . 2>&1 | tee build_output.txt
10
+ :::-> $ cat build_output.txt
11
+ ```
12
+
13
+ > [!NOTE]
14
+ > Your output may differ.
15
+
16
+ Verify that you see “Successfully built image my-image-name” at the end of the output. And verify that the image is present locally:
17
+
18
+ ```
19
+ :::>> $ docker image ls --format "table {{.ID}}\t{{.Repository}}\t{{.Tag}}" | grep my-image-name
20
+ ```
@@ -0,0 +1,13 @@
1
+ ## Configuring your web process with the Procfile
2
+
3
+ Most buildpacks rely on existing community standards to allow you to configure your application declaratively. They can also implement custom logic based on file contents on disk or environment variables present at build time.
4
+
5
+ The `Procfile` is a configuration file format that was [introduced by Heroku in 2011](https://devcenter.heroku.com/articles/procfile), you can now use this behavior on your CNB-powered application via the `heroku/procfile`, which like the rest of the buildpacks in our builder [is open source](https://github.com/heroku/buildpacks-procfile). The `heroku/procfile` buildpack allows you to configure your web startup process.
6
+
7
+ This is the `Procfile` of the getting started guide:
8
+
9
+ ```
10
+ :::-> $ cat Procfile
11
+ ```
12
+
13
+ By including this file and using `heroku/procfile` buildpack, your application will receive a default web process. You can configure this behavior by changing the contents of that file.
@@ -0,0 +1,52 @@
1
+ ## Use the image
2
+
3
+ Even though we used `pack` and CNBs to build our image, it can be run with your favorite tools like any other OCI image. We will be using the `docker` command line to run our image.
4
+
5
+ By default, images will be booted into a web server configuration. You can launch the app we just built by running:
6
+
7
+ ```
8
+ $ docker run -it --rm --env PORT=9292 -p 9292:9292 my-image-name
9
+ :::-> background.start("docker run --rm --env PORT=9292 -p 9292:9292 my-image-name", name: "docker_server")
10
+ :::-- $ sleep 10
11
+ :::-> background.log.read(name: "docker_server")
12
+ ```
13
+
14
+ Now when you visit [http://localhost:9292](http://localhost:9292) you should see a working web application:
15
+
16
+ ```
17
+ :::>> website.visit(name: "localhost", url: "http://localhost:9292")
18
+ :::>> website.screenshot(name: "localhost")
19
+ ```
20
+
21
+ Don't forget to stop the docker container when you're done.
22
+
23
+ ```
24
+ :::-- $ docker stop $(docker ps -q --filter ancestor=my-image-name )
25
+ :::-- background.stop(name: "docker_server")
26
+ ```
27
+
28
+ Here's a quick breakdown of that command we just ran:
29
+
30
+ - `docker run` Create and run a new container from an image.
31
+ - `-it` Makes the container interactive and allocates a TTY.
32
+ - `--rm` Automatically remove the container when it exits.
33
+ - `--env PORT=9292` Creates an environment variable named `PORT` and sets it to `9292` this is needed so the application inside the container knows what port to bind the web server.
34
+ - `-p 9292:9292` Publishes a container's port(s) to the host. This is what allows requests from your machine to be received by the container.
35
+ - `my-image-name` The name of the image you want to use for the application.
36
+
37
+ So far, we've downloaded an application via git and run a single command `pack build` to generate an image, and then we can use that image as if it was generated via a Dockerfile via the `docker run` command.
38
+
39
+ In addition to running the image as a web server, you can access the container's terminal interactively. In a new terminal window try running this command:
40
+
41
+ ```
42
+ $ docker run -it --rm my-image-name bash
43
+ ```
44
+
45
+ Now you can inspect the container interactively. For example, you can see the files on disk with `ls`:
46
+
47
+ ```
48
+ $ ls
49
+ :::-> $ docker run --rm my-image-name ls
50
+ ```
51
+
52
+ And anything else you would typically do via an interactive container session.
@@ -0,0 +1,18 @@
1
+ ## What is a builder?
2
+
3
+ > [!NOTE]
4
+ > Skip ahead if you want to build the application first and get into the details later. You won't need to
5
+ > know about builders for the rest of this tutorial.
6
+
7
+ In short, a builder is a delivery mechanism for buildpacks. A builder contains references to base images and individual buildpacks. A base image contains the operating system and system dependencies. Buildpacks are the components that will configure an image to run your application, that’s where the bulk of the logic lives and why the project is called “Cloud Native Buildpacks” and not “Cloud Native Builders.”
8
+
9
+ You can view the contents of a builder via the command `pack builder inspect`. For example:
10
+
11
+ ```
12
+ :::>> $ pack builder inspect heroku/builder:22 | grep Buildpacks: -m1 -A10
13
+ ```
14
+
15
+ > [!NOTE]
16
+ > Your output version numbers may differ.
17
+
18
+ This output shows the various buildpacks that represent the different languages that are supported by this builder such as `heroku/go` and `heroku/nodejs-engine`.
@@ -252,13 +252,11 @@ Provision a Postgresql database using Add-ons.
252
252
  >A `mini` Postgres size costs [$5 a month, prorated to the minute](https://elements.heroku.com/addons/heroku-postgresql). At the end of this tutorial, you will be prompted to [delete your database](https://devcenter.heroku.com/articles/heroku-postgresql#removing-the-add-on) to minimize costs.
253
253
 
254
254
  ```term
255
- $ heroku addons:create heroku-postgresql:mini
256
- Creating heroku-postgresql:mini on ⬢ shrouded-anchorage-34700... $5/month
257
- Database has been created and is available
258
- ! This database is empty. If upgrading, you can transfer
259
- ! data from another database with pg:copy
260
-
261
- Created postgresql-encircled-75487 as DATABASE_URL
255
+ $ heroku addons:create heroku-postgresql:essential-0
256
+ Creating heroku-postgresql:essential-0 on ⬢ shrouded-anchorage-34700... ~$0.007/hour (max $5/month)
257
+ Database should be available soon
258
+ postgresql-encircled-75487 is being created in the background. The app will restart when complete...
259
+ Use heroku addons:info postgresql-encircled-75487 to check creation progress
262
260
  Use heroku addons:docs heroku-postgresql to view documentation
263
261
  ```
264
262
 
@@ -249,7 +249,7 @@ Provision a Postgresql database using Add-ons.
249
249
  >A `mini` Postgres size costs [$5 a month, prorated to the minute](https://elements.heroku.com/addons/heroku-postgresql). At the end of this tutorial, you will be prompted to [delete your database](https://devcenter.heroku.com/articles/heroku-postgresql#removing-the-add-on) to minimize costs.
250
250
 
251
251
  ```term
252
- :::>> $ heroku addons:create heroku-postgresql:mini
252
+ :::>> $ heroku addons:create heroku-postgresql:essential-0
253
253
  ```
254
254
 
255
255
  Your Heroku app now has access to a Postgresql database. The credentials are stored in the `DATABASE_URL` environment variable, which Rails will connect to by convention.
@@ -279,7 +279,7 @@ Provision a [Heroku Postgres](https://devcenter.heroku.com/articles/heroku-postg
279
279
  >A `mini` Postgres size costs [$5 a month, prorated to the minute](https://elements.heroku.com/addons/heroku-postgresql). At the end of this tutorial, we prompt you to [delete your database](https://devcenter.heroku.com/articles/heroku-postgresql#removing-the-add-on) to minimize costs.
280
280
 
281
281
  ```term
282
- :::>> $ heroku addons:create heroku-postgresql:mini
282
+ :::>> $ heroku addons:create heroku-postgresql:essential-0
283
283
  ```
284
284
 
285
285
  Your Heroku app can now access this Postgres database. The `DATABASE_URL` environment variable stores your credentials, which Rails connects to by convention.
@@ -315,7 +315,7 @@ To use an interactive shell session instead, you can execute `heroku run bash`.
315
315
 
316
316
  ## Scale and Access the Application
317
317
 
318
- Heroku runs application code using defined processes and [process types](procfile). New applications don't a process type active by default. The following command scales your app up to one dyno, running the `web` process:
318
+ Heroku runs application code using defined processes and [process types](procfile). New applications don't have a process type active by default. The following command scales your app up to one dyno, running the `web` process:
319
319
 
320
320
  ```term
321
321
  :::>- $ heroku ps:scale web=1
@@ -3,7 +3,6 @@
3
3
  email = ENV['HEROKU_EMAIL'] || `heroku auth:whoami`
4
4
 
5
5
  Rundoc.configure do |config|
6
- config.project_root = "myapp"
7
6
  config.filter_sensitive(email => "developer@example.com")
8
7
  config.filter_sensitive(Dir.pwd => ".")
9
8
  end
@@ -251,7 +250,7 @@ Provision a [Heroku Postgres](https://devcenter.heroku.com/articles/heroku-postg
251
250
  >A `mini` Postgres size costs [$5 a month, prorated to the minute](https://elements.heroku.com/addons/heroku-postgresql). At the end of this tutorial, we prompt you to [delete your database](https://devcenter.heroku.com/articles/heroku-postgresql#removing-the-add-on) to minimize costs.
252
251
 
253
252
  ```term
254
- :::>> $ heroku addons:create heroku-postgresql:mini
253
+ :::>> $ heroku addons:create heroku-postgresql:essential-0
255
254
  ```
256
255
 
257
256
  Your Heroku app can now access this Postgres database. The `DATABASE_URL` environment variable stores your credentials, which Rails connects to by convention.
@@ -287,7 +286,7 @@ To use an interactive shell session instead, you can execute `heroku run bash`.
287
286
 
288
287
  ## Scale and Access the Application
289
288
 
290
- Heroku runs application code using defined processes and [process types](procfile). New applications don't a process type active by default. The following command scales your app up to one dyno, running the `web` process:
289
+ Heroku runs application code using defined processes and [process types](procfile). New applications don't have a process type active by default. The following command scales your app up to one dyno, running the `web` process:
291
290
 
292
291
  ```term
293
292
  :::>- $ heroku ps:scale web=1
@@ -0,0 +1,13 @@
1
+ ```
2
+ :::-- $ git config --get user.email || git config --global user.email "developer@example.com"
3
+ :::-- $ git config --get user.name || git config --global user.name "Developer name"
4
+ ```
5
+
6
+ ```
7
+ :::>> $ echo "hello world" >> lol.txt
8
+ :::>> $ git init .
9
+ :::>> $ git add .
10
+ :::>> $ git commit -m first
11
+ :::>> $ echo "so long and thanks for all the fish" >> lol.txt
12
+ :::>> $ git add . && git commit -m second
13
+ ```
@@ -0,0 +1,62 @@
1
+ require "test_helper"
2
+
3
+ class IntegrationAfterBuildTest < Minitest::Test
4
+ def test_modifies_directory_structure
5
+ Dir.mktmpdir do |dir|
6
+ Dir.chdir(dir) do
7
+ dir = Pathname(dir)
8
+
9
+ source_path = dir.join("RUNDOC.md")
10
+ source_path.write <<~EOF
11
+ ```
12
+ :::>> $ mkdir lol
13
+ :::>> $ touch lol/rofl.txt
14
+ ```
15
+ EOF
16
+
17
+ io = StringIO.new
18
+
19
+ Rundoc::CLI.new(
20
+ io: io,
21
+ source_path: source_path,
22
+ on_success_dir: dir.join(SUCCESS_DIRNAME)
23
+ ).call
24
+
25
+ assert dir.join(SUCCESS_DIRNAME).join("lol").exist?
26
+ assert dir.join(SUCCESS_DIRNAME).join("lol").join("rofl.txt").exist?
27
+
28
+ FileUtils.remove_entry_secure(dir.join(SUCCESS_DIRNAME))
29
+
30
+ source_path.write <<~EOF
31
+ ```
32
+ :::-- rundoc.configure
33
+ Rundoc.configure do |config|
34
+ config.after_build do |context|
35
+ Dir.glob(context.output_dir.join("lol").join("*")).each do |item|
36
+ FileUtils.mv(item, context.output_dir)
37
+ end
38
+
39
+ FileUtils.rm_rf(context.output_dir.join("lol"))
40
+ end
41
+ end
42
+ ```
43
+
44
+ ```
45
+ :::>> $ mkdir lol
46
+ :::>> $ touch lol/rofl.txt
47
+ ```
48
+ EOF
49
+
50
+ io = StringIO.new
51
+
52
+ Rundoc::CLI.new(
53
+ io: io,
54
+ source_path: source_path,
55
+ on_success_dir: dir.join(SUCCESS_DIRNAME)
56
+ ).call
57
+
58
+ assert dir.join(SUCCESS_DIRNAME).join("rofl.txt").exist?
59
+ end
60
+ end
61
+ end
62
+ end
@@ -1,6 +1,6 @@
1
1
  require "test_helper"
2
2
 
3
- class ParserTest < Minitest::Test
3
+ class IntegrationPrintTest < Minitest::Test
4
4
  def test_erb_shared_binding_persists_values
5
5
  key = SecureRandom.hex
6
6
  contents = <<~RUBY
@@ -20,7 +20,7 @@ class ParserTest < Minitest::Test
20
20
  one
21
21
  #{key}
22
22
  EOF
23
- parsed = Rundoc::Parser.new(contents)
23
+ parsed = parse_contents(contents)
24
24
  actual = parsed.to_md.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "")
25
25
  assert_equal expected, actual
26
26
  end
@@ -43,7 +43,7 @@ class ParserTest < Minitest::Test
43
43
  expected = <<~EOF
44
44
  one
45
45
  EOF
46
- parsed = Rundoc::Parser.new(contents)
46
+ parsed = parse_contents(contents)
47
47
  actual = parsed.to_md.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "")
48
48
  assert_equal expected, actual
49
49
  end
@@ -69,7 +69,7 @@ class ParserTest < Minitest::Test
69
69
  there
70
70
  ```
71
71
  EOF
72
- parsed = Rundoc::Parser.new(contents)
72
+ parsed = parse_contents(contents)
73
73
  actual = parsed.to_md.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "")
74
74
  assert_equal expected, actual
75
75
  end
@@ -93,7 +93,7 @@ class ParserTest < Minitest::Test
93
93
  Hello
94
94
  there
95
95
  EOF
96
- parsed = Rundoc::Parser.new(contents)
96
+ parsed = parse_contents(contents)
97
97
  actual = parsed.to_md.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "")
98
98
  assert_equal expected, actual
99
99
  end
@@ -117,7 +117,7 @@ class ParserTest < Minitest::Test
117
117
  Hello
118
118
  there
119
119
  EOF
120
- parsed = Rundoc::Parser.new(contents)
120
+ parsed = parse_contents(contents)
121
121
  actual = parsed.to_md.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "")
122
122
  assert_equal expected, actual
123
123
  end
@@ -141,7 +141,7 @@ class ParserTest < Minitest::Test
141
141
  Hello
142
142
  there
143
143
  EOF
144
- parsed = Rundoc::Parser.new(contents)
144
+ parsed = parse_contents(contents)
145
145
  actual = parsed.to_md.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "")
146
146
  assert_equal expected, actual
147
147
  end
@@ -162,7 +162,7 @@ class ParserTest < Minitest::Test
162
162
  expected = <<~EOF
163
163
  Hello there
164
164
  EOF
165
- parsed = Rundoc::Parser.new(contents)
165
+ parsed = parse_contents(contents)
166
166
  actual = parsed.to_md.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "")
167
167
  assert_equal expected, actual
168
168
  end
@@ -185,7 +185,7 @@ class ParserTest < Minitest::Test
185
185
  Hello there
186
186
  ```
187
187
  EOF
188
- parsed = Rundoc::Parser.new(contents)
188
+ parsed = parse_contents(contents)
189
189
  actual = parsed.to_md.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "")
190
190
  assert_equal expected, actual
191
191
  end
@@ -0,0 +1,63 @@
1
+ require "test_helper"
2
+
3
+ class IntegrationRequireTest < Minitest::Test
4
+ def test_require_embeds_results
5
+ Dir.mktmpdir do |dir|
6
+ Dir.chdir(dir) do
7
+ dir = Pathname(dir)
8
+ source_path = dir.join("RUNDOC.md")
9
+ source_path.write <<~EOF
10
+ ```
11
+ :::>> rundoc.require "./day_one/rundoc.md"
12
+ ```
13
+ EOF
14
+
15
+ dir.join("day_one").tap(&:mkpath).join("rundoc.md").write <<~EOF
16
+ ```
17
+ :::-> print.text Hello World!
18
+ ```
19
+ EOF
20
+
21
+ parsed = parse_contents(
22
+ source_path.read,
23
+ source_path: source_path
24
+ )
25
+ actual = parsed.to_md.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "")
26
+ assert_equal "Hello World!", actual.strip
27
+ end
28
+ end
29
+ end
30
+
31
+ def test_require_runs_code_but_embeds_nothing_if_hidden
32
+ Dir.mktmpdir do |dir|
33
+ Dir.chdir(dir) do
34
+ dir = Pathname(dir)
35
+ source_path = dir.join("RUNDOC.md")
36
+ source_path.write <<~EOF
37
+ ```
38
+ :::-- rundoc.require "./day_one/rundoc.md"
39
+ ```
40
+ EOF
41
+
42
+ dir.join("day_one").tap(&:mkpath).join("rundoc.md").write <<~EOF
43
+ ```
44
+ :::-> print.text Hello World!
45
+ :::>> $ echo "echo hello world" > foo.txt
46
+ ```
47
+ EOF
48
+
49
+ parsed = parse_contents(
50
+ source_path.read,
51
+ source_path: source_path
52
+ )
53
+ actual = parsed.to_md.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "")
54
+ # Command was run
55
+ assert dir.join("foo.txt").exist?
56
+ assert "echo hello world", dir.join("foo.txt").read.strip
57
+
58
+ # But nothing was embedded
59
+ assert_equal "", actual.strip
60
+ end
61
+ end
62
+ end
63
+ end
@@ -0,0 +1,35 @@
1
+ require "test_helper"
2
+
3
+ class IntegrationWebsiteTest < Minitest::Test
4
+ def test_screenshot_command
5
+ contents = <<~RUBY
6
+ ```
7
+ :::>> website.visit(name: "example", url: "http://example.com")
8
+ :::>> website.screenshot(name: "example")
9
+ ```
10
+ RUBY
11
+
12
+ Dir.mktmpdir do |dir|
13
+ Dir.chdir(dir) do
14
+ env = {}
15
+ env[:before] = []
16
+
17
+ screenshots_dirname = "screenshots"
18
+ screenshots_dir = Pathname(dir).join(screenshots_dirname)
19
+ screenshot_1_path = screenshots_dir.join("screenshot_1.png")
20
+
21
+ parsed = parse_contents(
22
+ contents,
23
+ output_dir: screenshots_dir.parent,
24
+ screenshots_dirname: screenshots_dirname
25
+ )
26
+ actual = parsed.to_md.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "")
27
+
28
+ expected = "![Screenshot of http://example.com/](screenshots/screenshot_1.png)"
29
+ assert_equal expected, actual.strip
30
+
31
+ assert screenshot_1_path.exist?
32
+ end
33
+ end
34
+ end
35
+ end
@@ -0,0 +1,118 @@
1
+ require "test_helper"
2
+
3
+ class CliArgumentParserTest < Minitest::Test
4
+ def test_help
5
+ io = StringIO.new
6
+ exit_obj = FakeExit.new
7
+ parser = Rundoc::CLIArgumentParser.new(
8
+ io: io,
9
+ argv: ["--help"],
10
+ env: {},
11
+ exit_obj: exit_obj
12
+ )
13
+ parser.call
14
+ output = io.string
15
+
16
+ assert output.include?("Prints this help output")
17
+ end
18
+
19
+ def test_help_no_flag
20
+ io = StringIO.new
21
+ exit_obj = FakeExit.new
22
+ parser = Rundoc::CLIArgumentParser.new(
23
+ io: io,
24
+ argv: ["help"],
25
+ env: {},
26
+ exit_obj: exit_obj
27
+ )
28
+ parser.call
29
+ output = io.string
30
+
31
+ assert output.include?("Prints this help output")
32
+ end
33
+
34
+ def test_no_such_file
35
+ io = StringIO.new
36
+ exit_obj = FakeExit.new
37
+ parser = Rundoc::CLIArgumentParser.new(
38
+ io: io,
39
+ argv: ["fileDoesNotExist.txt"],
40
+ env: {},
41
+ exit_obj: exit_obj
42
+ )
43
+ parser.call
44
+ output = io.string
45
+
46
+ assert exit_obj.value == 1
47
+ assert_includes output, "No such file"
48
+ end
49
+
50
+ def test_dir_not_file
51
+ Dir.mktmpdir do |dir|
52
+ io = StringIO.new
53
+ exit_obj = FakeExit.new
54
+ parser = Rundoc::CLIArgumentParser.new(
55
+ io: io,
56
+ argv: [dir],
57
+ env: {},
58
+ exit_obj: exit_obj
59
+ )
60
+ parser.call
61
+ output = io.string
62
+
63
+ assert exit_obj.value == 1
64
+ assert_includes output, "Path is not a file"
65
+ end
66
+ end
67
+
68
+ def test_valid_inputs
69
+ Dir.mktmpdir do |dir|
70
+ Dir.chdir(dir) do
71
+ tmp = Pathname(dir)
72
+ rundoc = tmp.join("rundoc.md")
73
+ rundoc.write("")
74
+
75
+ io = StringIO.new
76
+ exit_obj = FakeExit.new
77
+ parser = Rundoc::CLIArgumentParser.new(
78
+ io: io,
79
+ argv: [
80
+ rundoc,
81
+ "--on-success-dir=./success",
82
+ "--on-failure-dir=./failure",
83
+ "--dotenv-path=./lol/.env",
84
+ "--screenshots-dirname=pics",
85
+ "--output-filename=OUTPUT.md",
86
+ "--force"
87
+ ],
88
+ env: {},
89
+ exit_obj: exit_obj
90
+ )
91
+ parser.call
92
+ output = io.string
93
+
94
+ assert !exit_obj.called?
95
+ assert output.empty?
96
+
97
+ assert_equal "./success", parser.options[:on_success_dir]
98
+ assert_equal "./failure", parser.options[:on_failure_dir]
99
+ assert_equal "./lol/.env", parser.options[:dotenv_path]
100
+ assert_equal "pics", parser.options[:screenshots_dirname]
101
+ assert_equal "OUTPUT.md", parser.options[:output_filename]
102
+ assert_equal true, parser.options[:force]
103
+
104
+ expected = [
105
+ :on_success_dir,
106
+ :on_failure_dir,
107
+ :dotenv_path,
108
+ :screenshots_dirname,
109
+ :output_filename,
110
+ :force,
111
+ :io,
112
+ :source_path
113
+ ]
114
+ assert_equal expected.sort, parser.options.keys.sort
115
+ end
116
+ end
117
+ end
118
+ end
@@ -15,7 +15,11 @@ class CodeSectionTest < Minitest::Test
15
15
  Dir.mktmpdir do |dir|
16
16
  Dir.chdir(dir) do
17
17
  match = contents.match(Rundoc::Parser::CODEBLOCK_REGEX)
18
- result = Rundoc::CodeSection.new(match, keyword: ":::").render
18
+ result = Rundoc::CodeSection.new(
19
+ match,
20
+ keyword: ":::",
21
+ context: default_context
22
+ ).render
19
23
  assert_equal "", result
20
24
  end
21
25
  end
@@ -30,7 +34,11 @@ class CodeSectionTest < Minitest::Test
30
34
  RUBY
31
35
 
32
36
  match = contents.match(Rundoc::Parser::CODEBLOCK_REGEX)
33
- result = Rundoc::CodeSection.new(match, keyword: ":::").render
37
+ result = Rundoc::CodeSection.new(
38
+ match,
39
+ keyword: ":::",
40
+ context: default_context
41
+ ).render
34
42
  assert_equal contents, result.gsub(Rundoc::CodeSection::AUTOGEN_WARNING, "\n")
35
43
  end
36
44
 
@@ -42,7 +50,11 @@ class CodeSectionTest < Minitest::Test
42
50
  RUBY
43
51
 
44
52
  match = contents.match(Rundoc::Parser::CODEBLOCK_REGEX)
45
- code_section = Rundoc::CodeSection.new(match, keyword: ":::")
53
+ code_section = Rundoc::CodeSection.new(
54
+ match,
55
+ keyword: ":::",
56
+ context: default_context
57
+ )
46
58
  code_section.render
47
59
 
48
60
  code_command = code_section.commands.first
@@ -56,7 +68,11 @@ class CodeSectionTest < Minitest::Test
56
68
  RUBY
57
69
 
58
70
  match = contents.match(Rundoc::Parser::CODEBLOCK_REGEX)
59
- code_section = Rundoc::CodeSection.new(match, keyword: ":::")
71
+ code_section = Rundoc::CodeSection.new(
72
+ match,
73
+ keyword: ":::",
74
+ context: default_context
75
+ )
60
76
  code_section.render
61
77
 
62
78
  code_command = code_section.commands.first
@@ -72,7 +88,11 @@ class CodeSectionTest < Minitest::Test
72
88
  RUBY
73
89
 
74
90
  match = contents.match(Rundoc::Parser::CODEBLOCK_REGEX)
75
- code_section = Rundoc::CodeSection.new(match, keyword: ":::")
91
+ code_section = Rundoc::CodeSection.new(
92
+ match,
93
+ keyword: ":::",
94
+ context: default_context
95
+ )
76
96
  code_section.render
77
97
 
78
98
  puts code_section.commands.inspect
@@ -89,7 +109,11 @@ class CodeSectionTest < Minitest::Test
89
109
  RUBY
90
110
 
91
111
  match = contents.match(Rundoc::Parser::CODEBLOCK_REGEX)
92
- code_section = Rundoc::CodeSection.new(match, keyword: ":::")
112
+ code_section = Rundoc::CodeSection.new(
113
+ match,
114
+ keyword: ":::",
115
+ context: default_context
116
+ )
93
117
  code_section.render
94
118
 
95
119
  code_command = code_section.commands.first
@@ -103,7 +127,11 @@ class CodeSectionTest < Minitest::Test
103
127
  RUBY
104
128
 
105
129
  match = contents.match(Rundoc::Parser::CODEBLOCK_REGEX)
106
- code_section = Rundoc::CodeSection.new(match, keyword: ":::")
130
+ code_section = Rundoc::CodeSection.new(
131
+ match,
132
+ keyword: ":::",
133
+ context: default_context
134
+ )
107
135
  code_section.render
108
136
 
109
137
  code_command = code_section.commands.first
@@ -119,7 +147,11 @@ class CodeSectionTest < Minitest::Test
119
147
  RUBY
120
148
 
121
149
  match = contents.match(Rundoc::Parser::CODEBLOCK_REGEX)
122
- code_section = Rundoc::CodeSection.new(match, keyword: ":::")
150
+ code_section = Rundoc::CodeSection.new(
151
+ match,
152
+ keyword: ":::",
153
+ context: default_context
154
+ )
123
155
  code_section.render
124
156
 
125
157
  code_command = code_section.commands.first