“Inhoud is niet toegestaan in prolog” bij het ontleden van perfect geldige XML op GAE

Ik heb de afgelopen 48 uur mijn hoofd geslagen tegen deze absoluut irritante bug, dus ik dacht dat ik eindelijk de handdoek in de ring zou gooien en het hier zou proberen te vragen voordat ik mijn laptop uit het raam gooi.

Ik probeer de respons-XML te ontleden van een aanroep die ik heb gedaan naar AWS SimpleDB. Het antwoord komt prima terug op de draad; het kan er bijvoorbeeld zo uitzien:

<?xml version="1.0" encoding="utf-8"?> 
<ListDomainsResponse xmlns="http://sdb.amazonaws.com/doc/2009-04-15/">
    <ListDomainsResult>
        <DomainName>Audio</DomainName>
        <DomainName>Course</DomainName>
        <DomainName>DocumentContents</DomainName>
        <DomainName>LectureSet</DomainName>
        <DomainName>MetaData</DomainName>
        <DomainName>Professors</DomainName>
        <DomainName>Tag</DomainName>
    </ListDomainsResult>
    <ResponseMetadata>
        <RequestId>42330b4a-e134-6aec-e62a-5869ac2b4575</RequestId>
        <BoxUsage>0.0000071759</BoxUsage>
    </ResponseMetadata>
</ListDomainsResponse>

Ik geef deze XML door aan een parser met

XMLEventReader eventReader = xmlInputFactory.createXMLEventReader(response.getContent());

en bel eventReader.nextEvent();een aantal keren om de gewenste gegevens te krijgen.

Hier is het bizarre-onderdeel – het werkt geweldig in de lokale server. Het antwoord komt binnen, ik parseer het, iedereen is blij. Het probleem is dat wanneer ik de code inzet naar Google App Engine, het uitgaande verzoek nog steeds werkt, en de respons XML lijkt 100% identiek en correct voor mij, maar het antwoord is niet vol met de volgende uitzondering:

com.amazonaws.http.HttpClient handleResponse: Unable to unmarshall response (ParseError at [row,col]:[1,1]
Message: Content is not allowed in prolog.): <?xml version="1.0" encoding="utf-8"?> 
<ListDomainsResponse xmlns="http://sdb.amazonaws.com/doc/2009-04-15/"><ListDomainsResult><DomainName>Audio</DomainName><DomainName>Course</DomainName><DomainName>DocumentContents</DomainName><DomainName>LectureSet</DomainName><DomainName>MetaData</DomainName><DomainName>Professors</DomainName><DomainName>Tag</DomainName></ListDomainsResult><ResponseMetadata><RequestId>42330b4a-e134-6aec-e62a-5869ac2b4575</RequestId><BoxUsage>0.0000071759</BoxUsage></ResponseMetadata></ListDomainsResponse>
javax.xml.stream.XMLStreamException: ParseError at [row,col]:[1,1]
Message: Content is not allowed in prolog.
    at com.sun.org.apache.xerces.internal.impl.XMLStreamReaderImpl.next(Unknown Source)
    at com.sun.xml.internal.stream.XMLEventReaderImpl.nextEvent(Unknown Source)
    at com.amazonaws.transform.StaxUnmarshallerContext.nextEvent(StaxUnmarshallerContext.java:153)
    ... (rest of lines omitted)

Ik heb deze XML dubbel, drievoudig, viervoudig gecontroleerd op ‘onzichtbare tekens’ of niet-UTF8-gecodeerde tekens, enz. Ik heb het byte-by-byte bekeken in een array voor byte-volgorde-markeringen of iets van dien aard . Niks; het doorstaat elke validatietest die ik erop zou kunnen gooien. Nog vreemder, het gebeurt als ik ook een op Saksen gebaseerde parser gebruik — maar ALLEEN op GAE werkt het altijd prima in mijn lokale omgeving.

Het maakt het erg moeilijk om de code te traceren voor problemen wanneer ik de debugger alleen kan uitvoeren in een omgeving die perfect werkt (ik heb geen goede manier gevonden om op afstand fouten te debuggen op GAE). Desalniettemin heb ik met de primitieve middelen die ik heb, een miljoen benaderingen geprobeerd, waaronder:

  • XML met en zonder de proloog
  • Met en zonder nieuwe regels
  • Met en zonder het kenmerk “encoding=” in de proloog
  • Beide stijlen voor nieuwe regels
  • Met en zonder de chunking-informatie die aanwezig is in de HTTP-stream

En ik heb de meeste hiervan in meerdere combinaties geprobeerd, waarbij het logisch was dat ze zouden interageren — niets! Ik ben aan het eind van mijn Latijn. Heeft iemand een probleem als dit eerder gezien dat er hopelijk enig licht op kan werpen?

Bedankt!


Antwoord 1, autoriteit 100%

De codering in uw XML en XSD (of DTD) is anders.
XML-bestandskop: <?xml version='1.0' encoding='utf-8'?>
Koptekst XSD-bestand: <?xml version='1.0' encoding='utf-16'?>

Een ander mogelijk scenario dat dit veroorzaakt, is wanneer er iets vóór de declaratie van het XML-documenttype komt. d.w.z. je zou zoiets in de buffer kunnen hebben:

helloworld<?xml version="1.0" encoding="utf-8"?>  

of zelfs een spatie of speciaal teken.

Er zijn enkele speciale tekens die bytevolgordemarkeringen worden genoemd en die zich in de buffer kunnen bevinden.
Doe dit voordat u de buffer doorgeeft aan de Parser…

String xml = "<?xml ...";
xml = xml.trim().replaceFirst("^([\\W]+)<","<");

Antwoord 2, autoriteit 7%

Ik had een probleem bij het inspecteren van het xml-bestand in notepad++ en het opslaan van het bestand, hoewel ik de top utf-8 xml-tag had als <?xml version="1.0" encoding="utf-8"?>

Opgelost door het bestand op te slaan in notpad++ met Encoding(Tab) > Coderen in UTF-8:selected (was coderen in UTF-8-BOM)


Antwoord 3, autoriteit 5%

Deze foutmelding wordt altijd veroorzaakt door de ongeldige XML-inhoud in het beginelement. Bijvoorbeeld een extra kleine punt “.” aan het begin van het XML-element.

Alle tekens vóór de “<?xml….” veroorzaken het bovenstaande “org.xml.sax.SAXParseException: Content is not allowed in prolog“-foutbericht .

Een kleine punt “.” voor de “<?xml….

Om het op te lossen, verwijdert u gewoon al die rare tekens vóór de “<?xml“.

Ref: http://www .mkyong.com/java/sax-error-content-is-not-allowed-in-prolog/


Antwoord 4, autoriteit 4%

Ik had hetzelfde probleem. In mijn geval werden XML-bestanden gegenereerd vanuit het c#-programma en ingevoerd in AS400 voor verdere verwerking. Na wat analyse bleek dat ik UTF8-codering gebruikte tijdens het genereren van XML-bestanden, terwijl javac (in AS400) “UTF8 zonder stuklijst” gebruikt.
Dus moest ik extra code schrijven zoals hieronder vermeld:

//create encoding with no BOM
Encoding outputEnc = new UTF8Encoding(false); 
//open file with encoding
TextWriter file = new StreamWriter(filePath, false, outputEnc);           
file.Write(doc.InnerXml);
file.Flush();
file.Close(); // save and close it

Antwoord 5, autoriteit 3%

Ik kreeg vandaag dezelfde foutmelding.
De oplossing was om het document te wijzigen van UTF-8 met stuklijst naar UTF-8 zonder stuklijst


Antwoord 6

In mijn xml-bestand zag de kop er als volgt uit:

<?xml version="1.0" encoding="utf-16"? />

In een testbestand las ik de bestandsbytes en decodeerde ik de gegevens als UTF-8 (niet beseffend dat de header in dit bestand utf-16 was) om een string te maken.

byte[] data = Files.readAllBytes(Paths.get(path));
String dataString = new String(data, "UTF-8");

Toen ik probeerde deze string te deserialiseren in een object, kreeg ik dezelfde fout te zien:

javax.xml.stream.XMLStreamException: ParseError at [row,col]:[1,1]
Message: Content is not allowed in prolog.

Toen ik de tweede regel update naar

String dataString = new String(data, "UTF-16");

Ik kon het object prima deserialiseren. Dus zoals Romain hierboven had opgemerkt, moeten de coderingen overeenkomen.


Antwoord 7

Het verwijderen van de xml-declaratie loste het op

<?xml version='1.0' encoding='utf-8'?>

Antwoord 8

Ik had hetzelfde probleem met de naam “Inhoud is niet toegestaan in prolog” in mijn xml-bestand.

Oplossing

Aanvankelijk was mijn hoofdmap ‘#Bestandsnaam‘.

Toen ik het eerste teken ‘#’ verwijderde, werd de fout opgelost.

Het is niet nodig om de #bestandsnaam te verwijderen…
Probeer het op deze manier..

Gebruik een FileInputStream in plaats van een File- of URL-object door te geven aan de unmarshaller-methode.

File myFile = new File("........");
Object obj = unmarshaller.unmarshal(new FileInputStream(myFile));

Antwoord 9

Onverwachte reden: #teken in bestandspad

Vanwege een interne bug verschijnt de fout Inhoud is niet toegestaan in proloogook als de bestandsinhoud zelf 100% correct is, maar u de bestandsnaam opgeeft zoals C:\Data\#22\file.xml.

Dit is mogelijk ook van toepassing op andere speciale tekens.

Hoe te controleren:als u uw bestand naar een pad zonder speciale tekens verplaatst en de fout verdwijnt, dan was dit dit probleem.


Antwoord 10

Ik had een tab-teken in plaats van spaties.
Het vervangen van het tabblad ‘\t’ loste het probleem op.

Knip en plak het hele document in een editor zoals Notepad++ en toon alle tekens.


Antwoord 11

In mijn geval van het probleem was de oplossing om Duitse umlauts (äöü) te vervangen door hun HTML-equivalenten…


Antwoord 12

hieronder is de oorzaak boven de uitzondering “org.xml.sax.SAXParseException: Inhoud is niet toegestaan in prolog”.

  1. Controleer eerst het bestandspad van schema.xsd en file.xml.
  2. De codering in uw XML en XSD (of DTD) moet hetzelfde zijn.
    XML-bestandskop: <?xml version='1.0' encoding='utf-8'?>
    Koptekst XSD-bestand: <?xml version='1.0' encoding='utf-8'?>
  3. als er iets voor de XML-documenttypedeclaratie komt.i.e: hello<?xml version='1.0' encoding='utf-16'?>

Antwoord 13

In de geest van “verwijder al die rare tekens voor de <?xml”, hier is mijn Java-code, die goed werkt met invoer via een BufferedReader:

   BufferedReader test = new BufferedReader(new InputStreamReader(fisTest));
    test.mark(4);
    while (true) {
        int earlyChar = test.read();
        System.out.println(earlyChar);
        if (earlyChar == 60) {
            test.reset();
            break;
        } else {
            test.mark(4);
        }
    }

FWIW, de bytes die ik zag zijn (in decimaal): 239, 187, 191.


Antwoord 14

Ik heb de xml in een Mac OS gezipt en naar een Windows-machine gestuurd, de standaardcompressie verandert deze bestanden, dus de codering heeft dit bericht verzonden.

Other episodes