Rest-Assured XSD References Other XSDs

2019-08-02 21:09发布

问题:

I am programming an XML validator according to schemas using Rest-Assured. However, I am having trouble handling XSDs that reference other XSDs, because I retrieve the original XSD from a URL using GET.

I have been trying to implement my own parsing to consolidate the XSDs(Strings) into one XSD(String), but it is becoming a recursive monster, and extremely inefficient/difficult. To see the algorithm, look at the end of the post.

I have two questions: 1) My problem is that I am using GET to retrieve the XSD, so it's not within the namespace. Is there a way to GET all referenced XSDs and consolidate them using Rest-Assured? I wouldn't have a clue about how to go about this.

2) Is there a better way to handle includes in general? As you can see, my algorithm is very costly and overcomplicated (especially the ref attribute), and I'm sure something will break easily if I change my test cases.

My algorithm(Pseudo-Code to avoid complexity) so far is like the following:

boolean xmlValid(String xmlAddress, String xsdAddress){

    LinkedList XSDList = new LinkedList;
    XSDList.add(xsdAddress);
    xsdString = getExternalXSDStrings(XSDList);

    try{ //No PseudoCode here
       RestAssured.expect().
            statusCode(200).
            body(
                    RestAssuredMatchers.matchesXsd(xsdString)).
            when().
            get(xmlAddress);
    }catch Exceptions{...}
}

String getExternalXSDStrings(LinkedList xsdReferences, String prevString){
    LinkedList recursiveXSDReferences = new LinkedList();

    for(xsdRef:xsdReferences){
         xsdAddress = "http://..." + xsdRef;
         Open InputStream From URL;
         while(inputLine != null){

             if(prologFlag) //Do Nothing, this is to avoid multiple prologs ;

             else if(includeFlag){

                 if(refFlag) Note Reference;
                 else recursiveXSDReferences.add(includeReference);

             }else if(refFlag){

                 referenceDefinition = Extract Reference Element Definition;
                 xsdString = xsdString + referenceDefinition;

             }else{
                 xsdString = xsdString + inputLine;
             }
         }
         Close input stream;
    }
    xsdString = prevString + xsdString;
    if(xsdReferences.length > 0) return getExternalXSDStrings(recursiveXSDReferences , xsdString);
    else return xsdString;
}

Thank you very much in advance!

回答1:

Perhaps can make use of the XmlConfig in detailed configuration. This gives you access to configure features and namespaces etc. For example if you want to disable the loading of external DTD's you could do:

given().config(RestAssured.config().xmlConfig(xmlConfig().disableLoadingOfExternalDtd())). .. 

So perhaps you could look in the "disableLoadingOfExternalDtd" method to see how it's implemented to get some hints.