1 // ==============================================================
2 //	This file is part of MegaGlest Unit Tests (www.megaglest.org)
3 //
4 //	Copyright (C) 2013 Mark Vejvoda
5 //
6 //	You can redistribute this code and/or modify it under
7 //	the terms of the GNU General Public License as published
8 //	by the Free Software Foundation; either version 2 of the
9 //	License, or (at your option) any later version
10 // ==============================================================
11 
12 #include <cppunit/extensions/HelperMacros.h>
13 #include <memory>
14 #include <fstream>
15 #include "xml_parser.h"
16 #include "platform_util.h"
17 
18 #if defined(WANT_XERCES)
19 
20 #include <xercesc/dom/DOM.hpp>
21 
22 //#include <xercesc/util/PlatformUtils.hpp>
23 //#include <xercesc/framework/LocalFileFormatTarget.hpp>
24 
25 #endif
26 
27 #ifdef WIN32
28 #include <io.h>
29 #else
30 #include <unistd.h>
31 #endif
32 
33 using namespace Shared::Xml;
34 using namespace Shared::Platform;
35 
36 //
37 // Utility methods for tests
38 //
removeTestFile(string file)39 bool removeTestFile(string file) {
40 #ifdef WIN32
41 	int result = _unlink(file.c_str());
42 #else
43     int result = unlink(file.c_str());
44 #endif
45 
46     return (result == 0);
47 }
48 
createValidXMLTestFile(const string & test_filename)49 void createValidXMLTestFile(const string& test_filename) {
50 	std::ofstream xmlFile(test_filename.c_str());
51 	xmlFile << "<?xml version=\"1.0\"?>" << std::endl
52 			<< "<menu mytest-attribute=\"true\">"	<< std::endl
53 			<< "<menu-background-model value=\"data/core/menu/main_model/menu_main1.g3d\"/>" << std::endl
54 			<< "</menu>" << std::endl;
55 	xmlFile.close();
56 }
57 
createMalformedXMLTestFile(const string & test_filename)58 void createMalformedXMLTestFile(const string& test_filename) {
59 	std::ofstream xmlFile(test_filename.c_str());
60 	xmlFile << "<?xml version=\"1.0\"?> #@$ !#@$@#$" << std::endl
61 			<< "<menu>" << std::endl
62 			<< "<menu-background-model value=\"data/core/menu/main_model/menu_main1.g3d\"/>"
63 			<< std::endl;
64 	xmlFile.close();
65 }
66 
67 class SafeRemoveTestFile {
68 private:
69 	string filename;
70 public:
SafeRemoveTestFile(const string & filename)71 	SafeRemoveTestFile(const string &filename) {
72 		this->filename = filename;
73 	}
~SafeRemoveTestFile()74 	~SafeRemoveTestFile() {
75 		removeTestFile(this->filename);
76 	}
77 };
78 //
79 
80 #if defined(WANT_XERCES)
81 
82 //
83 // Tests for XmlIo
84 //
85 class XmlIoTest : public CppUnit::TestFixture {
86 	// Register the suite of tests for this fixture
87 	CPPUNIT_TEST_SUITE( XmlIoTest );
88 
89 	CPPUNIT_TEST( test_getInstance );
90 	CPPUNIT_TEST( test_cleanup );
91 	CPPUNIT_TEST_EXCEPTION( test_load_file_missing,  megaglest_runtime_error );
92 	CPPUNIT_TEST( test_load_file_valid );
93 	CPPUNIT_TEST_EXCEPTION( test_load_file_malformed_content,  megaglest_runtime_error );
94 	CPPUNIT_TEST_EXCEPTION( test_save_file_null_node,  megaglest_runtime_error );
95 	CPPUNIT_TEST(test_save_file_valid_node );
96 
97 	CPPUNIT_TEST_SUITE_END();
98 	// End of Fixture registration
99 
100 public:
101 
test_getInstance()102 	void test_getInstance() {
103 		XmlIo &newInstance = XmlIo::getInstance();
104 		CPPUNIT_ASSERT_EQUAL( true, newInstance.isInitialized() );
105 	}
test_cleanup()106 	void test_cleanup() {
107 		XmlIo &newInstance = XmlIo::getInstance();
108 		CPPUNIT_ASSERT_EQUAL( true, newInstance.isInitialized() );
109 
110 		newInstance.cleanup();
111 		CPPUNIT_ASSERT_EQUAL( false, newInstance.isInitialized() );
112 	}
test_load_file_missing()113 	void test_load_file_missing() {
114 		XmlNode *rootNode = XmlIo::getInstance().load("/some/path/that/does/not exist", std::map<string,string>());
115 		delete rootNode;
116 	}
test_load_file_valid()117 	void test_load_file_valid() {
118 		const string test_filename = "xml_test_valid.xml";
119 		createValidXMLTestFile(test_filename);
120 		SafeRemoveTestFile deleteFile(test_filename);
121 
122 		XmlNode *rootNode = XmlIo::getInstance().load(test_filename, std::map<string,string>());
123 
124 		CPPUNIT_ASSERT( rootNode != NULL );
125 		CPPUNIT_ASSERT_EQUAL( string("menu"), (rootNode != NULL ? rootNode->getName() : string("")) );
126 
127 		delete rootNode;
128 	}
test_load_file_malformed_content()129 	void test_load_file_malformed_content() {
130 		const string test_filename = "xml_test_malformed.xml";
131 		createMalformedXMLTestFile(test_filename);
132 		SafeRemoveTestFile deleteFile(test_filename);
133 
134 		XmlNode *rootNode = XmlIo::getInstance().load(test_filename, std::map<string,string>());
135 		delete rootNode;
136 	}
137 
test_save_file_null_node()138 	void test_save_file_null_node() {
139 		XmlNode *rootNode = NULL;
140 		XmlIo::getInstance().save("",rootNode);
141 	}
142 
test_save_file_valid_node()143 	void test_save_file_valid_node() {
144 		const string test_filename_load = "xml_test_save_load_valid.xml";
145 		const string test_filename_save = "xml_test_save_valid.xml";
146 		createValidXMLTestFile(test_filename_load);
147 		SafeRemoveTestFile deleteFile(test_filename_load);
148 
149 		XmlNode *rootNode = XmlIo::getInstance().load(test_filename_load, std::map<string,string>());
150 
151 		XmlIo::getInstance().save(test_filename_save,rootNode);
152 		SafeRemoveTestFile deleteFile2(test_filename_save);
153 
154 		delete rootNode;
155 	}
156 };
157 
158 #endif
159 
160 //
161 // Tests for XmlIoRapid
162 //
163 class XmlIoRapidTest : public CppUnit::TestFixture {
164 	// Register the suite of tests for this fixture
165 	CPPUNIT_TEST_SUITE( XmlIoRapidTest );
166 
167 	CPPUNIT_TEST( test_getInstance );
168 	CPPUNIT_TEST( test_cleanup );
169 	CPPUNIT_TEST_EXCEPTION( test_load_file_missing,  megaglest_runtime_error );
170 	CPPUNIT_TEST( test_load_file_valid );
171 	CPPUNIT_TEST_EXCEPTION( test_load_file_malformed_content,  megaglest_runtime_error );
172 	CPPUNIT_TEST_EXCEPTION( test_save_file_null_node,  megaglest_runtime_error );
173 	CPPUNIT_TEST(test_save_file_valid_node );
174 
175 	CPPUNIT_TEST_SUITE_END();
176 	// End of Fixture registration
177 
178 public:
179 
test_getInstance()180 	void test_getInstance() {
181 		XmlIoRapid &newInstance = XmlIoRapid::getInstance();
182 		CPPUNIT_ASSERT_EQUAL( true, newInstance.isInitialized() );
183 	}
test_cleanup()184 	void test_cleanup() {
185 		XmlIoRapid &newInstance = XmlIoRapid::getInstance();
186 		CPPUNIT_ASSERT_EQUAL( true, newInstance.isInitialized() );
187 
188 		newInstance.cleanup();
189 		CPPUNIT_ASSERT_EQUAL( false, newInstance.isInitialized() );
190 	}
test_load_file_missing()191 	void test_load_file_missing() {
192 		XmlNode *rootNode = XmlIoRapid::getInstance().load("/some/path/that/does/not exist", std::map<string,string>());
193 		delete rootNode;
194 	}
test_load_file_valid()195 	void test_load_file_valid() {
196 		const string test_filename = "xml_test_valid.xml";
197 		createValidXMLTestFile(test_filename);
198 		SafeRemoveTestFile deleteFile(test_filename);
199 
200 		XmlNode *rootNode = XmlIoRapid::getInstance().load(test_filename, std::map<string,string>());
201 
202 		CPPUNIT_ASSERT( rootNode != NULL );
203 		CPPUNIT_ASSERT_EQUAL( string("menu"), (rootNode != NULL ? rootNode->getName() : string("")) );
204 
205 		delete rootNode;
206 	}
test_load_file_malformed_content()207 	void test_load_file_malformed_content() {
208 		const string test_filename = "xml_test_malformed.xml";
209 		createMalformedXMLTestFile(test_filename);
210 		SafeRemoveTestFile deleteFile(test_filename);
211 		XmlNode *rootNode = XmlIoRapid::getInstance().load(test_filename, std::map<string,string>());
212 		delete rootNode;
213 	}
214 
test_save_file_null_node()215 	void test_save_file_null_node() {
216 		XmlNode *rootNode = NULL;
217 		XmlIoRapid::getInstance().save("",rootNode);
218 	}
219 
test_save_file_valid_node()220 	void test_save_file_valid_node() {
221 		const string test_filename_load = "xml_test_save_load_valid.xml";
222 		const string test_filename_save = "xml_test_save_valid.xml";
223 		createValidXMLTestFile(test_filename_load);
224 		SafeRemoveTestFile deleteFile(test_filename_load);
225 
226 		XmlNode *rootNode = XmlIoRapid::getInstance().load(test_filename_load, std::map<string,string>());
227 
228 		XmlIoRapid::getInstance().save(test_filename_save,rootNode);
229 		SafeRemoveTestFile deleteFile2(test_filename_save);
230 
231 		delete rootNode;
232 	}
233 };
234 
235 //
236 // Tests for XmlTree
237 //
238 class XmlTreeTest : public CppUnit::TestFixture {
239 	// Register the suite of tests for this fixture
240 	CPPUNIT_TEST_SUITE( XmlTreeTest );
241 
242 	CPPUNIT_TEST_EXCEPTION( test_invalid_xml_engine_lowerbound,  megaglest_runtime_error );
243 	CPPUNIT_TEST_EXCEPTION( test_invalid_xml_engine_upperbound,  megaglest_runtime_error );
244 	CPPUNIT_TEST( test_valid_xml_engine );
245 	CPPUNIT_TEST( test_init );
246 	CPPUNIT_TEST_EXCEPTION( test_load_simultaneously_same_file,  megaglest_runtime_error );
247 	CPPUNIT_TEST( test_load_simultaneously_different_file );
248 
249 	CPPUNIT_TEST_SUITE_END();
250 	// End of Fixture registration
251 
252 public:
253 
254 #if defined(WANT_XERCES)
255 
test_invalid_xml_engine_lowerbound()256 	void test_invalid_xml_engine_lowerbound() {
257 		xml_engine_parser_type testType = static_cast<xml_engine_parser_type>(XML_XERCES_ENGINE - 1);
258 		if((int)testType == (int)(XML_XERCES_ENGINE - 1)) {
259 			XmlTree xml(testType);
260 		}
261 	}
262 
263 #else
264 
265 	void test_invalid_xml_engine_lowerbound() {
266 		xml_engine_parser_type testType = static_cast<xml_engine_parser_type>(XML_RAPIDXML_ENGINE - 1);
267 		if((int)testType == (int)(XML_RAPIDXML_ENGINE - 1)) {
268 			XmlTree xml(testType);
269 		}
270 	}
271 
272 #endif
273 
test_invalid_xml_engine_upperbound()274 	void test_invalid_xml_engine_upperbound() {
275 		xml_engine_parser_type testType = static_cast<xml_engine_parser_type>(XML_RAPIDXML_ENGINE + 1);
276 		if((int)testType == (int)(XML_RAPIDXML_ENGINE + 1)) {
277 			XmlTree xml(testType);
278 		}
279 	}
test_valid_xml_engine()280 	void test_valid_xml_engine() {
281 		XmlTree xmlInstance;
282 		CPPUNIT_ASSERT_EQUAL( (XmlNode *)NULL, xmlInstance.getRootNode() );
283 	}
test_init()284 	void test_init() {
285 		XmlTree xmlInstance;
286 		xmlInstance.init("");
287 		CPPUNIT_ASSERT( xmlInstance.getRootNode() != NULL );
288 		CPPUNIT_ASSERT_EQUAL( string(""), xmlInstance.getRootNode()->getName() );
289 
290 		xmlInstance.init("testRoot");
291 		CPPUNIT_ASSERT( xmlInstance.getRootNode() != NULL );
292 		CPPUNIT_ASSERT_EQUAL( string("testRoot"), xmlInstance.getRootNode()->getName() );
293 	}
test_load_simultaneously_same_file()294 	void test_load_simultaneously_same_file() {
295 		const string test_filename = "xml_test_valid.xml";
296 		createValidXMLTestFile(test_filename);
297 		SafeRemoveTestFile deleteFile(test_filename);
298 
299 		XmlTree xmlInstance1;
300 		xmlInstance1.load(test_filename, std::map<string,string>());
301 		XmlTree xmlInstance2;
302 		xmlInstance2.load(test_filename, std::map<string,string>());
303 	}
test_load_simultaneously_different_file()304 	void test_load_simultaneously_different_file() {
305 		const string test_filename1 = "xml_test_valid1.xml";
306 		createValidXMLTestFile(test_filename1);
307 		SafeRemoveTestFile deleteFile(test_filename1);
308 		const string test_filename2 = "xml_test_valid2.xml";
309 		createValidXMLTestFile(test_filename2);
310 		SafeRemoveTestFile deleteFile2(test_filename2);
311 
312 		XmlTree xmlInstance1;
313 		xmlInstance1.load(test_filename1, std::map<string,string>());
314 		XmlTree xmlInstance2;
315 		xmlInstance2.load(test_filename2, std::map<string,string>());
316 	}
317 };
318 
319 
320 //
321 // Tests for XmlNode
322 //
323 class XmlNodeTest : public CppUnit::TestFixture {
324 	// Register the suite of tests for this fixture
325 	CPPUNIT_TEST_SUITE( XmlNodeTest );
326 
327 #if defined(WANT_XERCES)
328 
329 	CPPUNIT_TEST_EXCEPTION( test_null_xerces_node,  megaglest_runtime_error );
330 	CPPUNIT_TEST( test_valid_xerces_node );
331 
332 #endif
333 
334 	CPPUNIT_TEST_EXCEPTION( test_null_rapidxml_node,  megaglest_runtime_error );
335 	CPPUNIT_TEST( test_valid_named_node );
336 	CPPUNIT_TEST( test_child_nodes );
337 	CPPUNIT_TEST( test_node_attributes );
338 
339 	CPPUNIT_TEST_SUITE_END();
340 	// End of Fixture registration
341 
342 private:
343 
344 #if defined(WANT_XERCES)
345 
346 	class XmlIoMock : public XmlIo {
347 	protected:
releaseDOMParser()348 		virtual void releaseDOMParser() { }
349 
350 	public:
XmlIoMock()351 		XmlIoMock() : XmlIo() {	}
352 
loadDOMNode(const string & path,bool noValidation=false)353 		DOMNode *loadDOMNode(const string &path, bool noValidation=false) {
354 			return XmlIo::loadDOMNode(path, noValidation);
355 		}
356 
manualParserRelease()357 		void manualParserRelease() {
358 			XmlIo::releaseDOMParser();
359 		}
360 	};
361 
362 #endif
363 
364 public:
365 
366 #if defined(WANT_XERCES)
367 
test_null_xerces_node()368 	void test_null_xerces_node() {
369 		XERCES_CPP_NAMESPACE::DOMNode *node = NULL;
370 		const std::map<string,string> mapTagReplacementValues;
371 		XmlNode(node, mapTagReplacementValues);
372 	}
373 
test_valid_xerces_node()374 	void test_valid_xerces_node() {
375 		const string test_filename = "xml_test_valid.xml";
376 		createValidXMLTestFile(test_filename);
377 		SafeRemoveTestFile deleteFile(test_filename);
378 
379 		XmlIoMock xml;
380 		XERCES_CPP_NAMESPACE::DOMNode *domNode = xml.loadDOMNode(test_filename);
381 
382 		CPPUNIT_ASSERT( domNode != NULL );
383 
384 		const std::map<string,string> mapTagReplacementValues;
385 		XmlNode node(domNode, mapTagReplacementValues);
386 
387 		xml.manualParserRelease();
388 
389 		CPPUNIT_ASSERT_EQUAL( string("menu"), node.getName() );
390 		CPPUNIT_ASSERT( node.hasAttribute("mytest-attribute") == true );
391 		CPPUNIT_ASSERT( node.hasChild("menu-background-model") == true );
392 	}
393 
394 #endif
395 
test_null_rapidxml_node()396 	void test_null_rapidxml_node() {
397 		xml_node<> *node = NULL;
398 		const std::map<string,string> mapTagReplacementValues;
399 		XmlNode(node, mapTagReplacementValues);
400 	}
test_valid_named_node()401 	void test_valid_named_node() {
402 		XmlNode node("testNode");
403 
404 		CPPUNIT_ASSERT_EQUAL( string("testNode"), node.getName() );
405 	}
406 
test_child_nodes()407 	void test_child_nodes() {
408 		XmlNode node("testNode");
409 
410 		CPPUNIT_ASSERT_EQUAL( string("testNode"), node.getName() );
411 		CPPUNIT_ASSERT_EQUAL( (size_t)0,node.getChildCount() );
412 
413 		XmlNode *childNode1 = node.addChild("child1");
414 		CPPUNIT_ASSERT_EQUAL( (size_t)1,node.getChildCount() );
415 		CPPUNIT_ASSERT_EQUAL( string(""), childNode1->getText() );
416 
417 		XmlNode *childChildNode1 = childNode1->addChild("childchild1", "testValue");
418 		CPPUNIT_ASSERT_EQUAL( (size_t)1,childNode1->getChildCount() );
419 		CPPUNIT_ASSERT_EQUAL( string("testValue"), childChildNode1->getText() );
420 
421 		XmlNode *childChildNode2 = childNode1->addChild("childchild2", "testValue2");
422 		CPPUNIT_ASSERT_EQUAL( (size_t)2, childNode1->getChildCount() );
423 		CPPUNIT_ASSERT_EQUAL( string("testValue2"), childChildNode2->getText() );
424 
425 		XmlNode *childChildNode3 = childNode1->addChild("childchild2", "testValue3");
426 		CPPUNIT_ASSERT_EQUAL( (size_t)3, childNode1->getChildCount() );
427 		CPPUNIT_ASSERT_EQUAL( string("testValue3"), childChildNode3->getText() );
428 
429 		CPPUNIT_ASSERT_EQUAL( true, childNode1->hasChildAtIndex("childchild2",1));
430 
431 		XmlNode *childNode2 = node.addChild("child2","child2Value");
432 		CPPUNIT_ASSERT_EQUAL( (size_t)2,node.getChildCount() );
433 		CPPUNIT_ASSERT_EQUAL( string("child2Value"), childNode2->getText() );
434 
435 		CPPUNIT_ASSERT_EQUAL( string("child2"), node.getChild(1)->getName() );
436 		CPPUNIT_ASSERT_EQUAL( string("child2"), node.getChild("child2")->getName() );
437 		CPPUNIT_ASSERT_EQUAL( string("child1"), node.getChild("child1")->getName() );
438 
439 		XmlNode *childNode2x = node.addChild("child2","child2xValue");
440 		CPPUNIT_ASSERT_EQUAL( (size_t)3, node.getChildCount() );
441 		CPPUNIT_ASSERT_EQUAL( string("child2xValue"), childNode2x->getText() );
442 		CPPUNIT_ASSERT_EQUAL( string("child2xValue"), node.getChild("child2",1)->getText() );
443 
444 		XmlNode *childNode3 = node.addChild("child3","child3Value");
445 		CPPUNIT_ASSERT_EQUAL( (size_t)4, node.getChildCount() );
446 
447 		vector<XmlNode *> child2List = node.getChildList("child2");
448 		CPPUNIT_ASSERT_EQUAL( (size_t)2, child2List.size() );
449 		CPPUNIT_ASSERT_EQUAL( string("child2Value"), child2List[0]->getText() );
450 		CPPUNIT_ASSERT_EQUAL( string("child2xValue"), child2List[1]->getText() );
451 
452 		//printf("%d\n",__LINE__);
453 		CPPUNIT_ASSERT_EQUAL( false, childNode3->hasChild("child2"));
454 		CPPUNIT_ASSERT_EQUAL( 2, node.clearChild("child2"));
455 		CPPUNIT_ASSERT_EQUAL( (size_t)2,node.getChildCount() );
456 	}
457 
test_node_attributes()458 	void test_node_attributes() {
459 		XmlNode node("testNode");
460 
461 		CPPUNIT_ASSERT_EQUAL( string("testNode"), node.getName() );
462 		CPPUNIT_ASSERT_EQUAL( (size_t)0,node.getAttributeCount() );
463 		CPPUNIT_ASSERT_EQUAL( (XmlAttribute *)NULL, node.getAttribute("some-attribute",false) );
464 		CPPUNIT_ASSERT_EQUAL( false, node.hasAttribute("some-attribute") );
465 
466 		std::map<string,string> mapTagReplacementValues;
467 		XmlAttribute *attribute1 = node.addAttribute("some-attribute", "some-value", mapTagReplacementValues);
468 		CPPUNIT_ASSERT_EQUAL( (size_t)1,node.getAttributeCount() );
469 		CPPUNIT_ASSERT_EQUAL( attribute1, node.getAttribute("some-attribute") );
470 		CPPUNIT_ASSERT_EQUAL( string("some-attribute"), node.getAttribute(0)->getName() );
471 		CPPUNIT_ASSERT_EQUAL( true, node.hasAttribute("some-attribute") );
472 	}
473 
474 };
475 
476 #if defined(WANT_XERCES)
477 //
478 // Tests for XmlAttribute
479 //
480 class XmlAttributeTest : public CppUnit::TestFixture {
481 	// Register the suite of tests for this fixture
482 	CPPUNIT_TEST_SUITE( XmlAttributeTest );
483 
484 	CPPUNIT_TEST_EXCEPTION( test_null_xerces_attribute,  megaglest_runtime_error );
485 
486 	CPPUNIT_TEST( test_node_attributes );
487 	CPPUNIT_TEST_EXCEPTION( test_node_attributes_restricted, megaglest_runtime_error );
488 	CPPUNIT_TEST_EXCEPTION( test_node_attributes_int_outofrange, megaglest_runtime_error );
489 	CPPUNIT_TEST_EXCEPTION( test_node_attributes_float_outofrange, megaglest_runtime_error );
490 
491 	CPPUNIT_TEST_SUITE_END();
492 	// End of Fixture registration
493 
494 private:
495 
496 	class XmlIoMock : public XmlIo {
497 	protected:
releaseDOMParser()498 		virtual void releaseDOMParser() { }
499 
500 	public:
XmlIoMock()501 		XmlIoMock() : XmlIo() {	}
502 
loadDOMNode(const string & path,bool noValidation=false)503 		DOMNode *loadDOMNode(const string &path, bool noValidation=false) {
504 			return XmlIo::loadDOMNode(path, noValidation);
505 		}
506 
manualParserRelease()507 		void manualParserRelease() {
508 			XmlIo::releaseDOMParser();
509 		}
510 	};
511 
512 public:
513 
test_null_xerces_attribute()514 	void test_null_xerces_attribute() {
515 		const string test_filename = "xml_test_valid.xml";
516 		createValidXMLTestFile(test_filename);
517 		SafeRemoveTestFile deleteFile(test_filename);
518 
519 		XERCES_CPP_NAMESPACE::DOMNode *node = NULL;
520 		const std::map<string,string> mapTagReplacementValues;
521 		XmlAttribute attr(node, mapTagReplacementValues);
522 	}
523 
test_node_attributes()524 	void test_node_attributes() {
525 		const string test_filename = "xml_test_valid.xml";
526 		createValidXMLTestFile(test_filename);
527 		SafeRemoveTestFile deleteFile(test_filename);
528 
529 		XmlIoMock xmlIo;
530 		XERCES_CPP_NAMESPACE::DOMNode *node = xmlIo.loadDOMNode(test_filename);
531 		const std::map<string,string> mapTagReplacementValues;
532 
533 		XmlAttribute attr(node, mapTagReplacementValues);
534 
535 		CPPUNIT_ASSERT_EQUAL( string("menu"),attr.getName() );
536 		CPPUNIT_ASSERT_EQUAL( string(""),attr.getValue() );
537 
538 		attr.setValue("abcdefg");
539 		CPPUNIT_ASSERT_EQUAL( string("abcdefg"),attr.getValue() );
540 		CPPUNIT_ASSERT_EQUAL( string("abcdefg"),attr.getRestrictedValue() );
541 
542 		attr.setValue("!@#$%^&*()_+");
543 		CPPUNIT_ASSERT_EQUAL( string("!@#$%^&*()_+"),attr.getValue() );
544 
545 		attr.setValue("true");
546 		CPPUNIT_ASSERT_EQUAL( true,attr.getBoolValue() );
547 
548 		attr.setValue("false");
549 		CPPUNIT_ASSERT_EQUAL( false,attr.getBoolValue() );
550 
551 		attr.setValue("-123456");
552 		CPPUNIT_ASSERT_EQUAL( -123456,attr.getIntValue() );
553 
554 		attr.setValue("1");
555 		CPPUNIT_ASSERT_EQUAL( 1,attr.getIntValue(1, 10) );
556 		attr.setValue("10");
557 		CPPUNIT_ASSERT_EQUAL( 10,attr.getIntValue(1, 10) );
558 		attr.setValue("5");
559 		CPPUNIT_ASSERT_EQUAL( 5,attr.getIntValue(1, 10) );
560 
561 		attr.setValue("-123456.123456");
562 		CPPUNIT_ASSERT_DOUBLES_EQUAL( -123456.123456f,attr.getFloatValue(), 1e-6 );
563 
564 		// Nasty floating point issues shown by this test sometimes may need to comment out
565 		attr.setValue("123456.123456");
566 		CPPUNIT_ASSERT_DOUBLES_EQUAL( 123456.123456f,attr.getFloatValue(123456.01f, 123456.999f), 1e-6 );
567 	}
568 
test_node_attributes_restricted()569 	void test_node_attributes_restricted() {
570 		const string test_filename = "xml_test_valid.xml";
571 		createValidXMLTestFile(test_filename);
572 		SafeRemoveTestFile deleteFile(test_filename);
573 
574 		XmlIoMock xmlIo;
575 
576 		XERCES_CPP_NAMESPACE::DOMNode *node = xmlIo.loadDOMNode(test_filename);
577 		const std::map<string,string> mapTagReplacementValues;
578 
579 		XmlAttribute attr(node, mapTagReplacementValues);
580 
581 		CPPUNIT_ASSERT_EQUAL( string("menu"),attr.getName() );
582 		CPPUNIT_ASSERT_EQUAL( string(""),attr.getValue() );
583 
584 		attr.setValue("!@#$%^&*()_+");
585 		CPPUNIT_ASSERT_EQUAL( string("!@#$%^&*()_+"),attr.getRestrictedValue() );
586 	}
587 
test_node_attributes_int_outofrange()588 	void test_node_attributes_int_outofrange() {
589 		const string test_filename = "xml_test_valid.xml";
590 		createValidXMLTestFile(test_filename);
591 		SafeRemoveTestFile deleteFile(test_filename);
592 
593 		XmlIoMock xmlIo;
594 		XERCES_CPP_NAMESPACE::DOMNode *node = xmlIo.loadDOMNode(test_filename);
595 		const std::map<string,string> mapTagReplacementValues;
596 
597 		XmlAttribute attr(node, mapTagReplacementValues);
598 
599 		CPPUNIT_ASSERT_EQUAL( string("menu"),attr.getName() );
600 		CPPUNIT_ASSERT_EQUAL( string(""),attr.getValue() );
601 
602 		attr.setValue("-123456");
603 		attr.getIntValue(1, 10);
604 	}
test_node_attributes_float_outofrange()605 	void test_node_attributes_float_outofrange() {
606 		const string test_filename = "xml_test_valid.xml";
607 		createValidXMLTestFile(test_filename);
608 		SafeRemoveTestFile deleteFile(test_filename);
609 
610 		XmlIoMock xmlIo;
611 		XERCES_CPP_NAMESPACE::DOMNode *node = xmlIo.loadDOMNode(test_filename);
612 		const std::map<string,string> mapTagReplacementValues;
613 
614 		XmlAttribute attr(node, mapTagReplacementValues);
615 
616 		attr.setValue("-123456.01");
617 		attr.getFloatValue(-123456.999f, -123456.123456f);
618 	}
619 };
620 
621 #endif
622 
623 // Test Suite Registrations
624 
625 CPPUNIT_TEST_SUITE_REGISTRATION( XmlIoRapidTest );
626 CPPUNIT_TEST_SUITE_REGISTRATION( XmlTreeTest );
627 CPPUNIT_TEST_SUITE_REGISTRATION( XmlNodeTest );
628 
629 #if defined(WANT_XERCES)
630 
631 CPPUNIT_TEST_SUITE_REGISTRATION( XmlIoTest );
632 CPPUNIT_TEST_SUITE_REGISTRATION( XmlAttributeTest );
633 
634 #endif
635 
636 //
637