-
Notifications
You must be signed in to change notification settings - Fork 4.1k
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
Allow unresolved symlinks inside a tree artifact #15454
Comments
I'm not too surprised. @coeuvre maybe this is something that could conceivably be fixed as a drive-by fix while you are poking at metadata handling for remote execution? (I dorealize this is a long shot) |
What is the use case for having unresolved symlinks? |
@alexjski in this case we generate an image with the application filesystem that is mounted in one of the target's partitions as read-only. One of the symlinks points to a file in the OS partition in the target. But I would say that having unresolved symlinks in the context of packaging is common. (thank you for the replying so quickly) |
After some discussion with @lfpino we came to the conclusion that there are two missing pieces before we can stabilize this:
I specifically don't want to add any requirement concerning Windows because symlinks on Windows are a shaky edifice anyway that is not used widely so I don't think it makes sense for Bazel to handle symlinks on Windows better than Windows itself. So if @lfpino fixes the above two issues, I see no obstacle to stabilizing this functionality (the flag will stay since we need to disable it at Google, but it can default to true and the Since I won't be able to attend to this in the near future, @coeuvre graciously agreed to oversee the process and review the code. |
I have RBE support implemented on a branch, which I can submit for review after #15700 and #15773. Specifically, the tests I added in #15700 seems to indicate that everything works pretty well on Windows (except possibly the Windows sandbox, which I haven't tested with yet). @lfpino Let me know if you want to sync on this. |
@fmeum I've only started looking at this recently, I'd definitely love to meet and chat about this. |
Looks like the two issues stated have been fixed. What's the status of the RBE branch? |
@ismell |
Ah, I was looking for the unresolved symlinks in tree artifacts support. Is that still being worked on or has it been shelved? |
I don't know, but I think @larsrc-google does. |
Unresolved symlinks in tree artifacts are not currently being worked on, to the best of my knowledge. |
@larsrc-google correct; we had a discussion with @tjgq and the outcome was that it's highly non-trivial how to handle them, because technically, each file in tree artifacts could require different treatment (Bazel could either resolve any symlink or not) and there isn't an obvious way to tell Bazel about each file what to do. The simplest way to resolve that to make the decision at the level of tree artifact (i.e. either every symlink is resolved or every symlink is unresolved), but making that behavior consistent requires some thought about how it works with remote execution and maybe changes to the protocol which we didn't have time for for Bazel 6.0 so we decided to shelve the problem for now. |
I'm adding this to the docs in my CL removing |
I changed the team, because the issue is more concerned with the execution phase than it is with Rules API. Local exec seemed to be the closest pick, although probably not precise one. |
@comius The feature request here is to support unresolved symlinks inside a tree artifact; the current semantics are to transparently resolve symlinks into the files they point to. I don't think this is purely an "execution phase" change, because it would affect the way artifacts are tracked by Skyframe, and require some sort of API to opt into it: either a flag to change the semantics for every tree artifact, or some way to toggle it on a per-tree or per-file-inside-tree basis. This seems within the purview of Build API (and perhaps even Core, given the Skyframe implications). |
I think it's all of the above: one would need to
|
… matching a locally produced one. This CL harmonizes the criteria for permitting a symlink for locally and remotely produced tree artifacts, namely: 1. A symlink to an absolute path is allowed. 2. A symlink to a relative path is allowed, as long as the target is inside the tree artifact. 3. The target path must exist (a consequence of tree artifacts transparently dereferencing symlinks; see also #15454). as enforced by TreeArtifactValue#visitTree (see https://cs.opensource.google/bazel/bazel/+/master:src/main/java/com/google/devtools/build/lib/skyframe/TreeArtifactValue.java;l=585;drc=de9d1f59915a36229978d46b78a22c9e5389db92). The admonition about symlinks potentially compromising hermeticity is still valid, but there's little gain in making the behavior divergent between local and remote execution. I don't believe we can go in the other direction and extend the restriction to cover local execution, as it would break existing projects. The --incompatible_remote_disallow_symlink_in_tree_artifact flag is deleted. It was added at a time when symlink resolution was extremely unreliable when building without the bytes; the state of symlink handling has improved a lot since then. I'm deleting the flag entirely (as opposed to making it a no-op) because it was only introduced in the Bazel 7 tree and hasn't made it into a stable release yet. Makes #18284 obsolete. PiperOrigin-RevId: 587691220 Change-Id: I470a8fc523bdbb7577ad5a564b6b2c0acab17d7d
…rtifact, matching a locally produced one. This CL harmonizes the criteria for permitting a symlink for locally and remotely produced tree artifacts, namely: 1. A symlink to an absolute path is allowed. 2. A symlink to a relative path is allowed, as long as the target is inside the tree artifact. 3. The target path must exist (a consequence of tree artifacts transparently dereferencing symlinks; see also bazelbuild#15454). as enforced by TreeArtifactValue#visitTree (see https://cs.opensource.google/bazel/bazel/+/master:src/main/java/com/google/devtools/build/lib/skyframe/TreeArtifactValue.java;l=585;drc=de9d1f59915a36229978d46b78a22c9e5389db92). The admonition about symlinks potentially compromising hermeticity is still valid, but there's little gain in making the behavior divergent between local and remote execution. I don't believe we can go in the other direction and extend the restriction to cover local execution, as it would break existing projects. The --incompatible_remote_disallow_symlink_in_tree_artifact flag is deleted. It was added at a time when symlink resolution was extremely unreliable when building without the bytes; the state of symlink handling has improved a lot since then. I'm deleting the flag entirely (as opposed to making it a no-op) because it was only introduced in the Bazel 7 tree and hasn't made it into a stable release yet. Makes bazelbuild#18284 obsolete. PiperOrigin-RevId: 587691220 Change-Id: I470a8fc523bdbb7577ad5a564b6b2c0acab17d7d
…rtifact, matching a locally produced one. (#20426) This CL harmonizes the criteria for permitting a symlink for locally and remotely produced tree artifacts, namely: 1. A symlink to an absolute path is allowed. 2. A symlink to a relative path is allowed, as long as the target is inside the tree artifact. 3. The target path must exist (a consequence of tree artifacts transparently dereferencing symlinks; see also #15454). as enforced by TreeArtifactValue#visitTree (see https://cs.opensource.google/bazel/bazel/+/master:src/main/java/com/google/devtools/build/lib/skyframe/TreeArtifactValue.java;l=585;drc=de9d1f59915a36229978d46b78a22c9e5389db92). The admonition about symlinks potentially compromising hermeticity is still valid, but there's little gain in making the behavior divergent between local and remote execution. I don't believe we can go in the other direction and extend the restriction to cover local execution, as it would break existing projects. The --incompatible_remote_disallow_symlink_in_tree_artifact flag is deleted. It was added at a time when symlink resolution was extremely unreliable when building without the bytes; the state of symlink handling has improved a lot since then. I'm deleting the flag entirely (as opposed to making it a no-op) because it was only introduced in the Bazel 7 tree and hasn't made it into a stable release yet. Makes #18284 obsolete. PiperOrigin-RevId: 587691220 Change-Id: I470a8fc523bdbb7577ad5a564b6b2c0acab17d7d
I ran into this issue while updating rules_zig to support the upcoming Zig 0.12.0 release (as of 0.12.0-dev.3366+8e7d9afda). With Bazel 7.0.2 this behavior raises errors of the form
With Bazel 7.1.0 this behavior raises a very confusing error of the form
|
…cannot be canonicalized (because one of the components is a non-directory or a dangling symlink). This improves the error message for a tree artifact containing a dangling symlink, which regressed in 4247c20 (see #15454 (comment)). PiperOrigin-RevId: 617870632 Change-Id: I6847084a52b1e4bb7d8a9384ad6cd5d015dddf1b
@tjgq Thank you! I tested Bazel as of commit b78d73f and can confirm that the error message is improved:
|
…cannot be canonicalized (because one of the components is a non-directory or a dangling symlink). This improves the error message for a tree artifact containing a dangling symlink, which regressed in bazelbuild@4247c20 (see bazelbuild#15454 (comment)). PiperOrigin-RevId: 617870632 Change-Id: I6847084a52b1e4bb7d8a9384ad6cd5d015dddf1b
…he path cannot be canonicalized (because one of the components is a non-directory or a dangling symlink). (#21800) This improves the error message for a tree artifact containing a dangling symlink, which regressed in 4247c20 (see #15454 (comment)). PiperOrigin-RevId: 617870632 Change-Id: I6847084a52b1e4bb7d8a9384ad6cd5d015dddf1b Commit b78d73f Co-authored-by: Googler <tjgq@google.com>
…cannot be canonicalized (because one of the components is a non-directory or a dangling symlink). This improves the error message for a tree artifact containing a dangling symlink, which regressed in bazelbuild@4247c20 (see bazelbuild#15454 (comment)). PiperOrigin-RevId: 617870632 Change-Id: I6847084a52b1e4bb7d8a9384ad6cd5d015dddf1b
…he path cannot be canonicalized (#21889) This improves the error message for a tree artifact containing a dangling symlink, which regressed in 4247c20 (see #15454 (comment)). PiperOrigin-RevId: 617870632 Change-Id: I6847084a52b1e4bb7d8a9384ad6cd5d015dddf1b Commit b78d73f Co-authored-by: Googler <tjgq@google.com>
@Wyverald This issue is a feature request that we haven't yet decided to implement. The sub-discussion started by #15454 (comment) is about a confusing error message, which has been fixed at head (b78d73f) and cherry-picked into 7.2.0 (86ff365). |
`cp -r` copies the _symlinks_, not the destination of symlinks. This results in a TreeArtifact with symlinks to content _outside_ the TreeArtifact, which is not well defined in bazel[^1]. At least bazel 7.1.1's linux-sandbox (bazel --spawn_strategy=sandboxed on Linux) does not follow the symlinks and destroys the temporary directory containing the actual files after the action, leaving a TreeArtifact of dangling symlinks. `cp -rL` chases the symlinks and creates a TreeArtifact of regular files. This has the desired behaviour in all bazel versions/sandboxes. [^1]: See discussion in bazelbuild/bazel#15454. It is unclear whether we _want_ to resolve these symlinks or leave them dangling, and behaviour varies across bazel versions and execution environment.
Hello,
I've noticed some strange behavior regarding how bazel evaluates invalid symlinks.
UC1:
When I declare an invalid symlink, in a custom rule, and I build a bazel target of that kind bazel prints out the message:
Error in declare_symlink: actions.declare_symlink() is not allowed; use the --experimental_allow_unresolved_symlinks command line option
As expected when the suggested option is added the target builds successfully.
UC2:
However when I declare a folder and add a invalid symlink in that folder I get:
ERROR: (...): Failed to resolve relative path invalid_symlink inside TreeArtifact (...) The associated file is either missing or is an invalid symlink.
Adding the --experimental_allow_unresolved_symlinks does not work in this case.
This seems like inconsistent behavior. Also it is pretty common to pack build artifacts that contain invalid symlinks that will only become valid when the package is installed on the intended target.
I looked in the documentation and did not find a way to circumvent the issue.
I prepared a minimal working example to replicate the problem: https://github.com/GWLeal/bazel_invalid_symlinks_ex
UC1:
bazel build //test:symlink_test
UC2:
bazel build //test:dir_symlink_test
I'm currently using bazel version 5.1.1
Thank you in advance for taking the time to look into this :)
The text was updated successfully, but these errors were encountered: