Skip to content

Commit d742813

Browse files
committed
fix(publish): Move .crate out of final artifact location
When `target_dir == build_dir`, ensure `cargo publish` doesn't put intermediate artifacts in the final artifact location of `cargo package`. If anyone was relying on this behavior of `cargo publish`, it will break them. We could avoid this and instead consider the location change to be part of the opt-in of using `build-dir` (until we make it opt-out). Note that we expect to be able to change the layouf of content written to `build-dir` even if users aren't opting in. On the other hand, this will help identify people relying on intermediate artifacts. While there aren't any performance benefits to this, it consolidates all of the uplifting logic and avoids dealing with overlapping `target_dir` and `build_dir`. We could optimize this further by doing a `rename` and only doing a copy if that fails.
1 parent 78a5531 commit d742813

File tree

1 file changed

+19
-28
lines changed
  • src/cargo/ops/cargo_package

1 file changed

+19
-28
lines changed

src/cargo/ops/cargo_package/mod.rs

Lines changed: 19 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
use std::collections::BTreeMap;
22
use std::collections::BTreeSet;
33
use std::collections::HashMap;
4-
use std::fs::{self, File};
4+
use std::fs::File;
55
use std::io::SeekFrom;
66
use std::io::prelude::*;
77
use std::path::{Path, PathBuf};
@@ -160,11 +160,8 @@ fn create_package(
160160
}
161161

162162
let filename = pkg.package_id().tarball_name();
163-
let dir = ws.build_dir().join("package");
164-
let mut dst = {
165-
let tmp = format!(".{}", filename);
166-
dir.open_rw_exclusive_create(&tmp, gctx, "package scratch space")?
167-
};
163+
let dir = ws.build_dir().join("package").join("tmp-crate");
164+
let dst = dir.open_rw_exclusive_create(&filename, gctx, "package scratch space")?;
168165

169166
// Package up and test a temporary tarball and only move it to the final
170167
// location if it actually passes all our tests. Any previously existing
@@ -176,16 +173,10 @@ fn create_package(
176173
let uncompressed_size = tar(ws, opts, pkg, local_reg, ar_files, dst.file(), &filename)
177174
.context("failed to prepare local package for uploading")?;
178175

179-
dst.seek(SeekFrom::Start(0))?;
180-
let src_path = dst.path();
181-
let dst_path = dst.parent().join(&filename);
182-
fs::rename(&src_path, &dst_path)
183-
.context("failed to move temporary tarball into final location")?;
184-
185176
let dst_metadata = dst
186177
.file()
187178
.metadata()
188-
.with_context(|| format!("could not learn metadata for: `{}`", dst_path.display()))?;
179+
.with_context(|| format!("could not learn metadata for: `{}`", dst.path().display()))?;
189180
let compressed_size = dst_metadata.len();
190181

191182
let uncompressed = HumanBytes(uncompressed_size);
@@ -219,22 +210,22 @@ pub fn package(ws: &Workspace<'_>, opts: &PackageOpts<'_>) -> CargoResult<Vec<Fi
219210

220211
let packaged = do_package(ws, opts, pkgs)?;
221212

213+
// Uplifting artifacts
222214
let mut result = Vec::new();
223-
let target_dir = ws.target_dir();
224-
let build_dir = ws.build_dir();
225-
if target_dir == build_dir {
226-
result.extend(packaged.into_iter().map(|(_, _, src)| src));
227-
} else {
228-
// Uplifting artifacts
229-
let artifact_dir = target_dir.join("package");
230-
for (pkg, _, src) in packaged {
231-
let filename = pkg.package_id().tarball_name();
232-
let dst =
233-
artifact_dir.open_rw_exclusive_create(filename, ws.gctx(), "uplifted package")?;
234-
src.file().seek(SeekFrom::Start(0))?;
235-
std::io::copy(&mut src.file(), &mut dst.file())?;
236-
result.push(dst);
237-
}
215+
let artifact_dir = ws.target_dir().join("package");
216+
for (pkg, _, src) in packaged {
217+
let filename = pkg.package_id().tarball_name();
218+
219+
let tmp = format!(".{filename}");
220+
let dst = artifact_dir.open_rw_exclusive_create(tmp, ws.gctx(), "uplifted package")?;
221+
src.file().seek(SeekFrom::Start(0))?;
222+
std::io::copy(&mut src.file(), &mut dst.file())?;
223+
224+
let src_path = dst.path();
225+
let dst_path = artifact_dir.join(&filename).into_path_unlocked();
226+
std::fs::rename(src_path, dst_path)?;
227+
228+
result.push(dst);
238229
}
239230

240231
Ok(result)

0 commit comments

Comments
 (0)