diff --git a/packages/std/toolchain/native/index.bri b/packages/std/toolchain/native/index.bri index 8053e0b..174c2dc 100644 --- a/packages/std/toolchain/native/index.bri +++ b/packages/std/toolchain/native/index.bri @@ -161,7 +161,9 @@ export const tools = std.memo(async (): Promise> => { MAGIC: { append: [{ path: "share/misc/magic.mgc" }] }, }); - return std.sync(tools); + tools = syncTarball(tools); + + return tools; }); /** @@ -312,7 +314,7 @@ export const toolchain = std.memo( toolchain = makePkgConfigPathsRelative(toolchain); - toolchain = std.sync(toolchain); + toolchain = syncTarball(toolchain); return toolchain; }, @@ -428,3 +430,36 @@ function makePkgConfigPathsRelative( }) .toDirectory(); } + +/** + * Sync a recipe by creating an archive of it, then unarchiving it. When + * fetched from the registry, the recipe will be downloaded as a single + * compressed tarball, which may be faster than syncing lots of individual + * files. + */ +function syncTarball( + recipe: std.AsyncRecipe, +): std.Recipe { + recipe = std.collectReferences(std.directory({ recipe })); + + const tarredRecipe = std + .process({ + command: "tar", + args: [ + "--zstd", + "-cf", + std.outputPath, + "--hard-dereference", + "-C", + recipe, + ".", + ], + dependencies: [tar(), zstd()], + }) + .toFile(); + + let untarredRecipe = tarredRecipe.unarchive("tar", "zstd"); + untarredRecipe = std.attachResources(untarredRecipe); + + return std.castToDirectory(untarredRecipe.get("recipe")); +}