Log On
Embarcadero Home
Watch, Follow, &
Connect with Us
Share This
QualityCentral
Communities
Articles
Blogs
Resources
Downloads
Help
QualityCentral
Delphi-BCB
SOAP
Client Applications
Components
Interface
Interoperability
Server Applications
Transfers
UDDI
Wizards
WSDL Importer
WSDL Importer- BCB
WSDLImp.exe
You are not logged in.
Help
Print
Public Report
Report From:
Delphi-BCB/SOAP/Transfers
[ Add a report in this area ]
Report #:
4950
Status:
Closed
Cannot have soap enumeration types in delphi due to reserved word syntax error for enumerations.
Project:
Delphi
Build #:
4.453
Version:
7.0
Submitted By:
Mehul Harry
Report Type:
Suggestion / Enhancement Request
Date Reported:
7/2/2003 6:58:16 PM
Severity:
Infrequently encountered problem
Last Updated:
11/6/2005 3:24:49 PM
Platform:
All platforms
Internal Tracking #:
Resolution:
Fixed
(Resolution Comments)
Resolved in Build:
:
9.0.1761.24408
Duplicate of:
None
Voting and Rating
Overall Rating:
No Ratings Yet
0.00 out of 5
Total Votes:
None
Description
My problem was I have an enum type called Region that contains the various supported states for my proj:
Region = (AZ, CO, DE, FL, regIN, KY, MD, regOR, RI, TX, WV);
Indiana and Orgeon cause a syntax problem.
Steps to Reproduce:
None
Workarounds
In your ...SoapClasses.pas you can now register enum values you want the converter to change during runtime:
RemClassRegistry.RegisterExternalPropName(TypeInfo(Region), 'regOR', 'OR');
RemClassRegistry.RegisterExternalPropName(TypeInfo(Region), 'regIN', 'IN');
So, the following changes were implemented that would allow changing enumerated values (many thanks to Atanas S. for the changes).
I am including the whole method but the changed are commented as:
//ATS - new code added
//end new code added
//All credit must go to Atanas Stoyanov for the changes to the unit.
//OPToSOAPDomConv.pas
function TSOAPDomConv.ObjInstanceToSOAP(Instance: TObject; RootNode, ParentNode: IXMLNode;
const NodeName, NodeNamespace: InvString; ObjConvOpts: TObjectConvertOptions;
out RefID: InvString): IXMLNode;
var
ID, Pre: InvString;
I, Count: Integer;
PropList: PPropList;
Kind: TTypeKind;
V: Variant;
Obj: TObject;
ElemURI, TypeName, TypeNamespace, NodeVal: InvString;
PrefixNode, InstNode, ElemNode, AttrNode: IXMLNode;
P: Pointer;
ExtPropName: InvString;
MultiRef, UsePrefix, SerializeProps, CanHaveType, HolderClass, LitParam : Boolean;
SerialOpts: TSerializationOptions;
ClsType: TClass;
begin
{ Get a new ID for this node - in case we're MultiRefing... }
RefID := GetNewID;
{ Retrieve the Serializatin options of this class }
SerialOpts := SerializationOptions(Instance);
{ Type attribute }
HolderClass := (xoHolderClass in SerialOpts);
LitParam := (xoLiteralParam in SerialOpts);
{ Object Custom Serialization flags }
UsePrefix := not (ocoDontPrefixNode in ObjConvOpts);
SerializeProps := not (ocoDontSerializeProps in ObjConvOpts);
CanHaveType := not (ocoDontPutTypeAttr in ObjConvOpts) and (not LitParam);
{ Get namespace prefix }
PrefixNode := RootNode;
{ Are we multiref'in the node }
MultiRef := MultiRefObject(Instance.ClassType);
{ No prefix in document style - or if flag set to false }
if not (soDocument in Options) and UsePrefix then
Pre := FindPrefixForURI(PrefixNode, ParentNode, NodeNamespace, True)
else
Pre := '';
{ Create the Node, if necessary }
if not HolderClass then
begin
if not MultiRef then
begin
if (soDocument in Options) then
begin
RemClassRegistry.ClassToURI(Instance.ClassType, TypeNamespace, TypeName);
if TypeNamespace = XMLSchemaNamespace then
InstNode := ParentNode.AddChild(NodeName)
else
InstNode := ParentNode.AddChild(NodeName, TypeNamespace);
end
else
begin
if UsePrefix or (Pre <> '') then
InstNode := ParentNode.AddChild(MakeNodeName(Pre, NodeName))
else
{ Create a node without any prefix }
InstNode := ParentNode.AddChild(NodeName, '');
end;
end
else
InstNode := CreateMultiRefNode(RootNode, MakeNodeName(Pre, NodeName), RefID);
end
else
{ Here this class was simply a holder - only its members are serialized!
the class itself is stealth }
InstNode := ParentNode;
{ Set Result Node }
Result := InstNode;
{ Can this type generate xsi:type attributes?? }
if CanHaveType then
begin
{ Retrieve Type Namespace }
RemClassRegistry.ClassToURI(Instance.ClassType, TypeNamespace, TypeName);
{ xsi:type=?? }
SetNodeType(PrefixNode, InstNode, TypeNamespace, TypeName);
end;
{ Store info that we multi refed' }
if MultiRef then
AddMultiRefNode(RefID, Instance);
{ Serialize Published Properties ?? }
if SerializeProps then
begin
{ Serialized published properties }
Count := GetTypeData(Instance.ClassInfo)^.PropCount;
if Count > 0 then
begin
GetMem(PropList, Count * SizeOf(Pointer));
try
GetPropInfos(Instance.ClassInfo, PropList);
{ Complex type as wrapper of a simple type }
if (xoSimpleTypeWrapper in SerialOpts) and (Count = 1) then
begin
NodeVal := GetObjectPropAsText(Instance, PropList[0]);
InstNode.Text := NodeVal;
end else
begin
for I := 0 to Count - 1 do
begin
ExtPropName := RemTypeRegistry.GetExternalPropName(Instance.ClassInfo, PropList[I].Name);
Kind := (PropList[I].PropType)^.Kind;
{ Class Property }
if Kind = tkClass then
begin
Obj := GetObjectProp(Instance, PropList[I]);
if Obj = nil then
begin
if not (soDontSendEmptyNodes in Options) then
CreateNULLNode(RootNode, InstNode, ExtPropName)
end
else
begin
ClsType := GetTypeData((PropList[I].PropType)^).ClassType;
RemClassRegistry.ClassToURI(ClsType, ElemURI, TypeName);
MultiRef := MultiRefObject(ClsType);
if not MultiRef then
begin
if IsObjectWriting(Obj) then
raise ESOAPDomConvertError.CreateFmt(SNoSerializeGraphs, [Obj.ClassName]);
AddObjectAsWriting(Instance);
{ NOTE: prefix for nested types ?? }
CreateObjectNode(Obj, RootNode, InstNode, ExtPropName, ElemURI, ObjConvOpts);
RemoveObjectAsWriting(Obj);
end else
begin
ElemNode := InstNode.AddChild(ExtPropName, '');
ID := FindMultiRefNodeByInstance(Obj);
{ NOTE: prefix for nested types ?? }
if ID = '' then
ID := CreateObjectNode(Obj, RootNode, InstNode, ExtPropName, ElemURI, ObjConvOpts);
ElemNode.Attributes[SXMLHREF] := SHREFPre + ID;
end;
end;
{ Array property }
end else if Kind = tkDynArray then
begin
P := Pointer(GetOrdPropEx(Instance, PropList[I]));
ConvertNativeArrayToSoap(RootNode, InstNode, ExtPropName,
(PropList[I].PropType)^, P, 0,
(xoInlineArrays in SerialOpts));
{ Variant property }
end else if Kind = tkVariant then
begin
V := GetVariantProp(Instance, PropList[I]);
ConvertVariantToSoap(RootNode, InstNode, ExtPropName, nil, nil, 0, V, True);
end else
{ Simple type property ?? }
begin
if not RemTypeRegistry.TypeInfoToXSD((PropList[I].PropType)^, ElemURI, TypeName) then
raise ESOAPDomConvertError.CreateFmt(SRemTypeNotRegistered, [(PropList[I].PropType)^.Name]);
{ Here we check the stored property flag - that's the flag to use an
attribute instead of a separate node - if the property is marked
stored False, we'll use an attribute instead }
if not IsStoredProp(Instance, PropList[I]) then
begin
{ Typically attributes go on the root/instance node. However, in some
cases the class serializes members and then the attribute goes on
the last member; this option allows attributes on specific members }
AttrNode := InstNode;
if (xoAttributeOnLastMember in SerialOpts) then
begin
if ntElementChildCount(InstNode) > 0 then
AttrNode := ntElementChild(InstNode, ntElementChildCount(InstNode)-1);
end;
//ATS - new code added
if Kind = tkEnumeration then
begin
NodeVal := GetObjectPropAsText(Instance, PropList[I]);
NodeVal := RemTypeRegistry.GetExternalPropName(PropList[I].PropType^, NodeVal);
end
else
//end new code added
NodeVal := GetObjectPropAsText(Instance, PropList[I]);
{ Check if user does not want to send empty nodes }
if (not (soDontSendEmptyNodes in Options)) or (NodeVal <> '') then
AttrNode.Attributes[ExtPropName] := NodeVal;
end
else
begin
//ATS - new code added
if Kind = tkEnumeration then
begin
NodeVal := GetObjectPropAsText(Instance, PropList[I]);
NodeVal := RemTypeRegistry.GetExternalPropName(PropList[I].PropType^, NodeVal);
end
else
//end new code added
NodeVal := GetObjectPropAsText(Instance, PropList[I]);
{ Check if user does not want to send empty nodes }
if (not (soDontSendEmptyNodes in Options)) or (NodeVal <> '') then
ElemNode := CreateScalarNodeXS(RootNode, InstNode, ExtPropName, ElemURI, TypeName, NodeVal);
end;
end;
end;
end;
finally
FreeMem(PropList, Count * SizeOf(Pointer));
end;
end;
end;
end;
Attachment
None
Comments
None
View Your Reports
Search
Server Response from: ETNACODE01
Developer Tools
Blackfish SQL
C++Builder
Delphi
FireMonkey
Prism
InterBase
JBuilder
J Optimizer
HTML5 Builder
3rdRail & TurboRuby
Database Tools
Change Manager
DBArtisan
DB Optimizer
ER/Studio
Performance Center
Rapid SQL
Technical Articles
Tutorials
White Papers
Press Releases
Newsletters
Add Content (GetPublished)
Audio
Audio & Video
Video
Bugs & Suggestions (QualityCentral)
Discussion Forums
Examples (CodeCentral)
Tags
Technology Partners
Downloads
Free Trials
Registered User Downloads
Beta Programs
Add Content (GetPublished)
Articles
Blogs
Bugs & Suggestions (QualityCentral)
Discussion Forums
Examples (CodeCentral)
Member Services
About
Connect with Us