kitchensync

xmldiffalgo.cpp
1/*
2 This file is part of KitchenSync.
3
4 Copyright (c) 2006 Daniel Gollub <dgollub@suse.de>
5
6 This program is free software; you can redistribute it and/or
7 modify it under the terms of the GNU Library General Public
8 License as published by the Free Software Foundation; either
9 version 2 of the License, or (at your option) any later version.
10
11 This library is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 Library General Public License for more details.
15
16 You should have received a copy of the GNU Library General Public License
17 along with this library; see the file COPYING.LIB. If not, write to
18 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
19 Boston, MA 02110-1301, USA.
20*/
21
22#include "xmldiffalgo.h"
23
24#include <kdebug.h>
25
26using namespace KSync;
27
28#ifndef KDE_USE_FINAL
29// With --enable-final, we get the (identical) compareString from
30// addresseediffalgo.cpp
31//
32static bool compareString( const TQString &left, const TQString &right )
33{
34 if ( left.isEmpty() && right.isEmpty() )
35 return true;
36 else
37 return left == right;
38}
39#endif
40
41XmlDiffAlgo::XmlDiffAlgo( const TQString &leftXml, const TQString &rightXml )
42{
43 kdDebug() << __func__ << " " << __LINE__ << endl;
44
45 mLeftXml.setContent( leftXml );
46 mRightXml.setContent( rightXml );
47
48}
49
50XmlDiffAlgo::XmlDiffAlgo( const TQDomDocument &leftXml, const TQDomDocument &rightXml )
51 : mLeftXml( leftXml ), mRightXml( rightXml )
52{
53 kdDebug() << __func__ << " " << __LINE__ << endl;
54}
55
56void XmlDiffAlgo::appendSingleNodes(TQDomElement &element, bool isLeft)
57{
58 TQDomNode node;
59
60 for ( node = element.firstChild(); !node.isNull(); node = node.nextSibling() ) {
61 TQDomElement child = node.toElement();
62
63 if (isLeft)
64 additionalLeftField( node.nodeName(), child.text() );
65 else
66 additionalRightField( node.nodeName(), child.text() );
67 }
68
69}
70
71void XmlDiffAlgo::appendConflictNodes(TQDomElement &leftElement, TQDomElement &rightElement)
72{
73 TQDomNode left, right;
74 TQDomElement leftChild, rightChild;
75
76 for ( left = leftElement.firstChild(); !left.isNull(); left = left.nextSibling() ) {
77 leftChild = left.toElement();
78
79 for ( right = rightElement.firstChild(); !right.isNull(); right = right.nextSibling() ) {
80 rightChild = right.toElement();
81
82 if ( leftChild.tagName() != rightChild.tagName() )
83 continue;
84
85 if (leftChild.text().isEmpty() || rightChild.text().isEmpty())
86 continue;
87
88 TQString id = leftChild.tagName();
89 if (id == "Content")
90 id = left.parentNode().nodeName();
91
92 conflictField( id, leftChild.text(), rightChild.text() );
93
94 left.parentNode().removeChild( left );
95 left = leftElement.firstChild();
96
97 right.parentNode().removeChild( right );
98 right = rightElement.firstChild();
99
100 }
101 }
102}
103
104void XmlDiffAlgo::compareNode(TQDomElement &leftElement, TQDomElement &rightElement)
105{
106 TQDomNode left, right;
107 TQDomElement leftChild, rightChild;
108 TQDomNodeList nlist;
109top:;
110
111 for ( left = leftElement.firstChild(); !left.isNull(); left = left.nextSibling() ) {
112 leftChild = left.toElement();
113
114 for ( right = rightElement.firstChild(); !right.isNull(); right = right.nextSibling() ) {
115 rightChild = right.toElement();
116
117 if (leftChild.tagName() != rightChild.tagName())
118 continue;
119
120 if ( left.childNodes().count() > 1 && right.childNodes().count() > 1 ) {
121 compareNode( leftChild, rightChild );
122
123 if ( !left.hasChildNodes() && !right.hasChildNodes() ) {
124 left.parentNode().removeChild( left );
125 right.parentNode().removeChild( right );
126 goto top;
127 }
128
129 break;
130 }
131
132 if ( leftChild.text() == rightChild.text() ) {
133 TQString id = leftChild.tagName();
134
135 if ( id == "Content" )
136 id = left.parentNode().nodeName();
137
138 if ( id != "Type" )
139 //matchingField( id, leftChild.text(), rightChild.text() );
140
141 left.parentNode().removeChild( left );
142 right.parentNode().removeChild( right );
143 goto top;
144 }
145 }
146 }
147
148 appendConflictNodes(rightElement, leftElement);
149
150 appendSingleNodes(rightElement, false);
151 appendSingleNodes(leftElement, true);
152}
153
154void XmlDiffAlgo::run()
155{
156 kdDebug() << __func__ << endl;
157 begin();
158
159 TQDomElement leftElement = mLeftXml.documentElement();
160 TQDomElement rightElement = mRightXml.documentElement();
161
162 compareNode( leftElement, rightElement );
163
164 end();
165}
166