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

Add basic incompatible target skipping #10945

Closed

Conversation

philsc
Copy link
Contributor

@philsc philsc commented Mar 11, 2020

This patch aims to implement a basic version of incompatible target
skipping outlined here:
https://docs.google.com/document/d/12n5QNHmFSkuh5yAbdEex64ot4hRgR-moL1zRimU7wHQ/edit?usp=sharing

The implementation in this patch supports target skipping based
on the target platform. In a BUILD file you can now add constraints
that the target platform must satisfy in order for the target to be
built and/or tested. For example, use the following snippet to declare
a target to be compatible with Windows platforms only:

cc_binary(
    name = "bin",
    srcs = ["bin.cc"],
    target_compatible_with = [
        "@platforms//os:windows",
    ],
)

Builds triggered with :all or ... on a non-Windows platform will
simply skip the incompatible target. An appropriate note is shown on
the command line if the --show_result threshold is high enough.
Targets that transitively depend on incompatible targets are
themselves considered incompatible and will also be skipped.

Explicitly requesting an incompatible target on the command line is an
error and will cause the build to fail. Bazel will print out an
appropriate error message and inform the user what constraint could
not be satisfied.

See the new documentation in this patch for more information. In
particular, https://docs.bazel.build/versions/master/platforms.html
should be a good bit more informative.

This implementation does not make any effort to support expressing
compatibility with toolchains. It is possible that using select()
(commented on below) already makes this possible, but it's not
validated or explicitly supported in this patch.

During implementation we noticed that select() can be quite powerful
in combination with target_compatible_with. A basic summary of this
is also documented on the Platforms page.

It may be useful to create helper functions in, say, skylib to help
make complex select() statements more readable. For example, we
could replace the following:

target_compatible_with = select({
    "@platforms//os:linux": [],
    "@platforms//os:macos": [],
    "//conditions:default": [":not_compatible"],
})

with something like:

target_compatible_with = constraints.any_of([
    "@platforms//os:linux",
    "@platforms//os:macos",
])

That, however, is work for follow-up patches.

Many thanks to Austin Schuh (@AustinSchuh) and Greg Estren
(@gregestren) for working on the proposal and helping a ton on this
patch itself. Also thanks to many others who provided feedback on the
implementation.

RELNOTES: Bazel skips incompatible targets based on target platform
and target_compatible_with contents. See
https://docs.bazel.build/versions/master/platforms.html for more
details.

@philsc philsc requested a review from lberki as a code owner March 11, 2020 04:52
@philsc
Copy link
Contributor Author

philsc commented Mar 11, 2020

I'm posting this review to get some feedback from @gregestren (and anyone else interested) regarding implementation, functionality, etc.

There is various documentation missing for starters. Also, the code could use some auto-formatting love.

@philsc
Copy link
Contributor Author

philsc commented Mar 11, 2020

Ah, also looks like I need to update various unit tests. I'll get around to that also.
Again, my main interest in the short term is to get some feedback on the implementation and such.

@gregestren gregestren self-requested a review March 16, 2020 21:42
@gregestren
Copy link
Contributor

Acknowledged. Please have patience but I'll look through as soon as I can.

@aiuto aiuto added the team-Configurability platforms, toolchains, cquery, select(), config transitions label Mar 24, 2020
@gregestren
Copy link
Contributor

@philsc thanks for your patience. I'm going to look at this Monday.

Copy link
Contributor

@gregestren gregestren left a comment

Choose a reason for hiding this comment

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

First pass. Will do another pass tomorrow.

Copy link
Contributor Author

@philsc philsc left a comment

Choose a reason for hiding this comment

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

It's been longer than I'd like since I last looked at this. Looks like I have to look at a lot of the pieces again.
I'll add some comments to keep future me on track.

Copy link
Contributor Author

@philsc philsc left a comment

Choose a reason for hiding this comment

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

I'm almost done incorporating your feedback. I also have to resolve a couple of conflicts when rebasing on 3.1.

@philsc philsc force-pushed the incompatible-target-skipping branch from 4a6f40d to 6c26d99 Compare July 5, 2020 22:11
@gregestren
Copy link
Contributor

Just as a sanity check, the commit on this PR is still old, right?

@philsc

This comment has been minimized.

@philsc philsc force-pushed the incompatible-target-skipping branch 2 times, most recently from c88047b to dd2e775 Compare July 12, 2020 03:58
Copy link
Contributor

@gregestren gregestren left a comment

Choose a reason for hiding this comment

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

All my nitty comments aside, looking fairly good to me. The status reporting logic look also looks really nice.

@philsc philsc force-pushed the incompatible-target-skipping branch from dd2e775 to 21b8d4d Compare August 5, 2020 04:26
Copy link
Contributor Author

@philsc philsc left a comment

Choose a reason for hiding this comment

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

A minor update to address some of @gregestren 's feedback.

Added more TODOs to remind myself to add documentation.

@philsc philsc force-pushed the incompatible-target-skipping branch from 21b8d4d to e4df959 Compare August 31, 2020 03:27
@AustinSchuh
Copy link
Contributor

Starting the merge process...

Woah! I feel like we should frame that message. Nice job Phil on doing the heavy lifting and getting this over the finish line and thanks Greg for all your help and wisdom.

@katre
Copy link
Member

katre commented Oct 22, 2020 via email

philsc added a commit to philsc/bazel that referenced this pull request Oct 23, 2020
The upcoming Incompatible Target Skipping patch (bazelbuild#10945) introduces a
new `target_compatible_with` attribute which clashes with one of the
custom attributes in the bazel-toolchains repo. This patch fixes the
clash so we can merge the Incompatible Target Skipping path.

This is essentially a backport of bazelbuild/bazel-toolchains#913.
@philsc
Copy link
Contributor Author

philsc commented Oct 23, 2020

It needs to be in a separate PR, not just a separate commit in this PR. Will the change work standalone or does it require the rest of these changes? Either way we can merge it, I can help with the third_party side (as well as reviewing the non-third_party side).

@katre , @gregestren , here's the separate PR for the third-party portion: #12336

philsc added a commit to philsc/bazel that referenced this pull request Oct 23, 2020
The upcoming Incompatible Target Skipping patch (bazelbuild#10945) introduces a
new `target_compatible_with` attribute which clashes with one of the
custom attributes in the bazel-toolchains repo. This patch fixes the
clash so we can merge the Incompatible Target Skipping path.

This is essentially a backport of bazelbuild/bazel-toolchains#913.
bazel-io pushed a commit that referenced this pull request Oct 23, 2020
The upcoming Incompatible Target Skipping patch (#10945) introduces a
new `target_compatible_with` attribute which clashes with one of the
custom attributes in the bazel-toolchains repo. This patch fixes the
clash so we can merge the Incompatible Target Skipping path.

This is essentially a backport of bazelbuild/bazel-toolchains#913.
@philsc philsc force-pushed the incompatible-target-skipping branch from 66f85e2 to 9c9905c Compare October 23, 2020 15:40
@philsc
Copy link
Contributor Author

philsc commented Oct 23, 2020

@katre , this is now rebased on top of the separate third-party and WORKSPACE patches.

Copy link
Member

@katre katre left a comment

Choose a reason for hiding this comment

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

Hi @philsc! This is a great change and I'm amazed at the progress you've made.

The large number of comments is my fault: I wasn't keeping up with the status of this PR and so am coming in late with suggestions and comments. Most of them are fairly minor, and are aimed at making the code be more inline with our internal style guide.

The only major change I'd like to propose is in IncompatiblePlatformProvider, and I've left comments there explaining my concerns and suggestions. If these have already been raised during this review, I apologize, and will happily defer to the previous reviewers. If you decide to leave that class as-is, however, could you add comments explaining the rationale for the decision?

Thanks, and sorry for my tardiness.

site/docs/platforms.md Outdated Show resolved Hide resolved
site/docs/platforms.md Outdated Show resolved Hide resolved
src/test/shell/bazel/target_compatible_with_test.sh Outdated Show resolved Hide resolved
src/test/shell/bazel/target_compatible_with_test.sh Outdated Show resolved Hide resolved
src/test/shell/bazel/target_compatible_with_test.sh Outdated Show resolved Hide resolved
src/test/shell/bazel/target_compatible_with_test.sh Outdated Show resolved Hide resolved
@AustinSchuh AustinSchuh force-pushed the incompatible-target-skipping branch from 9c9905c to 22818fa Compare October 23, 2020 21:43
@AustinSchuh
Copy link
Contributor

Since I have the day off, I volunteered to help Phil out addressing comments. The easy ones should be done. Pushed to get some CI feedback. Now time to look at the harder ones.

@AustinSchuh AustinSchuh force-pushed the incompatible-target-skipping branch 4 times, most recently from 2915f50 to 397f3bc Compare October 23, 2020 23:57
This patch aims to implement a basic version of incompatible target
skipping outlined here:
https://docs.google.com/document/d/12n5QNHmFSkuh5yAbdEex64ot4hRgR-moL1zRimU7wHQ/edit?usp=sharing

The implementation in this patch supports target skipping based
on the target platform. In a `BUILD` file you can now add constraints
that the target platform must satisfy in order for the target to be
built and/or tested. For example, use the following snippet to declare
a target to be compatible with Windows platforms only:

  cc_binary(
      name = "bin",
      srcs = ["bin.cc"],
      target_compatible_with = [
          "@platforms//os:windows",
      ],
  )

Builds triggered with `:all` or `...` on a non-Windows platform will
simply skip the incompatible target. An appropriate note is shown on
the command line if the `--show_result` threshold is high enough.
Targets that transitively depend on incompatible targets are
themselves considered incompatible and will also be skipped.

Explicitly requesting an incompatible target on the command line is an
error and will cause the build to fail. Bazel will print out an
appropriate error message and inform the user what constraint could
not be satisfied.

See the new documentation in this patch for more information. In
particular, https://docs.bazel.build/versions/master/platforms.html
should be a good bit more informative.

This implementation does not make any effort to support expressing
compatibility with toolchains. It is possible that using `select()`
(commented on below) already makes this possible, but it's not
validated or explicitly supported in this patch.

During implementation we noticed that `select()` can be quite powerful
in combination with `target_compatible_with`. A basic summary of this
is also documented on the Platforms page.

It may be useful to create helper functions in, say, skylib to help
make complex `select()` statements more readable. For example, we
could replace the following:

  target_compatible_with = select({
      "@platforms//os:linux": [],
      "@platforms//os:macos": [],
      "//conditions:default": [":not_compatible"],
  })

with something like:

  target_compatible_with = constraints.any_of([
      "@platforms//os:linux",
      "@platforms//os:macos",
  ])

That, however, is work for follow-up patches.

Many thanks to Austin Schuh (@AustinSchuh) and Greg Estren
(@gregestren) for working on the proposal and helping a ton on this
patch itself. Also thanks to many others who provided feedback on the
implementation.

RELNOTES: Bazel skips incompatible targets based on target platform
and `target_compatible_with` contents. See
https://docs.bazel.build/versions/master/platforms.html for more
details.
@AustinSchuh AustinSchuh force-pushed the incompatible-target-skipping branch from 397f3bc to c853ee9 Compare October 24, 2020 01:05
Copy link
Member

@katre katre left a comment

Choose a reason for hiding this comment

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

This looks great, thanks so much.

Greg, it's ready to be re-imported. let me know if you want me to help.

@gregestren
Copy link
Contributor

This looks great, thanks so much.

Greg, it's ready to be re-imported. let me know if you want me to help.

Got it. I'll re-import today. Stay tuned all...

bazel-io pushed a commit that referenced this pull request Oct 26, 2020
ARM-only target with --cpu=x86.

Support work for #10945.

PiperOrigin-RevId: 339113675
@bazel-io bazel-io closed this in 22b4dbc Oct 27, 2020
philsc added a commit to philsc/bazel-toolchains that referenced this pull request Oct 28, 2020
…rbe_config

This essentially the same patch as
9a2fbe2 except that it deals with
`target_compatible_with` instead of `exec_properties`.

The PR bazelbuild/bazel#10945 adds a new `target_compatible_with`
attribute to all rules. That includes repository rules. Currently the
patch fails in `//src/test/shell/bazel:bazel_bootstrap_distfile_test`.
The error complains about:

  Error in repository_rule: There is already a built-in attribute 'target_compatible_with' which cannot be overridden

Since the repository rule is abstracted by a macro, it should be
fairly safe to rename the attribute to
`internal_target_compatible_with`.
@philsc philsc deleted the incompatible-target-skipping branch November 3, 2020 04:13
@peakschris
Copy link

Does this feature work with general rules? I'm finding that the presence of this rule continues to trigger load of py3_image in WORKSPACE when building on windows, and since io_bazel_rules_docker are not supported on Windows, this causes a build error.

py3_image(
name = "myscript",
srcs = ["myscript.py"],
data = [":somedeps"],
deps = [requirement("flask")],
target_compatible_with = ["@platforms//os:linux"],
)

@aiuto
Copy link
Contributor

aiuto commented Sep 8, 2022

Skipping the target happens after we have analyzed enough to evaluate the rule, so all the workspace loads have to have happened already. If you want py3_image to essentially be a no-op when you are building from windows, then you'll have to do workspace gymnastics to load fake docker rules.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
cla: yes team-Configurability platforms, toolchains, cquery, select(), config transitions
Projects
None yet
Development

Successfully merging this pull request may close these issues.

10 participants