doubleshot 0.2.0-java → 0.3.0-java
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/Doubleshot +16 -6
- data/README-OLD.textile +216 -0
- data/README.textile +38 -182
- data/lib/doubleshot.rb +100 -39
- data/lib/doubleshot/commands/gem.rb +15 -12
- data/lib/doubleshot/commands/test.rb +38 -5
- data/lib/doubleshot/configuration.rb +2 -2
- data/lib/doubleshot/dependencies/dependency.rb +1 -1
- data/lib/doubleshot/dependencies/gem_dependency.rb +2 -10
- data/lib/doubleshot/dependencies/jar_dependency.rb +12 -2
- data/lib/doubleshot/lockfile.rb +9 -6
- data/lib/doubleshot/pom.rb +15 -2
- data/lib/doubleshot/resolver.rb +1 -0
- data/lib/doubleshot/resolver/gem_resolver.rb +45 -0
- data/lib/doubleshot/resolver/gem_resolver/artifact.rb +146 -0
- data/lib/doubleshot/resolver/gem_resolver/demand.rb +57 -0
- data/lib/doubleshot/resolver/gem_resolver/dependency.rb +57 -0
- data/lib/doubleshot/resolver/gem_resolver/errors.rb +37 -0
- data/lib/doubleshot/resolver/gem_resolver/gem_source.rb +58 -0
- data/lib/doubleshot/resolver/gem_resolver/graph.rb +200 -0
- data/lib/doubleshot/resolver/gem_resolver/solver.rb +279 -0
- data/lib/doubleshot/resolver/gem_resolver/solver/constraint_row.rb +29 -0
- data/lib/doubleshot/resolver/gem_resolver/solver/constraint_table.rb +35 -0
- data/lib/doubleshot/resolver/gem_resolver/solver/variable_row.rb +47 -0
- data/lib/doubleshot/resolver/gem_resolver/solver/variable_table.rb +59 -0
- data/lib/doubleshot/resolver/gem_resolver/source.rb +36 -0
- data/lib/doubleshot/resolver/jar_resolver.rb +1 -3
- data/lib/ruby/gem/requirement.rb +9 -0
- data/target/doubleshot.jar +0 -0
- data/test/compiler_spec.rb +31 -3
- data/test/configuration_spec.rb +11 -3
- data/test/dependencies/gem_dependency_spec.rb +3 -17
- data/test/dependencies/jar_dependency_spec.rb +20 -0
- data/test/helper.rb +3 -1
- data/test/helpers/stub_source.rb +120 -0
- data/test/lockfile_spec.rb +9 -17
- data/test/pom_spec.rb +31 -1
- data/test/resolver/gem_resolver/artifact_spec.rb +106 -0
- data/test/resolver/gem_resolver/demand_spec.rb +70 -0
- data/test/resolver/gem_resolver/dependency_spec.rb +33 -0
- data/test/resolver/gem_resolver/gem_source_spec.rb +28 -0
- data/test/resolver/gem_resolver/graph_spec.rb +239 -0
- data/test/resolver/gem_resolver/solver_spec.rb +449 -0
- data/test/resolver/gem_resolver/source_spec.rb +18 -0
- data/test/resolver/gem_resolver_spec.rb +102 -0
- metadata +35 -73
- data/lib/doubleshot/jar.rb +0 -62
data/lib/doubleshot.rb
CHANGED
@@ -18,6 +18,7 @@ require "doubleshot/readonly_collection"
|
|
18
18
|
require "doubleshot/configuration"
|
19
19
|
require "doubleshot/compiler"
|
20
20
|
require "doubleshot/lockfile"
|
21
|
+
require "doubleshot/resolver"
|
21
22
|
|
22
23
|
class Doubleshot
|
23
24
|
|
@@ -85,9 +86,72 @@ class Doubleshot
|
|
85
86
|
end
|
86
87
|
# END: Cleanup tasks
|
87
88
|
|
89
|
+
load_gems! unless @config.runtime.gems.empty? && @config.development.gems.empty?
|
88
90
|
load_jars! unless @config.runtime.jars.empty? && @config.development.jars.empty?
|
89
91
|
end
|
90
92
|
|
93
|
+
def load_gems!
|
94
|
+
if lockfile.gems.empty?
|
95
|
+
dependencies = @config.runtime.gems + @config.development.gems
|
96
|
+
|
97
|
+
puts "Dependencies not locked. Resolving the following:"
|
98
|
+
dependencies.each do |dependency|
|
99
|
+
puts " #{dependency.name}: #{dependency.requirements.map(&:to_s).join(", ")}"
|
100
|
+
end
|
101
|
+
|
102
|
+
unless dependencies.empty?
|
103
|
+
resolver = Resolver::GemResolver.new *@config.gem_repositories
|
104
|
+
puts "Using repositories: #{@config.gem_repositories.map(&:to_s).join(",")}"
|
105
|
+
|
106
|
+
resolver.resolve! dependencies
|
107
|
+
|
108
|
+
puts "Resolved dependencies:"
|
109
|
+
dependencies.each do |dependency|
|
110
|
+
puts " #{dependency.name}: #{dependency.version}"
|
111
|
+
end
|
112
|
+
|
113
|
+
require "rubygems/dependency_installer"
|
114
|
+
Gem::sources = @config.gem_repositories.entries
|
115
|
+
installer = Gem::DependencyInstaller.new domain: :both
|
116
|
+
dependencies.each do |dependency|
|
117
|
+
begin
|
118
|
+
puts "Activating: #{dependency.name} #{dependency.version}"
|
119
|
+
gem dependency.name, dependency.version
|
120
|
+
rescue LoadError
|
121
|
+
puts "Gem not installed! Installing: #{dependency.name} #{dependency.version}"
|
122
|
+
installer.install dependency.name, dependency.version
|
123
|
+
gem dependency.name, dependency.version
|
124
|
+
end
|
125
|
+
lockfile.add dependency
|
126
|
+
end
|
127
|
+
|
128
|
+
dependencies.each { |dependency| lockfile.add dependency }
|
129
|
+
lockfile.flush!
|
130
|
+
end
|
131
|
+
else
|
132
|
+
missing_dependencies = []
|
133
|
+
lockfile.gems.each do |dependency|
|
134
|
+
begin
|
135
|
+
gem dependency.name, dependency.version
|
136
|
+
rescue LoadError
|
137
|
+
missing_dependencies << dependency
|
138
|
+
end
|
139
|
+
end
|
140
|
+
|
141
|
+
unless missing_dependencies.empty?
|
142
|
+
# TODO: Figure out how to use #gem_repositories here
|
143
|
+
require "rubygems/dependency_installer"
|
144
|
+
Gem::sources = @config.gem_repositories.entries
|
145
|
+
installer = Gem::DependencyInstaller.new domain: :both
|
146
|
+
|
147
|
+
missing_dependencies.each do |dependency|
|
148
|
+
installer.install dependency.name, dependency.version
|
149
|
+
gem dependency.name, dependency.version
|
150
|
+
end
|
151
|
+
end
|
152
|
+
end
|
153
|
+
end
|
154
|
+
|
91
155
|
def load_jars!
|
92
156
|
if classpath_cache.exist?
|
93
157
|
# We survived the cleanup checks, go ahead and just load
|
@@ -100,7 +164,7 @@ class Doubleshot
|
|
100
164
|
require jar.path
|
101
165
|
self.classpath << jar.path
|
102
166
|
rescue LoadError
|
103
|
-
warn "Could not load: #{jar.
|
167
|
+
warn "Could not load: #{jar.to_s.inspect}"
|
104
168
|
raise
|
105
169
|
end
|
106
170
|
end
|
@@ -108,46 +172,41 @@ class Doubleshot
|
|
108
172
|
# No classpath_cache exists, we must resolve the paths
|
109
173
|
# to our dependencies, then store the results in
|
110
174
|
# classpath_cache for future processes to use.
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
|
120
|
-
|
121
|
-
jars = Dependencies::JarDependencyList.new
|
122
|
-
lockfile.jars.each do |jar|
|
123
|
-
jars.add jar
|
175
|
+
jars = @config.runtime.jars + @config.development.jars
|
176
|
+
unless jars.empty?
|
177
|
+
|
178
|
+
resolver = Resolver::JarResolver.new(*@config.mvn_repositories)
|
179
|
+
|
180
|
+
if lockfile.exist? && !lockfile.jars.empty?
|
181
|
+
jars = Dependencies::JarDependencyList.new
|
182
|
+
lockfile.jars.each do |jar|
|
183
|
+
jars.add jar
|
184
|
+
end
|
124
185
|
end
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
|
129
|
-
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
|
134
|
-
|
135
|
-
|
136
|
-
|
137
|
-
|
138
|
-
|
139
|
-
|
140
|
-
|
141
|
-
warn "Could not load: #{jar.path.inspect}"
|
142
|
-
raise
|
186
|
+
|
187
|
+
resolver.resolve! jars
|
188
|
+
|
189
|
+
jars.each { |jar| lockfile.add jar }
|
190
|
+
lockfile.flush!
|
191
|
+
|
192
|
+
cache = {}
|
193
|
+
jars.each do |jar|
|
194
|
+
cache[jar.to_s] = jar.path.to_s
|
195
|
+
begin
|
196
|
+
require jar.path
|
197
|
+
self.classpath << jar.path
|
198
|
+
rescue LoadError
|
199
|
+
warn "Could not load: #{jar.to_s.inspect}"
|
200
|
+
raise
|
201
|
+
end
|
143
202
|
end
|
144
|
-
|
145
|
-
|
146
|
-
|
147
|
-
|
148
|
-
end
|
149
|
-
end
|
150
|
-
end
|
203
|
+
|
204
|
+
classpath_cache.open("w+") do |file|
|
205
|
+
file << cache.to_yaml
|
206
|
+
end
|
207
|
+
end # unless jars.empty?
|
208
|
+
end # if classpath_cache.exist?
|
209
|
+
end # def load_jars!
|
151
210
|
|
152
211
|
def classpath_cache
|
153
212
|
@classpath_cache ||= Pathname(".classpath.cache")
|
@@ -169,6 +228,7 @@ class Doubleshot
|
|
169
228
|
jar = Dependencies::JarDependency.new(coordinate)
|
170
229
|
jar.path = path
|
171
230
|
lockfile.add jar
|
231
|
+
# puts "Added coordinate: #{coordinate.inspect} as #{jar.to_s.inspect}"
|
172
232
|
end
|
173
233
|
|
174
234
|
lockfile.flush!
|
@@ -177,6 +237,7 @@ class Doubleshot
|
|
177
237
|
file << resolved.to_yaml
|
178
238
|
end
|
179
239
|
else
|
240
|
+
# TODO: This is problematic since Maven and Aether resolve different dependencies...
|
180
241
|
setup!
|
181
242
|
end
|
182
243
|
end
|
@@ -37,22 +37,25 @@ class Doubleshot::CLI::Commands::Gem < Doubleshot::CLI
|
|
37
37
|
Doubleshot::CLI::Commands::Build.start(args)
|
38
38
|
end
|
39
39
|
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
40
|
+
target = doubleshot.config.target
|
41
|
+
jarfile = target + "#{doubleshot.config.project}.jar"
|
42
|
+
jarfile.delete if jarfile.exist?
|
43
|
+
|
44
|
+
begin
|
45
|
+
unless Pathname::glob(doubleshot.config.source.java + "**/*.java").empty?
|
46
|
+
ant.jar jarfile: jarfile, basedir: target do
|
47
|
+
doubleshot.lockfile.jars.each do |jar|
|
48
|
+
zipfileset src: jar.path.expand_path, excludes: "META-INF/*.SF"
|
49
|
+
end
|
49
50
|
end
|
50
51
|
end
|
52
|
+
|
53
|
+
# WARN: This is version specific since in HEAD they've changed this to Gem::Package::build.
|
54
|
+
::Gem::Builder.new(doubleshot.config.gemspec).build
|
55
|
+
ensure
|
56
|
+
jarfile.delete if jarfile.exist?
|
51
57
|
end
|
52
58
|
|
53
|
-
# WARN: This is version specific since in HEAD they've changed this to Gem::Package::build.
|
54
|
-
::Gem::Builder.new(doubleshot.config.gemspec).build
|
55
|
-
|
56
59
|
puts(" Size: %.2fM" % (Pathname(doubleshot.config.gemspec.file_name).size.to_f / 1024 / 1024))
|
57
60
|
|
58
61
|
return 0
|
@@ -22,6 +22,11 @@ class Doubleshot::CLI::Commands::Test < Doubleshot::CLI
|
|
22
22
|
options.build = true
|
23
23
|
end
|
24
24
|
|
25
|
+
options.force_tests = false
|
26
|
+
options.on "--force", "Run tests, even if doubleshot_test.pid exists." do
|
27
|
+
options.force_tests = true
|
28
|
+
end
|
29
|
+
|
25
30
|
options.separator ""
|
26
31
|
options.separator "Summary: #{summary}"
|
27
32
|
end
|
@@ -29,6 +34,24 @@ class Doubleshot::CLI::Commands::Test < Doubleshot::CLI
|
|
29
34
|
|
30
35
|
def self.start(args)
|
31
36
|
options = self.options.parse!(args)
|
37
|
+
|
38
|
+
@@pid_file = Pathname(".doubleshot_test.pid")
|
39
|
+
if @@pid_file.exist? && !options.force_tests
|
40
|
+
|
41
|
+
begin
|
42
|
+
if Process.getpgid(@@pid_file.read.to_i)
|
43
|
+
puts ".doubleshot_test.pid exists: Are you running tests elsewhere? (Use --force to override.)"
|
44
|
+
exit 1
|
45
|
+
end
|
46
|
+
rescue Errno::ESRCH
|
47
|
+
@@pid_file.delete
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
@@pid_file.open("w") do |pid|
|
52
|
+
pid << $$
|
53
|
+
end
|
54
|
+
|
32
55
|
doubleshot = Doubleshot::current
|
33
56
|
|
34
57
|
if Pathname::glob(doubleshot.config.source.tests + "**/*_{spec,test}.rb").empty?
|
@@ -53,21 +76,25 @@ class Doubleshot::CLI::Commands::Test < Doubleshot::CLI
|
|
53
76
|
end
|
54
77
|
end
|
55
78
|
|
56
|
-
|
57
|
-
|
58
|
-
watcher = new(doubleshot.config, options.ci_test)
|
79
|
+
watcher = new(doubleshot.config, options.ci_test, options.force_tests)
|
59
80
|
watcher.run
|
60
81
|
end
|
61
82
|
|
62
|
-
def initialize(config, ci_test)
|
83
|
+
def initialize(config, ci_test, force_tests)
|
63
84
|
@config = config
|
64
85
|
@interrupted = false
|
65
86
|
@ci_test = ci_test
|
87
|
+
@force_tests = force_tests
|
66
88
|
|
67
89
|
# Hit Ctrl-C once to re-run all specs; twice to exit the program.
|
68
90
|
Signal.trap("INT") do
|
69
91
|
if @interrupted
|
70
92
|
puts "\nShutting down..."
|
93
|
+
|
94
|
+
unless @force_tests
|
95
|
+
@@pid_file.delete if @@pid_file.exist?
|
96
|
+
end
|
97
|
+
|
71
98
|
exit 0
|
72
99
|
else
|
73
100
|
@interrupted = true
|
@@ -79,7 +106,11 @@ class Doubleshot::CLI::Commands::Test < Doubleshot::CLI
|
|
79
106
|
|
80
107
|
def run
|
81
108
|
if @ci_test
|
82
|
-
run_all_specs
|
109
|
+
exit_status = run_all_specs
|
110
|
+
unless @force_tests
|
111
|
+
@@pid_file.delete if @@pid_file.exist?
|
112
|
+
end
|
113
|
+
exit_status
|
83
114
|
else
|
84
115
|
Doubleshot::CLI::Commands::Build.start([ "--conditional" ])
|
85
116
|
# Output here just so you know when changes will be
|
@@ -91,6 +122,8 @@ class Doubleshot::CLI::Commands::Test < Doubleshot::CLI
|
|
91
122
|
|
92
123
|
private
|
93
124
|
def listener
|
125
|
+
require "listen"
|
126
|
+
|
94
127
|
# This creates a MultiListener
|
95
128
|
Listen.to(@config.source.tests.to_s, @config.source.ruby.to_s, @config.source.java.to_s).change do |modified, added, removed|
|
96
129
|
modified.each do |location|
|
@@ -179,7 +179,7 @@ class Doubleshot
|
|
179
179
|
end
|
180
180
|
|
181
181
|
def gem_repositories
|
182
|
-
ReadonlyCollection.new(@gem_repositories)
|
182
|
+
ReadonlyCollection.new(@gem_repositories.empty? ? [ Resolver::GemResolver::DEFAULT_REPOSITORY ] : @gem_repositories)
|
183
183
|
end
|
184
184
|
|
185
185
|
def mvn_repository(uri)
|
@@ -188,7 +188,7 @@ class Doubleshot
|
|
188
188
|
end
|
189
189
|
|
190
190
|
def mvn_repositories
|
191
|
-
ReadonlyCollection.new(@mvn_repositories)
|
191
|
+
ReadonlyCollection.new(@mvn_repositories.empty? ? [ Resolver::JarResolver::DEFAULT_REPOSITORY ] : @mvn_repositories)
|
192
192
|
end
|
193
193
|
|
194
194
|
def source
|
@@ -24,20 +24,12 @@ class Doubleshot
|
|
24
24
|
end
|
25
25
|
|
26
26
|
def to_s(long_form = false)
|
27
|
-
if long_form &&
|
28
|
-
"#{name}
|
27
|
+
if long_form && @version
|
28
|
+
"#{name}:#{version}"
|
29
29
|
else
|
30
30
|
@name
|
31
31
|
end
|
32
32
|
end
|
33
|
-
|
34
|
-
# def gemspec
|
35
|
-
# end
|
36
|
-
|
37
|
-
# def dependencies
|
38
|
-
# #gemspec.runtime_dependencies
|
39
|
-
# end
|
40
|
-
|
41
33
|
end
|
42
34
|
end
|
43
35
|
end
|
@@ -6,7 +6,7 @@ class Doubleshot
|
|
6
6
|
|
7
7
|
PACKAGE_TYPES = [ "pom", "jar", "maven-plugin", "ejb", "war", "ear", "rar", "par", "bundle" ]
|
8
8
|
|
9
|
-
attr_reader :group, :artifact, :packaging, :classifier, :version, :path
|
9
|
+
attr_reader :group, :artifact, :packaging, :classifier, :version, :path, :exclusions
|
10
10
|
|
11
11
|
def initialize(maven_coordinate)
|
12
12
|
# This is Maven's default package type, if unspecified.
|
@@ -32,11 +32,13 @@ class Doubleshot
|
|
32
32
|
@classifier = classifier
|
33
33
|
end
|
34
34
|
|
35
|
-
@name = "#{@group}:#{@artifact}:#{@packaging}
|
35
|
+
@name = "#{@group}:#{@artifact}:#{@packaging}:#{@version}"
|
36
36
|
|
37
37
|
if [ @group, @artifact, @packaging, @version ].any? &:blank?
|
38
38
|
raise ArgumentError.new("Invalid coordinate: #{@name}")
|
39
39
|
end
|
40
|
+
|
41
|
+
@exclusions = []
|
40
42
|
end
|
41
43
|
|
42
44
|
def to_s(long_form = false)
|
@@ -47,6 +49,14 @@ class Doubleshot
|
|
47
49
|
@path = Pathname(path.to_s)
|
48
50
|
end
|
49
51
|
|
52
|
+
def exclude(coordinate)
|
53
|
+
if coordinate.split(":").size != 2
|
54
|
+
raise ArgumentError.new("JarDependency#exclude takes a string of format \"groupId:artifactId\", you provided #{coordinate.inspect}")
|
55
|
+
end
|
56
|
+
@exclusions << coordinate
|
57
|
+
self
|
58
|
+
end
|
59
|
+
|
50
60
|
private
|
51
61
|
|
52
62
|
def packaging=(value = "jar")
|
data/lib/doubleshot/lockfile.rb
CHANGED
@@ -69,14 +69,17 @@ class Doubleshot
|
|
69
69
|
|
70
70
|
def load
|
71
71
|
unless @loaded
|
72
|
-
(data["JARS"] || []).each do |
|
73
|
-
@jars.add Dependencies::JarDependency.new(
|
72
|
+
(data["JARS"] || []).each do |coordinate|
|
73
|
+
@jars.add Dependencies::JarDependency.new(coordinate)
|
74
74
|
end
|
75
75
|
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
76
|
+
(data["GEMS"] || []).each do |spec|
|
77
|
+
name, version = *spec.split(":")
|
78
|
+
dependency = Dependencies::GemDependency.new(name)
|
79
|
+
dependency.lock(version)
|
80
|
+
|
81
|
+
@gems.add dependency
|
82
|
+
end
|
80
83
|
end
|
81
84
|
|
82
85
|
@loaded = true
|
data/lib/doubleshot/pom.rb
CHANGED
@@ -29,7 +29,20 @@ class Doubleshot
|
|
29
29
|
<type>#{jar.packaging}</type>
|
30
30
|
#{
|
31
31
|
"<classifier>#{jar.classifier}</classifier>" unless jar.classifier.blank?
|
32
|
-
}<version>#{jar.version}</version
|
32
|
+
}<version>#{jar.version}</version>#{
|
33
|
+
unless jar.exclusions.empty?
|
34
|
+
"\n <exclusions>\n " +
|
35
|
+
jar.exclusions.map do |exclusion|
|
36
|
+
groupId, artifactId = exclusion.split(":")
|
37
|
+
<<-EXCLUSION.strip
|
38
|
+
<exclusion>
|
39
|
+
<groupId>#{groupId}</groupId>
|
40
|
+
<artifactId>#{artifactId}</artifactId>
|
41
|
+
</exclusion>
|
42
|
+
EXCLUSION
|
43
|
+
end.join("\n ") +
|
44
|
+
"\n </exclusions>"
|
45
|
+
end}
|
33
46
|
</dependency>
|
34
47
|
JAR
|
35
48
|
end.join("\n ") +
|
@@ -39,4 +52,4 @@ class Doubleshot
|
|
39
52
|
EOS
|
40
53
|
end
|
41
54
|
end
|
42
|
-
end
|
55
|
+
end
|