public RulesProfile parse(Reader reader, ValidationMessages messages) {
    RulesProfile profile = RulesProfile.create();
    SMInputFactory inputFactory = initStax();
    try {
      SMHierarchicCursor rootC = inputFactory.rootElementCursor(reader);
      rootC.advance(); // <profile>
      SMInputCursor cursor = rootC.childElementCursor();
      while (cursor.getNext() != null) {
        String nodeName = cursor.getLocalName();
        if (StringUtils.equals("rules", nodeName)) {
          SMInputCursor rulesCursor = cursor.childElementCursor("rule");
          processRules(rulesCursor, profile, messages);

        } else if (StringUtils.equals("name", nodeName)) {
          profile.setName(StringUtils.trim(cursor.collectDescendantText(false)));

        } else if (StringUtils.equals("language", nodeName)) {
          profile.setLanguage(StringUtils.trim(cursor.collectDescendantText(false)));
        }
      }
    } catch (XMLStreamException e) {
      messages.addErrorText("XML is not valid: " + e.getMessage());
    }
    checkProfile(profile, messages);
    return profile;
  }
  private void processRules(
      SMInputCursor rulesCursor, RulesProfile profile, ValidationMessages messages)
      throws XMLStreamException {
    Map<String, String> parameters = new HashMap<>();
    while (rulesCursor.getNext() != null) {
      SMInputCursor ruleCursor = rulesCursor.childElementCursor();

      String repositoryKey = null;
      String key = null;
      RulePriority priority = null;
      parameters.clear();

      while (ruleCursor.getNext() != null) {
        String nodeName = ruleCursor.getLocalName();

        if (StringUtils.equals("repositoryKey", nodeName)) {
          repositoryKey = StringUtils.trim(ruleCursor.collectDescendantText(false));

        } else if (StringUtils.equals("key", nodeName)) {
          key = StringUtils.trim(ruleCursor.collectDescendantText(false));

        } else if (StringUtils.equals("priority", nodeName)) {
          priority =
              RulePriority.valueOf(StringUtils.trim(ruleCursor.collectDescendantText(false)));

        } else if (StringUtils.equals("parameters", nodeName)) {
          SMInputCursor propsCursor = ruleCursor.childElementCursor("parameter");
          processParameters(propsCursor, parameters);
        }
      }

      Rule rule = ruleFinder.findByKey(repositoryKey, key);
      if (rule == null) {
        messages.addWarningText("Rule not found: " + ruleToString(repositoryKey, key));

      } else {
        ActiveRule activeRule = profile.activateRule(rule, priority);
        for (Map.Entry<String, String> entry : parameters.entrySet()) {
          if (rule.getParam(entry.getKey()) == null) {
            messages.addWarningText(
                "The parameter '"
                    + entry.getKey()
                    + "' does not exist in the rule: "
                    + ruleToString(repositoryKey, key));
          } else {
            activeRule.setParameter(entry.getKey(), entry.getValue());
          }
        }
      }
    }
  }
  private void loadRuleKeys() {
    XMLInputFactory xmlFactory = XMLInputFactory.newInstance();
    xmlFactory.setProperty(XMLInputFactory.IS_COALESCING, Boolean.TRUE);
    xmlFactory.setProperty(XMLInputFactory.IS_NAMESPACE_AWARE, Boolean.FALSE);
    // just so it won't try to load DTD in if there's DOCTYPE
    xmlFactory.setProperty(XMLInputFactory.SUPPORT_DTD, Boolean.FALSE);
    xmlFactory.setProperty(XMLInputFactory.IS_VALIDATING, Boolean.FALSE);
    SMInputFactory inputFactory = new SMInputFactory(xmlFactory);
    InputStream inputStream =
        getClass().getResourceAsStream(AndroidLintRulesDefinition.RULES_XML_PATH);
    InputStreamReader reader = new InputStreamReader(inputStream, Charsets.UTF_8);
    try {
      SMHierarchicCursor rootC = inputFactory.rootElementCursor(reader);
      rootC.advance(); // <rules>

      SMInputCursor rulesC = rootC.childElementCursor("rule");
      while (rulesC.getNext() != null) {
        // <rule>
        SMInputCursor cursor = rulesC.childElementCursor();
        while (cursor.getNext() != null) {
          if (StringUtils.equalsIgnoreCase("key", cursor.getLocalName())) {
            String key = StringUtils.trim(cursor.collectDescendantText(false));
            ruleKeys.add(key);
          }
        }
      }

    } catch (XMLStreamException e) {
      throw new IllegalStateException("XML is not valid", e);
    }
  }
  private ParamStruct processParameter(SMInputCursor ruleC) throws XMLStreamException {
    ParamStruct param = new ParamStruct();

    // BACKWARD COMPATIBILITY WITH DEPRECATED FORMAT
    String keyAttribute = ruleC.getAttrValue("key");
    if (StringUtils.isNotBlank(keyAttribute)) {
      param.key = StringUtils.trim(keyAttribute);
    }

    // BACKWARD COMPATIBILITY WITH DEPRECATED FORMAT
    String typeAttribute = ruleC.getAttrValue("type");
    if (StringUtils.isNotBlank(typeAttribute)) {
      param.type = RuleParamType.parse(typeAttribute);
    }

    SMInputCursor paramC = ruleC.childElementCursor();
    while (paramC.getNext() != null) {
      String propNodeName = paramC.getLocalName();
      String propText = StringUtils.trim(paramC.collectDescendantText(false));
      if (StringUtils.equalsIgnoreCase("key", propNodeName)) {
        param.key = propText;

      } else if (StringUtils.equalsIgnoreCase("description", propNodeName)) {
        param.description = propText;

      } else if (StringUtils.equalsIgnoreCase("type", propNodeName)) {
        param.type = RuleParamType.parse(propText);

      } else if (StringUtils.equalsIgnoreCase("defaultValue", propNodeName)) {
        param.defaultValue = propText;
      }
    }
    return param;
  }
示例#5
0
  private static void processRule(Rule rule, SMInputCursor ruleC) throws XMLStreamException {
    /* BACKWARD COMPATIBILITY WITH DEPRECATED FORMAT */
    String keyAttribute = ruleC.getAttrValue("key");
    if (StringUtils.isNotBlank(keyAttribute)) {
      rule.setKey(StringUtils.trim(keyAttribute));
    }

    /* BACKWARD COMPATIBILITY WITH DEPRECATED FORMAT */
    String priorityAttribute = ruleC.getAttrValue("priority");
    if (StringUtils.isNotBlank(priorityAttribute)) {
      rule.setSeverity(RulePriority.valueOf(StringUtils.trim(priorityAttribute)));
    }

    List<String> tags = Lists.newArrayList();
    SMInputCursor cursor = ruleC.childElementCursor();

    while (cursor.getNext() != null) {
      String nodeName = cursor.getLocalName();

      if (StringUtils.equalsIgnoreCase("name", nodeName)) {
        rule.setName(StringUtils.trim(cursor.collectDescendantText(false)));

      } else if (StringUtils.equalsIgnoreCase("description", nodeName)) {
        rule.setDescription(StringUtils.trim(cursor.collectDescendantText(false)));

      } else if (StringUtils.equalsIgnoreCase("key", nodeName)) {
        rule.setKey(StringUtils.trim(cursor.collectDescendantText(false)));

      } else if (StringUtils.equalsIgnoreCase("configKey", nodeName)) {
        rule.setConfigKey(StringUtils.trim(cursor.collectDescendantText(false)));

      } else if (StringUtils.equalsIgnoreCase("priority", nodeName)) {
        rule.setSeverity(
            RulePriority.valueOf(StringUtils.trim(cursor.collectDescendantText(false))));

      } else if (StringUtils.equalsIgnoreCase("cardinality", nodeName)) {
        rule.setCardinality(
            Cardinality.valueOf(StringUtils.trim(cursor.collectDescendantText(false))));

      } else if (StringUtils.equalsIgnoreCase("status", nodeName)) {
        rule.setStatus(StringUtils.trim(cursor.collectDescendantText(false)));

      } else if (StringUtils.equalsIgnoreCase("param", nodeName)) {
        processParameter(rule, cursor);

      } else if (StringUtils.equalsIgnoreCase("tag", nodeName)) {
        tags.add(StringUtils.trim(cursor.collectDescendantText(false)));
      }
    }
    if (Strings.isNullOrEmpty(rule.getKey())) {
      throw new SonarException("Node <key> is missing in <rule>");
    }
    rule.setTags(tags.toArray(new String[tags.size()]));
  }
  private static void processParameters(SMInputCursor propsCursor, Map<String, String> parameters)
      throws XMLStreamException {
    while (propsCursor.getNext() != null) {
      SMInputCursor propCursor = propsCursor.childElementCursor();
      String key = null;
      String value = null;
      while (propCursor.getNext() != null) {
        String nodeName = propCursor.getLocalName();
        if (StringUtils.equals("key", nodeName)) {
          key = StringUtils.trim(propCursor.collectDescendantText(false));

        } else if (StringUtils.equals("value", nodeName)) {
          value = StringUtils.trim(propCursor.collectDescendantText(false));
        }
      }
      if (key != null) {
        parameters.put(key, value);
      }
    }
  }
 private void createViolation(SMInputCursor violationsCursor, Rule currentRule)
     throws XMLStreamException {
   org.sonar.api.resources.File sonarFile =
       org.sonar.api.resources.File.fromIOFile(
           new File(violationsCursor.getAttrValue("Source")), project);
   if (context.isIndexed(sonarFile, false)) {
     Violation violation = Violation.create(currentRule, sonarFile);
     String lineNumber = violationsCursor.getAttrValue("LineNumber");
     if (lineNumber != null) {
       violation.setLineId(Integer.parseInt(lineNumber));
     }
     violation.setMessage(violationsCursor.collectDescendantText().trim());
     violation.setSeverity(currentRule.getSeverity());
     context.saveViolation(violation);
   } else {
     LOG.debug("Violation could not be saved, associated resource not indexed " + sonarFile);
   }
 }
示例#8
0
  private static void processParameter(Rule rule, SMInputCursor ruleC) throws XMLStreamException {
    RuleParam param = rule.createParameter();

    String keyAttribute = ruleC.getAttrValue("key");
    if (StringUtils.isNotBlank(keyAttribute)) {
      /* BACKWARD COMPATIBILITY WITH DEPRECATED FORMAT */
      param.setKey(StringUtils.trim(keyAttribute));
    }

    String typeAttribute = ruleC.getAttrValue("type");
    if (StringUtils.isNotBlank(typeAttribute)) {
      /* BACKWARD COMPATIBILITY WITH DEPRECATED FORMAT */
      param.setType(type(StringUtils.trim(typeAttribute)));
    }

    SMInputCursor paramC = ruleC.childElementCursor();
    while (paramC.getNext() != null) {
      String propNodeName = paramC.getLocalName();
      String propText = StringUtils.trim(paramC.collectDescendantText(false));
      if (StringUtils.equalsIgnoreCase("key", propNodeName)) {
        param.setKey(propText);

      } else if (StringUtils.equalsIgnoreCase("description", propNodeName)) {
        param.setDescription(propText);

      } else if (StringUtils.equalsIgnoreCase("type", propNodeName)) {
        param.setType(type(propText));

      } else if (StringUtils.equalsIgnoreCase("defaultValue", propNodeName)) {
        param.setDefaultValue(propText);
      }
    }
    if (Strings.isNullOrEmpty(param.getKey())) {
      throw new SonarException("Node <key> is missing in <param>");
    }
  }
  private void processRule(RulesDefinition.NewExtendedRepository repo, SMInputCursor ruleC)
      throws XMLStreamException {
    String key = null;
    String name = null;
    String description = null;
    String internalKey = null;
    String severity = Severity.defaultSeverity();
    String status = null;
    Cardinality cardinality = Cardinality.SINGLE;
    List<ParamStruct> params = new ArrayList<>();
    List<String> tags = new ArrayList<>();

    /* BACKWARD COMPATIBILITY WITH VERY OLD FORMAT */
    String keyAttribute = ruleC.getAttrValue("key");
    if (StringUtils.isNotBlank(keyAttribute)) {
      key = StringUtils.trim(keyAttribute);
    }
    String priorityAttribute = ruleC.getAttrValue("priority");
    if (StringUtils.isNotBlank(priorityAttribute)) {
      severity = StringUtils.trim(priorityAttribute);
    }

    SMInputCursor cursor = ruleC.childElementCursor();
    while (cursor.getNext() != null) {
      String nodeName = cursor.getLocalName();

      if (StringUtils.equalsIgnoreCase("name", nodeName)) {
        name = StringUtils.trim(cursor.collectDescendantText(false));

      } else if (StringUtils.equalsIgnoreCase("description", nodeName)) {
        description = StringUtils.trim(cursor.collectDescendantText(false));

      } else if (StringUtils.equalsIgnoreCase("key", nodeName)) {
        key = StringUtils.trim(cursor.collectDescendantText(false));

      } else if (StringUtils.equalsIgnoreCase("configKey", nodeName)) {
        // deprecated field, replaced by internalKey
        internalKey = StringUtils.trim(cursor.collectDescendantText(false));

      } else if (StringUtils.equalsIgnoreCase("internalKey", nodeName)) {
        internalKey = StringUtils.trim(cursor.collectDescendantText(false));

      } else if (StringUtils.equalsIgnoreCase("priority", nodeName)) {
        // deprecated field, replaced by severity
        severity = StringUtils.trim(cursor.collectDescendantText(false));

      } else if (StringUtils.equalsIgnoreCase("severity", nodeName)) {
        severity = StringUtils.trim(cursor.collectDescendantText(false));

      } else if (StringUtils.equalsIgnoreCase("cardinality", nodeName)) {
        cardinality = Cardinality.valueOf(StringUtils.trim(cursor.collectDescendantText(false)));

      } else if (StringUtils.equalsIgnoreCase("status", nodeName)) {
        status = StringUtils.trim(cursor.collectDescendantText(false));

      } else if (StringUtils.equalsIgnoreCase("param", nodeName)) {
        params.add(processParameter(cursor));

      } else if (StringUtils.equalsIgnoreCase("tag", nodeName)) {
        tags.add(StringUtils.trim(cursor.collectDescendantText(false)));
      }
    }
    RulesDefinition.NewRule rule =
        repo.createRule(key)
            .setHtmlDescription(description)
            .setSeverity(severity)
            .setName(name)
            .setInternalKey(internalKey)
            .setTags(tags.toArray(new String[tags.size()]))
            .setTemplate(cardinality == Cardinality.MULTIPLE);
    if (status != null) {
      rule.setStatus(RuleStatus.valueOf(status));
    }
    for (ParamStruct param : params) {
      rule.createParam(param.key)
          .setDefaultValue(param.defaultValue)
          .setType(param.type)
          .setDescription(param.description);
    }
  }