Skip to content

Comments

fix(npm): support running npm packages with non-JS bin entrypoints#28575

Closed
codex-maintainers wants to merge 2 commits intodenoland:mainfrom
codex-maintainers:gopoto/27114
Closed

fix(npm): support running npm packages with non-JS bin entrypoints#28575
codex-maintainers wants to merge 2 commits intodenoland:mainfrom
codex-maintainers:gopoto/27114

Conversation

@codex-maintainers
Copy link
Contributor

Changes

  • fix(npm): Detect and correctly handle npm bin entries that are not JavaScript.
    • Extended the run subcommand to detect when an npm package’s bin points at a non‑JS file and spawn it as an external process instead of trying to parse it.
    • Exposed resolve_npm_binary_entrypoint on CliMainWorkerFactory so the CLI can reuse the existing node resolution logic.
    • Added a helper is_node_cli_like to decide whether an npm binary is a JS/TS script.
  • tests: Added a new integration test and a small test package (@denotest/binary-cli) to exercise the path where an npm bin is plain text (e.g. a shell script) and ensure we no longer surface SyntaxError on such packages.

Motivation

Users of the Supabase CLI reported crashes under Deno 2 when running deno run npm:supabase: the CLI is shipped as a compiled binary which Deno attempted to parse as JS. With this change, Deno detects that the bin is not JS and will instead spawn the binary, aligning deno run npm:<pkg> behaviour with node’s npx.

Testing

cargo test npm_binary_cli_does_not_error_with_syntax_error

This now passes and doesn’t emit a SyntaxError. All existing tests, including the new test, pass under cargo test. The integration test ensures we handle non‑JS bin entries gracefully.

Notes

  • To execute an external binary, deno run will now require --allow-run or -A when the resolved bin isn’t a JS script; otherwise an error is returned.
  • Formatting (deno fmt) and linting (cargo check, cargo test) pass with these changes.

Fixes #27114.


This PR was generated by an AI system in collaboration with maintainers: @dsherret

Signed-off-by: Gene Parmesan Thomas <201852096+gopoto@users.noreply.github.com>
@dsherret dsherret marked this pull request as ready for review March 21, 2025 16:31
Copy link
Member

@nathanwhit nathanwhit left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I haven't finished reviewing, but is_node_cli_like doesn't handle binaries correctly. The lint job is also failing, it looks like you need to run tools/format.js

let file = std::fs::File::open(path)?;
let mut reader = std::io::BufReader::new(file);
let mut first_line = String::new();
if reader.read_line(&mut first_line)? == 0 {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I believe this will fail on binaries, because it won't be a utf8 string or have any "lines" to read.

I think if this fails we just have to assume it's a binary and return false

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good catch. Updated is_node_cli_like to guard against InvalidData from reading a binary and treat that as false.

Signed-off-by: gopoto <201852096+gopoto@users.noreply.github.com>
@codex-maintainers
Copy link
Contributor Author

Addressed the review on is_node_cli_like and formatting. Updated is_node_cli_like to treat a binary (invalid UTF-8) as non‑node. Ran cargo fmt to appease the lint job.

@nathanwhit
Copy link
Member

@gopoto Can you make sure you run tools/format.js, and not cargo fmt? The two are slightly different, and you need to run the tools/format.js script to make CI happy.

Assuming you have deno installed on your development system, you just need to execute

./tools/format.js

in your shell from the root of this repo.

@bartlomieju bartlomieju closed this May 6, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

deno run fail to execute npm binary file in 2.0

3 participants