[Zope3-checkins] CVS: zopeproducts/zwiki/StructuredText/regressions - Acquisition.ref:1.1 Acquisition.stx:1.1 ExtensionClass.ref:1.1 ExtensionClass.stx:1.1 InnerLinks.ref:1.1 InnerLinks.stx:1.1 Links.ref:1.1 Links.stx:1.1 MultiMapping.ref:1.1 MultiMapping.stx:1.1 create_referencesfiles.py:1.1 examples.ref:1.1 examples.stx:1.1 examples1.ref:1.1 examples1.stx:1.1 index.ref:1.1 index.stx:1.1 table.ref:1.1 table.stx:1.1

Stephan Richter srichter@cbu.edu
Tue, 8 Apr 2003 00:11:32 -0400


Update of /cvs-repository/zopeproducts/zwiki/StructuredText/regressions
In directory cvs.zope.org:/tmp/cvs-serv5333/StructuredText/regressions

Added Files:
	Acquisition.ref Acquisition.stx ExtensionClass.ref 
	ExtensionClass.stx InnerLinks.ref InnerLinks.stx Links.ref 
	Links.stx MultiMapping.ref MultiMapping.stx 
	create_referencesfiles.py examples.ref examples.stx 
	examples1.ref examples1.stx index.ref index.stx table.ref 
	table.stx 
Log Message:
Add structured text until Zope 3 decides what it wants to do.


=== Added File zopeproducts/zwiki/StructuredText/regressions/Acquisition.ref ===
<html>
<head>
<title>Acquisition</title>
</head>
<body>
<h1>Acquisition</h1>
<p>  <a href="COPYRIGHT.html">Copyright (C) 1996-1998, Digital Creations</a>.</p>
<p>  Acquisition <a href="#ref1">[1]</a> is a mechanism that allows objects to obtain
  attributes from their environment.  It is similar to inheritence,
  except that, rather than traversing an inheritence hierarchy
  to obtain attributes, a containment hierarchy is traversed.</p>
<p>  The <a href="ExtensionClass.html">ExtensionClass</a>. release includes mix-in
  extension base classes that can be used to add acquisition as a
  feature to extension subclasses.  These mix-in classes use the
  context-wrapping feature of ExtensionClasses to implement
  acquisition. Consider the following example:
<pre>
    import ExtensionClass, Acquisition

    class C(ExtensionClass.Base):
      color='red'

    class A(Acquisition.Implicit):

      def report(self):
        print self.color

    a=A()
    c=C()
    c.a=A()

    c.a.report() # prints 'red'

    d=C()
    d.color='green'
    d.a=a

    d.a.report() # prints 'green'

    a.report() # raises an attribute error
</pre>
</p>
<p>  The class <code>A</code> inherits acquisition behavior from
  <code>Acquisition.Implicit</code>.  The object, <code>a</code>, "has" the color of
  objects <code>c</code> and <code>d</code> when it is accessed through them, but it
  has no color by itself.  The object <code>a</code> obtains attributes
  from it's environment, where it's environment is defined by
  the access path used to reach <code>a</code>.</p>
<h2>  Acquisition wrappers</h2>
<p>    When an object that supports acquisition is accessed through
    an extension class instance, a special object, called an
    acquisition wrapper, is returned.  In the example above, the
    expression <code>c.a</code> returns an acquisition wrapper that
    contains references to both <code>c</code> and <code>a</code>.  It is this wrapper
    that performs attribute lookup in <code>c</code> when an attribute
    cannot be found in <code>a</code>.</p>
<p>    Aquisition wrappers provide access to the wrapped objects
    through the attributes <code>aq_parent</code>, <code>aq_self</code>, <code>aq_base</code>.  
    In the example above, the expressions:
<pre>
       'c.a.aq_parent is c'
</pre>
</p>
<p>    and:
<pre>
       'c.a.aq_self is a'
</pre>
</p>
<p>    both evaluate to true, but the expression:
<pre>
       'c.a is a'
</pre>
</p>
<p>    evaluates to false, because the expression <code>c.a</code> evaluates
    to an acquisition wrapper around <code>c</code> and <code>a</code>, not <code>a</code> itself.</p>
<p>    The attribute <code>aq_base</code> is similar to <code>aq_self</code>.  Wrappers may be
    nested and <code>aq_self</code> may be a wrapped object.  The <code>aq_base</code>
    attribute is the underlying object with all wrappers removed.</p>
<h2>  Acquisition Control</h2>
<p>    Two styles of acquisition are supported in the current
    ExtensionClass release, implicit and explicit aquisition.</p>
<h3>    Implicit acquisition</h3>
<p>      Implicit acquisition is so named because it searches for
      attributes from the environment automatically whenever an
      attribute cannot be obtained directly from an object or
      through inheritence.</p>
<p>      An attribute may be implicitly acquired if it's name does
      not begin with an underscore, <code>_</code>.</p>
<p>      To support implicit acquisition, an object should inherit
      from the mix-in class <code>Acquisition.Implicit</code>.</p>
<h3>    Explicit Acquisition</h3>
<p>      When explicit acquisition is used, attributes are not
      automatically obtained from the environment.  Instead, the
      method <code>aq_aquire</code> must be used, as in:
<pre>
        print c.a.aq_acquire('color')
</pre>
</p>
<p>      To support explicit acquisition, an object should inherit
      from the mix-in class <code>Acquisition.Explicit</code>.</p>
<h3>    Controlled Acquisition</h3>
<p>      A class (or instance) can provide attribute by attribute control
      over acquisition.  This is done by:</p>

<ul>
<li>subclassing from <code>Acquisition.Explicit</code>, and</li>
<li>setting all attributes that should be acquired to the special
        value: <code>Acquisition.Acquired</code>.  Setting an attribute to this
        value also allows inherited attributes to be overridden with
        acquired ones.<p>        For example, in:
<pre>
          class C(Acquisition.Explicit):
             id=1
             secret=2
             color=Acquisition.Acquired
             __roles__=Acquisition.Acquired
</pre>
</p>
<p>        The <em>only</em> attributes that are automatically acquired from
        containing objects are <code>color</code>, and <code>__roles__</code>.  Note also
        that the <code>__roles__</code> attribute is acquired even though it's
        name begins with an underscore.  In fact, the special
        <code>Acquisition.Acquired</code> value can be used in
        <code>Acquisition.Implicit</code> objects to implicitly acquire selected
        objects that smell like private objects.</p>
</li>

</ul>
<h3>    Filtered Acquisition</h3>
<p>      The acquisition method, <code>aq_acquire</code>, accepts two optional
      arguments. The first of the additional arguments is a
      "filtering" function that is used when considering whether to
      acquire an object.  The second of the additional arguments is an
      object that is passed as extra data when calling the filtering
      function and which defaults to <code>None</code>.</p>
<p>      The filter function is called with five arguments:</p>

<ul>
<li>The object that the <code>aq_acquire</code> method was called on,</li>
<li>The object where an object was found,</li>
<li>The name of the object, as passed to <code>aq_acquire</code>,</li>
<li>The object found, and</li>
<li>The extra data passed to <code>aq_acquire</code>.</li>

</ul>
<p>      If the filter returns a true object that the object found is
      returned, otherwise, the acquisition search continues.</p>
<p>      For example, in:
<pre>
        from Acquisition import Explicit

        class HandyForTesting:
            def __init__(self, name): self.name=name
            def __str__(self):
                return "%s(%s)" % (self.name, self.__class__.__name__)
            __repr__=__str__

        class E(Explicit, HandyForTesting): pass

        class Nice(HandyForTesting):
            isNice=1
            def __str__(self):
                return HandyForTesting.__str__(self)+' and I am nice!'
            __repr__=__str__

        a=E('a')
        a.b=E('b')
        a.b.c=E('c')
        a.p=Nice('spam')
        a.b.p=E('p')

        def find_nice(self, ancestor, name, object, extra):
            return hasattr(object,'isNice') and object.isNice

        print a.b.c.aq_acquire('p', find_nice)
</pre>
</p>
<p>      The filtered acquisition in the last line skips over the first
      attribute it finds with the name <code>p</code>, because the attribute
      doesn't satisfy the condition given in the filter. The output of
      the last line is:
<pre>
        spam(Nice) and I am nice!
</pre>
</p>
<h2>  Acquisition and methods</h2>
<p>    Python methods of objects that support acquisition can use
    acquired attributes as in the <code>report</code> method of the first example
    above.  When a Python method is called on an object that is
    wrapped by an acquisition wrapper, the wrapper is passed to the
    method as the first argument.  This rule also applies to
    user-defined method types and to C methods defined in pure mix-in
    classes.</p>
<p>    Unfortunately, C methods defined in extension base classes that
    define their own data structures, cannot use aquired attributes at
    this time.  This is because wrapper objects do not conform to the
    data structures expected by these methods.</p>
<h2>  Acquiring Acquiring objects</h2>
<p>    Consider the following example:
<pre>
      from Acquisition import Implicit

      class C(Implicit):
          def __init__(self, name): self.name=name
          def __str__(self):
              return "%s(%s)" % (self.name, self.__class__.__name__)
          __repr__=__str__

      a=C("a")
      a.b=C("b")
      a.b.pref="spam"
      a.b.c=C("c")
      a.b.c.color="red"
      a.b.c.pref="eggs"
      a.x=C("x")

      o=a.b.c.x
</pre>
</p>
<p>    The expression <code>o.color</code> might be expected to return <code>"red"</code>. In
    earlier versions of ExtensionClass, however, this expression
    failed.  Acquired acquiring objects did not acquire from the
    environment they were accessed in, because objects were only
    wrapped when they were first found, and were not rewrapped as they
    were passed down the acquisition tree.</p>
<p>    In the current release of ExtensionClass, the expression "o.color"
    does indeed return <code>"red"</code>.</p>
<p>    When searching for an attribute in <code>o</code>, objects are searched in
    the order <code>x</code>, <code>a</code>, <code>b</code>, <code>c</code>. So, for example, the expression,
    <code>o.pref</code> returns <code>"spam"</code>, not <code>"eggs"</code>.  In earlier releases of
    ExtensionClass, the attempt to get the <code>pref</code> attribute from <code>o</code>
    would have failed.</p>
<p>    If desired, the current rules for looking up attributes in complex
    expressions can best be understood through repeated application of
    the <code>__of__</code> method:</p>
<dl>
<dt>    <code>a.x</code></dt>
<dd><code>x.__of__(a)</code></dd>
<dt>    <code>a.b</code></dt>
<dd><code>b.__of__(a)</code></dd>
<dt>    <code>a.b.x</code></dt>
<dd><code>x.__of__(a).__of__(b.__of__(a))</code></dd>
<dt>    <code>a.b.c</code></dt>
<dd><code>c.__of__(b.__of__(a))</code></dd>
<dt>    <code>a.b.c.x</code></dt>
<dd><code>x.__of__(a).__of__(b.__of__(a)).__of__(c.__of__(b.__of__(a)))</code></dd>
</dl>
<p>    and by keeping in mind that attribute lookup in a wrapper
    is done by trying to lookup the attribute in the wrapped object
    first and then in the parent object.  In the expressions above
    involving the <code>__of__</code> method, lookup proceeds from left to right.</p>
<p>    Note that heuristics are used to avoid most of the repeated
    lookups. For example, in the expression: <code>a.b.c.x.foo</code>, the object
    <code>a</code> is searched no more than once, even though it is wrapped three
    times.</p>
<p><a name="ref1">[1]</a> Gil, J., Lorenz, D., 
   <a href="http://www.bell-labs.com/people/cope/oopsla/Oopsla96TechnicalProgramAbstracts.html#GilLorenz">Environmental Acquisition--A New Inheritance-Like Abstraction Mechanism</a>, 
   OOPSLA '96 Proceedings, ACM SIG-PLAN, October, 1996</p>
</body>
</html>


=== Added File zopeproducts/zwiki/StructuredText/regressions/Acquisition.stx ===
Acquisition

  "Copyright (C) 1996-1998, Digital Creations":COPYRIGHT.html.

  Acquisition [1] is a mechanism that allows objects to obtain
  attributes from their environment.  It is similar to inheritence,
  except that, rather than traversing an inheritence hierarchy
  to obtain attributes, a containment hierarchy is traversed.

  The "ExtensionClass":ExtensionClass.html. release includes mix-in
  extension base classes that can be used to add acquisition as a
  feature to extension subclasses.  These mix-in classes use the
  context-wrapping feature of ExtensionClasses to implement
  acquisition. Consider the following example::

    import ExtensionClass, Acquisition

    class C(ExtensionClass.Base):
      color='red'

    class A(Acquisition.Implicit):

      def report(self):
        print self.color

    a=A()
    c=C()
    c.a=A()

    c.a.report() # prints 'red'

    d=C()
    d.color='green'
    d.a=a

    d.a.report() # prints 'green'

    a.report() # raises an attribute error

  The class 'A' inherits acquisition behavior from
  'Acquisition.Implicit'.  The object, 'a', "has" the color of
  objects 'c' and 'd' when it is accessed through them, but it
  has no color by itself.  The object 'a' obtains attributes
  from it's environment, where it's environment is defined by
  the access path used to reach 'a'.

  Acquisition wrappers

    When an object that supports acquisition is accessed through
    an extension class instance, a special object, called an
    acquisition wrapper, is returned.  In the example above, the
    expression 'c.a' returns an acquisition wrapper that
    contains references to both 'c' and 'a'.  It is this wrapper
    that performs attribute lookup in 'c' when an attribute
    cannot be found in 'a'.

    Aquisition wrappers provide access to the wrapped objects
    through the attributes 'aq_parent', 'aq_self', 'aq_base'.  
    In the example above, the expressions::
      
       'c.a.aq_parent is c'

    and::

       'c.a.aq_self is a'

    both evaluate to true, but the expression::

       'c.a is a'

    evaluates to false, because the expression 'c.a' evaluates
    to an acquisition wrapper around 'c' and 'a', not 'a' itself.

    The attribute 'aq_base' is similar to 'aq_self'.  Wrappers may be
    nested and 'aq_self' may be a wrapped object.  The 'aq_base'
    attribute is the underlying object with all wrappers removed.

  Acquisition Control

    Two styles of acquisition are supported in the current
    ExtensionClass release, implicit and explicit aquisition.
  
    Implicit acquisition
    
      Implicit acquisition is so named because it searches for
      attributes from the environment automatically whenever an
      attribute cannot be obtained directly from an object or
      through inheritence.
  
      An attribute may be implicitly acquired if it's name does
      not begin with an underscore, '_'.
  
      To support implicit acquisition, an object should inherit
      from the mix-in class 'Acquisition.Implicit'.
  
    Explicit Acquisition
  
      When explicit acquisition is used, attributes are not
      automatically obtained from the environment.  Instead, the
      method 'aq_aquire' must be used, as in::
  
	print c.a.aq_acquire('color')
  
      To support explicit acquisition, an object should inherit
      from the mix-in class 'Acquisition.Explicit'.

    Controlled Acquisition

      A class (or instance) can provide attribute by attribute control
      over acquisition.  This is done by:

      - subclassing from 'Acquisition.Explicit', and

      - setting all attributes that should be acquired to the special
        value: 'Acquisition.Acquired'.  Setting an attribute to this
        value also allows inherited attributes to be overridden with
        acquired ones.

	For example, in::

	  class C(Acquisition.Explicit):
	     id=1
	     secret=2
	     color=Acquisition.Acquired
	     __roles__=Acquisition.Acquired

	The *only* attributes that are automatically acquired from
	containing objects are 'color', and '__roles__'.  Note also
	that the '__roles__' attribute is acquired even though it's
	name begins with an underscore.  In fact, the special
	'Acquisition.Acquired' value can be used in
	'Acquisition.Implicit' objects to implicitly acquire selected
	objects that smell like private objects.

    Filtered Acquisition

      The acquisition method, 'aq_acquire', accepts two optional
      arguments. The first of the additional arguments is a
      "filtering" function that is used when considering whether to
      acquire an object.  The second of the additional arguments is an
      object that is passed as extra data when calling the filtering
      function and which defaults to 'None'.

      The filter function is called with five arguments:

      - The object that the 'aq_acquire' method was called on,

      - The object where an object was found,

      - The name of the object, as passed to 'aq_acquire',

      - The object found, and

      - The extra data passed to 'aq_acquire'.

      If the filter returns a true object that the object found is
      returned, otherwise, the acquisition search continues.

      For example, in::

	from Acquisition import Explicit
	
	class HandyForTesting:
	    def __init__(self, name): self.name=name
	    def __str__(self):
		return "%s(%s)" % (self.name, self.__class__.__name__)
	    __repr__=__str__
	
	class E(Explicit, HandyForTesting): pass
	
	class Nice(HandyForTesting):
	    isNice=1
	    def __str__(self):
		return HandyForTesting.__str__(self)+' and I am nice!'
	    __repr__=__str__
	
	a=E('a')
	a.b=E('b')
	a.b.c=E('c')
	a.p=Nice('spam')
	a.b.p=E('p')
	
	def find_nice(self, ancestor, name, object, extra):
	    return hasattr(object,'isNice') and object.isNice
	
	print a.b.c.aq_acquire('p', find_nice)

      The filtered acquisition in the last line skips over the first
      attribute it finds with the name 'p', because the attribute
      doesn't satisfy the condition given in the filter. The output of
      the last line is::

        spam(Nice) and I am nice!

  Acquisition and methods

    Python methods of objects that support acquisition can use
    acquired attributes as in the 'report' method of the first example
    above.  When a Python method is called on an object that is
    wrapped by an acquisition wrapper, the wrapper is passed to the
    method as the first argument.  This rule also applies to
    user-defined method types and to C methods defined in pure mix-in
    classes.

    Unfortunately, C methods defined in extension base classes that
    define their own data structures, cannot use aquired attributes at
    this time.  This is because wrapper objects do not conform to the
    data structures expected by these methods.

  Acquiring Acquiring objects

    Consider the following example::

      from Acquisition import Implicit
      
      class C(Implicit):
	  def __init__(self, name): self.name=name
	  def __str__(self):
	      return "%s(%s)" % (self.name, self.__class__.__name__)
	  __repr__=__str__
      
      a=C("a")
      a.b=C("b")
      a.b.pref="spam"
      a.b.c=C("c")
      a.b.c.color="red"
      a.b.c.pref="eggs"
      a.x=C("x")

      o=a.b.c.x

    The expression 'o.color' might be expected to return '"red"'. In
    earlier versions of ExtensionClass, however, this expression
    failed.  Acquired acquiring objects did not acquire from the
    environment they were accessed in, because objects were only
    wrapped when they were first found, and were not rewrapped as they
    were passed down the acquisition tree.

    In the current release of ExtensionClass, the expression "o.color"
    does indeed return '"red"'.

    When searching for an attribute in 'o', objects are searched in
    the order 'x', 'a', 'b', 'c'. So, for example, the expression,
    'o.pref' returns '"spam"', not '"eggs"'.  In earlier releases of
    ExtensionClass, the attempt to get the 'pref' attribute from 'o'
    would have failed.

    If desired, the current rules for looking up attributes in complex
    expressions can best be understood through repeated application of
    the '__of__' method:

    'a.x' -- 'x.__of__(a)'

    'a.b' -- 'b.__of__(a)'

    'a.b.x' -- 'x.__of__(a).__of__(b.__of__(a))'

    'a.b.c' -- 'c.__of__(b.__of__(a))'

    'a.b.c.x' --
        'x.__of__(a).__of__(b.__of__(a)).__of__(c.__of__(b.__of__(a)))'

    and by keeping in mind that attribute lookup in a wrapper
    is done by trying to lookup the attribute in the wrapped object
    first and then in the parent object.  In the expressions above
    involving the '__of__' method, lookup proceeds from left to right.

    Note that heuristics are used to avoid most of the repeated
    lookups. For example, in the expression: 'a.b.c.x.foo', the object
    'a' is searched no more than once, even though it is wrapped three
    times.

.. [1] Gil, J., Lorenz, D., 
   "Environmental Acquisition--A New Inheritance-Like Abstraction Mechanism",
   http://www.bell-labs.com/people/cope/oopsla/Oopsla96TechnicalProgramAbstracts.html#GilLorenz, 
   OOPSLA '96 Proceedings, ACM SIG-PLAN, October, 1996
	 


=== Added File zopeproducts/zwiki/StructuredText/regressions/ExtensionClass.ref === (514/614 lines abridged)
<html>
<head>
<title>Extension Classes, Python Extension Types Become Classes</title>
</head>
<body>
<h1>Extension Classes, Python Extension Types Become Classes</h1>
<p>  Jim Fulton, Digital Creations, Inc.
  jim@digicool.com</p>
<p>  <a href="COPYRIGHT.html">Copyright (C) 1996-1998, Digital Creations</a>.</p>
<h2>  Abstract</h2>
<p>    A lightweight mechanism has been developed for making Python
    extension types more class-like.  Classes can be developed in an
    extension language, such as C or C++, and these classes can be
    treated like other python classes:</p>

<ul>
<li>They can be sub-classed in python,</li>
<li>They provide access to method documentation strings, and</li>
<li>They can be used to directly create new instances.</li>

</ul>
<p>    An example class shows how extension classes are implemented and how
    they differ from extension types.</p>
<p>    Extension classes provide additional extensions to class and
    instance semantics, including:</p>

<ul>
<li>A protocol for accessing subobjects "in the context of" their
      containers.  This is used to implement custom method types
      and <a href="Acquisition.html">environmental acquisition</a>.</li>
<li>A protocol for overriding method call semantics.  This is used
      to implement "synchonized" classes and could be used to
      implement argument type checking.</li>
<li>A protocol for class initialization that supports execution of a
      special <code>__class_init__</code> method after a class has been
      initialized. </li>

</ul>
<p>    Extension classes illustrate how the Python class mechanism can be
    extended and may provide a basis for improved or specialized class
    models. </p>
<h2>  Releases</h2>
<p>    To find out what's changed in this release,
    see the <a href="release.html">release notes</a>.</p>
<h2>  Problem</h2>
<p>    Currently, Python provides two ways of defining new kinds of objects:</p>

<ul>
<li>Python classes</li>
<li>Extension types</li>

[-=- -=- -=- 514 lines omitted -=- -=- -=-]

<li>The extension class module defines new method types to bind C and
      python methods to extension class instances.  It would be useful
      for these method objects to provide access to function call
      information, such as the number and names of arguments and the
      number of defaults, by parsing extension function documentation
      strings.</li>

</ul>
<h2>  Applications</h2>
<p>    Aside from test and demonstration applications, the extension class
    mechanism has been used to provide an extension-based implementation
    of the persistence mechanism described in <a href="#ref1">[1]</a>.  We have developed
    this further to provide features such as automatic deactivation of
    objects not used after some period of time and to provide more
    efficient persistent-object cache management.</p>
<p>    Acquisition has been heavily used in our recent products.
    Synchonized classes have also been used in recent products.</p>
<h2>  Summary</h2>
<p>    The extension-class mechanism described here provides a way to add
    class services to extension types.  It allows:
<ul>
<li>Sub-classing extension classes in Python,</li>
<li>Construction of extension class instances by calling extension
        classes,</li>
<li>Extension classes to provide meta-data, such as unbound methods
        and their documentation string.</li>

</ul>
</p>
<p>    In addition, the extension class module provides a relatively
    concise example of the use of mechanisms that were added to Python
    to support MESS <a href="#ref6">[6]</a>, and that were described at the fourth Python
    Workshop <a href="#ref4">[4]</a>.  It is hoped that this will spur research in improved
    and specialized models for class implementation in Python.</p>
<p>  References</p>
<p><a name="ref1">[1]</a> Fulton, J., <a href="http://www.digicool.com/papers/Persistence.html">Providing Persistence for World-Wide-Web Applications</a>,
 Proceedings of the 5th Python Workshop.</p>
<p><a name="ref2">[2]</a> Page, R. and Cropper, S., <a href="http://www.digicool.com/papers/DocumentTemplate.html">Document Template</a>,
 Proceedings of the 5th Python Workshop.</p>
<p><a name="ref3">[3]</a> Beaudry, D., <a href="http://www.python.org/workshops/1994-11/BuiltInClasses/BuiltInClasses_1.html">Deriving Built-In Classes in Python</a>,
 Proceedings of the First International Python Workshop.</p>
<p><a name="ref4">[4]</a> Van Rossum, G., <a href="http://www.python.org/workshops/1996-06/notes/thursday.html">Don Beaudry Hack - MESS</a>,
 presented in the Developer's Future Enhancements session of the 
 4th Python Workshop. </p>
<p><a name="ref5">[5]</a> Fulton, J., <a href="http://www.digicool.com/jim/MetaType.c">Meta-Type Object</a>,
 This is a small proposal, the text of which is contained in a 
 sample implementation source file,  </p>
<p><a name="ref6">[6]</a> Beaudry, D., and Ascher, D., <a href="http://starship.skyport.net/~da/mess/">The Meta-Extension Set</a>.</p>
</body>
</html>


=== Added File zopeproducts/zwiki/StructuredText/regressions/ExtensionClass.stx === (614/714 lines abridged)
Extension Classes, Python Extension Types Become Classes

  Jim Fulton, Digital Creations, Inc.
  jim@digicool.com

  "Copyright (C) 1996-1998, Digital Creations":COPYRIGHT.html.

  Abstract
  
    A lightweight mechanism has been developed for making Python
    extension types more class-like.  Classes can be developed in an
    extension language, such as C or C++, and these classes can be
    treated like other python classes:
  
    - They can be sub-classed in python,
  
    - They provide access to method documentation strings, and
  
    - They can be used to directly create new instances.
  
    An example class shows how extension classes are implemented and how
    they differ from extension types.
  
    Extension classes provide additional extensions to class and
    instance semantics, including:

    - A protocol for accessing subobjects "in the context of" their
      containers.  This is used to implement custom method types
      and "environmental acquisition":Acquisition.html.

    - A protocol for overriding method call semantics.  This is used
      to implement "synchonized" classes and could be used to
      implement argument type checking.

    - A protocol for class initialization that supports execution of a
      special '__class_init__' method after a class has been
      initialized. 
  
    Extension classes illustrate how the Python class mechanism can be
    extended and may provide a basis for improved or specialized class
    models. 

  Releases

    To find out what's changed in this release,
    see the "release notes":release.html.
  
  Problem
  
    Currently, Python provides two ways of defining new kinds of objects:

[-=- -=- -=- 614 lines omitted -=- -=- -=-]

    efficient persistent-object cache management.

    Acquisition has been heavily used in our recent products.
    Synchonized classes have also been used in recent products.
  
  Summary
    
    The extension-class mechanism described here provides a way to add
    class services to extension types.  It allows:
  
      - Sub-classing extension classes in Python,
  
      - Construction of extension class instances by calling extension
	classes,
  
      - Extension classes to provide meta-data, such as unbound methods
	and their documentation string.
  
    In addition, the extension class module provides a relatively
    concise example of the use of mechanisms that were added to Python
    to support MESS [6], and that were described at the fourth Python
    Workshop [4].  It is hoped that this will spur research in improved
    and specialized models for class implementation in Python.
  
  References
  
.. [1] Fulton, J., "Providing Persistence for World-Wide-Web Applications", 
 http://www.digicool.com/papers/Persistence.html,
 Proceedings of the 5th Python Workshop.
   
.. [2] Page, R. and Cropper, S., "Document Template", 
 http://www.digicool.com/papers/DocumentTemplate.html,
 Proceedings of the 5th Python Workshop.
   
.. [3] Beaudry, D., "Deriving Built-In Classes in Python", 
 http://www.python.org/workshops/1994-11/BuiltInClasses/BuiltInClasses_1.html,
 Proceedings of the First International Python Workshop.
   
.. [4] Van Rossum, G., "Don Beaudry Hack - MESS", 
 http://www.python.org/workshops/1996-06/notes/thursday.html,
 presented in the Developer's Future Enhancements session of the 
 4th Python Workshop. 
   
.. [5] Fulton, J., "Meta-Type Object",
 http://www.digicool.com/jim/MetaType.c,
 This is a small proposal, the text of which is contained in a 
 sample implementation source file,  
   
.. [6] Beaudry, D., and Ascher, D., "The Meta-Extension Set", 
 http://starship.skyport.net/~da/mess/.


=== Added File zopeproducts/zwiki/StructuredText/regressions/InnerLinks.ref ===
<html>
<head>
<title>This is the InnerLinkTest</title>
</head>
<body>
<h1>This is the InnerLinkTest</h1>
<p>  see also <a href="#ref1">[1]</a> and <a href="#ref2">[2]</a></p>
<p>  <a name="ref1">[1]</a> "Zope Book" by Amos Lattmeier and Michel Pelletier</p>
<p>  <a name="ref2">[2]</a> "Python Book" by Guido van Rossum</p>
</body>
</html>


=== Added File zopeproducts/zwiki/StructuredText/regressions/InnerLinks.stx ===
This is the InnerLinkTest


  see also [1] and [2]


  .. [1] "Zope Book" by Amos Lattmeier and Michel Pelletier

  .. [2] "Python Book" by Guido van Rossum
  


=== Added File zopeproducts/zwiki/StructuredText/regressions/Links.ref ===
<html>
<head>
<title>This is LinkTest</title>
</head>
<body>
<h1>This is LinkTest</h1>

<ul>
<li>please click <a href="/Members/Zope">here</a></li>
<li>please click <a href="/Members/Zope?a=b&c=d%20blabla">here</a></li>
<li>please click <a href="http://www.zope.org">here</a></li>
<li>please click <a href="http://www.zope.org/members/">here</a></li>
<li>please click <a href="http://www.zope.org:2001">here</a> </li>
<li>please click <a href="http://www.zope.org:2001/members/">here</a></li>
<li>please click <a href="http://www.zope.org:2001/%20/Members/zope?a=222&b=213&_xc=just%20a%20test">here</a> </li>
<li>please click <a href="http://www.zope.org:2001/%20/Members/zope?a=222&b=213&_xc=just%20a%20test">here</a> </li>
<li>please click <a href="http://www.zope.org:2001/%20/Members/zope?a=222&b=213&_xc=just%20a%20test">here</a> </li>

</ul>
<p>  And now a paragraph with <a href="http://www.zope-rocks.org">Link 1</a> and 
  <a href="http://www.zope-is-kewl.com">Link 2</a>  and <a href="http://www.freshmeat.net">one more link - yeah.</a></p>
</body>
</html>


=== Added File zopeproducts/zwiki/StructuredText/regressions/Links.stx ===
This is LinkTest

  - please click "here":/Members/Zope

  - please click "here":/Members/Zope?a=b&c=d%20blabla

  - please click "here":http://www.zope.org

  - please click "here":http://www.zope.org/members/

  - please click "here":http://www.zope.org:2001 
 
  - please click "here":http://www.zope.org:2001/members/

  - please click "here":http://www.zope.org:2001/%20/Members/zope?a=222&b=213&_xc=just%20a%20test 

  - please click "here":http://www.zope.org:2001/%20/Members/zope?a=222&b=213&_xc=just%20a%20test 

  - please click "here", http://www.zope.org:2001/%20/Members/zope?a=222&b=213&_xc=just%20a%20test 


  And now a paragraph with "Link 1":http://www.zope-rocks.org and 
  "Link 2":http://www.zope-is-kewl.com  and "one more link - yeah.":http://www.freshmeat.net



=== Added File zopeproducts/zwiki/StructuredText/regressions/MultiMapping.ref ===
<html>
<head>
<title>Example: MultiMapping objects</title>
</head>
<body>
<h1>Example: MultiMapping objects</h1>
<p>  <a href="COPYRIGHT.html">Copyright (C) 1996-1998, Digital Creations</a>.</p>
<p>  As an example, consider an extension class that implements a
  "MultiMapping". A multi-mapping is an object that encapsulates 0
  or more mapping objects.  When an attempt is made to lookup an
  object, the encapsulated mapping objects are searched until an
  object is found.</p>
<p>  Consider an implementation of a MultiMapping extension type,
  without use of the extension class mechanism:
<pre>
    #include "Python.h"

    #define UNLESS(E) if(!(E))

    typedef struct {
        PyObject_HEAD
        PyObject *data;
    } MMobject;

    staticforward PyTypeObject MMtype;

    static PyObject *
    MM_push(MMobject *self, PyObject *args){
        PyObject *src;
        UNLESS(PyArg_ParseTuple(args, "O", &amp;src)) return NULL;
        UNLESS(-1 != PyList_Append(self-&gt;data,src)) return NULL;
        Py_INCREF(Py_None);
        return Py_None;
    }

    static PyObject *
    MM_pop(MMobject *self, PyObject *args){
        long l;
        PyObject *r;
        static PyObject *emptyList=0;

        UNLESS(emptyList) UNLESS(emptyList=PyList_New(0)) return NULL;
        UNLESS(PyArg_ParseTuple(args, "")) return NULL;
        UNLESS(-1 != (l=PyList_Size(self-&gt;data))) return NULL;
        l--;
        UNLESS(r=PySequence_GetItem(self-&gt;data,l)) return NULL;
        UNLESS(-1 != PyList_SetSlice(self-&gt;data,l,l+1,emptyList)) goto err;
        return r;
    err:
        Py_DECREF(r);
        return NULL;
    }

    static struct PyMethodDef MM_methods[] = {
        {"push", (PyCFunction) MM_push, 1,
         "push(mapping_object) -- Add a data source"},
        {"pop",  (PyCFunction) MM_pop,  1,
         "pop() -- Remove and return the last data source added"}, 
        {NULL,              NULL}           /* sentinel */
    };

    static PyObject *
    newMMobject(PyObject *ignored, PyObject *args){
        MMobject *self;

        UNLESS(PyArg_ParseTuple(args, "")) return NULL;
        UNLESS(self = PyObject_NEW(MMobject, &amp;MMtype)) return NULL;
        UNLESS(self-&gt;data=PyList_New(0)) goto err;
        return (PyObject *)self;
    err:
        Py_DECREF(self);
        return NULL;
    }

    static void
    MM_dealloc(MMobject *self){
        Py_XDECREF(self-&gt;data);
        PyMem_DEL(self);
    }

    static PyObject *
    MM_getattr(MMobject *self, char *name){
        return Py_FindMethod(MM_methods, (PyObject *)self, name);
    }

    static int
    MM_length(MMobject *self){
        long l=0, el, i;
        PyObject *e=0;

        UNLESS(-1 != (i=PyList_Size(self-&gt;data))) return -1;
        while(--i &gt;= 0)
          {
            e=PyList_GetItem(self-&gt;data,i);
            UNLESS(-1 != (el=PyObject_Length(e))) return -1;
            l+=el;
          }
        return l;
    }

    static PyObject *
    MM_subscript(MMobject *self, PyObject *key){
        long i;
        PyObject *e;

        UNLESS(-1 != (i=PyList_Size(self-&gt;data))) return NULL;
        while(--i &gt;= 0)
          {
            e=PyList_GetItem(self-&gt;data,i);
            if(e=PyObject_GetItem(e,key)) return e;
            PyErr_Clear();
          }
        PyErr_SetObject(PyExc_KeyError,key);
        return NULL;
    }

    static PyMappingMethods MM_as_mapping = {
              (inquiry)MM_length,           /*mp_length*/
              (binaryfunc)MM_subscript,             /*mp_subscript*/
              (objobjargproc)NULL,          /*mp_ass_subscript*/
    };

    /* -------------------------------------------------------- */

    static char MMtype__doc__[] = 
    "MultiMapping -- Combine multiple mapping objects for lookup"
    ;

    static PyTypeObject MMtype = {
              PyObject_HEAD_INIT(&amp;PyType_Type)
              0,                            /*ob_size*/
              "MultMapping",                        /*tp_name*/
              sizeof(MMobject),             /*tp_basicsize*/
              0,                            /*tp_itemsize*/
              /* methods */
              (destructor)MM_dealloc,               /*tp_dealloc*/
              (printfunc)0,                 /*tp_print*/
              (getattrfunc)MM_getattr,      /*tp_getattr*/
              (setattrfunc)0,                       /*tp_setattr*/
              (cmpfunc)0,                   /*tp_compare*/
              (reprfunc)0,                  /*tp_repr*/
              0,                            /*tp_as_number*/
              0,                            /*tp_as_sequence*/
              &amp;MM_as_mapping,                       /*tp_as_mapping*/
              (hashfunc)0,                  /*tp_hash*/
              (ternaryfunc)0,                       /*tp_call*/
              (reprfunc)0,                  /*tp_str*/

              /* Space for future expansion */
              0L,0L,0L,0L,
              MMtype__doc__ /* Documentation string */
    };

    static struct PyMethodDef MultiMapping_methods[] = {
        {"MultiMapping", (PyCFunction)newMMobject, 1,
         "MultiMapping() -- Create a new empty multi-mapping"},
        {NULL,              NULL}           /* sentinel */
    };

    void
    initMultiMapping(){
        PyObject *m;

        m = Py_InitModule4(
            "MultiMapping", MultiMapping_methods,
              "MultiMapping -- Wrap multiple mapping objects for lookup",
              (PyObject*)NULL,PYTHON_API_VERSION);

        if (PyErr_Occurred()) 
           Py_FatalError("can't initialize module MultiMapping");
    }
</pre>
</p>
<p>  This module defines an extension type, <code>MultiMapping</code>, and exports a
  module function, <code>MultiMapping</code>, that creates <code>MultiMapping</code>
  Instances. The type provides two methods, <code>push</code>, and <code>pop</code>, for
  adding and removing mapping objects to the multi-mapping.
  The type provides mapping behavior, implementing mapping length
  and subscript operators but not mapping a subscript assignment
  operator.</p>
<p>  Now consider an extension class implementation of MultiMapping
  objects:
<pre>
    #include "Python.h"
    #include "ExtensionClass.h"

    #define UNLESS(E) if(!(E))

    typedef struct {
        PyObject_HEAD
        PyObject *data;
    } MMobject;

    staticforward PyExtensionClass MMtype;

    static PyObject *
    MM_push(self, args)
              MMobject *self;
              PyObject *args;
    {
        PyObject *src;
        UNLESS(PyArg_ParseTuple(args, "O", &amp;src)) return NULL;
        UNLESS(-1 != PyList_Append(self-&gt;data,src)) return NULL;
        Py_INCREF(Py_None);
        return Py_None;
    }

    static PyObject *
    MM_pop(self, args)
              MMobject *self;
              PyObject *args;
    {
        long l;
        PyObject *r;
        static PyObject *emptyList=0;

        UNLESS(emptyList) UNLESS(emptyList=PyList_New(0)) return NULL;
        UNLESS(PyArg_ParseTuple(args, "")) return NULL;
        UNLESS(-1 != (l=PyList_Size(self-&gt;data))) return NULL;
        l--;
        UNLESS(r=PySequence_GetItem(self-&gt;data,l)) return NULL;
        UNLESS(-1 != PyList_SetSlice(self-&gt;data,l,l+1,emptyList)) goto err;
        return r;
    err:
        Py_DECREF(r);
        return NULL;
    }

    static PyObject *
    MM__init__(self, args)
           MMobject *self;
           PyObject *args;
    {
        UNLESS(PyArg_ParseTuple(args, "")) return NULL;
        UNLESS(self-&gt;data=PyList_New(0)) goto err;
        Py_INCREF(Py_None);
        return Py_None;
    err:
        Py_DECREF(self);
        return NULL;
    }

    static struct PyMethodDef MM_methods[] = {
        {"__init__", (PyCFunction)MM__init__, 1,
         "__init__() -- Create a new empty multi-mapping"},
        {"push", (PyCFunction) MM_push, 1,
         "push(mapping_object) -- Add a data source"},
        {"pop",  (PyCFunction) MM_pop,  1,
         "pop() -- Remove and return the last data source added"}, 
        {NULL,              NULL}           /* sentinel */
    };

    static void
    MM_dealloc(self)
           MMobject *self;
    {
        Py_XDECREF(self-&gt;data);
        PyMem_DEL(self);
    }

    static PyObject *
    MM_getattr(self, name)
              MMobject *self;
              char *name;
    {
        return Py_FindMethod(MM_methods, (PyObject *)self, name);
    }

    static int
    MM_length(self)
              MMobject *self;
    {
        long l=0, el, i;
        PyObject *e=0;

        UNLESS(-1 != (i=PyList_Size(self-&gt;data))) return -1;
        while(--i &gt;= 0)
          {
            e=PyList_GetItem(self-&gt;data,i);
            UNLESS(-1 != (el=PyObject_Length(e))) return -1;
            l+=el;
          }
        return l;
    }

    static PyObject *
    MM_subscript(self, key)
              MMobject *self;
              PyObject *key;
    {
        long i;
        PyObject *e;

        UNLESS(-1 != (i=PyList_Size(self-&gt;data))) return NULL;
        while(--i &gt;= 0)
          {
            e=PyList_GetItem(self-&gt;data,i);
            if(e=PyObject_GetItem(e,key)) return e;
            PyErr_Clear();
          }
        PyErr_SetObject(PyExc_KeyError,key);
        return NULL;
    }

    static PyMappingMethods MM_as_mapping = {
              (inquiry)MM_length,           /*mp_length*/
              (binaryfunc)MM_subscript,             /*mp_subscript*/
              (objobjargproc)NULL,          /*mp_ass_subscript*/
    };

    /* -------------------------------------------------------- */

    static char MMtype__doc__[] = 
    "MultiMapping -- Combine multiple mapping objects for lookup"
    ;

    static PyExtensionClass MMtype = {
              PyObject_HEAD_INIT(&amp;PyType_Type)
              0,                            /*ob_size*/
              "MultMapping",                        /*tp_name*/
              sizeof(MMobject),             /*tp_basicsize*/
              0,                            /*tp_itemsize*/
              /* methods */
              (destructor)MM_dealloc,               /*tp_dealloc*/
              (printfunc)0,                 /*tp_print*/
              (getattrfunc)MM_getattr,      /*tp_getattr*/
              (setattrfunc)0,                       /*tp_setattr*/
              (cmpfunc)0,                   /*tp_compare*/
              (reprfunc)0,                  /*tp_repr*/
              0,                            /*tp_as_number*/
              0,                            /*tp_as_sequence*/
              &amp;MM_as_mapping,                       /*tp_as_mapping*/
              (hashfunc)0,                  /*tp_hash*/
              (ternaryfunc)0,                       /*tp_call*/
              (reprfunc)0,                  /*tp_str*/

              /* Space for future expansion */
              0L,0L,0L,0L,
              MMtype__doc__, /* Documentation string */
              METHOD_CHAIN(MM_methods)
    };

    static struct PyMethodDef MultiMapping_methods[] = {
        {NULL,              NULL}           /* sentinel */
    };

    void
    initMultiMapping()
    {
        PyObject *m, *d;

        m = Py_InitModule4(
            "MultiMapping", MultiMapping_methods,
            "MultiMapping -- Wrap multiple mapping objects for lookup",
            (PyObject*)NULL,PYTHON_API_VERSION);
        d = PyModule_GetDict(m);
        PyExtensionClass_Export(d,"MultiMapping",MMtype);

        if (PyErr_Occurred()) 
           Py_FatalError("can't initialize module MultiMapping");
    }
</pre>
</p>
<p>  This version includes <code>ExtensionClass.h</code>.  The two declarations of
  <code>MMtype</code> have been changed from <code>PyTypeObject</code> to <code>PyExtensionClass</code>.
  The <code>METHOD_CHAIN</code> macro has been used to add methods to the end of
  the definition for <code>MMtype</code>.  The module function, newMMobject has
  been replaced by the <code>MMtype</code> method, <code>MM__init__</code>.  Note that this
  method does not create or return a new object.  Finally, the lines:
<pre>
    d = PyModule_GetDict(m);
    PyExtensionClass_Export(d,"MultiMapping",MMtype);
</pre>
</p>
<p>  Have been added to both initialize the extension class and to export
  it in the module dictionary.</p>
<p>  To use this module, compile, link, and import it as with any other
  extension module.  The following python code illustrates the
  module's use:
<pre>
    from MultiMapping import MultiMapping
    m=MultiMapping()
    m.push({'spam':1, 'eggs':2})
    m.push({'spam':3, 'ham':4})

    m['spam'] # returns 3
    m['ham']  # returns 4
    m['foo']  # raises a key error
</pre>
</p>
<p>  Creating the <code>MultiMapping</code> object took three steps, one to create
  an empty <code>MultiMapping</code>, and two to add mapping objects to it.  We
  might wish to simplify the process of creating MultiMapping
  objects by providing a constructor that takes source mapping
  objects as parameters.  We can do this by sub-classing MultiMapping
  in Python:
<pre>
    from MultiMapping import MultiMapping
    class ExtendedMultiMapping(MultiMapping):
        def __init__(self,*data):
          MultiMapping.__init__(self)
          for d in data: self.push(d)

    m=ExtendedMultiMapping({'spam':1, 'eggs':2}, {'spam':3, 'ham':4})

    m['spam'] # returns 3
    m['ham']  # returns 4
    m['foo']  # raises a key error
</pre>
</p>
<p>  Note that the source file included in the ExtensionClass
  distribution has numerous enhancements beyond the version shown in
  this document.</p>
</body>
</html>


=== Added File zopeproducts/zwiki/StructuredText/regressions/MultiMapping.stx ===
Example: MultiMapping objects

  "Copyright (C) 1996-1998, Digital Creations":COPYRIGHT.html.

  As an example, consider an extension class that implements a
  "MultiMapping". A multi-mapping is an object that encapsulates 0
  or more mapping objects.  When an attempt is made to lookup an
  object, the encapsulated mapping objects are searched until an
  object is found.

  Consider an implementation of a MultiMapping extension type,
  without use of the extension class mechanism::

    #include "Python.h"
    
    #define UNLESS(E) if(!(E))
    
    typedef struct {
        PyObject_HEAD
        PyObject *data;
    } MMobject;
    
    staticforward PyTypeObject MMtype;
    
    static PyObject *
    MM_push(MMobject *self, PyObject *args){
        PyObject *src;
        UNLESS(PyArg_ParseTuple(args, "O", &src)) return NULL;
        UNLESS(-1 != PyList_Append(self->data,src)) return NULL;
        Py_INCREF(Py_None);
        return Py_None;
    }
    
    static PyObject *
    MM_pop(MMobject *self, PyObject *args){
        long l;
        PyObject *r;
        static PyObject *emptyList=0;
    
        UNLESS(emptyList) UNLESS(emptyList=PyList_New(0)) return NULL;
        UNLESS(PyArg_ParseTuple(args, "")) return NULL;
        UNLESS(-1 != (l=PyList_Size(self->data))) return NULL;
        l--;
        UNLESS(r=PySequence_GetItem(self->data,l)) return NULL;
        UNLESS(-1 != PyList_SetSlice(self->data,l,l+1,emptyList)) goto err;
        return r;
    err:
        Py_DECREF(r);
        return NULL;
    }
    
    static struct PyMethodDef MM_methods[] = {
        {"push", (PyCFunction) MM_push, 1,
         "push(mapping_object) -- Add a data source"},
        {"pop",  (PyCFunction) MM_pop,  1,
         "pop() -- Remove and return the last data source added"}, 
        {NULL,              NULL}           /* sentinel */
    };
    
    static PyObject *
    newMMobject(PyObject *ignored, PyObject *args){
        MMobject *self;
              
        UNLESS(PyArg_ParseTuple(args, "")) return NULL;
        UNLESS(self = PyObject_NEW(MMobject, &MMtype)) return NULL;
        UNLESS(self->data=PyList_New(0)) goto err;
        return (PyObject *)self;
    err:
        Py_DECREF(self);
        return NULL;
    }
    
    static void
    MM_dealloc(MMobject *self){
        Py_XDECREF(self->data);
        PyMem_DEL(self);
    }
    
    static PyObject *
    MM_getattr(MMobject *self, char *name){
        return Py_FindMethod(MM_methods, (PyObject *)self, name);
    }
    
    static int
    MM_length(MMobject *self){
        long l=0, el, i;
        PyObject *e=0;
    
        UNLESS(-1 != (i=PyList_Size(self->data))) return -1;
        while(--i >= 0)
          {
            e=PyList_GetItem(self->data,i);
            UNLESS(-1 != (el=PyObject_Length(e))) return -1;
            l+=el;
          }
        return l;
    }
    
    static PyObject *
    MM_subscript(MMobject *self, PyObject *key){
        long i;
        PyObject *e;
    
        UNLESS(-1 != (i=PyList_Size(self->data))) return NULL;
        while(--i >= 0)
          {
            e=PyList_GetItem(self->data,i);
            if(e=PyObject_GetItem(e,key)) return e;
            PyErr_Clear();
          }
        PyErr_SetObject(PyExc_KeyError,key);
        return NULL;
    }
    
    static PyMappingMethods MM_as_mapping = {
              (inquiry)MM_length,           /*mp_length*/
              (binaryfunc)MM_subscript,             /*mp_subscript*/
              (objobjargproc)NULL,          /*mp_ass_subscript*/
    };
    
    /* -------------------------------------------------------- */
    
    static char MMtype__doc__[] = 
    "MultiMapping -- Combine multiple mapping objects for lookup"
    ;
    
    static PyTypeObject MMtype = {
              PyObject_HEAD_INIT(&PyType_Type)
              0,                            /*ob_size*/
              "MultMapping",                        /*tp_name*/
              sizeof(MMobject),             /*tp_basicsize*/
              0,                            /*tp_itemsize*/
              /* methods */
              (destructor)MM_dealloc,               /*tp_dealloc*/
              (printfunc)0,                 /*tp_print*/
              (getattrfunc)MM_getattr,      /*tp_getattr*/
              (setattrfunc)0,                       /*tp_setattr*/
              (cmpfunc)0,                   /*tp_compare*/
              (reprfunc)0,                  /*tp_repr*/
              0,                            /*tp_as_number*/
              0,                            /*tp_as_sequence*/
              &MM_as_mapping,                       /*tp_as_mapping*/
              (hashfunc)0,                  /*tp_hash*/
              (ternaryfunc)0,                       /*tp_call*/
              (reprfunc)0,                  /*tp_str*/
    
              /* Space for future expansion */
              0L,0L,0L,0L,
              MMtype__doc__ /* Documentation string */
    };
    
    static struct PyMethodDef MultiMapping_methods[] = {
        {"MultiMapping", (PyCFunction)newMMobject, 1,
         "MultiMapping() -- Create a new empty multi-mapping"},
        {NULL,              NULL}           /* sentinel */
    };
    
    void
    initMultiMapping(){
        PyObject *m;
    
        m = Py_InitModule4(
            "MultiMapping", MultiMapping_methods,
              "MultiMapping -- Wrap multiple mapping objects for lookup",
              (PyObject*)NULL,PYTHON_API_VERSION);
    
        if (PyErr_Occurred()) 
           Py_FatalError("can't initialize module MultiMapping");
    }

  This module defines an extension type, 'MultiMapping', and exports a
  module function, 'MultiMapping', that creates 'MultiMapping'
  Instances. The type provides two methods, 'push', and 'pop', for
  adding and removing mapping objects to the multi-mapping.
  The type provides mapping behavior, implementing mapping length
  and subscript operators but not mapping a subscript assignment
  operator.

  Now consider an extension class implementation of MultiMapping
  objects::

    #include "Python.h"
    #include "ExtensionClass.h"
    
    #define UNLESS(E) if(!(E))
    
    typedef struct {
        PyObject_HEAD
        PyObject *data;
    } MMobject;
    
    staticforward PyExtensionClass MMtype;
    
    static PyObject *
    MM_push(self, args)
              MMobject *self;
              PyObject *args;
    {
        PyObject *src;
        UNLESS(PyArg_ParseTuple(args, "O", &src)) return NULL;
        UNLESS(-1 != PyList_Append(self->data,src)) return NULL;
        Py_INCREF(Py_None);
        return Py_None;
    }
    
    static PyObject *
    MM_pop(self, args)
              MMobject *self;
              PyObject *args;
    {
        long l;
        PyObject *r;
        static PyObject *emptyList=0;
    
        UNLESS(emptyList) UNLESS(emptyList=PyList_New(0)) return NULL;
        UNLESS(PyArg_ParseTuple(args, "")) return NULL;
        UNLESS(-1 != (l=PyList_Size(self->data))) return NULL;
        l--;
        UNLESS(r=PySequence_GetItem(self->data,l)) return NULL;
        UNLESS(-1 != PyList_SetSlice(self->data,l,l+1,emptyList)) goto err;
        return r;
    err:
        Py_DECREF(r);
        return NULL;
    }
    
    static PyObject *
    MM__init__(self, args)
           MMobject *self;
           PyObject *args;
    {
        UNLESS(PyArg_ParseTuple(args, "")) return NULL;
        UNLESS(self->data=PyList_New(0)) goto err;
        Py_INCREF(Py_None);
        return Py_None;
    err:
        Py_DECREF(self);
        return NULL;
    }
    
    static struct PyMethodDef MM_methods[] = {
        {"__init__", (PyCFunction)MM__init__, 1,
         "__init__() -- Create a new empty multi-mapping"},
        {"push", (PyCFunction) MM_push, 1,
         "push(mapping_object) -- Add a data source"},
        {"pop",  (PyCFunction) MM_pop,  1,
         "pop() -- Remove and return the last data source added"}, 
        {NULL,              NULL}           /* sentinel */
    };
    
    static void
    MM_dealloc(self)
           MMobject *self;
    {
        Py_XDECREF(self->data);
        PyMem_DEL(self);
    }
    
    static PyObject *
    MM_getattr(self, name)
              MMobject *self;
              char *name;
    {
        return Py_FindMethod(MM_methods, (PyObject *)self, name);
    }
    
    static int
    MM_length(self)
              MMobject *self;
    {
        long l=0, el, i;
        PyObject *e=0;
    
        UNLESS(-1 != (i=PyList_Size(self->data))) return -1;
        while(--i >= 0)
          {
            e=PyList_GetItem(self->data,i);
            UNLESS(-1 != (el=PyObject_Length(e))) return -1;
            l+=el;
          }
        return l;
    }
    
    static PyObject *
    MM_subscript(self, key)
              MMobject *self;
              PyObject *key;
    {
        long i;
        PyObject *e;
    
        UNLESS(-1 != (i=PyList_Size(self->data))) return NULL;
        while(--i >= 0)
          {
            e=PyList_GetItem(self->data,i);
            if(e=PyObject_GetItem(e,key)) return e;
            PyErr_Clear();
          }
        PyErr_SetObject(PyExc_KeyError,key);
        return NULL;
    }
    
    static PyMappingMethods MM_as_mapping = {
              (inquiry)MM_length,           /*mp_length*/
              (binaryfunc)MM_subscript,             /*mp_subscript*/
              (objobjargproc)NULL,          /*mp_ass_subscript*/
    };
    
    /* -------------------------------------------------------- */
    
    static char MMtype__doc__[] = 
    "MultiMapping -- Combine multiple mapping objects for lookup"
    ;
    
    static PyExtensionClass MMtype = {
              PyObject_HEAD_INIT(&PyType_Type)
              0,                            /*ob_size*/
              "MultMapping",                        /*tp_name*/
              sizeof(MMobject),             /*tp_basicsize*/
              0,                            /*tp_itemsize*/
              /* methods */
              (destructor)MM_dealloc,               /*tp_dealloc*/
              (printfunc)0,                 /*tp_print*/
              (getattrfunc)MM_getattr,      /*tp_getattr*/
              (setattrfunc)0,                       /*tp_setattr*/
              (cmpfunc)0,                   /*tp_compare*/
              (reprfunc)0,                  /*tp_repr*/
              0,                            /*tp_as_number*/
              0,                            /*tp_as_sequence*/
              &MM_as_mapping,                       /*tp_as_mapping*/
              (hashfunc)0,                  /*tp_hash*/
              (ternaryfunc)0,                       /*tp_call*/
              (reprfunc)0,                  /*tp_str*/
    
              /* Space for future expansion */
              0L,0L,0L,0L,
              MMtype__doc__, /* Documentation string */
              METHOD_CHAIN(MM_methods)
    };
    
    static struct PyMethodDef MultiMapping_methods[] = {
        {NULL,              NULL}           /* sentinel */
    };
    
    void
    initMultiMapping()
    {
        PyObject *m, *d;
    
        m = Py_InitModule4(
            "MultiMapping", MultiMapping_methods,
            "MultiMapping -- Wrap multiple mapping objects for lookup",
            (PyObject*)NULL,PYTHON_API_VERSION);
        d = PyModule_GetDict(m);
        PyExtensionClass_Export(d,"MultiMapping",MMtype);
    
        if (PyErr_Occurred()) 
           Py_FatalError("can't initialize module MultiMapping");
    }

  This version includes 'ExtensionClass.h'.  The two declarations of
  'MMtype' have been changed from 'PyTypeObject' to 'PyExtensionClass'.
  The 'METHOD_CHAIN' macro has been used to add methods to the end of
  the definition for 'MMtype'.  The module function, newMMobject has
  been replaced by the 'MMtype' method, 'MM__init__'.  Note that this
  method does not create or return a new object.  Finally, the lines::

    d = PyModule_GetDict(m);
    PyExtensionClass_Export(d,"MultiMapping",MMtype);

  Have been added to both initialize the extension class and to export
  it in the module dictionary.

  To use this module, compile, link, and import it as with any other
  extension module.  The following python code illustrates the
  module's use::

    from MultiMapping import MultiMapping
    m=MultiMapping()
    m.push({'spam':1, 'eggs':2})
    m.push({'spam':3, 'ham':4})

    m['spam'] # returns 3
    m['ham']  # returns 4
    m['foo']  # raises a key error

  Creating the 'MultiMapping' object took three steps, one to create
  an empty 'MultiMapping', and two to add mapping objects to it.  We
  might wish to simplify the process of creating MultiMapping
  objects by providing a constructor that takes source mapping
  objects as parameters.  We can do this by sub-classing MultiMapping
  in Python::

    from MultiMapping import MultiMapping
    class ExtendedMultiMapping(MultiMapping):
        def __init__(self,*data):
          MultiMapping.__init__(self)
          for d in data: self.push(d)

    m=ExtendedMultiMapping({'spam':1, 'eggs':2}, {'spam':3, 'ham':4})

    m['spam'] # returns 3
    m['ham']  # returns 4
    m['foo']  # raises a key error

  Note that the source file included in the ExtensionClass
  distribution has numerous enhancements beyond the version shown in
  this document.


=== Added File zopeproducts/zwiki/StructuredText/regressions/create_referencesfiles.py ===
##############################################################################
#
# Copyright (c) 2001 Zope Corporation and Contributors. All Rights Reserved.
# 
# This software is subject to the provisions of the Zope Public License,
# Version 2.0 (ZPL).  A copy of the ZPL should accompany this distribution.
# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
# FOR A PARTICULAR PURPOSE
# 
##############################################################################


import os,sys
from StructuredText.StructuredText import HTML


if len(sys.argv)>1:
    files = sys.argv[1:]
else:
    files = os.listdir('.')
    files = filter(lambda x: x.endswith('.stx'), files)


for f in files:

    data = open(f,'r').read()
    html = HTML(data)

    outfile = f.replace('.stx','.ref')
    open(outfile,'w').write(html)



=== Added File zopeproducts/zwiki/StructuredText/regressions/examples.ref ===
<html>
<head>
<title>Small Trials for Structured Text Formatting</title>
</head>
<body>
<h1>Small Trials for Structured Text Formatting</h1>
<p>  This paragraph should be preceded by a level 1 header.  It should
  not, itself, be made into a header, just a regular paragraph.</p>
<p>  Here are a few presentation styles, in a list <a href="#ref1">[1]</a>:</p>

<ul>
<li>A word: <em>emphasized</em>.</li>
<li>A word: <u>underlined</u>.</li>
<li>A word <strong>strong</strong>.</li>
<li>An inline example: <code>1+2</code>.</li>
<li>Another example with a different format:
    ``x='spam''' or ``y='spam''' or ``<dtml-var spam>'<code>.</code><p>    We can use expressions in the DTML var tag as 
    in ``<dtml-var "x+'.txt'">''</p>
</li>
<li>A mult-line example:
<pre>
     blah

     *foo bar*

     &lt;dtml-var yeha&gt;
</pre>
</li>

</ul>
<p><a name="ref1">[1]</a> (The referring text should be a paragraph, not a header, and
should contain a reference to this footnote, footnote "<a href="#ref1">[1]</a>".)<p>  Some hrefs, in a definition list:</p>
<dl>
<dt>  <u>Regular</u></dt>
<dd><a href="http://www.zope.org">http://www.zope.org/</a></dd>
<dt>  <u>W/trailing punctuation</u></dt>
<dd><a href="http://www.zope.org">http://www.zope.org/</a>.</dd>
<dt>  <u>W protocol implicit</u></dt>
<dd><a href=":locallink">locallink</a></dd>
<dt>  <u>W protocol implicit</u>, alternate</dt>
<dd>"locallink", :locallink</dd>
</dl>
<p>  |||| A Simple Two-column Table ||
  || Column A || Column B ||
  || Apples   || Oranges  ||</p>
</p>
</body>
</html>


=== Added File zopeproducts/zwiki/StructuredText/regressions/examples.stx ===
Small Trials for Structured Text Formatting

  This paragraph should be preceded by a level 1 header.  It should
  not, itself, be made into a header, just a regular paragraph.

  Here are a few presentation styles, in a list [1]:

  - A word: *emphasized*.

  - A word: _underlined_.

  - A word **strong**.
 
  - An inline example: '1+2'.

  - Another example with a different format:
    ``x='spam''' or ``y='spam''' or ``<dtml-var spam>''.'

    We can use expressions in the DTML var tag as 
    in ``<dtml-var "x+'.txt'">''

  - A mult-line example::

     blah

     *foo bar*

     <dtml-var yeha>


.. [1] (The referring text should be a paragraph, not a header, and
should contain a reference to this footnote, footnote "[1]".)

  Some hrefs, in a definition list:

  _Regular_ -- "http://www.zope.org/":http://www.zope.org

  _W/trailing punctuation_ -- "http://www.zope.org/":http://www.zope.org.

  _W protocol implicit_ -- "locallink"::locallink

  _W protocol implicit_, alternate -- "locallink", :locallink

  |||| A Simple Two-column Table ||
  || Column A || Column B ||
  || Apples   || Oranges  ||



=== Added File zopeproducts/zwiki/StructuredText/regressions/examples1.ref ===
<html>
<head>
<title>Test</title>
</head>
<body>
<h1>Test</h1>
<p>  For instance:
<pre>
    &lt;table border="0"&gt;
      &lt;tr&gt;&lt;td&gt;blabla&lt;/td&gt;&lt;/tr&gt;
    &lt;/table&gt;
</pre>
</p>
</body>
</html>


=== Added File zopeproducts/zwiki/StructuredText/regressions/examples1.stx ===
Test
 
  For instance::
    
    <table border="0">
      <tr><td>blabla</td></tr>
    </table>




=== Added File zopeproducts/zwiki/StructuredText/regressions/index.ref ===
<html>
<head>
<title>Extension Class</title>
</head>
<body>
<h1>Extension Class</h1>
<p>    <a href="COPYRIGHT.html">Copyright (C) 1996-1998, Digital Creations</a>.</p>
<p>    A lightweight mechanism has been developed for making Python
    extension types more class-like.  Classes can be developed in an
    extension language, such as C or C++, and these classes can be
    treated like other python classes:</p>

<ul>
<li>They can be sub-classed in python,</li>
<li>They provide access to method documentation strings, and</li>
<li>They can be used to directly create new instances.</li>

</ul>
<p>    Extension classes provide additional extensions to class and
    instance semantics, including:</p>

<ul>
<li>A protocol for accessing subobjects "in the context of" their
      containers.  This is used to implement custom method types
      and <a href="Acquisition.html">environmental acquisition</a>.</li>
<li>A protocol for overriding method call semantics.  This is used
      to implement "synchonized" classes and could be used to
      implement argument type checking.</li>
<li>A protocol for class initialization that supports execution of a
      special <code>__class_init__</code> method after a class has been
      initialized. </li>

</ul>
<p>    Extension classes illustrate how the Python class mechanism can be
    extended and may provide a basis for improved or specialized class
    models. </p>
<h2>  Releases</h2>
<p>    The current release is <a href="ExtensionClass-1.2.tar.gz">1.2</a>,
    To find out what's changed in this release,
    see the <a href="release.html">release notes</a>.</p>
<p>    Documentation is available <a href="ExtensionClass.html">on-line</a>.</p>
<h3>  Windows Binaries</h3>
<p>    A win32 binary release, <a href="ec12.zip">ec12.zip</a>, is available.  This
    release includes all of the ExtensionClass modules built as 
    Windows extension modules (.pyd) files.  These were built for
    Python 1.5.1 using Microsoft Visual C++ 5.0 in "Release" mode.</p>
</body>
</html>


=== Added File zopeproducts/zwiki/StructuredText/regressions/index.stx ===

Extension Class
  
    "Copyright (C) 1996-1998, Digital Creations":COPYRIGHT.html.

    A lightweight mechanism has been developed for making Python
    extension types more class-like.  Classes can be developed in an
    extension language, such as C or C++, and these classes can be
    treated like other python classes:
  
    - They can be sub-classed in python,
  
    - They provide access to method documentation strings, and
  
    - They can be used to directly create new instances.
  
    Extension classes provide additional extensions to class and
    instance semantics, including:

    - A protocol for accessing subobjects "in the context of" their
      containers.  This is used to implement custom method types
      and "environmental acquisition":Acquisition.html.

    - A protocol for overriding method call semantics.  This is used
      to implement "synchonized" classes and could be used to
      implement argument type checking.

    - A protocol for class initialization that supports execution of a
      special '__class_init__' method after a class has been
      initialized. 
  
    Extension classes illustrate how the Python class mechanism can be
    extended and may provide a basis for improved or specialized class
    models. 

  Releases

    The current release is "1.2":ExtensionClass-1.2.tar.gz,
    To find out what's changed in this release,
    see the "release notes":release.html.

    Documentation is available "on-line":ExtensionClass.html.

  Windows Binaries

    A win32 binary release, "ec12.zip":ec12.zip, is available.  This
    release includes all of the ExtensionClass modules built as 
    Windows extension modules (.pyd) files.  These were built for
    Python 1.5.1 using Microsoft Visual C++ 5.0 in "Release" mode.

    



=== Added File zopeproducts/zwiki/StructuredText/regressions/table.ref ===
<html>
<body>
<table border="1" cellpadding="2">
<tr>
<th colspan="1" align="left" valign="middle"><p> Function  </p>
</th>
<th colspan="1" align="left" valign="middle"><p>  Documentation                       </p>
</th>
</tr>
<tr>
<td colspan="1" align="left" valign="top"><p> <code>__str__</code> </p>
</td>
<td colspan="1" align="left" valign="middle"><p>  This method converts the            
   the object to a string.            </p>

<ul>
<li>Blah                              </li>
<li>Blaf                              <table border="1" cellpadding="2">
<tr>
<th colspan="1" align="center" valign="top"><p>  Name   </p>
</th>
<th colspan="1" align="left" valign="middle"><p>  Favorite       
  Color          </p>
</th>
</tr>
<tr>
<td colspan="1" align="left" valign="middle"><p> Jim     </p>
</td>
<td colspan="1" align="center" valign="middle"><p>   Red           </p>
</td>
</tr>
<tr>
<td colspan="1" align="left" valign="middle"><p> John    </p>
</td>
<td colspan="1" align="center" valign="middle"><p>   Blue          </p>
</td>
</tr>
</table>
</li>

</ul>
</td>
</tr>
</table>
<table border="1" cellpadding="2">
<tr>
<td colspan="3" align="left" valign="middle"><p> This should give a row with colspan 3 </p>
</td>
</tr>
<tr>
<td colspan="1" align="left" valign="middle"><p> Col 1  </p>
</td>
<td colspan="1" align="center" valign="middle"><p>       Col 2  </p>
</td>
<td colspan="1" align="center" valign="middle"><p>        Col 3    </p>
</td>
</tr>
<tr>
<td colspan="1" align="left" valign="middle"><p> Col 1  </p>
</td>
<td colspan="2" align="center" valign="middle"><p>       Col 2                   </p>
</td>
</tr>
<tr>
<td colspan="2" align="left" valign="middle"><p> Col 1                </p>
</td>
<td colspan="1" align="center" valign="middle"><p>        Col 2    </p>
</td>
</tr>
</table>
</body>
</html>


=== Added File zopeproducts/zwiki/StructuredText/regressions/table.stx ===
|-------------------------------------------------|
| Function  | Documentation                       |
|=================================================|
| '__str__' | This method converts the            |
|           |  the object to a string.            |
|           |                                     |
|           | - Blah                              |
|           |                                     |
|           | - Blaf                              |
|           |                                     |
|           |       |--------------------------|  |
|           |       |  Name   | Favorite       |  |
|           |       |         | Color          |  |
|           |       |==========================|  |
|           |       | Jim     |  Red           |  |
|           |       |--------------------------|  |
|           |       | John    |  Blue          |  |
|           |       |--------------------------|  |
|-------------------------------------------------|



|---------------------------------------|
| This should give a row with colspan 3 |
|---------------------------------------|
| Col 1  |      Col 2  |       Col 3    |
|---------------------------------------|
| Col 1  |      Col 2                   |
|---------------------------------------|
| Col 1                |       Col 2    |
|---------------------------------------|