1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.scala_tools.maven;
17
18 import java.util.HashSet;
19 import java.util.Iterator;
20 import java.util.List;
21 import java.util.Set;
22
23 import org.apache.maven.artifact.Artifact;
24 import org.apache.maven.artifact.factory.ArtifactFactory;
25 import org.apache.maven.artifact.repository.ArtifactRepository;
26 import org.apache.maven.artifact.resolver.ArtifactNotFoundException;
27 import org.apache.maven.artifact.resolver.ArtifactResolutionException;
28 import org.apache.maven.artifact.resolver.ArtifactResolver;
29 import org.apache.maven.artifact.resolver.filter.AndArtifactFilter;
30 import org.apache.maven.artifact.resolver.filter.ArtifactFilter;
31 import org.apache.maven.artifact.resolver.filter.ScopeArtifactFilter;
32 import org.apache.maven.model.Dependency;
33 import org.apache.maven.plugin.AbstractMojo;
34 import org.apache.maven.plugin.MojoExecutionException;
35 import org.apache.maven.plugin.MojoFailureException;
36 import org.apache.maven.project.MavenProject;
37 import org.apache.maven.project.MavenProjectBuilder;
38 import org.apache.maven.project.ProjectBuildingException;
39 import org.apache.maven.project.artifact.InvalidDependencyVersionException;
40 import org.codehaus.plexus.util.StringUtils;
41
42 abstract class ScalaMojoSupport extends AbstractMojo {
43
44 public static final String SCALA_GROUPID= "org.scala-lang";
45 public static final String SCALA_LIBRARY_ARTIFACTID= "scala-library";
46
47
48
49
50
51 protected MavenProject project;
52
53
54
55
56
57
58
59
60 protected ArtifactFactory factory;
61
62
63
64
65
66
67
68
69 protected ArtifactResolver resolver;
70
71
72
73
74
75
76
77 protected ArtifactRepository localRepo;
78
79
80
81
82
83
84
85
86 protected List<?> remoteRepos;
87
88
89
90
91
92
93
94
95
96
97
98
99
100 protected BasicArtifact[] dependencies;
101
102
103
104
105
106
107 protected String[] jvmArgs;
108
109
110
111
112
113
114 protected String[] args;
115
116
117
118
119
120
121
122
123 protected String scalaClassName;
124
125
126
127
128
129 protected String scalaVersion;
130
131
132
133
134
135
136
137
138 protected boolean displayCmd;
139
140
141
142
143
144
145
146
147 protected MavenProjectBuilder mavenProjectBuilder;
148
149
150
151
152
153
154
155
156
157
158
159 @SuppressWarnings("unchecked")
160 protected Set<Artifact> resolveDependencyArtifacts(MavenProject theProject) throws Exception {
161 AndArtifactFilter filter = new AndArtifactFilter();
162 filter.add(new ScopeArtifactFilter(Artifact.SCOPE_TEST));
163 filter.add(new ArtifactFilter(){
164 public boolean include(Artifact artifact) {
165 return !artifact.isOptional();
166 }
167 });
168 Set<Artifact> artifacts = theProject.createArtifacts(factory, Artifact.SCOPE_RUNTIME, filter);
169 for (Artifact artifact : artifacts) {
170 resolver.resolve(artifact, remoteRepos, localRepo);
171 }
172 return artifacts;
173 }
174
175
176
177
178
179
180
181
182
183
184
185
186
187 protected Set<Artifact> resolveArtifactDependencies(Artifact artifact) throws Exception {
188 Artifact pomArtifact = factory.createArtifact(artifact.getGroupId(), artifact.getArtifactId(), artifact.getVersion(), "", "pom");
189 MavenProject pomProject = mavenProjectBuilder.buildFromRepository(pomArtifact, remoteRepos, localRepo);
190 return resolveDependencyArtifacts(pomProject);
191 }
192
193 protected void addToClasspath(String groupId, String artifactId, String version, Set<String> classpath) throws Exception {
194 addToClasspath(factory.createArtifact(groupId, artifactId, version, Artifact.SCOPE_RUNTIME, "jar"), classpath);
195 }
196
197 protected void addToClasspath(Artifact artifact, Set<String> classpath) throws Exception {
198 resolver.resolve(artifact, remoteRepos, localRepo);
199 classpath.add(artifact.getFile().getCanonicalPath());
200 for(Artifact dep: resolveArtifactDependencies(artifact)) {
201 classpath.add(dep.getFile().getCanonicalPath());
202 }
203 }
204
205 public void execute() throws MojoExecutionException, MojoFailureException {
206 try {
207 checkScalaVersion();
208 doExecute();
209 } catch (MojoExecutionException exc) {
210 throw exc;
211 } catch (MojoFailureException exc) {
212 throw exc;
213 } catch (RuntimeException exc) {
214 throw exc;
215 } catch (Exception exc) {
216 throw new MojoExecutionException("wrap: " + exc, exc);
217 }
218 }
219
220 @SuppressWarnings("unchecked")
221 protected List<Dependency> getDependencies() {
222 return project.getCompileDependencies();
223 }
224
225 @SuppressWarnings("unchecked")
226 protected void checkScalaVersion() throws Exception {
227 String detectedScalaVersion = null;
228 for (Iterator it = getDependencies().iterator(); it.hasNext();) {
229 Dependency dep = (Dependency) it.next();
230 if (SCALA_GROUPID.equals(dep.getGroupId()) && SCALA_LIBRARY_ARTIFACTID.equals(dep.getArtifactId())) {
231 detectedScalaVersion = dep.getVersion();
232 }
233 }
234 if (StringUtils.isEmpty(detectedScalaVersion)) {
235 getLog().warn("you don't define "+SCALA_GROUPID + ":" + SCALA_LIBRARY_ARTIFACTID + " as a dependency of the project");
236 } else {
237 if (StringUtils.isNotEmpty(scalaVersion)) {
238 if (!scalaVersion.equals(detectedScalaVersion)) {
239 getLog().warn("scala library version define in dependencies doesn't match the scalaVersion of the plugin");
240 }
241 getLog().info("suggestion: remove the scalaVersion from pom.xml");
242 } else {
243 scalaVersion = detectedScalaVersion;
244 }
245 }
246 if (StringUtils.isEmpty(scalaVersion)) {
247 throw new MojoFailureException("no scalaVersion detected or set");
248 }
249 }
250
251 protected abstract void doExecute() throws Exception;
252
253 protected JavaCommand getScalaCommand() throws Exception {
254 JavaCommand cmd = getEmptyScalaCommand(scalaClassName);
255 cmd.addArgs(args);
256 cmd.addJvmArgs(jvmArgs);
257 return cmd;
258 }
259
260 protected JavaCommand getEmptyScalaCommand(String mainClass) throws Exception {
261 JavaCommand cmd = new JavaCommand(this, mainClass, getToolClasspath(), null, null);
262 cmd.addJvmArgs("-Xbootclasspath/a:"+ getBootClasspath());
263 return cmd;
264 }
265
266 private String getToolClasspath() throws Exception {
267 Set<String> classpath = new HashSet<String>();
268 addToClasspath(SCALA_GROUPID, "scala-compiler", scalaVersion, classpath);
269
270
271 if (dependencies != null) {
272 for(BasicArtifact artifact: dependencies) {
273 addToClasspath(artifact.groupId, artifact.artifactId, artifact.version, classpath);
274 }
275 }
276 return JavaCommand.toMultiPath(classpath.toArray(new String[classpath.size()]));
277 }
278
279 private String getBootClasspath() throws Exception {
280 Set<String> classpath = new HashSet<String>();
281 addToClasspath(SCALA_GROUPID, SCALA_LIBRARY_ARTIFACTID, scalaVersion, classpath);
282 return JavaCommand.toMultiPath(classpath.toArray(new String[classpath.size()]));
283 }
284
285
286
287
288
289 protected boolean isJavaSupportedByCompiler() {
290 return new VersionNumber(scalaVersion).compareTo(new VersionNumber("2.7.2")) >= 0;
291 }
292
293 }