Welcome, guest | Sign In | My Account | Store | Cart

Notice! PyPM is being replaced with the ActiveState Platform, which enhances PyPM’s build and deploy capabilities. Create your free Platform account to download ActivePython or customize Python with the packages you require and get automatic updates.

Download
ActivePython
INSTALL>
pypm install mfabrik.behaviorutilities

How to install mfabrik.behaviorutilities

  1. Download and install ActivePython
  2. Open Command Prompt
  3. Type pypm install mfabrik.behaviorutilities
 Python 2.7Python 3.2Python 3.3
Windows (32-bit)
0.1.1 Available View build log
Windows (64-bit)
0.1.1 Available View build log
Mac OS X (10.5+)
0.1.1 Available View build log
Linux (32-bit)
0.1.1 Available View build log
Linux (64-bit)
0.1.1 Available View build log
 
License
GPL
Dependencies
Depended by
Lastest release
version 0.1.1 on Jan 5th, 2011

Introduction

mfabrik.behaviorutilities is plone.behavior support and helper package for Plone 3 and Archetypes.

About Behavior pattern

Behavior pattern is a way to provide extensible behavior for content objects, without touching the actual content object class source code and so that behaviors can be turned on and off.

First read plone.behavior tutorial

Note that the tutorial does not describe how to use behavior objects with Archetypes based content and this Python module tries to fill in some gaps there.

Features

  • Create plone.behavior behaviors for Archetypes objects and make them assignable
  • On-demand behavior object creation - do not make saves or Zope transactions

System Message: WARNING/2 (<string>, line 29)

Bullet list ends without a blank line; unexpected unindent.

if behavior defaults are not changed

  • z3c.form support to make behavior objects context aware and thus selection widget vocabulary resolving working
  • Traversing tools

Sample code walkthrough

Note: Code here is only for example purposes and probably does not work as is. Proper usage documentation will be done after the framework has taken more shape. Refer to existing code users for more help.

Behavior is defined as an interface, which also defines form options which user can edit for this behavior. Schema is defined using plone.directives.form package:

System Message: WARNING/2 (<string>, line 58)

Literal block expected; none found.

class IMultiChannelBehavior(form.Schema): """ How content and its children react to differt medias """

contentMedias = schema.Choice(title=u"Content medias", description=u"Does this content appear on web, mobile or both", default=ContentMediaOption.USE_PARENT, required=True)

# More form fields here

alsoProvides(IMultiChannelBehavior, form.IFormFieldProvider)

The behavior implementation is persistent Zope object, which knowns its context i.e. object for which behavior is assigned by using mfabrik.beahviorutilities.volatilecontext.VolatileContext base class, which is a subclass of Zope Persistent class.

Implementation maps behavior interface fields itself as class attributes using FieldProperties.

We use AnnotationPersistentFactory to store behavior. This means that when behavior is once saved on your content object, you can access by directly by traversing:

System Message: WARNING/2 (<string>, line 82)

Literal block expected; none found.

context.__annotations__["your_annotation_key_name"]

Example:

System Message: WARNING/2 (<string>, line 86)

Literal block expected; none found.

class MobileBehaviorStorage(VolatileContext):

# Implement your behavior implements(IMobileBehavior)

mobileFolderListing = FieldProperty(IMobileBehavior["mobileFolderListing"])

appearInFolderListing = FieldProperty(IMobileBehavior["appearInFolderListing"])

# This defines a behavior factoty method mobile_behavior_factory = AnnotationPersistentFactory(MobileBehaviorStorage, "mobile")

Now you can create and query behaviors.

First we check that the behavior is assignable. Currently it is hardcoded that all behaviors are assignable to all Archetypes content objects:

System Message: WARNING/2 (<string>, line 104)

Literal block expected; none found.

self.loginAsPortalOwner() self.portal.invokeFactory("Document", "doc") doc = self.portal.doc

# Check assignable works from plone.behavior.interfaces import IBehaviorAssignable assignable = IBehaviorAssignable(doc, None)

self.assertTrue(assignable.supports(IMobileBehavior)) self.assertNotEqual(assignable, None)

When we query the behavior it is created on the fly if it does not already exist on the content. If the behavior is created, then its attributes are populated with the default values specific in the schema:

System Message: WARNING/2 (<string>, line 119)

Literal block expected; none found.

behavior = IMobileBehavior(doc)

Behavior knowns on which content it belongs. This is implemented as volatile reference, so no circular pointers are stored to ZODB.

doc == behavior.context

You can edit the behavior parameters by using properties defined on the storage class:

System Message: WARNING/2 (<string>, line 130)

Literal block expected; none found.

behavior.mobileFolderListing = True

If you do any changes to the behavior you need to call save() method of the VolatileContext class. This makes sure that if the behavior is not the default behavior, you need to actually save persistent parameters in the annotations:

System Message: WARNING/2 (<string>, line 137)

Literal block expected; none found.

behavior.save()

# Recreate behavior from the scratch # and see it is persistent behavior = IMobileBehavior(doc) assert behavior.behavior.mobileFolderListing == True

Each behavior also needs edit form - you can easily do this using z3c.form:

System Message: WARNING/2 (<string>, line 146)

Literal block expected; none found.

class MobileForm(z3c.form.form.EditForm): """ Folder/page specific mobile publishing options """

fields = field.Fields(IMobileBehavior)

prefix = "mobile" label = u"Mobile navigation options"

def update(self): return z3c.form.form.EditForm.update(self)

def getContent(self): """ Return the object which the form should edit. """ behavior = IMobileBehavior(self.context) return behavior

def applyChanges(self, data): # Call super content = self.getContent() val = z3c.form.form.EditForm.applyChanges(self, data)

# Write behavior to database content = self.getContent() content.save()

return val

MobileFormView = wrap_form(MobileForm)

It is easiest to link this form to your object using document_actions link. actions.xml snippet:

<?xml version="1.0"?>
<object name="portal_actions" meta_type="Plone Actions Tool"

System Message: ERROR/3 (<string>, line 182)

Inconsistent literal block quoting.

xmlns:i18n="http://xml.zope.org/namespaces/i18n">

<object name="document_actions" meta_type="CMF Action Category">

<object name="mobile_options" meta_type="CMF Action" i18n:domain="plone"> <property name="title" i18n:translate="">Mobile settings</property> <property name="description" i18n:translate="">Set mobile publishing options</property> <property name="url_expr">string:$object_url/@@mobile_options</property> <property name="icon_expr"></property> <property name="available_expr"></property> <property name="permissions"> <element value="Modify portal content"/> </property> <property name="visible">True</property> </object>

</object>

</object>

0.1 - 0.1.1

  • plone.org release
  • Updated README

0.1

  • Initial release

Subscribe to package updates

Last updated Jan 5th, 2011

Download Stats

Last month:2

What does the lock icon mean?

Builds marked with a lock icon are only available via PyPM to users with a current ActivePython Business Edition subscription.

Need custom builds or support?

ActivePython Enterprise Edition guarantees priority access to technical support, indemnification, expert consulting and quality-assured language builds.

Plan on re-distributing ActivePython?

Get re-distribution rights and eliminate legal risks with ActivePython OEM Edition.