ddollar-gem-prune 1.0.3

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/LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2009 David Dollar
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.rdoc ADDED
@@ -0,0 +1,25 @@
1
+ = gem-prune
2
+
3
+ Adds a 'prune' command to rubygems to help keep things tidy. Traverses your
4
+ dependency tree, finds the leaves, and asks you whether or not you want to
5
+ keep them. Remembers which gems you want to keep in ~/.gem-prune
6
+
7
+ Installation
8
+
9
+ $ gem install ddollar-gem-prune
10
+
11
+ Usage
12
+
13
+ $ sudo gem prune
14
+
15
+ Example
16
+
17
+ json_pure (1.1.6)
18
+ [k] keep this gem
19
+ [u] uninstall this gem
20
+ [s] skip (default)
21
+ >
22
+
23
+ == Copyright
24
+
25
+ Copyright (c) 2009 David Dollar. See LICENSE for details.
data/bin/prune ADDED
@@ -0,0 +1,10 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'rubygems'
4
+ $:.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
5
+
6
+ require 'gem/commands/prune_command'
7
+ #require File.join(File.dirname(__FILE__), '..', 'lib', 'gem', 'commands', 'prune_command')
8
+
9
+ prune = Gem::Commands::PruneCommand.new
10
+ prune.execute
@@ -0,0 +1,124 @@
1
+ require 'rubygems/command'
2
+ require 'rubygems/command_manager'
3
+ require 'rubygems/uninstaller'
4
+ require 'gem/prune/gem'
5
+ require 'gem/prune/version'
6
+
7
+ class Gem::Commands::PruneCommand < Gem::Command
8
+
9
+ def initialize
10
+ super 'prune', 'Identify and remove old gems'
11
+ end
12
+
13
+ def execute
14
+ return if leaves.empty?
15
+ leaves.each do |name, versions|
16
+ begin
17
+ question = "#{name} (#{versions.map { |v| v.version }.join(', ')})\n"
18
+ question << " [k] keep this gem\n"
19
+ question << " [u] uninstall this gem\n"
20
+ question << " [s] skip (default)\n"
21
+ question << "> "
22
+ print question
23
+ case $stdin.gets.chomp
24
+ when 'k' then keep_gem(name)
25
+ when 'u' then uninstall(name)
26
+ end
27
+ rescue Gem::FilePermissionError
28
+ puts 'Unable to uninstall. Try sudo?'
29
+ next
30
+ end
31
+ end
32
+ rescue Exception
33
+ end
34
+
35
+ ## commands ##################################################################
36
+
37
+ def keep_gem(name)
38
+ kept = load_kept_gems
39
+ kept << name
40
+ save_kept_gems(kept.uniq)
41
+ end
42
+
43
+ def uninstall(name)
44
+ leaves[name].each do |version|
45
+ uninstaller(name, version.version).uninstall
46
+ end
47
+ end
48
+
49
+ private ######################################################################
50
+
51
+ def gems
52
+ @gems ||= begin
53
+ gems = Gem.source_index.gems.values.inject({}) do |memo, raw|
54
+ next(memo) if ignore_specification(raw)
55
+ gem = memo[raw.name] || Gem::Prune::Gem.new(raw.name)
56
+ gem.versions << Gem::Prune::Version.new(gem, raw)
57
+ memo.update(raw.name => gem)
58
+ end
59
+ discover_relationships(gems)
60
+ gems
61
+ end
62
+ end
63
+
64
+ def discover_relationships(gems)
65
+ gems.values.each { |gem| gem.clear_relationships }
66
+
67
+ gems.each do |name, gem|
68
+ gem.versions.each do |version|
69
+ version.raw.dependencies.each do |dep|
70
+ next if ignore_dependency(dep)
71
+ next unless gems[dep.name]
72
+ match = gems[dep.name].versions.sort.reverse.detect { |v| dep =~ v }
73
+ match.dependants << version
74
+ version.dependencies << match
75
+ end
76
+ end
77
+ end
78
+ end
79
+
80
+ def leaves
81
+ @leaves ||= gems.keys.inject({}) do |memo, name|
82
+ leaves = gems[name].versions.select do |version|
83
+ version.dependants.length.zero? && !ignore_version(version)
84
+ end
85
+ memo[name] = leaves unless leaves.length.zero?
86
+ memo
87
+ end
88
+ end
89
+
90
+ def ignore_version(version)
91
+ return true if load_kept_gems.include?(version.gem.name)
92
+ false
93
+ end
94
+
95
+ def ignore_specification(specification)
96
+ return true if specification.loaded_from =~ /\/System\/Library/
97
+ false
98
+ end
99
+
100
+ def ignore_dependency(dependency)
101
+ false
102
+ end
103
+
104
+ def uninstaller(name, version)
105
+ Gem::Uninstaller.new(name, :version => version, :executables => true)
106
+ end
107
+
108
+ def load_kept_gems
109
+ YAML::load_file(settings_filename)['keep']
110
+ rescue
111
+ []
112
+ end
113
+
114
+ def save_kept_gems(gems)
115
+ File.open(settings_filename, 'w') do |file|
116
+ file.puts({ 'keep' => gems }.to_yaml)
117
+ end
118
+ end
119
+
120
+ def settings_filename
121
+ File.expand_path('~/.gem-prune')
122
+ end
123
+
124
+ end
@@ -0,0 +1,15 @@
1
+ module Gem; module Prune; class Gem
2
+
3
+ attr_reader :name
4
+ attr_reader :versions
5
+
6
+ def initialize(name)
7
+ @name = name
8
+ @versions = []
9
+ end
10
+
11
+ def clear_relationships
12
+ versions.each { |v| v.clear_relationships }
13
+ end
14
+
15
+ end; end; end
@@ -0,0 +1,41 @@
1
+ module Gem; module Prune; class Version
2
+
3
+ attr_reader :gem
4
+ attr_reader :raw
5
+ attr_reader :dependants
6
+ attr_reader :dependencies
7
+
8
+ def initialize(gem, raw)
9
+ @gem = gem
10
+ @raw = raw
11
+
12
+ clear_relationships
13
+ end
14
+
15
+ def inspect
16
+ pretty = %{<Gem::Prune::Version }
17
+ pretty << %{@name="#{name}" }
18
+ pretty << %{@version="#{version}" }
19
+ pretty << %{@dependants="#{dependants.map { |d| "#{d.name}-#{d.version}" }.join(' ') }" }
20
+ pretty << %{@dependencies="#{dependencies.map { |d| "#{d.name}-#{d.version}" }.join(' ') }"}
21
+ pretty << %{>}
22
+ end
23
+
24
+ def name
25
+ raw.name
26
+ end
27
+
28
+ def version
29
+ raw.version
30
+ end
31
+
32
+ def clear_relationships
33
+ @dependants = []
34
+ @dependencies = []
35
+ end
36
+
37
+ def <=>(other)
38
+ version <=> other.version
39
+ end
40
+
41
+ end; end; end
@@ -0,0 +1,3 @@
1
+ require 'gem/commands/prune_command'
2
+
3
+ Gem::CommandManager.instance.register_command :prune
@@ -0,0 +1,7 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe "GemPrune" do
4
+ it "fails" do
5
+ fail "hey buddy, you should probably rename this file and start specing for real"
6
+ end
7
+ end
@@ -0,0 +1,9 @@
1
+ require 'spec'
2
+
3
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
4
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
5
+ require 'gem-prune'
6
+
7
+ Spec::Runner.configure do |config|
8
+
9
+ end
metadata ADDED
@@ -0,0 +1,60 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: ddollar-gem-prune
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.3
5
+ platform: ruby
6
+ authors:
7
+ - David Dollar
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2009-05-21 00:00:00 -07:00
13
+ default_executable: prune
14
+ dependencies: []
15
+
16
+ description:
17
+ email: <ddollar@gmail.com>
18
+ executables:
19
+ - prune
20
+ extensions: []
21
+
22
+ extra_rdoc_files:
23
+ - LICENSE
24
+ - README.rdoc
25
+ files:
26
+ - lib/gem/commands/prune_command.rb
27
+ - lib/gem/prune/gem.rb
28
+ - lib/gem/prune/version.rb
29
+ - lib/rubygems_plugin.rb
30
+ - LICENSE
31
+ - README.rdoc
32
+ has_rdoc: false
33
+ homepage: http://github.com/ddollar/gem-prune
34
+ post_install_message:
35
+ rdoc_options:
36
+ - --charset=UTF-8
37
+ require_paths:
38
+ - lib
39
+ required_ruby_version: !ruby/object:Gem::Requirement
40
+ requirements:
41
+ - - ">="
42
+ - !ruby/object:Gem::Version
43
+ version: "0"
44
+ version:
45
+ required_rubygems_version: !ruby/object:Gem::Requirement
46
+ requirements:
47
+ - - ">="
48
+ - !ruby/object:Gem::Version
49
+ version: "0"
50
+ version:
51
+ requirements: []
52
+
53
+ rubyforge_project:
54
+ rubygems_version: 1.2.0
55
+ signing_key:
56
+ specification_version: 3
57
+ summary: Identify and remove old Rubygems
58
+ test_files:
59
+ - spec/gem-prune_spec.rb
60
+ - spec/spec_helper.rb