Skip to content
New issue

Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? # to your account

Followup: External modules navigation in starlark files #7294

Merged
merged 2 commits into from
Feb 17, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1,216 changes: 5 additions & 1,211 deletions MODULE.bazel.lock

Large diffs are not rendered by default.

Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@

/** Bazel version */
public class BazelVersion implements ProtoWrapper<ProjectData.BazelVersion> {
static final BazelVersion DEVELOPMENT = new BazelVersion(999, 999, 999);
public static final BazelVersion DEVELOPMENT = new BazelVersion(999, 999, 999);
private static final Pattern PATTERN = Pattern.compile("([[0-9]\\.]+)");

private final int major;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,10 @@ public BuildSystemName buildSystem() {
return bazelVersion != null ? BuildSystemName.Bazel : BuildSystemName.Blaze;
}

public BazelVersion getBazelVersion() {
return bazelVersion;
}

@Override
public String toString() {
if (bazelVersion != null) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,27 +15,31 @@
*/
package com.google.idea.blaze.base.model;

import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
import com.google.idea.blaze.base.async.FutureUtil;
import com.google.idea.blaze.base.async.executor.BlazeExecutor;
import com.google.idea.blaze.base.bazel.BazelVersion;
import com.google.idea.blaze.base.bazel.BuildSystem;
import com.google.idea.blaze.base.command.BlazeCommandName;
import com.google.idea.blaze.base.command.BlazeFlags;
import com.google.idea.blaze.base.command.BlazeInvocationContext;
import com.google.idea.blaze.base.command.info.BlazeInfo;
import com.google.idea.blaze.base.command.mod.BlazeModRunner;
import com.google.idea.blaze.base.projectview.ProjectViewSet;
import com.google.idea.blaze.base.scope.BlazeContext;
import com.google.idea.blaze.base.scope.output.StatusOutput;
import com.google.idea.blaze.base.scope.scopes.TimingScope.EventType;
import com.google.idea.blaze.base.settings.Blaze;
import com.google.idea.blaze.base.settings.BlazeImportSettings;
import com.google.idea.blaze.base.settings.BlazeImportSettingsManager;
import com.google.idea.blaze.base.sync.SyncListener;
import com.google.idea.blaze.base.sync.SyncMode;
import com.google.idea.blaze.exception.BuildException;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.registry.Registry;

import javax.annotation.Nonnull;
import java.util.List;
import java.util.concurrent.ExecutionException;
import javax.annotation.Nonnull;

public class ExternalWorkspaceDataProvider {

Expand All @@ -55,23 +59,23 @@ public static ExternalWorkspaceDataProvider getInstance(Project project) {
return project.getService(ExternalWorkspaceDataProvider.class);
}

static Boolean isEnabled(BlazeVersionData blazeVersionData) {
private static Boolean isEnabled(BazelVersion version) {
if (!Registry.is("bazel.read.external.workspace.data")) {
logger.info("disabled by registry");
return false;
}

return blazeVersionData.bazelIsAtLeastVersion(MINIMUM_BLAZE_VERSION);
return version.isAtLeast(MINIMUM_BLAZE_VERSION);
}

public ListenableFuture<ExternalWorkspaceData> getExternalWorkspaceData(
public ExternalWorkspaceData getExternalWorkspaceData(
BlazeContext context,
List<String> blazeFlags,
BlazeVersionData blazeVersionData,
BlazeInfo blazeInfo) {
ProjectViewSet projectViewSet,
BazelVersion bazelVersion,
BlazeInfo blazeInfo) throws BuildException {
// check minimum bazel version
if (!isEnabled(blazeVersionData)) {
return Futures.immediateFuture(ExternalWorkspaceData.EMPTY);
if (!isEnabled(bazelVersion)) {
return ExternalWorkspaceData.EMPTY;
}

// validate that bzlmod is enabled (technically this validates that the --enable_bzlmod is not
Expand All @@ -80,19 +84,41 @@ public ListenableFuture<ExternalWorkspaceData> getExternalWorkspaceData(
if (starLarkSemantics == null
|| starLarkSemantics.isEmpty()
|| starLarkSemantics.contains("enable_bzlmod=false")) {
return Futures.immediateFuture(ExternalWorkspaceData.EMPTY);
return ExternalWorkspaceData.EMPTY;
}

return BlazeExecutor.getInstance()
.submit(() -> getCachedExternalWorkspaceData(context, blazeFlags));
List<String> blazeFlags =
BlazeFlags.blazeFlags(
project,
projectViewSet,
BlazeCommandName.MOD,
context,
BlazeInvocationContext.SYNC_CONTEXT);

final var future = BlazeExecutor.getInstance()
.submit(() -> getOrComputeWorkspaceData(context, blazeFlags));

final var result = FutureUtil.waitForFuture(context, future)
.timed(Blaze.buildSystemName(project) + "Mod", EventType.BlazeInvocation)
.withProgressMessage("Resolving module repository mapping...")
.onError(String.format("Could not run %s mod dump_repo_mapping", Blaze.buildSystemName(project)))
.run();

final var data = result.result();
if (data != null) {
return data;
}

throw new BuildException("Could not resolve module repository mapping", result.exception());
}

private @Nonnull ExternalWorkspaceData getCachedExternalWorkspaceData(
private @Nonnull ExternalWorkspaceData getOrComputeWorkspaceData(
BlazeContext context, List<String> blazeFlags) {
if (externalWorkspaceData != null) {
logger.info("Using cached External Repository Mapping");
return externalWorkspaceData;
}

try {
BlazeImportSettings importSettings =
BlazeImportSettingsManager.getInstance(project).getImportSettings();
Expand All @@ -119,7 +145,7 @@ public ListenableFuture<ExternalWorkspaceData> getExternalWorkspaceData(
return externalWorkspaceData;
}

public void invalidate(BlazeContext context, SyncMode syncMode) {
private void invalidate(BlazeContext context, SyncMode syncMode) {
logger.info("Invalidating External Repository Mapping info");
context.output(
new StatusOutput(
Expand All @@ -128,6 +154,7 @@ public void invalidate(BlazeContext context, SyncMode syncMode) {
}

public static final class Invalidator implements SyncListener {

@Override
public void onSyncStart(Project project, BlazeContext context, SyncMode syncMode) {
if (syncMode == SyncMode.FULL) {
Expand Down
39 changes: 39 additions & 0 deletions base/src/com/google/idea/blaze/base/qsync/BazelInfoHandler.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
/*
* Copyright 2024 The Bazel Authors. All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.google.idea.blaze.base.qsync;

import static com.google.idea.blaze.base.sync.SyncScope.SyncFailedException;

import com.google.idea.blaze.base.bazel.BuildSystem;
import com.google.idea.blaze.base.command.info.BlazeInfo;
import com.google.idea.blaze.exception.BuildException;

public class BazelInfoHandler {
private final BuildSystem.BuildInvoker buildInvoker;

BazelInfoHandler(BuildSystem.BuildInvoker buildInvoker) {
this.buildInvoker = buildInvoker;
}

public BlazeInfo getBazelInfo() throws BuildException {
// TODO: can we cache the results from handlers?
try {
return buildInvoker.getBlazeInfo();
} catch (SyncFailedException e) {
throw new BuildException("Could not get bazel info", e);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@
*/
package com.google.idea.blaze.base.qsync;

import com.google.auto.value.extension.memoized.Memoized;
import com.google.idea.blaze.base.bazel.BazelVersion;
import com.google.idea.blaze.base.bazel.BuildSystem;
import com.google.idea.blaze.base.bazel.BuildSystem.BuildInvoker;
import com.google.idea.blaze.base.sync.SyncScope.SyncFailedException;
Expand All @@ -34,11 +36,18 @@ public BazelVersionHandler(BuildSystem buildSystem, BuildInvoker buildInvoker) {
this.buildInvoker = buildInvoker;
}

public Optional<String> getBazelVersion() throws BuildException {
public Optional<String> getBazelVersionStr() throws BuildException {
// TODO: can we cache the results from handlers?
try {
return buildSystem.getBazelVersionString(buildInvoker.getBlazeInfo());
} catch (SyncFailedException e) {
throw new BuildException("Could not get bazel version", e);
}
}

public BazelVersion getBazelVersion() throws BuildException {
return getBazelVersionStr()
.map(BazelVersion::parseVersion)
.orElse(BazelVersion.DEVELOPMENT);
}
}
16 changes: 14 additions & 2 deletions base/src/com/google/idea/blaze/base/qsync/ProjectLoader.java
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,9 @@
import com.google.common.util.concurrent.ListeningExecutorService;
import com.google.idea.blaze.base.bazel.BuildSystem;
import com.google.idea.blaze.base.bazel.BuildSystemProvider;
import com.google.idea.blaze.base.command.info.BlazeInfo;
import com.google.idea.blaze.base.model.ExternalWorkspaceData;
import com.google.idea.blaze.base.model.ExternalWorkspaceDataProvider;
import com.google.idea.blaze.base.model.primitives.WorkspaceRoot;
import com.google.idea.blaze.base.projectview.ProjectViewManager;
import com.google.idea.blaze.base.projectview.ProjectViewSet;
Expand Down Expand Up @@ -213,14 +216,21 @@ public QuerySyncProject loadProject(BlazeContext context) throws BuildException
QuerySync.USE_NEW_RES_DIR_LOGIC::getValue,
() -> !QuerySync.EXTRACT_RES_PACKAGES_AT_BUILD_TIME.getValue());
QueryRunner queryRunner = createQueryRunner(buildSystem);
BazelVersionHandler versionHandler =
new BazelVersionHandler(buildSystem, buildSystem.getBuildInvoker(project, context));
ProjectQuerier projectQuerier =
createProjectQuerier(
projectRefresher,
queryRunner,
vcsHandler,
new BazelVersionHandler(buildSystem, buildSystem.getBuildInvoker(project, context)));
versionHandler);
QuerySyncSourceToTargetMap sourceToTargetMap =
new QuerySyncSourceToTargetMap(graph, workspaceRoot.path());
BlazeInfo blazeInfo =
new BazelInfoHandler(buildSystem.getBuildInvoker(project, context))
.getBazelInfo();
ExternalWorkspaceData externalWorkspaceData = ExternalWorkspaceDataProvider.getInstance(project)
.getExternalWorkspaceData(context, projectViewSet, versionHandler.getBazelVersion(), blazeInfo);

QuerySyncProject querySyncProject =
new QuerySyncProject(
Expand All @@ -247,7 +257,9 @@ public QuerySyncProject loadProject(BlazeContext context) throws BuildException
sourceToTargetMap,
projectViewManager,
buildSystem,
projectTransformRegistry);
projectTransformRegistry,
blazeInfo,
externalWorkspaceData);
QuerySyncProjectListenerProvider.registerListenersFor(querySyncProject);
projectTransformRegistry.addAll(ProjectProtoTransformProvider.getAll(latestProjectDef));

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ public PostQuerySyncData fullQuery(ProjectDefinition projectDef, BlazeContext co

RefreshOperation fullQuery =
projectRefresher.startFullUpdate(
context, projectDef, vcsState, bazelVersionProvider.getBazelVersion());
context, projectDef, vcsState, bazelVersionProvider.getBazelVersionStr());

QuerySpec querySpec = fullQuery.getQuerySpec().get();
return fullQuery.createPostQuerySyncData(queryRunner.runQuery(querySpec, context));
Expand Down Expand Up @@ -134,7 +134,7 @@ public PostQuerySyncData update(

Optional<String> bazelVersion = Optional.empty();
try {
bazelVersion = bazelVersionProvider.getBazelVersion();
bazelVersion = bazelVersionProvider.getBazelVersionStr();
} catch (BuildException e) {
context.handleExceptionAsWarning("Could not get bazel version", e);
}
Expand Down
13 changes: 11 additions & 2 deletions base/src/com/google/idea/blaze/base/qsync/QuerySyncProject.java
Original file line number Diff line number Diff line change
Expand Up @@ -26,8 +26,10 @@
import com.google.common.io.ByteSource;
import com.google.common.io.MoreFiles;
import com.google.idea.blaze.base.bazel.BuildSystem;
import com.google.idea.blaze.base.command.info.BlazeInfo;
import com.google.idea.blaze.base.logging.utils.querysync.BuildDepsStatsScope;
import com.google.idea.blaze.base.logging.utils.querysync.SyncQueryStatsScope;
import com.google.idea.blaze.base.model.ExternalWorkspaceData;
import com.google.idea.blaze.base.model.primitives.WorkspacePath;
import com.google.idea.blaze.base.model.primitives.WorkspaceRoot;
import com.google.idea.blaze.base.projectview.ProjectViewManager;
Expand Down Expand Up @@ -146,7 +148,9 @@ public QuerySyncProject(
QuerySyncSourceToTargetMap sourceToTargetMap,
ProjectViewManager projectViewManager,
BuildSystem buildSystem,
ProjectProtoTransform.Registry projectProtoTransforms) {
ProjectProtoTransform.Registry projectProtoTransforms,
BlazeInfo blazeInfo,
ExternalWorkspaceData externalWorkspaceData) {
this.project = project;
this.snapshotFilePath = snapshotFilePath;
this.snapshotHolder = snapshotHolder;
Expand All @@ -171,7 +175,12 @@ public QuerySyncProject(
this.projectViewManager = projectViewManager;
this.buildSystem = buildSystem;
this.projectProtoTransforms = projectProtoTransforms;
projectData = new QuerySyncProjectData(workspacePathResolver, workspaceLanguageSettings);
projectData = new QuerySyncProjectData(
workspacePathResolver,
workspaceLanguageSettings,
blazeInfo,
externalWorkspaceData
);
}

public Project getIdeProject() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,8 @@ public class QuerySyncProjectData implements BlazeProjectData {

private final WorkspacePathResolver workspacePathResolver;
private final Optional<QuerySyncProjectSnapshot> blazeProject;
private final ExternalWorkspaceData externalWorkspaceData;
private final BlazeInfo blazeInfo;

/**
* Static language settings are those derived from the {@code .blazeproject} file. The dynamic
Expand All @@ -58,22 +60,37 @@ public class QuerySyncProjectData implements BlazeProjectData {

QuerySyncProjectData(
WorkspacePathResolver workspacePathResolver,
WorkspaceLanguageSettings workspaceLanguageSettings) {
this(Optional.empty(), workspacePathResolver, workspaceLanguageSettings);
WorkspaceLanguageSettings workspaceLanguageSettings,
BlazeInfo blazeInfo,
ExternalWorkspaceData externalWorkspaceData) {
this(
Optional.empty(),
workspacePathResolver,
workspaceLanguageSettings, blazeInfo,
externalWorkspaceData);
}

private QuerySyncProjectData(
Optional<QuerySyncProjectSnapshot> projectSnapshot,
WorkspacePathResolver workspacePathResolver,
WorkspaceLanguageSettings workspaceLanguageSettings) {
WorkspaceLanguageSettings workspaceLanguageSettings,
BlazeInfo blazeInfo,
ExternalWorkspaceData externalWorkspaceData) {
this.blazeProject = projectSnapshot;
this.workspacePathResolver = workspacePathResolver;
this.staticLanguageSettings = workspaceLanguageSettings;
this.blazeInfo = blazeInfo;
this.externalWorkspaceData = externalWorkspaceData;
}

public QuerySyncProjectData withSnapshot(QuerySyncProjectSnapshot newSnapshot) {
return new QuerySyncProjectData(
Optional.of(newSnapshot), workspacePathResolver, staticLanguageSettings);
Optional.of(newSnapshot),
workspacePathResolver,
staticLanguageSettings,
blazeInfo,
externalWorkspaceData
);
}

@Nullable
Expand Down Expand Up @@ -140,7 +157,7 @@ public TargetMap getTargetMap() {

@Override
public BlazeInfo getBlazeInfo() {
throw new NotSupportedWithQuerySyncException("getBlazeInfo");
return blazeInfo;
}

@Override
Expand Down Expand Up @@ -179,7 +196,7 @@ public RemoteOutputArtifacts getRemoteOutputs() {

@Override
public ExternalWorkspaceData getExternalWorkspaceData() {
throw new NotSupportedWithQuerySyncException("getExternalWorkspaceData");
return externalWorkspaceData;
}

@Override
Expand Down
Loading