terradoc 0.1.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 ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: becee654fffe5ec2bb4e0b798cf831f259b0cdbf117835b58c88964d213a5a13
4
+ data.tar.gz: caa198ed9694b6af9b11a312cd64e9b840495d67f02912c87c0d9f8d1a529e94
5
+ SHA512:
6
+ metadata.gz: 0e6dd4bd07e79b6524c92f003a409b0d14d18b4001495780a514cc3e1e9b95046f488bb1657215db2ed6a4a613a35a421f5868d98c59c74e39929ef4076543d2
7
+ data.tar.gz: 6fe4358a94c96b115c918c52989fcfb235c497841d635c93140888d8447982316c01d51869830f7a57ceeefbe36f6b88596fc2fba0e950a5847a98e74d286e8c
data/.gitattributes ADDED
@@ -0,0 +1,2 @@
1
+ # Just override github
2
+ * linguist-language=Ruby
data/.gitignore ADDED
@@ -0,0 +1,22 @@
1
+ .idea
2
+ ab-results*
3
+ .lock
4
+ .caretaker.yml
5
+
6
+ /.bundle/
7
+ /.yardoc
8
+ /_yardoc/
9
+ /coverage/
10
+ /doc/
11
+ /pkg/
12
+ /spec/reports/
13
+ /tmp/
14
+
15
+ /Gemfile.lock
16
+
17
+ *.gem
18
+
19
+ # rspec failure tracking
20
+ .rspec_status
21
+
22
+
data/.rspec ADDED
@@ -0,0 +1,3 @@
1
+ --format documentation
2
+ --color
3
+ --require spec_helper
data/.rubocop.yml ADDED
@@ -0,0 +1,71 @@
1
+ AllCops:
2
+ TargetRubyVersion: 2.5
3
+
4
+ #
5
+ # New
6
+ #
7
+ Style/HashEachMethods:
8
+ Enabled: false
9
+
10
+ Style/HashTransformKeys:
11
+ Enabled: false
12
+
13
+ Style/HashTransformValues:
14
+ Enabled: false
15
+
16
+ Layout/FirstHashElementIndentation:
17
+ Enabled: false
18
+
19
+ Layout/HashAlignment:
20
+ Enabled: false
21
+
22
+ Layout/IndentationWidth:
23
+ Width: 4
24
+
25
+ Layout/LineLength:
26
+ Enabled: false
27
+
28
+ Layout/SpaceAroundOperators:
29
+ Enabled: false
30
+
31
+ Metrics/BlockNesting:
32
+ Enabled: false
33
+
34
+ Metrics/AbcSize:
35
+ Enabled: false
36
+
37
+ Metrics/BlockLength:
38
+ Enabled: false
39
+
40
+ Metrics/ClassLength:
41
+ Enabled: false
42
+
43
+ Metrics/CyclomaticComplexity:
44
+ Enabled: false
45
+
46
+ Metrics/MethodLength:
47
+ Enabled: false
48
+
49
+ Metrics/PerceivedComplexity:
50
+ Enabled: false
51
+
52
+ Style/FrozenStringLiteralComment:
53
+ Enabled: false
54
+
55
+ Style/HashSyntax:
56
+ Enabled: false
57
+
58
+ Style/RaiseArgs:
59
+ EnforcedStyle: compact
60
+
61
+ Style/RedundantParentheses:
62
+ Enabled: false
63
+
64
+ Style/RedundantBegin:
65
+ Enabled: false
66
+
67
+ Style/RedundantReturn:
68
+ Enabled: false
69
+
70
+ Style/SpecialGlobalVars:
71
+ Enabled: false
data/.travis.yml ADDED
@@ -0,0 +1,64 @@
1
+ matrix:
2
+ include:
3
+ - language: ruby
4
+ name: Bundler (rvm 2.5 & bundler)
5
+ rvm: 2.5
6
+ before_install:
7
+ - gem install bundler
8
+ - language: ruby
9
+ name: Bundler (rvm 2.6 & bundler)
10
+ rvm: 2.6
11
+ before_install:
12
+ - gem install bundler
13
+ - language: ruby
14
+ name: Bundler (rvm 2.7 & bundler)
15
+ rvm: 2.7
16
+ before_install:
17
+ - gem install bundler
18
+ - language: ruby
19
+ name: Rubocop (rvm 2.5)
20
+ env: SKIP_INTERPRETER=true
21
+ rvm: 2.5
22
+ before_install:
23
+ - git clone https://github.com/TravisToolbox/rubocop-travis.git
24
+ install:
25
+ - "./rubocop-travis/install.sh"
26
+ script:
27
+ - "./rubocop-travis/scan.sh"
28
+ - language: ruby
29
+ name: Rubocop (rvm 2.6)
30
+ env: SKIP_INTERPRETER=true
31
+ rvm: 2.6
32
+ before_install:
33
+ - git clone https://github.com/TravisToolbox/rubocop-travis.git
34
+ install:
35
+ - "./rubocop-travis/install.sh"
36
+ script:
37
+ - "./rubocop-travis/scan.sh"
38
+ - language: ruby
39
+ name: Rubocop (rvm 2.7)
40
+ env: SKIP_INTERPRETER=true
41
+ rvm: 2.7
42
+ before_install:
43
+ - git clone https://github.com/TravisToolbox/rubocop-travis.git
44
+ install:
45
+ - "./rubocop-travis/install.sh"
46
+ script:
47
+ - "./rubocop-travis/scan.sh"
48
+ - language: ruby
49
+ name: Link Checking (rvm 2.7)
50
+ rvm: 2.7
51
+ env:
52
+ - WHITELIST="https://img.shields.io"
53
+ - EXCLUDE_FILES="CHANGELOG.md"
54
+ before_install:
55
+ - mkdir travis
56
+ - git clone https://github.com/TravisToolbox/awesomebot-travis.git travis/awesomebot
57
+ install:
58
+ - "./travis/awesomebot/install.sh"
59
+ script:
60
+ - "./travis/awesomebot/scan.sh"
61
+ notifications:
62
+ email: false
63
+ slack:
64
+ secure: X44KdQElVK2NVkGtb9qda7XQzZPepO+odLBeNxqPCEAQ/0GpgTFi+nJ6iFMQ01usrCfz78EgerwKF51RAhjrdNAr6ySIxmErsLzbmtKKbpF46meLZ5qdWAisuVCMpc+t+ypFnQ/sEjboC5HbhBZH4waFnH/sWU6GorSVotkNaz/dEoHUD8No2iJTbbohPBO8ftX6NtCV7L9kd2pB2P9WWqUxMlT3DJJY4VruDKBC/zJnLa6+R9Af2BxZ9JIfSHoRGKIDcSto53FD8R+h7jOQGMRHTkwbNgA5E9B5u+5zmRVKXfUSAY84Z71sE3Srt+B3nGDh3e0iez2L9JvmWfJBvrNBbfnOTmHHSCtMpfzq4a37RNHUS/8M3KwZFcg3zYKubifg1qG3C3JHscikwNnSiSoImJUvS04V6Wzr3lyfOkUunF6HiffEFJ7wOVIo00dqqdADw0u2POVae0FGf34MOLCBA/mLpU51cJA9G+RxomPPhP7byNCPM3aBNqQD+YlyChT9Co+e6+G2YXwTxMEGrBP8628yDk+aM/MRuGFVv55N5gMXspZgTzwP3OcDT4CtxDHhKAZl/Wf9EJcqhzrEUWfss5vHLqDRYwbJCqPGJ5iyxHNHAzc3F0HLWjEhO8DVknn/wyEzEQWolzgxURICmPb8Ej1VSg+jlfzY+0e/ams=
data/CHANGELOG.md ADDED
@@ -0,0 +1,17 @@
1
+ # Changelog
2
+
3
+ All notable changes to this project will be documented in this file.
4
+
5
+
6
+ This changelog was automatically generated using [Caretaker](https://github.com/TerraformToolbox/terradoc) by [Wolf Software](https://github.com/WolfSoftware)
7
+
8
+ ### [v0.1.0](https://github.com/TerraformToolbox/terradoc/releases/v0.1.0)
9
+
10
+ > Released on March, 17th 2020
11
+
12
+ - Add version file for caretaker to manage tags/releases [`[c7d9d84]`](https://github.com/TerraformToolbox/terradoc/commit/c7d9d8427db0896113dc685f54f0d23f42e01745) [`[TGWolf]`](https://github.com/TGWolf)
13
+
14
+ - Update README [`[7bc378b]`](https://github.com/TerraformToolbox/terradoc/commit/7bc378b152cc64eb826d60cab610146c17134433) [`[TGWolf]`](https://github.com/TGWolf)
15
+
16
+ - Initial Push [`[cf4ca4a]`](https://github.com/TerraformToolbox/terradoc/commit/cf4ca4ad9093fe84c4f8133a78f31191ce52b2e0) [`[TGWolf]`](https://github.com/TGWolf)
17
+
data/CODEOWNERS ADDED
@@ -0,0 +1,7 @@
1
+ # The codeowners file:
2
+ #
3
+ # For more information please read: https://help.github.com/articles/about-codeowners/
4
+
5
+ # These owners will be the default owners for everything in
6
+ # the repo. Unless a later match takes precedence,
7
+ * @TerraformToolbox/reviewers
data/CONTRIBUTING.md ADDED
@@ -0,0 +1,3 @@
1
+ # Contributing
2
+
3
+ Please refer to the [contributing](https://github.com/TerraformToolbox/contributing) documentation.
data/EXAMPLE.md ADDED
@@ -0,0 +1,24 @@
1
+ # Some example README
2
+
3
+ ## Terraform Data Sources
4
+ <!--Terradoc-data-sources-start-->
5
+ <!--Terradoc-data-sources-end-->
6
+
7
+ ## Terraform Modules
8
+ <!--Terradoc-modules-start-->
9
+ <!--Terradoc-modules-end-->
10
+
11
+ ## The Outputs
12
+ <!--Terradoc-outputs-start-->
13
+ <!--Terradoc-outputs-end-->
14
+
15
+ ## The resources we create
16
+ <!--Terradoc-resources-start-->
17
+ <!--Terradoc-resources-end-->
18
+
19
+ ## The inputs / variables
20
+ <!--Terradoc-variables-start-->
21
+ <!--Terradoc-variables-end-->
22
+
23
+
24
+ # END
data/Gemfile ADDED
@@ -0,0 +1,7 @@
1
+ source 'https://rubygems.org'
2
+ ruby '>= 2.5.0'
3
+
4
+ git_source(:github) { |repo_name| "https://github.com/#{repo_name}" }
5
+
6
+ # Specify your gem's dependencies in slackit.gemspec
7
+ gemspec
data/LICENSE.md ADDED
@@ -0,0 +1,24 @@
1
+ # The MIT License (MIT)
2
+
3
+ Copyright © `2016 - 2020` `AntiPhoton Limited`
4
+
5
+ Permission is hereby granted, free of charge, to any person
6
+ obtaining a copy of this software and associated documentation
7
+ files (the “Software”), to deal in the Software without
8
+ restriction, including without limitation the rights to use,
9
+ copy, modify, merge, publish, distribute, sublicense, and/or sell
10
+ copies of the Software, and to permit persons to whom the
11
+ Software is furnished to do so, subject to the following
12
+ conditions:
13
+
14
+ The above copyright notice and this permission notice shall be
15
+ included in all copies or substantial portions of the Software.
16
+
17
+ THE SOFTWARE IS PROVIDED “AS IS”, WITHOUT WARRANTY OF ANY KIND,
18
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
19
+ OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
20
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
21
+ HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
22
+ WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
23
+ FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
24
+ OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,77 @@
1
+ [![Build Status](https://img.shields.io/travis/TerraformToolbox/terradoc/master?style=for-the-badge&logo=travis)](https://travis-ci.org/TerraformToolbox/terradoc)
2
+ [![Software License](https://img.shields.io/badge/license-MIT-blue?style=for-the-badge)](LICENSE.md)
3
+ [![Release](https://img.shields.io/github/release/TerraformToolbox/terradoc?color=blue&style=for-the-badge&logo=github&label=Latest%20Release)](https://github.com/TerraformToolbox/terradoc/releases/latest)
4
+ [![Last Release](https://img.shields.io/github/release-date/TerraformToolbox/terradoc?color=blue&style=for-the-badge&logo=github)](https://github.com/TerraformToolbox/terradoc/releases/latest)
5
+ [![Github commits (since latest release)](https://img.shields.io/github/commits-since/TerraformToolbox/terradoc/latest?color=blue&style=for-the-badge&logo=github)](https://github.com/TerraformToolbox/terradoc/commits)
6
+ [![Last Commit](https://img.shields.io/github/last-commit/TerraformToolbox/terradoc?color=blue&style=for-the-badge&logo=github)](https://github.com/TerraformToolbox/terradoc/commits/master)
7
+ [![TerraformToolbox](https://img.shields.io/badge/Released%20By-Wolf%20Software%20Ltd.-blue?style=for-the-badge)](https://github.com/TerraformToolbox)
8
+
9
+ # Terradoc
10
+
11
+ Terradoc is a tool creating documentation from terraform code. It will parse all of the terraform code in a given directory and generate 5 data tables.
12
+
13
+ 1. Data Sources
14
+ 2. Modules
15
+ 3. Outputs
16
+ 4. Resources
17
+ 5. Variables
18
+
19
+ You can then use the custom tags to insert these data tables into your README or other markdown files.
20
+
21
+ ## Installation
22
+
23
+ Add this line to your application's Gemfile:
24
+
25
+ ```ruby
26
+ gem 'terradoc'
27
+ ```
28
+
29
+ And then execute:
30
+
31
+ ```shell
32
+ $ bundle install
33
+ ```
34
+
35
+ Or install it yourself as:
36
+
37
+ ```shell
38
+ $ gem install terradoc
39
+ ```
40
+
41
+ ## Usage
42
+
43
+ ```
44
+ Usage: terradoc
45
+ -h, --help Display this screen
46
+ -v, --verbose Turn on verbose mode
47
+ -o, --output string Name of the output file. [default: README.md]
48
+ -p, --path string Path to the terraform code. [default: current directory]
49
+
50
+ ```
51
+
52
+ Once you have installed Terradoc you can simply run ```terradoc``` and it will generate the output.
53
+
54
+ ## Contributing to Terradoc
55
+
56
+ ### Setup
57
+
58
+ After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake spec` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
59
+
60
+ To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will
61
+ create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
62
+
63
+
64
+ ### Testing
65
+
66
+ For local testing make sure that you run `bundle exec rspec spec` and then `rake install` to install the gem locally.
67
+
68
+ For further information please refer to the [contributing](https://github.com/TerraformToolbox/contributing) documentation.
69
+
70
+ ## To-Do List
71
+
72
+ - [ ] Allow for setting of root url for linking to terraform registry
73
+ - [ ] Allow different format outputs
74
+ - [ ] Allow got global config files
75
+ - [ ] Pre/Post git commit hook
76
+
77
+
data/Rakefile ADDED
@@ -0,0 +1,6 @@
1
+ require 'bundler/gem_tasks'
2
+ require 'rspec/core/rake_task'
3
+
4
+ RSpec::Core::RakeTask.new(:spec)
5
+
6
+ task :default => :spec
data/VERSION.txt ADDED
@@ -0,0 +1 @@
1
+ 0.1.0
data/bin/console ADDED
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'bundler/setup'
4
+ require 'terradoc'
5
+
6
+ # You can add fixtures and/or initialization code here to make experimenting
7
+ # with your gem easier. You can also use a different console, if you like.
8
+
9
+ # (If you use this, don't forget to add pry to your Gemfile!)
10
+ # require 'pry'
11
+ # Pry.start
12
+
13
+ require 'irb'
14
+ IRB.start(__FILE__)
data/bin/setup ADDED
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+ set -vx
5
+
6
+ bundle install
7
+
8
+ # Do any other automated setup that you need to do here
data/exe/terradoc ADDED
@@ -0,0 +1,88 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ $LOAD_PATH.unshift('./lib')
4
+
5
+ require 'optparse'
6
+ require 'terradoc'
7
+
8
+ # -------------------------------------------------------------------------------- #
9
+ # Run Terradoc #
10
+ # -------------------------------------------------------------------------------- #
11
+ # Pass the command line options to the class and run terradoc #
12
+ # -------------------------------------------------------------------------------- #
13
+
14
+ def run_terradoc(options)
15
+ begin
16
+ Terradoc.new(options)
17
+ rescue StandardError => e
18
+ puts "Error: #{e}"
19
+ puts e.backtrace if options[:verbose]
20
+ exit(1)
21
+ end
22
+ end
23
+
24
+ # -------------------------------------------------------------------------------- #
25
+ # Process Arguments #
26
+ # -------------------------------------------------------------------------------- #
27
+ # This function will process the input from the command line and work out what it #
28
+ # is that the user wants to see. #
29
+ # #
30
+ # This is the main processing function where all the processing logic is handled. #
31
+ # -------------------------------------------------------------------------------- #
32
+
33
+ def process_arguments
34
+ options = { :verbose => false }
35
+ # Enforce the presence of
36
+ mandatory = %I[]
37
+
38
+ optparse = OptionParser.new do |opts|
39
+ opts.banner = "Usage: #{$PROGRAM_NAME}"
40
+
41
+ opts.on('-h', '--help', 'Display this screen') do
42
+ puts opts
43
+ exit(1)
44
+ end
45
+ opts.on('-v', '--verbose', 'Turn on verbose mode') do
46
+ options[:verbose] = true
47
+ end
48
+
49
+ opts.on('-o', '--output string', 'Set the name of the output file. [default: README.md]') do |output|
50
+ options[:output] = output
51
+ end
52
+ opts.on('-p', '--path string', 'Set the path for where the terraform code is. [default: current directory]') do |path|
53
+ options[:path] = path
54
+ end
55
+ end
56
+
57
+ begin
58
+ optparse.parse!
59
+ missing = mandatory.select { |param| options[param].nil? }
60
+ raise OptionParser::MissingArgument.new(missing.join(', ')) unless missing.empty?
61
+ rescue OptionParser::InvalidOption, OptionParser::MissingArgument => e
62
+ puts e.to_s
63
+ puts optparse
64
+ exit
65
+ end
66
+
67
+ exit 0 if run_terradoc(options)
68
+
69
+ exit 1
70
+ end
71
+
72
+ # -------------------------------------------------------------------------------- #
73
+ # Main() #
74
+ # -------------------------------------------------------------------------------- #
75
+ # The main function where all of the heavy lifting and script config is done. #
76
+ # -------------------------------------------------------------------------------- #
77
+
78
+ def main
79
+ process_arguments
80
+ end
81
+
82
+ main
83
+
84
+ # -------------------------------------------------------------------------------- #
85
+ # End of Script #
86
+ # -------------------------------------------------------------------------------- #
87
+ # This is the end - nothing more to see here. #
88
+ # -------------------------------------------------------------------------------- #
@@ -0,0 +1,3 @@
1
+ class Terradoc
2
+ VERSION = '0.1.0'.freeze
3
+ end
data/lib/terradoc.rb ADDED
@@ -0,0 +1,333 @@
1
+ require 'terradoc/version'
2
+
3
+ require 'tty-spinner'
4
+
5
+ # -------------------------------------------------------------------------------- #
6
+ # -------------------------------------------------------------------------------- #
7
+ # -------------------------------------------------------------------------------- #
8
+ class Terradoc
9
+ # -------------------------------------------------------------------------------- #
10
+ # -------------------------------------------------------------------------------- #
11
+ def initialize(options = {})
12
+ @base_path = '.'
13
+ @base_path = options[:path] unless options[:path].nil?
14
+ @base_path.chomp!('/')
15
+ raise StandardError.new("Path #{@base_path} does not exist - Aborting") unless Dir.exist? @base_path
16
+
17
+ @output_file = 'CHANGELOG.md'
18
+ @output_file = options[:output] unless options[:output].nil?
19
+
20
+ @files = []
21
+ @pattern = "#{@base_path}/*.tf"
22
+
23
+ @config = {
24
+ 'data-sources' => {
25
+ 'include' => 'data',
26
+ 'match' => /^(?!data).*/,
27
+ 'regex' => /^data\s*"(?<name>.*)"\s*".*/,
28
+ 'split' => /(?=data\s*")/,
29
+ 'start' => '<!--Terradoc-data-sources-start-->',
30
+ 'end' => '<!--Terradoc-data-sources-end-->',
31
+ 'raw_results' => [],
32
+ 'sorted_results' => [],
33
+ 'data_table' => []
34
+ },
35
+ 'modules' => {
36
+ 'include' => 'module',
37
+ 'match' => /^(?!module).*/,
38
+ 'regex' => /^module\s*".*"\s*{\s*source\s*=\s*"(?<name>.*?)"/,
39
+ 'split' => /(?=module\s*")/,
40
+ 'start' => '<!--Terradoc-modules-start-->',
41
+ 'end' => '<!--Terradoc-modules-end-->',
42
+ 'raw_results' => [],
43
+ 'sorted_results' => [],
44
+ 'data_table' => []
45
+ },
46
+ 'outputs' => {
47
+ 'include' => 'output',
48
+ 'match' => /^(?!output).*/,
49
+ 'regex' => /^output\s*"(?<name>.*)"\s*{\s*(?<details>.*)\s*}/,
50
+ 'regex_stage_2' => /description\s*=\s*"(?<description>.*?)".*/,
51
+ 'split' => /(?=output\s*")/,
52
+ 'start' => '<!--Terradoc-outputs-start-->',
53
+ 'end' => '<!--Terradoc-outputs-end-->',
54
+ 'raw_results' => [],
55
+ 'sorted_results' => [],
56
+ 'data_table' => []
57
+ },
58
+ 'resources' => {
59
+ 'include' => 'resource',
60
+ 'match' => /^(?!resource).*/,
61
+ 'regex' => /^resource\s*"(?<name>.*)"\s*".*/,
62
+ 'split' => /(?=resource\s*")/,
63
+ 'start' => '<!--Terradoc-resources-start-->',
64
+ 'end' => '<!--Terradoc-resources-end-->',
65
+ 'raw_results' => [],
66
+ 'sorted_results' => [],
67
+ 'data_table' => []
68
+ },
69
+ 'variables' => {
70
+ 'include' => 'variable',
71
+ 'match' => /^(?!variable).*/,
72
+ 'regex' => /^variable\s*"(?<name>.*)"\s*{\s*(?<details>.*)\s*}/,
73
+ 'regex_stage_2' => /(description|type|default)\s*=\s*(.*?(?=description|type|default\s*=\s*|$))/,
74
+ 'split' => /(?=variable\s*")/,
75
+ 'start' => '<!--Terradoc-variables-start-->',
76
+ 'end' => '<!--Terradoc-variables-end-->',
77
+ 'raw_results' => [],
78
+ 'sorted_results' => [],
79
+ 'data_table' => []
80
+ }
81
+ }
82
+
83
+ terradoc_main
84
+ end
85
+
86
+ # -------------------------------------------------------------------------------- #
87
+ # -------------------------------------------------------------------------------- #
88
+ def terradoc_main
89
+ spinners = TTY::Spinner::Multi.new("[:spinner] Terradoc is processing your files (Path: #{@base_path}, Output File: #{@output_file})")
90
+
91
+ sp1 = spinners.register '[:spinner] Locating files'
92
+ sp2 = spinners.register '[:spinner] Processing files'
93
+ sp3 = spinners.register '[:spinner] Sorting the results'
94
+ sp4 = spinners.register '[:spinner] Generating data tables'
95
+ sp5 = spinners.register '[:spinner] Writing output'
96
+
97
+ sp1.auto_spin
98
+ sp2.auto_spin
99
+ sp3.auto_spin
100
+ sp4.auto_spin
101
+ sp5.auto_spin
102
+
103
+ generate_file_list
104
+ sp1.success
105
+
106
+ process_files
107
+ sp2.success
108
+
109
+ sort_details
110
+ sp3.success
111
+
112
+ generate_data_tables
113
+ sp4.success
114
+
115
+ write_output
116
+ sp5.success
117
+ end
118
+
119
+ # -------------------------------------------------------------------------------- #
120
+ # -------------------------------------------------------------------------------- #
121
+ def generate_file_list
122
+ Dir.glob(@pattern).each do |file|
123
+ @files << file
124
+ end
125
+ end
126
+
127
+ # -------------------------------------------------------------------------------- #
128
+ # -------------------------------------------------------------------------------- #
129
+ def process_files
130
+ @files.each do |file|
131
+ lines = File.readlines(file)
132
+ lines = lines.reject { |x| x.start_with? '#' }
133
+ data = lines.join(' ').gsub("\r\n", ' ').gsub("\n", ' ').gsub("\r", ' ').squeeze(' ').strip
134
+
135
+ process_file(data)
136
+ end
137
+ end
138
+
139
+ # -------------------------------------------------------------------------------- #
140
+ # -------------------------------------------------------------------------------- #
141
+ def cleanup_array(array)
142
+ array = array.uniq { |k| k[:name] } if array.count.positive?
143
+ array = array.sort_by { |k| k[:name] } if array.count.positive?
144
+
145
+ return array
146
+ end
147
+
148
+ # -------------------------------------------------------------------------------- #
149
+ # -------------------------------------------------------------------------------- #
150
+ def sort_details
151
+ @config['data-sources']['sorted_results'] = cleanup_array(@config['data-sources']['raw_results'])
152
+ @config['modules']['sorted_results'] = cleanup_array(@config['modules']['raw_results'])
153
+ @config['outputs']['sorted_results'] = cleanup_array(@config['outputs']['raw_results'])
154
+ @config['resources']['sorted_results'] = cleanup_array(@config['resources']['raw_results'])
155
+ @config['variables']['sorted_results'] = cleanup_array(@config['variables']['raw_results'])
156
+ end
157
+
158
+ # -------------------------------------------------------------------------------- #
159
+ # -------------------------------------------------------------------------------- #
160
+ def generate_data_tables
161
+ if @config['data-sources']['sorted_results'].size.positive?
162
+ @config['data-sources']['data_table'] << '| Name |'
163
+ @config['data-sources']['data_table'] << '| ---- |'
164
+ @config['data-sources']['sorted_results'].each do |item|
165
+ @config['data-sources']['data_table'] << "| #{item[:name]} |"
166
+ end
167
+ else
168
+ @config['data-sources']['data_table'] << '> No data found'
169
+ end
170
+
171
+ if @config['modules']['sorted_results'].size.positive?
172
+ @config['modules']['data_table'] << '| Name |'
173
+ @config['modules']['data_table'] << '| ---- |'
174
+ @config['modules']['sorted_results'] .each do |item|
175
+ @config['modules']['data_table'] << "| #{item[:name]} |"
176
+ end
177
+ else
178
+ @config['modules']['data_table'] << '> No data found'
179
+ end
180
+
181
+ if @config['outputs']['sorted_results'].size.positive?
182
+ @config['outputs']['data_table'] << '| Name | Description |'
183
+ @config['outputs']['data_table'] << '| ---- | ----------- |'
184
+ @config['outputs']['sorted_results'].each do |item|
185
+ @config['outputs']['data_table'] << "| #{item[:name]} | #{item[:description]} |"
186
+ end
187
+ else
188
+ @config['outputs']['data_table'] << '> No data found'
189
+ end
190
+
191
+ if @config['resources']['sorted_results'].size.positive?
192
+ @config['resources']['data_table'] << '| Name |'
193
+ @config['resources']['data_table'] << '| ---- |'
194
+ @config['resources']['sorted_results'].each do |item|
195
+ @config['resources']['data_table'] << "| #{item[:name]} |"
196
+ end
197
+ else
198
+ @config['resources']['data_table'] << '> No data found'
199
+ end
200
+
201
+ if @config['variables']['sorted_results'].size.positive?
202
+ @config['variables']['data_table'] << '| Name | Description | Type | Default | Required? |'
203
+ @config['variables']['data_table'] << '| ---- | ----------- | ---- |:-------:|:---------:|'
204
+ @config['variables']['sorted_results'].each do |item|
205
+ @config['variables']['data_table'] << "| #{item[:name]} | #{item[:description]} | #{item[:type]} | #{item[:default]} | #{item[:required]} |"
206
+ end
207
+ else
208
+ @config['variables']['data_table'] << '> No data found'
209
+ end
210
+ end
211
+
212
+ # -------------------------------------------------------------------------------- #
213
+ # -------------------------------------------------------------------------------- #
214
+ def clean_string(str)
215
+ return str if str.empty?
216
+
217
+ return str.strip.gsub(/\"/, '').chomp('.').strip
218
+ end
219
+
220
+ # -------------------------------------------------------------------------------- #
221
+ # -------------------------------------------------------------------------------- #
222
+ def process_file(data)
223
+ @config.each do |key, value|
224
+ next unless data.include?(value['include'])
225
+
226
+ items = data.split(value['split'])
227
+ items.each do |item|
228
+ result = {}
229
+
230
+ item.strip!
231
+ next if item.match(value['match'])
232
+
233
+ matches = item.match(value['regex'])
234
+ next unless matches.size.positive?
235
+ next unless matches.names.include?('name')
236
+
237
+ result[:name] = matches[:name].gsub('_', '\_')
238
+
239
+ if matches.names.include?('details')
240
+ if key == 'outputs'
241
+ description = '-'
242
+
243
+ parts = item.match(value['regex_stage_2'])
244
+ description = clean_string(parts[:description]) if parts.size.positive?
245
+
246
+ result[:description] = description
247
+ else
248
+ matches[:details].scan(value['regex_stage_2']).each do |key2, value2|
249
+ result[key2.to_sym] = if key2 == 'default'
250
+ value2
251
+ else
252
+ clean_string(value2)
253
+ end
254
+ end
255
+
256
+ result[:required] = if result.key?(:default)
257
+ 'No'
258
+ else
259
+ 'Yes'
260
+ end
261
+ end
262
+ end
263
+ value['raw_results'] << result
264
+ end
265
+ end
266
+ end
267
+
268
+ # -------------------------------------------------------------------------------- #
269
+ # -------------------------------------------------------------------------------- #
270
+ def load_file(filename)
271
+ lines = []
272
+
273
+ begin
274
+ lines = File.readlines(filename).each(&:chomp!)
275
+ rescue SystemCallError
276
+ raise StandardError.new("Failed to open file #{filename} for reading")
277
+ end
278
+ return lines
279
+ end
280
+
281
+ # -------------------------------------------------------------------------------- #
282
+ # -------------------------------------------------------------------------------- #
283
+ def generate_output(lines, start_tag, end_tag, data_table)
284
+ processed = []
285
+
286
+ skip_lines = false
287
+ lines.each do |line|
288
+ if line.casecmp?(end_tag) && skip_lines
289
+ processed << line
290
+ skip_lines = false
291
+ next
292
+ end
293
+
294
+ next if skip_lines
295
+
296
+ processed << line
297
+
298
+ next unless line.casecmp?(start_tag)
299
+
300
+ skip_lines = true
301
+ data_table.each do |row|
302
+ processed << row
303
+ end
304
+ end
305
+
306
+ return processed
307
+ end
308
+
309
+ # -------------------------------------------------------------------------------- #
310
+ # -------------------------------------------------------------------------------- #
311
+ def write_output
312
+ permissions = 0o0644
313
+
314
+ lines = load_file(@output_file)
315
+
316
+ lines = generate_output(lines, @config['data-sources']['start'], @config['data-sources']['end'], @config['data-sources']['data_table'])
317
+ lines = generate_output(lines, @config['modules']['start'], @config['modules']['end'], @config['modules']['data_table'])
318
+ lines = generate_output(lines, @config['outputs']['start'], @config['outputs']['end'], @config['outputs']['data_table'])
319
+ lines = generate_output(lines, @config['resources']['start'], @config['resources']['end'], @config['resources']['data_table'])
320
+ lines = generate_output(lines, @config['variables']['start'], @config['variables']['end'], @config['variables']['data_table'])
321
+
322
+ begin
323
+ File.open(@output_file, 'w') do |f|
324
+ lines.each do |line|
325
+ f.puts line
326
+ end
327
+ f.chmod(permissions)
328
+ end
329
+ rescue SystemCallError
330
+ raise StandardError.new("Failed to open file #{filename} for writing")
331
+ end
332
+ end
333
+ end
@@ -0,0 +1,14 @@
1
+ require 'bundler/setup'
2
+ require 'terradoc'
3
+
4
+ RSpec.configure do |config|
5
+ # Enable flags like --only-failures and --next-failure
6
+ config.example_status_persistence_file_path = '.rspec_status'
7
+
8
+ # Disable RSpec exposing methods globally on `Module` and `main`
9
+ config.disable_monkey_patching!
10
+
11
+ config.expect_with :rspec do |c|
12
+ c.syntax = :expect
13
+ end
14
+ end
@@ -0,0 +1,5 @@
1
+ RSpec.describe Terradoc do
2
+ it 'has a version number' do
3
+ expect(Terradoc::VERSION).not_to be nil
4
+ end
5
+ end
data/stale.yml ADDED
@@ -0,0 +1,17 @@
1
+ # Number of days of inactivity before an issue becomes stale
2
+ daysUntilStale: 60
3
+ # Number of days of inactivity before a stale issue is closed
4
+ daysUntilClose: 7
5
+ # Issues with these labels will never be considered stale
6
+ exemptLabels:
7
+ - pinned
8
+ - security
9
+ # Label to use when marking an issue as stale
10
+ staleLabel: wontfix
11
+ # Comment to post when marking an issue as stale. Set to `false` to disable
12
+ markComment: >
13
+ This issue has been automatically marked as stale because it has not had
14
+ recent activity. It will be closed if no further activity occurs. Thank you
15
+ for your contributions.
16
+ # Comment to post when closing a stale issue. Set to `false` to disable
17
+ closeComment: true
data/terradoc.gemspec ADDED
@@ -0,0 +1,30 @@
1
+ lib = File.expand_path('lib', __dir__)
2
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
3
+ require 'terradoc/version'
4
+
5
+ Gem::Specification.new do |spec|
6
+ spec.name = 'terradoc'
7
+ spec.version = Terradoc::VERSION
8
+ spec.authors = ['Tim Gurney aka Wolf']
9
+ spec.email = ['wolf@tgwolf.com']
10
+
11
+ spec.summary = 'A simple tool for creating automatic documentaion from terraform source code.'
12
+ spec.description = 'A simple tool for creating automatic documentaion from terraform source code.'
13
+ spec.homepage = 'https://github.com/TerraformToolbox/terradoc'
14
+ spec.license = 'MIT'
15
+
16
+ spec.files = `git ls-files`.split($/)
17
+
18
+ spec.bindir = 'exe'
19
+ spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
20
+ spec.require_paths = ['lib']
21
+
22
+ spec.required_ruby_version = '>= 2.5'
23
+
24
+ spec.add_development_dependency 'bundler', '~> 2'
25
+ spec.add_development_dependency 'rake', '~> 13.0'
26
+ spec.add_development_dependency 'rspec', '~> 3.0'
27
+ spec.add_development_dependency 'tty-spinner', '~> 0.9.0'
28
+
29
+ spec.add_runtime_dependency 'tty-spinner', '~> 0.9.0'
30
+ end
data/testing/terradoc ADDED
@@ -0,0 +1,89 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ $LOAD_PATH.unshift('./lib')
4
+
5
+ require 'bundler/setup'
6
+ require 'optparse'
7
+ require 'terradoc'
8
+
9
+ # -------------------------------------------------------------------------------- #
10
+ # Run Terradoc #
11
+ # -------------------------------------------------------------------------------- #
12
+ # Pass the command line options to the class and run terradoc #
13
+ # -------------------------------------------------------------------------------- #
14
+
15
+ def run_terradoc(options)
16
+ begin
17
+ Terradoc.new(options)
18
+ rescue StandardError => e
19
+ puts "Error: #{e}"
20
+ puts e.backtrace if options[:verbose]
21
+ exit(1)
22
+ end
23
+ end
24
+
25
+ # -------------------------------------------------------------------------------- #
26
+ # Process Arguments #
27
+ # -------------------------------------------------------------------------------- #
28
+ # This function will process the input from the command line and work out what it #
29
+ # is that the user wants to see. #
30
+ # #
31
+ # This is the main processing function where all the processing logic is handled. #
32
+ # -------------------------------------------------------------------------------- #
33
+
34
+ def process_arguments
35
+ options = { :verbose => false }
36
+ # Enforce the presence of
37
+ mandatory = %I[]
38
+
39
+ optparse = OptionParser.new do |opts|
40
+ opts.banner = "Usage: #{$PROGRAM_NAME}"
41
+
42
+ opts.on('-h', '--help', 'Display this screen') do
43
+ puts opts
44
+ exit(1)
45
+ end
46
+ opts.on('-v', '--verbose', 'Turn on verbose mode') do
47
+ options[:verbose] = true
48
+ end
49
+
50
+ opts.on('-o', '--output string', 'Set the name of the output file. [default: README.md]') do |output|
51
+ options[:output] = output
52
+ end
53
+ opts.on('-p', '--path string', 'Set the path for where the terraform code is. [default: current directory]') do |path|
54
+ options[:path] = path
55
+ end
56
+ end
57
+
58
+ begin
59
+ optparse.parse!
60
+ missing = mandatory.select { |param| options[param].nil? }
61
+ raise OptionParser::MissingArgument.new(missing.join(', ')) unless missing.empty?
62
+ rescue OptionParser::InvalidOption, OptionParser::MissingArgument => e
63
+ puts e.to_s
64
+ puts optparse
65
+ exit
66
+ end
67
+
68
+ exit 0 if run_terradoc(options)
69
+
70
+ exit 1
71
+ end
72
+
73
+ # -------------------------------------------------------------------------------- #
74
+ # Main() #
75
+ # -------------------------------------------------------------------------------- #
76
+ # The main function where all of the heavy lifting and script config is done. #
77
+ # -------------------------------------------------------------------------------- #
78
+
79
+ def main
80
+ process_arguments
81
+ end
82
+
83
+ main
84
+
85
+ # -------------------------------------------------------------------------------- #
86
+ # End of Script #
87
+ # -------------------------------------------------------------------------------- #
88
+ # This is the end - nothing more to see here. #
89
+ # -------------------------------------------------------------------------------- #
metadata ADDED
@@ -0,0 +1,139 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: terradoc
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Tim Gurney aka Wolf
8
+ autorequire:
9
+ bindir: exe
10
+ cert_chain: []
11
+ date: 2020-03-17 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: bundler
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '2'
20
+ type: :development
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '2'
27
+ - !ruby/object:Gem::Dependency
28
+ name: rake
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: '13.0'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: '13.0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rspec
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: '3.0'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: '3.0'
55
+ - !ruby/object:Gem::Dependency
56
+ name: tty-spinner
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - "~>"
60
+ - !ruby/object:Gem::Version
61
+ version: 0.9.0
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - "~>"
67
+ - !ruby/object:Gem::Version
68
+ version: 0.9.0
69
+ - !ruby/object:Gem::Dependency
70
+ name: tty-spinner
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - "~>"
74
+ - !ruby/object:Gem::Version
75
+ version: 0.9.0
76
+ type: :runtime
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - "~>"
81
+ - !ruby/object:Gem::Version
82
+ version: 0.9.0
83
+ description: A simple tool for creating automatic documentaion from terraform source
84
+ code.
85
+ email:
86
+ - wolf@tgwolf.com
87
+ executables:
88
+ - terradoc
89
+ extensions: []
90
+ extra_rdoc_files: []
91
+ files:
92
+ - ".gitattributes"
93
+ - ".gitignore"
94
+ - ".rspec"
95
+ - ".rubocop.yml"
96
+ - ".travis.yml"
97
+ - CHANGELOG.md
98
+ - CODEOWNERS
99
+ - CONTRIBUTING.md
100
+ - EXAMPLE.md
101
+ - Gemfile
102
+ - LICENSE.md
103
+ - README.md
104
+ - Rakefile
105
+ - VERSION.txt
106
+ - bin/console
107
+ - bin/setup
108
+ - exe/terradoc
109
+ - lib/terradoc.rb
110
+ - lib/terradoc/version.rb
111
+ - spec/spec_helper.rb
112
+ - spec/terradoc_spec.rb
113
+ - stale.yml
114
+ - terradoc.gemspec
115
+ - testing/terradoc
116
+ homepage: https://github.com/TerraformToolbox/terradoc
117
+ licenses:
118
+ - MIT
119
+ metadata: {}
120
+ post_install_message:
121
+ rdoc_options: []
122
+ require_paths:
123
+ - lib
124
+ required_ruby_version: !ruby/object:Gem::Requirement
125
+ requirements:
126
+ - - ">="
127
+ - !ruby/object:Gem::Version
128
+ version: '2.5'
129
+ required_rubygems_version: !ruby/object:Gem::Requirement
130
+ requirements:
131
+ - - ">="
132
+ - !ruby/object:Gem::Version
133
+ version: '0'
134
+ requirements: []
135
+ rubygems_version: 3.0.3
136
+ signing_key:
137
+ specification_version: 4
138
+ summary: A simple tool for creating automatic documentaion from terraform source code.
139
+ test_files: []