pik 0.1.1 → 0.2.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.
Files changed (68) hide show
  1. data/History.txt +13 -0
  2. data/Manifest.txt +35 -1
  3. data/README.rdoc +99 -39
  4. data/Rakefile +49 -8
  5. data/bin/pik_install +23 -0
  6. data/features/add_command.feature +28 -0
  7. data/features/checkup_command.feature +0 -0
  8. data/features/config_command.feature +12 -0
  9. data/features/default_command.feature +12 -0
  10. data/features/env.rb +52 -0
  11. data/features/gemsync_command.feature +0 -0
  12. data/features/help_command.feature +13 -0
  13. data/features/implode_command.feature +12 -0
  14. data/features/install_command.feature +13 -0
  15. data/features/list_command.feature +18 -0
  16. data/features/remove_command.feature +18 -0
  17. data/features/run_command.feature +22 -0
  18. data/features/step_definitions/pik_commands.rb +140 -0
  19. data/features/switch_command.feature +35 -0
  20. data/features/tag_command.feature +18 -0
  21. data/features/version.feature +9 -0
  22. data/lib/pik.rb +17 -3
  23. data/lib/pik/commands/add_command.rb +6 -6
  24. data/lib/pik/commands/batch_file_editor.rb +22 -8
  25. data/lib/pik/commands/checkup_command.rb +5 -2
  26. data/lib/pik/commands/command.rb +30 -26
  27. data/lib/pik/commands/config_command.rb +54 -2
  28. data/lib/pik/commands/default_command.rb +19 -5
  29. data/lib/pik/commands/help_command.rb +1 -1
  30. data/lib/pik/commands/implode_command.rb +12 -1
  31. data/lib/pik/commands/install_command.rb +182 -0
  32. data/lib/pik/commands/list_command.rb +3 -2
  33. data/lib/pik/commands/remove_command.rb +6 -6
  34. data/lib/pik/commands/run_command.rb +70 -10
  35. data/lib/pik/commands/switch_command.rb +10 -10
  36. data/lib/pik/commands/tag_command.rb +56 -0
  37. data/lib/pik/config_file.rb +26 -2
  38. data/lib/pik/contrib/progressbar.rb +237 -0
  39. data/lib/pik/contrib/unzip.rb +14 -0
  40. data/lib/pik/contrib/uri_ext.rb +296 -0
  41. data/lib/pik/contrib/zip/ioextras.rb +155 -0
  42. data/lib/pik/contrib/zip/stdrubyext.rb +111 -0
  43. data/lib/pik/contrib/zip/tempfile_bugfixed.rb +195 -0
  44. data/lib/pik/contrib/zip/zip.rb +1846 -0
  45. data/lib/pik/contrib/zip/zipfilesystem.rb +609 -0
  46. data/lib/pik/contrib/zip/ziprequire.rb +90 -0
  47. data/lib/pik/core_ext/pathname.rb +20 -7
  48. data/lib/pik/search_path.rb +21 -13
  49. data/lib/pik/which.rb +52 -0
  50. data/lib/pik/windows_env.rb +64 -25
  51. data/spec/add_command_spec.rb +0 -2
  52. data/spec/batch_file_spec.rb +3 -3
  53. data/spec/command_spec.rb +0 -7
  54. data/spec/gemsync_command_spec.rb +1 -1
  55. data/spec/help_command_spec.rb +1 -1
  56. data/spec/list_command_spec.rb +1 -1
  57. data/spec/pathname_spec.rb +30 -0
  58. data/spec/remove_command_spec.rb +6 -6
  59. data/spec/run_command_spec.rb +2 -30
  60. data/spec/search_path_spec.rb +9 -0
  61. data/spec/switch_command_spec.rb +14 -2
  62. data/spec/which_spec.rb +7 -0
  63. data/tools/pik.bat +2 -0
  64. data/tools/pik/pik +45 -0
  65. data/tools/pik/pik.exe +0 -0
  66. data/tools/pik/pik.exy +198 -0
  67. metadata +50 -21
  68. data/bin/pik +0 -33
File without changes
@@ -0,0 +1,13 @@
1
+ Feature: display help information
2
+ In order to know how to use pik
3
+ A developer
4
+ Wants an interface to the program
5
+ So that he can display help information
6
+
7
+ Scenario: Getting help
8
+ When I run "pik help"
9
+ Then I should see "Usage: pik command [options]"
10
+ And I should see "To get help with a command"
11
+ And I should see " pik help (command)"
12
+ And I should see "To list all commands and descriptions:"
13
+ And I should see " pik help commands"
@@ -0,0 +1,12 @@
1
+ Feature: implode command
2
+ In order to delete all pik configuration data
3
+ A developer
4
+ Wants an interface to the program
5
+ So that he can delete all pik configuration data
6
+
7
+
8
+ Scenario: pik implode
9
+ Given I have a directory "C:/temp/.pik"
10
+ And it contains a config.yml
11
+ When I run "pik implode -f"
12
+ Then the directory should be deleted
@@ -0,0 +1,13 @@
1
+ Feature: install command
2
+ In order to keep up to date with multiple ruby implementations
3
+ A developer
4
+ Wants a command line tool
5
+ So that he can download and install them
6
+
7
+ Scenario: install from the intarwebs
8
+ When I run "pik install ruby"
9
+ Then I should see "** Downloading: http://rubyforge.org/frs/download.php/62269/ruby-1.9.1-p243-i386-mingw32.7z"
10
+ And I should see " to: c:\temp\.pik"
11
+ And I should see "** Extracting: c:\temp\.pik\downloads"
12
+ And I should see "** Adding: "
13
+
@@ -0,0 +1,18 @@
1
+ Feature: list command
2
+ In order to list ruby versions that pik is aware of
3
+ A developer
4
+ Wants an interface to the program
5
+ So that he can list configuration information
6
+
7
+ Scenario: list versions
8
+ When I run "pik list"
9
+ Then I should find "^\d+\: .+ruby"
10
+
11
+ Scenario: Determining the current ruby version from the list
12
+ When I run "pik list"
13
+ Then I should find "^\d+\: .+\*$"
14
+
15
+ Scenario: list verbose output
16
+ When I run "pik list -v"
17
+ Then I should find "^\d+\: .+\*$"
18
+ And I should find "path\: C\:[\\\/].+"
@@ -0,0 +1,18 @@
1
+ Feature: remove command
2
+ In order to remove ruby versions from pik
3
+ A developer
4
+ Wants a command line interface
5
+ So that she can remove versions.
6
+
7
+ Scenario: remove a version from the config
8
+ Given I have already added "ruby 1.8.6 (2009-03-31 patchlevel 368) [i386-mingw32]"
9
+ When I run "pik remove 186 min -f"
10
+ Then I should see "removed"
11
+ And the version should be removed.
12
+
13
+ Scenario: remove a version from the config and the filesystem
14
+ Given I have already added "ruby 1.8.6 (2009-03-31 patchlevel 368) [i386-mingw32]"
15
+ When I run "pik remove 186 min -f "
16
+ Then I should see "removed"
17
+ And the version should be removed.
18
+
@@ -0,0 +1,22 @@
1
+ Feature: run command
2
+ In order to test code against different ruby implementations
3
+ A developer
4
+ Wants an interface to the program
5
+ So that he can run commands against all versions that pik is aware of
6
+
7
+ Scenario: run code
8
+ When I run "pik run "path""
9
+ Then I should find "PATH=" 9 times
10
+ And I should see each version's path listed
11
+ And I should see each version listed.
12
+
13
+ Scenario: ruby command
14
+ When I run "pik ruby -e "puts 'hello world!'" "
15
+ Then I should find "hello world!" 9 times
16
+ And I should see each version listed.
17
+
18
+ Scenario: gem command
19
+ When I run "pik gem -v"
20
+ Then I should find "\n\d\.\d\.\d\n" 9 times
21
+ And I should see each version listed.
22
+
@@ -0,0 +1,140 @@
1
+ require 'yaml'
2
+ require 'pathname'
3
+ require 'fileutils'
4
+
5
+ PIK_LOG = 'log\\output.log'
6
+ PIK_HOME = Pathname.new( ENV['HOME'] || ENV['USERPROFILE'] ) + '.pik'
7
+
8
+ Given /^I have.+added "(.+)"/ do |version|
9
+ @version = version
10
+ @version_reg = Regexp.new(Regexp.escape(version), Regexp::IGNORECASE)
11
+ @config_file = PIK_HOME + 'config.yml'
12
+ @original_config = YAML.load(File.read(@config_file))
13
+ @ver = @original_config.keys.grep(@version_reg){|k| @original_config[k] }
14
+ @ver.size.should eql(1)
15
+ end
16
+
17
+ Given /^I am currently using it\.$/ do
18
+ unless `ruby -v` =~ @version_reg
19
+ k,v = `pik switch #{@version} & path`.split('=')
20
+ ENV[k]=v
21
+ end
22
+ `ruby -v`.should match(@version_reg)
23
+ end
24
+
25
+ Given /^I am currently using "(.+)"$/ do |version|
26
+ Given "I have added \"#{version}\""
27
+ Given "I am currently using it."
28
+ end
29
+
30
+ Given /^I have a directory "(.+)"/ do |directory|
31
+ @dir = directory
32
+ Pathname(@dir).directory?.should be_true
33
+ end
34
+
35
+ Given /^it contains a config\.yml/ do
36
+ config = Pathname(@dir) + 'config.yml'
37
+ config.should exist
38
+ end
39
+
40
+ Given /^I have no \.pik directory/ do
41
+ FileUtils.rm_rf PIK_HOME
42
+ PIK_HOME.should_not exist
43
+ end
44
+
45
+ Given /^I have an empty config\.yml/ do
46
+ File.open(PIK_HOME + 'config.yml','w'){|f| }
47
+ end
48
+
49
+ When /^I run "pik (.+?)" and "pik (.+)",$/ do |args1, args2|
50
+ %x[tools\\pik.bat #{args1} > #{PIK_LOG} 2>&1 && tools\\pik.bat #{args2} > #{PIK_LOG} 2>&1]
51
+ end
52
+
53
+ When /^I run "pik (.+?)"$/ do |args|
54
+ %x[tools\\pik.bat #{args} > #{PIK_LOG} 2>&1 ]
55
+ end
56
+
57
+ When /^I run "pik (.*)" and check the path$/ do |args|
58
+ %x[tools\\pik.bat #{args} > #{PIK_LOG} 2>&1 & PATH >> #{PIK_LOG} ]
59
+ end
60
+
61
+ Then /^I should see "(.*)"$/ do |data|
62
+ stdout = File.read(PIK_LOG)
63
+ stdout.should match(Regexp.new(Regexp.escape(data)))
64
+ end
65
+
66
+ Then /^I should find "(.*)"$/ do |regexp|
67
+ stdout = File.read(PIK_LOG)
68
+ stdout.should match(Regexp.new(regexp))
69
+ end
70
+
71
+
72
+ Then /^I should find "(.*)" (\d+) times$/ do |regexp, count|
73
+ stdout = File.read(PIK_LOG)
74
+ items = stdout.scan(Regexp.new(regexp))
75
+ items.size.should eql(count.to_i)
76
+ end
77
+
78
+ Then /^the path should point to it\.$/ do
79
+ path = @ver[0][:path]
80
+ path = path.to_s.gsub('/','\\')
81
+ Then "the path should point to \"#{path}\""
82
+ end
83
+
84
+ Then /^the path should point to "(.+)"$/ do |path|
85
+ stdout = File.read(PIK_LOG)
86
+ stdout.should match( Regexp.new(Regexp.escape(path)) )
87
+ end
88
+
89
+
90
+ Then /^I should see each version.s path listed$/ do
91
+ stdout = File.read(PIK_LOG)
92
+ config_file = PIK_HOME + 'config.yml'
93
+ config = YAML.load(File.read(config_file))
94
+ config.each{|k,v|
95
+ path = Regexp.new(Regexp.escape(v[:path].to_s.gsub('/','\\')))
96
+ stdout.should match(path)
97
+ }
98
+ end
99
+
100
+ Then /^I should see each version listed\.$/ do
101
+ stdout = File.read(PIK_LOG)
102
+ config_file = PIK_HOME + 'config.yml'
103
+ config = YAML.load(File.read(config_file))
104
+ config.each{|k,v|
105
+ version = Regexp.new(Regexp.escape(k.split(': ')[1..-1].join(': ')))
106
+ stdout.should match(version)
107
+ }
108
+ end
109
+
110
+ Then /^the GEM_HOME might get set\.$/ do
111
+ gem_home = @ver[0][:gem_home]
112
+ if gem_home
113
+ gem_home = gem_home.to_s.gsub('/','\\')
114
+ reg_gem_home = Regexp.new(Regexp.escape(gem_home), Regexp::IGNORECASE)
115
+ stdout = File.read(PIK_LOG)
116
+ stdout.should match(reg_gem_home)
117
+ end
118
+ end
119
+
120
+ Then /^the directory should be deleted$/ do
121
+ Pathname(@dir).should_not exist
122
+ end
123
+
124
+ Then /^nothing should be added to the config file\.$/ do
125
+ @current_config = YAML.load(File.read(@config_file))
126
+ @current_config.size.should eql(@original_config.size)
127
+ end
128
+
129
+ Then /^the version should be removed\.$/ do
130
+ @current_config = YAML.load(File.read(@config_file))
131
+ @current_config.size.should eql(@original_config.size - 1)
132
+ end
133
+
134
+
135
+ Then /^a gem_home option should be added to the config\.$/ do
136
+ @ver[0][:gem_home].should be_nil
137
+ @current_config = YAML.load(File.read(@config_file))
138
+ @ver = @current_config.keys.grep(@version_reg){|k| @current_config[k] }
139
+ @ver[0][:gem_home].should_not be_nil
140
+ end
@@ -0,0 +1,35 @@
1
+ Feature: switch command
2
+ In order to switch from one ruby version to another
3
+ A developer
4
+ Wants an interface to the program
5
+ So that she can easily update the path and other environment variables.
6
+
7
+ Scenario Outline: Switching versions with switch command
8
+ Given I have added "<version>" to pik
9
+ When I run "pik switch <patterns> -v" and check the path
10
+ Then I should see "<version>"
11
+ And the path should point to it.
12
+ And the GEM_HOME might get set.
13
+
14
+ Examples:
15
+ | version | patterns |
16
+ | IronRuby 0.9.1.0 on .NET 2.0.0.0 | Ir 91 |
17
+ | jruby 1.4.0RC1 (ruby 1.8.7 patchlevel 174) | jruby 1.4 |
18
+ | ruby 1.8.6 (2008-08-11 patchlevel 287) [i386-mswin32] | 186 ms |
19
+ | ruby 1.8.6 (2009-03-31 patchlevel 368) [i386-mingw32] | 186 mi |
20
+ | ruby 1.9.1p243 (2009-07-16 revision 24175) [i386-mingw32] | 191 p2 |
21
+
22
+ Scenario Outline: Switching versions with pattern only
23
+ Given I have added "<version>" to pik
24
+ When I run "pik <patterns>" and check the path
25
+ Then the path should point to it.
26
+ And the GEM_HOME might get set.
27
+
28
+ Examples:
29
+ | version | patterns |
30
+ | IronRuby 0.9.1.0 on .NET 2.0.0.0 | Ir 91 |
31
+ | jruby 1.4.0RC1 (ruby 1.8.7 patchlevel 174) | jruby 1.4 |
32
+ | ruby 1.8.6 (2008-08-11 patchlevel 287) [i386-mswin32] | 186 ms |
33
+ | ruby 1.8.6 (2009-03-31 patchlevel 368) [i386-mingw32] | 186 mi |
34
+ | ruby 1.9.1p243 (2009-07-16 revision 24175) [i386-mingw32] | 191 p2 |
35
+
@@ -0,0 +1,18 @@
1
+ Feature: tag command
2
+ In order to test code against specific ruby implementations
3
+ A developer
4
+ Wants an interface to the program
5
+ So that he can tag versions that pik is aware of
6
+
7
+ Scenario: tag version
8
+ When I run "pik Ir 91" and "pik tag iron",
9
+ And I run "pik config list"
10
+ Then I should find "tags: \n iron:"
11
+ And I should see " - 091: IronRuby 0.9.1.0 on .NET 2.0.0.0"
12
+
13
+ Scenario: run tagged versions
14
+ When I run "pik Ir 91" and "pik tag iron",
15
+ And I run "pik Ir 90" and "pik tag iron",
16
+ And I run "pik tags iron run echo."
17
+ Then I should find "IronRuby 0.9.1.0 on .NET 2.0.0.0"
18
+ And I should find "IronRuby 0.9.0.0 on .NET 2.0.0.0"
@@ -0,0 +1,9 @@
1
+ Feature: display pik version
2
+ In order to know what version pik is at
3
+ A developer
4
+ Wants an interface to the program
5
+ So that he can display version information
6
+
7
+ Scenario: Listing versions
8
+ When I run "pik -V"
9
+ Then I should find "^pik \d.\d.\d"
data/lib/pik.rb CHANGED
@@ -1,9 +1,11 @@
1
1
  module Pik
2
- VERSION = '0.1.1'
2
+ VERSION = '0.2.0'
3
3
  end
4
4
 
5
- require 'highline'
5
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
6
+ require 'yaml'
6
7
  require 'pathname'
8
+ require 'fileutils'
7
9
  require 'rbconfig'
8
10
 
9
11
  require 'pik/core_ext/pathname'
@@ -11,6 +13,7 @@ require 'pik/commands'
11
13
  require 'pik/commands/config_file_editor'
12
14
  require 'pik/commands/batch_file_editor'
13
15
  require 'pik/commands/command'
16
+ require 'pik/commands/install_command'
14
17
  require 'pik/commands/list_command'
15
18
  require 'pik/commands/add_command'
16
19
  require 'pik/commands/help_command'
@@ -22,9 +25,20 @@ require 'pik/commands/config_command'
22
25
  require 'pik/commands/gemsync_command'
23
26
  require 'pik/commands/default_command'
24
27
  require 'pik/commands/implode_command'
28
+ require 'pik/commands/tag_command'
25
29
  require 'pik/config_file'
26
30
  require 'pik/windows_env'
31
+ require 'pik/which'
27
32
  require 'pik/batch_file'
28
33
  require 'pik/search_path'
29
34
 
30
- PIK_HOME = Pathname.new( ENV['HOME'] || ENV['USERPROFILE'] ) + '.pik'
35
+ require 'highline'
36
+
37
+ PIK_HOME = Pathname.new( ENV['HOME'] || ENV['USERPROFILE'] ) + '.pik'
38
+
39
+ if defined? ExerbRuntime
40
+ PIK_BATCH = Pathname.new(ARGV.shift).ruby
41
+ else
42
+ pik_exe = Pathname.new($0).expand_path + '..'
43
+ PIK_BATCH = pik_exe.dirname + "#{pik_exe.basename}.bat"
44
+ end
@@ -9,20 +9,20 @@ module Pik
9
9
 
10
10
  def execute(path=nil)
11
11
  return add_interactive if interactive
12
- path = @args.first || ::Config::CONFIG['bindir']
12
+ path = @args.first || Which::Ruby.find
13
13
  add(path)
14
14
  end
15
15
 
16
16
  def add(path)
17
17
  path = Pathname.new(path)
18
18
  path = path.dirname if path.file?
19
- if ruby_exists_at?(path)
20
- if config[get_version(path)]
19
+ if Which::Ruby.exist?(path)
20
+ if find_config_from_path(path)
21
21
  puts "This version has already been added."
22
22
  else
23
23
  version = get_version(path)
24
- path = path.expand_path.to_ruby
25
- puts "Adding: #{version}'\n Located at: #{path}\n"
24
+ path = Pathname(path.expand_path.to_ruby)
25
+ puts "** Adding: #{version}\n Located at: #{path}\n"
26
26
  @config[version] = {}
27
27
  @config[version][:path] = path
28
28
  end
@@ -50,7 +50,7 @@ module Pik
50
50
  }
51
51
  menu.choice('s]earch'){
52
52
  search_dir = @hl.ask("Enter a search path")
53
- files = ruby_glob(search_dir + '**')
53
+ files = Which::Ruby.glob(search_dir + '**')
54
54
  files.each{|file|
55
55
  dir = File.dirname(file)
56
56
  add(dir) if @hl.agree("Add '#{dir}'? [Yn] ")
@@ -24,12 +24,25 @@ module Pik
24
24
  end
25
25
 
26
26
  def switch_path_to(new_ver)
27
- dir = current_ruby_bin_path
27
+ dir = Which::Ruby.find
28
+ current_config = config[ find_config_from_path(dir) ]
29
+
28
30
  new_path = SearchPath.new(ENV['PATH']).replace_or_add(dir, new_ver[:path])
29
- if new_ver[:gem_home]
30
- new_path.replace_or_add(current_gem_bin_path, Pathname.new(new_ver[:gem_home]) + 'bin')
31
+ if new_gem_home = new_ver[:gem_home]
32
+
33
+ new_gem_bin = Pathname.new(new_gem_home) + 'bin'
34
+
35
+ if current_gem_home = current_config[:gem_home]
36
+ current_gem_bin = Pathname.new(current_gem_home) + 'bin'
37
+ new_path.replace(current_gem_bin, new_gem_bin)
38
+ else
39
+ new_path.add(new_gem_bin)
40
+ end
31
41
  else
32
- new_path.remove(current_gem_bin_path)
42
+ if current_gem_home = current_config[:gem_home]
43
+ current_gem_bin = Pathname.new(current_gem_home) + 'bin'
44
+ new_path.remove(current_gem_bin)
45
+ end
33
46
  end
34
47
  @batch.set('PATH' => new_path.join )
35
48
  end
@@ -41,16 +54,17 @@ module Pik
41
54
  @batch.set('GEM_HOME' => gem_path )
42
55
  end
43
56
 
44
- def echo_ruby_version(verb='Using')
45
- @batch.file_data << "for /f \"delims=\" %%a in ('ruby -v') do @echo #{verb} %%a "
57
+ def echo_ruby_version(path, verb='')
58
+ rb = Which::Ruby.exe(path).basename
59
+ @batch.file_data << "for /f \"delims=\" %%a in ('#{rb} -v') do @echo #{verb} %%a "
46
60
  end
47
61
 
48
- def echo_running_with_ruby_version
62
+ def echo_running_with_ruby_version(path)
49
63
  echo_ruby_version('Running with')
50
64
  end
51
65
 
52
66
  def update_gem_batch
53
- BatchFile.open("#{$0}.bat") do |gem_bat|
67
+ BatchFile.open(PIK_BATCH) do |gem_bat|
54
68
  # call new .pik/pik batch
55
69
  gem_bat.call(%Q("#{@batch.path.to_windows}")) if @batch
56
70
  gem_bat.write
@@ -17,7 +17,7 @@ module Pik
17
17
  end
18
18
 
19
19
  def rubyopt
20
- unless WindowsEnv.user['rubyopt'].empty? && WindowsEnv.system['rubyopt'].empty?
20
+ unless WindowsEnv.user['rubyopt'].nil? && WindowsEnv.system['rubyopt'].nil?
21
21
  fail('rubyopt')
22
22
  else
23
23
  pass('rubyopt')
@@ -33,7 +33,9 @@ module Pik
33
33
  end
34
34
 
35
35
  def path
36
- dirs = (WindowsEnv.user['path'] + WindowsEnv.system['path']).split(';')
36
+ user_path = WindowsEnv.user['path'] || ''
37
+ syst_path = WindowsEnv.system['path'] || ''
38
+ dirs = (user_path + syst_path).split(';')
37
39
  dirs = dirs.select{|dir| File.exist?( File.join(dir,'ruby.exe') ) }
38
40
  unless dirs.size == 1
39
41
  fail('path')
@@ -59,6 +61,7 @@ module Pik
59
61
 
60
62
  def fail(test)
61
63
  print 'F'
64
+ $stdout.flush
62
65
  # @output << @text[test][:fail]
63
66
  end
64
67