Skip to content

Commit 4980ba6

Browse files
authored
Fix #460 Delay classpath resolution to the compile phase (#461)
- Delay the classpath computation - Add a ValidateClassPathMojo if earlier validation/computation is desired
1 parent 1fe29d7 commit 4980ba6

File tree

7 files changed

+141
-45
lines changed

7 files changed

+141
-45
lines changed

tycho-compiler-plugin/src/main/java/org/eclipse/tycho/compiler/AbstractOsgiCompilerMojo.java

+2-4
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,6 @@
6969
import org.eclipse.tycho.classpath.JavaCompilerConfiguration;
7070
import org.eclipse.tycho.classpath.SourcepathEntry;
7171
import org.eclipse.tycho.core.BundleProject;
72-
import org.eclipse.tycho.core.TychoConstants;
7372
import org.eclipse.tycho.core.TychoProject;
7473
import org.eclipse.tycho.core.dotClasspath.JREClasspathEntry;
7574
import org.eclipse.tycho.core.dotClasspath.M2ClasspathVariable;
@@ -662,10 +661,9 @@ private void configureBootclasspathAccessRules(CompilerConfiguration compilerCon
662661
}
663662
}
664663

665-
@SuppressWarnings("unchecked")
666664
private List<AccessRule> getStrictBootClasspathAccessRules() throws MojoExecutionException {
667-
return (List<AccessRule>) DefaultReactorProject.adapt(project)
668-
.getContextValue(TychoConstants.CTX_ECLIPSE_PLUGIN_STRICT_BOOTCLASSPATH_ACCESSRULES);
665+
return ((OsgiBundleProject) getBundleProject()).getBundleClassPath(DefaultReactorProject.adapt(project))
666+
.getStrictBootClasspathAccessRules();
669667
}
670668

671669
private void configureJavaHome(CompilerConfiguration compilerConfiguration) throws MojoExecutionException {
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
/*******************************************************************************
2+
* Copyright (c) 2021 Christoph Läubrich and others.
3+
* All rights reserved. This program and the accompanying materials
4+
* are made available under the terms of the Eclipse Public License v1.0
5+
* which accompanies this distribution, and is available at
6+
* http://www.eclipse.org/legal/epl-v10.html
7+
*
8+
* Contributors:
9+
* Christoph Läubrich - initial API and implementation
10+
*******************************************************************************/
11+
package org.eclipse.tycho.compiler;
12+
13+
import java.util.Map;
14+
15+
import org.apache.maven.plugin.AbstractMojo;
16+
import org.apache.maven.plugin.MojoExecutionException;
17+
import org.apache.maven.plugin.MojoFailureException;
18+
import org.apache.maven.plugins.annotations.Component;
19+
import org.apache.maven.plugins.annotations.LifecyclePhase;
20+
import org.apache.maven.plugins.annotations.Mojo;
21+
import org.apache.maven.plugins.annotations.Parameter;
22+
import org.apache.maven.plugins.annotations.ResolutionScope;
23+
import org.apache.maven.project.MavenProject;
24+
import org.eclipse.tycho.core.TychoProject;
25+
import org.eclipse.tycho.core.osgitools.DefaultReactorProject;
26+
import org.eclipse.tycho.core.osgitools.OsgiBundleProject;
27+
28+
/**
29+
* This mojo could be added to a build if validation of the classpath is desired before the
30+
* compile-phase.
31+
*/
32+
@Mojo(name = "validate-classpath", defaultPhase = LifecyclePhase.VALIDATE, requiresDependencyResolution = ResolutionScope.COMPILE, threadSafe = true)
33+
public class ValidateClassPathMojo extends AbstractMojo {
34+
35+
@Parameter(property = "project", readonly = true)
36+
private MavenProject project;
37+
38+
@Component(role = TychoProject.class)
39+
private Map<String, TychoProject> projectTypes;
40+
41+
@Override
42+
public void execute() throws MojoExecutionException, MojoFailureException {
43+
44+
TychoProject projectType = projectTypes.get(project.getPackaging());
45+
if (projectType instanceof OsgiBundleProject) {
46+
OsgiBundleProject bundleProject = (OsgiBundleProject) projectType;
47+
bundleProject.getClasspath(DefaultReactorProject.adapt(project));
48+
}
49+
}
50+
51+
}

tycho-core/src/main/java/org/eclipse/tycho/core/TychoConstants.java

+2-9
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*******************************************************************************
2-
* Copyright (c) 2008, 2014 Sonatype Inc. and others.
2+
* Copyright (c) 2008, 2021 Sonatype Inc. and others.
33
* All rights reserved. This program and the accompanying materials
44
* are made available under the terms of the Eclipse Public License v1.0
55
* which accompanies this distribution, and is available at
@@ -24,15 +24,8 @@ public interface TychoConstants {
2424
*/
2525
static final String CTX_TEST_DEPENDENCY_ARTIFACTS = CTX_BASENAME + "/testDependencyArtifacts";
2626
static final String CTX_ECLIPSE_PLUGIN_PROJECT = CTX_BASENAME + "/eclipsePluginProject";
27-
static final String CTX_ECLIPSE_PLUGIN_CLASSPATH = CTX_BASENAME + "/eclipsePluginClasspath";
28-
/**
29-
* Stores test-specific classpath (usually derived from .classpath)
30-
*/
3127
static final String CTX_ECLIPSE_PLUGIN_TEST_CLASSPATH = CTX_BASENAME + "/eclipsePluginTestClasspath";
32-
static final String CTX_ECLIPSE_PLUGIN_STRICT_BOOTCLASSPATH_ACCESSRULES = CTX_BASENAME
33-
+ "/eclipsePluginStrictBootclasspathAccessRules";
34-
static final String CTX_ECLIPSE_PLUGIN_BOOTCLASSPATH_EXTRA_ACCESSRULES = CTX_BASENAME
35-
+ "/eclipsePluginBootclasspathExtraAccessRules";
28+
3629
static final String CTX_MERGED_PROPERTIES = CTX_BASENAME + "/mergedProperties";
3730
static final String CTX_TARGET_PLATFORM_CONFIGURATION = CTX_BASENAME + "/targetPlatformConfiguration";
3831
static final String CTX_EXECUTION_ENVIRONMENT_CONFIGURATION = CTX_BASENAME + "/executionEnvironmentConfiguration";

tycho-core/src/main/java/org/eclipse/tycho/core/osgitools/AbstractTychoProject.java

+2-5
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,13 @@
11
/*******************************************************************************
2-
* Copyright (c) 2008, 2012 Sonatype Inc. and others.
2+
* Copyright (c) 2008, 2021 Sonatype Inc. and others.
33
* All rights reserved. This program and the accompanying materials
44
* are made available under the terms of the Eclipse Public License v1.0
55
* which accompanies this distribution, and is available at
66
* http://www.eclipse.org/legal/epl-v10.html
77
*
88
* Contributors:
99
* Sonatype Inc. - initial API and implementation
10+
* Christoph Läubrich - Issue #460 - Delay classpath resolution to the compile phase
1011
*******************************************************************************/
1112
package org.eclipse.tycho.core.osgitools;
1213

@@ -73,10 +74,6 @@ public void setupProject(MavenSession session, MavenProject project) {
7374
public void checkForMissingDependencies(ReactorProject project) {
7475
}
7576

76-
public void resolveClassPath(MavenSession session, MavenProject project) {
77-
// do nothing by default
78-
}
79-
8077
protected TargetEnvironment[] getEnvironments(ReactorProject project, TargetEnvironment environment) {
8178
if (environment != null) {
8279
return new TargetEnvironment[] { environment };
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
/*******************************************************************************
2+
* Copyright (c) 2021 Christoph Läubrich and others.
3+
* All rights reserved. This program and the accompanying materials
4+
* are made available under the terms of the Eclipse Public License v1.0
5+
* which accompanies this distribution, and is available at
6+
* http://www.eclipse.org/legal/epl-v10.html
7+
*
8+
* Contributors:
9+
* Christoph Läubrich - initial API and implementation
10+
*******************************************************************************/
11+
package org.eclipse.tycho.core.osgitools;
12+
13+
import java.util.Collections;
14+
import java.util.List;
15+
16+
import org.eclipse.tycho.classpath.ClasspathEntry;
17+
import org.eclipse.tycho.classpath.ClasspathEntry.AccessRule;
18+
19+
public class BundleClassPath {
20+
21+
private List<ClasspathEntry> classpath;
22+
private List<AccessRule> strictBootClasspathAccessRules;
23+
private List<AccessRule> bootClasspathExtraAccessRules;
24+
25+
BundleClassPath(List<ClasspathEntry> classpath, List<AccessRule> strictBootClasspathAccessRules,
26+
List<AccessRule> bootClasspathExtraAccessRules) {
27+
this.classpath = Collections.unmodifiableList(classpath);
28+
this.strictBootClasspathAccessRules = Collections.unmodifiableList(strictBootClasspathAccessRules);
29+
this.bootClasspathExtraAccessRules = Collections.unmodifiableList(bootClasspathExtraAccessRules);
30+
}
31+
32+
public List<ClasspathEntry> getClasspathEntries() {
33+
return classpath;
34+
}
35+
36+
public List<AccessRule> getStrictBootClasspathAccessRules() {
37+
return strictBootClasspathAccessRules;
38+
}
39+
40+
public List<AccessRule> getExtraBootClasspathAccessRules() {
41+
return bootClasspathExtraAccessRules;
42+
}
43+
44+
}

tycho-core/src/main/java/org/eclipse/tycho/core/osgitools/OsgiBundleProject.java

+38-23
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
* Sonatype Inc. - initial API and implementation
1010
* Christoph Läubrich - [Bug 572416] Tycho does not understand "additional.bundles" directive in build.properties
1111
* [Bug 572416] Compile all source folders contained in .classpath
12+
* [Issue #460] Delay classpath resolution to the compile phase
1213
*******************************************************************************/
1314
package org.eclipse.tycho.core.osgitools;
1415

@@ -23,6 +24,7 @@
2324
import java.util.LinkedHashSet;
2425
import java.util.List;
2526
import java.util.Map;
27+
import java.util.Objects;
2628
import java.util.Properties;
2729
import java.util.Set;
2830
import java.util.regex.Matcher;
@@ -89,7 +91,11 @@
8991
@Component(role = TychoProject.class, hint = PackagingType.TYPE_ECLIPSE_PLUGIN)
9092
public class OsgiBundleProject extends AbstractTychoProject implements BundleProject {
9193

92-
private static final String CTX_ARTIFACT_KEY = TychoConstants.CTX_BASENAME + "/osgiBundle/artifactKey";
94+
private static final String CTX_OSGI_BUNDLE_BASENAME = TychoConstants.CTX_BASENAME + "/osgiBundle";
95+
private static final String CTX_ARTIFACT_KEY = CTX_OSGI_BUNDLE_BASENAME + "/artifactKey";
96+
private static final String CTX_MAVEN_SESSION = CTX_OSGI_BUNDLE_BASENAME + "/mavenSession";
97+
private static final String CTX_MAVEN_PROJECT = CTX_OSGI_BUNDLE_BASENAME + "/mavenProject";
98+
private static final String CTX_CLASSPATH = CTX_OSGI_BUNDLE_BASENAME + "/classPath";
9399

94100
@Requirement
95101
private BundleReader bundleReader;
@@ -171,7 +177,20 @@ public ArtifactKey getArtifactKey(ReactorProject project) {
171177
@Override
172178
public void setupProject(MavenSession session, MavenProject project) {
173179
ArtifactKey key = readArtifactKey(project.getBasedir());
174-
DefaultReactorProject.adapt(project).setContextValue(CTX_ARTIFACT_KEY, key);
180+
ReactorProject reactorProject = DefaultReactorProject.adapt(project);
181+
reactorProject.setContextValue(CTX_ARTIFACT_KEY, key);
182+
reactorProject.setContextValue(CTX_MAVEN_SESSION, session);
183+
reactorProject.setContextValue(CTX_MAVEN_PROJECT, project);
184+
}
185+
186+
private MavenSession getMavenSession(ReactorProject reactorProject) {
187+
return Objects.requireNonNull((MavenSession) reactorProject.getContextValue(CTX_MAVEN_SESSION),
188+
"Project not setup correctly");
189+
}
190+
191+
private MavenProject getMavenProject(ReactorProject reactorProject) {
192+
return Objects.requireNonNull((MavenProject) reactorProject.getContextValue(CTX_MAVEN_PROJECT),
193+
"Project not setup correctly");
175194
}
176195

177196
public ArtifactKey readArtifactKey(File location) {
@@ -188,8 +207,8 @@ private OsgiManifest getManifest(ReactorProject project) {
188207
return bundleReader.loadManifest(project.getBasedir());
189208
}
190209

191-
@Override
192-
public void resolveClassPath(MavenSession session, MavenProject project) {
210+
private BundleClassPath resolveClassPath(MavenSession session, MavenProject project) {
211+
logger.info("Resolving class path of " + project.getName() + "...");
193212
ReactorProject reactorProject = DefaultReactorProject.adapt(project);
194213
DependencyArtifacts artifacts = getDependencyArtifacts(reactorProject);
195214

@@ -247,13 +266,10 @@ public void resolveClassPath(MavenSession session, MavenProject project) {
247266
List<File> projectClasspath = getThisProjectClasspath(artifact, reactorProject);
248267
classpath.add(new DefaultClasspathEntry(reactorProject, artifact.getKey(), projectClasspath, null));
249268

250-
reactorProject.setContextValue(TychoConstants.CTX_ECLIPSE_PLUGIN_CLASSPATH, classpath);
251-
reactorProject.setContextValue(TychoConstants.CTX_ECLIPSE_PLUGIN_STRICT_BOOTCLASSPATH_ACCESSRULES,
252-
strictBootClasspathAccessRules);
253-
reactorProject.setContextValue(TychoConstants.CTX_ECLIPSE_PLUGIN_BOOTCLASSPATH_EXTRA_ACCESSRULES,
254-
dependencyComputer.computeBootClasspathExtraAccessRules(state));
269+
List<AccessRule> bootClasspathExtraAccessRules = dependencyComputer.computeBootClasspathExtraAccessRules(state);
255270

256271
addPDESourceRoots(project);
272+
return new BundleClassPath(classpath, strictBootClasspathAccessRules, bootClasspathExtraAccessRules);
257273
}
258274

259275
private Collection<ClasspathEntry> computeExtraTestClasspath(ReactorProject reactorProject) {
@@ -365,24 +381,22 @@ private void populateProperties(Properties mavenProjectProperties, EclipsePlugin
365381

366382
@Override
367383
public List<ClasspathEntry> getClasspath(ReactorProject project) {
368-
@SuppressWarnings("unchecked")
369-
List<ClasspathEntry> classpath = (List<ClasspathEntry>) project
370-
.getContextValue(TychoConstants.CTX_ECLIPSE_PLUGIN_CLASSPATH);
371-
if (classpath == null) {
372-
throw new IllegalStateException();
373-
}
374-
return classpath;
384+
return getBundleClassPath(project).getClasspathEntries();
375385
}
376386

377387
@Override
378388
public List<ClasspathEntry.AccessRule> getBootClasspathExtraAccessRules(ReactorProject project) {
379-
@SuppressWarnings("unchecked")
380-
List<ClasspathEntry.AccessRule> rules = (List<AccessRule>) project
381-
.getContextValue(TychoConstants.CTX_ECLIPSE_PLUGIN_BOOTCLASSPATH_EXTRA_ACCESSRULES);
382-
if (rules == null) {
383-
throw new IllegalStateException();
389+
return getBundleClassPath(project).getExtraBootClasspathAccessRules();
390+
}
391+
392+
public synchronized BundleClassPath getBundleClassPath(ReactorProject project) {
393+
Object contextValue = project.getContextValue(CTX_CLASSPATH);
394+
if (contextValue instanceof BundleClassPath) {
395+
return (BundleClassPath) contextValue;
384396
}
385-
return rules;
397+
BundleClassPath cp = resolveClassPath(getMavenSession(project), getMavenProject(project));
398+
project.setContextValue(CTX_CLASSPATH, cp);
399+
return cp;
386400
}
387401

388402
/**
@@ -485,7 +499,8 @@ private void addExtraClasspathEntries(List<ClasspathEntry> classpath, ReactorPro
485499
if (entry instanceof LibraryClasspathEntry) {
486500
LibraryClasspathEntry libraryClasspathEntry = (LibraryClasspathEntry) entry;
487501
ArtifactKey projectKey = getArtifactKey(project);
488-
classpath.add(new DefaultClasspathEntry(project, projectKey, Collections.singletonList(libraryClasspathEntry.getLibraryPath()), null));
502+
classpath.add(new DefaultClasspathEntry(project, projectKey,
503+
Collections.singletonList(libraryClasspathEntry.getLibraryPath()), null));
489504
}
490505
}
491506
}

tycho-core/src/main/java/org/eclipse/tycho/core/resolver/DefaultTychoResolver.java

+2-4
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*******************************************************************************
2-
* Copyright (c) 2008, 2020 Sonatype Inc. and others.
2+
* Copyright (c) 2008, 2021 Sonatype Inc. and others.
33
* All rights reserved. This program and the accompanying materials
44
* are made available under the terms of the Eclipse Public License v1.0
55
* which accompanies this distribution, and is available at
@@ -8,6 +8,7 @@
88
* Contributors:
99
* Sonatype Inc. - initial API and implementation
1010
* Christoph Läubrich - Bug 532575
11+
* Christoph Läubrich - Issue #460 - Delay classpath resolution to the compile phase
1112
*******************************************************************************/
1213
package org.eclipse.tycho.core.resolver;
1314

@@ -169,9 +170,6 @@ public List<ArtifactKey> getExtraRequirements() {
169170
Objects.requireNonNullElse(testDependencyArtifacts, new DefaultDependencyArtifacts()));
170171
}
171172

172-
logger.info("Resolving class path of " + project);
173-
dr.resolveClassPath(session, project);
174-
175173
resolver.injectDependenciesIntoMavenModel(project, dr, dependencyArtifacts, testDependencyArtifacts, logger);
176174

177175
if (logger.isDebugEnabled() && DebugUtils.isDebugEnabled(session, project)) {

0 commit comments

Comments
 (0)