Package org.apache.ws.resource.properties.impl

Source Code of org.apache.ws.resource.properties.impl.AbstractSetResourcePropertiesPortType

/*=============================================================================*
*  Copyright 2004 The Apache Software Foundation
*
*  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.
*=============================================================================*/
package org.apache.ws.resource.properties.impl;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.ws.resource.ResourceContext;
import org.apache.ws.resource.i18n.Keys;
import org.apache.ws.resource.i18n.MessagesImpl;
import org.apache.ws.resource.properties.MetaDataViolationException;
import org.apache.ws.resource.properties.ResourceProperty;
import org.apache.ws.resource.properties.ResourcePropertyCallback;
import org.apache.ws.resource.properties.ResourcePropertyMetaData;
import org.apache.ws.resource.properties.ResourcePropertyValueChangeListener;
import org.apache.ws.resource.properties.SetResourcePropertyCallback;
import org.apache.ws.resource.properties.faults.DeleteResourcePropertyRequestFailedFaultException;
import org.apache.ws.resource.properties.faults.InvalidInsertResourcePropertiesRequestContentFaultException;
import org.apache.ws.resource.properties.faults.InvalidResourcePropertyQNameFaultException;
import org.apache.ws.resource.properties.faults.InvalidSetResourcePropertiesRequestContentFaultException;
import org.apache.ws.resource.properties.faults.InvalidUpdateResourcePropertiesRequestContentFaultException;
import org.apache.ws.resource.properties.faults.SetResourcePropertyRequestFailedFaultException;
import org.apache.ws.resource.properties.faults.UnableToModifyResourcePropertyFaultException;
import org.apache.ws.util.XmlBeanUtils;
import org.apache.ws.util.i18n.Messages;
import org.apache.xmlbeans.XmlObject;
import javax.xml.namespace.QName;
import java.util.Iterator;

/**
* A version-neutral base class that is extended by all impls of SetRP, InsertRPs, DeleteRPs, and UpdateRPs portTypes.
*
* @author Ian Springer
*/
public abstract class AbstractSetResourcePropertiesPortType
   extends AbstractResourcePropertiesPortType
{
   private static final Log      LOG = LogFactory.getLog( AbstractSetResourcePropertiesPortType.class );
   private static final Messages MSG = MessagesImpl.getInstance(  );

   /**
    * Creates a new {@link AbstractSetResourcePropertiesPortType} object.
    *
    * @param resourceContext DOCUMENT_ME
    */
   protected AbstractSetResourcePropertiesPortType( ResourceContext resourceContext )
   {
      super( resourceContext );
   }

   /**
    * DOCUMENT_ME
    *
    * @param oldValue DOCUMENT_ME
    * @param newValue DOCUMENT_ME
    *
    * @return DOCUMENT_ME
    */
   protected abstract AbstractXmlBeansResourcePropertyValueChangeEvent getResourcePropertyValueChangeEvent( Object[] oldValue,
                                                                                                            Object[] newValue );

   /**
    * DOCUMENT_ME
    *
    * @param nameOfPropToBeDeleted name of property to be deleted
    */
   protected void deleteResourceProperty( QName nameOfPropToBeDeleted )
   {
      if ( LOG.isDebugEnabled(  ) )
      {
         LOG.debug( MSG.getMessage( Keys.DEL_RP_REQ, nameOfPropToBeDeleted ) );
      }

      if ( nameOfPropToBeDeleted == null )
      {
         throw new DeleteResourcePropertyRequestFailedFaultException( getResource(  ).getNamespaceSet(  ),
                                                                      MSG.getMessage( Keys.DEL_MISSING_RP_ATTRIB ) );
      }

      ResourceProperty prop = getProperties(  ).get( nameOfPropToBeDeleted );
      if ( prop == null )
      {
         if ( getProperties(  ).getMetaData(  ).isOpenContent(  ) )
         {
            return;
         }
         else
         {
            throw new InvalidResourcePropertyQNameFaultException( getResource(  ).getNamespaceSet(  ),
                                                                  nameOfPropToBeDeleted );
         }
      }

      throwFaultIfPropertyIsReadOnly( prop );
      throwFaultIfDeletionViolatesSchema( prop );
      try
      {
         deletePropertyCallback( prop );
      }
      catch ( RuntimeException re )
      {
         throw new DeleteResourcePropertyRequestFailedFaultException( getResource(  ).getNamespaceSet(  ),
                                                                      re.toString(  ) );
      }

      Object[] oldValue = getValue( prop );
      prop.clear(  );
      Object[] newValue = null;
      firePropChangeEvents( prop, oldValue, newValue );
   }

   /**
    * DOCUMENT_ME
    *
    * @param propElemsToBeInserted DOCUMENT_ME
    */
   protected void insertResourceProperty( XmlObject[] propElemsToBeInserted )
   {
      if ( LOG.isDebugEnabled(  ) )
      {
         LOG.debug( MSG.getMessage( Keys.INSERT_RP_REQ ) );
      }

      if ( propElemsToBeInserted.length == 0 )
      {
         return; // nothing to do
      }

      if ( elementNamesNotHomogenous( propElemsToBeInserted ) )
      {
         throw new InvalidInsertResourcePropertiesRequestContentFaultException( getResource(  ).getNamespaceSet(  ),
                                                                                MSG.getMessage( Keys.ERROR_INSERT_ELEMS_NOT_HOMOGENOUS ) );
      }

      QName            propName = XmlBeanUtils.getName( propElemsToBeInserted[0] );
      ResourceProperty prop = getProperty( propName );

      if ( prop == null )
      {
         prop = createAnyProperty( propName );
         getProperties(  ).add( prop );
      }

      if ( !prop.getMetaData(  ).isAny(  ) )
      {
         throwFaultIfInsertionViolatesSchema( prop, propElemsToBeInserted );
      }

      throwFaultIfPropertyIsReadOnly( prop );

      try
      {
         insertPropertyCallback( prop, propElemsToBeInserted );
      }
      catch ( RuntimeException re )
      {
         throw new SetResourcePropertyRequestFailedFaultException( getResource(  ).getNamespaceSet(  ),
                                                                   re.toString(  ) );
      }

      Object[] oldValue = getValue( prop );
      for ( int i = 0; i < propElemsToBeInserted.length; i++ )
      {
         try
         {
            prop.add( propElemsToBeInserted[i] );
         }
         catch ( MetaDataViolationException mdve )
         {
            throw new InvalidSetResourcePropertiesRequestContentFaultException( getResource(  ).getNamespaceSet(  ),
                                                                                mdve );
         }
      }

      Object[] newValue = getValue( prop );
      firePropChangeEvents( prop, oldValue, newValue );
   }

   /**
    * DOCUMENT_ME
    *
    * @param newPropElems DOCUMENT_ME
    */
   protected void updateResourceProperty( XmlObject[] newPropElems )
   {
      if ( LOG.isDebugEnabled(  ) )
      {
         LOG.debug( MSG.getMessage( Keys.UPDATE_RP_REQ ) );
      }

      if ( newPropElems.length == 0 )
      {
         return; // nothing to do
      }

      QName            propName = XmlBeanUtils.getName( newPropElems[0] );
      ResourceProperty prop = getProperty( propName );

      throwFaultIfPropertyIsReadOnly( prop );
      if ( elementNamesNotHomogenous( newPropElems ) )
      {
         throw new InvalidUpdateResourcePropertiesRequestContentFaultException( getResource(  ).getNamespaceSet(  ),
                                                                                MSG.getMessage( Keys.ERROR_UPDATE_ELEMS_NOT_HOMOGENOUS ) );
      }

      throwFaultIfUpdateViolatesSchema( prop, newPropElems );

      try
      {
         updatePropertyCallback( prop, newPropElems );
      }
      catch ( RuntimeException re )
      {
         throw new SetResourcePropertyRequestFailedFaultException( getResource(  ).getNamespaceSet(  ),
                                                                   re.toString(  ) );
      }

      Object[] oldValue = getValue( prop );

      try
      {
         prop.clear(  );
         for ( int i = 0; i < newPropElems.length; i++ )
         {
            prop.add( newPropElems[i] );
         }
      }
      catch ( MetaDataViolationException mdve )
      {
         throw new InvalidSetResourcePropertiesRequestContentFaultException( getResource(  ).getNamespaceSet(  ),
                                                                             mdve );
      }

      Object[] newValue = getValue( prop );
      firePropChangeEvents( prop, oldValue, newValue );
   }

   private ResourceProperty getProperty( QName propName )
   {
      LOG.debug( MSG.getMessage( Keys.GET_RP_WITH_NAME,
                                 propName.toString(  ) ) );
      ResourceProperty prop = getProperties(  ).get( propName );
      if ( prop == null )
      {
         if ( !getProperties(  ).getMetaData(  ).isOpenContent(  ) )
         {
            throw new InvalidResourcePropertyQNameFaultException( getResource(  ).getNamespaceSet(  ), propName );
         }
      }

      return prop;
   }

   /**
    * Returns SetResourcePropertyCallback or null
    *
    * @param prop
    *
    * @return SetResourcePropertyCallback or null
    */
   private SetResourcePropertyCallback getSetResourcePropertyCallback( ResourceProperty prop )
   {
      SetResourcePropertyCallback setResourcePropertyCallback = null;
      ResourcePropertyCallback    callBack = prop.getCallBack(  );
      if ( callBack instanceof SetResourcePropertyCallback )
      {
         setResourcePropertyCallback = (SetResourcePropertyCallback) callBack;
      }

      return setResourcePropertyCallback;
   }

   private Object[] getValue( ResourceProperty prop )
   {
      Object[] value        = new Object[prop.size(  )];
      Iterator propElemIter = prop.iterator(  );
      int      i            = 0;
      while ( propElemIter.hasNext(  ) )
      {
         value[i++] = XmlBeanUtils.copyXmlBean( (XmlObject) propElemIter.next(  ) );
      }

      return value;
   }

   private ResourceProperty createAnyProperty( QName propName )
   {
      ResourcePropertyMetaData propMetaData = new AnyResourcePropertyMetaData( propName );
      return propMetaData.create( getProperties(  ) );
   }

   private void deletePropertyCallback( ResourceProperty prop )
   {
      QName                       nameOfPropToBeDeleted       = prop.getMetaData(  ).getName(  );
      SetResourcePropertyCallback setResourcePropertyCallback = getSetResourcePropertyCallback( prop );
      if ( setResourcePropertyCallback != null )
      {
         try
         {
            setResourcePropertyCallback.deleteProperty( nameOfPropToBeDeleted );
         }
         catch ( Exception e )
         {
            LOG.debug( MSG.getMessage( Keys.ERROR_DURING_DELETE_CALLBACK, setResourcePropertyCallback ),
                       e );
            throw new SetResourcePropertyRequestFailedFaultException( getResource(  ).getNamespaceSet(  ),
                                                                      MSG.getMessage( Keys.ERROR_DURING_DELETE ) );
         }
      }
   }

   private boolean elementNamesNotHomogenous( XmlObject[] propElems )
   {
      QName firstPropElemName = XmlBeanUtils.getName( propElems[0] );
      for ( int i = 1; i < propElems.length; i++ )
      {
         QName propElemName = XmlBeanUtils.getName( propElems[i] );
         if ( !firstPropElemName.equals( propElemName ) )
         {
            return true;
         }
      }

      return false;
   }

   private void firePropChangeEvents( ResourceProperty prop,
                                      Object[]         oldValue,
                                      Object[]         newValue )
   {
      for ( int i = 0; i < prop.getChangeListeners(  ).length; i++ )
      {
         ResourcePropertyValueChangeListener listener = prop.getChangeListeners(  )[i];
         listener.propertyChanged( getResourcePropertyValueChangeEvent( oldValue, newValue ) );
      }
   }

   private void insertPropertyCallback( ResourceProperty prop,
                                        XmlObject[]      propElemsToBeInserted )
   {
      SetResourcePropertyCallback setResourcePropertyCallback = getSetResourcePropertyCallback( prop );
      if ( setResourcePropertyCallback != null )
      {
         try
         {
            setResourcePropertyCallback.insertProperty( propElemsToBeInserted );
         }
         catch ( Exception e )
         {
            LOG.debug( MSG.getMessage( Keys.ERROR_DURING_INSERT_CALLBACK, setResourcePropertyCallback ),
                       e );
            throw new SetResourcePropertyRequestFailedFaultException( getResource(  ).getNamespaceSet(  ),
                                                                      MSG.getMessage( Keys.ERROR_DURING_INSERT ) );
         }
      }
   }

   private void throwFaultIfDeletionViolatesSchema( ResourceProperty prop )
   {
      if ( prop.getMetaData(  ).getMinOccurs(  ) != 0 )
      {
         throw new InvalidSetResourcePropertiesRequestContentFaultException( getResource(  ).getNamespaceSet(  ),
                                                                             MSG.getMessage(
                                                                                             Keys.ERROR_PROPERTY_DELETE_VIOLATES_SCHEMA,
                                                                                             prop.getMetaData(  )
                                                                                                 .getName(  ) ) );
      }
   }

   private void throwFaultIfInsertionViolatesSchema( ResourceProperty prop,
                                                     XmlObject[]      propElemsToBeInserted )
   {
      // TODO (low-priority): if prop is an xsd:any, a more complex algorithm needs to be used to check for minOccurs/maxOccurs violations
      if ( ( prop.getMetaData(  ).getMaxOccurs(  ) != -1 )
           && ( ( prop.size(  ) + propElemsToBeInserted.length ) > prop.getMetaData(  ).getMaxOccurs(  ) ) )
      {
         throw new InvalidInsertResourcePropertiesRequestContentFaultException( getResource(  ).getNamespaceSet(  ),
                                                                                MSG.getMessage(
                                                                                                Keys.ERROR_PROPERTY_INSERT_VIOLATES_SCHEMA,
                                                                                                ( ( propElemsToBeInserted.length > 1 )
                                                                                                  ? "s" : "" ),
                                                                                                prop.getMetaData(  )
                                                                                                    .getName(  ) ) );
      }
   }

   private void throwFaultIfPropertyIsReadOnly( ResourceProperty prop )
   {
      if ( prop.getMetaData(  ).isReadOnly(  ) )
      {
         throw new UnableToModifyResourcePropertyFaultException( getResource(  ).getNamespaceSet(  ),
                                                                 prop.getMetaData(  ).getName(  ) );
      }
   }

   private void throwFaultIfUpdateViolatesSchema( ResourceProperty prop,
                                                  XmlObject[]      newPropElems )
   {
      // TODO (low-priority): if prop is an xsd:any, a more complex algorithm needs to be used to check for minOccurs/maxOccurs violations
      if ( ( prop.getMetaData(  ).getMaxOccurs(  ) != -1 )
           && ( newPropElems.length > prop.getMetaData(  ).getMaxOccurs(  ) ) )
      {
         throw new InvalidUpdateResourcePropertiesRequestContentFaultException( getResource(  ).getNamespaceSet(  ),
                                                                                MSG.getMessage(
                                                                                                Keys.ERROR_PROPERTY_UPDATE_VIOLATES_SCHEMA,
                                                                                                prop.getMetaData(  )
                                                                                                    .getName(  ) ) );
      }
   }

   private void updatePropertyCallback( ResourceProperty prop,
                                        XmlObject[]      newPropElems )
   {
      SetResourcePropertyCallback setResourcePropertyCallback = getSetResourcePropertyCallback( prop );
      if ( setResourcePropertyCallback != null )
      {
         try
         {
            setResourcePropertyCallback.updateProperty( newPropElems );
         }
         catch ( Exception e )
         {
            LOG.debug( MSG.getMessage( Keys.ERROR_DURING_UPDATE_CALLBACK, setResourcePropertyCallback ),
                       e );
            throw new SetResourcePropertyRequestFailedFaultException( getResource(  ).getNamespaceSet(  ),
                                                                      MSG.getMessage( Keys.ERROR_DURING_UPDATE ) );
         }
      }
   }
}
TOP

Related Classes of org.apache.ws.resource.properties.impl.AbstractSetResourcePropertiesPortType

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.