package org.jboss.as.controller; import static javax.xml.stream.XMLStreamConstants.END_ELEMENT; import static org.jboss.as.controller.ControllerMessages.MESSAGES; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.ADDRESS; import static org.jboss.as.controller.descriptions.ModelDescriptionConstants.NAME; import java.util.HashMap; import java.util.List; import java.util.Map; import javax.xml.stream.XMLStreamConstants; import javax.xml.stream.XMLStreamException; import org.jboss.as.controller.descriptions.ResourceDescriptionResolver; import org.jboss.as.controller.operations.common.Util; import org.jboss.as.controller.parsing.ParseUtils; import org.jboss.as.controller.registry.ManagementResourceRegistration; import org.jboss.as.controller.registry.OperationEntry; import org.jboss.dmr.ModelNode; import org.jboss.dmr.Property; import org.jboss.staxmapper.XMLExtendedStreamReader; import org.jboss.staxmapper.XMLExtendedStreamWriter; /** * @author <a href="mailto:tomaz.cerar@redhat.com">Tomaz Cerar</a> (c) 2013 Red Hat Inc. */ public abstract class SimplePersistentResourceDefinition extends SimpleResourceDefinition implements PersistentResourceDefinition { protected SimplePersistentResourceDefinition(PathElement pathElement, ResourceDescriptionResolver descriptionResolver) { super(pathElement, descriptionResolver); } protected SimplePersistentResourceDefinition(PathElement pathElement, ResourceDescriptionResolver descriptionResolver, OperationStepHandler addHandler, OperationStepHandler removeHandler) { super(pathElement, descriptionResolver, addHandler, removeHandler); } protected SimplePersistentResourceDefinition(PathElement pathElement, ResourceDescriptionResolver descriptionResolver, OperationStepHandler addHandler, OperationStepHandler removeHandler, OperationEntry.Flag addRestartLevel, OperationEntry.Flag removeRestartLevel) { super(pathElement, descriptionResolver, addHandler, removeHandler, addRestartLevel, removeRestartLevel); } protected Map<String, AttributeDefinition> getAttributeMap() { Map<String, AttributeDefinition> res = new HashMap<>(); for (AttributeDefinition def : getAttributes()) { res.put(def.getName(), def); } return res; } @Override public String getXmlElementName() { return getPathElement().getKey(); } @Override public String getXmlWrapperElement() { return null; } @Override public PersistentResourceDefinition[] getChildren() { return new PersistentResourceDefinition[0]; } @Override public void registerChildren(ManagementResourceRegistration resourceRegistration) { super.registerChildren(resourceRegistration); for (PersistentResourceDefinition child : getChildren()) { resourceRegistration.registerSubModel(child); } } @Override public void parse(final XMLExtendedStreamReader reader, PathAddress parentAddress, List<ModelNode> list) throws XMLStreamException { if (getXmlWrapperElement() != null) { if (reader.getLocalName().equals(getXmlWrapperElement())) { if (reader.hasNext()) { if (reader.nextTag() == END_ELEMENT) { return; } } } else { throw ParseUtils.unexpectedElement(reader); } } boolean wildcard = getPathElement().isWildcard(); String name = null; ModelNode op = Util.createAddOperation(); Map<String, AttributeDefinition> attributes = getAttributeMap(); for (int i = 0; i < reader.getAttributeCount(); i++) { String attributeName = reader.getAttributeLocalName(i); String value = reader.getAttributeValue(i); if (wildcard && NAME.equals(attributeName)) { name = value; } else if (attributes.containsKey(attributeName)) { AttributeDefinition def = attributes.get(attributeName); if (def instanceof SimpleAttributeDefinition) { ((SimpleAttributeDefinition) def).parseAndSetParameter(value, op, reader); } else { throw new IllegalArgumentException("we should know how to handle " + def); } } else { throw ParseUtils.unexpectedAttribute(reader, i); } } if (wildcard && name == null) { throw MESSAGES.missingRequiredAttributes(new StringBuilder(NAME), reader.getLocation()); } PathElement path = wildcard ? PathElement.pathElement(getPathElement().getKey(), name) : getPathElement(); PathAddress address = parentAddress.append(path); op.get(ADDRESS).set(address.toModelNode()); list.add(op); parseChildren(reader, address, list); if (getXmlWrapperElement() != null) { ParseUtils.requireNoContent(reader); } } private Map<String, PersistentResourceDefinition> getChildrenMap() { Map<String, PersistentResourceDefinition> res = new HashMap<>(); for (PersistentResourceDefinition child : getChildren()) { res.put(child.getXmlElementName(), child); } return res; } public void parseChildren(final XMLExtendedStreamReader reader, PathAddress parentAddress, List<ModelNode> list) throws XMLStreamException { if (getChildren().length == 0) { ParseUtils.requireNoContent(reader); } else { Map<String, PersistentResourceDefinition> children = getChildrenMap(); while (reader.hasNext() && reader.nextTag() != XMLStreamConstants.END_ELEMENT) { PersistentResourceDefinition child = children.get(reader.getLocalName()); if (child != null) { child.parse(reader, parentAddress, list); } else { throw ParseUtils.unexpectedElement(reader); } } } } protected boolean useValueAsElementName() { return false; } @Override public void persist(XMLExtendedStreamWriter writer, ModelNode model) throws XMLStreamException { boolean wildcard = getPathElement().isWildcard(); model = wildcard ? model.get(getPathElement().getKey()) : model.get(getPathElement().getKeyValuePair()); if (!model.isDefined() && !useValueAsElementName()) { return; } boolean writeWrapper = getXmlWrapperElement() != null; if (writeWrapper) { writer.writeStartElement(getXmlWrapperElement()); } if (wildcard) { for (Property p : model.asPropertyList()) { if (useValueAsElementName()) { writer.writeStartElement(p.getName()); } else { writer.writeStartElement(getXmlElementName()); writer.writeAttribute(NAME, p.getName()); } for (AttributeDefinition def : getAttributes()) { def.getAttributeMarshaller().marshallAsAttribute(def, p.getValue(), false, writer); } persistChildren(writer, p.getValue()); writer.writeEndElement(); } } else { if (useValueAsElementName()){ writer.writeStartElement(getPathElement().getValue()); }else{ writer.writeStartElement(getXmlElementName()); } for (AttributeDefinition def : getAttributes()) { def.getAttributeMarshaller().marshallAsAttribute(def, model, false, writer); } persistChildren(writer, model); writer.writeEndElement(); } if (writeWrapper) { writer.writeEndElement(); } } public void persistChildren(XMLExtendedStreamWriter writer, ModelNode model) throws XMLStreamException { for (PersistentResourceDefinition child : getChildren()) { child.persist(writer, model); } } }