1 package org.codehaus.mojo.aspectj;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27 import java.io.File;
28 import java.io.IOException;
29 import java.util.ArrayList;
30 import java.util.Iterator;
31 import java.util.List;
32 import java.util.Set;
33
34 import org.apache.maven.artifact.Artifact;
35 import org.apache.maven.artifact.ArtifactUtils;
36 import org.apache.maven.artifact.handler.ArtifactHandler;
37 import org.apache.maven.plugin.MojoExecutionException;
38 import org.aspectj.bridge.IMessage;
39 import org.aspectj.tools.ajc.Main;
40 import org.codehaus.plexus.util.FileUtils;
41
42
43
44
45
46
47 public abstract class AbstractAjcCompiler
48 extends AbstractAjcMojo
49 {
50
51
52
53
54
55 protected String aspectDirectory = "src/main/aspect";
56
57
58
59
60
61 protected String testAspectDirectory = "src/test/aspect";
62
63
64
65
66
67
68
69
70 protected String[] includes;
71
72
73
74
75
76
77
78
79 protected String[] excludes;
80
81
82
83
84
85
86
87 protected String ajdtBuildDefFile;
88
89
90
91
92
93
94 protected boolean outxml;
95
96
97
98
99
100
101 protected String outxmlfile;
102
103
104
105
106
107
108 protected boolean emacssym;
109
110
111
112
113
114
115
116
117
118
119 protected String Xlint;
120
121
122
123
124
125
126
127
128
129
130
131
132 protected boolean XhasMember;
133
134
135
136
137
138
139 protected String target;
140
141
142
143
144
145
146
147
148
149
150
151 protected String source;
152
153
154
155
156
157
158
159 protected String complianceLevel;
160
161
162
163
164
165
166 protected boolean deprecation;
167
168
169
170
171
172
173 protected boolean noImportError;
174
175
176
177
178
179
180 protected boolean proceedOnError;
181
182
183
184
185
186
187 protected boolean preserveAllLocals;
188
189
190
191
192
193
194 protected boolean referenceInfo;
195
196
197
198
199
200
201 protected String encoding;
202
203
204
205
206
207
208 protected boolean verbose;
209
210
211
212
213
214
215 protected boolean showWeaveInfo;
216
217
218
219
220
221
222 protected int repeat;
223
224
225
226
227
228
229
230
231
232 protected boolean Xreweavable;
233
234
235
236
237
238
239 protected boolean XnoInline;
240
241
242
243
244
245
246 protected boolean XserializableAspects;
247
248
249
250
251
252
253
254 protected boolean XaddSerialVersionUID;
255
256
257
258
259
260
261
262 protected String bootclasspath;
263
264
265
266
267
268
269 protected String warn;
270
271
272
273
274
275
276
277
278
279
280
281 protected String argumentFileName = "builddef.lst";
282
283
284
285
286
287
288
289 protected boolean forceAjcCompile;
290
291
292
293
294 protected List ajcOptions = new ArrayList();
295
296
297
298
299 protected Set resolvedIncludes;
300
301
302
303
304
305
306
307 protected abstract List getOutputDirectories();
308
309
310
311
312
313
314 protected abstract List getSourceDirectories();
315
316
317
318
319
320 protected abstract String getAdditionalAspectPaths();
321
322
323
324
325
326
327 public void execute()
328 throws MojoExecutionException
329 {
330 ArtifactHandler artifactHandler = project.getArtifact().getArtifactHandler();
331 if ( !"java".equals( artifactHandler.getLanguage() ) )
332 {
333 getLog().warn( "Not executing aspectJ compiler as the project is not a Java classpath-capable package" );
334 return;
335 }
336
337 Thread.currentThread().setContextClassLoader( this.getClass().getClassLoader() );
338 project.getCompileSourceRoots().add( basedir.getAbsolutePath() + "/" + aspectDirectory );
339 project.getTestCompileSourceRoots().add( basedir.getAbsolutePath() + "/" + testAspectDirectory );
340 assembleArguments();
341
342 if ( !hasSourcesToCompile() )
343 {
344 getLog().warn( "No sources found skipping aspectJ compile" );
345 return;
346 }
347
348 if ( !forceAjcCompile && !isBuildNeeded() )
349 {
350 getLog().info( "No modifications found skipping aspectJ compile" );
351 return;
352 }
353
354 if ( getLog().isDebugEnabled() )
355 {
356 String command = "Running : ajc ";
357 Iterator iter = ajcOptions.iterator();
358 while ( iter.hasNext() )
359 {
360 command += ( iter.next() + " " );
361 }
362 getLog().debug( command );
363 }
364 try
365 {
366 getLog().debug( "Compiling and weaving " + resolvedIncludes.size() + " sources to " + getOutputDirectories().get( 0 ) );
367 File outDir = new File( (String) getOutputDirectories().get( 0 ) );
368 AjcHelper.writeBuildConfigToFile( ajcOptions, argumentFileName, outDir );
369 getLog().debug(
370 "Argumentsfile written : "
371 + new File( outDir.getAbsolutePath() + argumentFileName ).getAbsolutePath() );
372 }
373 catch ( IOException e )
374 {
375 throw new MojoExecutionException( "Could not write arguments file to the target area", e );
376 }
377 Main main = new Main();
378 MavenMessageHandler mavenMessageHandler = new MavenMessageHandler( getLog() );
379 main.setHolder( mavenMessageHandler );
380
381 main.runMain( (String[]) ajcOptions.toArray( new String[0] ), false );
382 IMessage[] errors = mavenMessageHandler.getMessages( IMessage.ERROR, true );
383 if ( !proceedOnError && errors.length > 0 )
384 {
385 throw new CompilationFailedException( errors );
386 }
387 }
388
389
390
391
392
393
394 protected void assembleArguments()
395 throws MojoExecutionException
396 {
397 if ( XhasMember ) {
398 ajcOptions.add( "-XhasMember" );
399 }
400
401
402 ajcOptions.add( "-classpath" );
403 ajcOptions.add( AjcHelper.createClassPath( project, null, getOutputDirectories() ) );
404
405
406 if ( null != bootclasspath )
407 {
408 ajcOptions.add( "-bootclasspath" );
409 ajcOptions.add( bootclasspath );
410 }
411
412
413 if (null != warn )
414 {
415 ajcOptions.add( "-warn:" + warn );
416 }
417
418
419 addModulesArgument( "-inpath", ajcOptions, weaveDependencies, null, "a dependency to weave" );
420
421
422 addModulesArgument( "-aspectpath", ajcOptions, aspectLibraries, getAdditionalAspectPaths(), "an aspect library" );
423
424
425 ajcOptions.add( "-d" );
426 ajcOptions.add( getOutputDirectories().get( 0 ) );
427
428
429 if ( null != ajdtBuildDefFile )
430 {
431 resolvedIncludes = AjcHelper.getBuildFilesForAjdtFile( ajdtBuildDefFile, basedir );
432 }
433 else
434 {
435 resolvedIncludes = AjcHelper.getBuildFilesForSourceDirs( getSourceDirectories(), this.includes,
436 this.excludes );
437 }
438 ajcOptions.addAll( resolvedIncludes );
439 }
440
441
442
443
444
445
446
447
448 private void addModulesArgument( String argument, List arguments, Module[] modules, String aditionalpath,
449 String role )
450 throws MojoExecutionException
451 {
452 StringBuffer buf = new StringBuffer();
453
454 if ( null != aditionalpath )
455 {
456 arguments.add( argument );
457 buf.append( aditionalpath );
458 }
459 if ( modules != null && modules.length > 0 )
460 {
461 if ( !arguments.contains( argument ) )
462 {
463 arguments.add( argument );
464 }
465
466 for ( int i = 0; i < modules.length; ++i )
467 {
468 Module module = modules[i];
469 String key = ArtifactUtils.versionlessKey( module.getGroupId(), module.getArtifactId() );
470 Artifact artifact = (Artifact) project.getArtifactMap().get( key );
471 if ( artifact == null )
472 {
473 throw new MojoExecutionException( "The artifact " + key + " referenced in aspectj plugin as "
474 + role + ", is not found the project dependencies" );
475 }
476 if ( buf.length() != 0 )
477 {
478 buf.append( File.pathSeparatorChar );
479 }
480 buf.append( artifact.getFile().getPath() );
481 }
482 }
483 if ( buf.length() > 0 )
484 {
485 String pathString = buf.toString();
486 arguments.add( pathString );
487 getLog().debug( "Adding " + argument + ": " + pathString );
488 }
489 }
490
491
492
493
494
495
496
497 protected boolean isBuildNeeded()
498 throws MojoExecutionException
499 {
500 File outDir = new File( getOutputDirectories().get( 0 ).toString() );
501 return hasNoPreviousBuild( outDir ) || hasArgumentsChanged( outDir ) || hasSourcesChanged( outDir );
502
503 }
504
505 private boolean hasNoPreviousBuild( File outDir )
506 {
507 return ( !FileUtils.fileExists( new File( outDir.getAbsolutePath(), argumentFileName ).getAbsolutePath() ) );
508 }
509
510 private boolean hasArgumentsChanged( File outDir )
511 throws MojoExecutionException
512 {
513 try
514 {
515 return ( !ajcOptions.equals( AjcHelper.readBuildConfigFile( argumentFileName, outDir ) ) );
516 }
517 catch ( IOException e )
518 {
519 throw new MojoExecutionException( "Error during reading of previous argumentsfile " );
520 }
521 }
522
523
524
525
526 private boolean hasSourcesToCompile()
527 {
528 return resolvedIncludes.size() > 0;
529 }
530
531 private boolean hasSourcesChanged( File outDir )
532 {
533 Iterator sourceIter = resolvedIncludes.iterator();
534 long lastBuild = new File( outDir.getAbsolutePath(), argumentFileName ).lastModified();
535 while ( sourceIter.hasNext() )
536 {
537 File sourceFile = new File( (String) sourceIter.next() );
538 long sourceModified = sourceFile.lastModified();
539 if ( sourceModified >= lastBuild )
540 {
541 return true;
542 }
543
544 }
545 return false;
546 }
547
548
549
550
551 public void setComplianceLevel( String complianceLevel )
552 {
553 if ( complianceLevel.equals( "1.3" ) || complianceLevel.equals( "1.4" ) || complianceLevel.equals( "1.5" ) || complianceLevel.equals( "1.6" ) )
554 {
555 ajcOptions.add( "-" + complianceLevel );
556 }
557
558 }
559
560 public void setDeprecation( boolean deprecation )
561 {
562 if ( deprecation )
563 {
564 ajcOptions.add( "-deprecation" );
565 }
566 }
567
568 public void setEmacssym( boolean emacssym )
569 {
570 if ( emacssym )
571 {
572 ajcOptions.add( "-emacssym" );
573 }
574
575 }
576
577 public void setEncoding( String encoding )
578 {
579 ajcOptions.add( "-encoding" );
580 ajcOptions.add( encoding );
581 }
582
583 public void setNoImportError( boolean noImportError )
584 {
585 if ( noImportError )
586 {
587 ajcOptions.add( "-noImportError" );
588 }
589
590 }
591
592 public void setOutxml( boolean outxml )
593 {
594 if ( outxml )
595 {
596 ajcOptions.add( "-outxml" );
597 }
598
599 }
600
601 public void setOutxmlfile( String outxmlfile )
602 {
603 ajcOptions.add( "-outxmlfile" );
604 ajcOptions.add( outxmlfile );
605 }
606
607 public void setPreserveAllLocals( boolean preserveAllLocals )
608 {
609 if ( preserveAllLocals )
610 {
611 ajcOptions.add( "-preserveAllLocals" );
612 }
613
614 }
615
616 public void setProceedOnError( boolean proceedOnError )
617 {
618 if ( proceedOnError )
619 {
620 ajcOptions.add( "-proceedOnError" );
621 }
622 this.proceedOnError = proceedOnError;
623 }
624
625 public void setReferenceInfo( boolean referenceInfo )
626 {
627 if ( referenceInfo )
628 {
629 ajcOptions.add( "-referenceInfo" );
630 }
631
632 }
633
634 public void setRepeat( int repeat )
635 {
636 ajcOptions.add( "-repeat" );
637 ajcOptions.add( "" + repeat );
638 }
639
640 public void setShowWeaveInfo( boolean showWeaveInfo )
641 {
642 if ( showWeaveInfo )
643 {
644 ajcOptions.add( "-showWeaveInfo" );
645 }
646
647 }
648
649 public void setTarget( String target )
650 {
651 ajcOptions.add( "-target" );
652 ajcOptions.add( target );
653 }
654
655 public void setSource( String source )
656 {
657 ajcOptions.add( "-source" );
658 ajcOptions.add( source );
659 }
660
661 public void setVerbose( boolean verbose )
662 {
663 if ( verbose )
664 {
665 ajcOptions.add( "-verbose" );
666 }
667 }
668
669 public void setXhasMember( boolean xhasMember )
670 {
671 XhasMember = xhasMember;
672 }
673
674 public void setXlint( String xlint )
675 {
676 ajcOptions.add( "-Xlint:" + xlint );
677 }
678
679 public void setXnoInline( boolean xnoInline )
680 {
681 if ( xnoInline )
682 {
683 ajcOptions.add( "-XnoInline" );
684 }
685
686 }
687
688 public void setXreweavable( boolean xreweavable )
689 {
690 if ( xreweavable )
691 {
692 ajcOptions.add( "-Xreweavable" );
693 }
694
695 }
696
697 public void setXserializableAspects( boolean xserializableAspects )
698 {
699 if ( xserializableAspects )
700 {
701 ajcOptions.add( "-XserializableAspects" );
702 }
703 }
704
705 public void setXaddSerialVersionUID( boolean xaddSerialVersionUID )
706 {
707 if ( xaddSerialVersionUID )
708 {
709 ajcOptions.add( "-XaddSerialVersionUID" );
710 }
711 }
712
713 public void setBootClassPath( String bootclasspath )
714 {
715 this.bootclasspath = bootclasspath;
716 }
717
718 public void setWarn( String warn )
719 {
720 this.warn = warn;
721 }
722
723 public void setArgumentFileName( String argumentFileName )
724 {
725 this.argumentFileName = argumentFileName;
726
727 }
728
729 }