org.xml.sax.SAXParseException: Вміст заборонений у prolog


161

У мене на веб-службі Java підключений клієнт веб-служби Java (реалізований на основі Axis1).

У моєму файлі журналу я отримую такий виняток:

Caused by: org.xml.sax.SAXParseException: Content is not allowed in prolog.
    at org.apache.xerces.util.ErrorHandlerWrapper.createSAXParseException(Unknown Source)
    at org.apache.xerces.util.ErrorHandlerWrapper.fatalError(Unknown Source)
    at org.apache.xerces.impl.XMLErrorReporter.reportError(Unknown Source)
    at org.apache.xerces.impl.XMLErrorReporter.reportError(Unknown Source)
    at org.apache.xerces.impl.XMLScanner.reportFatalError(Unknown Source)
    at org.apache.xerces.impl.XMLDocumentScannerImpl$PrologDispatcher.dispatch(Unknown Source)
    at org.apache.xerces.impl.XMLDocumentFragmentScannerImpl.scanDocument(Unknown Source)
    at org.apache.xerces.parsers.XML11Configuration.parse(Unknown Source)
    at org.apache.xerces.parsers.XML11Configuration.parse(Unknown Source)
    at org.apache.xerces.parsers.XMLParser.parse(Unknown Source)
    at org.apache.xerces.parsers.AbstractSAXParser.parse(Unknown Source)
    at javax.xml.parsers.SAXParser.parse(Unknown Source)
    at org.apache.axis.encoding.DeserializationContext.parse(DeserializationContext.java:227)
    at org.apache.axis.SOAPPart.getAsSOAPEnvelope(SOAPPart.java:696)
    at org.apache.axis.Message.getSOAPEnvelope(Message.java:435)
    at org.apache.ws.axis.security.WSDoAllReceiver.invoke(WSDoAllReceiver.java:114)
    at org.apache.axis.strategies.InvocationStrategy.visit(InvocationStrategy.java:32)
    at org.apache.axis.SimpleChain.doVisiting(SimpleChain.java:118)
    at org.apache.axis.SimpleChain.invoke(SimpleChain.java:83)
    at org.apache.axis.client.AxisClient.invoke(AxisClient.java:198)
    at org.apache.axis.client.Call.invokeEngine(Call.java:2784)
    at org.apache.axis.client.Call.invoke(Call.java:2767)
    at org.apache.axis.client.Call.invoke(Call.java:2443)
    at org.apache.axis.client.Call.invoke(Call.java:2366)
    at org.apache.axis.client.Call.invoke(Call.java:1812)

11
Це допоможе, якби ви показали нам XML, який ви намагаєтеся розібрати. (Очікується, саме перші кілька рядків зробили б.)
Стівен C,

Дякую, Стівен, я намагаюсь отримати XML-запит із рамки AXIS і вставити його сюди. Тож загальне розуміння вищезгаданої помилки XML не сформовано.
ag112

У мене виникла ця проблема, тому що я намагався перетворити ім'я рядка файлу xml, а не файл xml як рядок! : P
Гаʀʀʏ

Відповіді:


242

Часто це викликано пробілом перед декларацією XML, але це може бути будь-який текст , як тире або будь-який символ. Я кажу, що це часто викликано білим простором, тому що люди припускають, що простір завжди ігнорується, але це не так.


Інша справа , що часто відбувається це UTF-8 BOM (порядок байт знак), який буде дозволений до декларації XML можна розглядати як пробіл , якщо документ передається у вигляді потоку символів в XML - парсер , а не як потік байт .

Це може статися, якщо для перевірки файлу xml використовуються файли схем (.xsd), а один із файлів схеми має BOM UTF-8 .


17
Для всіх, як я, хто намагається зрозуміти, що робити з Джоном Хамфрісом - пропозиція w00te: змінити Document document = documentBuilder.parse(new InputSource(new StringReader(xml)))наDocument document = documentBuilder.parse(new InputSource(new ByteArrayInputStream(xml.getBytes("UTF-8"))))
RealMan

32

Власне, крім посади Юрія Зубарева

Коли ви передасте неіснуючий XML-файл для розбору. Наприклад, ви проходите

new File("C:/temp/abc")

коли у вашій файловій системі існує лише файл C: /temp/abc.xml

В будь-якому випадку

builder = DocumentBuilderFactory.newInstance().newDocumentBuilder();
document = builder.parse(new File("C:/temp/abc"));

або

DOMParser parser = new DOMParser();
parser.parse("file:C:/temp/abc");

Усі дають однакове повідомлення про помилку.

Дуже розчаровує помилка, адже наступний слід

javax.servlet.ServletException
    at org.apache.xerces.parsers.DOMParser.parse(Unknown Source)
...
Caused by: org.xml.sax.SAXParseException: Content is not allowed in prolog.
... 40 more

нічого не говорить про факт "ім'я файлу невірно" або "такий файл не існує". У моєму випадку у мене був абсолютно правильний XML-файл і мені довелося витратити 2 дні, щоб визначити справжню проблему.


Те саме зі спробою розбору каталогу замість імені файлу, FWIW.
rogerdpack

... @ Egor, тому всі ненавидять XML. Втратити 2 дні роботи за таку дурну невдачу ..
Gewure

Абсолютно згідний @Gewure :) Це був якийсь древній пост з 2012 року, і я навіть про нього забуваю, але правда
Єгор

1
Це також трапляється, коли у вас є правильний шлях, але зі спеціальними символами, наприклад: C: \ # MyFolder \ My.XML Файл існує, але "#" приносить проблему парсеру XML ... Самій Java, а також M $ Windows, не має жодних проблем з цим ім'ям папки .... Дуже погана поведінка повідомлення про виняток ....
Alex

26

Спробуйте додати пробіл між encoding="UTF-8"рядком у пролозі та завершенням ?>. У XML пролог позначає цей елемент, обмежений знаком запитання, розміщеним на початку документа (тоді як тег prolog у stackoverflow відноситься до мови програмування).

Додано: Це тире перед вашою частиною документа прологу? Це було б помилка там, маючи дані перед прологом, -<?xml version="1.0" encoding="UTF-8"?>.


1
+1. Я виявив, що деякі XML-аналізатори переважають цим винятком, навіть коли пролог XML містить пробіли - тому, я думаю, напевно варто перевірити, чи ніщо не передує <?xml ver...біту.

11

У мене була та сама проблема (і вирішена) під час спроби розбору XML-документа з freemarker.

Я не мав пробілів перед заголовком XML-файла.

Проблема виникає тоді, коли і лише тоді, коли кодування файлу та атрибут кодування XML відрізняються. (напр .: файл UTF-8 з атрибутом UTF-16 у заголовку).

Тож у мене було два шляхи вирішення проблеми:

  1. зміна кодування самого файлу
  2. зміна заголовка UTF-16 на UTF-8

1
Я думаю, що в цілому будь-який випадок, коли аналізатор отримує суперечливу інформацію про кодування символів, може викликати цю проблему.
Raedwald

9

Це означає, що XML неправильно сформований або орган відповіді зовсім не є XML-документом.


Я перевірив і схоже, що XML добре сформований. Ось знімок: - <? Xml version = "1.0" encoding = "UTF-8"?> <Soapenv: Конверт xmlns: soapenv = " schemas.xmlsoap.org/soap/envelope " xmlns: xsd = " w3.org/ 2001 / XMLSchema "xmlns: xsi =" w3.org/2001/XMLSchema-instance "> <soapenv: Header> <wsse: Security xmlns: wsse =" docs.oasis-open.org/wss/2004/01/… " soapenv: mustUnderstand = "1"> .... </ wsse: Security> </ soapenv: Header> <soapenv: Body> .XX .. </ soapenv: Body> </ soapenv: Envelope>
ag112

1
Так, якщо попереду є тире, він би порушив XML.
Юрій Зубарев

7

Щойно витратив 4 години на відстеження подібної проблеми в WSDL. Виявляється, WSDL використовував XSD, який імпортує іншу область імен XSD. Цей імпортований XSD містив наступне:

<?xml version="1.0" encoding="UTF-8"?>
<schema targetNamespace="http://www.xyz.com/Services/CommonTypes" elementFormDefault="qualified"
    xmlns="http://www.w3.org/2001/XMLSchema" 
    xmlns:xsd="http://www.w3.org/2001/XMLSchema"
    xmlns:CommonTypes="http://www.xyz.com/Services/CommonTypes">

 <include schemaLocation=""></include>  
    <complexType name="RequestType">
        <....

Зверніть увагу на порожній includeелемент! Це був корінь моїх неприємностей. Я здогадуюсь, що це зміна файлу Егора, не знайденого вище.

+1 до невтішних повідомлень про помилки.


4

У моєму випадку видалення атрибута 'encoding = "UTF-8" взагалі спрацювало.

Це схоже на проблему кодування набору символів, можливо, тому що ваш файл насправді не знаходиться в UTF-8.


4

Моя відповідь, мабуть, не допоможе вам, але загалом це допоможе.

Коли ви бачите такий виняток, вам слід спробувати відкрити свій XML-файл у будь-якому Hex Editor, а колись ви можете побачити додаткові байти на початку файлу, який текстовий редактор не відображає.

Видаліть їх, і ваш XML буде проаналізований


4

Іноді це код, а не XML

Наступний код,

Document doc = dBuilder.parse(new InputSource(new StringReader("file.xml")));

це також призведе до цієї помилки,

[Фатальна помилка]: 1: 1: вміст заборонено в prolog.org.xml.sax.SAXParseException; рядокNumber: 1; колонкаNumber: 1; Вміст заборонений у prolog.

тому що він намагається проаналізувати літеральний рядок "file.xml"(а не вміст file.xmlфайлу) і зазнає невдачі, тому що "file.xml"як рядок недостатньо сформований XML.

Виправлення: Видалити StringReader():

Document doc = dBuilder.parse(new InputSource("file.xml"));

Аналогічно, проблеми з брудним буфером можуть залишити залишковий мотлох перед фактичним XML. Якщо ви ретельно перевірили свій XML і все ще отримуєте цю помилку, запишіть точний вміст, який передається в аналізатор; іноді дивує те, що насправді буває (намагався проаналізувати).


1
Це рішення орієнтувалося на правильний шлях, оскільки я забув додати applicaionContext.xmlшлях у код, і не перевіряв код шукав помилку лише у XML-файлі
Mrinmoy

3

Спочатку чистий проект, потім реконструкція проекту. Я також стикався з тим же питанням. Після цього все вийшло добре.


2

Якщо все інше не вдається, відкрийте файл у двійковому форматі, щоб переконатися, що на початку файлу немає смішних символів [3 символи, які не можна роздрукувати, які ідентифікують файл як utf-8]. Ми це зробили і знайшли. тому ми перетворили файл з utf-8 в ascii і він працював.


2

З цих же проблем я видалив наступний рядок,

  File file = new File("c:\\file.xml");
  InputStream inputStream= new FileInputStream(file);
  Reader reader = new InputStreamReader(inputStream,"UTF-8");
  InputSource is = new InputSource(reader);
  is.setEncoding("UTF-8");

Це прекрасно працює. Не так точно, чому UTF-8 створює проблеми. Щоб утримати мене в шоці, він чудово працює і для UTF-8.

Я використовую Windows-7 32-бітний і Netbeans IDE з Java * jdk1.6.0_13 *. Поняття не маю, як це працює.


2

Як вже зазначав Майк Соколов, однією з можливих причин є наявність деяких тегів (наприклад, пробілу) перед тегом.

Якщо ваш вхідний XML читається як String (на відміну від байтового масиву), ви можете використовувати заміну вхідної рядки кодом нижче, щоб переконатися, що всі "непотрібні" символи перед тегом xml видаляються.

inputXML=inputXML.substring(inputXML.indexOf("<?xml"));

Ви повинні бути впевнені, що вхідний xml починається з тега xml.


2

У моєму випадку web.xml у моєму додатку має додатковий простір навіть після того, як я видалив не працював, мені довелося повернути чеки та його виправлення, і так, я грав у logc.properties та web.xml у своєму tomcat, але навіть після того, як я повернув помилка відображалася, тому це виправлено)).

додатковий простір

Щоб бути конкретним, я спробував додати org.apache.catalina.filters.ExpiresFilter.level = FINE стек над потоком щось про logging.properties


1

Я дотримувався наведених тут інструкцій, і я отримав ту ж помилку.

Я спробував вирішити це декілька речей (тобто змінити кодування, ввести XML-файл, а не скопіювати його ect) у Notepad та XML Notepad, але нічого не вийшло.

Проблему вирішили, коли я редагував і зберігав свій XML-файл у Notepad ++ (кодування -> utf-8 без BOM)


1

Для всіх тих, хто отримує цю помилку: ПОПЕРЕДЖЕННЯ: Catalina.start за допомогою conf / server.xml: Вміст заборонений у prolog.

Не дуже інформативно .. але що це насправді означає, що у вашому файлі conf / server.xml є сміття.

Я бачив цю точну помилку в інших XML-файлах. Ця помилка може бути викликана внесенням змін до текстового редактора, який вводить сміття.

Те, як ви можете перевірити, чи є у вас сміття у файлі, - це відкрити його за допомогою "HEX Editor". Якщо перед цим рядком ви бачите будь-який символ

     "<?xml version="1.0" encoding="UTF-8"?>"

як би це сміття

     "‰ŠŒ<?xml version="1.0" encoding="UTF-8"?>"

це ваша проблема .... Рішення полягає у використанні хорошого редактора HEX .. Такого, який дозволить вам зберігати файли з різними типами кодування ..

Тоді просто збережіть його як UTF-8. Деякі системи, які використовують файли XML, можуть потребувати його збереження як UTF NO BOM, що означає "NO Byte Order Mark"

Сподіваюся, це допомагає комусь там !!



1

Щоб виправити проблему BOM в системах Unix / Linux:

  1. Перевірте, чи є небажаний символ BOM: hexdump -C myfile.xml | more небажаний символ BOM з'явиться на початку файлу як...<?xml>

  2. Крім того, зробіть file myfile.xml. Файл із символом BOM з'явиться як:myfile.xml: XML 1.0 document text, UTF-8 Unicode (with BOM) text

  3. Виправити один файл за допомогою: tail -c +4 myfile.xml > temp.xml && mv temp.xml myfile.xml

  4. Повторіть 1 або 2, щоб перевірити, чи файл був оздоровлений. Напевно, також розумно зробити view myfile.xmlперевірку вмісту залишився.

Ось базовий сценарій для очищення цілої папки файлів XML:

#!/usr/bin/env bash

# This script is to sanitise XML files to remove any BOM characters

has_bom() { head -c3 "$1" | LC_ALL=C grep -qe '\xef\xbb\xbf'; }

for filename in *.xml ; do
  if has_bom ${filename}; then
    tail -c +4 ${filename} > temp.xml
    mv temp.xml ${filename}
  fi
done

0

Просто додаткова думка щодо цього на майбутнє. Отримати цю помилку може так, коли ви просто натискаєте клавішу видалення або якусь іншу клавішу випадковим чином, коли вони мають вікно XML як активний дисплей і не звертають уваги. Це сталося зі мною раніше з файлом struts.xml у моєму веб-додатку. Незграбні лікті ...


Я переконався, що я не натискаю жодної клавіші
Mad-D

0

Я теж отримував те саме

XML reader error: javax.xml.stream.XMLStreamException: ParseError at [row,col]:[1,2] Message: Reference is not allowed in prolog.

, коли моя програма створювала відповідь XML на виклик веб-сервісу RestFull. Під час створення рядка формату XML я замінив & lt і & gt на <і>, тоді помилка зникла, і я отримав належну відповідь. Не впевнений, як це працювало, але це спрацювало.

зразок :

String body = "<ns:addNumbersResponse xmlns:ns=\"http://java.duke.org\"><ns:return>"
            +sum
            +"</ns:return></ns:addNumbersResponse>";

0

У мене було те саме питання.

Спочатку я завантажив XML-файл на місцевий робочий стіл, і я потрапив Content is not allowed in prologпід час імпорту файлу на сервер порталу. Навіть візуально файл виглядав добре для мене, але якось він зіпсований.

Тому я повторно завантажив той самий файл і спробував той самий, і він спрацював.


0

У нас була така ж проблема нещодавно, і виявилося, що це випадки неправильної URL-адреси, а отже, стандартної відповіді HTTP 403 (що очевидно не є дійсною XML, яку клієнт шукав). Я збираюся поділитися деталями у випадку, якщо хтось із того самого контексту зіткнеться з цією проблемою:

Це веб-додаток на базі Spring, в якому "JaxWsPortProxyFactoryBean" бон був налаштований для викриття проксі для віддаленого порту.

<bean id="ourPortJaxProxyService"
    class="org.springframework.remoting.jaxws.JaxWsPortProxyFactoryBean"
    p:serviceInterface="com.amir.OurServiceSoapPortWs"
    p:wsdlDocumentUrl="${END_POINT_BASE_URL}/OurService?wsdl"
    p:namespaceUri="http://amir.com/jaxws" p:serviceName="OurService"
    p:portName="OurSoapPort" />

"END_POINT_BASE_URL" - це змінна середовище, налаштована в "setenv.sh" екземпляра Tomcat, який розміщує веб-додаток. Вміст файлу приблизно такий:

export END_POINT_BASE_URL="http://localhost:9001/BusinessAppServices"
#export END_POINT_BASE_URL="http://localhost:8765/BusinessAppServices"

Зниклих ";" після кожного рядка викликав неправильну URL-адресу і, таким чином, погану реакцію. Тобто, замість "BusinessAppServices / OurService? Wsdl" URL-адреса мала CR раніше "/". "Монітор TCP / IP" виявився досить зручним під час вирішення проблеми.


0

У моєму випадку я отримав цю помилку, оскільки API, який я використовував, може повертати дані або у форматі XML, або у форматі JSON. Коли я тестував його за допомогою браузера, він встановив дефолт у форматі XML, але коли я викликав той самий виклик від програми Java, API повернув відповідь у форматі JSON, що, природно, спричинило помилку розбору.


0

Навіть я стикався з подібною проблемою. Причина була деяким сміттєвим символом на початку файлу.

Виправлення: просто відкрийте файл у текстовому редакторі (тестується на тексті Sublime), видаліть будь-який відступ, якщо такий є у файлі, та скопіюйте вставте весь вміст у новий файл та збережіть його. Це воно!. Коли я запустив новий файл, він запускався без помилок розбору.


0

Я взяв код Dineshkumar і змінив, щоб правильно підтвердити свій XML-файл:

import org.apache.log4j.Logger;

public class Myclass{

private static final Logger LOGGER = Logger.getLogger(Myclass.class);

/**
 * Validate XML file against Schemas XSD in pathEsquema directory
 * @param pathEsquema directory that contains XSD Schemas to validate
 * @param pathFileXML XML file to validate
 * @throws BusinessException if it throws any Exception
 */
public static void validarXML(String pathEsquema, String pathFileXML) 
	throws BusinessException{	
	String W3C_XML_SCHEMA = "http://www.w3.org/2001/XMLSchema";
	String nameFileXSD = "file.xsd";
	String MY_SCHEMA1 = pathEsquema+nameFileXSD);
	ParserErrorHandler parserErrorHandler;
	try{
		SchemaFactory schemaFactory = SchemaFactory.newInstance(W3C_XML_SCHEMA);
		
		Source [] source = { 
			new StreamSource(new File(MY_SCHEMA1))
			};
		Schema schemaGrammar = schemaFactory.newSchema(source);

		Validator schemaValidator = schemaGrammar.newValidator();
		schemaValidator.setErrorHandler(
			parserErrorHandler= new ParserErrorHandler());
		
		/** validate xml instance against the grammar. */
		File file = new File(pathFileXML);
		InputStream isS= new FileInputStream(file);
		Reader reader = new InputStreamReader(isS,"UTF-8");
		schemaValidator.validate(new StreamSource(reader));
		
		if(parserErrorHandler.getErrorHandler().isEmpty()&& 
			parserErrorHandler.getFatalErrorHandler().isEmpty()){
			if(!parserErrorHandler.getWarningHandler().isEmpty()){
				LOGGER.info(
				String.format("WARNING validate XML:[%s] Descripcion:[%s]",
					pathFileXML,parserErrorHandler.getWarningHandler()));
			}else{
				LOGGER.info(
				String.format("OK validate  XML:[%s]",
					pathFileXML));
			}
		}else{
			throw new BusinessException(
				String.format("Error validate  XML:[%s], FatalError:[%s], Error:[%s]",
				pathFileXML,
				parserErrorHandler.getFatalErrorHandler(),
				parserErrorHandler.getErrorHandler()));
		}		
	}
	catch(SAXParseException e){
		throw new BusinessException(String.format("Error validate XML:[%s], SAXParseException:[%s]",
			pathFileXML,e.getMessage()),e);
	}
	catch (SAXException e){
		throw new BusinessException(String.format("Error validate XML:[%s], SAXException:[%s]",
			pathFileXML,e.getMessage()),e);
	}
	catch (IOException e) {
		throw new BusinessException(String.format("Error validate XML:[%s], 
			IOException:[%s]",pathFileXML,e.getMessage()),e);
	}
	
}

}


0

Налаштуйте документ таким чином:

<?xml version="1.0" encoding="UTF-8" ?>
<root>
    %children%
</root>

0

У мене було те саме питання з весною

MarshallingMessageConverter

і за кодом попередньої обробки.

Можливо, комусь знадобиться причина: BytesMessage #readBytes - читання байтів .., і я забув, що читання - це одна операція напрямку. Не можна читати двічі.


0

Спробуйте з BOMInputStream в apache.commons.io:

public static <T> T getContent(Class<T> instance, SchemaType schemaType, InputStream stream) throws JAXBException, SAXException, IOException {

    JAXBContext context = JAXBContext.newInstance(instance);
    Unmarshaller unmarshaller = context.createUnmarshaller();
    Reader reader = new InputStreamReader(new BOMInputStream(stream), "UTF-8");

    JAXBElement<T> entry = unmarshaller.unmarshal(new StreamSource(reader), instance);

    return entry.getValue();
}

0

У мене була така ж проблема під час розбору info.plistфайлу в моєму Mac. Однак проблема була виправлена ​​за допомогою наступної команди, яка перетворила файл у XML.

plutil -convert xml1 info.plist

Сподіваюся, що хтось допомагає.


0

У мене була така ж проблема з деякими файлами XML, я вирішив прочитати файл з кодуванням ANSI (Windows-1252) і записати файл з кодуванням UTF-8 з невеликим сценарієм в Python. Я спробував використовувати Notepad ++, але успіху у мене не було:

import os
import sys

path = os.path.dirname(__file__)

file_name = 'my_input_file.xml'

if __name__ == "__main__":
    with open(os.path.join(path, './' + file_name), 'r', encoding='cp1252') as f1:
        lines = f1.read()
        f2 = open(os.path.join(path, './' + 'my_output_file.xml'), 'w', encoding='utf-8')
        f2.write(lines)
        f2.close()
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.