hem 1.0.1.beta1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.editorconfig +10 -0
- data/.gitignore +3 -0
- data/.rspec +2 -0
- data/CHANGELOG.md +125 -0
- data/DoD.md +5 -0
- data/Gemfile +4 -0
- data/Gemfile.lock +71 -0
- data/Guardfile +14 -0
- data/Hemfile +43 -0
- data/LICENSE +21 -0
- data/README.md +42 -0
- data/Rakefile +23 -0
- data/bin/hem +64 -0
- data/features/deps.feature +43 -0
- data/features/hem/basic.feature +43 -0
- data/features/hem/help.feature +16 -0
- data/features/hem/subcommands.feature +15 -0
- data/features/seed/plant.feature +64 -0
- data/features/step_definitions/env.rb +6 -0
- data/features/step_definitions/seed.rb +11 -0
- data/features/support/env.rb +6 -0
- data/hem.gemspec +47 -0
- data/lib/hem/asset_applicator.rb +33 -0
- data/lib/hem/asset_applicators/files.rb +5 -0
- data/lib/hem/asset_applicators/sqldump.rb +38 -0
- data/lib/hem/cli.rb +252 -0
- data/lib/hem/config/file.rb +22 -0
- data/lib/hem/config.rb +5 -0
- data/lib/hem/error_handlers/debug.rb +12 -0
- data/lib/hem/error_handlers/exit_code_map.rb +17 -0
- data/lib/hem/error_handlers/friendly.rb +58 -0
- data/lib/hem/errors.rb +89 -0
- data/lib/hem/help_formatter.rb +118 -0
- data/lib/hem/helper/file_locator.rb +44 -0
- data/lib/hem/helper/github.rb +10 -0
- data/lib/hem/helper/http_download.rb +41 -0
- data/lib/hem/helper/shell.rb +101 -0
- data/lib/hem/helper/vm_command.rb +30 -0
- data/lib/hem/lib/github/api.rb +48 -0
- data/lib/hem/lib/github/client.rb +52 -0
- data/lib/hem/lib/host_check/deps.rb +39 -0
- data/lib/hem/lib/host_check/git.rb +76 -0
- data/lib/hem/lib/host_check/ruby.rb +53 -0
- data/lib/hem/lib/host_check/vagrant.rb +45 -0
- data/lib/hem/lib/host_check.rb +34 -0
- data/lib/hem/lib/s3/local/file.rb +40 -0
- data/lib/hem/lib/s3/local/iohandler.rb +36 -0
- data/lib/hem/lib/s3/remote/file.rb +57 -0
- data/lib/hem/lib/s3/remote/iohandler.rb +38 -0
- data/lib/hem/lib/s3/sync.rb +134 -0
- data/lib/hem/lib/seed/project.rb +71 -0
- data/lib/hem/lib/seed/replacer.rb +56 -0
- data/lib/hem/lib/seed/seed.rb +111 -0
- data/lib/hem/lib/self_signed_cert_generator.rb +38 -0
- data/lib/hem/lib/vm/command.rb +131 -0
- data/lib/hem/lib/vm/inspector.rb +73 -0
- data/lib/hem/logging.rb +20 -0
- data/lib/hem/metadata.rb +42 -0
- data/lib/hem/null.rb +31 -0
- data/lib/hem/patches/deepstruct.rb +21 -0
- data/lib/hem/patches/rake.rb +101 -0
- data/lib/hem/patches/rubygems.rb +6 -0
- data/lib/hem/patches/slop.rb +69 -0
- data/lib/hem/paths.rb +96 -0
- data/lib/hem/tasks/assets.rb +92 -0
- data/lib/hem/tasks/config.rb +15 -0
- data/lib/hem/tasks/deps.rb +103 -0
- data/lib/hem/tasks/exec.rb +3 -0
- data/lib/hem/tasks/magento.rb +281 -0
- data/lib/hem/tasks/ops.rb +6 -0
- data/lib/hem/tasks/pr.rb +45 -0
- data/lib/hem/tasks/seed.rb +61 -0
- data/lib/hem/tasks/self.rb +45 -0
- data/lib/hem/tasks/shell_init.rb +25 -0
- data/lib/hem/tasks/system/completions.rb +76 -0
- data/lib/hem/tasks/system.rb +18 -0
- data/lib/hem/tasks/tools.rb +17 -0
- data/lib/hem/tasks/vm.rb +140 -0
- data/lib/hem/ui.rb +182 -0
- data/lib/hem/util.rb +76 -0
- data/lib/hem/version.rb +3 -0
- data/lib/hem.rb +72 -0
- data/lib/hobo/tasks/magento.rb +3 -0
- data/spec/hem/asset_applicator_spec.rb +30 -0
- data/spec/hem/cli_spec.rb +166 -0
- data/spec/hem/config/file_spec.rb +55 -0
- data/spec/hem/error_handlers/debug_spec.rb +43 -0
- data/spec/hem/error_handlers/friendly_spec.rb +97 -0
- data/spec/hem/error_spec.rb +0 -0
- data/spec/hem/help_formatter_spec.rb +162 -0
- data/spec/hem/helpers/file_locator_spec.rb +11 -0
- data/spec/hem/helpers/github_spec.rb +31 -0
- data/spec/hem/helpers/shell_spec.rb +22 -0
- data/spec/hem/helpers/vm_command_spec.rb +96 -0
- data/spec/hem/lib/github/api_spec.rb +92 -0
- data/spec/hem/lib/s3/sync_spec.rb +16 -0
- data/spec/hem/lib/seed/project_spec.rb +80 -0
- data/spec/hem/lib/seed/replacer_spec.rb +45 -0
- data/spec/hem/lib/seed/seed_spec.rb +127 -0
- data/spec/hem/logging_spec.rb +27 -0
- data/spec/hem/metadata_spec.rb +55 -0
- data/spec/hem/null_spec.rb +30 -0
- data/spec/hem/patches/rake_spec.rb +230 -0
- data/spec/hem/paths_spec.rb +75 -0
- data/spec/hem/ui_spec.rb +189 -0
- data/spec/hem/util_spec.rb +74 -0
- data/spec/spec_helper.rb +12 -0
- data/ssl/ca-bundle-s3.crt +3554 -0
- data/test_files/vagrant_fail/vagrant +2 -0
- metadata +339 -0
@@ -0,0 +1,103 @@
|
|
1
|
+
desc "Dependency related tasks"
|
2
|
+
hidden true
|
3
|
+
namespace :deps do
|
4
|
+
|
5
|
+
desc "Install Gem dependencies"
|
6
|
+
task :gems do
|
7
|
+
locate "*Gemfile" do
|
8
|
+
required = shell("bundle", "check", :exit_status => true) != 0
|
9
|
+
if required
|
10
|
+
Hem.ui.title "Installing Gem dependencies"
|
11
|
+
shell "bundle", "install", realtime: true, indent: 2
|
12
|
+
Hem.ui.separator
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
desc "Install composer dependencies"
|
18
|
+
task :composer do
|
19
|
+
if File.exists? File.join(Hem.project_path, "composer.json")
|
20
|
+
Rake::Task["tools:composer"].invoke
|
21
|
+
Hem.ui.title "Installing composer dependencies"
|
22
|
+
Dir.chdir Hem.project_path do
|
23
|
+
ansi = Hem.ui.supports_color? ? '--ansi' : ''
|
24
|
+
args = [ "php bin/composer.phar install #{ansi} --prefer-dist", { realtime: true, indent: 2 } ]
|
25
|
+
complete = false
|
26
|
+
|
27
|
+
unless maybe(Hem.project_config.tasks.deps.composer.disable_host_run)
|
28
|
+
check = Hem::Lib::HostCheck.check(:filter => /php_present/)
|
29
|
+
|
30
|
+
if check[:php_present] == :ok
|
31
|
+
begin
|
32
|
+
shell *args
|
33
|
+
complete = true
|
34
|
+
rescue Hem::ExternalCommandError
|
35
|
+
Hem.ui.warning "Installing composer dependencies locally failed!"
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
if !complete
|
41
|
+
vm_shell *args
|
42
|
+
end
|
43
|
+
|
44
|
+
Hem.ui.success "Composer dependencies installed"
|
45
|
+
end
|
46
|
+
|
47
|
+
Hem.ui.separator
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
desc "Install vagrant plugins"
|
52
|
+
task :vagrant_plugins => [ "deps:gems" ] do
|
53
|
+
plugins = shell "vagrant plugin list", :capture => true
|
54
|
+
locate "*Vagrantfile" do
|
55
|
+
to_install = []
|
56
|
+
File.read("Vagrantfile").split("\n").each do |line|
|
57
|
+
if line.match /#\s*Hem.vagrant_plugin (.*)/ or line.match /#\s*Hobo.vagrant_plugin (.*)/
|
58
|
+
to_install << $1
|
59
|
+
else
|
60
|
+
next if line.match /^\s*#/
|
61
|
+
next unless line.match /Vagrant\.require_plugin (.*)/
|
62
|
+
to_install << $1
|
63
|
+
end
|
64
|
+
end
|
65
|
+
|
66
|
+
to_install.each do |plugin|
|
67
|
+
plugin.gsub!(/['"]*/, '')
|
68
|
+
next if plugins.include? "#{plugin} "
|
69
|
+
Hem.ui.title "Installing vagrant plugin: #{plugin}"
|
70
|
+
shell "vagrant", "plugin", "install", plugin, :realtime => true, :indent => 2
|
71
|
+
Hem.ui.separator
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
75
|
+
|
76
|
+
desc "Install chef dependencies"
|
77
|
+
task :chef => [ "deps:gems" ] do
|
78
|
+
locate "*Cheffile" do
|
79
|
+
Hem.ui.title "Installing chef dependencies via librarian"
|
80
|
+
bundle_shell "librarian-chef", "install", "--verbose", :realtime => true, :indent => 2 do |line|
|
81
|
+
line =~ /Installing.*</ ? line.strip + "\n" : nil
|
82
|
+
end
|
83
|
+
Hem.ui.separator
|
84
|
+
end
|
85
|
+
|
86
|
+
locate "*Berksfile" do
|
87
|
+
Hem.ui.title "Installing chef dependencies via berkshelf"
|
88
|
+
executor = (shell("bash -c 'which berks'", :capture => true).strip =~ /chefdk/) ?
|
89
|
+
lambda { |*args| shell *args } :
|
90
|
+
lambda { |*args| bundle_shell *args }
|
91
|
+
|
92
|
+
executor.call "berks", "install", :realtime => true, :indent => 2
|
93
|
+
version = executor.call "berks", "-v", :capture => true
|
94
|
+
if version =~ /^[3-9]/
|
95
|
+
shell "rm -rf cookbooks"
|
96
|
+
executor.call "berks", "vendor", "cookbooks"
|
97
|
+
else
|
98
|
+
executor.call "berks", "install", "--path", "cookbooks"
|
99
|
+
end
|
100
|
+
Hem.ui.separator
|
101
|
+
end
|
102
|
+
end
|
103
|
+
end
|
@@ -0,0 +1,281 @@
|
|
1
|
+
namespace :tools do
|
2
|
+
desc "Fetches the n98-magerun utility"
|
3
|
+
task :n98magerun do
|
4
|
+
FileUtils.mkdir_p "bin"
|
5
|
+
vm_shell '"wget" --no-check-certificate "https://raw.github.com/netz98/n98-magerun/master/n98-magerun.phar" -O bin/n98-magerun.phar'
|
6
|
+
FileUtils.chmod 0755, "bin/n98-magerun.phar"
|
7
|
+
end
|
8
|
+
end
|
9
|
+
|
10
|
+
desc "Magento related tasks"
|
11
|
+
namespace :magento do
|
12
|
+
|
13
|
+
desc "Patch tasks"
|
14
|
+
namespace :patches do
|
15
|
+
def magento_path
|
16
|
+
unless @magento_path
|
17
|
+
files = locate('*app/Mage.php')
|
18
|
+
unless files.length > 0
|
19
|
+
raise Hem::UserError.new "Could not find app/Mage.php in the git repository, this command should only be run for Magento projects"
|
20
|
+
end
|
21
|
+
|
22
|
+
/(?:(.*)\/)app\/Mage\.php/.match(files[0])
|
23
|
+
@magento_path = $1
|
24
|
+
end
|
25
|
+
@magento_path
|
26
|
+
end
|
27
|
+
|
28
|
+
def detect_clean
|
29
|
+
status = shell('git status -z', :capture => true, :strip => false)
|
30
|
+
status.split("\u0000").each do |line|
|
31
|
+
match = line.match(/^([\s\S]{2})\s+(.*)$/)
|
32
|
+
next if match.nil?
|
33
|
+
|
34
|
+
if ![' ', '?'].include?($1[0]) || $2.start_with?(magento_path)
|
35
|
+
raise Hem::UserError.new "Please remove all files from the git index, and stash all changes in '#{magento_path}' before continuing"
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
def detect_version
|
41
|
+
config_dirty = false
|
42
|
+
magento_version_file = "#{magento_path}/app/Mage.php"
|
43
|
+
|
44
|
+
if Hem.project_config[:magento_edition].nil?
|
45
|
+
magento_edition = nil
|
46
|
+
if magento_version_file
|
47
|
+
args = [ "php -r \"require '#{magento_version_file}'; echo Mage::getEdition();\""]
|
48
|
+
|
49
|
+
magento_edition = vm_shell(*args, :capture => true).to_s.downcase
|
50
|
+
end
|
51
|
+
|
52
|
+
edition_options = ['community', 'enterprise', 'professional', 'go']
|
53
|
+
|
54
|
+
unless edition_options.include? magento_edition
|
55
|
+
raise Hem::Error.new "Invalid Magento edition '#{magento_edition}' was found when calling Mage::getEdition(), skipping patches"
|
56
|
+
end
|
57
|
+
|
58
|
+
Hem.project_config[:magento_edition] = magento_edition
|
59
|
+
config_dirty = true
|
60
|
+
end
|
61
|
+
|
62
|
+
if Hem.project_config[:magento_version].nil?
|
63
|
+
magento_version = nil
|
64
|
+
if magento_version_file
|
65
|
+
args = [ "php -r \"require '#{magento_version_file}'; echo Mage::getVersion();\""]
|
66
|
+
|
67
|
+
magento_version = vm_shell(*args, :capture => true)
|
68
|
+
end
|
69
|
+
|
70
|
+
version_regex = /^\d+(\.\d+){3}$/
|
71
|
+
|
72
|
+
unless version_regex.match(magento_version)
|
73
|
+
raise Hem::Error.new "Invalid Magento version '#{magento_version}' was found when calling Mage::getVersion(), skipping patches"
|
74
|
+
end
|
75
|
+
|
76
|
+
Hem.project_config[:magento_version] = magento_version
|
77
|
+
config_dirty = true
|
78
|
+
end
|
79
|
+
|
80
|
+
if config_dirty
|
81
|
+
Hem::Config::File.save(Hem.project_config_file, Hem.project_config)
|
82
|
+
end
|
83
|
+
end
|
84
|
+
|
85
|
+
def detect_tools
|
86
|
+
use_vm = shell("which which", :exit_status => true) != 0
|
87
|
+
|
88
|
+
tools = ['patch', 'sed']
|
89
|
+
tools_command = tools.map {|tool| "which #{tool}"}.join " && "
|
90
|
+
status = 0
|
91
|
+
|
92
|
+
unless use_vm
|
93
|
+
status = shell(tools_command, :exit_status => true)
|
94
|
+
use_vm = status != 0
|
95
|
+
end
|
96
|
+
|
97
|
+
if use_vm
|
98
|
+
status = vm_shell(tools_command, :exit_status => true)
|
99
|
+
end
|
100
|
+
|
101
|
+
if status != 0
|
102
|
+
raise Hem::UserError.new "Please make sure '#{tools.join(',')}' is installed on your host or VM before continuing"
|
103
|
+
end
|
104
|
+
|
105
|
+
use_vm
|
106
|
+
end
|
107
|
+
|
108
|
+
desc "Apply patches to Magento"
|
109
|
+
task "apply" do
|
110
|
+
detect_clean
|
111
|
+
detect_version
|
112
|
+
|
113
|
+
config = Hem.project_config
|
114
|
+
|
115
|
+
sync = Hem::Lib::S3::Sync.new(Hem.aws_credentials)
|
116
|
+
|
117
|
+
patches_path = "#{Hem.project_path}/tools/patches"
|
118
|
+
incoming_path = "#{patches_path}/incoming"
|
119
|
+
|
120
|
+
Hem.ui.success("Downloading Magento #{config[:magento_edition].capitalize} #{config[:magento_version]} patches")
|
121
|
+
changes = sync.sync(
|
122
|
+
"s3://inviqa-assets-magento/#{config[:magento_edition]}/patches/#{config[:magento_version]}/",
|
123
|
+
"#{incoming_path}/",
|
124
|
+
:delete => false
|
125
|
+
)
|
126
|
+
Hem.ui.separator
|
127
|
+
|
128
|
+
use_vm = false
|
129
|
+
use_vm = detect_tools if Dir.glob("#{incoming_path}/*.sh").length > 0
|
130
|
+
|
131
|
+
patch_files = Dir.glob("#{incoming_path}/*.{sh,patch,diff}")
|
132
|
+
|
133
|
+
Hem.ui.success("#{patch_files.length} new patches found")
|
134
|
+
|
135
|
+
Hem.ui.separator
|
136
|
+
|
137
|
+
patch_files.each do |file|
|
138
|
+
filename = File.basename(file)
|
139
|
+
base_filename = File.basename(filename, File.extname(filename))
|
140
|
+
|
141
|
+
if File.exist?("#{patches_path}/#{filename}")
|
142
|
+
Hem.ui.debug("Patch #{filename} has already been applied, so skipping it")
|
143
|
+
|
144
|
+
File.delete file
|
145
|
+
next
|
146
|
+
end
|
147
|
+
|
148
|
+
if File.exist?("#{patches_path}/#{base_filename}.skip")
|
149
|
+
File.delete file
|
150
|
+
next
|
151
|
+
end
|
152
|
+
|
153
|
+
Hem.ui.success("Applying patch #{filename}")
|
154
|
+
|
155
|
+
yaml_file = File.join(File.dirname(file), base_filename + ".yaml")
|
156
|
+
|
157
|
+
metadata = {
|
158
|
+
'commit_message' => "Apply Magento patch #{filename}"
|
159
|
+
}
|
160
|
+
if File.exist?(yaml_file)
|
161
|
+
metadata = Hem::Config::File.load(yaml_file)
|
162
|
+
end
|
163
|
+
|
164
|
+
Hem.ui.info(metadata['description']) unless metadata['description'].nil?
|
165
|
+
|
166
|
+
patch_options = %w( yes never skip )
|
167
|
+
answer = Hem.ui.ask_choice('Do you want to apply this patch?', patch_options)
|
168
|
+
|
169
|
+
if answer == 'skip'
|
170
|
+
next
|
171
|
+
end
|
172
|
+
|
173
|
+
if answer == 'never'
|
174
|
+
File.delete file
|
175
|
+
File.write("#{patches_path}/#{base_filename}.skip", '')
|
176
|
+
|
177
|
+
shell "git add '#{patches_path}/#{base_filename}.skip'"
|
178
|
+
shell "git commit -m 'Add a skip file for patch #{filename}'"
|
179
|
+
next
|
180
|
+
end
|
181
|
+
|
182
|
+
if /\.sh$/.match(file)
|
183
|
+
File.rename file, "#{magento_path}/#{filename}"
|
184
|
+
file = "#{magento_path}/#{filename}"
|
185
|
+
if use_vm
|
186
|
+
vm_shell "cd #{magento_path} && sh #{filename}", :realtime => true, :indent => 2
|
187
|
+
else
|
188
|
+
shell "cd #{magento_path} && sh #{filename}", :realtime => true, :indent => 2
|
189
|
+
end
|
190
|
+
else
|
191
|
+
shell "git apply --directory #{magento_path} #{file}"
|
192
|
+
end
|
193
|
+
File.rename file, "#{patches_path}/#{filename}"
|
194
|
+
shell "git add #{magento_path}"
|
195
|
+
shell "git add #{patches_path}/#{filename}"
|
196
|
+
|
197
|
+
if File.exist?(yaml_file)
|
198
|
+
yaml_filename = File.basename(yaml_file)
|
199
|
+
File.rename yaml_file, "#{patches_path}/#{yaml_filename}"
|
200
|
+
shell "git add #{patches_path}/#{yaml_filename}"
|
201
|
+
end
|
202
|
+
shell "git commit -m #{metadata['commit_message'].shellescape}"
|
203
|
+
|
204
|
+
Hem.ui.separator
|
205
|
+
end
|
206
|
+
|
207
|
+
Hem.ui.success("Finished applying #{patch_files.length} patches")
|
208
|
+
end
|
209
|
+
end
|
210
|
+
|
211
|
+
desc "Setup script tasks"
|
212
|
+
namespace :'setup-scripts' do
|
213
|
+
desc "Run magento setup scripts"
|
214
|
+
task :run => ['tools:n98magerun'] do
|
215
|
+
Hem.ui.success "Running setup scripts"
|
216
|
+
vm_shell("bin/n98-magerun.phar cache:clean config", :realtime => true, :indent => 2)
|
217
|
+
vm_shell("bin/n98-magerun.phar sys:setup:incremental -n", :realtime => true, :indent => 2)
|
218
|
+
Hem.ui.separator
|
219
|
+
end
|
220
|
+
end
|
221
|
+
|
222
|
+
desc "Cache tasks"
|
223
|
+
namespace :cache do
|
224
|
+
desc "Clear cache"
|
225
|
+
task :clear => ['tools:n98magerun'] do
|
226
|
+
Hem.ui.success "Clearing magento cache"
|
227
|
+
vm_shell("bin/n98-magerun.phar cache:flush", :realtime => true, :indent => 2)
|
228
|
+
Hem.ui.separator
|
229
|
+
end
|
230
|
+
end
|
231
|
+
|
232
|
+
desc "Configuration related tasks"
|
233
|
+
namespace :config do
|
234
|
+
desc "Configure magento base URLs"
|
235
|
+
task :'configure-urls' => ['tools:n98magerun'] do
|
236
|
+
Hem.ui.success "Configuring magento base urls"
|
237
|
+
domain = Hem.project_config.hostname
|
238
|
+
vm_shell("bin/n98-magerun.phar config:set web/unsecure/base_url 'http://#{domain}/'", :realtime => true, :indent => 2)
|
239
|
+
vm_shell("bin/n98-magerun.phar config:set web/secure/base_url 'https://#{domain}/'", :realtime => true, :indent => 2)
|
240
|
+
Hem.ui.separator
|
241
|
+
end
|
242
|
+
|
243
|
+
desc "Enable magento errors"
|
244
|
+
task :'enable-errors' do
|
245
|
+
error_config = File.join(Hem.project_path, 'public/errors/local.xml')
|
246
|
+
|
247
|
+
FileUtils.cp(
|
248
|
+
error_config + ".sample",
|
249
|
+
error_config
|
250
|
+
) unless File.exists? error_config
|
251
|
+
end
|
252
|
+
|
253
|
+
desc "Create admin user"
|
254
|
+
task :'create-admin-user' do
|
255
|
+
initialized = vm_shell("bin/n98-magerun.phar admin:user:list | grep admin", :exit_status => true) == 0
|
256
|
+
unless initialized
|
257
|
+
Hem.ui.success "Creating admin user"
|
258
|
+
vm_shell("bin/n98-magerun.phar admin:user:create admin '' admin admin admin", :realtime => true, :indent => 2)
|
259
|
+
Hem.ui.separator
|
260
|
+
end
|
261
|
+
end
|
262
|
+
|
263
|
+
desc "Enable rewrites"
|
264
|
+
task :'enable-rewrites' do
|
265
|
+
Hem.ui.success "Enabling rewrites"
|
266
|
+
vm_shell("bin/n98-magerun.phar config:set web/seo/use_rewrites 1", :realtime => true, :indent => 2)
|
267
|
+
Hem.ui.separator
|
268
|
+
end
|
269
|
+
end
|
270
|
+
|
271
|
+
desc "Initializes magento specifics on the virtual machine after a fresh build"
|
272
|
+
task :'initialize-vm' => [
|
273
|
+
'magento:config:enable-errors',
|
274
|
+
'tools:n98magerun',
|
275
|
+
'magento:setup-scripts:run',
|
276
|
+
'magento:config:configure-urls',
|
277
|
+
'magento:config:create-admin-user',
|
278
|
+
'magento:config:enable-rewrites',
|
279
|
+
'magento:cache:clear'
|
280
|
+
]
|
281
|
+
end
|
data/lib/hem/tasks/pr.rb
ADDED
@@ -0,0 +1,45 @@
|
|
1
|
+
desc 'Perform pull request operations'
|
2
|
+
namespace :pr do
|
3
|
+
desc 'Create a new pull request'
|
4
|
+
task :create do
|
5
|
+
source_branch = Hem.ui.ask 'Source branch', default: (Hem::Helper.shell 'git rev-parse --abbrev-ref HEAD', :capture => true)
|
6
|
+
target_branch = Hem.ui.ask 'Target branch', default: 'develop'
|
7
|
+
|
8
|
+
pr_content = <<-prbody
|
9
|
+
# The line below this comment is the title of your pull request. Keep it short and on a single line.
|
10
|
+
PR_TITLE
|
11
|
+
|
12
|
+
# All text below this comment will appear as the body of the pull request.
|
13
|
+
# If your project has a DoD.md in the project root, it will be automatically included.
|
14
|
+
# Any line starting with a hash (comment) will be ignored
|
15
|
+
|
16
|
+
PR_DOD
|
17
|
+
prbody
|
18
|
+
|
19
|
+
pr_content['PR_TITLE'] = Hem::Helper.shell 'git log -1 --pretty=%B', :capture => true
|
20
|
+
|
21
|
+
dod_path = Hem::Helper.locate('DoD.md')
|
22
|
+
|
23
|
+
if dod_path && !dod_path.empty?
|
24
|
+
dod_file = File.open dod_path[0]
|
25
|
+
pr_content['PR_DOD'] = dod_file.read
|
26
|
+
dod_file.close
|
27
|
+
else
|
28
|
+
pr_content['PR_DOD'] = '# No DoD.md file found, add one to your project root.'
|
29
|
+
end
|
30
|
+
|
31
|
+
pr_body = Hem.ui.editor(pr_content).lines.reject{ |line| line[0] == '#' }.join
|
32
|
+
|
33
|
+
pr_title = pr_body.lines.to_a[0]
|
34
|
+
|
35
|
+
pr_body = pr_body.lines.to_a[1..-1].join
|
36
|
+
|
37
|
+
git_parts = Hem::Helper.parse_github_url(Hem.project_config.git_url)
|
38
|
+
repo = "#{git_parts[:owner]}/#{git_parts[:repo]}"
|
39
|
+
|
40
|
+
api = Hem::Lib::Github::Api.new
|
41
|
+
pr_url = api.create_pull_request(repo, target_branch, source_branch, pr_title, pr_body)
|
42
|
+
|
43
|
+
Hem::ui.success "Pull request created: #{pr_url}"
|
44
|
+
end
|
45
|
+
end
|
@@ -0,0 +1,61 @@
|
|
1
|
+
|
2
|
+
desc "Project seed commands"
|
3
|
+
namespace :seed do
|
4
|
+
|
5
|
+
desc "Create a new project from a seed repository"
|
6
|
+
|
7
|
+
option '-g=', '--git-url=', 'Git repository for project'
|
8
|
+
option '-s=', '--seed=', 'Seed name or URL to use'
|
9
|
+
option '-b=', '--branch=', 'Seed branch to use'
|
10
|
+
option '-d=', '--data=', 'Seed data to save to the project hem configuration', :as => Hash
|
11
|
+
|
12
|
+
task :plant, [ :name ] do |t, args|
|
13
|
+
name = args[:name]
|
14
|
+
|
15
|
+
Hem.project_path = File.join(Dir.pwd, name)
|
16
|
+
|
17
|
+
raise Hem::UserError.new "Name must match sprint zero guidelines" unless name.match /[a-z0-9\-]+/
|
18
|
+
raise Hem::UserError.new "#{Hem.project_path} already exists!" if File.exists? Hem.project_path
|
19
|
+
|
20
|
+
config = {
|
21
|
+
:name => name,
|
22
|
+
:project_path => Hem.project_path,
|
23
|
+
:git_url => t.opts[:'git-url'] || Hem.ui.ask("Repository URL", default: "git@github.com:inviqa/#{name}"),
|
24
|
+
:ref => t.opts[:branch] || 'master'
|
25
|
+
}
|
26
|
+
|
27
|
+
seed_options = %w( default magento symfony custom )
|
28
|
+
|
29
|
+
seed_name = t.opts[:seed] || Hem.ui.ask_choice('Project seed', seed_options, default: 'default')
|
30
|
+
use_short_seed_name = true
|
31
|
+
|
32
|
+
if seed_name == 'custom'
|
33
|
+
seed_name = Hem.ui.ask('Please enter a git url or a path to a local git checkout containing the seed')
|
34
|
+
use_short_seed_name = false
|
35
|
+
end
|
36
|
+
|
37
|
+
config[:seed] = {
|
38
|
+
:name => File.basename(seed_name, '.git'),
|
39
|
+
:url => Hem::Lib::Seed::Seed.name_to_url(seed_name, :use_short_seed_name => use_short_seed_name)
|
40
|
+
}
|
41
|
+
|
42
|
+
unless t.opts[:data].nil?
|
43
|
+
data = t.opts[:data].inject({}){|hash,(k,v)| hash[k.to_sym] = v; hash}
|
44
|
+
config.merge!(data)
|
45
|
+
end
|
46
|
+
|
47
|
+
seed = Hem::Lib::Seed::Seed.new(
|
48
|
+
File.join(Hem.seed_cache_path, config[:seed][:name]),
|
49
|
+
config[:seed][:url]
|
50
|
+
)
|
51
|
+
|
52
|
+
config[:vm_ip] = seed.vm_ip
|
53
|
+
|
54
|
+
Hem::Lib::Seed::Project.new().setup(seed, config)
|
55
|
+
|
56
|
+
Hem.ui.separator
|
57
|
+
Hem.ui.success "Your new project is available in #{Hem.project_path}."
|
58
|
+
Hem.ui.success "You will need to review the initial commit and if all is well, push the repository to github using `git push origin --all`."
|
59
|
+
Hem.ui.separator
|
60
|
+
end
|
61
|
+
end
|
@@ -0,0 +1,45 @@
|
|
1
|
+
desc "Internal hem debugging tools"
|
2
|
+
hidden true
|
3
|
+
namespace 'self' do
|
4
|
+
|
5
|
+
desc "REPL"
|
6
|
+
task :repl do
|
7
|
+
require 'pry'
|
8
|
+
Pry.config.prompt = if STDIN.tty?
|
9
|
+
proc { 'hem > '}
|
10
|
+
else
|
11
|
+
proc { '' }
|
12
|
+
end
|
13
|
+
pry
|
14
|
+
end
|
15
|
+
|
16
|
+
desc "Tasks for debugging hem"
|
17
|
+
namespace 'debug' do
|
18
|
+
desc "Display project paths"
|
19
|
+
project_only
|
20
|
+
task "paths" do
|
21
|
+
Hem.ui.info "<%=color('Project path:', :green)%> " + Hem.project_path
|
22
|
+
{
|
23
|
+
:gemfile => "*Gemfile",
|
24
|
+
:vagrantfile => "*Vagrantfile",
|
25
|
+
:cheffile => "*Cheffile",
|
26
|
+
:berksfile => "*Berksfile",
|
27
|
+
:'composer.json' => "composer.json"
|
28
|
+
}.each do |k,v|
|
29
|
+
path = nil
|
30
|
+
locate v do |file, full_file|
|
31
|
+
path = full_file
|
32
|
+
end
|
33
|
+
Hem.ui.info "<%=color('#{k.to_s}:', :green) %> #{path.nil? ? "none" : path}"
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
desc "Locate"
|
38
|
+
project_only
|
39
|
+
task "locate", [ :arg ] do |task, args|
|
40
|
+
locate args[:arg] do |file, full_file|
|
41
|
+
puts full_file
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
@@ -0,0 +1,25 @@
|
|
1
|
+
namespace 'shell-init' do
|
2
|
+
def posix_export_path
|
3
|
+
Hem.ui.output %Q(export PATH="#{ENV['PATH']}")
|
4
|
+
end
|
5
|
+
|
6
|
+
def fish_export_path
|
7
|
+
Hem.ui.output %Q(set -gx PATH "#{ENV['PATH'].split(':').join('" "')}" 2>/dev/null;)
|
8
|
+
end
|
9
|
+
|
10
|
+
task 'bash' do
|
11
|
+
posix_export_path
|
12
|
+
end
|
13
|
+
|
14
|
+
task 'sh' do
|
15
|
+
posix_export_path
|
16
|
+
end
|
17
|
+
|
18
|
+
task 'zsh' do
|
19
|
+
posix_export_path
|
20
|
+
end
|
21
|
+
|
22
|
+
task 'fish' do
|
23
|
+
fish_export_path
|
24
|
+
end
|
25
|
+
end
|
@@ -0,0 +1,76 @@
|
|
1
|
+
desc "System configuration related commands"
|
2
|
+
namespace :system do
|
3
|
+
|
4
|
+
desc "Shell completion related commands"
|
5
|
+
namespace :completions do
|
6
|
+
|
7
|
+
desc "Install shell completion helpers"
|
8
|
+
option '-f', '--fish', 'Install completions for FISH'
|
9
|
+
option '-b', '--bash', 'Install completions for Bash'
|
10
|
+
option '-z', '--zsh', 'Install completions for ZSH'
|
11
|
+
task "install" do |task|
|
12
|
+
if task.opts[:fish]
|
13
|
+
script = <<-EOF
|
14
|
+
function __hem_completion -d "Create hem completions"
|
15
|
+
set -l cache_dir "/tmp/fish_hem_completion_cache"
|
16
|
+
mkdir -p $cache_dir
|
17
|
+
set -l hashed_pwd (ruby -r 'digest' -e 'puts Digest::MD5.hexdigest(`pwd`)')
|
18
|
+
set -l hem_cache_file "$cache_dir/$hashed_pwd"
|
19
|
+
|
20
|
+
if not test -f "$hem_cache_file"
|
21
|
+
hem system completions fish --skip-host-checks > "$hem_cache_file"
|
22
|
+
end
|
23
|
+
|
24
|
+
cat "$hem_cache_file"
|
25
|
+
end
|
26
|
+
|
27
|
+
function __hem_scope_test -d "Hem scoped completion test"
|
28
|
+
set cmd (commandline -opc)
|
29
|
+
if [ "$cmd" = "$argv" ]
|
30
|
+
return 0
|
31
|
+
end
|
32
|
+
return 1
|
33
|
+
end
|
34
|
+
|
35
|
+
eval (__hem_completion)
|
36
|
+
EOF
|
37
|
+
target = File.join(ENV['HOME'], '.config/fish/completions/hem.fish')
|
38
|
+
FileUtils.mkdir_p(File.dirname(target))
|
39
|
+
File.write(target, script)
|
40
|
+
end
|
41
|
+
|
42
|
+
if task.opts[:bash]
|
43
|
+
raise "Bash completions not yet implemented"
|
44
|
+
end
|
45
|
+
|
46
|
+
if task.opts[:zsh]
|
47
|
+
raise "ZSH completions not yet implemented"
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
desc "Display FISH shell completion commands"
|
52
|
+
task :fish do
|
53
|
+
Hem.cli.slop.options.each do |option|
|
54
|
+
short = option.short.nil? ? '' : "-s #{option.short}"
|
55
|
+
long = option.long.nil? ? '' : "-l #{option.long}"
|
56
|
+
arg = option.config[:argument] ? '' : '-x'
|
57
|
+
puts "complete #{arg} -c hem #{short} #{long} --description '#{option.description}';"
|
58
|
+
end
|
59
|
+
|
60
|
+
map = Hem.cli.help_formatter.command_map
|
61
|
+
map.each do |k, v|
|
62
|
+
next if v.description.nil? || v.description.empty?
|
63
|
+
k = k.split(':')
|
64
|
+
k.unshift 'hem'
|
65
|
+
c = k.pop
|
66
|
+
puts "complete -x -c hem -n '__hem_scope_test #{k.join(' ')}' -a #{c} --description '#{v.description}';"
|
67
|
+
v.options.each do |option|
|
68
|
+
short = option.short.nil? ? '' : "-s #{option.short}"
|
69
|
+
long = option.long.nil? ? '' : "-l #{option.long}"
|
70
|
+
arg = option.config[:argument] ? '' : '-x'
|
71
|
+
puts "complete #{arg} -c hem -n '__hem_scope_test #{k.concat([c]).join(' ')}' #{short} #{long} --description '#{option.description}';"
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
desc "System configuration related commands"
|
2
|
+
namespace :system do
|
3
|
+
|
4
|
+
desc "Check system configuration for potential problems"
|
5
|
+
task :check do
|
6
|
+
Hem::Lib::HostCheck.check.each do |k,v|
|
7
|
+
name = k.to_s.gsub('_', ' ')
|
8
|
+
name[0] = name[0].upcase
|
9
|
+
|
10
|
+
if v == :ok
|
11
|
+
Hem.ui.success "#{name}: OK"
|
12
|
+
else
|
13
|
+
Hem.ui.error "#{name}: FAILED\n"
|
14
|
+
Hem.ui.warning v.advice.gsub(/^/, ' ')
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
desc "Tasks to retrieve common tools"
|
2
|
+
hidden
|
3
|
+
namespace :tools do
|
4
|
+
|
5
|
+
desc "Fetch composer"
|
6
|
+
task :composer do
|
7
|
+
bin_file = File.join(Hem.project_bin_path, "composer.phar")
|
8
|
+
unless File.exists?(bin_file)
|
9
|
+
Hem.ui.success "Getting composer"
|
10
|
+
FileUtils.mkdir_p File.dirname(bin_file)
|
11
|
+
vm_shell "cd bin && php -r \"readfile('https://getcomposer.org/installer');\" | php", :realtime => true, :indent => 2
|
12
|
+
else
|
13
|
+
Hem.ui.success "Composer already available in bin/composer.phar"
|
14
|
+
end
|
15
|
+
Hem.ui.separator
|
16
|
+
end
|
17
|
+
end
|