text: #*****************************************************************************
  #   Copyright 2004-2008 Steve Menard
  #
  #   Licensed under the Apache License, Version 2.0 (the "License");
  #   you may not use this file except in compliance with the License.
  #   You may obtain a copy of the License at
  #
  #	   http://www.apache.org/licenses/LICENSE-2.0
  #
  #   Unless required by applicable law or agreed to in writing, software
  #   distributed under the License is distributed on an "AS IS" BASIS,
  #   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  #   See the License for the specific language governing permissions and
  #   limitations under the License.
  #   
  #*****************************************************************************
  import _jclass, _jpype
  
  _PROPERTY_ACCESSOR_PREFIX_LEN = 3
  
  def _initialize() :
  	_jclass.registerClassCustomizer(PropertiesCustomizer())
  
  def _extract_accessor_pairs(members):
          """Extract pairs of corresponding property access methods
          (getter and setter) from a Java class's members (attributes).
  
          If a public method with a property's name exists no pair for
          that property will be extracted.
  
          Returns a dictionary with the property name as key and a tuple
          of (getter method, setter method) as value. A tuple element
          value might be `None` if only a getter or only a setter
          exists.
          """
          accessor_pairs = {}
  
          for name, member in members.items():
                  if not (len(name) > _PROPERTY_ACCESSOR_PREFIX_LEN \
                                  and _is_java_method(member)):
                          continue
                  access, rest = ( name[:_PROPERTY_ACCESSOR_PREFIX_LEN],
                                   name[_PROPERTY_ACCESSOR_PREFIX_LEN:] )
                  property_name = rest[:1].lower() + rest[1:]
                  if property_name in members:
                          if _is_java_method(members[property_name]):
                                  continue
                  if access == 'get' and member.isBeanAccessor():
                          try:
                                  pair = accessor_pairs[property_name]
                                  pair[0] = member
                          except KeyError:
                                  accessor_pairs[property_name] = [member, None]
                  elif access == 'set' and member.isBeanMutator():
                          try:
                                  pair = accessor_pairs[property_name]
                                  pair[1] = member
                          except KeyError:
                                  accessor_pairs[property_name] = [None, member]
          return accessor_pairs
  
  def _is_java_method(attribute):
          return isinstance(attribute, _jpype._JavaMethod)
  
  class PropertiesCustomizer(object) :
  	def canCustomize(self, name, jc) :
  		return True
  		
  	def customize(self, class_name, jc, bases, members) :
  		accessor_pairs = _extract_accessor_pairs(members)
  		for attr_name, (getter, setter) in accessor_pairs.items():
                          if attr_name in members:
                                  if not getter:
                                          # add default getter if we
                                          # only have a setter
                                          getter = members[attr_name].fget
                                  elif not setter:
                                          # add default setter if we
                                          # only have a getter
                                          setter = members[attr_name].fset
                          members[attr_name] = property(getter, setter)
  