Skip to content
New issue

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

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

Already on GitHub? Sign in to your account

Migrate to Bzlmod #74

Merged
merged 12 commits into from
Dec 6, 2024
Merged

Migrate to Bzlmod #74

merged 12 commits into from
Dec 6, 2024

Conversation

jadenPete
Copy link

@jadenPete jadenPete commented Dec 4, 2024

This PR removes WORKSPACE and tests/WORKSPACE, migrating the ruleset to Bzlmod. For the most part, the ruleset can be used just as it was before (although including it is much simpler, thanks to Bzlmod's system for importing external repositories). There are a few breaking changes, though:

  • Toolchains must be registered manually (i.e. without macros like scala_register_toolchains and scala_proto_register_toolchains), since Bzlmod only allows them to be registered in MODULE.bazel-like files
  • The default Scala toolchain is no longer set via scala_register_toolchains, since that macro no longer exists. Instead, users of the ruleset must set a flag like --@rules_scala_annex//rules/scala:scala-toolchain=annex_zinc_2_13 in their .bazelrc file.
    • Previously, scala_register_toolchains invoked a repository rule that would generate the configuration value for the Scala toolchain. That way, the default could be set dynamically in the repository importing rules_scala_annex. This is no longer possible, since rules_scala_annex can't share repositories like rules_scala_annex_scala_toolchain with the repository that imports it.
  • For the targets in rules/scala_with_scalafmt.bzl, the default Scalafmt configuration file can't be set via scalafmt_default_config for the same reason mentioned above. Instead, we set it via a toolchain and use the new scalafmt_toolchain_name attribute to override the file for specific targets.
  • The emulate_rules_scala workspace macro, which was used to provide compatibility with bazelbuild/rules_scala's rules, has been deleted. It hasn't been updated in years and relied on deprecated Bazel constructs like bind and //external/... that are no longer supported in Bzlmod. I figured that now that we're pursuing unifying the rulesets, there's little point in keeping it around.

@jadenPete jadenPete requested a review from jjudd December 4, 2024 17:54
@jadenPete jadenPete self-assigned this Dec 4, 2024
MODULE.bazel Outdated
bazel_dep(name = "bazel_skylib", version = "1.7.1")

# TODO: Use buildifier instead of buildifier_prebuilt once
# https://github.com/bazelbuild/bazel-central-registry/issues/380 is resolved
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I realized after I wrote this that we could just use archive_override, but I don't think it makes much sense to have users of the ruleset fetch an entire Go toolchain and compile buildifier from scratch when it's only used internally.

Copy link

@jjudd jjudd left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Took a look through things. Had a few questions and comments. Mostly LGTM.

MODULE.bazel Outdated

# TODO: Use buildifier instead of buildifier_prebuilt once
# https://github.com/bazelbuild/bazel-central-registry/issues/380 is resolved
bazel_dep(name = "buildifier_prebuilt", version = "7.3.1")
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we mark dev dependencies as such, so they don't propagate to downstream projects? I believe we can just set dev_dependency = True on the bazel_dep call to make that the case.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I originally tried marking this as a dev dependency, but then the test repository failed to build because we reference buildifier_prebuilt in @rules_scala_annex//:BUILD.bazel.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Huh that's interesting. Do we need to do that?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We do for BUILD file formatting. I think we do it because the CI hosts don't necessarily have buildifier installed, so we need to pull it in through the repository.

MODULE.bazel Outdated
bazel_dep(name = "rules_java", version = "7.12.2")
bazel_dep(name = "rules_jvm_external", version = "6.5")
bazel_dep(name = "rules_pkg", version = "1.0.1")
bazel_dep(name = "stardoc", version = "0.7.1")
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this is also a dev dependency

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See my comment here:
#74 (comment)

MODULE.bazel Outdated
bazel_dep(name = "buildifier_prebuilt", version = "7.3.1")
bazel_dep(name = "rules_java", version = "7.12.2")
bazel_dep(name = "rules_jvm_external", version = "6.5")
bazel_dep(name = "rules_pkg", version = "1.0.1")
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this is also a dev dependency

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See my comment here:
#74 (comment)

http_archive(
name = "rules_scala_annex",
integrity = "sha256-WjZvojiclkiyVxQ1NqkH1lDeGaDLyzQOGiDsCfhVAec=",
archive_override(
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do folks need to set up toolchains in their repos with bzlmod or are our toolchains just set up in their repo by including our ruleset?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nope, they're set up by including our ruleset. I think that's the one aspect of external repositories in Bzlmod that isn't isolated—toolchains are shared throughout the entire Bazel server. See the documentation on toolchain resolution, namely the bit about the order in which toolchains are resolved.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice.

"@scala_compiler_2_13//jar",
"@scala_library_2_13//jar",
"@scala_reflect_2_13//jar",
"@annex//:org_scala_lang_scala_compiler",
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we want these to be @annex or should we assume that the person setting up the Scala toolchain has their own maven dependency tree?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh, that's a good point. The comment above says "You'll need to pull these in via rules_jvm_external", but it would be helpful to mention that annex should be replaced with the name of their dependency tree. I'll do that.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I suggest you rename it something like @maven I worry that people will miss your note and be confused as to how this is supposed to come from annex. I think both the @maven and your note will hopefully avoid that confusion.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good idea. I'll rename it.

@@ -8,14 +8,14 @@ scala_test(
],
scala_toolchain_name = "test_zinc_2_13",
runtime_deps = [
"@hamcrest_core//jar",
"@junit_interface//jar",
"@annex_test//:com_novocode_junit_interface",
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice does this mean you removed the last vestiges of the jvm imported deps and everything is now using rules_jvm_external? If so, that's awesome.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It does!


http_file = use_repo_rule("@bazel_tools//tools/build_defs/repo:http.bzl", "http_file")

http_file(
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is scope creep, but can this be downloaded with rules_jvm_external instead?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See my comment here:
#74 (comment)

urls = ["https://repo.maven.apache.org/maven2/com/chuusai/shapeless_2.13/2.3.7/shapeless_2.13-2.3.7.jar"],
)

http_file(
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Similar thought here. Can this be downloaded with rules_jvm_external instead?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I considered migrating it to rules_jvm_external, but thought it was best if it continued to be fetched via http_file. That way, it wouldn't have JavaInfo or any extra providers added, which tests that scala_import doesn't rely on any of this information.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah. Do you want to add a comment to these http_files explaining why they aren't part of rules_jvm_external? I think others may have the same thought as me in the future.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Will do.

@@ -1,19 +1,19 @@
load("@rules_scala_annex//rules:register_toolchain.bzl", "register_zinc_toolchain")
load("@rules_scala_annex//rules:scala.bzl", "scala_library")
load("@rules_scala_annex//rules/scala:workspace.bzl", "scala_2_13_version")
load("@rules_scala_annex//rules/scala:versions.bzl", "scala_2_13_version")
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It feels weird to have versions come from annex and then the jars come from the test workspace, but perhaps that is just how things are now?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmm, it does. Would you prefer we split versions.bzl into two files: one for rules_scala_annex and another for rules_scala_annex_test? I figured that even though we're forced to declare the versions in multiple places and define separate dependencies trees, it would still be best to have a single source of truth.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah probably best to minimize the number of places versions can come from and leave it as is.

MODULE.bazel Outdated
"//src/main/scala:annex_zinc_3",
)

# Please ensure these stay up-to-date with the versions in `rules/scala/versions.bzl`.
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we update this to ask folks to keep these in sync with versions.bzl and the test MODULE.bazel?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See my comment here:
#74 (comment)

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Similar response.

Jaden Peterson added 9 commits December 6, 2024 13:50
This commit redeclares every dependency in `@annex//...` depended on in
`/tests` in the `annex_test` repository.

Fortunately in most cases, but unfortunately in this case, Bzlmod
prohibits repositories from depending on each other's external
repositories. That means that the repository in `/tests` can't depend on
anything in `@annex//...` unless it defines an `annex` repository
itself.

I considered using `include` so that we could declare `annex` with the
same set of dependencies in both repositories, but unfortunately,
`/tests` wouldn't be able to `include` such a file because, according to
the documentation for `include`, "only files in the main repo may be
included".
@jadenPete
Copy link
Author

Squashed.

@jadenPete jadenPete merged commit d9e701d into lucid-master Dec 6, 2024
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants