You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@karaf.apache.org by gg...@apache.org on 2017/12/06 19:03:55 UTC
[karaf] 07/17: [KARAF-5468] Add comments to generated
target/assembly/etc/profile.cfg
This is an automated email from the ASF dual-hosted git repository.
ggrzybek pushed a commit to branch KARAF-5376-overrides_v2
in repository https://gitbox.apache.org/repos/asf/karaf.git
commit 52b88dfdb2223ede0c3b8c30280eb7e45e5ea18a
Author: Grzegorz Grzybek <gr...@gmail.com>
AuthorDate: Fri Nov 17 12:58:20 2017 +0100
[KARAF-5468] Add comments to generated target/assembly/etc/profile.cfg
---
.../org/apache/karaf/profile/ProfileConstants.java | 5 +
.../org/apache/karaf/profile/assembly/Builder.java | 2 -
.../karaf/profile/impl/ProfileBuilderImpl.java | 187 ++++++++++++++++++---
.../apache/karaf/profile/impl/PropertiesTest.java | 41 +++++
4 files changed, 211 insertions(+), 24 deletions(-)
diff --git a/profile/src/main/java/org/apache/karaf/profile/ProfileConstants.java b/profile/src/main/java/org/apache/karaf/profile/ProfileConstants.java
index fe9417d..8df688b 100644
--- a/profile/src/main/java/org/apache/karaf/profile/ProfileConstants.java
+++ b/profile/src/main/java/org/apache/karaf/profile/ProfileConstants.java
@@ -46,6 +46,11 @@ public interface ProfileConstants {
String HIDDEN = "hidden";
/**
+ * The attribute key for the <em>overlay</em> flag meaning the parents are already included/merged in the profile.
+ */
+ String OVERLAY = "overlay";
+
+ /**
* <p>Key indicating a deletion.</p>
* <p>This value can appear as the value of a key in a configuration
* or as a key itself. If used as a key, the whole configuration
diff --git a/profile/src/main/java/org/apache/karaf/profile/assembly/Builder.java b/profile/src/main/java/org/apache/karaf/profile/assembly/Builder.java
index 6df4243..672d166 100644
--- a/profile/src/main/java/org/apache/karaf/profile/assembly/Builder.java
+++ b/profile/src/main/java/org/apache/karaf/profile/assembly/Builder.java
@@ -788,7 +788,6 @@ public class Builder {
// Unzip KARs
//
LOGGER.info("Unzipping kars");
-// Map<String, RepositoryInfo> repositories = new LinkedHashMap<>(this.repositories);
Downloader downloader = manager.createDownloader();
for (String kar : kars.keySet()) {
downloader.download(kar, null);
@@ -811,7 +810,6 @@ public class Builder {
// Propagate feature installation from repositories
//
LOGGER.info("Loading repositories");
-// Map<String, Stage> features = new LinkedHashMap<>(this.features);
Map<String, Features> karRepositories = loadRepositories(manager, repositories.keySet(), false);
for (String repo : repositories.keySet()) {
RepositoryInfo info = repositories.get(repo);
diff --git a/profile/src/main/java/org/apache/karaf/profile/impl/ProfileBuilderImpl.java b/profile/src/main/java/org/apache/karaf/profile/impl/ProfileBuilderImpl.java
index 10331bd..24dbe98 100644
--- a/profile/src/main/java/org/apache/karaf/profile/impl/ProfileBuilderImpl.java
+++ b/profile/src/main/java/org/apache/karaf/profile/impl/ProfileBuilderImpl.java
@@ -22,15 +22,18 @@ import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
+import java.util.LinkedHashMap;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;
+import org.apache.felix.utils.properties.TypedProperties;
import org.apache.karaf.profile.Profile;
import org.apache.karaf.profile.ProfileBuilder;
+import static org.apache.karaf.profile.ProfileConstants.*;
import static org.apache.karaf.profile.impl.ProfileImpl.ConfigListType;
/**
@@ -39,7 +42,7 @@ import static org.apache.karaf.profile.impl.ProfileImpl.ConfigListType;
public final class ProfileBuilderImpl implements ProfileBuilder {
private String profileId;
- private Map<String, byte[]> fileMapping = new HashMap<>();
+ private Map<String, FileContent> fileMapping = new HashMap<>();
private boolean isOverlay;
@Override
@@ -58,7 +61,7 @@ public final class ProfileBuilderImpl implements ProfileBuilder {
@Override
public List<String> getParents() {
Map<String, Object> config = getConfigurationInternal(Profile.INTERNAL_PID);
- String pspec = (String) config.get(Profile.PARENTS);
+ String pspec = (String) config.get(PARENTS);
String[] parentIds = pspec != null ? pspec.split(" ") : new String[0];
return Arrays.asList(parentIds);
}
@@ -100,9 +103,9 @@ public final class ProfileBuilderImpl implements ProfileBuilder {
private void updateParentsAttribute(Collection<String> parentIds) {
Map<String, Object> config = getConfigurationInternal(Profile.INTERNAL_PID);
- config.remove(Profile.PARENTS);
+ config.remove(PARENTS);
if (parentIds.size() > 0) {
- config.put(Profile.PARENTS, parentsAttributeValue(parentIds));
+ config.put(PARENTS, parentsAttributeValue(parentIds));
}
addConfiguration(Profile.INTERNAL_PID, config);
}
@@ -118,18 +121,19 @@ public final class ProfileBuilderImpl implements ProfileBuilder {
@Override
public byte[] getFileConfiguration(String key) {
- return fileMapping.get(key);
+ return fileMapping.get(key) == null ? null : fileMapping.get(key).bytes;
}
- @Override
- public ProfileBuilder setFileConfigurations(Map<String, byte[]> configurations) {
- fileMapping = new HashMap<>(configurations);
- return this;
- }
+ @Override
+ public ProfileBuilder setFileConfigurations(Map<String, byte[]> configurations) {
+ fileMapping = new HashMap<>();
+ configurations.forEach((name, bytes) -> fileMapping.put(name, new FileContent(bytes, false)));
+ return this;
+ }
@Override
public ProfileBuilder addFileConfiguration(String fileName, byte[] data) {
- fileMapping.put(fileName, data);
+ fileMapping.put(fileName, new FileContent(data, false));
return this;
}
@@ -152,7 +156,7 @@ public final class ProfileBuilderImpl implements ProfileBuilder {
@Override
public ProfileBuilder addConfiguration(String pid, Map<String, Object> config) {
- fileMapping.put(pid + Profile.PROPERTIES_SUFFIX, Utils.toBytes(config));
+ fileMapping.put(pid + Profile.PROPERTIES_SUFFIX, new FileContent(Utils.toBytes(config), true));
return this;
}
@@ -181,8 +185,8 @@ public final class ProfileBuilderImpl implements ProfileBuilder {
}
private Map<String, Object> getConfigurationInternal(String pid) {
- byte[] bytes = fileMapping.get(pid + Profile.PROPERTIES_SUFFIX);
- return Utils.toProperties(bytes);
+ FileContent content = fileMapping.get(pid + Profile.PROPERTIES_SUFFIX);
+ return Utils.toProperties(content == null ? null : content.bytes);
}
@Override
@@ -239,10 +243,11 @@ public final class ProfileBuilderImpl implements ProfileBuilder {
return this;
}
- public ProfileBuilder setOverlay(boolean overlay) {
- this.isOverlay = overlay;
- return this;
- }
+ public ProfileBuilder setOverlay(boolean overlay) {
+ this.isOverlay = overlay;
+ addConfiguration(Profile.INTERNAL_PID, Profile.ATTRIBUTE_PREFIX + Profile.OVERLAY, Boolean.toString(overlay));
+ return this;
+ }
@Override
public ProfileBuilder addAttribute(String key, String value) {
@@ -286,10 +291,148 @@ public final class ProfileBuilderImpl implements ProfileBuilder {
addConfiguration(Profile.INTERNAL_PID, config);
}
-
+ /**
+ * Returns an immutable implementation of {@link Profile}
+ * @return
+ */
@Override
- public Profile getProfile() {
- return new ProfileImpl(profileId, getParents(), fileMapping, isOverlay);
- }
+ public Profile getProfile() {
+ // reformatting all generated files.
+ Map<String, byte[]> files = new LinkedHashMap<>();
+ fileMapping.forEach((k, v) -> files.put(k, reformat(k, v)));
+ return new ProfileImpl(profileId, getParents(), files, isOverlay);
+ }
+
+ /**
+ * If some properties file has been marked as {@link FileContent#generated}, then we can add some comment hints.
+ * @param name
+ * @param fileContent
+ * @return
+ */
+ private byte[] reformat(String name, FileContent fileContent) {
+ if (!fileContent.generated && !(isOverlay && name.equals(INTERNAL_PID + PROPERTIES_SUFFIX))) {
+ return fileContent.bytes;
+ }
+
+ TypedProperties properties = Utils.toProperties(fileContent.bytes);
+ TypedProperties result = Utils.toProperties((byte[])null);
+
+ String parents = null;
+ Map<String, Object> attributes = new LinkedHashMap<>();
+ Map<String, Object> repositories = new LinkedHashMap<>();
+ Map<String, Object> features = new LinkedHashMap<>();
+ Map<String, Object> bundles = new LinkedHashMap<>();
+ Map<String, Object> libraries = new LinkedHashMap<>();
+ Map<String, Object> bootLibraries = new LinkedHashMap<>();
+ Map<String, Object> endorsedLibraries = new LinkedHashMap<>();
+ Map<String, Object> extLibraries = new LinkedHashMap<>();
+ Map<String, Object> config = new LinkedHashMap<>();
+ Map<String, Object> system = new LinkedHashMap<>();
+ Map<String, Object> overrides = new LinkedHashMap<>();
+ Map<String, Object> optionals = new LinkedHashMap<>();
+ for (String key : properties.keySet()) {
+ Object v = properties.get(key);
+ if (key.equals(PARENTS)) {
+ parents = (String) v;
+ } else if (key.startsWith(ATTRIBUTE_PREFIX)) {
+ attributes.put(key, v);
+ } else if (key.startsWith(REPOSITORY_PREFIX)) {
+ repositories.put(key, v);
+ } else if (key.startsWith(FEATURE_PREFIX)) {
+ features.put(key, v);
+ } else if (key.startsWith(BUNDLE_PREFIX)) {
+ bundles.put(key, v);
+ } else if (key.startsWith(LIB_PREFIX)) {
+ libraries.put(key, v);
+ } else if (key.startsWith(BOOT_PREFIX)) {
+ bootLibraries.put(key, v);
+ } else if (key.startsWith(ENDORSED_PREFIX)) {
+ endorsedLibraries.put(key, v);
+ } else if (key.startsWith(EXT_PREFIX)) {
+ extLibraries.put(key, v);
+ } else if (key.startsWith(CONFIG_PREFIX)) {
+ config.put(key, v);
+ } else if (key.startsWith(SYSTEM_PREFIX)) {
+ system.put(key, v);
+ } else if (key.startsWith(OVERRIDE_PREFIX)) {
+ overrides.put(key, v);
+ } else if (key.startsWith(OPTIONAL_PREFIX)) {
+ optionals.put(key, v);
+ }
+ }
+
+ result.setHeader(Arrays.asList("#", "# Profile generated by Karaf Assembly Builder", "#"));
+ if (parents != null) {
+ result.put(PARENTS, comment("Parent profiles"), parents);
+ }
+ addGroupOfProperties("Attributes", result, attributes);
+ addGroupOfProperties("Feature XML repositories", result, repositories);
+ addGroupOfProperties("Features", result, features);
+ addGroupOfProperties("Bundles", result, bundles);
+ addGroupOfProperties("Libraries", result, libraries);
+ addGroupOfProperties("Boot libraries", result, bootLibraries);
+ addGroupOfProperties("Endorsed libraries", result, endorsedLibraries);
+ addGroupOfProperties("Extension libraries", result, extLibraries);
+ addGroupOfProperties("Configuration properties for etc/config.properties", result, config);
+ addGroupOfProperties("Configuration properties for etc/system.properties", result, system);
+ addGroupOfProperties("Bundle overrides (deprecated)", result, overrides);
+ addGroupOfProperties("Optional resources for resolution", result, optionals);
+
+ return Utils.toBytes(result);
+ }
+
+ /**
+ * Puts properties under single comment.
+ * @param comment
+ * @param properties
+ * @param values
+ */
+ private void addGroupOfProperties(String comment, TypedProperties properties, Map<String, Object> values) {
+ boolean first = true;
+ for (Entry<String, Object> entry : values.entrySet()) {
+ if (first) {
+ first = false;
+ properties.put(entry.getKey(), comment(comment), entry.getValue());
+ } else {
+ properties.put(entry.getKey(), entry.getValue());
+ }
+ }
+ }
+
+ /**
+ * Helper method to generate comments above property groups in {@link TypedProperties}
+ * @param comment
+ * @return
+ */
+ private List<String> comment(String comment) {
+ return Arrays.asList("", "# " + comment);
+ }
+
+ /**
+ * We can distinguish between bytes read from external file and bytes from serialized
+ * {@link org.apache.felix.utils.properties.TypedProperties}
+ */
+ static class FileContent {
+ byte[] bytes;
+ boolean generated;
+
+ public FileContent(byte[] bytes, boolean generated) {
+ this.bytes = bytes;
+ this.generated = generated;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+ FileContent that = (FileContent) o;
+ return Arrays.equals(bytes, that.bytes);
+ }
+
+ @Override
+ public int hashCode() {
+ return Arrays.hashCode(bytes);
+ }
+ }
}
diff --git a/profile/src/test/java/org/apache/karaf/profile/impl/PropertiesTest.java b/profile/src/test/java/org/apache/karaf/profile/impl/PropertiesTest.java
new file mode 100644
index 0000000..a8a0edc
--- /dev/null
+++ b/profile/src/test/java/org/apache/karaf/profile/impl/PropertiesTest.java
@@ -0,0 +1,41 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.karaf.profile.impl;
+
+import java.io.IOException;
+import java.util.Arrays;
+
+import org.apache.felix.utils.properties.TypedProperties;
+import org.junit.Test;
+
+public class PropertiesTest {
+
+ @Test
+ public void typedProperties() throws IOException {
+ TypedProperties tp = new TypedProperties();
+ tp.put("commented-key", "# commented-key comment", "value");
+ tp.put("commented-key2", Arrays.asList("# ca", "# cb"), "value");
+ tp.put("normal-key", "value");
+ tp.put("listed-key", Arrays.asList("# ca", "# cb"), Arrays.asList("va", "vb"));
+ tp.setHeader(Arrays.asList("#", "# ASF License 2.0", "#"));
+ tp.setFooter(Arrays.asList("#", "# bye!", "#"));
+ tp.save(System.out);
+ }
+
+}
--
To stop receiving notification emails like this one, please contact
"commits@karaf.apache.org" <co...@karaf.apache.org>.