private void parseArtifactVersions(
     final XMLStreamReader reader, final FeaturePackDescription result) throws XMLStreamException {
   final Set<Artifact> artifactVersions = result.getArtifactVersions();
   while (reader.hasNext()) {
     switch (reader.nextTag()) {
       case XMLStreamConstants.END_ELEMENT:
         {
           return;
         }
       case XMLStreamConstants.START_ELEMENT:
         {
           final Element element = Element.of(reader.getName());
           switch (element) {
             case ARTIFACT:
               artifactVersions.add(parseArtifact(reader));
               break;
             default:
               throw ParsingUtils.unexpectedContent(reader);
           }
           break;
         }
       default:
         {
           throw ParsingUtils.unexpectedContent(reader);
         }
     }
   }
   throw ParsingUtils.endOfDocument(reader.getLocation());
 }
  @Override
  public void readElement(final XMLExtendedStreamReader reader, final FeaturePackDescription result)
      throws XMLStreamException {

    final Set<Attribute> required = EnumSet.noneOf(Attribute.class);
    final int count = reader.getAttributeCount();

    for (int i = 0; i < count; i++) {
      throw ParsingUtils.unexpectedContent(reader);
    }
    if (!required.isEmpty()) {
      throw ParsingUtils.missingAttributes(reader.getLocation(), required);
    }
    while (reader.hasNext()) {
      switch (reader.nextTag()) {
        case XMLStreamConstants.END_ELEMENT:
          {
            return;
          }
        case XMLStreamConstants.START_ELEMENT:
          {
            final Element element = Element.of(reader.getName());

            switch (element) {
              case DEPENDENCIES:
                parseDependencies(reader, result);
                break;
              case ARTIFACT_VERSIONS:
                parseArtifactVersions(reader, result);
                break;
              case CONFIG:
                configModelParser.parseConfig(reader, result.getConfig());
                break;
              case COPY_ARTIFACTS:
                copyArtifactsModelParser.parseCopyArtifacts(reader, result.getCopyArtifacts());
                break;
              case FILE_PERMISSIONS:
                filePermissionsModelParser.parseFilePermissions(
                    reader, result.getFilePermissions());
                break;
              default:
                throw ParsingUtils.unexpectedContent(reader);
            }
            break;
          }
        default:
          {
            throw ParsingUtils.unexpectedContent(reader);
          }
      }
    }
    throw ParsingUtils.endOfDocument(reader.getLocation());
  }
  public void parse() throws IOException, XMLStreamException {
    try (InputStream in = inputStreamSource.getInputStream()) {
      XMLInputFactory factory = XMLInputFactory.newInstance();
      factory.setProperty(XMLInputFactory.IS_COALESCING, Boolean.FALSE);
      XMLStreamReader reader = factory.createXMLStreamReader(in);

      reader.require(START_DOCUMENT, null, null);
      ParsingUtils.getNextElement(reader, rootElementName, null, false);
      root = super.parseNode(reader, rootElementName);
    }
  }
 private String parseName(final XMLStreamReader reader) throws XMLStreamException {
   final int count = reader.getAttributeCount();
   String name = null;
   final Set<Attribute> required = EnumSet.of(Attribute.NAME);
   for (int i = 0; i < count; i++) {
     final Attribute attribute = Attribute.of(reader.getAttributeName(i));
     required.remove(attribute);
     switch (attribute) {
       case NAME:
         name = reader.getAttributeValue(i);
         break;
       default:
         throw ParsingUtils.unexpectedContent(reader);
     }
   }
   if (!required.isEmpty()) {
     throw ParsingUtils.missingAttributes(reader.getLocation(), required);
   }
   ParsingUtils.parseNoContent(reader);
   return propertyReplacer.replaceProperties(name);
 }
 private Artifact parseArtifact(final XMLStreamReader reader) throws XMLStreamException {
   final int count = reader.getAttributeCount();
   String groupId = null;
   String artifactId = null;
   String version = null;
   String classifier = null;
   String extension = null;
   final Set<Attribute> required =
       EnumSet.of(Attribute.GROUP_ID, Attribute.ARTIFACT_ID, Attribute.VERSION);
   for (int i = 0; i < count; i++) {
     final Attribute attribute = Attribute.of(reader.getAttributeName(i));
     required.remove(attribute);
     switch (attribute) {
       case GROUP_ID:
         groupId = propertyReplacer.replaceProperties(reader.getAttributeValue(i));
         break;
       case ARTIFACT_ID:
         artifactId = propertyReplacer.replaceProperties(reader.getAttributeValue(i));
         break;
       case VERSION:
         version = propertyReplacer.replaceProperties(reader.getAttributeValue(i));
         break;
       case CLASSIFIER:
         classifier = propertyReplacer.replaceProperties(reader.getAttributeValue(i));
         break;
       case EXTENSION:
         extension = propertyReplacer.replaceProperties(reader.getAttributeValue(i));
         break;
       default:
         throw ParsingUtils.unexpectedContent(reader);
     }
   }
   if (!required.isEmpty()) {
     throw ParsingUtils.missingAttributes(reader.getLocation(), required);
   }
   ParsingUtils.parseNoContent(reader);
   return new Artifact(groupId, artifactId, classifier, extension, version);
 }
  /*
  we only override this method, for now only change new EXTRACT_SCHEMAS_GROUPS attribute
   */
  @Override
  public void readElement(
      final XMLExtendedStreamReader reader, final ServerProvisioningDescription result)
      throws XMLStreamException {
    for (int i = 0; i < reader.getAttributeCount(); i++) {
      final Attribute attribute = Attribute.of(reader.getAttributeName(i));
      switch (attribute) {
        case COPY_MODULE_ARTIFACTS:
          result.setCopyModuleArtifacts(Boolean.parseBoolean(reader.getAttributeValue(i)));
          break;
        case EXTRACT_SCHEMAS:
          result.setExtractSchemas(Boolean.parseBoolean(reader.getAttributeValue(i)));
          break;
        case EXTRACT_SCHEMAS_GROUPS:
          result.setExtractSchemasGroups(reader.getAttributeValue(i));
          break;
        case EXCLUDE_DEPENDENCIES:
          result.setExcludeDependencies(Boolean.parseBoolean(reader.getAttributeValue(i)));
          break;
        default:
          throw ParsingUtils.unexpectedAttribute(reader, i);
      }
    }

    while (reader.hasNext()) {
      switch (reader.nextTag()) {
        case XMLStreamConstants.END_ELEMENT:
          {
            return;
          }
        case XMLStreamConstants.START_ELEMENT:
          {
            final Element element = Element.of(reader.getLocalName());

            switch (element) {
              case FEATURE_PACKS:
                parseFeaturePacks(reader, result);
                break;
              case VERSION_OVERRIDES:
                parseVersionOverrides(reader, result);
                break;
              case COPY_ARTIFACTS:
                copyArtifactsModelParser.parseCopyArtifacts(reader, result.getCopyArtifacts());
                break;
              default:
                throw new XMLStreamException(
                    String.format(
                        "Unknown element: '%s', elementName: %s, localName: %s",
                        element, reader.getName(), reader.getLocalName()),
                    reader.getLocation());
                // throw ParsingUtils.unexpectedContent(reader);
            }
            break;
          }
        default:
          {
            throw ParsingUtils.unexpectedContent(reader);
          }
      }
    }
    throw ParsingUtils.endOfDocument(reader.getLocation());
  }