1

以下のドキュメントのような XML を検証するために、Xerces-C++ (バージョン 2.6.1) SAX2 パーサーを使用しています。(これは MSML - RFC 5707で定義されている Media Server Markup Languageです。)

<?xml version="1.0" encoding="UTF-8"?>
<msml version="1.1">
   <createconference name="example">
      <audiomix>
         <n-loudest n="3"/>
         <asn ri="10s"/>
      </audiomix>
   </createconference>
</msml>

RFC はMSML を検証するための XML スキーマを提供しています。私はそれらを Xerces SAX2 パーサーと組み合わせて使用​​して、MSML を検証および解析しようとしています。解析は正常に機能していますが、検証に失敗しています。検証しようとしている MSML に属性が含まれていないため、問題が発生している可能性があると思われますが、受け取る XML を制御できませんschemaLocation。msml.xsd を使用して検証を強制したいXML で提供されます。schemaLocationnoNamespaceSchemaLocation

私のコードは次のようになります。

SAX2XMLReader* parser = XMLReaderFactory::createXMLReader();

// Enable the parser's schema support 
parser->setFeature(XMLUni::fgXercesSchema, true);

// Schema validation requires namespace processing to be turned on.
parser->setFeature(XMLUni::fgSAX2CoreValidation, true);
parser->setFeature(XMLUni::fgSAX2CoreNameSpaces, true);

// Define the location of the MSML schema.
XMLCh* schemaLocation = XMLString::transcode("/directory/path/msml-core.xsd");
parser->setProperty(XMLUni::fgXercesSchemaExternalNoNameSpaceSchemaLocation,
                    schemaLocation);

// MSMLHandler is defined elsewhere and inherits from xercesc/sax2/DefaultHandler
// It overrides startElement and fatalError.
MxMSMLHandler* msmlHandler = new MSMLHandler(xiSessionID, xoMSMLResponse);
parser->setContentHandler((ContentHandler*) msmlHandler);
parser->setErrorHandler((ErrorHandler*) msmlHandler);

// Do the parse
parser->parse(*xmlInputSource);
4

1 に答える 1

2

そして、試行錯誤を繰り返しながら、最終的に問題を見つけました。検証エラーは、パーサーに渡されたときにerrorコールバックに報告されます。属性に ErrorHandler問題はありませんでした。schemaLocation

これを修正し、パフォーマンスを向上させるために XML 文法のキャッシュを追加すると、コードは次のようになります。

SAX2XMLReader* parser = XMLReaderFactory::createXMLReader();

// Enable the parser's schema support 
parser->setFeature(XMLUni::fgXercesSchema, true);

// Schema validation requires namespace processing to be turned on.
parser->setFeature(XMLUni::fgSAX2CoreValidation, true);
parser->setFeature(XMLUni::fgSAX2CoreNameSpaces, true);

// Cache the XML grammar and use it for subsequent parses.
mParser->setFeature(XMLUni::fgXercesCacheGrammarFromParse, true);
mParser->setFeature(XMLUni::fgXercesUseCachedGrammarInParse, true);

// Define the location of the MSML schema.
XMLCh* schemaLocation = XMLString::transcode("/directory/path/msml-core.xsd");
parser->setProperty(XMLUni::fgXercesSchemaExternalNoNameSpaceSchemaLocation,
                    schemaLocation);

// MSMLHandler is defined elsewhere and inherits from xercesc/sax2/DefaultHandler
// It overrides startElement, fatalError *and error*.
MxMSMLHandler* msmlHandler = new MSMLHandler(xiSessionID, xoMSMLResponse);
parser->setContentHandler((ContentHandler*) msmlHandler);
parser->setErrorHandler((ErrorHandler*) msmlHandler);

// Do the parse
parser->parse(*xmlInputSource);
于 2010-12-09T15:57:40.343 に答える