diff options
Diffstat (limited to 'src/install/install.zig')
-rw-r--r-- | src/install/install.zig | 154 |
1 files changed, 88 insertions, 66 deletions
diff --git a/src/install/install.zig b/src/install/install.zig index 6ff76d421..ab3bb3eef 100644 --- a/src/install/install.zig +++ b/src/install/install.zig @@ -574,17 +574,16 @@ const Task = struct { } this.err = err; this.status = Status.fail; + this.data = .{ .package_manifest = .{} }; this.package_manager.resolve_tasks.writeItem(this.*) catch unreachable; return; }; - this.data = .{ .package_manifest = .{} }; - switch (package_manifest) { .cached => unreachable, .fresh => |manifest| { - this.data = .{ .package_manifest = manifest }; this.status = Status.success; + this.data = .{ .package_manifest = manifest }; this.package_manager.resolve_tasks.writeItem(this.*) catch unreachable; return; }, @@ -593,6 +592,7 @@ const Task = struct { this.request.package_manifest.name.slice(), }) catch unreachable; this.status = Status.fail; + this.data = .{ .package_manifest = .{} }; this.package_manager.resolve_tasks.writeItem(this.*) catch unreachable; return; }, @@ -6649,6 +6649,63 @@ pub const PackageManager = struct { } } } + + var scripts = this.lockfile.packages.items(.scripts)[package_id]; + if (scripts.hasAny()) { + var path_buf: [bun.MAX_PATH_BYTES]u8 = undefined; + const path_str = Path.joinAbsString( + bun.getFdPath(this.node_modules_folder.dir.fd, &path_buf) catch unreachable, + &[_]string{destination_dir_subpath}, + .posix, + ); + + scripts.enqueue(this.lockfile, buf, path_str); + } else if (!scripts.filled and switch (resolution.tag) { + .folder => Features.folder.scripts, + .npm => Features.npm.scripts, + .git, .github, .gitlab, .local_tarball, .remote_tarball => Features.tarball.scripts, + .symlink => Features.link.scripts, + .workspace => Features.workspace.scripts, + else => false, + }) { + var path_buf: [bun.MAX_PATH_BYTES]u8 = undefined; + const path_str = Path.joinAbsString( + bun.getFdPath(this.node_modules_folder.dir.fd, &path_buf) catch unreachable, + &[_]string{destination_dir_subpath}, + .posix, + ); + + scripts.enqueueFromPackageJSON( + this.manager.log, + this.lockfile, + this.node_modules_folder.dir, + destination_dir_subpath, + path_str, + ) catch |err| { + if (comptime log_level != .silent) { + const fmt = "\n<r><red>error:<r> failed to parse life-cycle scripts for <b>{s}<r>: {s}\n"; + const args = .{ name, @errorName(err) }; + + if (comptime log_level.showProgress()) { + if (Output.enable_ansi_colors) { + this.progress.log(comptime Output.prettyFmt(fmt, true), args); + } else { + this.progress.log(comptime Output.prettyFmt(fmt, false), args); + } + } else { + Output.prettyErrorln(fmt, args); + } + } + + if (this.manager.options.enable.fail_early) { + Global.exit(1); + } + + Output.flush(); + this.summary.fail += 1; + return; + }; + } }, .fail => |cause| { if (cause.isPackageMissingFromCache()) { @@ -7522,6 +7579,22 @@ pub const PackageManager = struct { } } + if (root.scripts.hasAny()) { + root.scripts.enqueue( + manager.lockfile, + manager.lockfile.buffers.string_bytes.items, + strings.withoutTrailingSlash(Fs.FileSystem.instance.top_level_dir), + ); + } + + var install_summary = PackageInstall.Summary{}; + if (manager.options.do.install_packages) { + install_summary = try manager.installPackages( + manager.lockfile, + log_level, + ); + } + // Install script order for npm 8.3.0: // 1. preinstall // 2. install @@ -7529,40 +7602,27 @@ pub const PackageManager = struct { // 4. preprepare // 5. prepare // 6. postprepare - const run_lifecycle_scripts = manager.options.do.run_scripts and manager.lockfile.scripts.hasAny() and manager.options.do.install_packages; - const has_pre_lifecycle_scripts = manager.lockfile.scripts.preinstall.items.len > 0; - const needs_configure_bundler_for_run = run_lifecycle_scripts and !has_pre_lifecycle_scripts; - - if (run_lifecycle_scripts and has_pre_lifecycle_scripts) { + if (run_lifecycle_scripts) { // We need to figure out the PATH and other environment variables // to do that, we re-use the code from bun run // this is expensive, it traverses the entire directory tree going up to the root // so we really only want to do it when strictly necessary - { - var this_bundler: bundler.Bundler = undefined; - var ORIGINAL_PATH: string = ""; - _ = try RunCommand.configureEnvForRun( - ctx, - &this_bundler, - manager.env, - &ORIGINAL_PATH, - log_level != .silent, - false, - ); - } + var this_bundler: bundler.Bundler = undefined; + var ORIGINAL_PATH: string = ""; + _ = try RunCommand.configureEnvForRun( + ctx, + &this_bundler, + manager.env, + &ORIGINAL_PATH, + log_level != .silent, + false, + ); + // 1. preinstall try manager.lockfile.scripts.run(manager.allocator, manager.env, log_level != .silent, "preinstall"); } - var install_summary = PackageInstall.Summary{}; - if (manager.options.do.install_packages) { - install_summary = try manager.installPackages( - manager.lockfile, - log_level, - ); - } - if (needs_new_lockfile) { manager.summary.add = @truncate(u32, manager.lockfile.packages.len); } @@ -7666,44 +7726,6 @@ pub const PackageManager = struct { } if (run_lifecycle_scripts and install_summary.fail == 0) { - // We need to figure out the PATH and other environment variables - // to do that, we re-use the code from bun run - // this is expensive, it traverses the entire directory tree going up to the root - // so we really only want to do it when strictly necessary - if (needs_configure_bundler_for_run) { - var this_bundler: bundler.Bundler = undefined; - var ORIGINAL_PATH: string = ""; - _ = try RunCommand.configureEnvForRun( - ctx, - &this_bundler, - manager.env, - &ORIGINAL_PATH, - log_level != .silent, - false, - ); - } else { - // bun install may have installed new bins, so we need to update the PATH - // this can happen if node_modules/.bin didn't previously exist - // note: it is harmless to have the same directory in the PATH multiple times - const current_path = manager.env.map.get("PATH") orelse ""; - - // TODO: windows - const cwd_without_trailing_slash = if (Fs.FileSystem.instance.top_level_dir.len > 1 and Fs.FileSystem.instance.top_level_dir[Fs.FileSystem.instance.top_level_dir.len - 1] == '/') - Fs.FileSystem.instance.top_level_dir[0 .. Fs.FileSystem.instance.top_level_dir.len - 1] - else - Fs.FileSystem.instance.top_level_dir; - - try manager.env.map.put("PATH", try std.fmt.allocPrint( - ctx.allocator, - "{s}:{s}/node_modules/.bin", - .{ - current_path, - cwd_without_trailing_slash, - }, - )); - } - - // 1. preinstall // 2. install // 3. postinstall try manager.lockfile.scripts.run(manager.allocator, manager.env, log_level != .silent, "install"); |