/** * Perform {@link com.android.manifmerger.ManifestMerger2.SystemProperty} injection. * * @param mergingReport to log actions and errors. * @param xmlDocument the xml document to inject into. */ protected void performSystemPropertiesInjection( MergingReport.Builder mergingReport, XmlDocument xmlDocument) { for (SystemProperty systemProperty : SystemProperty.values()) { String propertyOverride = mSystemPropertyResolver.getValue(systemProperty); if (propertyOverride != null) { systemProperty.addTo(mergingReport.getActionRecorder(), xmlDocument, propertyOverride); } } }
private void visit( @NonNull ManifestMerger2.MergeType mergeType, @NonNull XmlElement xmlElement, @NonNull KeyBasedValueResolver<String> valueProvider, @NonNull MergingReport.Builder mergingReportBuilder) { for (XmlAttribute xmlAttribute : xmlElement.getAttributes()) { StringBuilder resultString = new StringBuilder(); String inputString = xmlAttribute.getValue(); Matcher matcher = PATTERN.matcher(inputString); if (matcher.matches()) { while (matcher.matches()) { String placeholderValue = valueProvider.getValue(matcher.group(2)); // whatever precedes the placeholder key is added back to the string. resultString.append(matcher.group(1)); if (placeholderValue == null) { // if this is a library, ignore the failure MergingReport.Record.Severity severity = mergeType == ManifestMerger2.MergeType.LIBRARY ? MergingReport.Record.Severity.INFO : MergingReport.Record.Severity.ERROR; xmlAttribute.addMessage( mergingReportBuilder, severity, String.format( "Attribute %1$s at %2$s requires a placeholder substitution" + " but no value for <%3$s> is provided.", xmlAttribute.getId(), xmlAttribute.printPosition(), matcher.group(2))); // we add back the placeholder key, since this is not an error for libraries resultString.append("${"); resultString.append(matcher.group(2)); resultString.append("}"); } else { // record the attribute set mergingReportBuilder .getActionRecorder() .recordAttributeAction( xmlAttribute, PositionImpl.UNKNOWN, Actions.ActionType.INJECTED, null /* attributeOperationType */); // substitute the placeholder key with its value. resultString.append(placeholderValue); } // the new input string is the tail of the previous match, as it may contain // more placeholders to substitute. inputString = matcher.group(3); // reset the pattern matching with that new string to test for more placeholders matcher = PATTERN.matcher(inputString); } // append the last remainder (without placeholders) in the result string. resultString.append(inputString); xmlAttribute.getXml().setValue(resultString.toString()); } } for (XmlElement childElement : xmlElement.getMergeableElements()) { visit(mergeType, childElement, valueProvider, mergingReportBuilder); } }