On 8/21/06, Daniel Waite <rabbitblue / gmail.com> wrote:
> Robert Klemme wrote:
> > I find it odd that AuthorizeNet is a module and that it's contained in
> > CreditCardProcessor which you said defines the interface.  First, you
> > don't have interfaces in Ruby (and you don't need them).
>
> I realize Ruby doesn't explicitly support the concept of an interface
> via a keyword (convention over configuration anyway, right?). However,
> that doesn't mean I can't program inline with the _concept_ of an
> interface. The _concept_ of design by contract. It's those concepts I'm
> trying to utilize because I believe they're helpful.

Yes, but Modules in Ruby provide implementation, so they don't really
make good reifications of the concept.

> > Second, nesting the "interface" and classes that implement
> > it seems weird to me.
>
> That's the hallmark of the Strategy pattern.

Here I have to politely disagree.  The hallmark of the Strategy
pattern is the provision of a configurable service object (which the
GOF calls a Context) which clients can configure by giving it
different ConcreteStrategy objects, and the separation of
implementation of the Context and the various ConcreteStrategies,
through the use of an interface definition called a Strategy.

So one way of looking at the strategy in the pattern is that it
identifies the species of duck that the context is looking for when
the client configures it.

But this can be done as documentation or commentary.

> > If we assume for the moment that we are using a language with
> > interfaces then the main point of them is, that you can have arbitrary
> > classes implement them.
>
> Yes and no. Mostly no in my situation. The point of using an interface
> _in this case_ is to encapsulate a defined set of behaviors into many
> possible implementations. We may well add another payment processor to
> our arsenal later down the road. Provided the interface is strong enough
> I should be able to code to that interface and not be able to tell which
> implementation I'm using.

But again, there's no real need or advantage to reify it in a Module.
And if you populate the Module with 'unimplemented' methods, and
require the ConcreteStrategies to include it, it actually obscures
whether or not a given ConcreteStrategy really implements the
Strategy.

> > Why does Company include CreditCardProcessor if it's just an interface?
>
> To this end I'm not certain. Looking at my examples again I suppose it
> doesn't make much sense to include it into Company.

It's not a feature of the Strategy pattern, which seems to be about
allowing a client to configure an internal implementation choice.
Having the Context export the strategy interface to the client seems
to be more related to Facade or Proxy, but not quite.


> Ilan Berci wrote:
> > Some of the GOF patterns don't translate to a dynamically typed language
> > such as Ruby.
>
> What's GOF?

GOF = [Erich_Gamma, Richard_Helm, Ralph_Johnson, John_Vlissides]

These were the authors of the book "Design Patterns" which was first
to really popularize the idea of patterns which was "discovered" by
Ward Cunningham and Kent Beck in the writings of  Architect (houses
and towns) Christopher Alexander, and developed into a burgeoning
movement including a cadre called the Hillside group which the book
brought out into the open. http://c2.com/cgi/wiki?HistoryOfPatterns

GOF.map { | author | author.native_language } => [[Swiss_German, C++],
[Strine, C++], [American, Smalltalk], [American, C++]]

I used to hang out fairly regularly with all four of them, and worked
with all but Ralph at IBM, OTI or both.  I used to kid GOF[2] that he
didn't hold up his end of the stick as the lonely dynamic language
guy. <G>  Sadly I recently discovered that GOF[3] passed away about a
year ago.

With the 3-1 composition of the GOF as guys with an abstract-data type
background, IMHO most of the patterns put too much emphasis on C++ish
implementation artifacts such as type-implementation confusion, and
templates (In fact in the implementation section on the Strategy
pattern they suggest cases where you might use C++ templates to
configure the Context rather than defining a Strategy interface).

Had Ralph pushed a bit harder, the book might well have abstracted
some of those concepts to duck types (Smalltalk had them, but I can't
recall that we used THAT name, it was most often roles or something
else http://talklikeaduck.denhaven2.com/articles/2006/07/26/my-favorite-duck-typing-story
), and folks might look on both the GOF patterns, and languages like
Ruby and Smalltalk in a different light.
-- 
Rick DeNatale

My blog on Ruby
http://talklikeaduck.denhaven2.com/