ViewVC Help
View File | Revision Log | View Changeset | Root Listing
root/Oni2/XmlTools2/trunk/xmlpatch.cpp
(Generate patch)

Comparing XmlTools2/trunk/xmlpatch.cpp (file contents):
Revision 910 by s10k, Sat Feb 1 16:02:56 2014 UTC vs.
Revision 920 by s10k, Sun Feb 2 18:50:10 2014 UTC

# Line 43 | Line 43 | void XmlPatch::readAndProcessPatchFile()
43  
44   }
45  
46 < void XmlPatch::addToOperation(const QString &xmlString, XmlFilter &filters, const QString &filesWildcard){
46 > void XmlPatch::insertNodesOperation(const QString &xmlString, XmlFilter &filters, const QString &xPathExpression, const QString &filesWildcard){
47  
48      QStringList filesToProcess;
49 <    pugi::xml_node nodeToInsertion;
49 >    QList<pugi::xml_node> nodesToInsertion;
50      pugi::xml_document newNode;
51      pugi::xml_parse_result result;
52  
53      filesToProcess=UtilXmlTools::getAllXmlFilesByWildcard(filesWildcard);
54  
55      if(filesToProcess.isEmpty()){
56 <        UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODE","No XML files were found for the wildcard: "+filesWildcard);
56 >        UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODES","No XML files were found for the wildcard: "+filesWildcard);
57      }
58  
59      result=newNode.load(xmlString.toLatin1().constData()); // load xml to insert
60  
61      if(result.status!=pugi::status_ok){
62 <        UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODE", "The xml node to insert is invalid.\n" + Util::toQString(result.description()));
62 >        UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODES", "The xml node to insert is invalid.\n" + Util::toQString(result.description()));
63      }
64  
65      // Process all XmlFiles
66      for(int i=0; i<filesToProcess.size(); i++){
67  
68 <        UtilXmlTools::loadXmlFile(filesToProcess[i],this->document,this->rootNode,this->backupsEnabled,"@ADD_INSIDE_NODE");
68 >        UtilXmlTools::loadXmlFile(filesToProcess[i],this->document,this->rootNode,this->backupsEnabled,"@ADD_INSIDE_NODES");
69  
70 <        nodeToInsertion=UtilXmlTools::getFirstNamedElements(this->rootNode,filters);
70 >        // Check how the element will be fetched via element name or xpath expression
71 >        if(xPathExpression.isEmpty()){
72 >            UtilXmlTools::getAllNamedElements(this->rootNode,nodesToInsertion,filters);
73 >        }
74 >        else{
75 >            UtilXmlTools::getAllXpathElements(xPathExpression,this->document,nodesToInsertion);
76 >        }
77  
78 <        if(nodeToInsertion.type()==pugi::node_null){
78 >        if(nodesToInsertion[0].type()==pugi::node_null){
79  
80              QString errMessage;
81  
82 <            errMessage = "It wasn't found a node with a ElementName: '" + filters.getElementName() + "'";
83 <            if(filters.getParentElementName()!=""){
84 <                errMessage += " and a ParentElementName: '" + filters.getParentElementName() + "'";
82 >            if(xPathExpression.isEmpty()){
83 >                errMessage = "It wasn't found any node with a ElementName: '" + filters.getElementName() + "'";
84 >                if(filters.getParentElementName()!=""){
85 >                    errMessage += " and a ParentElementName: '" + filters.getParentElementName() + "'";
86 >                }
87 >                if(filters.getAttributeName()!=""){
88 >                    errMessage += " and an AttributeName: '" + filters.getAttributeName() + "' and an AttributeValue: '" + filters.getAttributeValue() + "'";
89 >                }
90              }
91 <            if(filters.getAttributeName()!=""){
92 <                errMessage += " and an AttributeName: '" + filters.getAttributeName() + "' and an AttributeValue: '" + filters.getAttributeValue() + "'";
91 >            else{
92 >                errMessage = "It wasn't found any node with a XPathExpression: '" + xPathExpression + "'";
93              }
94  
95 <            UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODE",errMessage);
95 >            UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODES",errMessage);
96          }
97  
98 <        nodeToInsertion.prepend_copy(newNode.first_child()); // append the new node
98 >        for(int j=0; j<nodesToInsertion.size(); j++){
99 >            nodesToInsertion[j].prepend_copy(newNode.first_child()); // append the new node
100 >        }
101  
102  
103 <        UtilXmlTools::saveXmlFile(filesToProcess[i],this->document, "@ADD_INSIDE_NODE");
103 >        UtilXmlTools::saveXmlFile(filesToProcess[i],this->document, "@ADD_INSIDE_NODES");
104      }
105  
106 <    UtilXmlTools::displaySuccessMessage(filesToProcess.size(),"@ADD_INSIDE_NODE");
106 >    UtilXmlTools::displaySuccessMessage(filesToProcess.size(),"@ADD_INSIDE_NODES");
107   }
108  
109 < void XmlPatch::removeNodeOperation(XmlFilter &filters, const QString &filesWildcard){
109 > void XmlPatch::removeNodesOperation(XmlFilter &filters, const QString &xPathExpression, const QString &filesWildcard){
110  
111      QStringList filesToProcess;
112  
113 <    pugi::xml_node nodeToDeletion;
113 >    QList<pugi::xml_node> nodesToDeletion;
114  
115      filesToProcess=UtilXmlTools::getAllXmlFilesByWildcard(filesWildcard);
116  
117      if(filesToProcess.isEmpty()){
118 <        UtilXmlTools::displayErrorMessage("@REMOVE_NODE","No XML files were found for the wildcard: "+filesWildcard);
118 >        UtilXmlTools::displayErrorMessage("@REMOVE_NODES","No XML files were found for the wildcard: "+filesWildcard);
119      }
120  
121      // Process all XmlFiles
122      for(int i=0; i<filesToProcess.size(); i++){
123  
124 <        UtilXmlTools::loadXmlFile(filesToProcess[i],this->document,this->rootNode,this->backupsEnabled,"@REMOVE_NODE");
124 >        UtilXmlTools::loadXmlFile(filesToProcess[i],this->document,this->rootNode,this->backupsEnabled,"@REMOVE_NODES");
125  
126 <        nodeToDeletion=UtilXmlTools::getFirstNamedElements(this->rootNode,filters);
126 >        // Check how the element will be fetched via element name or xpath expression
127 >        if(xPathExpression.isEmpty()){
128 >            UtilXmlTools::getAllNamedElements(this->rootNode,nodesToDeletion,filters);
129 >        }
130 >        else{
131 >            UtilXmlTools::getAllXpathElements(xPathExpression,this->document,nodesToDeletion);
132 >        }
133 >
134 >        if(nodesToDeletion[0].type()==pugi::node_null){
135  
115        if(nodeToDeletion.type()==pugi::node_null){
136              QString errMessage;
137  
138 <            errMessage = "It wasn't found a node with a ElementName: '" + filters.getElementName() + "'";
139 <            if(filters.getParentElementName()!=""){
140 <                errMessage += " and a ParentElementName: '" + filters.getParentElementName() + "'";
138 >            if(xPathExpression.isEmpty()){
139 >                errMessage = "It wasn't found any node with a ElementName: '" + filters.getElementName() + "'";
140 >                if(filters.getParentElementName()!=""){
141 >                    errMessage += " and a ParentElementName: '" + filters.getParentElementName() + "'";
142 >                }
143 >                if(filters.getAttributeName()!=""){
144 >                    errMessage += " and an AttributeName: '" + filters.getAttributeName() + "' and an AttributeValue: '" + filters.getAttributeValue() + "'";
145 >                }
146              }
147 <            if(filters.getAttributeName()!=""){
148 <                errMessage += " and an AttributeName: '" + filters.getAttributeName() + "' and an AttributeValue: '" + filters.getAttributeValue() + "'";
147 >            else{
148 >                errMessage = "It wasn't found any node with a XPathExpression: '" + xPathExpression + "'";
149              }
150  
151 <            UtilXmlTools::displayErrorMessage("@REMOVE_NODE",errMessage);
151 >            UtilXmlTools::displayErrorMessage("@REMOVE_NODES",errMessage);
152          }
153  
154 <        if(!nodeToDeletion.parent().remove_child(nodeToDeletion)){  // remove the node
154 >        // Delete all the specified nodes
155 >        for(int j=0; j<nodesToDeletion.size(); j++){
156 >            if(!nodesToDeletion[j].parent().remove_child(nodesToDeletion[j])){  // remove the node
157  
158 <            QString errMessage;
158 >                QString errMessage;
159 >                if(xPathExpression.isEmpty()){
160 >                    errMessage = "Couldn't remove the node with Element '" + filters.getElementName() + "'";
161  
162 <            errMessage = "Couldn't remove the node with Element '" + filters.getElementName() + "'";
162 >                    if(filters.getParentElementName()!=""){
163 >                        errMessage += " and a ParentElement: '" + filters.getParentElementName() + "'";
164 >                    }
165 >                }
166 >                else{
167 >                    errMessage = "Couldn't remove the node with the XPathExpression '" + xPathExpression + "'";
168 >                }
169  
170 <            if(filters.getParentElementName()!=""){
136 <                errMessage += " and a ParentElement: '" + filters.getParentElementName() + "'";
170 >                UtilXmlTools::displayErrorMessage("@REMOVE_NODES",errMessage);
171              }
138
139            UtilXmlTools::displayErrorMessage("@REMOVE_NODE",errMessage);
172          }
173  
174 <        UtilXmlTools::saveXmlFile(filesToProcess[i],this->document, "@REMOVE_NODE");
174 >        UtilXmlTools::saveXmlFile(filesToProcess[i],this->document, "@REMOVE_NODES");
175      }
176  
177 <    UtilXmlTools::displaySuccessMessage(filesToProcess.size(), "@REMOVE_NODE");
177 >    UtilXmlTools::displaySuccessMessage(filesToProcess.size(), "@REMOVE_NODES");
178   }
179  
180   void XmlPatch::executeCommandOperation(const QString &commandString){
# Line 151 | Line 183 | void XmlPatch::executeCommandOperation(c
183      QString resultOutput;
184  
185      // Avoid infinite fork loops
186 <    if(commandString.contains("-p") || commandString.contains("--patch-files")){
186 >    if(commandString.contains(" -p ") || commandString.contains(" --patch-files ")){
187          UtilXmlTools::displayErrorMessage("@COMMAND","Use of --patch-files option is not allowed inside a patch file");
188      }
189  
190 <    newXmlToolsInstance.start(GlobalVars::AppName + " " + commandString);
190 >    newXmlToolsInstance.start(GlobalVars::AppExecutable + " " + commandString);
191      newXmlToolsInstance.waitForFinished(-1); // wait for new instance to finish
192  
193      resultOutput=newXmlToolsInstance.readAll();
# Line 165 | Line 197 | void XmlPatch::executeCommandOperation(c
197          exit(1);
198      }
199  
200 <    std::cout << "@COMMAND patch operation output:\n" << resultOutput.toLatin1().constData() << std::endl;
200 >    std::cout << "@COMMAND patch operation output:\n"
201 >              << "########################################################################\n"
202 >              << resultOutput.toLatin1().constData()
203 >              << "########################################################################"
204 >              << std::endl;
205  
206      UtilXmlTools::displaySuccessMessage(1,"@COMMAND");
207   }
# Line 288 | Line 324 | void XmlPatch::checkAndProcessValidComma
324  
325      QString line, filesWildcard;
326      QString xmlToInsert, command, jsCode;
327 +    QString xPathExpression;
328      XmlFilter filters;
329  
330      // Process the rest of the commands in patch file
# Line 297 | Line 334 | void XmlPatch::checkAndProcessValidComma
334          if(line.startsWith('#')){ // Ignore comments
335              continue;
336          }
337 <        else if(line.startsWith("@ADD_INSIDE_NODE")){
337 >        else if(line.startsWith("@ADD_INSIDE_NODES")){
338 >            xPathExpression=getPatchParameterValue(line,"XPathExpression");
339              filters.setElementName(getPatchParameterValue(line,"ElementName"));
340              filters.setParentElementName(getPatchParameterValue(line,"ParentElementName"));
341              filters.setAttributeName(getPatchParameterValue(line,"AttributeName"));
# Line 310 | Line 348 | void XmlPatch::checkAndProcessValidComma
348                  filesWildcard=getPatchParameterValue(line,"Files");
349              }
350  
351 <            // Check attribute filters
351 >            // Check options
352 >            if(xPathExpression.isEmpty() && filters.getElementName().isEmpty()){
353 >                UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODES","ElementName option or XPathExpression option is required.");
354 >            }
355 >            else if(!xPathExpression.isEmpty() && !filters.getElementName().isEmpty()){
356 >                UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODES","ElementName option and XPathExpression options cannot be used simultaneously.");
357 >            }
358              if(filters.getAttributeName()!="" && filters.getAttributeValue()==""){
359 <                UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODE","attribute-value option is required if using attribute-name option.");
359 >                UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODES","AttributeValue option is required if using AttributeName option.");
360              }
361  
362              if(filters.getAttributeValue()!="" && filters.getAttributeName()==""){
363 <                UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODE","attribute-name option is required if using attribute-value option.");
363 >                UtilXmlTools::displayErrorMessage("@ADD_INSIDE_NODES","AttributeName option is required if using AttributeValue option.");
364              }
365  
366              while ( !fileStream.atEnd() && !line.startsWith("</xml>")){
# Line 327 | Line 371 | void XmlPatch::checkAndProcessValidComma
371                  }
372              }
373  
374 <            addToOperation(xmlToInsert,filters,filesWildcard);
374 >            insertNodesOperation(xmlToInsert,filters,xPathExpression,filesWildcard);
375  
376 +            xmlToInsert.clear();
377 +            filters.clear();
378 +            xPathExpression.clear();
379 +            filesWildcard.clear();
380          }
381 <        else if(line.startsWith("@REMOVE_NODE")){
381 >        else if(line.startsWith("@REMOVE_NODES")){
382  
383 +            xPathExpression=getPatchParameterValue(line,"XPathExpression");
384              filters.setElementName(getPatchParameterValue(line,"ElementName"));
385              filters.setParentElementName(getPatchParameterValue(line,"ParentElementName"));
386              filters.setAttributeName(getPatchParameterValue(line,"AttributeName"));
# Line 344 | Line 393 | void XmlPatch::checkAndProcessValidComma
393                  filesWildcard=getPatchParameterValue(line,"Files");
394              }
395  
396 <            // Check attribute filters
396 >            // Check options
397 >            if(xPathExpression.isEmpty() && filters.getElementName().isEmpty()){
398 >                UtilXmlTools::displayErrorMessage("@REMOVE_NODES","ElementName option or XPathExpression option is required.");
399 >            }
400 >            else if(!xPathExpression.isEmpty() && !filters.getElementName().isEmpty()){
401 >                UtilXmlTools::displayErrorMessage("@REMOVE_NODES","ElementName option and XPathExpression options cannot be used simultaneously.");
402 >            }
403 >
404              if(filters.getAttributeName()!="" && filters.getAttributeValue()==""){
405 <                UtilXmlTools::displayErrorMessage("@REMOVE_NODE","attribute-value option is required if using attribute-name option.");
405 >                UtilXmlTools::displayErrorMessage("@REMOVE_NODES","AttributeValue option is required if using AttributeName option.");
406              }
407  
408              if(filters.getAttributeValue()!="" && filters.getAttributeName()==""){
409 <                UtilXmlTools::displayErrorMessage("@REMOVE_NODE","attribute-name option is required if using attribute-value option.");
409 >                UtilXmlTools::displayErrorMessage("@REMOVE_NODES","AttributeName option is required if using AttributeValue option.");
410              }
411  
412 <            removeNodeOperation(filters,filesWildcard);
412 >            removeNodesOperation(filters,xPathExpression,filesWildcard);
413  
414 +            filters.clear();
415 +            xPathExpression.clear();
416 +            filesWildcard.clear();
417          }
418          else if(line.startsWith("@COMMAND")){
419  
420 <            command=getPatchParameterValue(line,"");
420 >            command=getPatchParameterValue(line,"Arguments");
421 >
422 >            command.replace("'","\""); //replace apostrophe by quotes, to avoid problems
423  
424              executeCommandOperation(command);
425 +
426 +            command.clear();
427          }
428          else if(line.startsWith("@CUSTOM_CODE")){
429  
# Line 381 | Line 444 | void XmlPatch::checkAndProcessValidComma
444              }
445  
446              executeCustomCommandOperation(jsCode,filesWildcard);
447 +
448 +            jsCode.clear();
449 +            filesWildcard.clear();
450          }
451      }
452   }
# Line 389 | Line 455 | QString XmlPatch::getPatchParameterValue
455  
456      int startValueIdx, endValueIdx;
457  
458 <    parameter+=" "; // Parameters include a space before it's value.
458 >    parameter=" "+parameter+" "; // Parameters include a space before and after it's value.
459  
460      if(!line.contains(parameter)){
461 <        if(parameter=="ParentElementName " || parameter=="AttributeName " || parameter=="AttributeValue "){
461 >        if(parameter==" ParentElementName " || parameter==" AttributeName " || parameter==" AttributeValue "
462 >                || parameter==" ElementName " || parameter==" XPathExpression "){
463              return ""; // not mandatory
464          }
465          parameter.remove(" "); // just remove the space added so it doesn't look weird when outputted to the user

Diff Legend

Removed lines
+ Added lines
< Changed lines (old)
> Changed lines (new)