pompompom 1.0.0 → 1.0.1

Sign up to get free protection for your applications and to get access to all the features.
data/README.mdown CHANGED
@@ -22,7 +22,7 @@ There is a command line tool that can be used to install artifacts:
22
22
 
23
23
  pompompom com.rabbitmq:amqp-client:1.8.0 com.google.inject:guice:2.0
24
24
 
25
- It will create a directory called `lib` and download JARs into it. In the future things may be configurable, and POMs will be cached to make things quicker.
25
+ It will create a directory called `lib` and download JARs into it. By default it will look in the main Maven repository, but you can add more repositories by editing ~/.pompompomrc (which is created automatically on the first run). Downloaded artifacts and POMs are cached in ~/.pompompom.
26
26
 
27
27
  ## Why another dependency management tool, why not use Maven, Buildr, sbt or Ivy?
28
28
 
data/lib/pompompom/cli.rb CHANGED
@@ -1,14 +1,17 @@
1
+ require 'yaml'
2
+
3
+
1
4
  module PomPomPom
2
5
  class Cli
3
- STANDARD_REPOSITORIES = [
4
- 'http://repo1.maven.org/maven2/'
5
- ]
6
-
6
+ STANDARD_REPOSITORIES = %w(http://repo1.maven.org/maven2)
7
7
  DEFAULT_DESTINATION_DIR = 'lib'
8
+ CACHE_DIR = File.expand_path('~/.pompompom')
9
+ CONFIG_FILE = File.expand_path('~/.pompompomrc')
8
10
 
9
11
  def initialize(stdin, stdout, stderr)
10
12
  @stdin, @stdout, @stderr = stdin, stdout, stderr
11
13
  @status_logger = EchoLogger.new(@stderr)
14
+ @downloader = CachingDownloader.new(CACHE_DIR, Downloader.new)
12
15
  end
13
16
 
14
17
  def run!(*args)
@@ -16,23 +19,24 @@ module PomPomPom
16
19
  print_usage
17
20
  return 1
18
21
  end
19
-
22
+
20
23
  resolver = create_resolver
21
24
 
25
+ create_config_file!
22
26
  create_lib_directory!
23
27
 
24
28
  @status_logger.info("Determining transitive dependencies...")
25
29
 
26
30
  dependencies = parse_dependencies(args)
27
31
  dependencies = resolver.find_transitive_dependencies(*dependencies)
28
- dependencies = dependencies.reject { |d| File.exists?(File.join(DEFAULT_DESTINATION_DIR, d.jar_file_name)) }
32
+ dependencies = dependencies.reject { |d| File.exists?(File.join(destination_dir_path, d.jar_file_name)) }
29
33
 
30
34
  if dependencies.empty?
31
35
  @status_logger.info('All dependencies are met')
32
36
  else
33
37
  dependencies.each do |dependency|
34
38
  @status_logger.info(%(Downloading "#{dependency.to_dependency.to_s}"))
35
- resolver.download!(DEFAULT_DESTINATION_DIR, false, dependency)
39
+ resolver.download!(destination_dir_path, false, dependency)
36
40
  end
37
41
  end
38
42
 
@@ -44,14 +48,42 @@ module PomPomPom
44
48
 
45
49
  private
46
50
 
51
+ def create_config_file!
52
+ return if File.exists?(config_file_path)
53
+ File.open(config_file_path, 'w') { |f| f.write(YAML.dump('repositories' => STANDARD_REPOSITORIES))}
54
+ end
55
+
47
56
  def create_lib_directory!
48
- return if File.directory?(DEFAULT_DESTINATION_DIR)
49
- raise %(Cannot create destination, "#{DEFAULT_DESTINATION_DIR}" is a file!) if File.exists?(DEFAULT_DESTINATION_DIR)
50
- Dir.mkdir(DEFAULT_DESTINATION_DIR)
57
+ return if File.directory?(destination_dir_path)
58
+ raise %(Cannot create destination, "#{destination_dir_path}" is a file!) if File.exists?(destination_dir_path)
59
+ Dir.mkdir(destination_dir_path)
51
60
  end
52
61
 
53
62
  def create_resolver
54
- Resolver.new(STANDARD_REPOSITORIES, :logger => @status_logger)
63
+ Resolver.new(
64
+ config[:repositories],
65
+ :logger => @status_logger,
66
+ :downloader => @downloader
67
+ )
68
+ end
69
+
70
+ def config
71
+ @config ||= symbolize_keys(YAML.load(File.read(config_file_path)))
72
+ end
73
+
74
+ def symbolize_keys(h)
75
+ h.keys.inject({}) do |acc, k|
76
+ acc[k.to_sym] = if Hash === h[k] then symbolize_keys(h[k]) else h[k] end
77
+ acc
78
+ end
79
+ end
80
+
81
+ def config_file_path
82
+ CONFIG_FILE
83
+ end
84
+
85
+ def destination_dir_path
86
+ DEFAULT_DESTINATION_DIR
55
87
  end
56
88
 
57
89
  def parse_dependencies(args)
@@ -1,4 +1,7 @@
1
1
  require 'open-uri'
2
+ require 'fileutils'
3
+ require 'uri'
4
+
2
5
 
3
6
  module PomPomPom
4
7
  class Downloader
@@ -9,7 +12,35 @@ module PomPomPom
9
12
 
10
13
  class FilesystemDownloader
11
14
  def get(path)
12
- File.read(path) if File.exists?(path)
15
+ raise %(Cannot read "#{path}": No such file) unless File.exists?(path)
16
+ File.read(path)
17
+ end
18
+ end
19
+
20
+ class CachingDownloader
21
+ def initialize(cache_dir, downloader=Downloader.new)
22
+ @cache_dir, @downloader = cache_dir, downloader
23
+ end
24
+
25
+ def get(url)
26
+ cached = cache_path(url)
27
+ if File.exists?(cached)
28
+ File.read(cached)
29
+ else
30
+ data = @downloader.get(url)
31
+ FileUtils.mkdir_p(File.dirname(cached))
32
+ File.open(cached, 'w') { |f| f.write(data) }
33
+ data
34
+ end
35
+ end
36
+
37
+ private
38
+
39
+ def cache_path(url)
40
+ uri = URI.parse(url)
41
+ path_components = uri.path.sub(%r{^/}, '').split('/')
42
+ path = File.join(@cache_dir, uri.host, *path_components)
43
+ path
13
44
  end
14
45
  end
15
46
  end
data/lib/pompompom.rb CHANGED
@@ -6,5 +6,5 @@ require 'pompompom/downloader'
6
6
  require 'pompompom/resolver'
7
7
 
8
8
  module PomPomPom
9
- VERSION = '1.0.0'
9
+ VERSION = '1.0.1'
10
10
  end
data/pompompom.gemspec CHANGED
@@ -5,7 +5,7 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{pompompom}
8
- s.version = "1.0.0"
8
+ s.version = "1.0.1"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Theo Hultberg"]
@@ -38,6 +38,7 @@ Gem::Specification.new do |s|
38
38
  "pompompom.gemspec",
39
39
  "spec/pompompom/cli_spec.rb",
40
40
  "spec/pompompom/dependency_spec.rb",
41
+ "spec/pompompom/downloader_spec.rb",
41
42
  "spec/pompompom/metadata_spec.rb",
42
43
  "spec/pompompom/pom_spec.rb",
43
44
  "spec/pompompom/resolver_spec.rb",
@@ -96,6 +97,7 @@ Gem::Specification.new do |s|
96
97
  s.test_files = [
97
98
  "spec/pompompom/cli_spec.rb",
98
99
  "spec/pompompom/dependency_spec.rb",
100
+ "spec/pompompom/downloader_spec.rb",
99
101
  "spec/pompompom/metadata_spec.rb",
100
102
  "spec/pompompom/pom_spec.rb",
101
103
  "spec/pompompom/resolver_spec.rb",
@@ -1,6 +1,7 @@
1
1
  require File.expand_path('../../spec_helper', __FILE__)
2
2
  require 'tmpdir'
3
3
  require 'fileutils'
4
+ require 'yaml'
4
5
 
5
6
 
6
7
  module PomPomPom
@@ -13,12 +14,14 @@ module PomPomPom
13
14
  @downloader = FilesystemDownloader.new
14
15
  @resolver = Resolver.new([@repository_path])
15
16
  @cli = Cli.new(@stdin, @stdout, @stderr)
16
- @cli.stub!(:create_resolver).and_return(@resolver)
17
- @cli.stub!(:create_lib_directory!)
18
17
  @tmp_dir = File.join(Dir.tmpdir, 'pompompom')
19
18
  FileUtils.rm_rf(@tmp_dir)
20
19
  Dir.mkdir(@tmp_dir)
21
20
  Dir.chdir(@tmp_dir)
21
+ @config_file_path = File.join(@tmp_dir, '.pompompomrc')
22
+ @cli.stub!(:create_resolver).and_return(@resolver)
23
+ @cli.stub!(:create_lib_directory!)
24
+ @cli.stub!(:config_file_path).and_return(@config_file_path)
22
25
  end
23
26
 
24
27
  after do
@@ -89,5 +92,35 @@ module PomPomPom
89
92
  @cli.run!('com.example:test:9.9').should == 1
90
93
  end
91
94
  end
95
+
96
+ context 'config file' do
97
+ it 'creates the config file if it doesn\'t exist' do
98
+ @cli.run!('net.iconara:pompompom:1.0', 'com.example:test:9.9')
99
+ File.exists?(@config_file_path).should be_true
100
+ end
101
+
102
+ it 'adds the standard repositories to the config file, if it doesn\'t exist' do
103
+ @cli.run!('net.iconara:pompompom:1.0', 'com.example:test:9.9')
104
+ @config = YAML.load(File.read(@config_file_path))
105
+ @config['repositories'].should == Cli::STANDARD_REPOSITORIES
106
+ end
107
+
108
+ it 'doesn\'t clobber an existing config file' do
109
+ @config = {'repositories' => %w(http://example.com/repo1 http://example.com/repo2)}
110
+ File.open(@config_file_path, 'w') { |f| f.write(YAML::dump(@config)) }
111
+ @cli.run!('net.iconara:pompompom:1.0', 'com.example:test:9.9')
112
+ @config = YAML.load(File.read(@config_file_path))
113
+ @config['repositories'].should == %w(http://example.com/repo1 http://example.com/repo2)
114
+ end
115
+
116
+ it 'reads the config file' do
117
+ @config = {'repositories' => %w(http://example.com/repo1 http://example.com/repo2)}
118
+ File.open(@config_file_path, 'w') { |f| f.write(YAML::dump(@config)) }
119
+ Resolver.should_receive(:new).with(%w(http://example.com/repo1 http://example.com/repo2), an_instance_of(Hash))
120
+ @cli = Cli.new(@stdin, @stdout, @stderr)
121
+ @cli.stub!(:config_file_path).and_return(@config_file_path)
122
+ @cli.run!('net.iconara:pompompom:1.0', 'com.example:test:9.9')
123
+ end
124
+ end
92
125
  end
93
126
  end
@@ -0,0 +1,63 @@
1
+ require File.expand_path('../../spec_helper', __FILE__)
2
+ require 'tmpdir'
3
+ require 'fileutils'
4
+
5
+
6
+ module PomPomPom
7
+ describe Downloader do
8
+ it 'downloads the given URL' do
9
+ Downloader.new.get('http://iconara.net/').should_not be_nil
10
+ end
11
+
12
+ it 'raises an error if the URL cannot be found' do
13
+ expect { Downloader.new.get('http://example.com/test') }.to raise_error
14
+ end
15
+ end
16
+
17
+ describe FilesystemDownloader do
18
+ it 'reads a file' do
19
+ FilesystemDownloader.new.get('/etc/hosts').should_not be_nil
20
+ end
21
+
22
+ it 'raises an error if the file cannot be found' do
23
+ expect { FilesystemDownloader.new.get('/plink') }.to raise_error
24
+ end
25
+ end
26
+
27
+ describe CachingDownloader do
28
+ before do
29
+ @tmp_dir = File.join(Dir.tmpdir, 'pompompom_cache')
30
+ FileUtils.rm_rf(@tmp_dir)
31
+ end
32
+
33
+ after do
34
+ FileUtils.rm_rf(@tmp_dir)
35
+ end
36
+
37
+ it 'creates the directory if it does not exist' do
38
+ CachingDownloader.new(@tmp_dir, stub(:get => 'DATA!')).get('http://example.com/')
39
+ File.directory?(@tmp_dir).should be_true
40
+ end
41
+
42
+ it 'delegates downloading to another downloader' do
43
+ @wrapped_downloader = stub()
44
+ @wrapped_downloader.should_receive(:get).with('http://example.com/')
45
+ CachingDownloader.new(@tmp_dir, @wrapped_downloader).get('http://example.com/')
46
+ end
47
+
48
+ it 'only downloads a URL once (same instance)' do
49
+ @wrapped_downloader = stub()
50
+ @wrapped_downloader.stub(:get).with('http://example.com/some/path/to/a/file.json').once.and_return('DATA!')
51
+ @downloader = CachingDownloader.new(@tmp_dir, @wrapped_downloader)
52
+ @downloader.get('http://example.com/some/path/to/a/file.json').should == 'DATA!'
53
+ @downloader.get('http://example.com/some/path/to/a/file.json').should == 'DATA!'
54
+ end
55
+
56
+ it 'only downloads a URL once (different instances)' do
57
+ @wrapped_downloader = stub()
58
+ @wrapped_downloader.stub(:get).with('http://example.com/some/path/to/a/file.json').once.and_return('DATA!')
59
+ CachingDownloader.new(@tmp_dir, @wrapped_downloader).get('http://example.com/some/path/to/a/file.json').should == 'DATA!'
60
+ CachingDownloader.new(@tmp_dir, @wrapped_downloader).get('http://example.com/some/path/to/a/file.json').should == 'DATA!'
61
+ end
62
+ end
63
+ end
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: pompompom
3
3
  version: !ruby/object:Gem::Version
4
- hash: 23
4
+ hash: 21
5
5
  prerelease: false
6
6
  segments:
7
7
  - 1
8
8
  - 0
9
- - 0
10
- version: 1.0.0
9
+ - 1
10
+ version: 1.0.1
11
11
  platform: ruby
12
12
  authors:
13
13
  - Theo Hultberg
@@ -48,6 +48,7 @@ files:
48
48
  - pompompom.gemspec
49
49
  - spec/pompompom/cli_spec.rb
50
50
  - spec/pompompom/dependency_spec.rb
51
+ - spec/pompompom/downloader_spec.rb
51
52
  - spec/pompompom/metadata_spec.rb
52
53
  - spec/pompompom/pom_spec.rb
53
54
  - spec/pompompom/resolver_spec.rb
@@ -135,6 +136,7 @@ summary: Ruby dependency manager for Maven repository artifacts
135
136
  test_files:
136
137
  - spec/pompompom/cli_spec.rb
137
138
  - spec/pompompom/dependency_spec.rb
139
+ - spec/pompompom/downloader_spec.rb
138
140
  - spec/pompompom/metadata_spec.rb
139
141
  - spec/pompompom/pom_spec.rb
140
142
  - spec/pompompom/resolver_spec.rb