diff --git a/MILESTONE3-README.md b/MILESTONE3-README.md new file mode 100644 index 000000000..2f3c499b5 --- /dev/null +++ b/MILESTONE3-README.md @@ -0,0 +1,12 @@ +**Performance Implications of doing this inside the +library vs. doing it in client code:** + +Performing a transformation on all the keys of the resulting JSON object is +much more efficient when done inside the library for two reasons: +1. You can modify the key as you're reading the XML file and generating the +JSON object versus generating the entire JSON Object first and then going back +to parse the entire structure again and updating the keys. + +2. You can provide your own custom transformations which can be +handled dynamically thanks to the functional interface built into +Java 8. \ No newline at end of file diff --git a/pom.xml b/pom.xml index e5449ba8c..e161b2d46 100644 --- a/pom.xml +++ b/pom.xml @@ -118,8 +118,8 @@ maven-compiler-plugin 2.3.2 - 1.6 - 1.6 + 8 + 8 diff --git a/src/main/java/org/json/XML.java b/src/main/java/org/json/XML.java index 805a5c376..cc52dd50e 100644 --- a/src/main/java/org/json/XML.java +++ b/src/main/java/org/json/XML.java @@ -29,7 +29,10 @@ of this software and associated documentation files (the "Software"), to deal import java.lang.reflect.Method; import java.math.BigDecimal; import java.math.BigInteger; -import java.util.Iterator; +import java.util.*; +import java.util.function.Consumer; +import java.util.function.Function; +import java.util.stream.Stream; /** @@ -40,7 +43,7 @@ of this software and associated documentation files (the "Software"), to deal * @version 2016-08-10 */ @SuppressWarnings("boxing") -public class XML { +public class XML{ /** The Character '&'. */ public static final Character AMP = '&'; @@ -709,6 +712,396 @@ public static JSONObject toJSONObject(String string, XMLParserConfiguration conf return toJSONObject(new StringReader(string), config); } + //[RJ ADDED] Overloaded static method + public static JSONObject toJSONObject(Reader reader, JSONPointer path) + { + //Need substring to take out first / so can use split successfully. + String[] pathArray = path.toString().substring(1).split("[\\\\/]", -1); + int pathSize = pathArray.length; + + + JSONObject jo = new JSONObject(); + XMLParserConfiguration config = new XMLParserConfiguration(); + XMLTokener x = new XMLTokener(reader); + + //Find the last non-numerical tag in pathArray + int containsNumber = 0; //index of array where number is + for(int i = 0; i < pathSize; i ++) + { + if(pathArray[i].matches("-?\\d+(\\.\\d+)?")) + { + containsNumber = i; + } + } + + System.out.println("Contains number: " + containsNumber); + + String parseTag;// = (containsNumber == 0) ? pathArray[pathSize - 1] : pathArray[containsNumber - 1]; + if(containsNumber == 0) + { + parseTag = pathArray[pathSize -1]; + } + else + { + if(pathSize < 2) + { + parseTag = pathArray[0]; + } + else + { + parseTag = pathArray[containsNumber - 1]; + } + } + String remArr = ""; + + //Need to get the new string array that can use JSONPointer to solve + if(containsNumber != 0) + { + for(int z = containsNumber-1; z < pathSize; z ++) + remArr += "/" + pathArray[z]; + } + + System.out.println("remArr: " + remArr); + System.out.println("Parse Tag: " + parseTag); + + //rebuild the sub xml + String rebuildXML = ""; + boolean cycle = false; + + boolean exitLoop = false; + + String currTag =""; + + String startString = "<" + parseTag; + String exitString = "...... + exitLoop = false; //Needed incase JSON has array structure. + } + + if(cycle) + { + if(exitLoop) + break; + + rebuildXML += currTag; + //System.out.println("Pre If: " + currTag); + } + + //Start recording after start string reached. + if(currTag.contains(exitString)) + { + exitLoop = true; + if(containsNumber != 0) + cycle = false; + else + cycle = true; + } + } + + //System.out.println(rebuildXML); + JSONObject query = XML.toJSONObject(rebuildXML); + //System.out.println(query.toString()); + + if(containsNumber != 0) + { + Object jsquery = query.query(remArr); + //System.out.println(jsquery); + if(jsquery instanceof String) + query = new JSONObject().put(pathArray[pathSize - 1], jsquery); + else if(jsquery instanceof BigDecimal) + query = new JSONObject().put(pathArray[pathSize - 1], jsquery.toString()); + else + query = (JSONObject) jsquery; + } + + //System.out.println("PrintingJSON"); + + return query; + + } + + public static JSONObject toJSONObject(Reader reader, JSONPointer path, JSONObject replacement) + { + //Logic + //Get the JSONObject (or XML) up to a certain nonnumerical path - done + //Concert the replacement to a JSONObject + //Merge the tw + + if(path.toString().equals("/")) + { + return XML.toJSONObject(XML.toString(replacement)); + } + + //Need substring to take out first / so can use split successfully. + String[] pathArray = path.toString().substring(1).split("[\\\\/]", -1); + int pathSize = pathArray.length; + + String replacementXML = toString(replacement); + + JSONObject jo = new JSONObject(); + XMLParserConfiguration config = new XMLParserConfiguration(); + XMLTokener x = new XMLTokener(reader); + + //Find the last non-numerical tag in pathArray + int containsNumber = 0; //index of array where number is + for(int i = 0; i < pathSize; i ++) + { + if(pathArray[i].matches("-?\\d+(\\.\\d+)?")) + { + containsNumber = i; + } + } + + System.out.println("Contains number: " + containsNumber); + + String parseTag;// = (containsNumber == 0) ? pathArray[pathSize - 1] : pathArray[containsNumber - 1]; + if(containsNumber == 0) + { + parseTag = pathArray[pathSize -1]; + } + else + { + if(pathSize < 2) + { + parseTag = pathArray[0]; + } + else + { + parseTag = pathArray[containsNumber - 1]; + } + } + String remArr = ""; + + //Need to get the new string array that can use JSONPointer to solve + if(containsNumber != 0) + { + for(int z = containsNumber-1; z < pathSize; z ++) + remArr += "/" + pathArray[z]; + } + + System.out.println("remArr: " + remArr); + System.out.println("Parse Tag: " + parseTag); + + //rebuild the sub xml + String rebuildXML = ""; + boolean cycle = true; + + //boolean replacementPast = false; + boolean firstPass = false; + boolean replaceEverything = false; + String currTag =""; + + String startString = "<" + parseTag; + String exitString = "" + replacementXML + exitString + ">"; + break; + } + //Stop recording after start string reached. + if(currTag.contains(startString)) + cycle = false; + + + if(cycle) + { + if(firstPass) + { + // add the replacement string + rebuildXML += replacementXML; + + //turn it off + firstPass = false; + } + + rebuildXML += currTag; + //System.out.println("Pre If: " + currTag); + } + + //Start recording after the LAST non-numerical path string is reached. + if(currTag.contains(exitString)) + { + // if(containsNumber != 0) + cycle = true; + + //Mark that we have been through one iteration of the parse tag + //Marking in case we need more in a JSON Array situation. + firstPass = true; + //else + // break; + } + } + + System.out.println(rebuildXML); + JSONObject query = XML.toJSONObject(rebuildXML); + System.out.println(query.toString()); + + if(containsNumber != 0) + { + Object jsquery = query.query(remArr); + //System.out.println(jsquery); + query = (JSONObject) jsquery; + } + + //System.out.println("PrintingJSON"); + + return query; + } + + //[RJ_ADDED] This overloaded static method replces all keys with output + //of keyTransformer output. + public static JSONObject toJSONObject(Reader reader, Function keyTransformer) + { + XMLTokener x = new XMLTokener(reader); + + //rebuild the sub xml + String rebuildXML = ""; + + String currTag =""; + + while (x.more()) { + x.skipPast("<"); + currTag = "<" + x.nextContent(); + + //Current tag holds the tag <> with possible info afterwards. + //1. Extract the first word after opening tag openTag = ",0); + //Get the first word after < in the tag + tag = tag[0].split(" ",0); + + //Handle close toStream(JSONObject obj) + { + /***Takes an already established JSON Object and converts it into + an XML object: **/ + String jsonXML = XML.toString(obj); + + //Now we can play with our XML + // a type of collections so that the Streams can act upon it. + /*************************************************************/ + XMLTokener x = new XMLTokener(jsonXML); + + //rebuild the sub xml + String rebuildXML = ""; + + String currTag =""; + + ArrayList listOfTags = new ArrayList<>(); + + while (x.more()) { + x.skipPast("<"); + currTag = "<" + x.nextContent(); + //System.out.println(currTag); + //Current tag holds the tag <> with possible info afterwards. + //1. Extract the first word after opening tag openTag = command, Consumer errorHandler) + { + + //"Thread run method" - Apply the User-Given function. + Runnable runnable = () -> { + try{ + JSONObject myJSON = toJSONObject(r); + command.apply(myJSON); + } + catch(Exception e) + { + errorHandler.accept(e); + } + + }; + + //"Creating Thread" + Thread thread = new Thread(runnable); + + //"Starting Thread" + thread.start(); + } + /** * Convert a JSONObject into a well-formed, element-normal XML string. * diff --git a/src/test/java/org/json/junit/XMLTest_SWE262.java b/src/test/java/org/json/junit/XMLTest_SWE262.java new file mode 100644 index 000000000..3c1c34d83 --- /dev/null +++ b/src/test/java/org/json/junit/XMLTest_SWE262.java @@ -0,0 +1,472 @@ +package org.json.junit; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertFalse; +import static org.junit.Assert.assertNotEquals; +import static org.junit.Assert.assertTrue; +import static org.junit.Assert.fail; + +import java.io.*; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.util.function.Function; +import java.util.stream.Collectors; + +import org.json.*; +import org.junit.Rule; +import org.junit.Test; +import org.junit.rules.TemporaryFolder; + +public class XMLTest_SWE262 { + /** + * JUnit supports temporary files and folders that are cleaned up after the test. + * https://garygregory.wordpress.com/2010/01/20/junit-tip-use-rules-to-manage-temporary-files-and-folders/ + */ + @Rule + public TemporaryFolder testFolder = new TemporaryFolder(); + + + /** + * Empty JSONObject from a non-XML string. + */ + @Test + public void testMethodOne_singleValue() { + + System.out.println("Rahul Hello World"); + + String expectedStr = + "{\"author\":\"Gambardella, Matthew\"}"; + String actualStr = ""; + + try { + FileReader filereader = new FileReader("src/test/resources/Catalog.xml"); + JSONObject jo = XML.toJSONObject(filereader, new JSONPointer("/catalog/book/0/author")); + + actualStr = jo.toString(); + + System.out.println("Actual: " + actualStr); + System.out.println("Expected: " + expectedStr); + assertEquals(expectedStr, actualStr); + + } catch (FileNotFoundException e) { + System.out.println("File not found"); + e.printStackTrace(); + } + } + + /** + * Empty JSONObject from a non-XML string. + */ + @Test + public void testMethodOne_outerTag() { + + System.out.println("Rahul Hello World"); + + String expectedStr = + " Ralls, Kim\n"+ + " Midnight Rain\n"+ + " Fantasy\n"+ + " 5.95\n"+ + " 2000-12-16\n"+ + " A former architect battles corporate zombies, " + + "an evil sorceress, and her own childhood to become queen " + + "of the world.\n" + + " bk102\n"; + + expectedStr = XML.toJSONObject(expectedStr).toString(); + //expectedStr = expectedStr.replaceAll("\\n", ""); + String actualStr = ""; + + try { + //FileReader filereader = new FileReader("src/test/resources/file.xml"); + //JSONObject jo = XML.toJSONObject(filereader, new JSONPointer("/clinical_study/sponsors/lead_sponsor/agency_class")); + FileReader filereader = new FileReader("src/test/resources/Catalog.xml"); + JSONObject jo = XML.toJSONObject(filereader, new JSONPointer("/catalog/book/1")); + + actualStr = jo.toString(); + //actualStr = actualStr.replaceAll((\\r\\n|\\n|\\r), ""); + + System.out.println("Actual: " + actualStr); + System.out.println("Expected: " + expectedStr); + assertEquals(expectedStr, actualStr); + + } catch (FileNotFoundException e) { + System.out.println("File not found"); + e.printStackTrace(); + } + } + + @Test + public void testMethodTwo_replaceTag() + { + System.out.println("\nIn Test Method 2"); + String expectedStr = "{\"catalog\":{\"tname\":\"rahul jain\"}}"; + + try { + FileReader filereader = new FileReader("src/test/resources/Catalog.xml"); + JSONObject jo = XML.toJSONObject(filereader, new JSONPointer("/catalog/book"), XML.toJSONObject("rahul jain")); + + String actualStr = jo.toString(); + assertEquals(expectedStr, actualStr); + + } catch (FileNotFoundException e) { + System.out.println("File not found"); + e.printStackTrace(); + } + } + + @Test + public void testMethodTwo_replaceAll() + { + System.out.println("\nIn Test Method 2"); + String expectedStr = "{\"tname\":\"rahul jain\"}"; + + try { + FileReader filereader = new FileReader("src/test/resources/Catalog.xml"); + JSONObject jo = XML.toJSONObject(filereader, new JSONPointer("/"), XML.toJSONObject("rahul jain")); + + String actualStr = jo.toString(); + assertEquals(expectedStr, actualStr); + + } catch (FileNotFoundException e) { + System.out.println("File not found"); + e.printStackTrace(); + } + } + + @Test + public void testMethodThree_replaceKey() + { + System.out.println("\nIn Test Method three"); + String expectedStr = "\n" + + "\n" + + " \n" + + " Gambardella, Matthew\n" + + " XML Developer's Guide\n" + + " Computer\n" + + " 44.95\n" + + " 2000-10-01\n" + + " An in-depth look at creating applications\n" + + " with XML.\n" + + " \n" + + " \n" + + " Ralls, Kim\n" + + " Midnight Rain\n" + + " Fantasy\n" + + " 5.95\n" + + " 2000-12-16\n" + + " A former architect battles corporate zombies, an evil sorceress, and her own childhood to become queen of the world.\n" + + " \n" + + " \n" + + " Corets, Eva\n" + + " Maeve Ascendant\n" + + " Fantasy\n" + + " 5.95\n" + + " 2000-11-17\n" + + " After the collapse of a nanotechnology\n" + + " society in England, the young survivors lay the\n" + + " foundation for a new society.\n" + + " \n" + + " \n" + + " Corets, Eva\n" + + " Oberon's Legacy\n" + + " Fantasy\n" + + " 5.95\n" + + " 2001-03-10\n" + + " In post-apocalypse England, the mysterious\n" + + " agent known only as Oberon helps to create a new life\n" + + " for the inhabitants of London. Sequel to Maeve\n" + + " Ascendant.\n" + + " \n" + + " \n" + + " Corets, Eva\n" + + " The Sundered Grail\n" + + " Fantasy\n" + + " 5.95\n" + + " 2001-09-10\n" + + " The two daughters of Maeve, half-sisters,\n" + + " battle one another for control of England. Sequel to\n" + + " Oberon's Legacy.\n" + + " \n" + + " \n" + + " Randall, Cynthia\n" + + " Lover Birds\n" + + " Romance\n" + + " 4.95\n" + + " 2000-09-02\n" + + " When Carla meets Paul at an ornithology\n" + + " conference, tempers fly as feathers get ruffled.\n" + + " \n" + + " \n" + + " Thurman, Paula\n" + + " Splish Splash\n" + + " Romance\n" + + " 4.95\n" + + " 2000-11-02\n" + + " A deep sea diver finds true love twenty\n" + + " thousand leagues beneath the sea.\n" + + " \n" + + " \n" + + " Knorr, Stefan\n" + + " Creepy Crawlies\n" + + " Horror\n" + + " 4.95\n" + + " 2000-12-06\n" + + " An anthology of horror stories about roaches,\n" + + " centipedes, scorpions and other insects.\n" + + " \n" + + " \n" + + " Kress, Peter\n" + + " Paradox Lost\n" + + " Science Fiction\n" + + " 6.95\n" + + " 2000-11-02\n" + + " After an inadvertant trip through a Heisenberg\n" + + " Uncertainty Device, James Salway discovers the problems\n" + + " of being quantum.\n" + + " \n" + + " \n" + + " O'Brien, Tim\n" + + " Microsoft .NET: The Programming Bible\n" + + " Computer\n" + + " 36.95\n" + + " 2000-12-09\n" + + " Microsoft's .NET initiative is explored in\n" + + " detail in this deep programmer's reference.\n" + + " \n" + + " \n" + + " O'Brien, Tim\n" + + " MSXML3: A Comprehensive Guide\n" + + " Computer\n" + + " 36.95\n" + + " 2000-12-01\n" + + " The Microsoft MSXML3 parser is covered in\n" + + " detail, with attention to XML DOM interfaces, XSLT processing,\n" + + " SAX and more.\n" + + " \n" + + " \n" + + " Galos, Mike\n" + + " Visual Studio 7: A Comprehensive Guide\n" + + " Computer\n" + + " 49.95\n" + + " 2001-04-16\n" + + " Microsoft Visual Studio 7 is explored in depth,\n" + + " looking at how Visual Basic, Visual C++, C#, and ASP+ are\n" + + " integrated into a comprehensive development\n" + + " environment.\n" + + " \n" + + ""; + + expectedStr = XML.toJSONObject(expectedStr).toString(); + try { + //Define the function + Function keyTransformer= (x) -> ("RJ_"+x); + FileReader filereader = new FileReader("src/test/resources/Catalog.xml"); + JSONObject jo = XML.toJSONObject(filereader, keyTransformer); + + System.out.println(XML.toString(jo)); + XML.toStream(jo); + + String actualStr = jo.toString(); + //System.out.println(actualStr); + assertEquals(expectedStr, actualStr); + + } catch (FileNotFoundException e) { + System.out.println("File not found"); + e.printStackTrace(); + } + } + + @Test + public void testReplaceKey2() + { + String expectedStr = "\n" + + "\n" + + " rajihul@gmail.com\n" + + ""; + expectedStr = XML.toJSONObject(expectedStr).toString(); + + try { + //Define the function + Function keyTransformer= (x) -> ("SWE262_"+x); + FileReader filereader = new FileReader("src/test/resources/TransformerTest.xml"); + JSONObject jo = XML.toJSONObject(filereader, keyTransformer); + + String actualStr = jo.toString(); + //System.out.println(actualStr); + assertEquals(expectedStr, actualStr); + + } catch (FileNotFoundException e) { + System.out.println("File not found"); + e.printStackTrace(); + } + + } + + @Test + public void testStream() + { + String expectedStr = "rajihul@gmail.com"; + + String Str = "\n" + + "\n" + + " rajihul@gmail.com\n" + + ""; + + //expectedStr = XML.toJSONObject(expectedStr).toString(); + String actualStr = ""; + + try { + //Define the function + //Function keyTransformer= (x) -> ("SWE262_"+x); + FileReader filereader = new FileReader("src/test/resources/TransformerTest.xml"); + JSONObject jo = XML.toJSONObject(Str); + + List trstr = XML.toStream(jo) + // .forEach(x -> x.replace("SWE262","RJ")) + .filter(x->x.contains("SWE262_email")) + .collect(Collectors.toList()); + + for(String i:trstr) + actualStr += i; + + //System.out.println(actualStr); + //System.out.println(actualStr); + assertEquals(expectedStr, actualStr); + + } catch (FileNotFoundException e) { + System.out.println("File not found"); + e.printStackTrace(); + } + } + @Test + public void testStream2() + { + String expectedStr = ""; + + String Str = "\n" + + "\n" + + " rajihul@gmail.com\n" + + ""; + + //expectedStr = XML.toJSONObject(expectedStr).toString(); + String actualStr = ""; + + try { + //Define the function + //Function keyTransformer= (x) -> ("SWE262_"+x); + FileReader filereader = new FileReader("src/test/resources/TransformerTest.xml"); + JSONObject jo = XML.toJSONObject(Str); + + List trstr = XML.toStream(jo) + // .forEach(x -> x.replace("SWE262","RJ")) + .filter(x->!x.contains("SWE262_email")) + .collect(Collectors.toList()); + + for(String i:trstr) + actualStr += i; + + System.out.println(actualStr); + //System.out.println(actualStr); + assertEquals(expectedStr, actualStr); + + } catch (FileNotFoundException e) { + System.out.println("File not found"); + e.printStackTrace(); + } + } + + /** For Milestone 5 **/ + @Test + public void async() + { + String expectedStr = ""; + //Generate output.txt + try + { + FileReader filereader = new FileReader("src/test/resources/Catalog.xml"); + FileWriter filewriter = new FileWriter("output.json"); + XML.toJSONObject(filereader, (JSONObject joo) -> joo.write(filewriter), (Exception e)-> e.printStackTrace()); + //XML.toJSONObject(); + expectedStr = XML.toJSONObject(filereader).toString(); + + + //Give thread adequate time to finish + try{ + Thread.sleep(1000); + + }catch(InterruptedException e) + { + e.printStackTrace(); + } + + //filewriter.flush(); + filewriter.close(); + }catch(IOException e) + { + e.printStackTrace(); + } + + //Compare the output.txt to the Catalog.xml JSON + try + { + FileReader filereader = new FileReader("output.json"); + JSONObject actualJSON = XML.toJSONObject(filereader); + assertEquals(expectedStr, actualJSON.toString()); + + }catch(IOException e) + { + e.printStackTrace(); + } + + } + + /** For Milestone 5 **/ + @Test + public void async_exception() + { + String expectedStr = ""; + //Generate output.txt + try + { + //The baddata file doens't have closing tag so should throw exception + FileReader filereader = new FileReader("src/test/resources/baddata.xml"); + FileWriter filewriter = new FileWriter("output.json"); + XML.toJSONObject(filereader, (JSONObject joo) -> joo.write(filewriter), (Exception e)-> System.out.println("Something went wrong!")); + //XML.toJSONObject(); + expectedStr = XML.toJSONObject(filereader).toString(); + + + //Give thread adequate time to finish + try{ + Thread.sleep(1000); + + }catch(InterruptedException e) + { + e.printStackTrace(); + } + + //filewriter.flush(); + filewriter.close(); + }catch(IOException e) + { + e.printStackTrace(); + } + + //Compare the output.txt to the Catalog.xml JSON + try + { + FileReader filereader = new FileReader("output.json"); + JSONObject actualJSON = XML.toJSONObject(filereader); + assertEquals(expectedStr, actualJSON.toString()); + + }catch(IOException e) + { + e.printStackTrace(); + } + + } + +} diff --git a/src/test/resources/Catalog.xml b/src/test/resources/Catalog.xml new file mode 100644 index 000000000..96fb8546f --- /dev/null +++ b/src/test/resources/Catalog.xml @@ -0,0 +1,118 @@ + + + + Gambardella, Matthew + XML Developer's Guide + Computer + 44.95 + 2000-10-01 + An in-depth look at creating applications + with XML. + + + Ralls, Kim + Midnight Rain + Fantasy + 5.95 + 2000-12-16 + A former architect battles corporate zombies, an evil sorceress, and her own childhood to become queen of the world. + + + Corets, Eva + Maeve Ascendant + Fantasy + 5.95 + 2000-11-17 + After the collapse of a nanotechnology + society in England, the young survivors lay the + foundation for a new society. + + + Corets, Eva + Oberon's Legacy + Fantasy + 5.95 + 2001-03-10 + In post-apocalypse England, the mysterious + agent known only as Oberon helps to create a new life + for the inhabitants of London. Sequel to Maeve + Ascendant. + + + Corets, Eva + The Sundered Grail + Fantasy + 5.95 + 2001-09-10 + The two daughters of Maeve, half-sisters, + battle one another for control of England. Sequel to + Oberon's Legacy. + + + Randall, Cynthia + Lover Birds + Romance + 4.95 + 2000-09-02 + When Carla meets Paul at an ornithology + conference, tempers fly as feathers get ruffled. + + + Thurman, Paula + Splish Splash + Romance + 4.95 + 2000-11-02 + A deep sea diver finds true love twenty + thousand leagues beneath the sea. + + + Knorr, Stefan + Creepy Crawlies + Horror + 4.95 + 2000-12-06 + An anthology of horror stories about roaches, + centipedes, scorpions and other insects. + + + Kress, Peter + Paradox Lost + Science Fiction + 6.95 + 2000-11-02 + After an inadvertant trip through a Heisenberg + Uncertainty Device, James Salway discovers the problems + of being quantum. + + + O'Brien, Tim + Microsoft .NET: The Programming Bible + Computer + 36.95 + 2000-12-09 + Microsoft's .NET initiative is explored in + detail in this deep programmer's reference. + + + O'Brien, Tim + MSXML3: A Comprehensive Guide + Computer + 36.95 + 2000-12-01 + The Microsoft MSXML3 parser is covered in + detail, with attention to XML DOM interfaces, XSLT processing, + SAX and more. + + + Galos, Mike + Visual Studio 7: A Comprehensive Guide + Computer + 49.95 + 2001-04-16 + Microsoft Visual Studio 7 is explored in depth, + looking at how Visual Basic, Visual C++, C#, and ASP+ are + integrated into a comprehensive development + environment. + + \ No newline at end of file diff --git a/src/test/resources/TransformerTest.xml b/src/test/resources/TransformerTest.xml new file mode 100644 index 000000000..cef50a89c --- /dev/null +++ b/src/test/resources/TransformerTest.xml @@ -0,0 +1,4 @@ + + + rajihul@gmail.com + \ No newline at end of file diff --git a/src/test/resources/baddata.xml b/src/test/resources/baddata.xml new file mode 100644 index 000000000..4c684918e --- /dev/null +++ b/src/test/resources/baddata.xml @@ -0,0 +1,11 @@ + + + + Gambardella, Matthew + XML Developer's Guide + Computer + 44.95 + 2000-10-01 + An in-depth look at creating applications + with XML. + \ No newline at end of file diff --git a/src/test/resources/file.xml b/src/test/resources/file.xml new file mode 100644 index 000000000..b38836331 --- /dev/null +++ b/src/test/resources/file.xml @@ -0,0 +1,36 @@ + + + + 11ClinicalTrials.gov processed this data on July 19, 2020 + Link to the current ClinicalTrials.gov record. + https://clinicaltrials.gov/show/NCT03874338 + + + 22ClinicalTrials.gov processed this data on July 19, 2020 + Link to the current ClinicalTrials.gov record. + https://clinicaltrials.gov/show/NCT03874338 + + + ClinicalTrials.gov processed this data on July 19, 2020 + Link to the current ClinicalTrials.gov record. + https://clinicaltrials.gov/show/NCT03874338 + + raji date caji + Link to the current ClinicalTrials.gov record. + https://clinicaltrials.gov/show/NCT03874338 + + + + NYU Langone Health + Other + + + Population Health Research Institute + Other + + + National Heart, Lung, and Blood Institute (NHLBI) + NIH + + +