Skip to content
This repository has been archived by the owner on Apr 3, 2023. It is now read-only.

Depend on package but not its dependencies #148

Open
achew22 opened this issue Jun 4, 2022 · 3 comments
Open

Depend on package but not its dependencies #148

achew22 opened this issue Jun 4, 2022 · 3 comments

Comments

@achew22
Copy link

achew22 commented Jun 4, 2022

A bit of an odd situation, so thank you in advance for humoring me.

I have a project that I'm working on that uses rules_spm for dependency management. I also am using the built into rules_swift grpc rules. This means my dependencies are partially managed by the built-in to rules_swift third_party stuff and partly by rules_spm.

Things worked great for quite a while, but eventually I ended up in a place where one of my dependencies depended on something that was provided both through rules_swift and through rules_spm. This causes the linker to be unsure of what to do, and it gives up (dumping a truly impressive amount out to the screen).

Errors are of the form:

duplicate symbol 'NIOConcurrencyHelpers.ConditionLock.__allocating_init(value: A) -> NIOConcurrencyHelpers.ConditionLock<A>' in:
    bazel-out/ios-sim_arm64-min15.0-applebin_ios-ios_sim_arm64-fastbuild-ST-4e6c2a19403f/bin/external/com_github_apple_swift_nio/libNIOConcurrencyHelpers.a(lock.swift.o)
    bazel-out/ios-sim_arm64-min15.0-applebin_ios-ios_sim_arm64-fastbuild-ST-4e6c2a19403f/bin/external/swift_pkgs/swift-nio/libNIOConcurrencyHelpers_a_file.a(lock.swift.o)

I looked in the docs for how do this but spm_pkg doesn't seem to have a way to adjust the dependencies of a dependency. Is there some other way to do this that I'm missing?

@cgrindel
Copy link
Owner

cgrindel commented Jun 8, 2022

Sorry for the delay in responding. I am out on vacation.

This is an interesting problem. I don't have an immediate answer. The current implementation for rules_spm let Swift Package Manager do the work of fetching and building the dependencies. The results are then made available to Bazel using import rules.

What would you prefer for the behavior?

  • Is your version different from the one that SPM picked?
  • Could you just use the one that SPM picked?

@achew22
Copy link
Author

achew22 commented Jun 9, 2022

Sorry for the delay in responding. I am out on vacation.

Feel no pressure to do anything while you're on vacation.

Is your version different from the one that SPM picked?

It is the same version that SPM picked.

Could you just use the one that SPM picked?

Unfortunately the dependency is baked into rules_swift. The fix here could be to use toolchains, but unfortunately proto toolchains is a feature not yet available.

You bring up an interesting solution to this problem which is that I can patch my copy of rules_swift to depend on the copy of gRPC that comes in from spm, which I'm going to try and may have some luck with. Ultimately, I think proto toolchains are the fix here, but without them being implemented I don't really see a path forward without something in rules_spm that lets you specify "overrides" or something like that, or the solution I put below.

I guess the real question here is. is this a generic problem that rules_spm needs to solve because there can be conflicts like this that are added by rules_swift, or another Bazel aware project, like say apple_support . Looking through rules_swift it doesn't look like there are a lot of direct dependencies that would exhibit this beyond gRPC, but, as I'm sure you're aware, transitive dependencies are tricky.


In case anyone is curious about this patch in the future, here is what I ended up with.

I put this patch file in //third_party/rules_swift:0001-Replace-support-libraries-with-rules_spm-targets.patch

From 2ce98b5e5d35d835adb5b669592ceb195367d980 Mon Sep 17 00:00:00 2001
From: Andrew Z Allen
Date: Wed, 8 Jun 2022 15:42:39 -0600
Subject: [PATCH] Replace support libraries with rules_spm targets

This allows installs a support version that deviates from the version
that was used to generate the compiled sources.
---
 swift/internal/swift_grpc_library.bzl      | 2 +-
 swift/internal/swift_protoc_gen_aspect.bzl | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/swift/internal/swift_grpc_library.bzl b/swift/internal/swift_grpc_library.bzl
index 52258f8..1b57a37 100644
--- a/swift/internal/swift_grpc_library.bzl
+++ b/swift/internal/swift_grpc_library.bzl
@@ -394,7 +394,7 @@ The kind of definitions that should be generated:
             ),
             # TODO(b/63389580): Migrate to proto_lang_toolchain.
             "_proto_support": attr.label_list(
-                default = [Label("@com_github_grpc_grpc_swift//:GRPC")],
+                default = [Label("@swift_pkgs//grpc-swift:GRPC")],
             ),
             "_protoc": attr.label(
                 cfg = "exec",
diff --git a/swift/internal/swift_protoc_gen_aspect.bzl b/swift/internal/swift_protoc_gen_aspect.bzl
index 1cca6a7..bee78a2 100644
--- a/swift/internal/swift_protoc_gen_aspect.bzl
+++ b/swift/internal/swift_protoc_gen_aspect.bzl
@@ -565,7 +565,7 @@ swift_protoc_gen_aspect = aspect(
             # TODO(b/63389580): Migrate to proto_lang_toolchain.
             "_proto_support": attr.label_list(
                 default = [
-                    Label("@com_github_apple_swift_protobuf//:SwiftProtobuf"),
+                    Label("@swift_pkgs//SwiftProtobuf:SwiftProtobuf"),
                 ],
             ),
             "_protoc": attr.label(
--

Then I applied it in my workspace thusly

load("@bazel_tools//tools/build_defs/repo:git.bzl", "git_repository")
git_repository(
    name = "build_bazel_rules_swift",
    commit = "a31c34e882dd68d15e8ed1007b1adc241857ab5a",
    remote = "https://github.com/bazelbuild/rules_swift",
    patch_args = ["-p1"],
    patches = [
      "//third_party/rules_swift:0001-Replace-support-libraries-with-rules_spm-targets.patch",
    ],
)

@cgrindel
Copy link
Owner

In the current implementation of rules_spm, I let Swift Package Manager perform the fetch and do the build. It then exposes the built targets via import rules. This leads to the duplicate symbols issue that has been reported. I am toying with the idea of updating rules_spm to let SPM do the fetch, but generate Bazel build targets. This would address this issue and some cross-platform issues that are not handled properly today.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants