问题
What are for you the pros and cons of using:
FooLib::Plugins
FooLib::Plugins::Bar
vs.
FooLib::Plugin
FooLib::Plugin::Bar
naming conventions? And what would you use or what are you using? What is more commonly used in the comunity?
回答1:
Use:
module FooLib end
module FooLib::Plugins end
class FooLib::Plugins::Plugin; end #the base for plugins
class FooLib::Plugins::Bar < FooLib::Plugins::Plugin; end
class FooLib::Plugins::Bar2 < FooLib::Plugins::Plugin; end
or in a different words:
module FooLib
module Plugins
class Plugin; end #the base for plugins
class Bar < Plugin; end
class Bar2 < Plugin; end
end
end
Also arrange the files like this:
- foo_lib/
- plugins/
- plugin.rb
- bar.rb
- bar2.rb
This is how Rails does it (so this is the Rails Way). I.e. look at the Associations namespace and the Associations::Association class from which all of the classes form the Associations namespace inherits (i.e. Associations::SingularAssociation).
回答2:
To me FooLib::Plugins
appears like a module, used as a namespace which various plugin classes are kept in. FooLib::Plugin
looks like a superclass for FooLib plugins.
In FooLib::Plugins::Bar
, Bar
definitely seems like the name of a plugin. With FooLib::Plugin::Bar
, I would be doubtful whether Bar
was a helper class used by Foo::Plugin
, or the name of a plugin.
回答3:
Assuming Plugin
is a base class:
class FooLib::Plugin::Bar < FooLib::Plugin
This is the one I use and recommend.
Bar
is aPlugin
inFooLib
and it inherits fromFooLib::Plugin
. It also keeps the plugins provided by theFooLib
library nested under the namespace of the general class, which reads naturally:# Assign the Bar Plugin of the FooLib library to p. p = FooLib::Plugin::Bar
If I were to develop a third party plugin for your library, I would create the following structure:
# Baz is a Plugin for the FooLib library provided by BarLib. class BarLib::FooLib::Plugin::Baz < ::FooLib::Plugin
Note that I mirror the
FooLib
hierarchy, but underBarLib
's namespace. I would not extend it directly.class FooLib::Plugins::Bar < FooLib::Plugin
I have also used this one, and I think it makes the most sense.
Bar
extendsFooLib::Plugin
and is one of thePlugins
provided byFooLib
. However, it creates a potentially needless module.I think this would be a great choice if
Plugins
was a central plugin repository that implements methods likePlugins.add
,Plugins.all
andPlugins.loaded
.Use it if you can justify the extra module.
class FooLib::Plugins::Bar < FooLib::Plugins
Doesn't make a lot of sense to me.
Bar
is one of thePlugins
inFooLib
, that part looks fine. However, it inherits fromPlugins
. Is it inheriting from more than one plugin? It sounds strange to me; the class name shouldn't suggest something that is impossible.
回答4:
I would second the approach outlined by @jtrim.
Given that the module (i.e. Plugin) is being used for namespacing only, I typically override the new method in the module:
module Foo
module Plugin
def self.included(base)
raise "cannot be included"
end
def self.extended(base)
raise "cannot extend"
end
def self.new(*args)
Base.new(*args)
end
class Base;end
end
end
base_plugin_obj = Foo::Plugin.new(...)
回答5:
Generally, the approach I tend to take is:
module Foo
module Plugin
class Base; end
end
end
class Foo::Plugin::Bar < Foo::Plugin::Base; end
The Base
class for plugins is a convention found all over the place in the RubyOnRails codebase as well as many others. (e.g. ActiveRecord::Base
, ActionController::Base
, etc.)
I disagree with @Matheus Moreira's approach where Foo::Plugin
is used both as the base class and the namespace for plugins.
The only functional reason why this shouldn't be done has to do with convention - in the Ruby community one will find many less instances of classes as namespaces than modules. The only time I really see classes used as a namespace for another class is when the purpose of said class is private to the namespace class and is not used externally.
来源:https://stackoverflow.com/questions/9293023/what-is-the-preferred-way-better-style-to-name-a-namespace-in-ruby-singular-o