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

cargo build doesn't detect file changes #9598

Closed
ComicalCache opened this issue Jun 18, 2021 · 4 comments
Closed

cargo build doesn't detect file changes #9598

ComicalCache opened this issue Jun 18, 2021 · 4 comments
Labels
C-bug Category: bug

Comments

@ComicalCache
Copy link

It appears as if cargo doesn't detect file changes when deleting and replacing files.
Running cargo 1.52.0 (6976741 2021-04-21)

  1. cargo new --bin app
  2. cd app
  3. cargo build
    running the generated binary should output "Hello, world!"
  4. rm src/main.rs
  5. echo fn main() { println!("Not Hello, world"); } > main.rs
  6. cp main.rs src/main.rs
  7. cargo build
    this build finishes immediatelly and running the "generated" binary will output "Hello, world!" again

Is this behaviour intendet?

@ComicalCache ComicalCache added the C-bug Category: bug label Jun 18, 2021
@ehuss
Copy link
Contributor

ehuss commented Jun 18, 2021

Thanks for the report! Unfortunately I'm not able to reproduce with the steps provided. Can you provide more information, such as which operating system you are using, which filesystem, are you running this in a strange environment like Docker?

Here's the output that I have:

~/Temp> cargo new --bin app
     Created binary (application) `app` package
~/Temp> cd app
~/Temp/app> cargo build
   Compiling app v0.1.0 (/home/eric/Temp/app)
    Finished dev [unoptimized + debuginfo] target(s) in 0.51s
~/Temp/app> target/debug/app
Hello, world!
~/Temp/app> rm src/main.rs
~/Temp/app> echo 'fn main() { println!("Not Hello, world"); }' > main.rs
~/Temp/app> cp main.rs src/main.rs
~/Temp/app> cargo build
   Compiling app v0.1.0 (/home/eric/Temp/app)
    Finished dev [unoptimized + debuginfo] target(s) in 0.20s
~/Temp/app> target/debug/app
Not Hello, world
~/Temp/app>

In general, cargo uses filesystem mtime timestamps to detect if something needs to be rebuilt. So if you are doing something that causes the timestemp to be in the past, then cargo won't think it has changed.

@ComicalCache
Copy link
Author

ComicalCache commented Jun 18, 2021

I was first encountering this error when building a Docker image, this is the part of my config causing it

FROM rust as builder
# use the global variable
ARG RUST_APP

# create project, copy dependencies and build with default src
RUN USER=root cargo new ${RUST_APP}
WORKDIR /${RUST_APP}
COPY Cargo.toml Cargo.toml
RUN cargo build --release
RUN sha1sum target/release/${RUST_APP}

# delete src, triggers layer with compiled dependencies
RUN rm -r src

# copy program code and rebuild
ADD src src
RUN cargo build --release
RUN sha1sum target/release/${RUST_APP}

comparing the sha sums of the built binaries yields that they are the same, to fix that i added the line

...

# delete src, triggers layer with compiled dependencies
RUN rm -r src
RUN rm target/release/deps/${RUST_APP}*

...

I was able to reproduce it on Windows 10 with

  1. cargo new --bin app
  2. cd app
  3. cargo build
    Again, output of the binary will be "Hello, world!"
  4. del src\main.rs
  5. copy path\to\dif\src src\
  6. cargo build
    Output of the binary didn't change

Edit:

In general, cargo uses filesystem mtime timestamps to detect if something needs to be rebuilt. So if you are doing something that causes the timestemp to be in the past, then cargo won't think it has changed.

I just read this in your answer, this explains it but it was a very confusing and hard to debug bug, at least for me

@ehuss
Copy link
Contributor

ehuss commented Jun 18, 2021

Ah, yea, IIRC when copying into docker, you may need to add a line to run touch src/lib.rs or whatever your source files are, to update the timestamp. And, I think Windows copy preserves the timestamp (whereas unix doesn't do that by default), so if you copy a file in with an older timestamp, it won't rebuild.

I understand that it can be confusing and difficult to understand and debug. There are some issues tracking improvements to deal with this. Primarily #6529 would add change tracking based on file contents, and #2904 is for adding the ability to provide better ways to diagnose why things are or are not rebuilt.

I'm going to close as the problems are well known and tracked in those linked issues.

@pablo-johnson
Copy link

I executed the following command to delete the cache
docker builder prune --filter type=exec.cachemount
in the next built it should take your changes

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
C-bug Category: bug
Projects
None yet
Development

No branches or pull requests

3 participants