aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGravatar Jarred Sumner <709451+Jarred-Sumner@users.noreply.github.com> 2023-01-25 17:25:19 -0800
committerGravatar Jarred Sumner <709451+Jarred-Sumner@users.noreply.github.com> 2023-01-25 17:25:19 -0800
commit0a8e42a4ba06fbe7a6b65086c6833731e6f6a78c (patch)
treed438a4eb76fff04948ebcb757bd02680cdd9f906
parentb767f9a99a2b4b6bd8f54cb851bda6a2696587ce (diff)
downloadbun-0a8e42a4ba06fbe7a6b65086c6833731e6f6a78c.tar.gz
bun-0a8e42a4ba06fbe7a6b65086c6833731e6f6a78c.tar.zst
bun-0a8e42a4ba06fbe7a6b65086c6833731e6f6a78c.zip
[bun install] For `github` dependencies, write a `.bun-tag` to mark the revision
-rw-r--r--src/install/extract_tarball.zig11
-rw-r--r--src/install/install.zig66
2 files changed, 77 insertions, 0 deletions
diff --git a/src/install/extract_tarball.zig b/src/install/extract_tarball.zig
index 46695e9bf..b1c1cbcec 100644
--- a/src/install/extract_tarball.zig
+++ b/src/install/extract_tarball.zig
@@ -234,6 +234,17 @@ fn extract(this: *const ExtractTarball, tgz_bytes: []const u8, task_id: u64) !In
true,
false,
);
+
+ // This tag is used to know which version of the package was
+ // installed from GitHub. package.json version becomes sort of
+ // meaningless in cases like this.
+ if (resolved.len > 0) insert_tag: {
+ const gh_tag = extract_destination.dir.createFileZ(".bun-tag", .{ .truncate = true }) catch break :insert_tag;
+ defer gh_tag.close();
+ gh_tag.writeAll(resolved) catch {
+ extract_destination.dir.deleteFileZ(".bun-tag") catch {};
+ };
+ }
},
else => {
_ = if (PackageManager.verbose_install)
diff --git a/src/install/install.zig b/src/install/install.zig
index e92557893..de82664c0 100644
--- a/src/install/install.zig
+++ b/src/install/install.zig
@@ -704,10 +704,76 @@ const PackageInstall = struct {
}
};
+ // 1. verify that .bun-tag exists (was it installed from bun?)
+ // 2. check .bun-tag against the resolved version
+ fn verifyGitHubResolution(this: *PackageInstall, resolution: *const Resolution, buf: []const u8) bool {
+ var allocator = this.allocator;
+
+ var total: usize = 0;
+ var read: usize = 0;
+
+ std.mem.copy(u8, this.destination_dir_subpath_buf[this.destination_dir_subpath.len..], std.fs.path.sep_str ++ ".bun-tag");
+ this.destination_dir_subpath_buf[this.destination_dir_subpath.len + std.fs.path.sep_str.len + ".bun-tag".len] = 0;
+ var bun_gh_tag_path: [:0]u8 = this.destination_dir_subpath_buf[0 .. this.destination_dir_subpath.len + std.fs.path.sep_str.len + ".bun-tag".len :0];
+ defer this.destination_dir_subpath_buf[this.destination_dir_subpath.len] = 0;
+ const gh_tag_file = this.destination_dir.dir.openFileZ(bun_gh_tag_path, .{ .mode = .read_only }) catch return false;
+ defer gh_tag_file.close();
+
+ var body_pool = Npm.Registry.BodyPool.get(allocator);
+ var mutable: MutableString = body_pool.data;
+ defer {
+ body_pool.data = mutable;
+ Npm.Registry.BodyPool.release(body_pool);
+ }
+
+ mutable.reset();
+
+ mutable.list.expandToCapacity();
+
+ // this file is pretty small
+ read = gh_tag_file.read(mutable.list.items[total..]) catch return false;
+ var remain = mutable.list.items[@min(total, read)..];
+ if (read > 0 and remain.len < 1024) {
+ mutable.growBy(4096) catch return false;
+ mutable.list.expandToCapacity();
+ }
+
+ // never read more than 2048 bytes. it should never be 2048 bytes.
+ while (read > 0 and total < 2048) : (read = gh_tag_file.read(remain) catch return false) {
+ total += read;
+
+ mutable.list.expandToCapacity();
+ remain = mutable.list.items[total..];
+
+ if (remain.len < 1024) {
+ mutable.growBy(4096) catch return false;
+ }
+ mutable.list.expandToCapacity();
+ remain = mutable.list.items[total..];
+ }
+
+ mutable.list.expandToCapacity();
+
+ return strings.eqlLong(resolution.value.github.resolved.slice(buf), mutable.list.items[0..total], true);
+ }
+
pub fn verify(
this: *PackageInstall,
+ resolution: *const Resolution,
+ buf: []const u8,
) bool {
+ if (resolution.tag == .github) {
+ return this.verifyGitHubResolution(resolution, buf);
+ }
+
+ return this.verifyPackageJSONNameAndVersion();
+ }
+
+ fn verifyPackageJSONNameAndVersion(this: *PackageInstall) bool {
var allocator = this.allocator;
+ var total: usize = 0;
+ var read: usize = 0;
+
std.mem.copy(u8, this.destination_dir_subpath_buf[this.destination_dir_subpath.len..], std.fs.path.sep_str ++ "package.json");
this.destination_dir_subpath_buf[this.destination_dir_subpath.len + std.fs.path.sep_str.len + "package.json".len] = 0;
var package_json_path: [:0]u8 = this.destination_dir_subpath_buf[0 .. this.destination_dir_subpath.len + std.fs.path.sep_str.len + "package.json".len :0];