Skip to content

Commit 14737e1

Browse files
committed
Add aemTenantsCloudManagerConditional handlebar helper to build conditional sling mapping definitions for AEM cloud service with a sling dispatcher configuration.
1 parent 95d8a76 commit 14737e1

5 files changed

Lines changed: 305 additions & 0 deletions

File tree

changes.xml

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,9 @@
2424
<body>
2525

2626
<release version="1.12.0" date="not released">
27+
<action type="add" dev="sseifert">
28+
Add aemTenantsCloudManagerConditional handlebar helper to build conditional sling mapping definitions for AEM cloud service with a sling dispatcher configuration.
29+
</action>
2730
<action type="add" dev="sseifert">
2831
conga-aem-maven-plugin: Add new parameter autoDependenciesMode which replaces/supercedes autoDependencies and autoDependenciesSeparateMutable flags.
2932
</action>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,184 @@
1+
/*
2+
* #%L
3+
* wcm.io
4+
* %%
5+
* Copyright (C) 2020 wcm.io
6+
* %%
7+
* Licensed under the Apache License, Version 2.0 (the "License");
8+
* you may not use this file except in compliance with the License.
9+
* You may obtain a copy of the License at
10+
*
11+
* http://www.apache.org/licenses/LICENSE-2.0
12+
*
13+
* Unless required by applicable law or agreed to in writing, software
14+
* distributed under the License is distributed on an "AS IS" BASIS,
15+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16+
* See the License for the specific language governing permissions and
17+
* limitations under the License.
18+
* #L%
19+
*/
20+
package io.wcm.devops.conga.plugins.aem.handlebars.helper;
21+
22+
import java.io.IOException;
23+
import java.util.ArrayList;
24+
import java.util.LinkedHashMap;
25+
import java.util.List;
26+
import java.util.Map;
27+
import java.util.stream.Collectors;
28+
29+
import org.apache.commons.lang3.builder.EqualsBuilder;
30+
import org.apache.commons.lang3.builder.HashCodeBuilder;
31+
import org.apache.commons.lang3.builder.ToStringBuilder;
32+
import org.apache.commons.lang3.builder.ToStringStyle;
33+
34+
import com.github.jknack.handlebars.Options;
35+
36+
import io.wcm.devops.conga.generator.ContextProperties;
37+
import io.wcm.devops.conga.generator.spi.handlebars.HelperPlugin;
38+
import io.wcm.devops.conga.generator.spi.handlebars.context.HelperContext;
39+
import io.wcm.devops.conga.model.environment.Tenant;
40+
import io.wcm.devops.conga.model.util.MapExpander;
41+
42+
/**
43+
* Gets all tenants which have a "httpd.cloudManagerConditional" configuration set, grouped by targetEnvironment value.
44+
* The resulting map with environment name as key and list of conditional configuration maps as value is
45+
* set to a context variable with the given name.
46+
*/
47+
public final class AemTenantsCloudManagerConditionalHelper implements HelperPlugin<Object> {
48+
49+
/**
50+
* Plugin/Helper name
51+
*/
52+
public static final String NAME = "aemTenantsCloudManagerConditional";
53+
54+
static final String CLOUD_MANAGER_CONDITIONAL_KEY = "httpd.cloudManagerConditional";
55+
static final String TARGET_ENVIRONMENT_KEY = "targetEnvironment";
56+
57+
@Override
58+
public String getName() {
59+
return NAME;
60+
}
61+
62+
@Override
63+
public Object apply(Object context, Options options, HelperContext pluginContext) throws IOException {
64+
String variableName = null;
65+
if (context instanceof String) {
66+
variableName = (String)context;
67+
}
68+
69+
// get tenants from context
70+
Object tenants = options.context.get(ContextProperties.TENANTS);
71+
72+
// generate grouped result map
73+
Map<String, List<CloudManagerConditional>> result = getTenantConfigs(tenants).stream()
74+
.flatMap(tenantConfig -> tenantConfig.getCloudManagerConditionals().stream())
75+
.filter(item -> item.getTargetEnvironment() != null)
76+
.collect(Collectors.groupingBy(CloudManagerConditional::getTargetEnvironment, LinkedHashMap::new, Collectors.toList()));
77+
78+
// set variable
79+
if (variableName != null) {
80+
options.context.data(variableName, result);
81+
}
82+
83+
return null;
84+
}
85+
86+
@SuppressWarnings("unchecked")
87+
private List<TenantConfig> getTenantConfigs(Object object) {
88+
List<TenantConfig> result = new ArrayList<>();
89+
if (object instanceof List) {
90+
List<Tenant> tenants = (List<Tenant>)object;
91+
for (Tenant tenant : tenants) {
92+
result.add(new TenantConfig(tenant));
93+
}
94+
}
95+
return result;
96+
}
97+
98+
private static class TenantConfig {
99+
100+
private final Tenant tenant;
101+
102+
TenantConfig(Tenant tenant) {
103+
this.tenant = tenant;
104+
}
105+
106+
@SuppressWarnings("unchecked")
107+
public List<CloudManagerConditional> getCloudManagerConditionals() {
108+
List<CloudManagerConditional> result = new ArrayList<>();
109+
Object object = MapExpander.getDeep(tenant.getConfig(), CLOUD_MANAGER_CONDITIONAL_KEY);
110+
if (object instanceof List) {
111+
List<Map<String, Object>> items = (List<Map<String, Object>>)object;
112+
for (Map<String, Object> item : items) {
113+
result.add(new CloudManagerConditional(item, tenant));
114+
}
115+
}
116+
return result;
117+
}
118+
119+
}
120+
121+
/**
122+
* Cloud manager conditional result per tenant and target environment.
123+
*/
124+
public static class CloudManagerConditional {
125+
126+
private final Map<String, Object> config;
127+
private final Tenant tenant;
128+
private final String targetEnvironment;
129+
130+
CloudManagerConditional(Map<String, Object> config, Tenant tenant) {
131+
this.config = config;
132+
this.tenant = tenant;
133+
Object value = config.get(TARGET_ENVIRONMENT_KEY);
134+
if (value instanceof String) {
135+
this.targetEnvironment = (String)value;
136+
}
137+
else {
138+
this.targetEnvironment = null;
139+
}
140+
}
141+
142+
public String getTargetEnvironment() {
143+
return targetEnvironment;
144+
}
145+
146+
public Map<String, Object> getConfig() {
147+
return config;
148+
}
149+
150+
public Tenant getTenant() {
151+
return this.tenant;
152+
}
153+
154+
@Override
155+
public int hashCode() {
156+
return new HashCodeBuilder()
157+
.append(config)
158+
.append(tenant.getTenant())
159+
.toHashCode();
160+
}
161+
162+
@Override
163+
public boolean equals(Object obj) {
164+
if (obj instanceof CloudManagerConditional) {
165+
CloudManagerConditional other = (CloudManagerConditional)obj;
166+
return new EqualsBuilder()
167+
.append(config, other.config)
168+
.append(tenant.getTenant(), other.tenant.getTenant())
169+
.isEquals();
170+
}
171+
return false;
172+
}
173+
174+
@Override
175+
public String toString() {
176+
return new ToStringBuilder(this, ToStringStyle.NO_CLASS_NAME_STYLE)
177+
.append("config", config)
178+
.append("tenant", tenant.getTenant())
179+
.toString();
180+
}
181+
182+
}
183+
184+
}

conga-aem-plugin/src/main/resources/META-INF/services/io.wcm.devops.conga.generator.spi.handlebars.HelperPlugin

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
io.wcm.devops.conga.plugins.aem.handlebars.helper.AemCryptoEncryptHelper
22
io.wcm.devops.conga.plugins.aem.handlebars.helper.AemDispatcherFilterHelper
33
io.wcm.devops.conga.plugins.aem.handlebars.helper.AemHttpdFilterHelper
4+
io.wcm.devops.conga.plugins.aem.handlebars.helper.AemTenantsCloudManagerConditionalHelper
45
io.wcm.devops.conga.plugins.aem.handlebars.helper.OakAuthorizableUuidHelper
56
io.wcm.devops.conga.plugins.aem.handlebars.helper.OakPasswordHashHelper
67
io.wcm.devops.conga.plugins.aem.handlebars.helper.WebConsolePasswordHashHelper
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,113 @@
1+
/*
2+
* #%L
3+
* wcm.io
4+
* %%
5+
* Copyright (C) 2017 wcm.io
6+
* %%
7+
* Licensed under the Apache License, Version 2.0 (the "License");
8+
* you may not use this file except in compliance with the License.
9+
* You may obtain a copy of the License at
10+
*
11+
* http://www.apache.org/licenses/LICENSE-2.0
12+
*
13+
* Unless required by applicable law or agreed to in writing, software
14+
* distributed under the License is distributed on an "AS IS" BASIS,
15+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16+
* See the License for the specific language governing permissions and
17+
* limitations under the License.
18+
* #L%
19+
*/
20+
package io.wcm.devops.conga.plugins.aem.handlebars.helper;
21+
22+
import static io.wcm.devops.conga.plugins.aem.handlebars.helper.TestUtils.assertHelper;
23+
import static org.junit.jupiter.api.Assertions.assertEquals;
24+
25+
import java.util.List;
26+
import java.util.Map;
27+
28+
import org.junit.jupiter.api.BeforeEach;
29+
import org.junit.jupiter.api.Test;
30+
31+
import com.github.jknack.handlebars.Options;
32+
import com.google.common.collect.ImmutableList;
33+
import com.google.common.collect.ImmutableMap;
34+
35+
import io.wcm.devops.conga.generator.ContextProperties;
36+
import io.wcm.devops.conga.generator.spi.handlebars.HelperPlugin;
37+
import io.wcm.devops.conga.generator.util.PluginManagerImpl;
38+
import io.wcm.devops.conga.model.environment.Tenant;
39+
import io.wcm.devops.conga.plugins.aem.handlebars.helper.AemTenantsCloudManagerConditionalHelper.CloudManagerConditional;
40+
41+
public class AemTenantsCloudManagerConditionalHelperTest {
42+
43+
private HelperPlugin<Object> helper;
44+
45+
@SuppressWarnings("unchecked")
46+
@BeforeEach
47+
public void setUp() {
48+
helper = new PluginManagerImpl().get(AemTenantsCloudManagerConditionalHelper.NAME, HelperPlugin.class);
49+
}
50+
51+
@Test
52+
public void testNull() throws Exception {
53+
Options options = new MockOptions();
54+
55+
assertHelper(null, helper, "my-var", options);
56+
57+
Map<String, List<Map<String, Object>>> expectedResult = ImmutableMap.of();
58+
assertEquals(expectedResult, options.context.get("my-var"));
59+
}
60+
61+
@Test
62+
public void testEmpty() throws Exception {
63+
Options options = new MockOptions();
64+
65+
List<Map<String, Object>> tenants = ImmutableList.of();
66+
options.context.data(ContextProperties.TENANTS, tenants);
67+
68+
assertHelper(null, helper, "my-var", options);
69+
70+
Map<String, List<Map<String, Object>>> expectedResult = ImmutableMap.of();
71+
assertEquals(expectedResult, options.context.get("my-var"));
72+
}
73+
74+
@Test
75+
public void testTenants() throws Exception {
76+
Options options = new MockOptions();
77+
78+
Map<String, Object> tenant1_dev = ImmutableMap.of("targetEnvironment", "dev", "serverName", "name1-dev");
79+
Map<String, Object> tenant1_stage = ImmutableMap.of("targetEnvironment", "stage", "serverName", "name1-stage");
80+
Map<String, Object> tenant2_dev = ImmutableMap.of("targetEnvironment", "dev", "serverName", "name2-dev");
81+
Map<String, Object> tenant2_null = ImmutableMap.of("serverName", "name2-null");
82+
83+
Tenant tenant1 = new Tenant();
84+
tenant1.setTenant("tenant1");
85+
tenant1.setConfig(ImmutableMap.of("httpd", ImmutableMap.of("cloudManagerConditional", ImmutableList.of(tenant1_dev, tenant1_stage))));
86+
87+
Tenant tenant2 = new Tenant();
88+
tenant2.setTenant("tenant2");
89+
tenant2.setConfig(ImmutableMap.of("httpd", ImmutableMap.of("cloudManagerConditional", ImmutableList.of(tenant2_dev, tenant2_null))));
90+
91+
Tenant tenant3 = new Tenant();
92+
tenant3.setTenant("tenant3");
93+
tenant3.setConfig(ImmutableMap.of());
94+
95+
Tenant tenant4 = new Tenant();
96+
tenant4.setTenant("tenant4");
97+
tenant4.setConfig(ImmutableMap.of("httpd", ImmutableMap.of("cloudManagerConditional", "invalid")));
98+
99+
List<Tenant> tenants = ImmutableList.of(tenant1, tenant2, tenant3, tenant4);
100+
options.context.data(ContextProperties.TENANTS, tenants);
101+
102+
assertHelper(null, helper, "my-var", options);
103+
104+
Map<String, List<CloudManagerConditional>> expectedResult = ImmutableMap.of(
105+
"dev", ImmutableList.of(
106+
new CloudManagerConditional(tenant1_dev, tenant1),
107+
new CloudManagerConditional(tenant2_dev, tenant2)),
108+
"stage", ImmutableList.of(
109+
new CloudManagerConditional(tenant1_stage, tenant1)));
110+
assertEquals(expectedResult, options.context.get("my-var"));
111+
}
112+
113+
}

src/site/markdown/handlebars-helpers.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -133,6 +133,10 @@ Generates AEM dispatcher filter rules for a filter expression. See [CONGA AEM De
133133
}
134134
```
135135

136+
### aemTenantsCloudManagerConditional
137+
138+
Used to build conditional sling mapping definitions for AEM cloud service with a sling dispatcher configuration. See [CONGA AEM Definitions][aem-definitions] for an usage example.
139+
136140

137141

138142
[handlebars-quickstart]: ../../handlebars-quickstart.html

0 commit comments

Comments
 (0)