crosstest-core 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: c0116950bbc38ceb7c21d1a532ea1816de54f29e
4
+ data.tar.gz: 353480f78e749159b8d3f337486650a935ef34b5
5
+ SHA512:
6
+ metadata.gz: 03837f8ea547880d2cb8d84c780670dac0dc34d708d35287c358bd6e7d50f676ee64e16524c390ef5ab7f3803752e47f9e54c4706713903cae75c4ff49a3179d
7
+ data.tar.gz: 97dffaf921fac6dcb26a31700a66c71ab8dc1f95dd18d6eb8ea7aa9b8bfb3c890c66cf8d9e48f2a563f5decffae5d5dc34654cca1609047b7a33a417094c4cbe
data/.gitignore ADDED
@@ -0,0 +1,17 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
data/.rubocop.yml ADDED
@@ -0,0 +1 @@
1
+ inherit_from: .rubocop_todo.yml
data/.rubocop_todo.yml ADDED
@@ -0,0 +1,30 @@
1
+ # This configuration was generated by `rubocop --auto-gen-config`
2
+ # on 2015-01-20 16:57:55 -0500 using RuboCop version 0.27.0.
3
+ # The point is for the user to remove these configuration records
4
+ # one by one as the offenses are removed from the code base.
5
+ # Note that changes in the inspected code, or installation of new
6
+ # versions of RuboCop, may require this file to be generated again.
7
+
8
+ # Offense count: 1
9
+ Metrics/AbcSize:
10
+ Max: 18
11
+
12
+ # Offense count: 10
13
+ # Configuration parameters: AllowURI, URISchemes.
14
+ Metrics/LineLength:
15
+ Max: 105
16
+
17
+ # Offense count: 4
18
+ # Configuration parameters: CountComments.
19
+ Metrics/MethodLength:
20
+ Max: 13
21
+
22
+ # Offense count: 14
23
+ Style/Documentation:
24
+ Enabled: false
25
+
26
+ # Offense count: 2
27
+ # Configuration parameters: MaxSlashes.
28
+ Style/RegexpLiteral:
29
+ Enabled: false
30
+
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in crosstest-core.gemspec
4
+ gemspec
data/LICENSE.txt ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2015 Max Lincoln
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,4 @@
1
+ # Crosstest::Core
2
+
3
+ Shared code for crosstest projects.
4
+ See [crosstest](https://github.com/crosstest/crosstest)
data/Rakefile ADDED
@@ -0,0 +1,12 @@
1
+ require 'bundler/gem_tasks'
2
+ require 'rubocop/rake_task'
3
+ require 'rake/notes/rake_task'
4
+ require 'rspec/core/rake_task'
5
+
6
+ task default: [:spec, :rubocop, :notes]
7
+
8
+ RSpec::Core::RakeTask.new('spec')
9
+ RuboCop::RakeTask.new(:rubocop) do |task|
10
+ # abort rake on failure
11
+ task.fail_on_error = true
12
+ end
@@ -0,0 +1,29 @@
1
+ # coding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'crosstest/core/version'
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = 'crosstest-core'
8
+ spec.version = Crosstest::Core::VERSION
9
+ spec.authors = ['Max Lincoln']
10
+ spec.email = ['max@devopsy.com']
11
+ spec.summary = 'Shared code for crosstest projects.'
12
+ spec.homepage = ''
13
+ spec.license = 'MIT'
14
+
15
+ spec.files = `git ls-files -z`.split("\x0")
16
+ spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
17
+ spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
18
+ spec.require_paths = ['lib']
19
+
20
+ spec.add_dependency 'thor', '~> 0.19'
21
+ spec.add_development_dependency 'bundler', '~> 1.5'
22
+ spec.add_development_dependency 'rake', '~> 10.0'
23
+ spec.add_development_dependency 'rake-notes'
24
+ spec.add_development_dependency 'simplecov'
25
+ spec.add_development_dependency 'rspec', '~> 3.0'
26
+ spec.add_development_dependency 'rubocop', '~> 0.18', '<= 0.27'
27
+ spec.add_development_dependency 'rubocop-rspec', '~> 1.2'
28
+ spec.add_development_dependency 'aruba'
29
+ end
@@ -0,0 +1,16 @@
1
+ require 'crosstest/core/version'
2
+ require 'logger'
3
+
4
+ module Crosstest
5
+ module Core
6
+ autoload :Util, 'crosstest/core/util'
7
+ autoload :FileSystem, 'crosstest/core/file_system'
8
+ autoload :CLI, 'crosstest/core/cli'
9
+ autoload :Logger, 'crosstest/core/logger'
10
+ autoload :Logging, 'crosstest/core/logging'
11
+ autoload :DefaultLogger, 'crosstest/core/logging'
12
+ autoload :StdoutLogger, 'crosstest/core/logging'
13
+ autoload :LogdevLogger, 'crosstest/core/logging'
14
+ autoload :Color, 'crosstest/core/color'
15
+ end
16
+ end
@@ -0,0 +1,41 @@
1
+ require 'English'
2
+ require 'thor'
3
+
4
+ module Crosstest
5
+ module Core
6
+ class CLI < Thor
7
+ BUILT_IN_TASKS = %w(bootstrap)
8
+
9
+ class << self
10
+ # Override Thor's start to strip extra_args from ARGV before it's processed
11
+ attr_accessor :extra_args
12
+
13
+ def start(given_args = ARGV, config = {})
14
+ if given_args && (split_pos = given_args.index('--'))
15
+ @extra_args = given_args.slice(split_pos + 1, given_args.length).map do | arg |
16
+ # Restore quotes
17
+ arg.match(/\=/) ? restore_quotes(arg) : arg
18
+ end
19
+ given_args = given_args.slice(0, split_pos)
20
+ end
21
+ super given_args, config
22
+ end
23
+
24
+ private
25
+
26
+ def restore_quotes(arg)
27
+ lhs, rhs = arg.split('=')
28
+ lhs = "\"#{lhs}\"" if lhs.match(/\s/)
29
+ rhs = "\"#{rhs}\"" if rhs.match(/\s/)
30
+ [lhs, rhs].join('=')
31
+ end
32
+ end
33
+
34
+ no_commands do
35
+ def extra_args
36
+ self.class.extra_args
37
+ end
38
+ end
39
+ end
40
+ end
41
+ end
@@ -0,0 +1,42 @@
1
+ module Crosstest
2
+ module Core
3
+ module Color
4
+ ANSI = {
5
+ reset: 0, black: 30, red: 31, green: 32, yellow: 33,
6
+ blue: 34, magenta: 35, cyan: 36, white: 37,
7
+ bright_black: 90, bright_red: 91, bright_green: 92,
8
+ bright_yellow: 93, bright_blue: 94, bright_magenta: 95,
9
+ bright_cyan: 96, bright_white: 97
10
+ }.freeze
11
+
12
+ COLORS = %w(
13
+ cyan yellow green magenta blue bright_cyan bright_yellow
14
+ bright_green bright_magenta bright_blue
15
+ ).freeze
16
+
17
+ # Returns an ansi escaped string representing a color control sequence.
18
+ #
19
+ # @param name [Symbol] a valid color representation, taken from
20
+ # Crosstest::Color::ANSI
21
+ # @return [String] an ansi escaped string if the color is valid and an
22
+ # empty string otherwise
23
+ def self.escape(name)
24
+ return '' if name.nil?
25
+ return '' unless ANSI[name]
26
+ "\e[#{ANSI[name]}m"
27
+ end
28
+
29
+ # Returns a colorized ansi escaped string with the given color.
30
+ #
31
+ # @param str [String] a string to colorize
32
+ # @param name [Symbol] a valid color representation, taken from
33
+ # Crosstest::Color::ANSI
34
+ # @return [String] an ansi escaped string if the color is valid and an
35
+ # unescaped string otherwise
36
+ def self.colorize(str, name)
37
+ color = escape(name)
38
+ color.empty? ? str : "#{color}#{str}#{escape(:reset)}"
39
+ end
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,60 @@
1
+ module Crosstest
2
+ module Core
3
+ module FileSystem
4
+ include Util::String
5
+
6
+ class << self
7
+ # Finds a file by loosely matching the file name to a scenario name
8
+ def find_file(search_path, scenario_name, ignored_patterns = nil)
9
+ ignored_patterns ||= read_gitignore(search_path)
10
+ glob_string = "#{search_path}/**/*#{slugify(scenario_name)}.*"
11
+ potential_files = Dir.glob(glob_string, File::FNM_CASEFOLD)
12
+ potential_files.concat Dir.glob(glob_string.gsub('_', '-'), File::FNM_CASEFOLD)
13
+ potential_files.concat Dir.glob(glob_string.gsub('_', ''), File::FNM_CASEFOLD)
14
+
15
+ # Filter out ignored filesFind the first file, not including generated files
16
+ files = potential_files.select do |f|
17
+ !ignored? ignored_patterns, search_path, f
18
+ end
19
+
20
+ # Select the shortest path, likely the best match
21
+ file = files.min_by(&:length)
22
+
23
+ fail Errno::ENOENT, "No file was found for #{scenario_name} within #{search_path}" if file.nil?
24
+ Pathname.new file
25
+ end
26
+
27
+ def relativize(file, base_path)
28
+ absolute_file = File.absolute_path(file)
29
+ absolute_base_path = File.absolute_path(base_path)
30
+ Pathname.new(absolute_file).relative_path_from Pathname.new(absolute_base_path)
31
+ end
32
+
33
+ private
34
+
35
+ # @api private
36
+ def read_gitignore(dir)
37
+ gitignore_file = "#{dir}/.gitignore"
38
+ File.read(gitignore_file)
39
+ rescue
40
+ ''
41
+ end
42
+
43
+ # @api private
44
+ def ignored?(ignored_patterns, base_path, target_file)
45
+ # Trying to match the git ignore rules but there's some discrepencies.
46
+ ignored_patterns.split.find do |pattern|
47
+ # if git ignores a folder, we should ignore all files it contains
48
+ pattern = "#{pattern}**" if pattern[-1] == '/'
49
+ started_with_slash = pattern.start_with? '/'
50
+
51
+ pattern.gsub!(/\A\//, '') # remove leading slashes since we're searching from root
52
+ file = relativize(target_file, base_path)
53
+ ignored = file.fnmatch? pattern
54
+ ignored || (file.fnmatch? "**/#{pattern}" unless started_with_slash)
55
+ end
56
+ end
57
+ end
58
+ end
59
+ end
60
+ end
@@ -0,0 +1,19 @@
1
+ require 'logger'
2
+
3
+ module Crosstest
4
+ module Core
5
+ module Logger
6
+ def logger
7
+ @logger ||= new_logger
8
+ end
9
+
10
+ def new_logger(_io = $stdout, _level = :debug)
11
+ ::Logger.new(STDOUT)
12
+ end
13
+
14
+ def log_level=(level)
15
+ logger.level = level
16
+ end
17
+ end
18
+ end
19
+ end
@@ -0,0 +1,125 @@
1
+ module Crosstest
2
+ module Core
3
+ module DefaultLogger
4
+ module ClassMethods
5
+ def logger
6
+ @logger ||= Crosstest.configuration.default_logger
7
+ end
8
+ end
9
+
10
+ def self.included(base)
11
+ base.extend(ClassMethods)
12
+ end
13
+
14
+ include ClassMethods
15
+ end
16
+
17
+ module Logging
18
+ class << self
19
+ private
20
+
21
+ def logger_method(meth)
22
+ define_method(meth) do |*args|
23
+ logger.public_send(meth, *args)
24
+ end
25
+ end
26
+ end
27
+
28
+ logger_method :banner
29
+ logger_method :debug
30
+ logger_method :info
31
+ logger_method :warn
32
+ logger_method :error
33
+ logger_method :fatal
34
+ end
35
+
36
+ # Internal class which adds a #banner method call that displays the
37
+ # message with a callout arrow.
38
+ class LogdevLogger < ::Logger
39
+ alias_method :super_info, :info
40
+
41
+ # Dump one or more messages to info.
42
+ #
43
+ # @param msg [String] a message
44
+ def <<(msg)
45
+ @buffer ||= ''
46
+ lines, _, remainder = msg.rpartition("\n")
47
+ if lines.empty?
48
+ @buffer << remainder
49
+ else
50
+ lines.insert(0, @buffer)
51
+ lines.split("\n").each { |l| format_line(l.chomp) }
52
+ @buffer = ''
53
+ end
54
+ end
55
+
56
+ # Log a banner message.
57
+ #
58
+ # @param msg [String] a message
59
+ def banner(msg = nil, &block)
60
+ super_info("-----> #{msg}", &block)
61
+ end
62
+
63
+ private
64
+
65
+ # Reformat a line if it already contains log formatting.
66
+ #
67
+ # @param line [String] a message line
68
+ # @api private
69
+ def format_line(line)
70
+ case line
71
+ when /^-----> / then banner(line.gsub(/^[ >-]{6} /, ''))
72
+ when /^>>>>>> / then error(line.gsub(/^[ >-]{6} /, ''))
73
+ when /^ / then info(line.gsub(/^[ >-]{6} /, ''))
74
+ else info(line)
75
+ end
76
+ end
77
+ end
78
+
79
+ # Internal class which reformats logging methods for display as console
80
+ # output.
81
+ class StdoutLogger < LogdevLogger
82
+ # Log a debug message
83
+ #
84
+ # @param msg [String] a message
85
+ def debug(msg = nil, &block)
86
+ super("D #{msg}", &block)
87
+ end
88
+
89
+ # Log an info message
90
+ #
91
+ # @param msg [String] a message
92
+ def info(msg = nil, &block)
93
+ super(" #{msg}", &block)
94
+ end
95
+
96
+ # Log a warn message
97
+ #
98
+ # @param msg [String] a message
99
+ def warn(msg = nil, &block)
100
+ super("$$$$$$ #{msg}", &block)
101
+ end
102
+
103
+ # Log an error message
104
+ #
105
+ # @param msg [String] a message
106
+ def error(msg = nil, &block)
107
+ super(">>>>>> #{msg}", &block)
108
+ end
109
+
110
+ # Log a fatal message
111
+ #
112
+ # @param msg [String] a message
113
+ def fatal(msg = nil, &block)
114
+ super("!!!!!! #{msg}", &block)
115
+ end
116
+
117
+ # Log an unknown message
118
+ #
119
+ # @param msg [String] a message
120
+ def unknown(msg = nil, &block)
121
+ super("?????? #{msg}", &block)
122
+ end
123
+ end
124
+ end
125
+ end
@@ -0,0 +1,204 @@
1
+ # -*- encoding: utf-8 -*-
2
+ #
3
+ # Much of this code has been adapted from Fletcher Nichol (<fnichol@nichol.ca>)
4
+ # work on test-kitchen.
5
+
6
+ module Crosstest
7
+ module Core
8
+ # Stateless utility methods used in different contexts. Essentially a mini
9
+ # PassiveSupport library.
10
+ module Util
11
+ module Hashable
12
+ def to_hash
13
+ instance_variables.each_with_object({}) do |var, hash|
14
+ hash[var.to_s.delete('@')] = instance_variable_get(var)
15
+ end
16
+ end
17
+ end
18
+
19
+ # Returns the standard library Logger level constants for a given symbol
20
+ # representation.
21
+ #
22
+ # @param symbol [Symbol] symbol representation of a logger level (:debug,
23
+ # :info, :warn, :error, :fatal)
24
+ # @return [Integer] Logger::Severity constant value or nil if input is not
25
+ # valid
26
+ def self.to_logger_level(symbol)
27
+ return nil unless [:debug, :info, :warn, :error, :fatal].include?(symbol)
28
+
29
+ ::Logger.const_get(symbol.to_s.upcase)
30
+ end
31
+
32
+ # Returns the symbol represenation of a logging levels for a given
33
+ # standard library Logger::Severity constant.
34
+ #
35
+ # @param const [Integer] Logger::Severity constant value for a logging
36
+ # level (Logger::DEBUG, Logger::INFO, Logger::WARN, Logger::ERROR,
37
+ # Logger::FATAL)
38
+ # @return [Symbol] symbol representation of the logging level
39
+ def self.from_logger_level(const)
40
+ case const
41
+ when ::Logger::DEBUG then :debug
42
+ when ::Logger::INFO then :info
43
+ when ::Logger::WARN then :warn
44
+ when ::Logger::ERROR then :error
45
+ else :fatal
46
+ end
47
+ end
48
+
49
+ # Returns a new Hash with all key values coerced to symbols. All keys
50
+ # within a Hash are coerced by calling #to_sym and hashes within arrays
51
+ # and other hashes are traversed.
52
+ #
53
+ # @param obj [Object] the hash to be processed. While intended for
54
+ # hashes, this method safely processes arbitrary objects
55
+ # @return [Object] a converted hash with all keys as symbols
56
+ def self.symbolized_hash(obj)
57
+ if obj.is_a?(Hash)
58
+ obj.each_with_object({}) do |(k, v), h|
59
+ h[k.to_sym] = symbolized_hash(v)
60
+ end
61
+ elsif obj.is_a?(Array)
62
+ obj.each_with_object([]) do |e, a|
63
+ a << symbolized_hash(e)
64
+ end
65
+ else
66
+ obj
67
+ end
68
+ end
69
+
70
+ # Returns a new Hash with all key values coerced to strings. All keys
71
+ # within a Hash are coerced by calling #to_s and hashes with arrays
72
+ # and other hashes are traversed.
73
+ #
74
+ # @param obj [Object] the hash to be processed. While intended for
75
+ # hashes, this method safely processes arbitrary objects
76
+ # @return [Object] a converted hash with all keys as strings
77
+ def self.stringified_hash(obj)
78
+ if obj.is_a?(Hash)
79
+ obj.each_with_object({}) do |(k, v), h|
80
+ h[k.to_s] = stringified_hash(v)
81
+ end
82
+ elsif obj.is_a?(Array)
83
+ obj.each_with_object([]) do |e, a|
84
+ a << stringified_hash(e)
85
+ end
86
+ else
87
+ obj
88
+ end
89
+ end
90
+
91
+ # Returns a formatted string representing a duration in seconds.
92
+ #
93
+ # @param total [Integer] the total number of seconds
94
+ # @return [String] a formatted string of the form (XmYY.00s)
95
+ def self.duration(total)
96
+ total = 0 if total.nil?
97
+ minutes = (total / 60).to_i
98
+ seconds = (total - (minutes * 60))
99
+ format('(%dm%.2fs)', minutes, seconds)
100
+ end
101
+
102
+ module String
103
+ module ClassMethods
104
+ def slugify(*labels)
105
+ labels.map do |label|
106
+ label.downcase.gsub(/[\.\s-]/, '_')
107
+ end.join('-')
108
+ end
109
+
110
+ def ansi2html(text)
111
+ HTML.from_ansi(text)
112
+ end
113
+
114
+ def escape_html(text)
115
+ HTML.escape_html(text)
116
+ end
117
+ alias_method :h, :escape_html
118
+
119
+ def highlight(source, opts = {})
120
+ return nil if source.nil?
121
+
122
+ opts[:language] ||= 'ruby'
123
+ opts[:formatter] ||= 'terminal256'
124
+ Highlight.new(opts).highlight(source)
125
+ end
126
+ end
127
+
128
+ def self.included(base)
129
+ base.extend(ClassMethods)
130
+ end
131
+
132
+ include ClassMethods
133
+ end
134
+
135
+ class Highlight
136
+ def initialize(opts)
137
+ @lexer = Rouge::Lexer.find(opts[:language]) || Rouge::Lexer.guess_by_filename(opts[:filename])
138
+ @formatter = opts[:formatter]
139
+ end
140
+
141
+ def highlight(source)
142
+ Rouge.highlight(source, @lexer, @formatter)
143
+ end
144
+ end
145
+
146
+ class HTML
147
+ ANSICODES = {
148
+ '1' => 'bold',
149
+ '4' => 'underline',
150
+ '30' => 'black',
151
+ '31' => 'red',
152
+ '32' => 'green',
153
+ '33' => 'yellow',
154
+ '34' => 'blue',
155
+ '35' => 'magenta',
156
+ '36' => 'cyan',
157
+ '37' => 'white',
158
+ '40' => 'bg-black',
159
+ '41' => 'bg-red',
160
+ '42' => 'bg-green',
161
+ '43' => 'bg-yellow',
162
+ '44' => 'bg-blue',
163
+ '45' => 'bg-magenta',
164
+ '46' => 'bg-cyan',
165
+ '47' => 'bg-white'
166
+ }
167
+
168
+ def self.from_ansi(text)
169
+ ansi = StringScanner.new(text)
170
+ html = StringIO.new
171
+ until ansi.eos?
172
+ if ansi.scan(/\e\[0?m/)
173
+ html.print(%(</span>))
174
+ elsif ansi.scan(/\e\[0?(\d+)m/)
175
+ # use class instead of style?
176
+ style = ANSICODES[ansi[1]] || 'text-reset'
177
+ html.print(%(<span class="#{style}">))
178
+ else
179
+ html.print(ansi.scan(/./m))
180
+ end
181
+ end
182
+ html.string
183
+ end
184
+
185
+ # From Rack
186
+
187
+ ESCAPE_HTML = {
188
+ '&' => '&amp;',
189
+ '<' => '&lt;',
190
+ '>' => '&gt;',
191
+ "'" => '&#x27;',
192
+ '"' => '&quot;',
193
+ '/' => '&#x2F;'
194
+ }
195
+ ESCAPE_HTML_PATTERN = Regexp.union(*ESCAPE_HTML.keys)
196
+
197
+ # Escape ampersands, brackets and quotes to their HTML/XML entities.
198
+ def self.escape_html(string)
199
+ string.to_s.gsub(ESCAPE_HTML_PATTERN) { |c| ESCAPE_HTML[c] }
200
+ end
201
+ end
202
+ end
203
+ end
204
+ end
@@ -0,0 +1,5 @@
1
+ module Crosstest
2
+ module Core
3
+ VERSION = '0.0.1'
4
+ end
5
+ end
metadata ADDED
@@ -0,0 +1,192 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: crosstest-core
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Max Lincoln
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2015-01-20 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: thor
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '0.19'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '0.19'
27
+ - !ruby/object:Gem::Dependency
28
+ name: bundler
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: '1.5'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: '1.5'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rake
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: '10.0'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: '10.0'
55
+ - !ruby/object:Gem::Dependency
56
+ name: rake-notes
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - ">="
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - ">="
67
+ - !ruby/object:Gem::Version
68
+ version: '0'
69
+ - !ruby/object:Gem::Dependency
70
+ name: simplecov
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - ">="
74
+ - !ruby/object:Gem::Version
75
+ version: '0'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - ">="
81
+ - !ruby/object:Gem::Version
82
+ version: '0'
83
+ - !ruby/object:Gem::Dependency
84
+ name: rspec
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - "~>"
88
+ - !ruby/object:Gem::Version
89
+ version: '3.0'
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - "~>"
95
+ - !ruby/object:Gem::Version
96
+ version: '3.0'
97
+ - !ruby/object:Gem::Dependency
98
+ name: rubocop
99
+ requirement: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - "~>"
102
+ - !ruby/object:Gem::Version
103
+ version: '0.18'
104
+ - - "<="
105
+ - !ruby/object:Gem::Version
106
+ version: '0.27'
107
+ type: :development
108
+ prerelease: false
109
+ version_requirements: !ruby/object:Gem::Requirement
110
+ requirements:
111
+ - - "~>"
112
+ - !ruby/object:Gem::Version
113
+ version: '0.18'
114
+ - - "<="
115
+ - !ruby/object:Gem::Version
116
+ version: '0.27'
117
+ - !ruby/object:Gem::Dependency
118
+ name: rubocop-rspec
119
+ requirement: !ruby/object:Gem::Requirement
120
+ requirements:
121
+ - - "~>"
122
+ - !ruby/object:Gem::Version
123
+ version: '1.2'
124
+ type: :development
125
+ prerelease: false
126
+ version_requirements: !ruby/object:Gem::Requirement
127
+ requirements:
128
+ - - "~>"
129
+ - !ruby/object:Gem::Version
130
+ version: '1.2'
131
+ - !ruby/object:Gem::Dependency
132
+ name: aruba
133
+ requirement: !ruby/object:Gem::Requirement
134
+ requirements:
135
+ - - ">="
136
+ - !ruby/object:Gem::Version
137
+ version: '0'
138
+ type: :development
139
+ prerelease: false
140
+ version_requirements: !ruby/object:Gem::Requirement
141
+ requirements:
142
+ - - ">="
143
+ - !ruby/object:Gem::Version
144
+ version: '0'
145
+ description:
146
+ email:
147
+ - max@devopsy.com
148
+ executables: []
149
+ extensions: []
150
+ extra_rdoc_files: []
151
+ files:
152
+ - ".gitignore"
153
+ - ".rubocop.yml"
154
+ - ".rubocop_todo.yml"
155
+ - Gemfile
156
+ - LICENSE.txt
157
+ - README.md
158
+ - Rakefile
159
+ - crosstest-core.gemspec
160
+ - lib/crosstest/core.rb
161
+ - lib/crosstest/core/cli.rb
162
+ - lib/crosstest/core/color.rb
163
+ - lib/crosstest/core/file_system.rb
164
+ - lib/crosstest/core/logger.rb
165
+ - lib/crosstest/core/logging.rb
166
+ - lib/crosstest/core/util.rb
167
+ - lib/crosstest/core/version.rb
168
+ homepage: ''
169
+ licenses:
170
+ - MIT
171
+ metadata: {}
172
+ post_install_message:
173
+ rdoc_options: []
174
+ require_paths:
175
+ - lib
176
+ required_ruby_version: !ruby/object:Gem::Requirement
177
+ requirements:
178
+ - - ">="
179
+ - !ruby/object:Gem::Version
180
+ version: '0'
181
+ required_rubygems_version: !ruby/object:Gem::Requirement
182
+ requirements:
183
+ - - ">="
184
+ - !ruby/object:Gem::Version
185
+ version: '0'
186
+ requirements: []
187
+ rubyforge_project:
188
+ rubygems_version: 2.4.2
189
+ signing_key:
190
+ specification_version: 4
191
+ summary: Shared code for crosstest projects.
192
+ test_files: []