pantograph 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (202) hide show
  1. checksums.yaml +7 -0
  2. data/.yardopts +1 -0
  3. data/LICENSE +21 -0
  4. data/README.md +197 -0
  5. data/bin/bin-proxy +19 -0
  6. data/bin/pantograph +23 -0
  7. data/pantograph/README.md +11 -0
  8. data/pantograph/lib/assets/ActionDetails.md.erb +106 -0
  9. data/pantograph/lib/assets/Actions.md.erb +43 -0
  10. data/pantograph/lib/assets/DefaultPantfileTemplate +20 -0
  11. data/pantograph/lib/assets/completions/completion.bash +23 -0
  12. data/pantograph/lib/assets/completions/completion.fish +39 -0
  13. data/pantograph/lib/assets/completions/completion.sh +12 -0
  14. data/pantograph/lib/assets/completions/completion.zsh +23 -0
  15. data/pantograph/lib/assets/custom_action_template.rb +80 -0
  16. data/pantograph/lib/assets/report_template.xml.erb +15 -0
  17. data/pantograph/lib/pantograph/action.rb +194 -0
  18. data/pantograph/lib/pantograph/action_collector.rb +35 -0
  19. data/pantograph/lib/pantograph/actions/README.md +3 -0
  20. data/pantograph/lib/pantograph/actions/actions_helper.rb +166 -0
  21. data/pantograph/lib/pantograph/actions/add_extra_platforms.rb +45 -0
  22. data/pantograph/lib/pantograph/actions/artifactory.rb +157 -0
  23. data/pantograph/lib/pantograph/actions/bundle_install.rb +156 -0
  24. data/pantograph/lib/pantograph/actions/changelog_from_git_commits.rb +197 -0
  25. data/pantograph/lib/pantograph/actions/clipboard.rb +52 -0
  26. data/pantograph/lib/pantograph/actions/cloc.rb +89 -0
  27. data/pantograph/lib/pantograph/actions/create_pull_request.rb +190 -0
  28. data/pantograph/lib/pantograph/actions/danger.rb +131 -0
  29. data/pantograph/lib/pantograph/actions/debug.rb +32 -0
  30. data/pantograph/lib/pantograph/actions/default_platform.rb +47 -0
  31. data/pantograph/lib/pantograph/actions/download.rb +76 -0
  32. data/pantograph/lib/pantograph/actions/echo.rb +14 -0
  33. data/pantograph/lib/pantograph/actions/ensure_bundle_exec.rb +59 -0
  34. data/pantograph/lib/pantograph/actions/ensure_env_vars.rb +58 -0
  35. data/pantograph/lib/pantograph/actions/ensure_git_branch.rb +69 -0
  36. data/pantograph/lib/pantograph/actions/ensure_git_status_clean.rb +81 -0
  37. data/pantograph/lib/pantograph/actions/erb.rb +88 -0
  38. data/pantograph/lib/pantograph/actions/get_build_number_repository.rb +120 -0
  39. data/pantograph/lib/pantograph/actions/get_github_release.rb +163 -0
  40. data/pantograph/lib/pantograph/actions/git_add.rb +93 -0
  41. data/pantograph/lib/pantograph/actions/git_branch.rb +58 -0
  42. data/pantograph/lib/pantograph/actions/git_commit.rb +80 -0
  43. data/pantograph/lib/pantograph/actions/git_pull.rb +53 -0
  44. data/pantograph/lib/pantograph/actions/git_submodule_update.rb +52 -0
  45. data/pantograph/lib/pantograph/actions/git_tag_exists.rb +74 -0
  46. data/pantograph/lib/pantograph/actions/github_api.rb +262 -0
  47. data/pantograph/lib/pantograph/actions/gradle.rb +278 -0
  48. data/pantograph/lib/pantograph/actions/import.rb +49 -0
  49. data/pantograph/lib/pantograph/actions/import_from_git.rb +71 -0
  50. data/pantograph/lib/pantograph/actions/is_ci.rb +51 -0
  51. data/pantograph/lib/pantograph/actions/jira.rb +115 -0
  52. data/pantograph/lib/pantograph/actions/lane_context.rb +60 -0
  53. data/pantograph/lib/pantograph/actions/last_git_commit.rb +58 -0
  54. data/pantograph/lib/pantograph/actions/last_git_tag.rb +51 -0
  55. data/pantograph/lib/pantograph/actions/make_changelog_from_jenkins.rb +81 -0
  56. data/pantograph/lib/pantograph/actions/min_pantograph_version.rb +57 -0
  57. data/pantograph/lib/pantograph/actions/nexus_upload.rb +230 -0
  58. data/pantograph/lib/pantograph/actions/notification.rb +75 -0
  59. data/pantograph/lib/pantograph/actions/number_of_commits.rb +75 -0
  60. data/pantograph/lib/pantograph/actions/opt_out_usage.rb +40 -0
  61. data/pantograph/lib/pantograph/actions/pantograph_version.rb +15 -0
  62. data/pantograph/lib/pantograph/actions/println.rb +14 -0
  63. data/pantograph/lib/pantograph/actions/prompt.rb +119 -0
  64. data/pantograph/lib/pantograph/actions/push_git_tags.rb +76 -0
  65. data/pantograph/lib/pantograph/actions/push_to_git_remote.rb +127 -0
  66. data/pantograph/lib/pantograph/actions/puts.rb +68 -0
  67. data/pantograph/lib/pantograph/actions/reset_git_repo.rb +121 -0
  68. data/pantograph/lib/pantograph/actions/rocket.rb +83 -0
  69. data/pantograph/lib/pantograph/actions/rsync.rb +74 -0
  70. data/pantograph/lib/pantograph/actions/ruby_version.rb +56 -0
  71. data/pantograph/lib/pantograph/actions/say.rb +56 -0
  72. data/pantograph/lib/pantograph/actions/scp.rb +114 -0
  73. data/pantograph/lib/pantograph/actions/set_github_release.rb +274 -0
  74. data/pantograph/lib/pantograph/actions/sh.rb +71 -0
  75. data/pantograph/lib/pantograph/actions/skip_docs.rb +52 -0
  76. data/pantograph/lib/pantograph/actions/slack.rb +288 -0
  77. data/pantograph/lib/pantograph/actions/sonar.rb +156 -0
  78. data/pantograph/lib/pantograph/actions/ssh.rb +162 -0
  79. data/pantograph/lib/pantograph/actions/twitter.rb +89 -0
  80. data/pantograph/lib/pantograph/actions/update_pantograph.rb +177 -0
  81. data/pantograph/lib/pantograph/actions/zip.rb +120 -0
  82. data/pantograph/lib/pantograph/auto_complete.rb +82 -0
  83. data/pantograph/lib/pantograph/boolean.rb +5 -0
  84. data/pantograph/lib/pantograph/cli_tools_distributor.rb +183 -0
  85. data/pantograph/lib/pantograph/command_line_handler.rb +43 -0
  86. data/pantograph/lib/pantograph/commands_generator.rb +344 -0
  87. data/pantograph/lib/pantograph/configuration_helper.rb +26 -0
  88. data/pantograph/lib/pantograph/core_ext/bundler_monkey_patch.rb +14 -0
  89. data/pantograph/lib/pantograph/documentation/actions_list.rb +214 -0
  90. data/pantograph/lib/pantograph/documentation/docs_generator.rb +95 -0
  91. data/pantograph/lib/pantograph/documentation/markdown_docs_generator.rb +221 -0
  92. data/pantograph/lib/pantograph/environment_printer.rb +282 -0
  93. data/pantograph/lib/pantograph/erb_template_helper.rb +30 -0
  94. data/pantograph/lib/pantograph/features.rb +4 -0
  95. data/pantograph/lib/pantograph/helper/README.md +29 -0
  96. data/pantograph/lib/pantograph/helper/dotenv_helper.rb +50 -0
  97. data/pantograph/lib/pantograph/helper/gem_helper.rb +26 -0
  98. data/pantograph/lib/pantograph/helper/git_helper.rb +135 -0
  99. data/pantograph/lib/pantograph/helper/gradle_helper.rb +62 -0
  100. data/pantograph/lib/pantograph/helper/sh_helper.rb +134 -0
  101. data/pantograph/lib/pantograph/junit_generator.rb +27 -0
  102. data/pantograph/lib/pantograph/lane.rb +97 -0
  103. data/pantograph/lib/pantograph/lane_list.rb +77 -0
  104. data/pantograph/lib/pantograph/lane_manager.rb +140 -0
  105. data/pantograph/lib/pantograph/lane_manager_base.rb +92 -0
  106. data/pantograph/lib/pantograph/markdown_table_formatter.rb +62 -0
  107. data/pantograph/lib/pantograph/new_action.rb +47 -0
  108. data/pantograph/lib/pantograph/one_off.rb +45 -0
  109. data/pantograph/lib/pantograph/other_action.rb +29 -0
  110. data/pantograph/lib/pantograph/pant_file.rb +377 -0
  111. data/pantograph/lib/pantograph/pantograph_require.rb +75 -0
  112. data/pantograph/lib/pantograph/plugins/plugin_fetcher.rb +55 -0
  113. data/pantograph/lib/pantograph/plugins/plugin_generator.rb +86 -0
  114. data/pantograph/lib/pantograph/plugins/plugin_generator_ui.rb +19 -0
  115. data/pantograph/lib/pantograph/plugins/plugin_info.rb +49 -0
  116. data/pantograph/lib/pantograph/plugins/plugin_info_collector.rb +159 -0
  117. data/pantograph/lib/pantograph/plugins/plugin_manager.rb +387 -0
  118. data/pantograph/lib/pantograph/plugins/plugin_search.rb +46 -0
  119. data/pantograph/lib/pantograph/plugins/plugin_update_manager.rb +70 -0
  120. data/pantograph/lib/pantograph/plugins/plugins.rb +12 -0
  121. data/pantograph/lib/pantograph/plugins/template/%gem_name%.gemspec.erb +35 -0
  122. data/pantograph/lib/pantograph/plugins/template/.circleci/config.yml +43 -0
  123. data/pantograph/lib/pantograph/plugins/template/.gitignore +12 -0
  124. data/pantograph/lib/pantograph/plugins/template/.rspec +5 -0
  125. data/pantograph/lib/pantograph/plugins/template/.rubocop.yml +179 -0
  126. data/pantograph/lib/pantograph/plugins/template/.travis.yml +4 -0
  127. data/pantograph/lib/pantograph/plugins/template/Gemfile +6 -0
  128. data/pantograph/lib/pantograph/plugins/template/LICENSE.erb +21 -0
  129. data/pantograph/lib/pantograph/plugins/template/README.md.erb +52 -0
  130. data/pantograph/lib/pantograph/plugins/template/Rakefile +9 -0
  131. data/pantograph/lib/pantograph/plugins/template/lib/pantograph/plugin/%plugin_name%/actions/%plugin_name%_action.rb.erb +47 -0
  132. data/pantograph/lib/pantograph/plugins/template/lib/pantograph/plugin/%plugin_name%/helper/%plugin_name%_helper.rb.erb +16 -0
  133. data/pantograph/lib/pantograph/plugins/template/lib/pantograph/plugin/%plugin_name%/version.rb.erb +5 -0
  134. data/pantograph/lib/pantograph/plugins/template/lib/pantograph/plugin/%plugin_name%.rb.erb +16 -0
  135. data/pantograph/lib/pantograph/plugins/template/pantograph/Pantfile.erb +3 -0
  136. data/pantograph/lib/pantograph/plugins/template/pantograph/Pluginfile.erb +1 -0
  137. data/pantograph/lib/pantograph/plugins/template/spec/%plugin_name%_action_spec.rb.erb +9 -0
  138. data/pantograph/lib/pantograph/plugins/template/spec/spec_helper.rb.erb +15 -0
  139. data/pantograph/lib/pantograph/runner.rb +371 -0
  140. data/pantograph/lib/pantograph/server/action_command.rb +61 -0
  141. data/pantograph/lib/pantograph/server/action_command_return.rb +14 -0
  142. data/pantograph/lib/pantograph/server/command_executor.rb +7 -0
  143. data/pantograph/lib/pantograph/server/command_parser.rb +36 -0
  144. data/pantograph/lib/pantograph/server/control_command.rb +23 -0
  145. data/pantograph/lib/pantograph/server/json_return_value_processor.rb +72 -0
  146. data/pantograph/lib/pantograph/server/socket_server.rb +232 -0
  147. data/pantograph/lib/pantograph/server/socket_server_action_command_executor.rb +101 -0
  148. data/pantograph/lib/pantograph/setup/setup.rb +290 -0
  149. data/pantograph/lib/pantograph/setup/setup_android.rb +64 -0
  150. data/pantograph/lib/pantograph/setup/setup_ios.rb +412 -0
  151. data/pantograph/lib/pantograph/shells.rb +6 -0
  152. data/pantograph/lib/pantograph/supported_platforms.rb +28 -0
  153. data/pantograph/lib/pantograph/tools.rb +10 -0
  154. data/pantograph/lib/pantograph/version.rb +5 -0
  155. data/pantograph/lib/pantograph.rb +51 -0
  156. data/pantograph_core/README.md +79 -0
  157. data/pantograph_core/lib/assets/XMLTemplate.xml.erb +12 -0
  158. data/pantograph_core/lib/pantograph_core/analytics/action_completion_context.rb +34 -0
  159. data/pantograph_core/lib/pantograph_core/analytics/action_launch_context.rb +38 -0
  160. data/pantograph_core/lib/pantograph_core/analytics/analytics_event_builder.rb +23 -0
  161. data/pantograph_core/lib/pantograph_core/analytics/analytics_ingester_client.rb +54 -0
  162. data/pantograph_core/lib/pantograph_core/analytics/analytics_session.rb +71 -0
  163. data/pantograph_core/lib/pantograph_core/cert_checker.rb +116 -0
  164. data/pantograph_core/lib/pantograph_core/command_executor.rb +99 -0
  165. data/pantograph_core/lib/pantograph_core/configuration/commander_generator.rb +103 -0
  166. data/pantograph_core/lib/pantograph_core/configuration/config_item.rb +314 -0
  167. data/pantograph_core/lib/pantograph_core/configuration/configuration.rb +332 -0
  168. data/pantograph_core/lib/pantograph_core/configuration/configuration_file.rb +182 -0
  169. data/pantograph_core/lib/pantograph_core/core_ext/shellwords.rb +63 -0
  170. data/pantograph_core/lib/pantograph_core/core_ext/string.rb +17 -0
  171. data/pantograph_core/lib/pantograph_core/env.rb +9 -0
  172. data/pantograph_core/lib/pantograph_core/feature/feature.rb +51 -0
  173. data/pantograph_core/lib/pantograph_core/features.rb +4 -0
  174. data/pantograph_core/lib/pantograph_core/globals.rb +27 -0
  175. data/pantograph_core/lib/pantograph_core/helper.rb +409 -0
  176. data/pantograph_core/lib/pantograph_core/keychain_importer.rb +74 -0
  177. data/pantograph_core/lib/pantograph_core/languages.rb +14 -0
  178. data/pantograph_core/lib/pantograph_core/module.rb +29 -0
  179. data/pantograph_core/lib/pantograph_core/pantograph_folder.rb +39 -0
  180. data/pantograph_core/lib/pantograph_core/pantograph_pty.rb +57 -0
  181. data/pantograph_core/lib/pantograph_core/pkg_file_analyser.rb +44 -0
  182. data/pantograph_core/lib/pantograph_core/print_table.rb +131 -0
  183. data/pantograph_core/lib/pantograph_core/string_filters.rb +51 -0
  184. data/pantograph_core/lib/pantograph_core/swag.rb +85 -0
  185. data/pantograph_core/lib/pantograph_core/tag_version.rb +31 -0
  186. data/pantograph_core/lib/pantograph_core/test_parser.rb +107 -0
  187. data/pantograph_core/lib/pantograph_core/ui/disable_colors.rb +17 -0
  188. data/pantograph_core/lib/pantograph_core/ui/errors/pantograph_common_error.rb +19 -0
  189. data/pantograph_core/lib/pantograph_core/ui/errors/pantograph_crash.rb +11 -0
  190. data/pantograph_core/lib/pantograph_core/ui/errors/pantograph_error.rb +25 -0
  191. data/pantograph_core/lib/pantograph_core/ui/errors/pantograph_exception.rb +19 -0
  192. data/pantograph_core/lib/pantograph_core/ui/errors/pantograph_shell_error.rb +11 -0
  193. data/pantograph_core/lib/pantograph_core/ui/errors.rb +1 -0
  194. data/pantograph_core/lib/pantograph_core/ui/github_issue_inspector_reporter.rb +62 -0
  195. data/pantograph_core/lib/pantograph_core/ui/implementations/shell.rb +159 -0
  196. data/pantograph_core/lib/pantograph_core/ui/interface.rb +205 -0
  197. data/pantograph_core/lib/pantograph_core/ui/pantograph_runner.rb +276 -0
  198. data/pantograph_core/lib/pantograph_core/ui/ui.rb +26 -0
  199. data/pantograph_core/lib/pantograph_core/update_checker/changelog.rb +37 -0
  200. data/pantograph_core/lib/pantograph_core/update_checker/update_checker.rb +107 -0
  201. data/pantograph_core/lib/pantograph_core.rb +45 -0
  202. metadata +987 -0
@@ -0,0 +1,43 @@
1
+ module Pantograph
2
+ class CommandLineHandler
3
+ # This method handles command line inputs and properly transforms them to a usable format
4
+ # @param [Array] args An array of all arguments (not options)
5
+ # @param [Array] args A hash of all options (e.g. --env NAME)
6
+ def self.handle(args, options)
7
+ lane_parameters = {} # the parameters we'll pass to the lane
8
+ platform_lane_info = [] # the part that's responsible for the lane/platform definition
9
+ args.each do |current|
10
+ if current.include?(":") # that's a key/value which we want to pass to the lane
11
+ key, value = current.split(":", 2)
12
+ UI.user_error!("Please pass values like this: key:value") unless key.length > 0
13
+ value = convert_value(value)
14
+ UI.verbose("Using #{key}: #{value}")
15
+ lane_parameters[key.to_sym] = value
16
+ else
17
+ platform_lane_info << current
18
+ end
19
+ end
20
+
21
+ platform = nil
22
+ lane = platform_lane_info[1]
23
+ if lane
24
+ platform = platform_lane_info[0]
25
+ else
26
+ lane = platform_lane_info[0]
27
+ end
28
+
29
+ dot_env = Helper.test? ? nil : options.env
30
+
31
+ Pantograph::LaneManager.cruise_lane(platform, lane, lane_parameters, dot_env)
32
+ end
33
+
34
+ # Helper to convert into the right data type
35
+ def self.convert_value(value)
36
+ return true if value == 'true' || value == 'yes'
37
+ return false if value == 'false' || value == 'no'
38
+
39
+ # Default case:
40
+ return value
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,344 @@
1
+ require 'commander'
2
+ require 'pantograph/new_action'
3
+
4
+ HighLine.track_eof = false
5
+
6
+ module Pantograph
7
+ class CommandsGenerator
8
+ include Commander::Methods
9
+
10
+ def self.start
11
+ # since at this point we haven't yet loaded commander
12
+ # however we do want to log verbose information in the PluginManager
13
+ PantographCore::Globals.verbose = true if ARGV.include?("--verbose")
14
+ if ARGV.include?("--capture_output")
15
+ PantographCore::Globals.verbose = true
16
+ PantographCore::Globals.capture_output = true
17
+ end
18
+ PantographCore::Swag.show_loader
19
+
20
+ # has to be checked here - in case we wan't to troubleshoot plugin related issues
21
+ if ARGV.include?("--troubleshoot")
22
+ self.confirm_troubleshoot
23
+ end
24
+
25
+ if PantographCore::Globals.capture_output?
26
+ # Trace mode is enabled
27
+ # redirect STDOUT and STDERR
28
+ out_channel = StringIO.new
29
+ $stdout = out_channel
30
+ $stderr = out_channel
31
+ end
32
+
33
+ Pantograph.load_actions
34
+ PantographCore::Swag.stop_loader
35
+ # do not use "include" as it may be some where in the commandline where "env" is required, therefore explicit index->0
36
+ unless ARGV[0] == "env" || CLIToolsDistributor.running_version_command? || CLIToolsDistributor.running_help_command?
37
+ # *after* loading the plugins
38
+ Pantograph.plugin_manager.load_plugins
39
+ Pantograph::PluginUpdateManager.start_looking_for_updates
40
+ end
41
+ self.new.run
42
+ ensure
43
+ Pantograph::PluginUpdateManager.show_update_status
44
+ if PantographCore::Globals.capture_output?
45
+ if $stdout.respond_to?(:string)
46
+ # Sometimes you can get NoMethodError: undefined method `string' for #<IO:<STDOUT>> when running with PantographRunner
47
+ PantographCore::Globals.captured_output = Helper.strip_ansi_colors($stdout.string)
48
+ end
49
+ $stdout = STDOUT
50
+ $stderr = STDERR
51
+
52
+ require "pantograph/environment_printer"
53
+ Pantograph::EnvironmentPrinter.output
54
+ end
55
+ end
56
+
57
+ def self.confirm_troubleshoot
58
+ if Helper.ci?
59
+ UI.error("---")
60
+ UI.error("You are trying to use '--troubleshoot' on CI")
61
+ UI.error("this option is not usable in CI, as it is insecure")
62
+ UI.error("---")
63
+ UI.user_error!("Do not use --troubleshoot in CI")
64
+ end
65
+ # maybe already set by 'start'
66
+ return if $troubleshoot
67
+ UI.error("---")
68
+ UI.error("Are you sure you want to enable '--troubleshoot'?")
69
+ UI.error("All commmands will run in full unfiltered output mode.")
70
+ UI.error("Sensitive data, like passwords, could be printed to the log.")
71
+ UI.error("---")
72
+ if UI.confirm("Do you really want to enable --troubleshoot")
73
+ $troubleshoot = true
74
+ end
75
+ end
76
+
77
+ def run
78
+ program :name, 'pantograph'
79
+ program :version, Pantograph::VERSION
80
+ program :description, [
81
+ "CLI for 'pantograph' - #{Pantograph::DESCRIPTION}\n",
82
+ "\tRun using `pantograph [platform] [lane_name]`",
83
+ "\tTo pass values to the lanes use `pantograph [platform] [lane_name] key:value key2:value2`"
84
+ ].join("\n")
85
+ program :help, 'Author', 'Felix Krause <pantograph@krausefx.com>'
86
+ program :help, 'Website', 'https://pantograph.tools'
87
+ program :help, 'GitHub', 'https://github.com/pantograph/pantograph'
88
+ program :help_formatter, :compact
89
+
90
+ global_option('--verbose') { PantographCore::Globals.verbose = true }
91
+ global_option('--capture_output', 'Captures the output of the current run, and generates a markdown issue template') do
92
+ PantographCore::Globals.capture_output = false
93
+ PantographCore::Globals.verbose = true
94
+ end
95
+ global_option('--troubleshoot', 'Enables extended verbose mode. Use with caution, as this even includes ALL sensitive data. Cannot be used on CI.')
96
+
97
+ always_trace!
98
+
99
+ command :trigger do |c|
100
+ c.syntax = 'pantograph [lane]'
101
+ c.description = 'Run a specific lane. Pass the lane name and optionally the platform first.'
102
+ c.option('--env STRING[,STRING2]', String, 'Add environment(s) to use with `dotenv`')
103
+
104
+ c.action do |args, options|
105
+ if ensure_pantfile
106
+ Pantograph::CommandLineHandler.handle(args, options)
107
+ end
108
+ end
109
+ end
110
+
111
+ command :init do |c|
112
+ c.syntax = 'pantograph init'
113
+ c.description = 'Helps you with your initial pantograph setup'
114
+
115
+ c.option('-u STRING', '--user STRING', String, 'iOS projects only: Your Apple ID')
116
+
117
+ c.action do |args, options|
118
+ Pantograph::Setup.start(user: options.user)
119
+ end
120
+ end
121
+
122
+ command :new_action do |c|
123
+ c.syntax = 'pantograph new_action'
124
+ c.description = 'Create a new custom action for pantograph.'
125
+
126
+ c.option('--name STRING', String, 'Name of your new action')
127
+
128
+ c.action do |args, options|
129
+ Pantograph::NewAction.run(new_action_name: options.name)
130
+ end
131
+ end
132
+
133
+ command :socket_server do |c|
134
+ c.syntax = 'pantograph start_server'
135
+ c.description = 'Starts local socket server and enables only a single local connection'
136
+ c.option('-s', '--stay_alive', 'Keeps socket server up even after error or disconnects, requires CTRL-C to kill.')
137
+ c.option('-c seconds', '--connection_timeout', 'Sets connection established timeout')
138
+ c.action do |args, options|
139
+ default_connection_timeout = 5
140
+ stay_alive = options.stay_alive || false
141
+ connection_timeout = options.connection_timeout || default_connection_timeout
142
+
143
+ if stay_alive && options.connection_timeout.nil?
144
+ UI.important("stay_alive is set, but the connection timeout is not, this will give you #{default_connection_timeout} seconds to (re)connect")
145
+ end
146
+
147
+ require 'pantograph/server/socket_server'
148
+ require 'pantograph/server/socket_server_action_command_executor'
149
+
150
+ command_executor = SocketServerActionCommandExecutor.new
151
+ server = Pantograph::SocketServer.new(
152
+ command_executor: command_executor,
153
+ connection_timeout: connection_timeout,
154
+ stay_alive: stay_alive
155
+ )
156
+ result = server.start
157
+ UI.success("Result: #{result}") if result
158
+ end
159
+ end
160
+
161
+ command :lanes do |c|
162
+ c.syntax = 'pantograph lanes'
163
+ c.description = 'Lists all available lanes and shows their description'
164
+ c.option("-j", "--json", "Output the lanes in JSON instead of text")
165
+
166
+ c.action do |args, options|
167
+ if options.json || ensure_pantfile
168
+ require 'pantograph/lane_list'
169
+ path = PantographCore::PantographFolder.pantfile_path
170
+
171
+ if options.json
172
+ Pantograph::LaneList.output_json(path)
173
+ else
174
+ Pantograph::LaneList.output(path)
175
+ end
176
+ end
177
+ end
178
+ end
179
+
180
+ command :list do |c|
181
+ c.syntax = 'pantograph list'
182
+ c.description = 'Lists all available lanes without description'
183
+ c.action do |args, options|
184
+ if ensure_pantfile
185
+ ff = Pantograph::PantFile.new(PantographCore::PantographFolder.pantfile_path)
186
+ UI.message("Available lanes:")
187
+ ff.runner.available_lanes.each do |lane|
188
+ UI.message("- #{lane}")
189
+ end
190
+ UI.important("Execute using `pantograph [lane_name]`")
191
+ end
192
+ end
193
+ end
194
+
195
+ command :docs do |c|
196
+ c.syntax = 'pantograph docs'
197
+ c.description = 'Generate a markdown based documentation based on the Pantfile'
198
+ c.option('-f', '--force', 'Overwrite the existing README.md in the ./pantograph folder')
199
+
200
+ c.action do |args, options|
201
+ if ensure_pantfile
202
+ ff = Pantograph::PantFile.new(File.join(PantographCore::PantographFolder.path || '.', 'Pantfile'))
203
+ UI.message("You don't need to run `pantograph docs` manually any more, this will be done automatically for you when running a lane.")
204
+ Pantograph::DocsGenerator.run(ff)
205
+ end
206
+ end
207
+ end
208
+
209
+ command :run do |c|
210
+ c.syntax = 'pantograph run [action] key1:value1 key2:value2'
211
+ c.description = 'Run a pantograph one-off action without a full lane'
212
+
213
+ c.action do |args, options|
214
+ require 'pantograph/one_off'
215
+ result = Pantograph::OneOff.execute(args: args)
216
+ UI.success("Result: #{result}") if result
217
+ end
218
+ end
219
+
220
+ command :actions do |c|
221
+ c.syntax = 'pantograph actions'
222
+ c.description = 'Lists all available pantograph actions'
223
+
224
+ c.option('--platform STRING', String, 'Only show actions available on the given platform')
225
+
226
+ c.action do |args, options|
227
+ require 'pantograph/documentation/actions_list'
228
+ Pantograph::ActionsList.run(filter: args.first, platform: options.platform)
229
+ end
230
+ end
231
+
232
+ command :action do |c|
233
+ c.syntax = 'pantograph action [tool_name]'
234
+ c.description = 'Shows more information for a specific command'
235
+ c.action do |args, options|
236
+ require 'pantograph/documentation/actions_list'
237
+ Pantograph::ActionsList.run(filter: args.first)
238
+ end
239
+ end
240
+
241
+ command :enable_auto_complete do |c|
242
+ c.syntax = 'pantograph enable_auto_complete'
243
+ c.description = 'Enable tab auto completion'
244
+ c.option('-c STRING[,STRING2]', '--custom STRING[,STRING2]', String, 'Add custom command(s) for which tab auto complete should be enabled too')
245
+
246
+ c.action do |args, options|
247
+ require 'pantograph/auto_complete'
248
+ Pantograph::AutoComplete.execute(args, options)
249
+ end
250
+ end
251
+
252
+ command :env do |c|
253
+ c.syntax = 'pantograph env'
254
+ c.description = 'Print your pantograph environment, use this when you submit an issue on GitHub'
255
+ c.action do |args, options|
256
+ require "pantograph/environment_printer"
257
+ Pantograph::EnvironmentPrinter.output
258
+ end
259
+ end
260
+
261
+ command :update_pantograph do |c|
262
+ c.syntax = 'pantograph update_pantograph'
263
+ c.description = 'Update pantograph to the latest release'
264
+ c.action do |args, options|
265
+ require 'pantograph/one_off'
266
+ Pantograph::OneOff.run(action: "update_pantograph", parameters: {})
267
+ end
268
+ end
269
+
270
+ #####################################################
271
+ # @!group Plugins
272
+ #####################################################
273
+
274
+ command :new_plugin do |c|
275
+ c.syntax = 'pantograph new_plugin [plugin_name]'
276
+ c.description = 'Create a new plugin that can be used with pantograph'
277
+
278
+ c.action do |args, options|
279
+ PluginGenerator.new.generate(args.shift)
280
+ end
281
+ end
282
+
283
+ command :add_plugin do |c|
284
+ c.syntax = 'pantograph add_plugin [plugin_name]'
285
+ c.description = 'Add a new plugin to your pantograph setup'
286
+
287
+ c.action do |args, options|
288
+ args << UI.input("Enter the name of the plugin to install: ") if args.empty?
289
+ args.each do |plugin_name|
290
+ Pantograph.plugin_manager.add_dependency(plugin_name)
291
+ end
292
+
293
+ UI.important("Make sure to commit your Gemfile, Gemfile.lock and #{PluginManager::PLUGINFILE_NAME} to version control")
294
+ Pantograph.plugin_manager.install_dependencies!
295
+ end
296
+ end
297
+
298
+ command :install_plugins do |c|
299
+ c.syntax = 'pantograph install_plugins'
300
+ c.description = 'Install all plugins for this project'
301
+
302
+ c.action do |args, options|
303
+ Pantograph.plugin_manager.install_dependencies!
304
+ end
305
+ end
306
+
307
+ command :update_plugins do |c|
308
+ c.syntax = 'pantograph update_plugins'
309
+ c.description = 'Update all plugin dependencies'
310
+
311
+ c.action do |args, options|
312
+ Pantograph.plugin_manager.update_dependencies!
313
+ end
314
+ end
315
+
316
+ command :search_plugins do |c|
317
+ c.syntax = 'pantograph search_plugins [search_query]'
318
+ c.description = 'Search for plugins, search query is optional'
319
+
320
+ c.action do |args, options|
321
+ search_query = args.last
322
+ PluginSearch.print_plugins(search_query: search_query)
323
+ end
324
+ end
325
+
326
+ default_command(:trigger)
327
+ run!
328
+ end
329
+
330
+ # Makes sure a Pantfile is available
331
+ # Shows an appropriate message to the user
332
+ # if that's not the case
333
+ # return true if the Pantfile is available
334
+ def ensure_pantfile
335
+ return true if PantographCore::PantographFolder.setup?
336
+
337
+ create = UI.confirm('Could not find pantograph in current directory. Make sure to have your pantograph configuration files inside a folder called "pantograph". Would you like to set pantograph up?')
338
+ if create
339
+ Pantograph::Setup.start
340
+ end
341
+ return false
342
+ end
343
+ end
344
+ end
@@ -0,0 +1,26 @@
1
+ module Pantograph
2
+ class ConfigurationHelper
3
+ def self.parse(action, params)
4
+ first_element = (action.available_options || []).first
5
+
6
+ if first_element && first_element.kind_of?(PantographCore::ConfigItem)
7
+ # default use case
8
+ return PantographCore::Configuration.create(action.available_options, params)
9
+ elsif first_element
10
+ UI.error("Old configuration format for action '#{action}'") if Helper.test?
11
+ return params
12
+ else
13
+
14
+ # No parameters... we still need the configuration object array
15
+ PantographCore::Configuration.create(action.available_options, {})
16
+
17
+ end
18
+ rescue => ex
19
+ if action.respond_to?(:action_name)
20
+ UI.error("You passed invalid parameters to '#{action.action_name}'.")
21
+ UI.error("Check out the error below and available options by running `pantograph action #{action.action_name}`")
22
+ end
23
+ raise ex
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,14 @@
1
+ # https://github.com/bundler/bundler/issues/4368
2
+ #
3
+ # There is an issue with RubyGems 2.6.2 where it attempts to call Bundler::SpecSet#size, which doesn't exist.
4
+ # If a gem is not installed, a `Gem::Specification.find_by_name` call will trigger this problem.
5
+ if Object.const_defined?(:Bundler) &&
6
+ Bundler.const_defined?(:SpecSet) &&
7
+ Bundler::SpecSet.instance_methods.include?(:length) &&
8
+ !Bundler::SpecSet.instance_methods.include?(:size)
9
+ module Bundler
10
+ class SpecSet
11
+ alias size length
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,214 @@
1
+ module Pantograph
2
+ class ActionsList
3
+ def self.run(filter: nil, platform: nil)
4
+ require 'terminal-table'
5
+ if filter
6
+ show_details(filter: filter)
7
+ else
8
+ print_all(platform: platform)
9
+ end
10
+ end
11
+
12
+ def self.print_all(platform: nil)
13
+ rows = []
14
+ all_actions(platform) do |action, name|
15
+ current = []
16
+
17
+ if Pantograph::Actions.is_deprecated?(action)
18
+ current << "#{name} (DEPRECATED)".deprecated
19
+ else
20
+ current << name.yellow
21
+ end
22
+
23
+ if action < Action
24
+ current << action.description.to_s.remove_markdown if action.description
25
+
26
+ authors = Array(action.author || action.authors)
27
+ current << authors.first.green if authors.count == 1
28
+ current << "Multiple".green if authors.count > 1
29
+ else
30
+ UI.error(action_subclass_error(name))
31
+ current << "Please update action file".red
32
+ current << ' '
33
+ end
34
+ rows << current
35
+ end
36
+
37
+ puts(Terminal::Table.new(
38
+ title: "Available pantograph actions".green,
39
+ headings: ['Action', 'Description', 'Author'],
40
+ rows: PantographCore::PrintTable.transform_output(rows)
41
+ ))
42
+ puts(" Platform filter: #{platform}".magenta) if platform
43
+ puts(" Total of #{rows.count} actions")
44
+
45
+ puts("\nGet more information for one specific action using `pantograph action [name]`\n".green)
46
+ end
47
+
48
+ def self.show_details(filter: nil)
49
+ puts("Loading documentation for #{filter}:".green)
50
+ puts("")
51
+
52
+ action = find_action_named(filter)
53
+
54
+ if action
55
+ unless action < Action
56
+ UI.user_error!(action_subclass_error(filter))
57
+ end
58
+
59
+ print_summary(action, filter)
60
+ print_options(action, filter)
61
+ print_output_variables(action, filter)
62
+ print_return_value(action, filter)
63
+
64
+ if Pantograph::Actions.is_deprecated?(action)
65
+ puts("==========================================".deprecated)
66
+ puts("This action (#{filter}) is deprecated".deprecated)
67
+ puts(action.deprecated_notes.to_s.remove_markdown.deprecated) if action.deprecated_notes
68
+ puts("==========================================\n".deprecated)
69
+ end
70
+
71
+ puts("More information can be found on https://docs.pantograph.tools/actions/#{filter}")
72
+ puts("")
73
+ else
74
+ puts("Couldn't find action for the given filter.".red)
75
+ puts("==========================================\n".red)
76
+
77
+ print_all # show all available actions instead
78
+ print_suggestions(filter)
79
+ end
80
+ end
81
+
82
+ def self.print_suggestions(filter)
83
+ if !filter.nil? && filter.length > 1
84
+ action_names = []
85
+ all_actions(nil) do |action_ref, action_name|
86
+ action_names << action_name
87
+ end
88
+
89
+ corrections = []
90
+
91
+ if defined?(DidYouMean::SpellChecker)
92
+ spell_checker = DidYouMean::SpellChecker.new(dictionary: action_names)
93
+ corrections << spell_checker.correct(filter).compact
94
+ end
95
+
96
+ corrections << action_names.select { |name| name.include?(filter) }
97
+
98
+ puts("Did you mean: #{corrections.flatten.uniq.join(', ')}?".green) unless corrections.flatten.empty?
99
+ end
100
+ end
101
+
102
+ def self.action_subclass_error(name)
103
+ "Please update your action '#{name}' to be a subclass of `Action` by adding ` < Action` after your class name."
104
+ end
105
+
106
+ def self.print_summary(action, name)
107
+ rows = []
108
+
109
+ if action.description
110
+ description = action.description.to_s.remove_markdown
111
+ rows << [description]
112
+ rows << [' ']
113
+ end
114
+
115
+ if action.details
116
+ details = action.details.to_s.remove_markdown
117
+ details.split("\n").each do |detail|
118
+ row = detail.empty? ? ' ' : detail
119
+ rows << [row]
120
+ end
121
+
122
+ rows << [' ']
123
+ end
124
+
125
+ authors = Array(action.author || action.authors)
126
+ rows << ["Created by #{authors.join(', ').green}"] unless authors.empty?
127
+
128
+ puts(Terminal::Table.new(title: name.green, rows: PantographCore::PrintTable.transform_output(rows)))
129
+ puts("")
130
+ end
131
+
132
+ def self.print_options(action, name)
133
+ options = parse_options(action.available_options) if action.available_options
134
+
135
+ if options
136
+ puts(Terminal::Table.new(
137
+ title: "#{name} Options".green,
138
+ headings: ['Key', 'Description', 'Env Var', 'Default'],
139
+ rows: PantographCore::PrintTable.transform_output(options)
140
+ ))
141
+ else
142
+ puts("No available options".yellow)
143
+ end
144
+ puts("* = default value is dependent on the user's system")
145
+ puts("")
146
+ end
147
+
148
+ def self.print_output_variables(action, name)
149
+ output = action.output
150
+ return if output.nil? || output.empty?
151
+
152
+ puts(Terminal::Table.new(
153
+ title: "#{name} Output Variables".green,
154
+ headings: ['Key', 'Description'],
155
+ rows: PantographCore::PrintTable.transform_output(output.map { |key, desc| [key.yellow, desc] })
156
+ ))
157
+ puts("Access the output values using `lane_context[SharedValues::VARIABLE_NAME]`")
158
+ puts("")
159
+ end
160
+
161
+ def self.print_return_value(action, name)
162
+ return unless action.return_value
163
+
164
+ puts(Terminal::Table.new(title: "#{name} Return Value".green,
165
+ rows: PantographCore::PrintTable.transform_output([[action.return_value]])))
166
+ puts("")
167
+ end
168
+
169
+ # Iterates through all available actions and yields from there
170
+ def self.all_actions(platform = nil)
171
+ action_symbols = Pantograph::Actions.constants.select { |c| Pantograph::Actions.const_get(c).kind_of?(Class) && c != :TestSampleCodeAction }
172
+ action_symbols.sort.each do |symbol|
173
+ action = Pantograph::Actions.const_get(symbol)
174
+
175
+ # We allow classes that don't respond to is_supported? to come through because we want to list
176
+ # them as broken actions in the table, regardless of platform specification
177
+ next if platform && action.respond_to?(:is_supported?) && !action.is_supported?(platform.to_sym)
178
+
179
+ name = symbol.to_s.gsub('Action', '').pantograph_underscore
180
+ yield(action, name)
181
+ end
182
+ end
183
+
184
+ def self.find_action_named(name)
185
+ all_actions do |action, action_name|
186
+ return action if action_name == name
187
+ end
188
+
189
+ nil
190
+ end
191
+
192
+ # Helper:
193
+ def self.parse_options(options, fill_all = true)
194
+ rows = []
195
+ rows << [options] if options.kind_of?(String)
196
+
197
+ if options.kind_of?(Array)
198
+ options.each do |current|
199
+ if current.kind_of?(PantographCore::ConfigItem)
200
+ rows << [current.key.to_s.yellow, current.deprecated ? current.description.red : current.description, current.env_name, current.help_default_value]
201
+ elsif current.kind_of?(Array)
202
+ # Legacy actions that don't use the new config manager
203
+ UI.user_error!("Invalid number of elements in this row: #{current}. Must be 2 or 3") unless [2, 3].include?(current.count)
204
+ rows << current
205
+ rows.last[0] = rows.last.first.yellow # color it yellow :)
206
+ rows.last << nil while fill_all && rows.last.count < 4 # to have a nice border in the table
207
+ end
208
+ end
209
+ end
210
+
211
+ rows
212
+ end
213
+ end
214
+ end