Skip to content

Commit

Permalink
Merge pull request #25933 from aloubyansky/workspace-discovery-normal…
Browse files Browse the repository at this point in the history
…-mode

Option to enable workspace discovery in NORMAL mode
  • Loading branch information
geoand authored Jun 3, 2022
2 parents 338fe10 + c72abd2 commit d65ab1d
Show file tree
Hide file tree
Showing 11 changed files with 130 additions and 18 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,13 @@ public class BootstrapConfig {
@ConfigItem(defaultValue = "false")
boolean effectiveModelBuilder;

/**
* If set to true, workspace discovery will be enabled for all launch modes.
* Usually, workspace discovery is enabled by default only for dev and test modes.
*/
@ConfigItem(defaultValue = "false")
Boolean workspaceDiscovery;

/**
* Whether to throw an error, warn or silently ignore misaligned platform BOM imports
*/
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -98,15 +98,24 @@ public Object buildAll(String modelName, ModelParameter parameter, Project proje
final Configuration deploymentConfig = classpathBuilder.getDeploymentConfiguration();
final PlatformImports platformImports = classpathBuilder.getPlatformImports();

final ResolvedDependency appArtifact = getProjectArtifact(project, mode);
boolean workspaceDiscovery = LaunchMode.DEVELOPMENT.equals(mode) || LaunchMode.TEST.equals(mode)
|| Boolean.parseBoolean(System.getProperty(BootstrapConstants.QUARKUS_BOOTSTRAP_WORKSPACE_DISCOVERY));
if (!workspaceDiscovery) {
Object o = project.getProperties().get(BootstrapConstants.QUARKUS_BOOTSTRAP_WORKSPACE_DISCOVERY);
if (o != null) {
workspaceDiscovery = Boolean.parseBoolean(o.toString());
}
}

final ResolvedDependency appArtifact = getProjectArtifact(project, workspaceDiscovery);
final ApplicationModelBuilder modelBuilder = new ApplicationModelBuilder()
.setAppArtifact(appArtifact)
.addReloadableWorkspaceModule(appArtifact.getKey())
.setPlatformImports(platformImports);

final Map<ArtifactKey, ResolvedDependencyBuilder> appDependencies = new LinkedHashMap<>();
collectDependencies(classpathConfig.getResolvedConfiguration(), mode, project, appDependencies, modelBuilder,
appArtifact.getWorkspaceModule().mutable());
collectDependencies(classpathConfig.getResolvedConfiguration(), workspaceDiscovery,
project, appDependencies, modelBuilder, appArtifact.getWorkspaceModule().mutable());
collectExtensionDependencies(project, deploymentConfig, appDependencies);

for (ResolvedDependencyBuilder d : appDependencies.values()) {
Expand All @@ -115,7 +124,7 @@ public Object buildAll(String modelName, ModelParameter parameter, Project proje
return modelBuilder.build();
}

public static ResolvedDependency getProjectArtifact(Project project, LaunchMode mode) {
public static ResolvedDependency getProjectArtifact(Project project, boolean workspaceDiscovery) {
final ResolvedDependencyBuilder appArtifact = ResolvedDependencyBuilder.newInstance()
.setGroupId(project.getGroup().toString())
.setArtifactId(project.getName())
Expand All @@ -133,7 +142,7 @@ public static ResolvedDependency getProjectArtifact(Project project, LaunchMode

initProjectModule(project, mainModule, javaConvention.getSourceSets().findByName(SourceSet.MAIN_SOURCE_SET_NAME),
SourceSet.MAIN_SOURCE_SET_NAME, ArtifactSources.MAIN);
if (mode.equals(LaunchMode.TEST) || mode.equals(LaunchMode.DEVELOPMENT)) {
if (workspaceDiscovery) {
initProjectModule(project, mainModule, javaConvention.getSourceSets().findByName(SourceSet.TEST_SOURCE_SET_NAME),
SourceSet.TEST_SOURCE_SET_NAME, ArtifactSources.TEST);
}
Expand Down Expand Up @@ -185,7 +194,7 @@ private void collectExtensionDependencies(Project project, Configuration deploym
}

private void collectDependencies(ResolvedConfiguration configuration,
LaunchMode mode, Project project, Map<ArtifactKey, ResolvedDependencyBuilder> appDependencies,
boolean workspaceDiscovery, Project project, Map<ArtifactKey, ResolvedDependencyBuilder> appDependencies,
ApplicationModelBuilder modelBuilder, WorkspaceModule.Mutable wsModule) {

final Set<ResolvedArtifact> resolvedArtifacts = configuration.getResolvedArtifacts();
Expand All @@ -197,7 +206,8 @@ private void collectDependencies(ResolvedConfiguration configuration,

configuration.getFirstLevelModuleDependencies()
.forEach(d -> {
collectDependencies(d, mode, project, appDependencies, artifactFiles, new HashSet<>(), modelBuilder,
collectDependencies(d, workspaceDiscovery, project, appDependencies, artifactFiles, new HashSet<>(),
modelBuilder,
wsModule,
(byte) (COLLECT_TOP_EXTENSION_RUNTIME_NODES | COLLECT_DIRECT_DEPS | COLLECT_RELOADABLE_MODULES));
});
Expand Down Expand Up @@ -238,7 +248,8 @@ private void collectDependencies(ResolvedConfiguration configuration,
}
}

private void collectDependencies(org.gradle.api.artifacts.ResolvedDependency resolvedDep, LaunchMode mode, Project project,
private void collectDependencies(org.gradle.api.artifacts.ResolvedDependency resolvedDep, boolean workspaceDiscovery,
Project project,
Map<ArtifactKey, ResolvedDependencyBuilder> appDependencies, Set<File> artifactFiles,
Set<ArtifactKey> processedModules, ApplicationModelBuilder modelBuilder, WorkspaceModule.Mutable parentModule,
byte flags) {
Expand All @@ -262,8 +273,7 @@ private void collectDependencies(org.gradle.api.artifacts.ResolvedDependency res
}

PathCollection paths = null;
if ((LaunchMode.DEVELOPMENT.equals(mode) || LaunchMode.TEST.equals(mode)) &&
a.getId().getComponentIdentifier() instanceof ProjectComponentIdentifier) {
if (workspaceDiscovery && a.getId().getComponentIdentifier() instanceof ProjectComponentIdentifier) {

final Project projectDep = project.getRootProject().findProject(
((ProjectComponentIdentifier) a.getId().getComponentIdentifier()).getProjectPath());
Expand Down Expand Up @@ -320,7 +330,8 @@ private void collectDependencies(org.gradle.api.artifacts.ResolvedDependency res
processedModules.add(new GACT(resolvedDep.getModuleGroup(), resolvedDep.getModuleName()));
for (org.gradle.api.artifacts.ResolvedDependency child : resolvedDep.getChildren()) {
if (!processedModules.contains(new GACT(child.getModuleGroup(), child.getModuleName()))) {
collectDependencies(child, mode, project, appDependencies, artifactFiles, processedModules, modelBuilder,
collectDependencies(child, workspaceDiscovery, project, appDependencies, artifactFiles, processedModules,
modelBuilder,
projectModule, flags);
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
import com.google.common.cache.Cache;
import com.google.common.cache.CacheBuilder;

import io.quarkus.bootstrap.BootstrapConstants;
import io.quarkus.bootstrap.BootstrapException;
import io.quarkus.bootstrap.app.CuratedApplication;
import io.quarkus.bootstrap.app.QuarkusBootstrap;
Expand Down Expand Up @@ -115,6 +116,14 @@ public void close() throws IOException {
}
}

private static boolean isWorkspaceDiscovery(QuarkusBootstrapMojo mojo) {
String v = System.getProperty(BootstrapConstants.QUARKUS_BOOTSTRAP_WORKSPACE_DISCOVERY);
if (v == null) {
v = mojo.mavenProject().getProperties().getProperty(BootstrapConstants.QUARKUS_BOOTSTRAP_WORKSPACE_DISCOVERY);
}
return Boolean.parseBoolean(v);
}

public class QuarkusMavenAppBootstrap implements Closeable {

private CuratedApplication prodApp;
Expand All @@ -123,9 +132,11 @@ public class QuarkusMavenAppBootstrap implements Closeable {

private MavenArtifactResolver artifactResolver(QuarkusBootstrapMojo mojo, LaunchMode mode)
throws MojoExecutionException {
isWorkspaceDiscovery(mojo);
try {
return MavenArtifactResolver.builder()
.setWorkspaceDiscovery(mode == LaunchMode.DEVELOPMENT || mode == LaunchMode.TEST)
.setWorkspaceDiscovery(
mode == LaunchMode.DEVELOPMENT || mode == LaunchMode.TEST || isWorkspaceDiscovery(mojo))
.setCurrentProject(mojo.mavenProject().getFile().toString())
.setPreferPomsFromWorkspace(mode == LaunchMode.DEVELOPMENT || mode == LaunchMode.TEST)
.setRepositorySystem(repoSystem)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -44,4 +44,6 @@ public interface BootstrapConstants {
String PLATFORM_PROPERTIES_ARTIFACT_ID_SUFFIX = "-quarkus-platform-properties";

String PLATFORM_PROPERTY_PREFIX = "platform.";

String QUARKUS_BOOTSTRAP_WORKSPACE_DISCOVERY = "quarkus.bootstrap.workspace-discovery";
}
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,18 @@ class BuildIT extends MojoTestBase {
private RunningInvoker running;
private File testDir;

@Test
void testQuarkusBootstrapWorkspaceDiscovery() throws Exception {
testDir = initProject("projects/project-with-extension", "projects/project-with-extension-build");
running = new RunningInvoker(testDir, false);
MavenProcessInvocationResult result = running
.execute(List.of("clean", "compile", "quarkus:build", "-Dquarkus.bootstrap.workspace-discovery"), Map.of());
assertThat(result.getProcess().waitFor()).isZero();

launch(TestContext.FAST_NO_PREFIX, "/app/hello/local-modules", new File(testDir, "runner"), "",
"[org.acme:acme-common-transitive:1.0-SNAPSHOT, org.acme:acme-common:1.0-SNAPSHOT, org.acme:acme-library:1.0-SNAPSHOT, org.acme:acme-quarkus-ext-deployment:1.0-SNAPSHOT, org.acme:acme-quarkus-ext:1.0-SNAPSHOT]");
}

@Test
void testCustomTestSourceSets()
throws MavenInvocationException, IOException, InterruptedException {
Expand Down Expand Up @@ -179,6 +191,11 @@ private void launch(TestContext context, String outputPrefix, String expectedMes
}

private void launch(TestContext context, File testDir, String outputPrefix, String expectedMessage) throws IOException {
launch(context, "/hello", testDir, outputPrefix, expectedMessage);
}

private void launch(TestContext context, String path, File testDir, String outputPrefix, String expectedMessage)
throws IOException {
File output = new File(testDir, String.format("target/%s%soutput.log", context.prefix, outputPrefix));
output.createNewFile();
Process process = JarRunnerIT
Expand All @@ -187,7 +204,7 @@ private void launch(TestContext context, File testDir, String outputPrefix, Stri
Collections.emptyList())
.start();
try {
Assertions.assertEquals(expectedMessage, DevModeTestUtils.getHttpResponse("/hello"));
Assertions.assertEquals(expectedMessage, DevModeTestUtils.getHttpResponse(path));
} finally {
process.destroy();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
<dependencies>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-core-deployment</artifactId>
<artifactId>quarkus-arc-deployment</artifactId>
</dependency>
<dependency>
<groupId>org.acme</groupId>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,19 @@
package org.acme.quarkus.ext.deployment;

import java.util.stream.Collectors;

import javax.inject.Singleton;

import io.quarkus.arc.deployment.SyntheticBeanBuildItem;
import io.quarkus.deployment.annotations.BuildStep;
import io.quarkus.deployment.annotations.ExecutionTime;
import io.quarkus.deployment.annotations.Record;
import io.quarkus.deployment.builditem.FeatureBuildItem;
import io.quarkus.deployment.pkg.builditem.CurateOutcomeBuildItem;
import io.quarkus.maven.dependency.Dependency;

import org.acme.AcmeQuarkusExtRecorder;
import org.acme.ModuleList;

class AcmeQuarkusExtProcessor {

Expand All @@ -12,4 +24,17 @@ FeatureBuildItem feature() {
return new FeatureBuildItem(FEATURE);
}

@BuildStep
@Record(ExecutionTime.STATIC_INIT)
SyntheticBeanBuildItem syntheticBean(AcmeQuarkusExtRecorder recorder, CurateOutcomeBuildItem curateOutcome) {
var localModules = curateOutcome.getApplicationModel().getDependencies().stream()
.filter(Dependency::isWorkspaceModule)
.map(Dependency::toCompactCoords)
.sorted()
.collect(Collectors.toList());
return SyntheticBeanBuildItem.configure(ModuleList.class)
.scope(Singleton.class)
.runtimeValue(recorder.initLocalModules(localModules))
.done();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-core</artifactId>
<artifactId>quarkus-arc</artifactId>
</dependency>
</dependencies>

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
package org.acme;

import java.util.List;

import io.quarkus.arc.runtime.BeanContainer;
import io.quarkus.runtime.RuntimeValue;
import io.quarkus.runtime.annotations.Recorder;

@Recorder
public class AcmeQuarkusExtRecorder {

public RuntimeValue<ModuleList> initLocalModules(List<String> localModules) {
return new RuntimeValue<>(new ModuleList(localModules));
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package org.acme;

import java.util.List;

public class ModuleList {

private final List<String> localModules;

public ModuleList(List<String> localModules) {
this.localModules = localModules;
}

public List<String> getModules() {
return localModules;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,12 @@

import org.eclipse.microprofile.config.inject.ConfigProperty;


import javax.inject.Inject;
import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;
import java.io.IOException;
import java.net.URL;
import java.util.Enumeration;

@Path("/hello")
public class HelloResource {
Expand All @@ -21,6 +19,9 @@ public class HelloResource {
@ConfigProperty(name = "greeting")
String greeting;

@Inject
ModuleList moduleList;

public HelloResource(CommonBean common, LibraryBean library) {
this.common = java.util.Objects.requireNonNull(common);
this.library = java.util.Objects.requireNonNull(library);
Expand All @@ -38,4 +39,11 @@ public String hello() {
public String greeting() {
return greeting;
}

@GET
@Path("/local-modules")
@Produces(MediaType.TEXT_PLAIN)
public String localModules() {
return moduleList.getModules().toString();
}
}

0 comments on commit d65ab1d

Please sign in to comment.