Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

TXML error with CDATA?

131 views
Skip to first unread message

Anatole Kolotovkin

unread,
Nov 30, 2009, 3:51:00 PM11/30/09
to
Hi,

I am trying an example DBF -> XML from xHarbour Guide
/*part of code
.....

IF aField[2] == "M"
// Memo fields are written as CDATA
cData := FieldGet( Hb_EnumIndex() )
oXmlField := TXmlNode():new( HBXML_TYPE_CDATA , ;
Lower( aField[1] ), ;
NIL , ;
cData )
*/
=== conversion result

<?xml version="1.0" encoding="windows-1251" ?>
- <database name="XMEMO">
- <structure>
<field dec="0" len="10" name="w1m" type="M" />
</structure>
- <records>
- <record id="1">
- <![CDATA[ 1 ]]>
</record>
- <record id="2">
- <![CDATA[ 2 ]]>
</record>
</records>
</database>
====

I think the result of conversion memo-field is incorrect,
result should contain the name of the field

- <record id="2">
<w1m>
- <![CDATA[ 2 ]]>
<\w1m>
</record>

--
Regards, Anatole.

Anatole Kolotovkin

unread,
Dec 1, 2009, 10:55:23 AM12/1/09
to
Somebody something can answer my question?
Thanks in advance.


Best regards, Anatole

Anatole Kolotovkin пишет:

dlzc

unread,
Dec 1, 2009, 2:29:06 PM12/1/09
to
Dear Anatole Kolotovkin:

Why do you think the field name needs to be repeated for every record,
when it is not for any other variable type?

> - <structure>
> <field dec="0" len="10" name="w1m" type="M" />
> </structure>

... I see a "w1m" clearly in what you reported as output. What do you
get for a regular character field?

David A. Smith

Robert Campsmith

unread,
Dec 1, 2009, 3:15:45 PM12/1/09
to
Anatole Kolotovkin wrote:
> Hi,
>
> I am trying an example DBF -> XML from xHarbour Guide
> /*part of code
> ......

Anatole,

You are welcome to try this function, it works for me. Use it as a
starting point for your own work.


#include "hbXml.ch"
****************************************
FUNCTION DBF2XML( cDataName, cOutName )
*
* Purpose: convert an xBase file to XML
* returns the number of records converted
*
LOCAL aStruct, aField, nFileHandle, nK := 0
LOCAL oXmlDoc, oXmlNode, hAttr, cData
LOCAL OXmlDatabase, oXmlStruct, oXmlRecord, oXmlField

USE (cDataName)
aStruct := DbStruct()

*- Create empty XML document with header
oXmlDoc := TXmlDocument():new( '<?xml version="1.0"?>' )

*- Create main XML node
oXmlDatabase := TXmlNode():new( , "database", { "name" =>
GetFileName(cDataName) } )
oXmlDoc:oRoot:addBelow( oXmlDatabase )

*- copy structure information to XML
oXmlStruct := TXmlNode():new( , "structure" )
oXmlDataBase:addBelow( oXmlStruct )

FOR EACH aField IN aStruct
*- store field information in XML attributes
hAttr := { "name" => Lower( aField[1] ), ;
"type" => aField[2], ;
"len" => LTrim( Str(aField[3]) ), ;
"dec" => LTrim( Str(aField[4]) ) }

oXmlField := TXmlNode():new(, "field", hAttr )
oXmlStruct:addBelow( oXmlField )
NEXT

*- copy all records to XML
oXmlNode := TXmlNode():new( , "records" )
oXmlDataBase:addBelow( oXmlNode )

BEGIN SEQUENCE

DO WHILE !EOF() .and. RECNO() < 101
hAttr := { "id" => LTrim( Str( Recno() ) ) }
oXmlRecord := TXmlNode():new( , "record", hAttr )

FOR EACH aField IN aStruct


IF aField[2] == "M"

*- Memo fields are written as CDATA


cData := FieldGet( Hb_EnumIndex() )
oXmlField := TXmlNode():new( HBXML_TYPE_CDATA , ;
Lower( aField[1] ), ;
NIL , ;
cData )

ELSE
*- other fields are written as normal tags


cData := FieldGet( Hb_EnumIndex() )

cData := Alltrim( CStr( cData ) )
oXmlField := TXmlNode():new( HBXML_TYPE_TAG , ;


Lower( aField[1] ), ;
NIL , ;
cData )

ENDIF
*- add field node to record
oXmlRecord:addBelow( oXmlField )
NEXT

*- add record node to records
oXmlNode:addBelow( oXmlRecord )
SKIP
ENDDO

*- create XML file
nFileHandle := FCreate( cOutName )

*- write the XML tree, this takes a long time.
oXmlDoc:write( nFileHandle, HBXML_STYLE_INDENT )

*- close files
FClose( nFileHandle )
END // SEQUENCE
CLOSE (cDataname)

RETURN( nK )
*

Good Luck,
-- Robert

Anatole Kolotovkin

unread,
Dec 1, 2009, 4:21:22 PM12/1/09
to
dlzc пишет:

Thank you for your response. Example of xHarbour Guide gives the
following result for a regular character field AND for memo field

<?xml version="1.0"?>
<database name="X2MEMO">
<structure>
<field dec="0" len="3" name="w1" type="C"/>
<field dec="0" len="3" name="w2" type="C"/>
<field dec="0" len="10" name="w2m" type="M"/>
<field dec="0" len="10" name="w3m" type="M"/>
<field dec="0" len="3" name="w3" type="N"/>
</structure>
<records>
<record id="1">
<w1>001</w1>
<w2>100</w2>
<![CDATA[001 ]]>
<![CDATA[100 ]]>
<w3>1</w3>
</record>


--
Regards, Anatole.

Anatole Kolotovkin

unread,
Dec 1, 2009, 4:50:14 PM12/1/09
to
Robert Campsmith пишет:

Thank you for your reply.
Your function gives a result similar to my

<?xml version="1.0"?>
<database name="X2MEMO">

<structure>


<field dec="0" len="3" name="w1" type="C"/>
<field dec="0" len="3" name="w2" type="C"/>
<field dec="0" len="10" name="w2m" type="M"/>
<field dec="0" len="10" name="w3m" type="M"/>
<field dec="0" len="3" name="w3" type="N"/>
</structure>
<records>
<record id="1">
<w1>001</w1>
<w2>100</w2>
<![CDATA[001 ]]>
<![CDATA[100 ]]>
<w3>1</w3>
</record>

.........


Remaining questions
1. xml2dbf How to find the field w2m or field w3m
2. from W3C Recommendation.

================================
2.7 CDATA Sections

[Definition: CDATA sections may occur anywhere character data may occur;
they are used to escape blocks of text containing characters which would
otherwise be recognized as markup. CDATA sections begin with the string
"<![CDATA[" and end with the string "]]>":]
=============================================================
IHMO, for memo-field must
<w2m>>
<![CDATA[001 ]]>
</w2m>
3. example XML from HWGUI
=======
- <method name="onFormInit">
- <![CDATA[
oForm1 := HFormTmpl():Read( "testget1.xml" )
oForm2 := HFormTmpl():Read( "testget2.xml" )
oForm3 := HFormTmpl():Read( "testdbf1.xml" )
oForm4 := HFormTmpl():Read( "test_ctrl.xml" )
oForm5 := HFormTmpl():Read( "barcode.xml" )
orep1 := hreptmpl():Read("testrep1.xml")
]]>
</method>
--
Regards, Anatole.

dos...@email.si

unread,
Dec 2, 2009, 11:16:07 AM12/2/09
to
Hi !

I suggest you reading document <xHb>/doc/hbxml.txt for begining ...
There you can see:
"
HBXML_TYPE_DATA
A pure data node. In this node-type only ::cData is valid, as all
other elements are meaningless.
"
and then you will correct code to work like you like.

Anatole Kolotovkin wrote in post <hf41cj$7ec$1...@news.eternal-september.org> ...

[...]


> >> IF aField[2] == "M"
> >> // Memo fields are written as CDATA
> >> cData := FieldGet( Hb_EnumIndex() )
> >> oXmlField := TXmlNode():new( HBXML_TYPE_CDATA , ;
> >> Lower( aField[1] ), ;
> >> NIL , ;
> >> cData )

[...]
Change to:
xData := FieldGet( Hb_EnumIndex() )
IF aField[ DBS_TYPE ] == "M"
// Memo field as CDATA
oN_field := TXmlNode():new( HBXML_TYPE_TAG, ;
Lower( aField[ DBS_NAME ] ) )
oCData := TXmlNode():new( HBXML_TYPE_CDATA, ;
,, RTrim( xData ) )
oN_field:addBelow( oCData )

ELSE
...

With best regards,
Dusan

Robert Campsmith

unread,
Dec 2, 2009, 11:50:17 AM12/2/09
to

Well, Anatole, you got me there because in my limited exposure to
XML I do not need to export or import any "Memo" fields. I do
remember though, the trouble I had when I was first trying to
teach myself about XML that the Memo fields were a problem. This
code is how I solved the problem -- temporarily, but I do not use
Memo fields in production.

-- Robert

Anatole Kolotovkin

unread,
Dec 2, 2009, 3:26:25 PM12/2/09
to
Robert Campsmith пишет:

> Well, Anatole, you got me there because in my limited exposure to XML I
> do not need to export or import any "Memo" fields. I do remember though,
> the trouble I had when I was first trying to teach myself about XML that
> the Memo fields were a problem. This code is how I solved the problem --
> temporarily, but I do not use Memo fields in production.
>
> -- Robert

I understand, thank you.
--
Regards, Anatole.

Anatole Kolotovkin

unread,
Dec 2, 2009, 4:02:25 PM12/2/09
to
dos...@email.si пишет:
Thank you for your help and the proposed solution.


--
Regards, Anatole.

Anatole Kolotovkin

unread,
Dec 2, 2009, 4:20:17 PM12/2/09
to

Thanks to everyone who tried to help understand


I now understand, TXmlNode():new( HBXML_TYPE_CDATA,"xName",NIL,cData)
gives no false positives, but only one result, which is valid in XML

IMHO, it would be good
if empty(cName)
<![CDATA ......>
else
<cName>
<![CDATA ......>
</cName>

Regards, Anatole.

0 new messages