Skip to content

Commit eb7c845

Browse files
committed
feat: only copy directories if necessary
Signed-off-by: Roman Volosatovs <[email protected]>
1 parent 6c955e3 commit eb7c845

File tree

4 files changed

+85
-59
lines changed

4 files changed

+85
-59
lines changed

Cargo.lock

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
[package]
22
name = "wit-deps-cli"
3-
version = "0.3.7"
3+
version = "0.4.0"
44
description = "WIT dependency manager"
55

66
authors.workspace = true
@@ -56,4 +56,4 @@ tracing = { version = "0.1", default-features = false }
5656
tracing-subscriber = { version = "0.3", default-features = false }
5757
url = { version = "2", default-features = false }
5858
wit-bindgen = { version = "0.7", default-features = false }
59-
wit-deps = { path = "./crates/wit-deps", version = "0.3.2" }
59+
wit-deps = { path = "./crates/wit-deps", version = "0.4" }

crates/wit-deps/Cargo.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
[package]
22
name = "wit-deps"
3-
version = "0.3.2"
3+
version = "0.4.0"
44
description = "WIT dependency management"
55
readme = "../../README.md"
66

crates/wit-deps/src/manifest.rs

Lines changed: 80 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -211,18 +211,94 @@ impl Entry {
211211
reqwest::Client::new()
212212
};
213213

214-
match self {
214+
let entry = if let Some(LockEntry {
215+
source,
216+
digest: ldigest,
217+
deps: ldeps,
218+
}) = lock
219+
{
220+
let deps = if ldeps.is_empty() {
221+
Ok(HashMap::default())
222+
} else {
223+
let base = out
224+
.parent()
225+
.with_context(|| format!("`{}` does not have a parent", out.display()))?;
226+
lock_deps(ldeps.iter().cloned().map(|id| {
227+
let path = base.join(&id);
228+
(id, path)
229+
}))
230+
.await
231+
};
232+
match (LockEntry::digest(out).await, source, deps) {
233+
(Ok(digest), Some(source), Ok(deps)) if digest == *ldigest => {
234+
// NOTE: Manually deleting transitive dependencies of this
235+
// dependency from `dst` is considered user error
236+
// TODO: Check that transitive dependencies are in sync
237+
match (self, source) {
238+
(Self::Url { url, .. }, LockEntrySource::Url(lurl)) if url == *lurl => {
239+
debug!("`{}` is already up-to-date, skip fetch", out.display());
240+
return Ok((
241+
LockEntry::new(
242+
Some(LockEntrySource::Url(url)),
243+
digest,
244+
deps.keys().cloned().collect(),
245+
),
246+
deps,
247+
));
248+
}
249+
(Self::Path(path), LockEntrySource::Path(lpath)) if path == *lpath => {
250+
debug!("`{}` is already up-to-date, skip copy", out.display());
251+
return Ok((
252+
LockEntry::new(
253+
Some(LockEntrySource::Path(path)),
254+
digest,
255+
deps.keys().cloned().collect(),
256+
),
257+
deps,
258+
));
259+
}
260+
(entry, _) => {
261+
debug!("source mismatch");
262+
entry
263+
}
264+
}
265+
}
266+
(Ok(digest), _, _) => {
267+
debug!(
268+
"`{}` is out-of-date (sha256: {})",
269+
out.display(),
270+
hex::encode(digest.sha256)
271+
);
272+
self
273+
}
274+
(Err(e), _, _) if e.kind() == std::io::ErrorKind::NotFound => {
275+
debug!("locked dependency for `{}` missing", out.display());
276+
self
277+
}
278+
(Err(e), _, _) => {
279+
error!(
280+
"failed to compute dependency digest for `{}`: {e}",
281+
out.display()
282+
);
283+
self
284+
}
285+
}
286+
} else {
287+
self
288+
};
289+
match entry {
215290
Self::Path(path) => {
216-
let dst = at.map(|at| at.as_ref().join(&path));
217-
let deps = copy_wits(&dst.as_ref().unwrap_or(&path), out, skip_deps).await?;
291+
let src = at.map(|at| at.as_ref().join(&path));
292+
let src = src.as_ref().unwrap_or(&path);
293+
let deps = copy_wits(src, out, skip_deps).await?;
218294
trace!(?deps, "copied WIT definitions to `{}`", out.display());
219295
let deps = lock_deps(deps).await?;
220296
trace!(
221297
?deps,
222298
"locked transitive dependencies of `{}`",
223299
out.display()
224300
);
225-
let digest = LockEntry::digest(&dst.as_ref().unwrap_or(&path)).await?;
301+
let digest = LockEntry::digest(out).await?;
226302
Ok((
227303
LockEntry::new(
228304
Some(LockEntrySource::Path(path)),
@@ -237,56 +313,6 @@ impl Entry {
237313
sha256,
238314
sha512,
239315
} => {
240-
if let Some(LockEntry {
241-
source,
242-
digest: ldigest,
243-
deps: ldeps,
244-
}) = lock
245-
{
246-
let deps = if ldeps.is_empty() {
247-
Ok(HashMap::default())
248-
} else {
249-
let base = out.parent().with_context(|| {
250-
format!("`{}` does not have a parent", out.display())
251-
})?;
252-
lock_deps(ldeps.iter().cloned().map(|id| {
253-
let path = base.join(&id);
254-
(id, path)
255-
}))
256-
.await
257-
};
258-
match (LockEntry::digest(out).await, source, deps) {
259-
(Ok(digest), Some(LockEntrySource::Url(lurl)), Ok(deps))
260-
if digest == *ldigest && url == *lurl =>
261-
{
262-
debug!("`{}` is already up-to-date, skip fetch", out.display());
263-
// NOTE: Manually deleting transitive dependencies of this
264-
// dependency from `dst` is considered user error
265-
// TODO: Check that transitive dependencies are in sync
266-
return Ok((
267-
LockEntry::new(
268-
Some(LockEntrySource::Url(url)),
269-
digest,
270-
deps.keys().cloned().collect(),
271-
),
272-
deps,
273-
));
274-
}
275-
(Ok(digest), _, _) => {
276-
debug!(
277-
"`{}` is out-of-date (sha256: {})",
278-
out.display(),
279-
hex::encode(digest.sha256)
280-
);
281-
}
282-
(Err(e), _, _) if e.kind() == std::io::ErrorKind::NotFound => {
283-
debug!("locked dependency for `{url}` missing");
284-
}
285-
(Err(e), _, _) => {
286-
error!("failed to compute dependency digest for `{url}`: {e}");
287-
}
288-
}
289-
}
290316
let cache = if let Some(cache) = cache {
291317
match cache.get(&url).await {
292318
Err(e) => error!("failed to get `{url}` from cache: {e}"),

0 commit comments

Comments
 (0)