Apache XMLSchema 核心 XSD/XML 解析器将根元素显示为所有子元素的父元素,而不是其直接父元素
Apache XMLSchema core XSD/XML parser shows the root element as parent for all children instead of its immediate parent
我正在尝试使用 Apache XMLSchema Core
解析 XSD
。我能够解析文件并将 Parent
及其 Child Element
信息存储在 HashMap
.
中
每个 Child
元素都存储在类型 XmlSchemaElement
中,该类型还包含该子元素的 Parent
信息。当我尝试查看与子元素相关的信息时,它显示所有元素的 Root
元素而不是其直接父元素。
例如:在我的 XSD
中,RestaurantMenu
是 Root
元素,它的直接子元素是 Food
。此外,Food
有子元素 name
、price
、calories
等。当我看到 name
的父元素时,我希望它是 Food
因为那是直接父级,但在 Debug
期间显示 RestaurantMenu
作为其父级,这有点令人困惑。
我想知道如何获取与每个元素的直接父元素相关的信息。
以下是我的 XSD
文件:
<xs:schema attributeFormDefault="unqualified"
elementFormDefault="qualified"
xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xs:element name="RestaurantMenu">
<xs:complexType>
<xs:sequence>
<xs:element name="food" maxOccurs="5" minOccurs="0">
<xs:complexType>
<xs:sequence>
<xs:element type="xs:string" name="name" />
<xs:element type="xs:string" name="price" />
<xs:element type="xs:string" name="description" />
<xs:element type="xs:short" name="calories" />
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>
以下是我使用 Apache XmlSchema Core XML Parser
编写的代码:
我正在尝试 Debug
点 :
List<XmlSchemaElement> childElements = getElementType(new QName("food"));
System.out.println(childElements.get(0));
以上代码将 return 食物的所有 Children
元素:name
、price
、calories
、description
、ingredients
。然后我试图查看其中一个元素的父元素,即 name
。以下是我正在使用的调试路径:
childElements -> [0] -> namedDelegate -> parentSchema -> items -> [0] -> namedDelegate -> qName.
在这个 qName
中,我期待 food
是我的直接父元素,但我得到 RestaurantMenu
这是我的 Root
xsd 元素。
请在下面找到完整的代码:
public class TestParser {
private static XmlSchemaCollection xmlSchemaCollection;
private static Map<QName, List<XmlSchemaElement>> xsdElements = new HashMap<QName, List<XmlSchemaElement>>();
private static List<XmlSchemaElement> schemaElements = new ArrayList<XmlSchemaElement>();
public static void main(String[] args) throws URISyntaxException, FileNotFoundException, UnsupportedEncodingException {
// Path for the file which is stored within the Resource folder
String xsdPath = Paths.get(TestParser.class.getClassLoader().getResource("test.xsd").toURI()).toFile().getAbsolutePath();
String filePath = Path.of(xsdPath).toString();
InputStream is = new FileInputStream(filePath);
xmlSchemaCollection = new XmlSchemaCollection();
// Schema contain the complete XSD content which needs to be parsed
XmlSchema schema = xmlSchemaCollection.read(new StreamSource(is));
// schema.write(System.out);
// Get the root element from XSD
Map.Entry<QName, XmlSchemaElement> entry = schema.getElements().entrySet().iterator().next();
// Get all the elements based on the parent element
XmlSchemaElement childElement = xmlSchemaCollection.getElementByQName(entry.getKey());
// Call method to get all the child elements
getChildElementNames(childElement);
// Get the elements type based on choice
List<XmlSchemaElement> childElements = xsdElements.get(new QName("food"));
System.out.println(childElements.get(0));
}
// Method to check for the child elements and return list
private static void getChildElementNames(XmlSchemaElement element) {
// Get the type of the element
XmlSchemaType elementType = element != null ? element.getSchemaType() : null;
// Confirm if the element is of Complex type
if (elementType instanceof XmlSchemaComplexType) {
// Get all particles associated with that element Type
XmlSchemaParticle allParticles = ((XmlSchemaComplexType) elementType).getParticle();
// Check particle belongs to which type
if (allParticles instanceof XmlSchemaSequence) {
// System.out.println("Sequence Schema Type");
final XmlSchemaSequence xmlSchemaSequence = (XmlSchemaSequence) allParticles;
final List<XmlSchemaSequenceMember> items = xmlSchemaSequence.getItems();
items.forEach((item) -> {
XmlSchemaElement itemElements = (XmlSchemaElement) item;
schemaElements.add(itemElements);
addChild(element.getQName(), itemElements);
// Call method recursively to get all subsequent element
getChildElementNames(itemElements);
schemaElements = new ArrayList<XmlSchemaElement>();
});
}
}
}
// Add child elements based on its parent
private static void addChild(QName qName, XmlSchemaElement child) {
List<XmlSchemaElement> values = xsdElements.get(qName);
if (values == null) {
values = new ArrayList<XmlSchemaElement>();
}
values.add(child);
xsdElements.put(qName, values);
}
}
免责声明:我不是 XSModel 方面的专家,但很久以前我确实用过一次。
XSModel 是 XSD 中几乎所有内容的完整完整记录。因此它确实包含您正在寻找的信息。意识到 XSModel 是为了验证 XML 文档而创建的可能会有所帮助 - 它从未打算成为 XSD 模型的通用内存表示。如果那是您所需要的,那么您可能会更好地使用 Eclipse XSD model。无论哪种方式,加载和操作 XSD 模型都是少数人的运动,您不应该期望 API 得到完美的记录。
Can you please assist me in how to find an immediate parent for a child element within the Apache XMLSchema core library.
当您谈论 'child element' 时,我认为您指的是 local element declaration
或 element reference
。通常,它们都可以有 多个 父元素声明,因为它们可以在全局复杂类型中声明。如果该全局复杂类型定义被多个元素声明使用,那么您的 'child element' 将有多个可能的父元素。
在 Java 的 Apache XMLSchema Core
库上工作了一段时间后,以下是我的观察。
无法直接使用库获取直接父元素,您可以从 XmlSchemaElement 中获取与当前元素及其子元素相关的信息。
我正在尝试使用 Apache XMLSchema Core
解析 XSD
。我能够解析文件并将 Parent
及其 Child Element
信息存储在 HashMap
.
每个 Child
元素都存储在类型 XmlSchemaElement
中,该类型还包含该子元素的 Parent
信息。当我尝试查看与子元素相关的信息时,它显示所有元素的 Root
元素而不是其直接父元素。
例如:在我的 XSD
中,RestaurantMenu
是 Root
元素,它的直接子元素是 Food
。此外,Food
有子元素 name
、price
、calories
等。当我看到 name
的父元素时,我希望它是 Food
因为那是直接父级,但在 Debug
期间显示 RestaurantMenu
作为其父级,这有点令人困惑。
我想知道如何获取与每个元素的直接父元素相关的信息。
以下是我的 XSD
文件:
<xs:schema attributeFormDefault="unqualified"
elementFormDefault="qualified"
xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xs:element name="RestaurantMenu">
<xs:complexType>
<xs:sequence>
<xs:element name="food" maxOccurs="5" minOccurs="0">
<xs:complexType>
<xs:sequence>
<xs:element type="xs:string" name="name" />
<xs:element type="xs:string" name="price" />
<xs:element type="xs:string" name="description" />
<xs:element type="xs:short" name="calories" />
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>
以下是我使用 Apache XmlSchema Core XML Parser
编写的代码:
我正在尝试 Debug
点 :
List<XmlSchemaElement> childElements = getElementType(new QName("food"));
System.out.println(childElements.get(0));
以上代码将 return 食物的所有 Children
元素:name
、price
、calories
、description
、ingredients
。然后我试图查看其中一个元素的父元素,即 name
。以下是我正在使用的调试路径:
childElements -> [0] -> namedDelegate -> parentSchema -> items -> [0] -> namedDelegate -> qName.
在这个 qName
中,我期待 food
是我的直接父元素,但我得到 RestaurantMenu
这是我的 Root
xsd 元素。
请在下面找到完整的代码:
public class TestParser {
private static XmlSchemaCollection xmlSchemaCollection;
private static Map<QName, List<XmlSchemaElement>> xsdElements = new HashMap<QName, List<XmlSchemaElement>>();
private static List<XmlSchemaElement> schemaElements = new ArrayList<XmlSchemaElement>();
public static void main(String[] args) throws URISyntaxException, FileNotFoundException, UnsupportedEncodingException {
// Path for the file which is stored within the Resource folder
String xsdPath = Paths.get(TestParser.class.getClassLoader().getResource("test.xsd").toURI()).toFile().getAbsolutePath();
String filePath = Path.of(xsdPath).toString();
InputStream is = new FileInputStream(filePath);
xmlSchemaCollection = new XmlSchemaCollection();
// Schema contain the complete XSD content which needs to be parsed
XmlSchema schema = xmlSchemaCollection.read(new StreamSource(is));
// schema.write(System.out);
// Get the root element from XSD
Map.Entry<QName, XmlSchemaElement> entry = schema.getElements().entrySet().iterator().next();
// Get all the elements based on the parent element
XmlSchemaElement childElement = xmlSchemaCollection.getElementByQName(entry.getKey());
// Call method to get all the child elements
getChildElementNames(childElement);
// Get the elements type based on choice
List<XmlSchemaElement> childElements = xsdElements.get(new QName("food"));
System.out.println(childElements.get(0));
}
// Method to check for the child elements and return list
private static void getChildElementNames(XmlSchemaElement element) {
// Get the type of the element
XmlSchemaType elementType = element != null ? element.getSchemaType() : null;
// Confirm if the element is of Complex type
if (elementType instanceof XmlSchemaComplexType) {
// Get all particles associated with that element Type
XmlSchemaParticle allParticles = ((XmlSchemaComplexType) elementType).getParticle();
// Check particle belongs to which type
if (allParticles instanceof XmlSchemaSequence) {
// System.out.println("Sequence Schema Type");
final XmlSchemaSequence xmlSchemaSequence = (XmlSchemaSequence) allParticles;
final List<XmlSchemaSequenceMember> items = xmlSchemaSequence.getItems();
items.forEach((item) -> {
XmlSchemaElement itemElements = (XmlSchemaElement) item;
schemaElements.add(itemElements);
addChild(element.getQName(), itemElements);
// Call method recursively to get all subsequent element
getChildElementNames(itemElements);
schemaElements = new ArrayList<XmlSchemaElement>();
});
}
}
}
// Add child elements based on its parent
private static void addChild(QName qName, XmlSchemaElement child) {
List<XmlSchemaElement> values = xsdElements.get(qName);
if (values == null) {
values = new ArrayList<XmlSchemaElement>();
}
values.add(child);
xsdElements.put(qName, values);
}
}
免责声明:我不是 XSModel 方面的专家,但很久以前我确实用过一次。
XSModel 是 XSD 中几乎所有内容的完整完整记录。因此它确实包含您正在寻找的信息。意识到 XSModel 是为了验证 XML 文档而创建的可能会有所帮助 - 它从未打算成为 XSD 模型的通用内存表示。如果那是您所需要的,那么您可能会更好地使用 Eclipse XSD model。无论哪种方式,加载和操作 XSD 模型都是少数人的运动,您不应该期望 API 得到完美的记录。
Can you please assist me in how to find an immediate parent for a child element within the Apache XMLSchema core library.
当您谈论 'child element' 时,我认为您指的是 local element declaration
或 element reference
。通常,它们都可以有 多个 父元素声明,因为它们可以在全局复杂类型中声明。如果该全局复杂类型定义被多个元素声明使用,那么您的 'child element' 将有多个可能的父元素。
在 Java 的 Apache XMLSchema Core
库上工作了一段时间后,以下是我的观察。
无法直接使用库获取直接父元素,您可以从 XmlSchemaElement 中获取与当前元素及其子元素相关的信息。