Permalink
Browse files

Generators: look for generators in all gems, not just those suffixed …

…with _generator, in the gem's generators or rails_generators directory. Allow use of the rails_generators directory instead of the standard generators directory in plugins also. Closes #8730.

git-svn-id: http://svn-commit.rubyonrails.org/rails/trunk@7139 5ecf4fe2-1ee6-0310-87b1-e25e094e27de
  • Loading branch information...
1 parent 557e193 commit 868e6b08df4b16fb71cc8a66308174253ff67bdb @jeremy jeremy committed Jun 27, 2007
View
@@ -1,5 +1,7 @@
*SVN*
+* Generators: look for generators in all gems, not just those suffixed with _generator, in the gem's generators or rails_generators directory. Allow use of the rails_generators directory instead of the standard generators directory in plugins also. #8730 [Dr Nic, topfunky]
+
* MySQL, PostgreSQL: database.yml defaults to utf-8. #8701 [matt]
* Added db:version to get the current schema number [via Err The Blog]
@@ -46,7 +46,7 @@ module Generator
#
# A spec is not a generator: it's a description of where to find
# the generator and how to create it. A source is anything that
- # yields generators from #each. PathSource and GemSource are provided.
+ # yields generators from #each. PathSource and GemGeneratorSource are provided.
module Lookup
def self.included(base)
base.extend(ClassMethods)
@@ -101,9 +101,13 @@ def use_component_sources!
sources << PathSource.new(:lib, "#{::RAILS_ROOT}/lib/generators")
sources << PathSource.new(:vendor, "#{::RAILS_ROOT}/vendor/generators")
sources << PathSource.new(:plugins, "#{::RAILS_ROOT}/vendor/plugins/*/**/generators")
+ sources << PathSource.new(:plugins, "#{::RAILS_ROOT}/vendor/plugins/*/**/rails_generators")
end
sources << PathSource.new(:user, "#{Dir.user_home}/.rails/generators")
- sources << GemSource.new if Object.const_defined?(:Gem)
+ if Object.const_defined?(:Gem)
+ sources << GemGeneratorSource.new
+ sources << GemPathSource.new
+ end
sources << PathSource.new(:builtin, "#{File.dirname(__FILE__)}/generators/components")
end
@@ -185,14 +189,15 @@ def each
end
end
-
- # GemSource hits the mines to quarry for generators. The latest versions
- # of gems named *_generator are selected.
- class GemSource < Source
+ class AbstractGemSource < Source
def initialize
super :RubyGems
end
+ end
+ # GemGeneratorSource hits the mines to quarry for generators. The latest versions
+ # of gems named *_generator are selected.
+ class GemGeneratorSource < AbstractGemSource
# Yield latest versions of generator gems.
def each
Gem::cache.search(/_generator$/).inject({}) { |latest, gem|
@@ -205,5 +210,31 @@ def each
end
end
+ # GemPathSource looks for generators within any RubyGem's /rails_generators/<generator_name>_generator.rb file.
+ class GemPathSource < AbstractGemSource
+ # Yield each generator within rails_generator subdirectories.
+ def each
+ generator_full_paths.each do |generator|
+ yield Spec.new(File.basename(generator).sub(/_generator.rb$/, ''), File.dirname(generator), label)
+ end
+ end
+
+ private
+ def generator_full_paths
+ @generator_full_paths ||=
+ Gem::cache.inject({}) do |latest, name_gem|
+ name, gem = name_gem
+ hem = latest[gem.name]
+ latest[gem.name] = gem if hem.nil? or gem.version > hem.version
+ latest
+ end.values.inject([]) do |mem, gem|
+ Dir[gem.full_gem_path + '/{rails_,}generators/**/*_generator.rb'].each do |generator|
+ mem << generator
+ end
+ mem
+ end
+ end
+ end
+
end
end
@@ -43,9 +43,12 @@ def banner
def usage_message
usage = "\nInstalled Generators\n"
- Rails::Generator::Base.sources.each do |source|
+ Rails::Generator::Base.sources.inject({}) do |mem, source|
label = source.label.to_s.capitalize
- names = source.names
+ mem[label] ||= []
+ mem[label] |= source.names
+ mem
+ end.each_pair do |label, names|
usage << " #{label}: #{names.join(', ')}\n" unless names.empty?
end
@@ -2,7 +2,7 @@ module Rails
module Generator
# A spec knows where a generator was found and how to instantiate it.
# Metadata include the generator's name, its base path, and the source
- # which yielded it (PathSource, GemSource, etc.)
+ # which yielded it (PathSource, GemPathSource, etc.)
class Spec
attr_reader :name, :path, :source

0 comments on commit 868e6b0

Please sign in to comment.