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,89 @@
1
+ module Pantograph
2
+ module Actions
3
+ class TwitterAction < Action
4
+ def self.run(params)
5
+ Actions.verify_gem!("twitter")
6
+ require 'twitter'
7
+ client = Twitter::REST::Client.new do |config|
8
+ config.consumer_key = params[:consumer_key]
9
+ config.consumer_secret = params[:consumer_secret]
10
+ config.access_token = params[:access_token]
11
+ config.access_token_secret = params[:access_token_secret]
12
+ end
13
+ client.update(params[:message])
14
+ UI.message(['[TWITTER]', "Successfully tweeted ", params[:message]].join(': '))
15
+ end
16
+
17
+ #####################################################
18
+ # @!group Documentation
19
+ #####################################################
20
+
21
+ def self.description
22
+ "Post a tweet on [Twitter.com](https://twitter.com)"
23
+ end
24
+
25
+ def self.details
26
+ "Post a tweet on Twitter. Requires you to setup an app on [twitter.com](https://twitter.com) and obtain `consumer` and `access_token`."
27
+ end
28
+
29
+ def self.available_options
30
+ [
31
+ PantographCore::ConfigItem.new(key: :consumer_key,
32
+ env_name: "FL_TW_CONSUMER_KEY",
33
+ description: "Consumer Key",
34
+ sensitive: true,
35
+ is_string: true,
36
+ optional: false),
37
+ PantographCore::ConfigItem.new(key: :consumer_secret,
38
+ env_name: "FL_TW_CONSUMER_SECRET",
39
+ sensitive: true,
40
+ description: "Consumer Secret",
41
+ is_string: true,
42
+ optional: false),
43
+ PantographCore::ConfigItem.new(key: :access_token,
44
+ env_name: "FL_TW_ACCESS_TOKEN",
45
+ sensitive: true,
46
+ description: "Access Token",
47
+ is_string: true,
48
+ optional: false),
49
+ PantographCore::ConfigItem.new(key: :access_token_secret,
50
+ env_name: "FL_TW_ACCESS_TOKEN_SECRET",
51
+ sensitive: true,
52
+ description: "Access Token Secret",
53
+ is_string: true,
54
+ optional: false),
55
+ PantographCore::ConfigItem.new(key: :message,
56
+ env_name: "FL_TW_MESSAGE",
57
+ description: "The tweet",
58
+ is_string: true,
59
+ optional: false)
60
+
61
+ ]
62
+ end
63
+
64
+ def self.authors
65
+ ["hjanuschka"]
66
+ end
67
+
68
+ def self.is_supported?(platform)
69
+ true
70
+ end
71
+
72
+ def self.example_code
73
+ [
74
+ 'twitter(
75
+ access_token: "XXXX",
76
+ access_token_secret: "xxx",
77
+ consumer_key: "xxx",
78
+ consumer_secret: "xxx",
79
+ message: "You rock!"
80
+ )'
81
+ ]
82
+ end
83
+
84
+ def self.category
85
+ :notifications
86
+ end
87
+ end
88
+ end
89
+ end
@@ -0,0 +1,177 @@
1
+ require 'rubygems/spec_fetcher'
2
+ require 'rubygems/command_manager'
3
+
4
+ module Pantograph
5
+ module Actions
6
+ # Makes sure pantograph tools are up-to-date when running pantograph
7
+ class UpdatePantographAction < Action
8
+ ALL_TOOLS = ["pantograph"]
9
+
10
+ def self.run(options)
11
+ return if options[:no_update] # this is used to update itself
12
+
13
+ tools_to_update = options[:tools].split(',') unless options[:tools].nil?
14
+ tools_to_update ||= all_installed_tools
15
+
16
+ if tools_to_update.count == 0
17
+ UI.error("No tools specified or couldn't find any installed pantograph.tools")
18
+ return
19
+ end
20
+
21
+ UI.message("Looking for updates for #{tools_to_update.join(', ')}...")
22
+
23
+ updater = Gem::CommandManager.instance[:update]
24
+ updater.options[:prerelease] = true if options[:nightly]
25
+ cleaner = Gem::CommandManager.instance[:cleanup]
26
+
27
+ gem_dir = ENV['GEM_HOME'] || Gem.dir
28
+ sudo_needed = !File.writable?(gem_dir)
29
+
30
+ if sudo_needed
31
+ UI.important("It seems that your Gem directory is not writable by your current user.")
32
+ UI.important("pantograph would need sudo rights to update itself, however, running 'sudo pantograph' is not recommended.")
33
+ UI.important("If you still want to use this action, please read the documentation on how to set this up:")
34
+ UI.important("https://docs.pantograph.tools/actions/update_pantograph/")
35
+ return
36
+ end
37
+
38
+ unless updater.respond_to?(:highest_installed_gems)
39
+ UI.important("The update_pantograph action requires rubygems version 2.1.0 or greater.")
40
+ UI.important("Please update your version of ruby gems before proceeding.")
41
+ UI.command "gem install rubygems-update"
42
+ UI.command "update_rubygems"
43
+ UI.command "gem update --system"
44
+ return
45
+ end
46
+
47
+ highest_versions = updater.highest_installed_gems.keep_if { |key| tools_to_update.include?(key) }
48
+ update_needed = updater.which_to_update(highest_versions, tools_to_update)
49
+
50
+ if update_needed.count == 0
51
+ UI.success("Nothing to update ✅")
52
+ show_information_about_nightly_builds unless options[:nightly]
53
+ return
54
+ end
55
+
56
+ # suppress updater output - very noisy
57
+ Gem::DefaultUserInteraction.ui = Gem::SilentUI.new
58
+
59
+ update_needed.each do |tool_info|
60
+ tool = tool_info[0]
61
+ gem_version = tool_info[1]
62
+ local_version = Gem::Version.new(highest_versions[tool].version)
63
+ latest_official_version = PantographCore::UpdateChecker.fetch_latest(tool)
64
+
65
+ if options[:nightly]
66
+ UI.message("Updating #{tool} from #{local_version.to_s.yellow} to nightly build #{gem_version.to_s.yellow}... (last official release #{latest_official_version.to_s.yellow}) 🚀")
67
+ else
68
+ UI.message("Updating #{tool} from #{local_version.to_s.yellow} to #{latest_official_version.to_s.yellow}... 🚀")
69
+ end
70
+
71
+ # Approximate_recommendation will create a string like "~> 0.10" from a version 0.10.0, e.g. one that is valid for versions >= 0.10 and <1.0
72
+ requirement_version = options[:nightly] ? gem_version : local_version.approximate_recommendation
73
+ updater.update_gem(tool, Gem::Requirement.new(requirement_version))
74
+
75
+ UI.success("Finished updating #{tool}")
76
+ end
77
+
78
+ UI.message("Cleaning up old versions...")
79
+ cleaner.options[:args] = tools_to_update
80
+ cleaner.execute
81
+
82
+ if options[:nightly]
83
+ UI.success("Thanks for using pantograph's nightly builds! This makes it easier for everyone to detect regressions earlier.")
84
+ UI.success("Please submit an issue on GitHub if anything behaves differently than it should 🍪")
85
+ else
86
+ show_information_about_nightly_builds
87
+ end
88
+
89
+ UI.message("pantograph.tools successfully updated! I will now restart myself... 😴")
90
+
91
+ # Set no_update to true so we don't try to update again
92
+ exec("FL_NO_UPDATE=true #{$PROGRAM_NAME} #{ARGV.join(' ')}")
93
+ end
94
+
95
+ def self.show_information_about_nightly_builds
96
+ UI.message("")
97
+ UI.message("Please help us test early releases of pantograph by opting into nightly builds 🌃")
98
+ UI.message("Just replace your `update_pantograph` call with")
99
+ UI.message("")
100
+ UI.command_output("update_pantograph(nightly: true)")
101
+ UI.message("")
102
+ UI.message("Nightly builds are reviewed and tested just like the public releases 🚂")
103
+ UI.message("")
104
+ end
105
+
106
+ def self.all_installed_tools
107
+ Gem::Specification.select { |s| ALL_TOOLS.include?(s.name) }.map(&:name).uniq
108
+ end
109
+
110
+ def self.description
111
+ "Makes sure pantograph-tools are up-to-date when running pantograph"
112
+ end
113
+
114
+ def self.details
115
+ sample = <<-SAMPLE.markdown_sample
116
+ ```bash
117
+ export GEM_HOME=~/.gems
118
+ export PATH=$PATH:~/.gems/bin
119
+ ```
120
+ SAMPLE
121
+
122
+ [
123
+ "This action will update pantograph to the most recent version - major version updates will not be performed automatically, as they might include breaking changes. If an update was performed, pantograph will be restarted before the run continues.",
124
+ "",
125
+ "If you are using rbenv or rvm, everything should be good to go. However, if you are using the system's default ruby, some additional setup is needed for this action to work correctly. In short, pantograph needs to be able to access your gem library without running in `sudo` mode.",
126
+ "",
127
+ "The simplest possible fix for this is putting the following lines into your `~/.bashrc` or `~/.zshrc` file:".markdown_preserve_newlines,
128
+ sample,
129
+ "After the above changes, restart your terminal, then run `mkdir $GEM_HOME` to create the new gem directory. After this, you're good to go!",
130
+ "",
131
+ "Recommended usage of the `update_pantograph` action is at the top inside of the `before_all` block, before running any other action."
132
+ ].join("\n")
133
+ end
134
+
135
+ def self.available_options
136
+ [
137
+ PantographCore::ConfigItem.new(key: :nightly,
138
+ env_name: "FL_UPDATE_PANTOGRAPH_NIGHTLY",
139
+ description: "Opt-in to install and use nightly pantograph builds",
140
+ is_string: false,
141
+ default_value: false),
142
+ PantographCore::ConfigItem.new(key: :no_update,
143
+ env_name: "FL_NO_UPDATE",
144
+ description: "Don't update during this run. This is used internally",
145
+ is_string: false,
146
+ default_value: false),
147
+ PantographCore::ConfigItem.new(key: :tools,
148
+ env_name: "FL_TOOLS_TO_UPDATE",
149
+ description: "Comma separated list of pantograph tools to update (e.g. `pantograph,sigh`)",
150
+ deprecated: true,
151
+ optional: true)
152
+ ]
153
+ end
154
+
155
+ def self.authors
156
+ ["milch", "KrauseFx"]
157
+ end
158
+
159
+ def self.is_supported?(platform)
160
+ true
161
+ end
162
+
163
+ def self.example_code
164
+ [
165
+ 'before_all do
166
+ update_pantograph
167
+ # ...
168
+ end'
169
+ ]
170
+ end
171
+
172
+ def self.category
173
+ :misc
174
+ end
175
+ end
176
+ end
177
+ end
@@ -0,0 +1,120 @@
1
+ module Pantograph
2
+ module Actions
3
+ class ZipAction < Action
4
+ def self.run(params)
5
+ UI.message("Compressing #{params[:path]}...")
6
+
7
+ params[:output_path] ||= params[:path]
8
+
9
+ absolute_output_path = File.expand_path(params[:output_path])
10
+
11
+ # Appends ".zip" if path does not end in ".zip"
12
+ unless absolute_output_path.end_with?(".zip")
13
+ absolute_output_path += ".zip"
14
+ end
15
+
16
+ absolute_output_dir = File.expand_path("..", absolute_output_path)
17
+ FileUtils.mkdir_p(absolute_output_dir)
18
+
19
+ Dir.chdir(File.expand_path("..", params[:path])) do # required to properly zip
20
+ zip_options = params[:verbose] ? "r" : "rq"
21
+ zip_options += "y" if params[:symlinks]
22
+
23
+ if params[:password]
24
+ password_option = "-P '#{params[:password]}'"
25
+ Actions.sh("zip -#{zip_options} #{password_option} #{absolute_output_path.shellescape} #{File.basename(params[:path]).shellescape}")
26
+ else
27
+ Actions.sh("zip -#{zip_options} #{absolute_output_path.shellescape} #{File.basename(params[:path]).shellescape}")
28
+ end
29
+ end
30
+
31
+ UI.success("Successfully generated zip file at path '#{File.expand_path(absolute_output_path)}'")
32
+ return File.expand_path(absolute_output_path)
33
+ end
34
+
35
+ #####################################################
36
+ # @!group Documentation
37
+ #####################################################
38
+
39
+ def self.description
40
+ "Compress a file or folder to a zip"
41
+ end
42
+
43
+ def self.available_options
44
+ [
45
+ PantographCore::ConfigItem.new(key: :path,
46
+ env_name: "FL_ZIP_PATH",
47
+ description: "Path to the directory or file to be zipped",
48
+ verify_block: proc do |value|
49
+ UI.user_error!("Couldn't find file/folder at path '#{File.expand_path(value)}'") unless File.exist?(value)
50
+ end),
51
+ PantographCore::ConfigItem.new(key: :output_path,
52
+ env_name: "FL_ZIP_OUTPUT_NAME",
53
+ description: "The name of the resulting zip file",
54
+ optional: true),
55
+ PantographCore::ConfigItem.new(key: :verbose,
56
+ env_name: "FL_ZIP_VERBOSE",
57
+ description: "Enable verbose output of zipped file",
58
+ default_value: true,
59
+ type: Boolean,
60
+ optional: true),
61
+ PantographCore::ConfigItem.new(key: :password,
62
+ env_name: "FL_ZIP_PASSWORD",
63
+ description: "Encrypt the contents of the zip archive using a password",
64
+ optional: true),
65
+ PantographCore::ConfigItem.new(key: :symlinks,
66
+ env_name: "FL_ZIP_SYMLINKS",
67
+ description: "Store symbolic links as such in the zip archive",
68
+ optional: true,
69
+ type: Boolean,
70
+ default_value: false)
71
+ ]
72
+ end
73
+
74
+ def self.example_code
75
+ [
76
+ 'zip',
77
+ 'zip(
78
+ path: "MyApp.app",
79
+ output_path: "Latest.app.zip"
80
+ )',
81
+ 'zip(
82
+ path: "MyApp.app",
83
+ output_path: "Latest.app.zip",
84
+ verbose: false
85
+ )',
86
+ 'zip(
87
+ path: "MyApp.app",
88
+ output_path: "Latest.app.zip",
89
+ verbose: false,
90
+ symlinks: true
91
+ )'
92
+ ]
93
+ end
94
+
95
+ def self.category
96
+ :misc
97
+ end
98
+
99
+ def self.output
100
+ []
101
+ end
102
+
103
+ def self.return_value
104
+ "The path to the output zip file"
105
+ end
106
+
107
+ def self.return_type
108
+ :string
109
+ end
110
+
111
+ def self.authors
112
+ ["KrauseFx"]
113
+ end
114
+
115
+ def self.is_supported?(platform)
116
+ true
117
+ end
118
+ end
119
+ end
120
+ end
@@ -0,0 +1,82 @@
1
+ require 'fileutils'
2
+
3
+ module Pantograph
4
+ # Enable tab auto completion
5
+ class AutoComplete
6
+ # This method copies the tab auto completion scripts to the user's home folder,
7
+ # while optionally adding custom commands for which to enable auto complete
8
+ # @param [Array] options An array of all options (e.g. --custom fl)
9
+ def self.execute(args, options)
10
+ shell = ENV['SHELL']
11
+
12
+ if shell.end_with?("fish")
13
+ fish_completions_dir = "~/.config/fish/completions"
14
+
15
+ if UI.interactive?
16
+ confirm = UI.confirm("This will copy a fish script into #{fish_completions_dir} that provides the command tab completion. If the directory does not exist it will be created. Sound good?")
17
+ return unless confirm
18
+ end
19
+
20
+ fish_completions_dir = File.expand_path(fish_completions_dir)
21
+ FileUtils.mkdir_p(fish_completions_dir)
22
+
23
+ completion_script_path = File.join(Pantograph::ROOT, 'lib', 'assets', 'completions', 'completion.fish')
24
+ final_completion_script_path = File.join(fish_completions_dir, 'pantograph.fish')
25
+
26
+ FileUtils.cp(completion_script_path, final_completion_script_path)
27
+
28
+ UI.success("Copied! You can now use tab completion for lanes")
29
+ else
30
+ pantograph_conf_dir = "~/.pantograph"
31
+
32
+ if UI.interactive?
33
+ confirm = UI.confirm("This will copy a shell script into #{pantograph_conf_dir} that provides the command tab completion. Sound good?")
34
+ return unless confirm
35
+ end
36
+
37
+ # create the ~/.pantograph directory
38
+ pantograph_conf_dir = File.expand_path(pantograph_conf_dir)
39
+ FileUtils.mkdir_p(pantograph_conf_dir)
40
+
41
+ # then copy all of the completions files into it from the gem
42
+ completion_script_path = File.join(Pantograph::ROOT, 'lib', 'assets', 'completions')
43
+ FileUtils.cp_r(completion_script_path, pantograph_conf_dir)
44
+
45
+ custom_commands = options.custom.to_s.split(',')
46
+
47
+ Pantograph::SHELLS.each do |shell_name|
48
+ open("#{pantograph_conf_dir}/completions/completion.#{shell_name}", 'a') do |file|
49
+ default_line_prefix = Helper.bundler? ? "bundle exec " : ""
50
+
51
+ file.puts(self.get_auto_complete_line(shell_name, "#{default_line_prefix}pantograph"))
52
+
53
+ custom_commands.each do |command|
54
+ auto_complete_line = self.get_auto_complete_line(shell_name, command)
55
+
56
+ next if auto_complete_line.nil?
57
+
58
+ file.puts(auto_complete_line)
59
+ end
60
+ end
61
+ end
62
+
63
+ UI.success("Copied! To use auto complete for pantograph, add the following line to your favorite rc file (e.g. ~/.bashrc)")
64
+ UI.important(" . ~/.pantograph/completions/completion.sh")
65
+ UI.success("Don't forget to source that file in your current shell! 🐚")
66
+ end
67
+ end
68
+
69
+ # Helper to get the auto complete register script line
70
+ def self.get_auto_complete_line(shell, command)
71
+ if shell == :bash
72
+ prefix = "complete -F"
73
+ elsif shell == :zsh
74
+ prefix = "compctl -K"
75
+ else
76
+ return nil
77
+ end
78
+
79
+ return "#{prefix} _pantograph_complete #{command}"
80
+ end
81
+ end
82
+ end
@@ -0,0 +1,5 @@
1
+ module Pantograph
2
+ class Boolean
3
+ # Used in config item generation
4
+ end
5
+ end
@@ -0,0 +1,183 @@
1
+ module Pantograph
2
+ # This class is responsible for checking the ARGV
3
+ # to see if the user wants to launch another pantograph
4
+ # tool or pantograph itself
5
+ class CLIToolsDistributor
6
+ class << self
7
+ def running_version_command?
8
+ ARGV.include?('-v') || ARGV.include?('--version')
9
+ end
10
+
11
+ def running_help_command?
12
+ ARGV.include?('-h') || ARGV.include?('--help')
13
+ end
14
+
15
+ def running_init_command?
16
+ ARGV.include?("init")
17
+ end
18
+
19
+ def utf8_locale?
20
+ (ENV['LANG'] || "").end_with?("UTF-8", "utf8") || (ENV['LC_ALL'] || "").end_with?("UTF-8", "utf8") || (PantographCore::CommandExecutor.which('locale') && `locale charmap`.strip == "UTF-8")
21
+ end
22
+
23
+ def take_off
24
+ before_import_time = Time.now
25
+
26
+ if !ENV["PANTOGRAPH_DISABLE_ANIMATION"]
27
+ # Usually in the pantograph code base we use
28
+ #
29
+ # Helper.show_loading_indicator
30
+ # longer_taking_task_here
31
+ # Helper.hide_loading_indicator
32
+ #
33
+ # but in this case we haven't required PantographCore yet
34
+ # so we'll have to access the raw API for now
35
+ require "tty-spinner"
36
+ require_pantograph_spinner = TTY::Spinner.new("[:spinner] 🚀 ", format: :dots)
37
+ require_pantograph_spinner.auto_spin
38
+
39
+ # this might take a long time if there is no Gemfile :(
40
+ # That's why we show the loading indicator here also
41
+ require "pantograph"
42
+
43
+ require_pantograph_spinner.success
44
+ else
45
+ require "pantograph"
46
+ end
47
+ # We want to avoid printing output other than the version number if we are running `pantograph -v`
48
+ unless running_version_command? || running_init_command?
49
+ print_bundle_exec_warning(is_slow: (Time.now - before_import_time > 3))
50
+ end
51
+
52
+ # Try to check UTF-8 with `locale`, fallback to environment variables
53
+ unless utf8_locale?
54
+ warn = "WARNING: pantograph requires your locale to be set to UTF-8. To learn more go to https://docs.pantograph.tools/getting-started/ios/setup/#set-up-environment-variables"
55
+ UI.error(warn)
56
+ at_exit do
57
+ # Repeat warning here so users hopefully see it
58
+ UI.error(warn)
59
+ end
60
+ end
61
+
62
+ # Loading any .env files before any lanes are called since
63
+ # variables like PANTOGRAPH_HIDE_CHANGELOG and PANTOGRAPH_DISABLE_COLORS
64
+ # need to be set early on in execution
65
+ require 'pantograph/helper/dotenv_helper'
66
+ Pantograph::Helper::DotenvHelper.load_dot_env(nil)
67
+
68
+ # Needs to go after load_dot_env for variable PANTOGRAPH_SKIP_UPDATE_CHECK
69
+ PantographCore::UpdateChecker.start_looking_for_update('pantograph')
70
+
71
+ # Disabling colors if environment variable set
72
+ require 'pantograph_core/ui/disable_colors' if PantographCore::Helper.colors_disabled?
73
+
74
+ tool_name = ARGV.first ? ARGV.first.downcase : nil
75
+
76
+ tool_name = process_emojis(tool_name)
77
+
78
+ if tool_name && Pantograph::TOOLS.include?(tool_name.to_sym) && !available_lanes.include?(tool_name.to_sym)
79
+ # Triggering a specific tool
80
+ # This happens when the users uses things like
81
+ #
82
+ # pantograph sigh
83
+ #
84
+ require tool_name
85
+ begin
86
+ # First, remove the tool's name from the arguments
87
+ # Since it will be parsed by the `commander` at a later point
88
+ # and it must not contain the binary name
89
+ ARGV.shift
90
+
91
+ # Import the CommandsGenerator class, which is used to parse
92
+ # the user input
93
+ require File.join(tool_name, "commands_generator")
94
+
95
+ # Call the tool's CommandsGenerator class and let it do its thing
96
+ commands_generator = Object.const_get(tool_name.pantograph_module)::CommandsGenerator
97
+ rescue LoadError
98
+ # This will only happen if the tool we call here, doesn't provide
99
+ # a CommandsGenerator class yet
100
+ # When we launch this feature, this should never be the case
101
+ abort("#{tool_name} can't be called via `pantograph #{tool_name}`, run '#{tool_name}' directly instead".red)
102
+ end
103
+
104
+ # Some of the tools use other actions so need to load all
105
+ # actions before we start the tool generator
106
+ # Example: scan uses slack
107
+ Pantograph.load_actions
108
+
109
+ commands_generator.start
110
+ # elsif tool_name == "pantograph-credentials"
111
+ # require 'credentials_manager'
112
+ # ARGV.shift
113
+ # CredentialsManager::CLI.new.run
114
+ else
115
+ # Triggering pantograph to call a lane
116
+ require "pantograph/commands_generator"
117
+ Pantograph::CommandsGenerator.start
118
+ end
119
+ ensure
120
+ # PantographCore::UpdateChecker.show_update_status('pantograph', Pantograph::VERSION)
121
+ end
122
+
123
+ # Since pantograph also supports the rocket and biceps emoji as executable
124
+ # we need to map those to the appropriate tools
125
+ def process_emojis(tool_name)
126
+ return {
127
+ "🚀" => "pantograph",
128
+ "💪" => "gym"
129
+ }[tool_name] || tool_name
130
+ end
131
+
132
+ def print_bundle_exec_warning(is_slow: false)
133
+ return if PantographCore::Helper.bundler? # user is alread using bundler
134
+ return if PantographCore::Env.truthy?('SKIP_SLOW_PANTOGRAPH_WARNING') # user disabled the warnings
135
+ return if PantographCore::Helper.contained_pantograph? # user uses the bundled pantograph
136
+
137
+ gemfile_path = PluginManager.new.gemfile_path
138
+ if gemfile_path
139
+ # The user has a Gemfile, but forgot to use `bundle exec`
140
+ # Let's tell the user how to use `bundle exec`
141
+ # We show this warning no matter if the command is slow or not
142
+ UI.important("pantograph detected a Gemfile in the current directory")
143
+ UI.important("however it seems like you don't use `bundle exec`")
144
+ UI.important("to launch pantograph faster, please use")
145
+ UI.message("")
146
+ UI.command "bundle exec pantograph #{ARGV.join(' ')}"
147
+ UI.message("")
148
+ elsif is_slow
149
+ # pantograph is slow and there is no Gemfile
150
+ # Let's tell the user how to use `gem cleanup` and how to
151
+ # start using a Gemfile
152
+ UI.important('Seems like launching pantograph takes a while - please run')
153
+ UI.message('')
154
+ UI.command('gem cleanup')
155
+ UI.message('')
156
+ UI.important('to uninstall outdated gems and make pantograph launch faster')
157
+ UI.important('Alternatively it is recommended to start using a Gemfile to lock your dependencies')
158
+ UI.important('To get started with a Gemfile, run')
159
+ UI.message('')
160
+ UI.command 'bundle init'
161
+ UI.command "echo 'gem \"pantograph\"' >> Gemfile"
162
+ UI.command 'bundle install'
163
+ UI.message('')
164
+ UI.important('After creating the Gemfile and Gemfile.lock, commit those files into version control')
165
+ end
166
+ UI.important('Get started using a Gemfile for pantograph https://docs.pantograph.tools/getting-started/ios/setup/#use-a-gemfile')
167
+ end
168
+
169
+ # Returns an array of symbols for the available lanes for the Pantfile
170
+ # This doesn't actually use the Pantfile parser, but only
171
+ # the available lanes. This way it's much faster, which
172
+ # is very important in this case, since it will be executed
173
+ # every time one of the tools is launched
174
+ # Use this only if performance is :key:
175
+ def available_lanes
176
+ pantfile_path = PantographCore::PantographFolder.pantfile_path
177
+ return [] if pantfile_path.nil?
178
+ output = `cat #{pantfile_path.shellescape} | grep \"^\s*lane \:\" | awk -F ':' '{print $2}' | awk -F ' ' '{print $1}'`
179
+ return output.strip.split(" ").collect(&:to_sym)
180
+ end
181
+ end
182
+ end
183
+ end