Adding methods to String, but only in my own Module?

Is there any way to add methods to the String class, but only within
the scope of a particular module? Example: adding a “fantastic” method
to String:

class String
def fantastic
self + “fantastic”
end
end

Now, given the limited usefulness of the “fantastic” method, I’d like
to be able to confine its impact to my Module only:

outside of my module this should raise a NoMethodError

“foo”.fantastic

class Example
def example
“foo”.fantastic # should work
end
end

I suspect the answer is going to be no, but wanted to ask anyway…

Cheers,
Greg

On Fri, Jan 26, 2007 at 06:35:07AM +0900, Greg H. wrote:

Is there any way to add methods to the String class, but only within
the scope of a particular module?

Glad to see I’m not the only one interested in this. See Pit C.'s
solution in the thread at

http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-core/9982

While I’m grateful for Pit’s suggestion it’s a rather suboptimal
solution to
the problem imho, and I wish this were possible in Ruby in a
straightforward
manner somehow.

On Jan 25, 2007, at 4:50 PM, Jos B. wrote:

While I’m grateful for Pit’s suggestion it’s a rather suboptimal
solution to
the problem imho, and I wish this were possible in Ruby in a
straightforward
manner somehow.

ruby-core: this was originally just a response to Jos, but it has some
thoughts related to the public/protected/private discussion on ruby-core

The problem with the import-module solution is that it is ultimately
manipulating a global data structure (the class/module hierarchy) so
that the visibility of the changes (even if temporary) is defined
temporally and globally rather then lexically localized to particular
modules or classes.

One of the interesting aspects of Plan 9 is the idea of per-process
namespaces. In Plan 9, the file system is not a global data structure
that is visible to and shared by all processes. Instead, each
process constructs its own private view of the world. There are various
mechanisms to allow processes to share views (default) or to create
and manipulate their own private hierarchy (think of per-process
symlinks).

Switching back to Ruby, I wonder if the Plan 9 concepts of private
file hierarchies could be adapted to permit per-module/class views of
the
class hierarchy?

class A
enhance String, MyModule
def foo
“bar”.my_method # my_method is resolved to MyModule#mymethod
# because the enhancement is visible in
A#foo
B.new.baz
end
end

class B
def baz
“bar”.my_method # NameError because the enhancement is not
# visible in B.
end
end

The idea is that when methods defined in A are executing, they
see the String class enhanced (i.e. included) via MyModule. Methods
that are not explicitly defined within A don’t see the enhancements.

I feel like this sort of thing is related to the ongoing discussion of
private over on ruby-core where the goal is to figure out how to keep
private methods visible only in a particular lexical scope (at least I
think that is the/a goal).

How about:

class A
enhance self do
def private_method_1
end
end

  def public_method
    private_method_1
  end

end

A.new.private_method_1    # NameError

My main point is that as long as the class-hierarchy is considered a
global
data structure you are going to have a hard time dealing with name
clashes.
Having a way to construct lexically scoped class-hierarchies may be a
way around
this problem.

Gary W.

On Fri, Jan 26, 2007 at 08:57:11AM +0900, [email protected] wrote:
[snip]

My main point is that as long as the class-hierarchy is considered a global
data structure you are going to have a hard time dealing with name clashes.
Having a way to construct lexically scoped class-hierarchies may be a way
around this problem.

Well put, thank you Gary.

Hi,

In message “Re: Method Dispatch (was Adding methods to String, but only
in my own Module?)”
on Fri, 26 Jan 2007 08:57:11 +0900, [email protected] writes:

|The problem with the import-module solution is that it is ultimately
|manipulating a global data structure (the class/module hierarchy) so
|that the visibility of the changes (even if temporary) is defined
|temporally and globally rather then lexically localized to particular
|modules or classes.

Keiju Ishitsuka, who named Ruby 14 years ago, once developed a library
named scope-in-state that did similar work in thread safe manner. The
problem is it has been lost for long time (no longer registered in
RAA). I will ask him to put it somewhere. I hope he still has.

          matz.

On 25.01.2007 22:34, Greg H. wrote:

Now, given the limited usefulness of the “fantastic” method, I’d like

I suspect the answer is going to be no, but wanted to ask anyway…

See the other replies for suggested solutions etc. For me it always
seemed easier to use /functions/ for this:

def fantastic(s)
s + “fantastic”
end

And you can scope them as you like / need.

Kind regards

robert

Aside: all this discussion about changing the core of Ruby and
alternative proposals for syntax names and whatnot…what
differentiates this discussion (held on ruby-core, in a particular
thread) from submitting an RCR and holding the discussion on the
mailing list for that RCR?

In message “Re: Method Dispatch (was Adding methods to String, but only
in my own Module?)”
on Fri, 26 Jan 2007 09:17:02 +0900, Yukihiro M.
[email protected] writes:

|Keiju Ishitsuka, who named Ruby 14 years ago, once developed a library
|named scope-in-state that did similar work in thread safe manner. The
|problem is it has been lost for long time (no longer registered in
|RAA). I will ask him to put it somewhere. I hope he still has.

It’s available from

http://www.rubyist.net/~keiju/src/scope-in-state.tgz

Note that it’s unmodified old code, so that no one know it works for
the current Ruby. You may need to tweak on it.

          matz.