| /* -*- C++ -*- */ |
| /* |
| * Copyright 2003-2004 The Apache Software Foundation. |
| // (c) Copyright IBM Corp. 2004, 2005 All Rights Reserved |
| * |
| * 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. |
| * |
| * |
| * |
| * @author Susantha Kumara (skumara@virtusa.com) |
| * |
| */ |
| |
| // !!! This include file must be first thing in file !!! |
| #include "../platforms/PlatformAutoSense.hpp" |
| |
| #include "axis/Axis.hpp" |
| |
| #include "Param.h" |
| #include "ArrayBean.h" |
| #include "BasicTypeSerializer.h" |
| #include "../engine/AxisEngine.h" |
| |
| #include "AxisTrace.h" |
| |
| AXIS_CPP_NAMESPACE_START |
| |
| ArrayBean:: |
| ArrayBean() |
| { |
| logEntryEngine("ArrayBean::ArrayBean") |
| |
| m_type = XSD_UNKNOWN; |
| m_ItemName = ""; |
| m_value.sta = NULL; |
| |
| logExit() |
| } |
| |
| ArrayBean:: |
| ~ArrayBean() |
| { |
| logEntryEngine("ArrayBean::~ArrayBean") |
| |
| if (USER_TYPE == m_type) |
| { |
| if (m_value.cta) |
| { |
| if (m_value.cta->pObject) |
| { |
| if (AxisEngine::m_bServer) |
| { |
| logDebugArg2("Calling object delete function %p for object %p", m_value.cta->pDelFunct, m_value.cta->pObject) |
| |
| m_value.cta->pDelFunct(m_value.cta->pObject, m_nSize); |
| |
| logDebugArg1("Returned from object delete function %p", m_value.cta->pDelFunct) |
| } |
| // make sure that the ComplexObjectHandler's destructor does |
| // not try to delete the objects again |
| m_value.cta->pObject = NULL; |
| } |
| delete m_value.cta; |
| } |
| } |
| else if (AxisEngine::m_bServer && m_value.sta) |
| { |
| // TODO - Why do we only do this for server? I think we need to do for client also. |
| if (m_nSize > 0) |
| { |
| for (int count = 0 ; count < m_nSize ; count++) |
| if (((void **) m_value.sta)[count] != NULL) |
| Axis::AxisDelete(((void **) m_value.sta)[count], m_type); |
| } |
| delete [] m_value.sta; |
| } |
| |
| logExit() |
| } |
| |
| int ArrayBean:: |
| GetArraySize() |
| { |
| return m_nSize; |
| } |
| |
| int ArrayBean:: |
| Serialize(SoapSerializer& pSZ) |
| { |
| logEntryEngine("ArrayBean::Serialize") |
| |
| if (USER_TYPE == m_type) |
| { |
| void* pItem; |
| AXIS_BINDING_STYLE nStyle = pSZ.getStyle(); |
| |
| void** ptrval = (void**) m_value.cta->pObject; |
| if (DOC_LITERAL == nStyle) |
| { |
| // Serialize functions for doc/lit services do not know the instance |
| // name and will not serialize outer element for the type |
| |
| for (int x=0; x<m_nSize; x++) |
| { |
| pItem = ptrval[x]; |
| |
| // try to find the prefix - array prefix overrides the |
| // serializer prefix |
| const AxisChar* pNamespace = pSZ.getNamespace(); |
| const AxisChar* pPrefix = NULL; |
| bool blnIsNewPrefix = false; |
| if (NULL != pNamespace) |
| if (strlen(pNamespace) > 0) |
| pPrefix = pSZ.getNamespacePrefix(pNamespace, blnIsNewPrefix); |
| |
| if (pPrefix != NULL) |
| { |
| pSZ.serialize("<", pPrefix, ":", m_ItemName.c_str(), NULL); |
| if (blnIsNewPrefix) |
| { |
| pSZ.serialize(" xmlns:", pPrefix, "=", PLATFORM_DOUBLE_QUOTE_S, pNamespace, PLATFORM_DOUBLE_QUOTE_S, NULL); |
| } |
| } |
| else |
| pSZ.serialize("<", m_ItemName.c_str(), NULL); |
| |
| // note : ">" is not serialized to enable the type's serializer |
| // to add attributes |
| |
| logDebugArg2("Calling object serializer function %p for object %p", m_value.cta->pSZFunct, pItem) |
| |
| int stat = AXIS_FAIL; |
| stat = m_value.cta->pSZFunct(pItem, &pSZ, true); |
| |
| logDebugArg2("Returned from calling object serializer function %p, status %d", m_value.cta->pSZFunct, stat) |
| |
| // no matter true or false is passed |
| if (pPrefix != NULL) |
| pSZ.serialize("</", pPrefix, ":", m_ItemName.c_str(), ">", NULL); |
| else |
| pSZ.serialize("</", m_ItemName.c_str(), ">", NULL); |
| |
| if (blnIsNewPrefix) |
| { |
| pSZ.removeNamespacePrefix(pNamespace); |
| } |
| } |
| } |
| else |
| { |
| // Serialize functions for RPC-encoded services will serialize |
| // outer element for the type. Also the type information is not |
| // added to the outer element as this object is part of an array |
| // (serialize function knows that when the 3rd parameter is 'true'. |
| for( int x = 0; x < m_nSize; x++) |
| { |
| pItem = ptrval[x]; |
| |
| logDebugArg2("Calling object serializer function %p for object %p", m_value.cta->pSZFunct, pItem) |
| |
| int stat = AXIS_FAIL; |
| stat = m_value.cta->pSZFunct(pItem, &pSZ, true); |
| |
| logDebugArg2("Returned from calling object serializer function %p, status %d", m_value.cta->pSZFunct, stat) |
| } |
| } |
| } |
| else |
| { |
| AXIS_BINDING_STYLE nStyle = pSZ.getStyle(); |
| |
| // this is to prevent serializing type information for basic array elements |
| |
| const AxisChar* pNamespace = pSZ.getNamespace(); |
| |
| if (RPC_ENCODED == nStyle) |
| pSZ.setStyle(RPC_LITERAL); |
| |
| void ** p = (void **) m_value.sta; |
| for (int ix = 0 ; ix < m_nSize ; ix++ ) |
| { |
| pSZ.serializeAsElement(m_ItemName.c_str(), pNamespace, p[ix], m_type); |
| } |
| |
| // restore Serializer's style after array serialization is finished |
| if (RPC_ENCODED == nStyle) |
| pSZ.setStyle(RPC_ENCODED); |
| } |
| |
| logExitWithReturnCode(AXIS_SUCCESS) |
| |
| return AXIS_SUCCESS; |
| } |
| |
| void ArrayBean:: |
| SetDimension(int nDim) |
| { |
| m_nSize = nDim; |
| } |
| |
| void ArrayBean:: |
| SetItemName(const AxisChar* sName) |
| { |
| m_ItemName = sName; |
| } |
| |
| void ArrayBean:: |
| SetTypeName(const AxisChar* sName) |
| { |
| m_TypeName = sName; |
| } |
| |
| void ArrayBean:: |
| SetUri(const AxisChar* sURI) |
| { |
| if (sURI) |
| m_URI = sURI; |
| } |
| |
| /** |
| * Used to remove the pointer to the object array. Mostly to avoid deletion |
| * by the destructor. |
| */ |
| |
| void ArrayBean:: |
| RemoveArrayPointer() |
| { |
| logEntryEngine("ArrayBean::RemoveArrayPointer") |
| |
| if (USER_TYPE == m_type) |
| { |
| if (m_value.cta) |
| m_value.cta->pObject = NULL; |
| } |
| else |
| m_value.sta = NULL; |
| |
| logExit() |
| } |
| |
| AXIS_CPP_NAMESPACE_END |