1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.maven.internal.impl.model.profile;
20
21 import java.util.HashMap;
22 import java.util.Map;
23 import java.util.function.Function;
24
25 import org.apache.maven.api.di.Inject;
26 import org.apache.maven.api.di.Named;
27 import org.apache.maven.api.di.Singleton;
28 import org.apache.maven.api.model.Activation;
29 import org.apache.maven.api.model.Profile;
30 import org.apache.maven.api.services.BuilderProblem.Severity;
31 import org.apache.maven.api.services.ModelProblem.Version;
32 import org.apache.maven.api.services.ModelProblemCollector;
33 import org.apache.maven.api.services.VersionParser;
34 import org.apache.maven.api.services.model.ProfileActivationContext;
35 import org.apache.maven.api.services.model.ProfileActivator;
36 import org.apache.maven.internal.impl.model.DefaultInterpolator;
37
38 import static org.apache.maven.internal.impl.model.profile.ConditionParser.toBoolean;
39
40
41
42
43
44 @Named("condition")
45 @Singleton
46 public class ConditionProfileActivator implements ProfileActivator {
47
48 private final VersionParser versionParser;
49
50
51
52
53
54
55 @Inject
56 public ConditionProfileActivator(VersionParser versionParser) {
57 this.versionParser = versionParser;
58 }
59
60
61
62
63
64
65
66
67
68 @Override
69 public boolean isActive(Profile profile, ProfileActivationContext context, ModelProblemCollector problems) {
70 if (profile.getActivation() == null || profile.getActivation().getCondition() == null) {
71 return false;
72 }
73 String condition = profile.getActivation().getCondition();
74 try {
75 Map<String, ConditionParser.ExpressionFunction> functions = registerFunctions(context, versionParser);
76 Function<String, String> propertyResolver = s -> property(context, s);
77 return toBoolean(new ConditionParser(functions, propertyResolver).parse(condition));
78 } catch (Exception e) {
79 problems.add(
80 Severity.ERROR, Version.V41, "Error parsing profile activation condition: " + e.getMessage(), e);
81 return false;
82 }
83 }
84
85
86
87
88
89
90
91
92
93 @Override
94 public boolean presentInConfig(Profile profile, ProfileActivationContext context, ModelProblemCollector problems) {
95 Activation activation = profile.getActivation();
96 if (activation == null) {
97 return false;
98 }
99 return activation.getCondition() != null && !activation.getCondition().isBlank();
100 }
101
102
103
104
105
106
107
108
109 public static Map<String, ConditionParser.ExpressionFunction> registerFunctions(
110 ProfileActivationContext context, VersionParser versionParser) {
111 Map<String, ConditionParser.ExpressionFunction> functions = new HashMap<>();
112
113 ConditionFunctions conditionFunctions = new ConditionFunctions(context, versionParser);
114
115 for (java.lang.reflect.Method method : ConditionFunctions.class.getDeclaredMethods()) {
116 String methodName = method.getName();
117 if (methodName.endsWith("_")) {
118 methodName = methodName.substring(0, methodName.length() - 1);
119 }
120 final String finalMethodName = methodName;
121
122 functions.put(finalMethodName, args -> {
123 try {
124 return method.invoke(conditionFunctions, args);
125 } catch (Exception e) {
126 StringBuilder causeChain = new StringBuilder();
127 Throwable cause = e;
128 while (cause != null) {
129 if (!causeChain.isEmpty()) {
130 causeChain.append(" Caused by: ");
131 }
132 causeChain.append(cause.toString());
133 cause = cause.getCause();
134 }
135 throw new RuntimeException(
136 "Error invoking function '" + finalMethodName + "': " + e + ". Cause chain: " + causeChain,
137 e);
138 }
139 });
140 }
141
142 return functions;
143 }
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159 static String property(ProfileActivationContext context, String name) {
160 String value = doGetProperty(context, name);
161 return new DefaultInterpolator().interpolate(value, s -> doGetProperty(context, s));
162 }
163
164 static String doGetProperty(ProfileActivationContext context, String name) {
165
166 if ("project.basedir".equals(name)) {
167 return context.getModelBaseDirectory();
168 }
169 if ("project.rootDirectory".equals(name)) {
170 return context.getModelRootDirectory();
171 }
172 if ("project.artifactId".equals(name)) {
173 return context.getModelArtifactId();
174 }
175 if ("project.packaging".equals(name)) {
176 return context.getModelPackaging();
177 }
178
179
180 String v = context.getUserProperty(name);
181 if (v == null) {
182
183
184
185 v = context.getModelProperty(name);
186 }
187 if (v == null) {
188
189 v = context.getSystemProperty(name);
190 }
191 return v;
192 }
193 }