busser 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- data/.cane +0 -0
- data/.gitignore +17 -0
- data/.simplecov +10 -0
- data/.tailor +4 -0
- data/.travis.yml +19 -0
- data/CHANGELOG.md +5 -0
- data/Gemfile +9 -0
- data/Guardfile +18 -0
- data/LICENSE +15 -0
- data/README.md +35 -0
- data/Rakefile +38 -0
- data/bin/busser +8 -0
- data/busser.gemspec +39 -0
- data/features/plugin_install_command.feature +26 -0
- data/features/setup_command.feature +17 -0
- data/features/step_definitions/busser_root_steps.rb +65 -0
- data/features/suite_cleanup_command.feature +28 -0
- data/features/suite_path_command.feature +15 -0
- data/features/support/env.rb +40 -0
- data/lib/busser.rb +22 -0
- data/lib/busser/cli.rb +42 -0
- data/lib/busser/command/plugin.rb +39 -0
- data/lib/busser/command/plugin_install.rb +95 -0
- data/lib/busser/command/plugin_list.rb +50 -0
- data/lib/busser/command/setup.rb +93 -0
- data/lib/busser/command/suite.rb +39 -0
- data/lib/busser/command/suite_cleanup.rb +43 -0
- data/lib/busser/command/suite_path.rb +38 -0
- data/lib/busser/command/test.rb +46 -0
- data/lib/busser/helpers.rb +37 -0
- data/lib/busser/plugin.rb +64 -0
- data/lib/busser/runner_plugin.rb +32 -0
- data/lib/busser/thor.rb +50 -0
- data/lib/busser/ui.rb +52 -0
- data/lib/busser/version.rb +21 -0
- data/spec/busser/helpers_spec.rb +42 -0
- data/spec/spec_helper.rb +24 -0
- metadata +319 -0
data/lib/busser/cli.rb
ADDED
@@ -0,0 +1,42 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
#
|
3
|
+
# Author:: Fletcher Nichol (<fnichol@nichol.ca>)
|
4
|
+
#
|
5
|
+
# Copyright (C) 2013, Fletcher Nichol
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
8
|
+
# you may not use this file except in compliance with the License.
|
9
|
+
# You may obtain a copy of the License at
|
10
|
+
#
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
12
|
+
#
|
13
|
+
# Unless required by applicable law or agreed to in writing, software
|
14
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
15
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
16
|
+
# See the License for the specific language governing permissions and
|
17
|
+
# limitations under the License.
|
18
|
+
|
19
|
+
require 'busser/thor'
|
20
|
+
require 'busser/command/plugin'
|
21
|
+
require 'busser/command/setup'
|
22
|
+
require 'busser/command/suite'
|
23
|
+
require 'busser/command/test'
|
24
|
+
|
25
|
+
module Busser
|
26
|
+
|
27
|
+
# Main command line interface class which delegates to subcommands.
|
28
|
+
#
|
29
|
+
# @author Fletcher Nichol <fnichol@nichol.ca>
|
30
|
+
#
|
31
|
+
class CLI < Thor::Base
|
32
|
+
|
33
|
+
register Busser::Command::Setup, "setup",
|
34
|
+
"setup", "Creates a Busser home"
|
35
|
+
register Busser::Command::Plugin, "plugin",
|
36
|
+
"plugin SUBCOMMAND", "Plugin subcommands"
|
37
|
+
register Busser::Command::Suite, "suite",
|
38
|
+
"suite SUBCOMMAND", "Suite subcommands"
|
39
|
+
register Busser::Command::Test, "test",
|
40
|
+
"test [PLUGIN ...]", "Runs test suites"
|
41
|
+
end
|
42
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
#
|
3
|
+
# Author:: Fletcher Nichol (<fnichol@nichol.ca>)
|
4
|
+
#
|
5
|
+
# Copyright (C) 2013, Fletcher Nichol
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
8
|
+
# you may not use this file except in compliance with the License.
|
9
|
+
# You may obtain a copy of the License at
|
10
|
+
#
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
12
|
+
#
|
13
|
+
# Unless required by applicable law or agreed to in writing, software
|
14
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
15
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
16
|
+
# See the License for the specific language governing permissions and
|
17
|
+
# limitations under the License.
|
18
|
+
|
19
|
+
require 'busser/thor'
|
20
|
+
require 'busser/command/plugin_install'
|
21
|
+
require 'busser/command/plugin_list'
|
22
|
+
|
23
|
+
module Busser
|
24
|
+
|
25
|
+
module Command
|
26
|
+
|
27
|
+
# Plugin commands.
|
28
|
+
#
|
29
|
+
# @author Fletcher Nichol <fnichol@nichol.ca>
|
30
|
+
#
|
31
|
+
class Plugin < Busser::Thor::Base
|
32
|
+
|
33
|
+
register Busser::Command::PluginInstall, "install",
|
34
|
+
"install PLUGIN [PLUGIN ...]", "Installs one or more plugins"
|
35
|
+
register Busser::Command::PluginList, "list",
|
36
|
+
"list", "Lists installed plugins"
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
@@ -0,0 +1,95 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
#
|
3
|
+
# Author:: Fletcher Nichol (<fnichol@nichol.ca>)
|
4
|
+
#
|
5
|
+
# Copyright (C) 2013, Fletcher Nichol
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
8
|
+
# you may not use this file except in compliance with the License.
|
9
|
+
# You may obtain a copy of the License at
|
10
|
+
#
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
12
|
+
#
|
13
|
+
# Unless required by applicable law or agreed to in writing, software
|
14
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
15
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
16
|
+
# See the License for the specific language governing permissions and
|
17
|
+
# limitations under the License.
|
18
|
+
|
19
|
+
require 'rubygems/dependency_installer'
|
20
|
+
require 'busser/thor'
|
21
|
+
|
22
|
+
module Busser
|
23
|
+
|
24
|
+
module Command
|
25
|
+
|
26
|
+
# Plugin install command.
|
27
|
+
#
|
28
|
+
# @author Fletcher Nichol <fnichol@nichol.ca>
|
29
|
+
#
|
30
|
+
class PluginInstall < Busser::Thor::BaseGroup
|
31
|
+
|
32
|
+
argument :plugins, :type => :array
|
33
|
+
|
34
|
+
def install_all
|
35
|
+
silence_gem_ui!
|
36
|
+
plugins.each { |plugin| install(plugin) }
|
37
|
+
end
|
38
|
+
|
39
|
+
private
|
40
|
+
|
41
|
+
def install(plugin)
|
42
|
+
install_gem(plugin)
|
43
|
+
end
|
44
|
+
|
45
|
+
def install_gem(plugin)
|
46
|
+
name, version = plugin.split("@")
|
47
|
+
|
48
|
+
if gem_installed?(name, version)
|
49
|
+
info "#{plugin} plugin already installed"
|
50
|
+
else
|
51
|
+
spec = dep_installer.install(new_dep(name, version)).first
|
52
|
+
info "Plugin #{plugin} installed (version #{spec.version})"
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
def gem_installed?(name, version)
|
57
|
+
installed = Array(Gem::Specification.find_all_by_name(name, version))
|
58
|
+
version = latest_version(name) if version.nil?
|
59
|
+
|
60
|
+
installed.find { |spec| spec.version.to_s == version }
|
61
|
+
end
|
62
|
+
|
63
|
+
def latest_version(name)
|
64
|
+
available_gems = dep_installer.find_gems_with_sources(new_dep(name))
|
65
|
+
|
66
|
+
spec, source = if available_gems.respond_to?(:last)
|
67
|
+
# DependencyInstaller sorts the results such that the last one is
|
68
|
+
# always the one it considers best.
|
69
|
+
spec_with_source = available_gems.last
|
70
|
+
spec_with_source && spec_with_source
|
71
|
+
else
|
72
|
+
# Rubygems 2.0 returns a Gem::Available set, which is a
|
73
|
+
# collection of AvailableSet::Tuple structs
|
74
|
+
available_gems.pick_best!
|
75
|
+
best_gem = available_gems.set.first
|
76
|
+
best_gem && [best_gem.spec, best_gem.source]
|
77
|
+
end
|
78
|
+
|
79
|
+
spec && spec.version && spec.version.to_s
|
80
|
+
end
|
81
|
+
|
82
|
+
def silence_gem_ui!
|
83
|
+
Gem::DefaultUserInteraction.ui = Gem::SilentUI.new
|
84
|
+
end
|
85
|
+
|
86
|
+
def dep_installer
|
87
|
+
Gem::DependencyInstaller.new
|
88
|
+
end
|
89
|
+
|
90
|
+
def new_dep(name, version = nil)
|
91
|
+
Gem::Dependency.new(name, version)
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|
95
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
#
|
3
|
+
# Author:: Fletcher Nichol (<fnichol@nichol.ca>)
|
4
|
+
#
|
5
|
+
# Copyright (C) 2013, Fletcher Nichol
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
8
|
+
# you may not use this file except in compliance with the License.
|
9
|
+
# You may obtain a copy of the License at
|
10
|
+
#
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
12
|
+
#
|
13
|
+
# Unless required by applicable law or agreed to in writing, software
|
14
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
15
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
16
|
+
# See the License for the specific language governing permissions and
|
17
|
+
# limitations under the License.
|
18
|
+
|
19
|
+
require 'busser/plugin'
|
20
|
+
require 'busser/thor'
|
21
|
+
|
22
|
+
module Busser
|
23
|
+
|
24
|
+
module Command
|
25
|
+
|
26
|
+
# Plugin list command.
|
27
|
+
#
|
28
|
+
# @author Fletcher Nichol <fnichol@nichol.ca>
|
29
|
+
#
|
30
|
+
class PluginList < Busser::Thor::BaseGroup
|
31
|
+
|
32
|
+
def list
|
33
|
+
if plugin_data.empty?
|
34
|
+
say "No plugins installed yet"
|
35
|
+
else
|
36
|
+
print_table([["Plugin", "Version"]] + plugin_data)
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
private
|
41
|
+
|
42
|
+
def plugin_data
|
43
|
+
@plugin_data ||= Busser::Plugin.runner_plugins.map do |path|
|
44
|
+
spec = Busser::Plugin.gem_from_path(path)
|
45
|
+
[File.basename(path), (spec && spec.version)]
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
@@ -0,0 +1,93 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
#
|
3
|
+
# Author:: Fletcher Nichol (<fnichol@nichol.ca>)
|
4
|
+
#
|
5
|
+
# Copyright (C) 2013, Fletcher Nichol
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
8
|
+
# you may not use this file except in compliance with the License.
|
9
|
+
# You may obtain a copy of the License at
|
10
|
+
#
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
12
|
+
#
|
13
|
+
# Unless required by applicable law or agreed to in writing, software
|
14
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
15
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
16
|
+
# See the License for the specific language governing permissions and
|
17
|
+
# limitations under the License.
|
18
|
+
|
19
|
+
require 'busser/thor'
|
20
|
+
require 'busser/plugin'
|
21
|
+
|
22
|
+
module Busser
|
23
|
+
|
24
|
+
module Command
|
25
|
+
|
26
|
+
# Setup command.
|
27
|
+
#
|
28
|
+
# @author Fletcher Nichol <fnichol@nichol.ca>
|
29
|
+
#
|
30
|
+
class Setup < Busser::Thor::BaseGroup
|
31
|
+
|
32
|
+
def perform
|
33
|
+
banner "Setting up Busser"
|
34
|
+
create_busser_root
|
35
|
+
generate_busser_binstub
|
36
|
+
end
|
37
|
+
|
38
|
+
private
|
39
|
+
|
40
|
+
def create_busser_root
|
41
|
+
info "Creating BUSSER_ROOT in #{root_path}"
|
42
|
+
empty_directory(root_path, :verbose => false)
|
43
|
+
end
|
44
|
+
|
45
|
+
def generate_busser_binstub
|
46
|
+
binstub = root_path + "bin/busser"
|
47
|
+
|
48
|
+
info "Creating busser binstub"
|
49
|
+
create_file(binstub, :verbose => false) do
|
50
|
+
<<-BUSSER_BINSTUB.gsub(/^ {12}/, '')
|
51
|
+
#!/usr/bin/env bash
|
52
|
+
#
|
53
|
+
# This file was generated by Busser.
|
54
|
+
#
|
55
|
+
# The application 'busser' is installed as part of a gem, and
|
56
|
+
# this file is here to facilitate running it.
|
57
|
+
#
|
58
|
+
|
59
|
+
# Get the directory where this ruby is. This will also resolve
|
60
|
+
# any symlinks in the directory/script, so it will be the fully
|
61
|
+
# resolved path.
|
62
|
+
SOURCE="#{ruby_bin}"
|
63
|
+
while [ -h "$SOURCE" ] ; do SOURCE="$(readlink "$SOURCE")"; done
|
64
|
+
DIR="$( cd -P "$( dirname "$SOURCE" )" && pwd )"
|
65
|
+
|
66
|
+
# Export gem paths so that we use the isolated gems.
|
67
|
+
export GEM_HOME="#{gem_home}"
|
68
|
+
export GEM_PATH="${GEM_HOME}"
|
69
|
+
|
70
|
+
# Unset RUBYOPT, we don't want this bleeding into our runtime.
|
71
|
+
unset RUBYOPT GEMRC
|
72
|
+
|
73
|
+
# Call the actual Busser bin with our arguments
|
74
|
+
exec "${DIR}/ruby" "${DIR}/busser" "$@"
|
75
|
+
BUSSER_BINSTUB
|
76
|
+
end
|
77
|
+
chmod(binstub, 0755, :verbose => false)
|
78
|
+
end
|
79
|
+
|
80
|
+
def ruby_bin
|
81
|
+
if bindir = RbConfig::CONFIG["bindir"]
|
82
|
+
File.join(bindir, "ruby")
|
83
|
+
else
|
84
|
+
"ruby"
|
85
|
+
end
|
86
|
+
end
|
87
|
+
|
88
|
+
def gem_home
|
89
|
+
Gem.paths.home
|
90
|
+
end
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
#
|
3
|
+
# Author:: Fletcher Nichol (<fnichol@nichol.ca>)
|
4
|
+
#
|
5
|
+
# Copyright (C) 2013, Fletcher Nichol
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
8
|
+
# you may not use this file except in compliance with the License.
|
9
|
+
# You may obtain a copy of the License at
|
10
|
+
#
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
12
|
+
#
|
13
|
+
# Unless required by applicable law or agreed to in writing, software
|
14
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
15
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
16
|
+
# See the License for the specific language governing permissions and
|
17
|
+
# limitations under the License.
|
18
|
+
|
19
|
+
require 'busser/thor'
|
20
|
+
require 'busser/command/suite_cleanup'
|
21
|
+
require 'busser/command/suite_path'
|
22
|
+
|
23
|
+
module Busser
|
24
|
+
|
25
|
+
module Command
|
26
|
+
|
27
|
+
# Suite commands.
|
28
|
+
#
|
29
|
+
# @author Fletcher Nichol <fnichol@nichol.ca>
|
30
|
+
#
|
31
|
+
class Suite < Busser::Thor::Base
|
32
|
+
|
33
|
+
register Busser::Command::SuiteCleanup, "cleanup",
|
34
|
+
"cleanup", "Cleans up test suite directories"
|
35
|
+
register Busser::Command::SuitePath, "path",
|
36
|
+
"path [<plugin_name>]", "Displays the directory for suite tests"
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
@@ -0,0 +1,43 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
#
|
3
|
+
# Author:: Fletcher Nichol (<fnichol@nichol.ca>)
|
4
|
+
#
|
5
|
+
# Copyright (C) 2013, Fletcher Nichol
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
8
|
+
# you may not use this file except in compliance with the License.
|
9
|
+
# You may obtain a copy of the License at
|
10
|
+
#
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
12
|
+
#
|
13
|
+
# Unless required by applicable law or agreed to in writing, software
|
14
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
15
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
16
|
+
# See the License for the specific language governing permissions and
|
17
|
+
# limitations under the License.
|
18
|
+
|
19
|
+
require 'busser/thor'
|
20
|
+
|
21
|
+
module Busser
|
22
|
+
|
23
|
+
module Command
|
24
|
+
|
25
|
+
# Suite cleanup command.
|
26
|
+
#
|
27
|
+
# @author Fletcher Nichol <fnichol@nichol.ca>
|
28
|
+
#
|
29
|
+
class SuiteCleanup < Busser::Thor::BaseGroup
|
30
|
+
|
31
|
+
def cleanup
|
32
|
+
if suite_path.directory?
|
33
|
+
Pathname.glob(suite_path + "*").each do |dir|
|
34
|
+
info "Removing #{dir}"
|
35
|
+
dir.rmtree
|
36
|
+
end
|
37
|
+
else
|
38
|
+
info "Suite path directory #{suite_path} does not exist, skipping."
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
@@ -0,0 +1,38 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
#
|
3
|
+
# Author:: Fletcher Nichol (<fnichol@nichol.ca>)
|
4
|
+
#
|
5
|
+
# Copyright (C) 2013, Fletcher Nichol
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
8
|
+
# you may not use this file except in compliance with the License.
|
9
|
+
# You may obtain a copy of the License at
|
10
|
+
#
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
12
|
+
#
|
13
|
+
# Unless required by applicable law or agreed to in writing, software
|
14
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
15
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
16
|
+
# See the License for the specific language governing permissions and
|
17
|
+
# limitations under the License.
|
18
|
+
|
19
|
+
require 'busser/thor'
|
20
|
+
|
21
|
+
module Busser
|
22
|
+
|
23
|
+
module Command
|
24
|
+
|
25
|
+
# Suite path command.
|
26
|
+
#
|
27
|
+
# @author Fletcher Nichol <fnichol@nichol.ca>
|
28
|
+
#
|
29
|
+
class SuitePath < Busser::Thor::BaseGroup
|
30
|
+
|
31
|
+
argument :suite_name, :required => false
|
32
|
+
|
33
|
+
def path
|
34
|
+
say suite_path(suite_name)
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|