NAME

pervasives.rb

SYNOPSIS

access to pristine object state.  if you don't metaprogram or write
debuggers you probably don't need it.

INSTALL

gem install pervasives

URIS

http://rubyforge.org/projects/codeforpeople/
http://codeforpeople.com/lib/ruby

HISTORY

1.1.0

  added Pervasives.call method, refactored a bit, updated samples, updated
  tests for new api

1.0.0

  is NOT backward compatible with any other pervasives version.  the new
  library is __greatly__ simplified

SAMPLES

<========< samples/a.rb >========>

~ > cat samples/a.rb

  #
  # Pervasives allows an object's methods to be accessed in a pristine state,
  # even when some effort has been made to derride them
  #
    require 'pervasives'

    class BlankSlate
      instance_methods.each{|m| undef_method m unless m[%r/__/]}
    end

    bs = BlankSlate.new

    p Pervasives(bs).methods #=> ["__object_pervasive__", "__id__", "__send__", "__pervasive__"]

    p Pervasives(bs).is_a?(BlankSlate) #=> true

    p Pervasives(bs).instance_eval{ @a = 42 } #=> 42

    p Pervasives(bs).instance_variables #=> ["@a"]

~ > ruby samples/a.rb

  ["__pervasive__", "__id__", "__send__"]
  true
  42
  ["@a"]

<========< samples/b.rb >========>

~ > cat samples/b.rb

  #
  # the special method __pervasive__ is added to all objects - it can be used to
  # access the pristine state 
  #
    require 'pervasives'

    class C
      def instance_eval(*a, &b) raise end 
    end

    c = C.new

    c.__pervasive__(:instance_eval){ @a = 42 }

    p c.instance_variables #=> ["@a"]

~ > ruby samples/b.rb

  ["@a"]

<========< samples/c.rb >========>

~ > cat samples/c.rb

  #
  # even if hackery removes the __pervasive__ method you can still call a
  # pristine method on an object 
  #
    require 'pervasives'

    class VeryBlankSlate
      instance_methods.each{ |m| undef_method m }
    end

    vbs = VeryBlankSlate.new

    begin
      vbs.__pervasive__
    rescue
      'nope not even that'
    end

    Pervasives.call(vbs, :instance_eval){ @a = 42 }

    p Pervasives.call(vbs, :instance_variables) #=> ["@a"]

~ > ruby samples/c.rb

  samples/c.rb:8: warning: undefining `__id__' may cause serious problem
  samples/c.rb:8: warning: undefining `__send__' may cause serious problem
  ["@a"]

<========< samples/d.rb >========>

~ > cat samples/d.rb

  #
  # of course it works for classes and modules too 
  #
    require 'pervasives'

    class C
      def self.new() raise end

      def inspect() 42.inspect end
    end

    c = C.__pervasive__ :new

    p c #=> 42

~ > ruby samples/d.rb

  42