From 07db922aad3b043a0b1826019e356b9e09c8d27b Mon Sep 17 00:00:00 2001 From: Colin McDonnell Date: Tue, 10 Oct 2023 00:07:41 -0700 Subject: WIP --- src/cli.zig | 422 ++++++++++++++++-------------------- src/cli/bunx_command.zig | 18 +- src/cli/package_manager_command.zig | 40 ++-- src/deps/zig-clap/clap.zig | 72 +----- src/install/install.zig | 148 ++++++++++++- 5 files changed, 353 insertions(+), 347 deletions(-) diff --git a/src/cli.zig b/src/cli.zig index 5ec2146ea..807d8568f 100644 --- a/src/cli.zig +++ b/src/cli.zig @@ -55,46 +55,7 @@ pub const Cli = struct { MainPanicHandler.Singleton = &panicker; Command.start(allocator, log) catch |err| { switch (err) { - // error.MissingEntryPoint => { - // Output.prettyErrorln("bun build v" ++ Global.package_json_version_with_sha ++ "", .{}); - // Output.prettyErrorln( - // \\error: Missing entrypoints. What would you like to bundle? - // \\ - // \\Usage: bun build [flags] [...entrypoints] - // \\ - // \\Common Flags: - // \\ --outfile Write the output to a specific file (default: stdout) - // \\ --outdir Write the output to a directory (required for splitting) - // \\ --minify Enable all minification flags - // \\ --minify-whitespace Remove unneeded whitespace - // \\ --minify-syntax Transform code to use less syntax - // \\ --minify-identifiers Shorten variable names - // \\ --sourcemap Generate sourcemaps - // \\ none | inline | external - // \\ --target The intended execution environment for the bundle. - // \\ browser | bun | node - // \\ --splitting Enable code splitting (requires --outdir) - // \\ --watch Run bundler in watch mode - // \\ - // \\Examples: - // \\ Frontend web apps: - // \\ bun build ./src/index.ts --outfile=bundle.js - // \\ bun build --minify --splitting --outdir=out ./index.jsx ./lib/worker.ts - // \\ - // \\ Bundle code to be run in Bun (reduces server startup time) - // \\ bun build --target=bun ./server.ts --outfile=server.js - // \\ - // \\ Creating a standalone executable (see https://bun.sh/docs/bundler/executables) - // \\ bun build --compile ./cli.ts --outfile=my-app - // \\ - // \\A full list of flags is available at https://bun.sh/docs/bundler - // \\ - // , .{}); - // Global.exit(1); - // }, else => { - // Always dump the logs - // std.debug.print("dump logs", .{}); if (Output.enable_ansi_colors_stderr) { log.printForLogLevelWithEnableAnsiColors(Output.errorWriter(), true) catch {}; } else { @@ -167,16 +128,15 @@ pub const Arguments = struct { const base_params_ = [_]ParamType{ clap.parseParam("-h, --help Display this menu and exit") catch unreachable, - // clap.parseParam("--all") catch unreachable, clap.parseParam("--cwd Absolute path to resolve files & entry points from. This just changes the process' cwd.") catch unreachable, - clap.parseParam("-c, --config ? Config file to load Bun from (e.g. -c bunfig.toml") catch unreachable, + clap.parseParam("-c, --config ? Specify path to Bun config file. Default $cwd/bunfig.toml") catch unreachable, clap.parseParam("...") catch unreachable, }; const transpiler_params_ = [_]ParamType{ clap.parseParam("--main-fields ... Main fields to lookup in package.json. Defaults to --target dependent") catch unreachable, clap.parseParam("--extension-order ... Defaults to: .tsx,.ts,.jsx,.js,.json ") catch unreachable, - clap.parseParam("--tsconfig-override Load tsconfig from path instead of cwd/tsconfig.json") catch unreachable, + clap.parseParam("--tsconfig-override Specify custom tsconfig.json. Default $cwd/tsconfig.json") catch unreachable, clap.parseParam("-d, --define ... Substitute K:V while parsing, e.g. --define process.env.NODE_ENV:\"development\". Values are parsed as JSON.") catch unreachable, clap.parseParam("-e, --external ... Exclude module from transpilation (can use * wildcards). ex: -e react") catch unreachable, clap.parseParam("-l, --loader ... Parse files with .ext:loader, e.g. --loader .js:jsx. Valid loaders: js, jsx, ts, tsx, json, toml, text, file, wasm, napi") catch unreachable, @@ -187,26 +147,13 @@ pub const Arguments = struct { clap.parseParam("--jsx-runtime \"automatic\" (default) or \"classic\"") catch unreachable, }; const runtime_params_ = [_]ParamType{ - // clap.parseParam("--cwd Absolute path to resolve files & entry points from. This just changes the process' cwd.") catch unreachable, - // clap.parseParam("-c, --config ? Config file to load Bun from (e.g. -c bunfig.toml") catch unreachable, - clap.parseParam("-r, --preload ... Import a module before other modules are loaded") catch unreachable, clap.parseParam("--hot Enable auto reload in the Bun runtime, test runner, or bundler") catch unreachable, clap.parseParam("--watch Automatically restart the process on file change") catch unreachable, - // clap.parseParam("--main-fields ... Main fields to lookup in package.json. Defaults to --target dependent") catch unreachable, - // clap.parseParam("--no-summary Don't print a summary (when generating .bun)") catch unreachable, - - // clap.parseParam("-u, --origin Rewrite import URLs to start with --origin. Default: \"\"") catch unreachable, - // clap.parseParam("-p, --port Port to serve Bun's dev server on. Default: \"3000\"") catch unreachable, clap.parseParam("--smol Use less memory, but run garbage collection more often") catch unreachable, - // clap.parseParam("--minify Minify (experimental)") catch unreachable, - // clap.parseParam("--minify-syntax Minify syntax and inline data (experimental)") catch unreachable, - // clap.parseParam("--minify-whitespace Minify whitespace (experimental)") catch unreachable, - // clap.parseParam("--minify-identifiers Minify identifiers") catch unreachable, - - clap.parseParam("--inspect ? Activate Bun's Debugger") catch unreachable, - clap.parseParam("--inspect-wait ? Activate Bun's Debugger, wait for a connection before executing") catch unreachable, - clap.parseParam("--inspect-brk ? Activate Bun's Debugger, set breakpoint on first line of code and wait") catch unreachable, + clap.parseParam("--inspect ? Activate Bun's debugger") catch unreachable, + clap.parseParam("--inspect-wait ? Activate Bun's debugger, wait for a connection before executing") catch unreachable, + clap.parseParam("--inspect-brk ? Activate Bun's debugger, set breakpoint on first line of code and wait") catch unreachable, clap.parseParam("--if-present Exit if the entrypoint does not exist") catch unreachable, clap.parseParam("--no-install Disable auto install in the Bun runtime") catch unreachable, clap.parseParam("-i Automatically install dependencies and use global cache in Bun's runtime, equivalent to --install=fallback") catch unreachable, @@ -215,15 +162,7 @@ pub const Arguments = struct { clap.parseParam("--prefer-latest Use the latest matching versions of packages in the Bun runtime, always checking npm") catch unreachable, }; - // const runtime_params = [_]ParamType{ - // clap.parseParam("--silent Don't repeat the command for bun run") catch unreachable, - // }; - // const positional_params_ = [_]ParamType{ - // clap.parseParam("...") catch unreachable, - // }; - const auto_only_params = [_]ParamType{ - // clap.parseParam("-h, --help Display this menu and exit") catch unreachable, clap.parseParam("--all") catch unreachable, clap.parseParam("-v, --version Print version and exit") catch unreachable, clap.parseParam("--revision Print version with revision and exit") catch unreachable, @@ -238,6 +177,11 @@ pub const Arguments = struct { }; const run_params = run_only_params ++ runtime_params_ ++ transpiler_params_ ++ base_params_; + const bunx_commands = [_]ParamType{ + clap.parseParam("--silent Don't repeat the command for bun run") catch unreachable, + clap.parseParam("-b, --bun Force a script or package to use Bun's runtime instead of Node.js (via symlinking node)") catch unreachable, + }; + // these commands don't use clap // Command.Tag.BunxCommand // Command.Tag.InitCommand @@ -419,10 +363,8 @@ pub const Arguments = struct { } pub fn parse(allocator: std.mem.Allocator, ctx: *Command.Context, comptime cmd: Command.Tag) !Api.TransformOptions { - std.debug.print("starting parse\n", .{}); var diag = clap.Diagnostic{}; const params_to_parse = comptime cmd.params(); - const params_to_print = comptime cmd.params_to_print(); var args = clap.parse(clap.Help, params_to_parse, .{ .diagnostic = &diag, @@ -432,25 +374,17 @@ pub const Arguments = struct { else 0, }) catch |err| { - std.debug.print("error caught\n", .{}); // Report useful error and exit clap.help(Output.errorWriter(), params_to_parse) catch {}; Output.errorWriter().writeAll("\n") catch {}; diag.report(Output.errorWriter(), err) catch {}; - std.debug.print("done printing\n", .{}); Global.exit(1); }; - std.debug.print("past parsing\n", .{}); - // const print_all_help = args.flag("--all"); const print_help = args.flag("--help"); if (print_help) { - std.debug.print("printing help\n", .{}); - cmd.print_helptext(params_to_print); - // clap.help(Output.writer(), params_to_parse[0..params_to_parse.len]) catch {}; - // Output.prettyln("\n-------\n\n", .{}); + cmd.printHelp(); Output.flush(); - // HelpCommand.printWithReason(.explicit); Global.exit(0); } @@ -581,6 +515,7 @@ pub const Arguments = struct { // if (args.option("--port")) |port_str| { // opts.port = std.fmt.parseInt(u16, port_str, 10) catch return error.InvalidPort; // } + opts.serve = false; // TODO opts.main_fields = args.options("--main-fields"); // we never actually supported inject. @@ -592,7 +527,6 @@ pub const Arguments = struct { // opts.no_summary = args.flag("--no-summary"); if (cmd == .AutoCommand or cmd == .RunCommand or cmd == .TestCommand) { - std.debug.print("auto/run/test\n", .{}); const preloads = args.options("--preload"); if (args.flag("--hot")) { @@ -858,15 +792,11 @@ pub const Arguments = struct { if (cmd == .BuildCommand) { if (opts.entry_points.len == 0 and opts.framework == null) { Output.prettyErrorln("bun build v" ++ Global.package_json_version_with_sha ++ "", .{}); - // Output.flush(); - // cmd.print_helptext(); - // Output.pretty("\n-------------\n", .{}); Output.prettyError("error: Missing entrypoints. What would you like to bundle?\n\n", .{}); Output.flush(); - Output.pretty("Usage:\n $ bun build \\ [...\\] [flags] \n", .{}); + Output.pretty("Usage:\n $ bun build \\ [...\\] [flags] \n", .{}); Output.pretty("\nTo see full documentation:\n $ bun build --help\n", .{}); Output.flush(); - // return error.MissingEntryPoint; Global.exit(1); } } @@ -979,6 +909,7 @@ pub const HelpCommand = struct { \\ \\ upgrade Get the latest version of Bun \\ bun --help Show all supported flags and commands + \\ bun [command] --help Print helptext for a specific command \\ \\ Learn more about Bun: https://bun.sh/docs \\ Join our Discord community: https://bun.sh/discord @@ -1148,11 +1079,8 @@ pub const Command = struct { ctx.allocator = allocator; if (comptime Command.Tag.uses_global_options.get(command)) { - std.debug.print("arguments.parse\n", .{}); ctx.args = try Arguments.parse(allocator, &ctx, command); - } else { - std.debug.print("doesnt use global options\n", .{}); - } + } else {} return ctx; } }; @@ -1358,12 +1286,11 @@ pub const Command = struct { switch (tag) { .DiscordCommand => return try DiscordCommand.exec(allocator), .HelpCommand => return try HelpCommand.exec(allocator), - .InitCommand => return try InitCommand.exec(allocator, bun.argv()), .ReservedCommand => return try ReservedCommand.exec(allocator), + .InitCommand => return try InitCommand.exec(allocator, bun.argv()), .BuildCommand => { if (comptime bun.fast_debug_build_mode and bun.fast_debug_build_cmd != .BuildCommand) unreachable; const ctx = try Command.Context.create(allocator, log, .BuildCommand); - try BuildCommand.exec(ctx); }, .InstallCompletionsCommand => { @@ -1547,18 +1474,24 @@ pub const Command = struct { var args = try std.process.argsAlloc(allocator); if (args.len <= 2) { - Output.prettyErrorln( - \\bun create: create a new project from a template - \\ - \\Usage: bun create [template] [...args] - \\ bun create [username/repo] [name] - \\ - \\If given a GitHub repository name, Bun will download it and use it as a template, - \\otherwise it will run bunx create-[template] with the given arguments. - \\ - \\Learn more about creating new projects: https://bun.sh/docs/templates - \\ - , .{}); + Command.Tag.printHelp(.CreateCommand); + Global.exit(1); + return; + } + + // iterate over args + // if --help, print help and exit + const print_help = brk: { + for (bun.argv()) |arg_| { + const arg = bun.span(arg_); + if (strings.eqlComptime(arg, "--help")) { + break :brk true; + } + } + break :brk false; + }; + if (print_help) { + Command.Tag.printHelp(.CreateCommand); Global.exit(1); return; } @@ -1595,11 +1528,11 @@ pub const Command = struct { \\ \\To create a project using Create React App, run \\ - \\ bun create react-app + \\ bun create react-app \\ \\To create a React project using Vite, run \\ - \\ bun create vite + \\ bun create vite \\ \\Then select "React" from the list of frameworks. \\ @@ -1644,13 +1577,10 @@ pub const Command = struct { return; }, .AutoCommand => { - std.debug.print("running autocommand\n", .{}); if (comptime bun.fast_debug_build_mode and bun.fast_debug_build_cmd != .AutoCommand) unreachable; var ctx = Command.Context.create(allocator, log, .AutoCommand) catch |e| { - std.debug.print("error in context.create()\n", .{}); switch (e) { error.MissingEntryPoint => { - std.debug.print("missing entry point\n", .{}); HelpCommand.execWithReason(allocator, .explicit); return; }, @@ -1759,7 +1689,7 @@ pub const Command = struct { } // Output.prettyWarnln("warn: failed to parse command\n", .{}); - // std.debug.print("fallback to help\n", .{}); + // Output.flush(); try HelpCommand.exec(allocator); }, @@ -1864,68 +1794,135 @@ pub const Command = struct { pub fn params(comptime cmd: Tag) []const Arguments.ParamType { return &comptime switch (cmd) { - Command.Tag.AutoCommand => Arguments.auto_params, - Command.Tag.RunCommand => Arguments.run_params, - Command.Tag.BuildCommand => Arguments.build_params, - Command.Tag.TestCommand => Arguments.test_params, - Command.Tag.BunxCommand => Arguments.run_params, + .AutoCommand => Arguments.auto_params, + .RunCommand => Arguments.run_params, + .BuildCommand => Arguments.build_params, + .TestCommand => Arguments.test_params, + .BunxCommand => Arguments.run_params, else => Arguments.base_params_ ++ Arguments.runtime_params_ ++ Arguments.transpiler_params_, }; } - pub fn params_to_print(comptime cmd: Tag) []const Arguments.ParamType { - return &comptime switch (cmd) { - Command.Tag.BuildCommand => Arguments.build_only_params, - Command.Tag.TestCommand => Arguments.test_only_params, - Command.Tag.InstallCommand => Install.PackageManager.install_params, - Command.Tag.AddCommand => Install.PackageManager.add_params, - Command.Tag.UpdateCommand => Install.PackageManager.update_params, - Command.Tag.RemoveCommand => Install.PackageManager.remove_params, - Command.Tag.LinkCommand => Install.PackageManager.link_params, - Command.Tag.UnlinkCommand => Install.PackageManager.unlink_params, - Command.Tag.AutoCommand => Arguments.auto_params, - Command.Tag.RunCommand => Arguments.run_params, - Command.Tag.BunxCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, - Command.Tag.InitCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, - Command.Tag.CreateCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, - Command.Tag.DiscordCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, - Command.Tag.GetCompletionsCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, - Command.Tag.HelpCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, - Command.Tag.InstallCompletionsCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, - Command.Tag.PackageManagerCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, - Command.Tag.UpgradeCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, - Command.Tag.ReplCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, - Command.Tag.ReservedCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, - }; - } - - // fn print_helptext_(intro: []u8, outro: []u8, params_list: []const Arguments.ParamType) void { - // Output.pretty("\n{s}", .{intro}); - // Output.flush(); - // Output.pretty("\nFlags:", .{}); - // Output.flush(); - // clap.simpleHelp(params_list); - // Output.pretty("\n\n{s}", .{outro}); - // Output.flush(); + // pub fn params_to_print(comptime cmd: Tag) []const Arguments.ParamType { + // return &comptime switch (cmd) { + // .BuildCommand => Arguments.build_only_params, + // .TestCommand => Arguments.test_only_params, + // .InstallCommand => Install.PackageManager.install_params, + // .AddCommand => Install.PackageManager.add_params, + // .UpdateCommand => Install.PackageManager.update_params, + // .RemoveCommand => Install.PackageManager.remove_params, + // .LinkCommand => Install.PackageManager.link_params, + // .UnlinkCommand => Install.PackageManager.unlink_params, + // .AutoCommand => Arguments.auto_params, + // .RunCommand => Arguments.run_params, + // .BunxCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, + // .InitCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, + // .CreateCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, + // .DiscordCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, + // .GetCompletionsCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, + // .HelpCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, + // .InstallCompletionsCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, + // .PackageManagerCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, + // .UpgradeCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, + // .ReplCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, + // .ReservedCommand => Arguments.runtime_params_ ++ Arguments.transpiler_params_, + // }; // } - pub fn print_helptext(cmd: Tag, params_list: []const Arguments.ParamType) void { + pub fn printHelp(comptime cmd: Tag) void { + // const params_list = comptime cmd.params_to_print(); switch (cmd) { + + // these commands do not use Context + // .DiscordCommand => return try DiscordCommand.exec(allocator), + // .HelpCommand => return try HelpCommand.exec(allocator), + // .ReservedCommand => return try ReservedCommand.exec(allocator), + + // these commands are implemented in install.zig + // Command.Tag.InstallCommand => {}, + // Command.Tag.AddCommand => {}, + // Command.Tag.RemoveCommand => {}, + // Command.Tag.UpdateCommand => {}, + // Command.Tag.PackageManagerCommand => {}, + // Command.Tag.LinkCommand => {}, + // Command.Tag.UnlinkCommand => {}, + + // fall back to HelpCommand.printWithReason Command.Tag.AutoCommand => { - Output.pretty("asdf", .{}); - Output.flush(); + HelpCommand.printWithReason(.explicit); }, Command.Tag.RunCommand => { - Output.pretty("asdf", .{}); + const intro_text = + \\Usage: + \\ Run a file or package.json script. + \\ bun run [flags] \ + \\ bun run [flags] \ + ; + + const outro_text = + \\Examples: + \\ Run a JavaScript or TypeScript file + \\ bun run ./index.js + \\ bun run ./index.tsx + \\ + \\ Run a package.json script + \\ bun run dev + \\ bun run lint + \\ + \\Full documentation is available at https://bun.sh/docs/cli/run + ; + + Output.pretty(intro_text ++ "\n\n", .{}); + Output.flush(); + Output.pretty("Flags:", .{}); + Output.flush(); + clap.simpleHelp(&Arguments.run_params); + Output.pretty("\n\n" ++ outro_text, .{}); Output.flush(); }, - Command.Tag.BunxCommand => { - Output.pretty("asdf", .{}); + + .InitCommand => { + const intro_text = + \\Usage: bun build [flags] [...entrypoints] + \\ Initialize a Bun project in the current directory. + \\ Creates a package.json, tsconfig.json, and bunfig.toml if they don't exist. + \\ + \\Flags: + \\ -y, --yes Accept all default options + \\ --minify Enable all minification flags + \\ + \\Examples: + \\ bun init + \\ bun init --yes ./src/index.ts --outfile=bundle.js + \\ + ; + + Output.pretty(intro_text, .{}); Output.flush(); }, + + Command.Tag.BunxCommand => { + Output.prettyErrorln( + \\usage: bunx [--bun] package[@version] [...flags or arguments to pass through] + \\ + \\bunx runs an npm package executable, automatically installing into a global shared cache if not installed in node_modules. + \\ + \\example: + \\ + \\ bunx bun-repl + \\ bunx prettier foo.js + \\ + \\The --bun flag forces the package to run in Bun's JavaScript runtime, even when it tries to use Node.js. + \\ + \\ bunx --bun tsc --version + \\ + , .{}); + }, Command.Tag.BuildCommand => { const intro_text = - \\Usage: bun build [flags] [...entrypoints] + \\Usage: + \\ Transpile and bundle one more more files. + \\ bun build [flags] [...entrypoints] ; const outro_text = @@ -1944,19 +1941,17 @@ pub const Command = struct { \\ ; - Output.pretty(intro_text, .{}); - Output.pretty("\n\n", .{}); + Output.pretty(intro_text ++ "\n\n", .{}); Output.flush(); Output.pretty("Flags:", .{}); Output.flush(); - clap.simpleHelp(params_list); - Output.pretty("\n\n", .{}); - Output.pretty(outro_text, .{}); + clap.simpleHelp(&Arguments.build_only_params); + Output.pretty("\n\n" ++ outro_text, .{}); Output.flush(); }, Command.Tag.TestCommand => { const intro_text = - \\Usage: bun test [flags] [patterns...] + \\Usage: bun test [flags] [patterns...] \\ Run all matching test files and print the results to stdout ; const outro_text = @@ -1977,118 +1972,69 @@ pub const Command = struct { Output.flush(); Output.pretty("\nFlags:", .{}); Output.flush(); - clap.simpleHelp(params_list); + clap.simpleHelp(&Arguments.test_only_params); Output.pretty("\n\n", .{}); Output.pretty(outro_text, .{}); Output.flush(); }, - Command.Tag.InitCommand => { - const intro_text = - \\Usage: bun init [flags] - \\ Run all matching test files and print the results to stdout - ; - const outro_text = - \\Examples: - \\ Run all test files - \\ bun test + Command.Tag.CreateCommand => { + Output.prettyErrorln( + \\bun create: create a new project from a template \\ - \\ Run all test files with "foo" or "bar" in the file name - \\ bun test foo bar + \\Usage: bun create [template] [...args] + \\ bun create [username/repo] [name] \\ - \\ Run all test files, only including tests whose names includes "baz" - \\ bun test --test-name-pattern baz + \\If given a GitHub repository name, Bun will download it and use it as a template, + \\otherwise it will run bunx create-[template] with the given arguments. \\ - \\Full documentation is available at https://bun.sh/docs/cli/test - ; - Output.pretty("\n", .{}); - Output.pretty(intro_text, .{}); - Output.flush(); - Output.pretty("\nFlags:", .{}); - Output.flush(); - clap.simpleHelp(params_list); - Output.pretty("\n\n", .{}); - Output.pretty(outro_text, .{}); - Output.flush(); - }, - Command.Tag.CreateCommand => { - Output.pretty("asdf", .{}); - Output.flush(); + \\Learn more about creating new projects: https://bun.sh/docs/templates + \\ + , .{}); }, Command.Tag.HelpCommand => { - Output.pretty("asdf", .{}); - Output.flush(); + HelpCommand.printWithReason(.explicit); }, Command.Tag.UpgradeCommand => { - Output.pretty("asdf", .{}); - Output.flush(); - }, - Command.Tag.ReplCommand => { - Output.pretty("asdf", .{}); - Output.flush(); - }, - Command.Tag.InstallCommand => { - Output.pretty("asdf", .{}); - Output.flush(); - }, - Command.Tag.AddCommand => { const intro_text = - \\Usage: bun add [flags] \ [...\] - \\ Install a package and add it to your package.json + \\Usage: bun upgrade [flags] + \\ Upgrade Bun ; const outro_text = \\Examples: - \\ Add a dependency from the npm registry - \\ bun add zod - \\ bun add zod@next - \\ bun add zod@3.0.0 + \\ Instal the latest stable version + \\ bun upgrade \\ - \\ Add a dev, optional, or peer dependency - \\ bun add -d typescript - \\ bun add -o lodash - \\ bun add --peer esbuild + \\ Install the most recent canary version of Bun + \\ bun upgrade --canary \\ - \\Full documentation is available at https://bun.sh/docs/cli/install + \\Full documentation is available at https://bun.sh/docs/installation#upgrading ; Output.pretty("\n", .{}); Output.pretty(intro_text, .{}); Output.flush(); Output.pretty("\nFlags:", .{}); Output.flush(); - clap.simpleHelp(params_list); + clap.simpleHelp(&Arguments.test_only_params); Output.pretty("\n\n", .{}); Output.pretty(outro_text, .{}); Output.flush(); }, - Command.Tag.RemoveCommand => { - Output.pretty("asdf", .{}); - Output.flush(); - }, - Command.Tag.UpdateCommand => { - Output.pretty("asdf", .{}); - Output.flush(); - }, - Command.Tag.LinkCommand => { - Output.pretty("asdf", .{}); - Output.flush(); - }, - Command.Tag.UnlinkCommand => { - Output.pretty("asdf", .{}); - Output.flush(); - }, - Command.Tag.PackageManagerCommand => { - Output.pretty("asdf", .{}); - Output.flush(); - }, - Command.Tag.DiscordCommand => { - Output.pretty("asdf", .{}); + Command.Tag.ReplCommand => { + const intro_text = + \\Usage: bun repl [flags] + \\ Open a Bun REPL + ; + + Output.pretty(intro_text, .{}); Output.flush(); }, + Command.Tag.GetCompletionsCommand => { - Output.pretty("asdf", .{}); + Output.pretty("Usage: bun getcompletes", .{}); Output.flush(); }, Command.Tag.InstallCompletionsCommand => { - Output.pretty("asdf", .{}); + Output.pretty("Usage: bun completions", .{}); Output.flush(); }, else => { diff --git a/src/cli/bunx_command.zig b/src/cli/bunx_command.zig index e7f35d10d..84155b502 100644 --- a/src/cli/bunx_command.zig +++ b/src/cli/bunx_command.zig @@ -9,7 +9,7 @@ const stringZ = bun.stringZ; const default_allocator = bun.default_allocator; const C = bun.C; const std = @import("std"); - +const Command = @import("../cli.zig").Command; const Run = @import("./run_command.zig").RunCommand; pub const BunxCommand = struct { @@ -142,21 +142,7 @@ pub const BunxCommand = struct { } fn exit_with_usage() noreturn { - Output.prettyErrorln( - \\usage: bunx [--bun] package[@version] [...flags or arguments to pass through] - \\ - \\bunx runs an npm package executable, automatically installing into a global shared cache if not installed in node_modules. - \\ - \\example: - \\ - \\ bunx bun-repl - \\ bunx prettier foo.js - \\ - \\The --bun flag forces the package to run in Bun's JavaScript runtime, even when it tries to use Node.js. - \\ - \\ bunx --bun tsc --version - \\ - , .{}); + Command.Tag.printHelp(.BunxCommand); Global.exit(1); } diff --git a/src/cli/package_manager_command.zig b/src/cli/package_manager_command.zig index 00326bc97..f51504a03 100644 --- a/src/cli/package_manager_command.zig +++ b/src/cli/package_manager_command.zig @@ -44,7 +44,7 @@ const ByName = struct { }; pub const PackageManagerCommand = struct { - pub fn printHelp(_: std.mem.Allocator) void {} + // pub fn printHelp(_: std.mem.Allocator) void {} pub fn printHash(ctx: Command.Context, lockfile_: []const u8) !void { @setCold(true); var lockfile_buffer: [bun.MAX_PATH_BYTES]u8 = undefined; @@ -83,6 +83,26 @@ pub const PackageManagerCommand = struct { return subcommand; } + pub fn printHelp() void { + Output.prettyln( + \\bun pm: Package manager utilities + \\ + \\ bun pm bin print the path to bin folder + \\ bun pm -g bin print the global path to bin folder + \\ bun pm ls list the dependency tree according to the current lockfile + \\ bun pm ls --all list the entire dependency tree according to the current lockfile + \\ bun pm hash generate & print the hash of the current lockfile + \\ bun pm hash-string print the string used to hash the lockfile + \\ bun pm hash-print print the hash stored in the current lockfile + \\ bun pm cache print the path to the cache folder + \\ bun pm cache rm clear the cache + \\ bun pm migrate migrate another package manager's lockfile without installing anything + \\ + \\Learn more about these at https://bun.sh/docs/install/utilities + \\ + , .{}); + } + pub fn exec(ctx: Command.Context) !void { var args = try std.process.argsAlloc(ctx.allocator); args = args[1..]; @@ -272,23 +292,7 @@ pub const PackageManagerCommand = struct { Global.exit(0); } - Output.prettyln( - \\bun pm: package manager related commands - \\ - \\ bun pm bin print the path to bin folder - \\ bun pm -g bin print the global path to bin folder - \\ bun pm ls list the dependency tree according to the current lockfile - \\ bun pm ls --all list the entire dependency tree according to the current lockfile - \\ bun pm hash generate & print the hash of the current lockfile - \\ bun pm hash-string print the string used to hash the lockfile - \\ bun pm hash-print print the hash stored in the current lockfile - \\ bun pm cache print the path to the cache folder - \\ bun pm cache rm clear the cache - \\ bun pm migrate migrate another package manager's lockfile without installing anything - \\ - \\Learn more about these at https://bun.sh/docs/install/utilities - \\ - , .{}); + printHelp(); if (subcommand.len > 0) { Output.prettyErrorln("\nerror: \"{s}\" unknown command\n", .{subcommand}); diff --git a/src/deps/zig-clap/clap.zig b/src/deps/zig-clap/clap.zig index bba58d445..3dd9d5a53 100644 --- a/src/deps/zig-clap/clap.zig +++ b/src/deps/zig-clap/clap.zig @@ -210,7 +210,6 @@ pub const Diagnostic = struct { /// Default diagnostics reporter when all you want is English with no colors. /// Use this as a reference for implementing your own if needed. pub fn report(diag: Diagnostic, stream: anytype, err: anyerror) !void { - std.debug.print("starting diag report", .{}); const Arg = struct { prefix: []const u8, name: []const u8, @@ -222,7 +221,6 @@ pub const Diagnostic = struct { else Arg{ .prefix = "", .name = diag.arg }; - std.debug.print("switching in diag.report", .{}); Output.pretty("Invalid argument '{s}{s}'\n", .{ a.prefix, a.name }); Output.pretty("{}", .{err}); Output.flush(); @@ -440,12 +438,7 @@ pub fn helpEx( ); } -pub fn simplePrintParam( - param: Param(Help), - // comptime Error: type, - // context: anytype, - // valueText: fn (@TypeOf(context), Param(Id)) Error![]const u8, -) !void { +pub fn simplePrintParam(param: Param(Help)) !void { Output.pretty("\n", .{}); if (param.names.short) |s| { Output.pretty("-{c}", .{s}); @@ -470,53 +463,12 @@ pub fn simplePrintParam( // } } pub fn simpleHelp( - // stream: anytype, params: []const Param(Help), - // helpText: *const fn (Param(Help)) []const u8, - // valueText: *const fn (Param(Help)) []const u8, ) void { - // _ = stream; - // const Context = struct { - // helpText: *const fn (Param(Help)) []const u8, - // valueText: *const fn (Param(Help)) []const u8, - - // pub fn help(c: @This(), p: Param(Id)) error{}![]const u8 { - // return c.helpText(p); - // } - - // pub fn value(c: @This(), p: Param(Id)) error{}![]const u8 { - // return c.valueText(p); - // } - // }; - - // return helpFull( - // stream, - // Id, - // params, - // error{}, - // Context{ - // .helpText = helpText, - // .valueText = valueText, - // }, - // Context.help, - // Context.value, - // ); - const max_spacing = blk: { var res: usize = 2; for (params) |param| { - // param.names.long.?.len orelse 0; - // var flags_len = brk: { - // if (param.names.long) |l| { - // break :brk l.len; - // } - // break :brk 0; - // }; var flags_len = if (param.names.long) |l| l.len else 0; - // if(param.names.short) flags_len += 4; - // var cs = io.countingWriter(io.null_writer); - // var flag_text = getValueSimple(param); - // try printParam(cs.writer(), Help, param, error{}, context, valueText); if (res < flags_len) res = flags_len; } @@ -528,15 +480,12 @@ pub fn simpleHelp( if (param.names.short == null and param.names.long == null) continue; + const desc_text = getHelpSimple(param); + if (desc_text.len == 0) continue; + // create a string with spaces_len spaces const default_allocator = @import("root").bun.default_allocator; - // var spaces_before = default_allocator.alloc(u8, num_spaces_after) catch unreachable; - // defer default_allocator.free(spaces_before); - // for (0..spaces_before) |i| { - // spaces_before[i] = ' '; - // } - const flags_len = if (param.names.long) |l| l.len else 0; const num_spaces_after = max_spacing - flags_len; var spaces_after = default_allocator.alloc(u8, num_spaces_after) catch unreachable; @@ -546,18 +495,7 @@ pub fn simpleHelp( } simplePrintParam(param) catch unreachable; - Output.pretty(" ", .{}); - const desc_text = getHelpSimple(param); - Output.pretty("{s} {s}", .{ spaces_after, desc_text }); - // print space spaces_len times - - // if (help_text.len > 0) { - // var cs = io.countingWriter(stream); - // try stream.print("\t", .{}); - // try printParam(cs.writer(), Help, param, error{}, context, valueText); - // try stream.writeByteNTimes(' ', max_spacing - @as(usize, @intCast(cs.bytes_written))); - // try stream.print("\t{s}\n", .{getHelpSimple(param)}); - // } + Output.pretty(" {s} {s}", .{ spaces_after, desc_text }); } } diff --git a/src/install/install.zig b/src/install/install.zig index 9b2dc4502..73e471ec5 100644 --- a/src/install/install.zig +++ b/src/install/install.zig @@ -48,6 +48,7 @@ const Bitset = bun.bit_set.DynamicBitSetUnmanaged; const z_allocator = @import("../memory_allocator.zig").z_allocator; const Syscall = bun.sys; const RunCommand = @import("../cli/run_command.zig").RunCommand; +const PackageManagerCommand = @import("../cli/package_manager_command.zig").PackageManagerCommand; threadlocal var initialized_store = false; const Futex = @import("../futex.zig"); @@ -6035,7 +6036,7 @@ pub const PackageManager = struct { "Possible values: \"hardlink\" (default), \"symlink\", \"copyfile\""; const install_params_ = [_]ParamType{ - clap.parseParam("-c, --config ? Load config (bunfig.toml)") catch unreachable, + clap.parseParam("-c, --config ? Specify path to config file (bunfig.toml)") catch unreachable, clap.parseParam("-y, --yarn Write a yarn.lock file (yarn v1)") catch unreachable, clap.parseParam("-p, --production Don't install devDependencies") catch unreachable, clap.parseParam("--no-save Don't save a lockfile") catch unreachable, @@ -6055,10 +6056,8 @@ pub const PackageManager = struct { clap.parseParam("--cwd Set a specific cwd") catch unreachable, clap.parseParam("--backend Platform-specific optimizations for installing dependencies. " ++ platform_specific_backend_label) catch unreachable, clap.parseParam("--link-native-bins ... Link \"bin\" from a matching platform-specific \"optionalDependencies\" instead. Default: esbuild, turbo") catch unreachable, - // clap.parseParam("--omit ... Skip installing dependencies of a certain type. \"dev\", \"optional\", or \"peer\"") catch unreachable, // clap.parseParam("--no-dedupe Disable automatic downgrading of dependencies that would otherwise cause unnecessary duplicate package versions ($BUN_CONFIG_NO_DEDUPLICATE)") catch unreachable, - clap.parseParam("--help Print this help menu") catch unreachable, }; @@ -6149,6 +6148,141 @@ pub const PackageManager = struct { } }; + pub fn printHelp(comptime subcommand: Subcommand) void { + switch (subcommand) { + // fall back to HelpCommand.printWithReason + Subcommand.install => { + const intro_text = + \\Usage: bun install [flags] [...\] + \\ Install the dependencies listed in package.json + ; + const outro_text = + \\Examples: + \\ Install the dependencies for the current project + \\ bun install + \\ + \\ Skip devDependencies + \\ bun install --production + \\ + \\Full documentation is available at https://bun.sh/docs/cli/install + ; + Output.pretty("\n" ++ intro_text, .{}); + Output.flush(); + Output.pretty("\nFlags:", .{}); + Output.flush(); + clap.simpleHelp(&PackageManager.add_params); + Output.pretty("\n\n" ++ outro_text, .{}); + Output.flush(); + }, + Subcommand.update => { + const intro_text = + \\Usage: bun update [flags] + \\ Update all dependencies to most recent versions within the version range in package.json + ; + const outro_text = + \\Examples: + \\ Update all dependencies: + \\ bun update + \\ + \\Full documentation is available at https://bun.sh/docs/cli/install#bun-update + ; + Output.pretty("\n" ++ intro_text, .{}); + Output.flush(); + Output.pretty("\nFlags:", .{}); + Output.flush(); + clap.simpleHelp(&PackageManager.add_params); + Output.pretty("\n\n" ++ outro_text, .{}); + Output.flush(); + }, + Subcommand.pm => { + PackageManagerCommand.printHelp(); + }, + Subcommand.add => { + const intro_text = + \\Usage: bun add [flags] \ [...\] + ; + const outro_text = + \\Examples: + \\ Add a dependency from the npm registry + \\ bun add zod + \\ bun add zod@next + \\ bun add zod@3.0.0 + \\ + \\ Add a dev, optional, or peer dependency + \\ bun add -d typescript + \\ bun add -o lodash + \\ bun add --peer esbuild + \\ + \\Full documentation is available at https://bun.sh/docs/cli/install + ; + Output.pretty("\n" ++ intro_text, .{}); + Output.flush(); + Output.pretty("\n\nFlags:", .{}); + Output.flush(); + clap.simpleHelp(&PackageManager.add_params); + Output.pretty("\n\n" ++ outro_text, .{}); + Output.flush(); + }, + Subcommand.remove => { + const intro_text = + \\Usage: bun remove [flags] \ [...\] + \\ Remove a package from package.json and uninstall from node_modules + ; + const outro_text = + \\Examples: + \\ Add a dependency from the npm registry + \\ bun remove ts-node + \\ + \\Full documentation is available at https://bun.sh/docs/cli/install#bun-remove + ; + Output.pretty("\n" ++ intro_text, .{}); + Output.flush(); + Output.pretty("\nFlags:", .{}); + Output.flush(); + clap.simpleHelp(&PackageManager.remove_params); + Output.pretty("\n\n" ++ outro_text, .{}); + Output.flush(); + }, + Subcommand.link => { + const intro_text = + \\Usage: bun link [flags] [\] + ; + const outro_text = + \\Examples: + \\ Register the current directory as a linkable package. + \\ Directory should contain a package.json. + \\ bun link + \\ + \\ Add a previously-registered linkable package as a dependency of the current project. + \\ bun link \ + \\ + \\Full documentation is available at https://bun.sh/docs/cli/install#bun-link + ; + Output.pretty("\n" ++ intro_text, .{}); + Output.flush(); + Output.pretty("\nFlags:", .{}); + Output.flush(); + clap.simpleHelp(&PackageManager.link_params); + Output.pretty("\n\n" ++ outro_text, .{}); + Output.flush(); + }, + Subcommand.unlink => { + const intro_text = + \\Usage: bun unlink [flags] + \\ + \\Examples: + \\ Unregister the current directory as a linkable package. + \\ bun unlink + \\ + \\Full documentation is available at https://bun.sh/docs/cli/install#bun-link + ; + + Output.pretty("\n" ++ intro_text, .{}); + Output.flush(); + }, + } + } + pub fn parse(allocator: std.mem.Allocator, comptime subcommand: Subcommand) !CommandLineArguments { comptime var params: []const ParamType = &switch (subcommand) { .install => install_params, @@ -6173,11 +6307,9 @@ pub const PackageManager = struct { }; if (args.flag("--help")) { - Output.prettyln("\nbun (package manager) flags:\n\n", .{}); - Output.flush(); - - clap.help(Output.writer(), params) catch {}; - + // Output.prettyln("\nbun (package manager) flags:\n\n", .{}); + // Output.flush(); + printHelp(subcommand); Global.exit(0); } -- cgit v1.2.3