1 package org.apache.maven.exception;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 import java.io.IOException;
23 import java.net.ConnectException;
24 import java.net.UnknownHostException;
25 import java.util.ArrayList;
26 import java.util.List;
27
28 import org.apache.maven.lifecycle.LifecycleExecutionException;
29 import org.apache.maven.model.building.ModelProblem;
30 import org.apache.maven.model.building.ModelProblemUtils;
31 import org.apache.maven.plugin.AbstractMojoExecutionException;
32 import org.apache.maven.plugin.MojoExecutionException;
33 import org.apache.maven.plugin.MojoFailureException;
34 import org.apache.maven.plugin.PluginContainerException;
35 import org.apache.maven.plugin.PluginExecutionException;
36 import org.apache.maven.project.ProjectBuildingException;
37 import org.apache.maven.project.ProjectBuildingResult;
38 import org.codehaus.plexus.component.annotations.Component;
39 import org.codehaus.plexus.util.StringUtils;
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89 @Component( role = ExceptionHandler.class )
90 public class DefaultExceptionHandler
91 implements ExceptionHandler
92 {
93
94 public ExceptionSummary handleException( Throwable exception )
95 {
96 return handle( "", exception );
97 }
98
99 private ExceptionSummary handle( String message, Throwable exception )
100 {
101 String reference = getReference( exception );
102
103 List<ExceptionSummary> children = null;
104
105 if ( exception instanceof ProjectBuildingException )
106 {
107 List<ProjectBuildingResult> results = ( (ProjectBuildingException) exception ).getResults();
108
109 children = new ArrayList<>();
110
111 for ( ProjectBuildingResult result : results )
112 {
113 ExceptionSummary child = handle( result );
114 if ( child != null )
115 {
116 children.add( child );
117 }
118 }
119
120 message = "The build could not read " + children.size() + " project" + ( children.size() == 1 ? "" : "s" );
121 }
122 else
123 {
124 message = getMessage( message, exception );
125 }
126
127 return new ExceptionSummary( exception, message, reference, children );
128 }
129
130 private ExceptionSummary handle( ProjectBuildingResult result )
131 {
132 List<ExceptionSummary> children = new ArrayList<>();
133
134 for ( ModelProblem problem : result.getProblems() )
135 {
136 ExceptionSummary child = handle( problem, result.getProjectId() );
137 if ( child != null )
138 {
139 children.add( child );
140 }
141 }
142
143 if ( children.isEmpty() )
144 {
145 return null;
146 }
147
148 String message =
149 "\nThe project " + result.getProjectId() + " (" + result.getPomFile() + ") has "
150 + children.size() + " error" + ( children.size() == 1 ? "" : "s" );
151
152 return new ExceptionSummary( null, message, null, children );
153 }
154
155 private ExceptionSummary handle( ModelProblem problem, String projectId )
156 {
157 if ( ModelProblem.Severity.ERROR.compareTo( problem.getSeverity() ) >= 0 )
158 {
159 String message = problem.getMessage();
160
161 String location = ModelProblemUtils.formatLocation( problem, projectId );
162
163 if ( StringUtils.isNotEmpty( location ) )
164 {
165 message += " @ " + location;
166 }
167
168 return handle( message, problem.getException() );
169 }
170 else
171 {
172 return null;
173 }
174 }
175
176 private String getReference( Throwable exception )
177 {
178 String reference = "";
179
180 if ( exception != null )
181 {
182 if ( exception instanceof MojoExecutionException )
183 {
184 reference = MojoExecutionException.class.getSimpleName();
185
186 Throwable cause = exception.getCause();
187 if ( cause instanceof IOException )
188 {
189 cause = cause.getCause();
190 if ( cause instanceof ConnectException )
191 {
192 reference = ConnectException.class.getSimpleName();
193 }
194 }
195 }
196 else if ( exception instanceof MojoFailureException )
197 {
198 reference = MojoFailureException.class.getSimpleName();
199 }
200 else if ( exception instanceof LinkageError )
201 {
202 reference = LinkageError.class.getSimpleName();
203 }
204 else if ( exception instanceof PluginExecutionException )
205 {
206 Throwable cause = exception.getCause();
207
208 if ( cause instanceof PluginContainerException )
209 {
210 Throwable cause2 = cause.getCause();
211
212 if ( cause2 instanceof NoClassDefFoundError )
213 {
214 String message = cause2.getMessage();
215 if ( message != null && message.contains( "org/sonatype/aether/" ) )
216 {
217 reference = "AetherClassNotFound";
218 }
219 }
220 }
221
222 if ( StringUtils.isEmpty( reference ) )
223 {
224 reference = getReference( cause );
225 }
226
227 if ( StringUtils.isEmpty( reference ) )
228 {
229 reference = exception.getClass().getSimpleName();
230 }
231 }
232 else if ( exception instanceof LifecycleExecutionException )
233 {
234 reference = getReference( exception.getCause() );
235 }
236 else if ( isNoteworthyException( exception ) )
237 {
238 reference = exception.getClass().getSimpleName();
239 }
240 }
241
242 if ( StringUtils.isNotEmpty( reference ) && !reference.startsWith( "http:" ) )
243 {
244 reference = "http://cwiki.apache.org/confluence/display/MAVEN/" + reference;
245 }
246
247 return reference;
248 }
249
250 private boolean isNoteworthyException( Throwable exception )
251 {
252 if ( exception == null )
253 {
254 return false;
255 }
256 else if ( exception instanceof Error )
257 {
258 return true;
259 }
260 else if ( exception instanceof RuntimeException )
261 {
262 return false;
263 }
264 else if ( exception.getClass().getName().startsWith( "java" ) )
265 {
266 return false;
267 }
268 return true;
269 }
270
271 private String getMessage( String message, Throwable exception )
272 {
273 String fullMessage = ( message != null ) ? message : "";
274
275 for ( Throwable t = exception; t != null; t = t.getCause() )
276 {
277 String exceptionMessage = t.getMessage();
278
279 if ( t instanceof AbstractMojoExecutionException )
280 {
281 String longMessage = ( (AbstractMojoExecutionException) t ).getLongMessage();
282 if ( StringUtils.isNotEmpty( longMessage ) )
283 {
284 if ( StringUtils.isEmpty( exceptionMessage ) || longMessage.contains( exceptionMessage ) )
285 {
286 exceptionMessage = longMessage;
287 }
288 else if ( !exceptionMessage.contains( longMessage ) )
289 {
290 exceptionMessage = join( exceptionMessage, '\n' + longMessage );
291 }
292 }
293 }
294
295 if ( StringUtils.isEmpty( exceptionMessage ) )
296 {
297 exceptionMessage = t.getClass().getSimpleName();
298 }
299
300 if ( t instanceof UnknownHostException && !fullMessage.contains( "host" ) )
301 {
302 fullMessage = join( fullMessage, "Unknown host " + exceptionMessage );
303 }
304 else if ( !fullMessage.contains( exceptionMessage ) )
305 {
306 fullMessage = join( fullMessage, exceptionMessage );
307 }
308 }
309
310 return fullMessage.trim();
311 }
312
313 private String join( String message1, String message2 )
314 {
315 String message = "";
316
317 if ( StringUtils.isNotEmpty( message1 ) )
318 {
319 message = message1.trim();
320 }
321
322 if ( StringUtils.isNotEmpty( message2 ) )
323 {
324 if ( StringUtils.isNotEmpty( message ) )
325 {
326 if ( message.endsWith( "." ) || message.endsWith( "!" ) || message.endsWith( ":" ) )
327 {
328 message += " ";
329 }
330 else
331 {
332 message += ": ";
333 }
334 }
335
336 message += message2;
337 }
338
339 return message;
340 }
341
342 }