jbundler 0.2.2 → 0.3.0
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/Gemfile.lock +2 -2
- data/Readme.md +55 -48
- data/bin/jbundle +27 -4
- data/lib/jbundler.jar +0 -0
- data/lib/jbundler.rb +4 -4
- data/lib/jbundler/aether.rb +6 -1
- data/lib/jbundler/classpath_file.rb +3 -3
- data/lib/jbundler/cli.rb +29 -18
- data/lib/jbundler/config.rb +71 -0
- data/lib/jbundler/config.rb~ +145 -0
- data/lib/jbundler/gemfile_lock.rb +4 -0
- data/lib/jbundler/lazy.rb +82 -0
- data/lib/jbundler/lazy.rb~ +24 -0
- data/spec/classpath_file_spec.rb +18 -10
- metadata +8 -4
data/Gemfile.lock
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
PATH
|
2
2
|
remote: .
|
3
3
|
specs:
|
4
|
-
jbundler (0.
|
4
|
+
jbundler (0.3.0)
|
5
5
|
ruby-maven (= 3.0.4.0.29.0)
|
6
6
|
|
7
7
|
GEM
|
@@ -17,7 +17,7 @@ GEM
|
|
17
17
|
diff-lcs (1.1.3)
|
18
18
|
gherkin (2.9.3-java)
|
19
19
|
json (>= 1.4.6)
|
20
|
-
json (1.7.
|
20
|
+
json (1.7.5-java)
|
21
21
|
maven-tools (0.29.3)
|
22
22
|
minitest (2.10.1)
|
23
23
|
rake (0.9.2.2)
|
data/Readme.md
CHANGED
@@ -11,90 +11,97 @@ manage jar dependencies similar than **bundler** manages gem dependencies.
|
|
11
11
|
|
12
12
|
## get started
|
13
13
|
|
14
|
-
|
14
|
+
install JBundler with
|
15
|
+
|
16
|
+
jruby -S gem install jbundler
|
17
|
+
|
18
|
+
first create a **Jarfile**, something like
|
19
|
+
|
20
|
+
jar 'org.yaml:snakeyaml'
|
21
|
+
jar 'org.slf4j:slf4j-simple', '>1.1'
|
22
|
+
|
23
|
+
### together with Bundler
|
24
|
+
|
25
|
+
just add it as **first** entry in your *Gemfile*
|
15
26
|
|
16
27
|
```gem 'jbundler'```
|
17
28
|
|
18
|
-
|
29
|
+
and now install the bundle both **gems and jars**
|
19
30
|
|
20
|
-
|
31
|
+
jbundle install
|
21
32
|
|
22
|
-
|
33
|
+
#### Gemfile only
|
23
34
|
|
24
|
-
|
35
|
+
if there is only a **Gemfile** and no Jarfile **jbundler** just handles all the declared [jar dependencies of gems](https://github.com/mkristian/jbundler/wiki/Build). it will only look into gems which bundler loaded.
|
25
36
|
|
26
|
-
|
37
|
+
#### Gemfile and Jarfile
|
27
38
|
|
28
|
-
|
39
|
+
if there is only a **Gemfile** and no Jarfile **jbundler** handles all the declared [jar dependencies of gems](https://github.com/mkristian/jbundler/wiki/Build) as well all the jars from the Jarfile. it will only look into gems which bundler loaded.
|
29
40
|
|
30
|
-
|
41
|
+
### without Bundler - Jarfile only
|
31
42
|
|
32
|
-
|
33
|
-
jruby -S bundle install
|
34
|
-
jruby -S bundle exec info.rb
|
43
|
+
requiring **jbundler** will trigger the classpath setup
|
35
44
|
|
36
|
-
|
45
|
+
```require 'jbundler'```
|
37
46
|
|
38
|
-
|
47
|
+
this you can use with **rubygems** or **isolate** or . . .
|
39
48
|
|
40
|
-
|
49
|
+
### Jarfile
|
41
50
|
|
42
|
-
|
51
|
+
more info about the **[Jarfile](https://github.com/torquebox/maven-tools/wiki/Jarfile)** and about [versions](https://github.com/torquebox/maven-tools/wiki/Versions).
|
43
52
|
|
44
|
-
|
53
|
+
for adding a maven repository see [Jarfile](https://github.com/torquebox/maven-tools/wiki/Jarfile).
|
54
|
+
|
55
|
+
## console ##
|
45
56
|
|
46
|
-
|
57
|
+
like bundler there is a console which sets up the gems (if there is Gemfile otherwise that part get skipped) and sets up the classloader:
|
47
58
|
|
48
|
-
|
59
|
+
jbundler console
|
49
60
|
|
50
|
-
|
51
|
-
source 'second', "http://example.org/repo"
|
52
|
-
source "http://example.org/repo/3"
|
53
|
-
|
54
|
-
|
55
|
-
## jar/pom dependencies ##
|
61
|
+
further it adds two methods to the root level:
|
56
62
|
|
57
|
-
|
63
|
+
> jars
|
58
64
|
|
59
|
-
|
65
|
+
to list the loaded jars and
|
60
66
|
|
61
|
-
jar 'org.
|
62
|
-
jar 'org.sonatype.aether:aether-api', '1.13'
|
67
|
+
> jar 'org.yaml:snakeyaml'
|
63
68
|
|
64
|
-
|
69
|
+
using the same syntax as use in the **Jarfile**. there are limitations with such a lazy jar loading but it is very convenient when trying out things.
|
65
70
|
|
66
|
-
|
67
|
-
s.name = 'gem_with_jar'
|
68
|
-
s.version = '0.0.0'
|
69
|
-
s.requirements << "jar 'org.slf4j:slf4j-api', '1.5.10'"
|
70
|
-
end
|
71
|
-
|
72
|
-
### maven like version ###
|
71
|
+
## lazy jar loading ##
|
73
72
|
|
74
|
-
|
73
|
+
require 'jbundler/lazy'
|
74
|
+
include JBundler::Lazy
|
75
|
+
|
76
|
+
will offer the same `jar`/`jars` method than you have inside the console.
|
75
77
|
|
76
|
-
|
78
|
+
## example ##
|
77
79
|
|
78
|
-
|
80
|
+
**please first build the jar file for the jbundler gem, see [Build](https://github.com/mkristian/jbundler/wiki/Build).**
|
79
81
|
|
80
|
-
|
82
|
+
*src/example/my_project* has a Gemfile which uses a gem which depends on jar dependency. see *src/example/gem_with_jar/gem_with_jar.gemspec* how the jar gets declared.
|
81
83
|
|
82
|
-
|
83
|
-
pom 'my.group:my-artifact-id', '=1.2.3'
|
84
|
-
jar 'my.group.id:artifact-id', '>1.2.3'
|
85
|
-
jar 'my.group:artifact-id', '>1.2.3', '=<2.0.1'
|
84
|
+
execute *src/example/my_project/info.rb* to see it in action:
|
86
85
|
|
87
|
-
|
86
|
+
cd src/example/my_project
|
87
|
+
jbundle install
|
88
|
+
bundle exec info.rb
|
89
|
+
|
90
|
+
## limitations ##
|
88
91
|
|
89
|
-
|
92
|
+
update of single artifacts is not possible.
|
93
|
+
|
94
|
+
since the version resolution happens in two steps - first the gems then the jars/poms - it is possible in case of a failure that there is a valid gems/jars version resolution which satisfies all version contraints. so there is plenty of space for improvements (like maven could resolve the gems as well, etc)
|
90
95
|
|
91
|
-
|
96
|
+
**Jarfile** is **not** a DSL but it could use a ruby DSL to read the data (any contribution welcome).
|
92
97
|
|
98
|
+
jbundler does not yet obey the **$HOME/.m2/settings.xml** from maven where you usually declare proxies, mirrors, etc.
|
99
|
+
|
93
100
|
## update ##
|
94
101
|
|
95
102
|
update of a single artifact is not possible (yet). but to update the whole set of artifacts just delete the lockfile *Jarfile.lock*
|
96
103
|
|
97
|
-
if jbundler sees that **Gemfile.lock** or **Jarfile** is newer then the **.jbundler/classpath.rb** file then jbundler tries to gracefully upgrade towards the changes.
|
104
|
+
if jbundler sees that **Gemfile.lock** or **Jarfile** is newer then the **.jbundler/classpath.rb** file then jbundler tries to gracefully upgrade towards the changes.
|
98
105
|
|
99
106
|
## meta-fu ##
|
100
107
|
|
data/bin/jbundle
CHANGED
@@ -9,11 +9,34 @@ if ARGV[0] == 'help'
|
|
9
9
|
|
10
10
|
else
|
11
11
|
|
12
|
-
load Gem.bin_path('bundler', 'bundle')
|
13
|
-
|
14
12
|
ARGV << 'install' if ARGV.size == 0
|
15
|
-
require 'jbundler/cli'
|
16
13
|
|
17
|
-
|
14
|
+
if ARGV[0] == 'console'
|
15
|
+
require 'irb'
|
16
|
+
require 'jbundler/lazy'
|
17
|
+
include JBundler::Lazy
|
18
|
+
end
|
19
|
+
|
20
|
+
begin
|
21
|
+
load Gem.bin_path('bundler', 'bundle')
|
22
|
+
rescue Exception
|
23
|
+
if ARGV[0] == 'console'
|
24
|
+
ARGV.shift
|
25
|
+
require 'jbundler'
|
26
|
+
if defined? JBUNDLER_CLASSPATH
|
27
|
+
warn 'Jarfile dependencies loaded'
|
28
|
+
else
|
29
|
+
warn 'Could not locate Jarfile'
|
30
|
+
|
31
|
+
end
|
32
|
+
IRB.start
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
if ARGV[0] && ['install', 'update', 'show'].member?(ARGV[0])
|
37
|
+
require 'jbundler/cli'
|
38
|
+
|
39
|
+
JBundler::Cli.start
|
40
|
+
end
|
18
41
|
|
19
42
|
end
|
data/lib/jbundler.jar
CHANGED
Binary file
|
data/lib/jbundler.rb
CHANGED
@@ -3,14 +3,14 @@ require 'jbundler/classpath_file'
|
|
3
3
|
require 'jbundler/gemfile_lock'
|
4
4
|
require 'jbundler/aether'
|
5
5
|
|
6
|
-
config = JBundler::
|
6
|
+
config = JBundler::Config.new
|
7
7
|
|
8
8
|
jarfile = Maven::Tools::Jarfile.new(config.jarfile)
|
9
9
|
if config.skip
|
10
10
|
warn "skip jbundler setup"
|
11
11
|
else
|
12
12
|
classpath_file = JBundler::ClasspathFile.new(config.classpath_file)
|
13
|
-
gemfile_lock = JBundler::GemfileLock.new(jarfile, config.
|
13
|
+
gemfile_lock = JBundler::GemfileLock.new(jarfile, config.gemfile_lock)
|
14
14
|
|
15
15
|
if classpath_file.needs_update?(jarfile, gemfile_lock)
|
16
16
|
aether = JBundler::AetherRuby.new(config)
|
@@ -21,11 +21,11 @@ else
|
|
21
21
|
|
22
22
|
aether.resolve
|
23
23
|
|
24
|
-
classpath_file.generate(aether.
|
24
|
+
classpath_file.generate(aether.classpath_array)
|
25
25
|
jarfile.generate_lockfile(aether.resolved_coordinates)
|
26
26
|
end
|
27
27
|
|
28
|
-
if classpath_file.exists?
|
28
|
+
if classpath_file.exists? && jarfile.exists_lock?
|
29
29
|
require 'java'
|
30
30
|
classpath_file.require_classpath
|
31
31
|
if config.verbose
|
data/lib/jbundler/aether.rb
CHANGED
@@ -1,4 +1,5 @@
|
|
1
1
|
require 'yaml'
|
2
|
+
require 'jbundler/config'
|
2
3
|
|
3
4
|
module JBundler
|
4
5
|
|
@@ -84,7 +85,7 @@ module JBundler
|
|
84
85
|
java_import 'jbundler.Aether'
|
85
86
|
end
|
86
87
|
|
87
|
-
def initialize(config =
|
88
|
+
def initialize(config = Config.new)
|
88
89
|
unless defined? Aether
|
89
90
|
self.class.setup_classloader
|
90
91
|
end
|
@@ -117,6 +118,10 @@ module JBundler
|
|
117
118
|
end
|
118
119
|
end
|
119
120
|
|
121
|
+
def classpath_array
|
122
|
+
classpath.split(/#{File::PATH_SEPARATOR}/)
|
123
|
+
end
|
124
|
+
|
120
125
|
def repositories
|
121
126
|
@aether.repositories
|
122
127
|
end
|
@@ -19,14 +19,14 @@ module JBundler
|
|
19
19
|
end
|
20
20
|
|
21
21
|
def needs_update?(jarfile, gemfile_lock)
|
22
|
-
!exists? || !jarfile.exists_lock? || (jarfile.exists? && (jarfile.mtime > mtime)) || (jarfile.exists_lock? && (jarfile.mtime_lock > mtime)) || (gemfile_lock.mtime > mtime)
|
22
|
+
(jarfile.exists? || gemfile_lock.exists?) && (!exists? || !jarfile.exists_lock? || (jarfile.exists? && (jarfile.mtime > mtime)) || (jarfile.exists_lock? && (jarfile.mtime_lock > mtime)) || (gemfile_lock.exists? && (gemfile_lock.mtime > mtime)))
|
23
23
|
end
|
24
24
|
|
25
|
-
def generate(
|
25
|
+
def generate(classpath_array)
|
26
26
|
FileUtils.mkdir_p(File.dirname(@classpathfile))
|
27
27
|
File.open(@classpathfile, 'w') do |f|
|
28
28
|
f.puts "JBUNDLER_CLASSPATH = []"
|
29
|
-
|
29
|
+
classpath_array.each do |path|
|
30
30
|
f.puts "JBUNDLER_CLASSPATH << '#{path}'" unless path =~ /pom$/
|
31
31
|
end
|
32
32
|
f.puts "JBUNDLER_CLASSPATH.freeze"
|
data/lib/jbundler/cli.rb
CHANGED
@@ -5,11 +5,34 @@ module JBundler
|
|
5
5
|
def mvn
|
6
6
|
@mvn ||= Maven::RubyMaven.new
|
7
7
|
end
|
8
|
+
|
9
|
+
def do_show
|
10
|
+
require 'java'
|
11
|
+
require 'jbundler/config'
|
12
|
+
require 'jbundler/classpath_file'
|
13
|
+
config = JBundler::Config.new
|
14
|
+
classpath_file = JBundler::ClasspathFile.new(config.classpath_file)
|
15
|
+
if classpath_file.exists?
|
16
|
+
classpath_file.require_classpath
|
17
|
+
puts "JBundler classpath:"
|
18
|
+
JBUNDLER_CLASSPATH.each do |path|
|
19
|
+
puts " * #{path}"
|
20
|
+
end
|
21
|
+
else
|
22
|
+
puts "JBundler classpath is not installed."
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
desc 'console', 'irb session with gems and/or jars and with lazy jar loading.'
|
28
|
+
def console
|
29
|
+
# dummy - never executed !!!
|
8
30
|
end
|
9
31
|
|
10
32
|
desc 'install', "first `bundle install` is called and then the jar dependencies will be installed. for more details see `bundle help install`, jbundler will ignore all options. the install command is also the default when no command is given."
|
11
33
|
def install
|
12
34
|
require 'jbundler'
|
35
|
+
do_show
|
13
36
|
puts 'Your jbundle is complete! Use `jbundle show` to see where the bundled jars are installed.'
|
14
37
|
end
|
15
38
|
|
@@ -17,11 +40,12 @@ module JBundler
|
|
17
40
|
def update
|
18
41
|
if ARGV.size == 1
|
19
42
|
require 'java'
|
20
|
-
require 'jbundler/
|
21
|
-
config = JBundler::
|
22
|
-
FileUtils.rm_f(config.
|
43
|
+
require 'jbundler/config'
|
44
|
+
config = JBundler::Config.new
|
45
|
+
FileUtils.rm_f(config.jarfile_lock)
|
23
46
|
|
24
47
|
require 'jbundler'
|
48
|
+
do_show
|
25
49
|
puts 'Your jbundle is updated! Use `jbundle show` to see where the bundled jars are installed.'
|
26
50
|
end
|
27
51
|
end
|
@@ -29,21 +53,8 @@ module JBundler
|
|
29
53
|
desc 'show', "first `bundle show` is called and if there are no options then the jar dependencies will be displayed. for more details see `bundle help show`."
|
30
54
|
def show
|
31
55
|
if ARGV.size == 1
|
32
|
-
|
33
|
-
|
34
|
-
require 'jbundler/classpath_file'
|
35
|
-
config = JBundler::AetherConfig.new
|
36
|
-
classpath_file = JBundler::ClasspathFile.new('.jbundler/classpath.rb')#config.classpath_file)
|
37
|
-
if classpath_file.exists?
|
38
|
-
classpath_file.require_classpath
|
39
|
-
puts "JBundler classpath:"
|
40
|
-
JBUNDLER_CLASSPATH.each do |path|
|
41
|
-
puts " * #{path}"
|
42
|
-
end
|
43
|
-
else
|
44
|
-
puts "JBundler classpath is not installed."
|
45
|
-
end
|
46
|
-
end
|
56
|
+
do_show
|
57
|
+
end
|
47
58
|
end
|
48
59
|
end
|
49
60
|
end
|
@@ -0,0 +1,71 @@
|
|
1
|
+
require 'yaml'
|
2
|
+
|
3
|
+
module JBundler
|
4
|
+
|
5
|
+
# allow yaml config in $HOME/.jbundlerrc and $PWD/.jbundlerrc
|
6
|
+
class Config
|
7
|
+
|
8
|
+
attr_accessor :verbose, :local_repository, :jarfile, :gemfile, :skip
|
9
|
+
|
10
|
+
def initialize
|
11
|
+
file = '.jbundlerrc'
|
12
|
+
homefile = File.join(ENV['HOME'], file)
|
13
|
+
home_config = YAML.load_file(homefile) if File.exists?(homefile)
|
14
|
+
pwd_config = YAML.load_file(file) if File.exists?(file)
|
15
|
+
@config = (home_config || {}).merge(pwd_config || {})
|
16
|
+
end
|
17
|
+
|
18
|
+
if defined? JRUBY_VERSION
|
19
|
+
def jbundler_env(key)
|
20
|
+
ENV[key.upcase.gsub(/./, '_')] || java.lang.System.getProperty(key.downcase.gsub(/_/, '.')) || @config[key.downcase.sub(/^j?bundler/, '').sub(/./, '_')]
|
21
|
+
end
|
22
|
+
else
|
23
|
+
def jbundler_env(key)
|
24
|
+
ENV[key.upcase.gsub(/./, '_')] || @config[key.downcase.sub(/^j?bundler/, '').sub(/./, '_')]
|
25
|
+
end
|
26
|
+
end
|
27
|
+
private :jbundler_env
|
28
|
+
|
29
|
+
def skip
|
30
|
+
skip = jbundler_env('JBUNDLE_SKIP')
|
31
|
+
# defaults to false
|
32
|
+
@skip ||= skip && skip != 'false'
|
33
|
+
end
|
34
|
+
|
35
|
+
def verbose
|
36
|
+
verbose = jbundler_env('JBUNDLE_VERBOSE')
|
37
|
+
# defaults to false
|
38
|
+
@verbose ||= verbose && verbose != 'false'
|
39
|
+
end
|
40
|
+
|
41
|
+
def jarfile
|
42
|
+
if File.exists?('Mvnfile')
|
43
|
+
warn "'Mvnfile' name is deprecated, please use 'Jarfile' instead"
|
44
|
+
@jarfile = 'Mvnfile'
|
45
|
+
end
|
46
|
+
@jarfile ||= jbundler_env('JBUNDLE_JARFILE') || 'Jarfile'
|
47
|
+
end
|
48
|
+
|
49
|
+
def jarfile_lock
|
50
|
+
"#{jarfile}.lock"
|
51
|
+
end
|
52
|
+
|
53
|
+
def gemfile
|
54
|
+
@gemfile ||= jbundler_env('BUNDLE_GEMFILE') || 'Gemfile'
|
55
|
+
end
|
56
|
+
|
57
|
+
def gemfile_lock
|
58
|
+
"#{gemfile}.lock"
|
59
|
+
end
|
60
|
+
|
61
|
+
def classpath_file
|
62
|
+
'.jbundler/classpath.rb'
|
63
|
+
end
|
64
|
+
|
65
|
+
def local_repository
|
66
|
+
# use maven default local repo as default
|
67
|
+
@local_maven_repository ||= (jbundler_env('JBUNDLE_LOCAL_REPOSITORY') ||
|
68
|
+
File.join( ENV['HOME'], ".m2", "repository"))
|
69
|
+
end
|
70
|
+
end
|
71
|
+
end
|
@@ -0,0 +1,145 @@
|
|
1
|
+
require 'yaml'
|
2
|
+
|
3
|
+
module JBundler
|
4
|
+
|
5
|
+
# allow yaml config in $HOME/.jbundlerrc and $PWD/.jbundlerrc
|
6
|
+
class AetherConfig
|
7
|
+
|
8
|
+
attr_accessor :verbose, :local_repository, :jarfile, :gemfile, :skip
|
9
|
+
|
10
|
+
def initialize
|
11
|
+
file = '.jbundlerrc'
|
12
|
+
homefile = File.join(ENV['HOME'], file)
|
13
|
+
home_config = YAML.load_file(homefile) if File.exists?(homefile)
|
14
|
+
pwd_config = YAML.load_file(file) if File.exists?(file)
|
15
|
+
@config = (home_config || {}).merge(pwd_config || {})
|
16
|
+
end
|
17
|
+
|
18
|
+
if defined? JRUBY_VERSION
|
19
|
+
def jbundler_env(key)
|
20
|
+
ENV[key.upcase.gsub(/./, '_')] || java.lang.System.getProperty(key.downcase.gsub(/_/, '.')) || @config[key.downcase.sub(/^j?bundler/, '').sub(/./, '_')]
|
21
|
+
end
|
22
|
+
else
|
23
|
+
def jbundler_env(key)
|
24
|
+
ENV[key.upcase.gsub(/./, '_')] || @config[key.downcase.sub(/^j?bundler/, '').sub(/./, '_')]
|
25
|
+
end
|
26
|
+
end
|
27
|
+
private :jbundler_env
|
28
|
+
|
29
|
+
def skip
|
30
|
+
skip = jbundler_env('JBUNDLE_SKIP')
|
31
|
+
# defaults to false
|
32
|
+
@skip ||= skip && skip != 'false'
|
33
|
+
end
|
34
|
+
|
35
|
+
def verbose
|
36
|
+
verbose = jbundler_env('JBUNDLE_VERBOSE')
|
37
|
+
# defaults to false
|
38
|
+
@verbose ||= verbose && verbose != 'false'
|
39
|
+
end
|
40
|
+
|
41
|
+
def jarfile
|
42
|
+
if File.exists?('Mvnfile')
|
43
|
+
warn "'Mvnfile' name is deprecated, please use 'Jarfile' instead"
|
44
|
+
@jarfile = 'Mvnfile'
|
45
|
+
end
|
46
|
+
@jarfile ||= jbundler_env('JBUNDLE_JARFILE') || 'Jarfile'
|
47
|
+
end
|
48
|
+
|
49
|
+
def gemfile
|
50
|
+
@gemfile ||= jbundler_env('BUNDLE_GEMFILE') || 'Gemfile'
|
51
|
+
end
|
52
|
+
|
53
|
+
def classpath_file
|
54
|
+
'.jbundler/classpath.rb'
|
55
|
+
end
|
56
|
+
|
57
|
+
def local_repository
|
58
|
+
# use maven default local repo as default
|
59
|
+
@local_maven_repository ||= (jbundler_env('JBUNDLE_LOCAL_REPOSITORY') ||
|
60
|
+
File.join( ENV['HOME'], ".m2", "repository"))
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
64
|
+
class AetherRuby
|
65
|
+
|
66
|
+
def self.setup_classloader
|
67
|
+
require 'java'
|
68
|
+
|
69
|
+
maven_home = File.dirname(File.dirname(Gem.bin_path('ruby-maven',
|
70
|
+
'rmvn')))
|
71
|
+
# TODO reduce to the libs which are really needed
|
72
|
+
Dir.glob(File.join(maven_home, 'lib', "*jar")).each {|path| require path }
|
73
|
+
begin
|
74
|
+
require 'jbundler.jar'
|
75
|
+
rescue LoadError
|
76
|
+
# allow the classes already be added to the classloader
|
77
|
+
begin
|
78
|
+
java_import 'jbundler.Aether'
|
79
|
+
rescue NameError
|
80
|
+
# assume this happens only when working on the git clone
|
81
|
+
raise "jbundler.jar is missing - maybe you need to build it first ? try\n$ rmvn prepare-package -Dmaven.test.skip\n"
|
82
|
+
end
|
83
|
+
end
|
84
|
+
java_import 'jbundler.Aether'
|
85
|
+
end
|
86
|
+
|
87
|
+
def initialize(config = AetherConfig.new)
|
88
|
+
unless defined? Aether
|
89
|
+
self.class.setup_classloader
|
90
|
+
end
|
91
|
+
@aether = Aether.new(config.local_repository, config.verbose)
|
92
|
+
end
|
93
|
+
|
94
|
+
def add_artifact(coordinate, extension = nil)
|
95
|
+
if extension
|
96
|
+
coord = coordinate.split(/:/)
|
97
|
+
coord.insert(2, extension)
|
98
|
+
@aether.add_artifact(coord.join(":"))
|
99
|
+
else
|
100
|
+
@aether.add_artifact(coordinate)
|
101
|
+
end
|
102
|
+
end
|
103
|
+
|
104
|
+
def add_repository(name, url)
|
105
|
+
@aether.add_repository(name, url)
|
106
|
+
end
|
107
|
+
|
108
|
+
def resolve
|
109
|
+
@aether.resolve unless artifacts.empty?
|
110
|
+
end
|
111
|
+
|
112
|
+
def classpath
|
113
|
+
if artifacts.empty?
|
114
|
+
''
|
115
|
+
else
|
116
|
+
@aether.classpath
|
117
|
+
end
|
118
|
+
end
|
119
|
+
|
120
|
+
def classpath_array
|
121
|
+
classpath.split(/#{File::PATH_SEPARATOR}/)
|
122
|
+
end
|
123
|
+
|
124
|
+
def repositories
|
125
|
+
@aether.repositories
|
126
|
+
end
|
127
|
+
|
128
|
+
def artifacts
|
129
|
+
@aether.artifacts
|
130
|
+
end
|
131
|
+
|
132
|
+
def resolved_coordinates
|
133
|
+
if artifacts.empty?
|
134
|
+
[]
|
135
|
+
else
|
136
|
+
@aether.resolved_coordinates
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
140
|
+
def install(coordinate, file)
|
141
|
+
@aether.install(coordinate, file)
|
142
|
+
end
|
143
|
+
|
144
|
+
end
|
145
|
+
end
|
@@ -0,0 +1,82 @@
|
|
1
|
+
require 'jbundler/aether'
|
2
|
+
require 'maven/tools/coordinate'
|
3
|
+
module JBundler
|
4
|
+
module Lazy
|
5
|
+
|
6
|
+
include Maven::Tools::Coordinate
|
7
|
+
|
8
|
+
def self.included(clazz)
|
9
|
+
begin
|
10
|
+
require 'java'
|
11
|
+
warn ''
|
12
|
+
warn 'lazy jar loading does NOT garantee the consistency of the classloader.'
|
13
|
+
warn 'duplicated jars with different version and other dependency conflicts can easily occur.'
|
14
|
+
warn ''
|
15
|
+
warn 'add new jars with:'
|
16
|
+
warn ''
|
17
|
+
warn "\tjar 'org.yaml:snakeyaml'"
|
18
|
+
warn "\tjar 'org.slf4j:slf4j-simple', '>1.1'"
|
19
|
+
warn ''
|
20
|
+
warn 'show loaded jars with:'
|
21
|
+
warn "\tjars"
|
22
|
+
warn ''
|
23
|
+
rescue LoadError
|
24
|
+
warn 'no jar support possible without JRuby - just launching an IRB session'
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
def jars
|
29
|
+
if jb_classpath.empty?
|
30
|
+
puts "\tno jars loaded via jbundler"
|
31
|
+
else
|
32
|
+
jb_classpath.each do |path|
|
33
|
+
puts "\t#{path}"
|
34
|
+
end
|
35
|
+
end
|
36
|
+
nil
|
37
|
+
end
|
38
|
+
|
39
|
+
def jar(name, *version)
|
40
|
+
unless defined? JRUBY_VERSION
|
41
|
+
warn 'no jar support possible without JRuby'
|
42
|
+
return
|
43
|
+
end
|
44
|
+
aether.add_artifact("#{name}:#{to_version(*version)}")
|
45
|
+
aether.resolve
|
46
|
+
result = false
|
47
|
+
aether.classpath_array.each do |path|
|
48
|
+
if result ||= (require path)
|
49
|
+
warn "added #{path} to classloader"
|
50
|
+
jb_classpath << path
|
51
|
+
else
|
52
|
+
warn "already loaded: #{path}"
|
53
|
+
end
|
54
|
+
end
|
55
|
+
result
|
56
|
+
end
|
57
|
+
|
58
|
+
private
|
59
|
+
|
60
|
+
def jb_classpath
|
61
|
+
@jb_cp ||= defined?(JBUNDLER_CLASSPATH) ? JBUNDLER_CLASSPATH.dup : []
|
62
|
+
end
|
63
|
+
|
64
|
+
def jb_config
|
65
|
+
@_jb_c ||= JBundler::Config.new
|
66
|
+
end
|
67
|
+
|
68
|
+
def aether
|
69
|
+
@_aether ||=
|
70
|
+
begin
|
71
|
+
aether = JBundler::AetherRuby.new(jb_config)
|
72
|
+
jarfile = Maven::Tools::Jarfile.new(jb_config.jarfile)
|
73
|
+
gemfile_lock = JBundler::GemfileLock.new(jarfile,
|
74
|
+
jb_config.gemfile_lock)
|
75
|
+
jarfile.populate_unlocked(aether)
|
76
|
+
gemfile_lock.populate_dependencies(aether) if gemfile_lock.exists?
|
77
|
+
jarfile.populate_locked(aether)
|
78
|
+
aether
|
79
|
+
end
|
80
|
+
end
|
81
|
+
end
|
82
|
+
end
|
@@ -0,0 +1,24 @@
|
|
1
|
+
module JBundler
|
2
|
+
module Lazy
|
3
|
+
|
4
|
+
def jar(name, version = '[0,)')
|
5
|
+
aether = aether_new
|
6
|
+
aether.add_artifact("#{name}:#{version}")
|
7
|
+
aether.resolve
|
8
|
+
aehter.classpath.each do |path|
|
9
|
+
puts "add #{path} to classloader"
|
10
|
+
require path
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
private
|
15
|
+
|
16
|
+
def jb_config
|
17
|
+
@_jb_c =|| JBundler::AetherConfig.new
|
18
|
+
end
|
19
|
+
|
20
|
+
def aether_new
|
21
|
+
JBundler::AetherRuby.new(jb_config)
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
data/spec/classpath_file_spec.rb
CHANGED
@@ -6,21 +6,26 @@ require 'jbundler/gemfile_lock'
|
|
6
6
|
|
7
7
|
describe JBundler::ClasspathFile do
|
8
8
|
|
9
|
-
let(:workdir) { 'target' }
|
10
|
-
let(:jfile) { File.join(workdir, '
|
11
|
-
let(:gfile_lock) { File.join(workdir, '
|
9
|
+
let(:workdir) { File.join('target', 'tmp') }
|
10
|
+
let(:jfile) { File.join(workdir, 'jarfile') }
|
11
|
+
let(:gfile_lock) { File.join(workdir, 'gemfile.lock') }
|
12
12
|
let(:jfile_lock) { jfile + ".lock"}
|
13
|
-
let(:cpfile) { File.join(workdir, '
|
13
|
+
let(:cpfile) { File.join(workdir, 'cp.rb') }
|
14
14
|
let(:jarfile) { Maven::Tools::Jarfile.new(jfile) }
|
15
15
|
let(:gemfile_lock) { JBundler::GemfileLock.new(jarfile, gfile_lock) }
|
16
16
|
subject { JBundler::ClasspathFile.new(cpfile) }
|
17
17
|
|
18
18
|
before do
|
19
|
-
|
20
|
-
|
19
|
+
FileUtils.mkdir_p(workdir)
|
20
|
+
Dir[File.join(workdir, '*')].each { |f| FileUtils.rm_f f }
|
21
21
|
end
|
22
22
|
|
23
|
-
it 'needs update when all files are missing' do
|
23
|
+
it 'needs no update when all files are missing' do
|
24
|
+
subject.needs_update?(jarfile, gemfile_lock).must_equal false
|
25
|
+
end
|
26
|
+
|
27
|
+
it 'needs update when only gemfile' do
|
28
|
+
FileUtils.touch gfile_lock
|
24
29
|
subject.needs_update?(jarfile, gemfile_lock).must_equal true
|
25
30
|
end
|
26
31
|
|
@@ -30,6 +35,7 @@ describe JBundler::ClasspathFile do
|
|
30
35
|
end
|
31
36
|
|
32
37
|
it 'needs update when jarfilelock is missing' do
|
38
|
+
FileUtils.touch gfile_lock
|
33
39
|
FileUtils.touch jfile
|
34
40
|
FileUtils.touch cpfile
|
35
41
|
subject.needs_update?(jarfile, gemfile_lock).must_equal true
|
@@ -42,7 +48,8 @@ describe JBundler::ClasspathFile do
|
|
42
48
|
subject.needs_update?(jarfile, gemfile_lock).must_equal false
|
43
49
|
end
|
44
50
|
|
45
|
-
it 'needs update when
|
51
|
+
it 'needs update when jar file is the youngest' do
|
52
|
+
FileUtils.touch gfile_lock
|
46
53
|
FileUtils.touch jfile_lock
|
47
54
|
FileUtils.touch cpfile
|
48
55
|
sleep 1
|
@@ -50,7 +57,8 @@ describe JBundler::ClasspathFile do
|
|
50
57
|
subject.needs_update?(jarfile, gemfile_lock).must_equal true
|
51
58
|
end
|
52
59
|
|
53
|
-
it 'needs update when
|
60
|
+
it 'needs update when jar lockfile is the youngest' do
|
61
|
+
FileUtils.touch gfile_lock
|
54
62
|
FileUtils.touch jfile
|
55
63
|
FileUtils.touch cpfile
|
56
64
|
sleep 1
|
@@ -68,7 +76,7 @@ describe JBundler::ClasspathFile do
|
|
68
76
|
end
|
69
77
|
|
70
78
|
it 'generates a classpath ruby file' do
|
71
|
-
subject.generate("a:b:c:d:f:".
|
79
|
+
subject.generate("a:b:c:d:f:".split(File::PATH_SEPARATOR))
|
72
80
|
File.read(cpfile).must_equal <<-EOF
|
73
81
|
JBUNDLER_CLASSPATH = []
|
74
82
|
JBUNDLER_CLASSPATH << 'a'
|
metadata
CHANGED
@@ -2,7 +2,7 @@
|
|
2
2
|
name: jbundler
|
3
3
|
version: !ruby/object:Gem::Version
|
4
4
|
prerelease:
|
5
|
-
version: 0.
|
5
|
+
version: 0.3.0
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
8
8
|
- Kristian Meier
|
@@ -10,7 +10,7 @@ autorequire:
|
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
12
|
|
13
|
-
date: 2012-08-
|
13
|
+
date: 2012-08-19 00:00:00 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: ruby-maven
|
@@ -49,7 +49,7 @@ dependencies:
|
|
49
49
|
type: :development
|
50
50
|
version_requirements: *id003
|
51
51
|
description: |
|
52
|
-
|
52
|
+
managing jar dependencies with or without bundler. adding bundler like handling of version ranges for jar dependencies.
|
53
53
|
|
54
54
|
email:
|
55
55
|
- m.kristian@web.de
|
@@ -70,13 +70,17 @@ files:
|
|
70
70
|
- lib/jbundler/pom.rb~
|
71
71
|
- lib/jbundler/mavenfile.rb~
|
72
72
|
- lib/jbundler/cli.rb
|
73
|
+
- lib/jbundler/lazy.rb~
|
73
74
|
- lib/jbundler/maven_version.rb~
|
75
|
+
- lib/jbundler/config.rb
|
74
76
|
- lib/jbundler/classpath_file.rb
|
75
77
|
- lib/jbundler/aether.rb
|
76
78
|
- lib/jbundler/gemfile_lock.rb~
|
77
79
|
- lib/jbundler/gemfile_lock.rb
|
78
80
|
- lib/jbundler/classpath_file.rb~
|
81
|
+
- lib/jbundler/config.rb~
|
79
82
|
- lib/jbundler/aether.rb~
|
83
|
+
- lib/jbundler/lazy.rb
|
80
84
|
- lib/jbundler/maven_util.rb~
|
81
85
|
- lib/jbundler/maven.rb~
|
82
86
|
- spec/maven_util_spec.rb~
|
@@ -120,7 +124,7 @@ rubyforge_project:
|
|
120
124
|
rubygems_version: 1.8.24
|
121
125
|
signing_key:
|
122
126
|
specification_version: 3
|
123
|
-
summary:
|
127
|
+
summary: managing jar dependencies
|
124
128
|
test_files:
|
125
129
|
- spec/classpath_file_spec.rb
|
126
130
|
- spec/pom_spec.rb
|