1
2 package it.serendigity.maven.plugin.lifecycle.helper;
3
4 import java.util.ArrayList;
5 import java.util.Arrays;
6 import java.util.List;
7 import java.util.Objects;
8
9 import org.apache.maven.execution.MavenSession;
10 import org.apache.maven.lifecycle.DefaultLifecycles;
11 import org.apache.maven.lifecycle.LifecycleExecutor;
12 import org.apache.maven.lifecycle.LifecycleNotFoundException;
13 import org.apache.maven.lifecycle.LifecyclePhaseNotFoundException;
14 import org.apache.maven.lifecycle.MavenExecutionPlan;
15 import org.apache.maven.lifecycle.internal.GoalTask;
16 import org.apache.maven.lifecycle.internal.LifecycleTask;
17 import org.apache.maven.lifecycle.internal.LifecycleTaskSegmentCalculator;
18 import org.apache.maven.lifecycle.internal.TaskSegment;
19 import org.apache.maven.plugin.AbstractMojo;
20 import org.apache.maven.plugin.InvalidPluginDescriptorException;
21 import org.apache.maven.plugin.MojoExecution;
22 import org.apache.maven.plugin.MojoFailureException;
23 import org.apache.maven.plugin.MojoNotFoundException;
24 import org.apache.maven.plugin.PluginDescriptorParsingException;
25 import org.apache.maven.plugin.PluginNotFoundException;
26 import org.apache.maven.plugin.PluginResolutionException;
27 import org.apache.maven.plugin.prefix.NoPluginFoundForPrefixException;
28 import org.apache.maven.plugin.version.PluginVersionResolutionException;
29 import org.apache.maven.plugins.annotations.Component;
30 import org.apache.maven.plugins.annotations.Parameter;
31 import org.apache.maven.project.MavenProject;
32 import org.apache.maven.shared.utils.logging.MessageUtils;
33
34 import it.serendigity.maven.plugin.lifecycle.helper.vo.MavenExecutionInfo;
35 import it.serendigity.maven.plugin.lifecycle.helper.vo.MavenExecutionPlanInfo;
36
37 public abstract class AbstractLifecycleMojo extends AbstractMojo {
38
39 @Parameter(defaultValue = "${session}", readonly = true)
40 private MavenSession session;
41
42 @Parameter(defaultValue = "${project}", readonly = true)
43 private MavenProject project;
44
45 @Component
46 private LifecycleExecutor lifecycleExecutor;
47
48 @Component
49 private LifecycleTaskSegmentCalculator lifecycleTaskSegmentCalculator;
50
51
52
53
54 @Component
55 protected DefaultLifecycles defaultLifecycles;
56
57
58
59
60
61
62
63 @Parameter(property = "lifecycle-helper.tasks", defaultValue = "post-clean,deploy,site-deploy")
64 private String[] paramLifecycleTasks;
65
66
67 @Parameter(property = "lifecycle-helper.filter.plugins")
68 private String[] paramFilterPlugins;
69
70
71
72
73
74 @Parameter(property = "lifecycle-helper.forceTasksFromSession", defaultValue = "false")
75 private boolean paramForceTasksFromSession;
76
77
78
79
80
81
82 @Parameter(property = "lifecycle-helper.skip", defaultValue = "false")
83 private boolean paramSkip;
84
85 protected boolean isParamForceTasksFromSession() {
86 return paramForceTasksFromSession;
87 }
88
89 private List<String> pluginToElaborate;
90 private String[] tasksToElaborate;
91
92 protected MavenExecutionPlanInfo calculateExecutionPlan( boolean calculateSummary ) throws MojoFailureException {
93
94 setPluginToElaborate( normalizeParamFilterPlugin() );
95
96 MavenExecutionPlanInfo planInfo = new MavenExecutionPlanInfo( calculateSummary );
97
98 try {
99
100 String[] tasks = calculateTasksToElaborate();
101 setTasksToElaborate( tasks );
102
103 MavenExecutionPlan calculateExecutionPlan = lifecycleExecutor.calculateExecutionPlan( session, tasks );
104 List<MojoExecution> mojoExecutions = calculateExecutionPlan.getMojoExecutions();
105
106 int order = 0;
107
108 for ( MojoExecution mojoExecution : mojoExecutions ) {
109
110 MavenExecutionInfo info = MavenExecutionInfo.from( order++, mojoExecution, defaultLifecycles );
111 if ( validateMavenExecution( info ) ) {
112 planInfo.addMavenExecutionInfo( info );
113 }
114 }
115
116 if ( planInfo.getMavenExecutionsInfo() == null || planInfo.getMavenExecutionsInfo().isEmpty() ) {
117 getLog().info( "No execution plan item found for requested parameters." );
118 }
119
120 }
121 catch (Exception e) {
122 throw new MojoFailureException( "Cannot calculate Maven execution plan, caused by: " + e.getMessage(), e );
123 }
124 return planInfo;
125 }
126
127 protected String[] calculateTasksToElaborate() throws MojoFailureException {
128 String[] result = null;
129
130 if ( isParamForceTasksFromSession() ) {
131 List<String> tasksFromSession = retrieveTasksFromSession();
132
133 if ( !tasksFromSession.isEmpty() ) {
134 result = tasksFromSession.toArray(new String[0]);
135 }
136 }
137 else {
138 result = paramLifecycleTasks;
139 }
140 return result;
141 }
142
143 protected boolean validateMavenExecution( MavenExecutionInfo info ) {
144 getLog().debug( "Validate maven execution ..." );
145
146 boolean result = validatePlugin( info, getPluginsToElaborate() );
147
148 if ( getLog().isDebugEnabled() ) {
149
150 getLog().debug( "Maven execution " + info + ". Validate: " + result );
151 }
152
153 return result;
154 }
155
156
157
158
159
160
161 protected List<String> normalizeParamFilterPlugin() {
162
163 List<String> result = null;
164
165 for ( String f : getParamFilterPlugins() ) {
166
167 if ( result == null ) {
168 result = new ArrayList<>();
169 }
170 if ( f != null ) {
171 result.add( f.trim() );
172 }
173 }
174
175 return result;
176 }
177
178
179
180
181
182
183 protected static boolean validatePlugin( MavenExecutionInfo info, List<String> filterPlugin ) {
184
185 boolean result = true;
186
187
188 if ( filterPlugin != null ) {
189
190 result = filterPlugin.contains( info.getPluginArtifactId() );
191
192 }
193
194 return result;
195 }
196
197 protected void handleOutput( final String output ) {
198 String header = headerParametersString();
199
200 String outputWithTitle = header + output;
201 getLog().info( outputWithTitle );
202
203 }
204
205
206
207
208
209
210 protected String headerParametersString() {
211 String header = MessageUtils.buffer().strong(
212 "\nProject: " + project.getName() + " (" + project.getArtifactId() + ":" + project.getVersion() + ")" )
213 + ".";
214
215 header = header + "\nForce tasks from Session: " + isParamForceTasksFromSession();
216
217 if ( isParamForceTasksFromSession() ) {
218 header = header + "\nExecution plan for Session tasks: " + Arrays.asList( getTasksToElaborate() );
219 }
220 else {
221 header = header + "\nExecution plan for run tasks: " + Arrays.asList( paramLifecycleTasks );
222 }
223
224 header = header + "\nFilter plugins: " + Objects.toString( getPluginsToElaborate(), "" );
225
226 return header;
227 }
228
229 protected String[] getParamFilterPlugins() {
230 return paramFilterPlugins;
231 }
232
233 protected List<String> getPluginsToElaborate() {
234 return pluginToElaborate;
235 }
236
237 protected void setPluginToElaborate( List<String> pluginToElaborate ) {
238 this.pluginToElaborate = pluginToElaborate;
239 }
240
241 protected List<String> retrieveTasksFromSession() throws MojoFailureException {
242
243 List<String> sessionTasksResult = new ArrayList<>();
244
245 List<TaskSegment> taskSegments;
246 try {
247 taskSegments = lifecycleTaskSegmentCalculator.calculateTaskSegments( session );
248
249 if ( taskSegments != null ) {
250
251 for ( TaskSegment taskSegmentList : taskSegments ) {
252
253 for ( Object task : taskSegmentList.getTasks() ) {
254
255 if ( task instanceof LifecycleTask ) {
256 sessionTasksResult.add( ( (LifecycleTask) task ).getLifecyclePhase() );
257 }
258 else if ( task instanceof GoalTask goalTask) {
259 sessionTasksResult.add( ( goalTask ).toString() );
260 }
261 else {
262 getLog().warn( "Task is not recognized. Task is ignored --> " + task + " " + task.getClass() );
263 }
264
265 }
266
267 }
268 }
269 }
270 catch (PluginNotFoundException | PluginResolutionException | PluginDescriptorParsingException | MojoNotFoundException | NoPluginFoundForPrefixException
271 | InvalidPluginDescriptorException | PluginVersionResolutionException | LifecyclePhaseNotFoundException | LifecycleNotFoundException e) {
272 throw new MojoFailureException( "Error retrieving task from session", e );
273 }
274
275 return sessionTasksResult;
276
277 }
278
279 protected String[] getTasksToElaborate() {
280 return tasksToElaborate;
281 }
282
283 protected void setTasksToElaborate( String[] tasksToElaborate ) {
284 this.tasksToElaborate = tasksToElaborate;
285 }
286
287
288
289
290
291
292 protected boolean isParamSkip() {
293 return paramSkip;
294 }
295
296 }