Skip to content

Is there a deterministic way of checking whether bundle exec is necessary? #486

Description

@mculp

Sort of related to #433, I've recently found out that bundle exec adds a significant amount of time to commands as opposed to the naked command when the binstub doesn't exist. This is especially important when running linters as a pre-commit hook.

I posted on lefthook's discussion board about this, but our team mostly uses chruby in local environments because it's in our onboarding guide, and y'all seem to more likely to know the answer to this: is there a deterministic or even near-deterministic way of checking whether bundle exec is necessary?

I came up with this pretty naive exec-wrapper script:

#!/usr/bin/env sh

if test -n "$RUBY_VERSION"
then
  if test -x "$0"
  then
    exec "$@"
  elif test -x chruby-exec
  then
    chruby-exec "$RUBY_VERSION" -- "$@"
  fi
else
  bundle exec "$@"
fi
Command Mean [ms] Min [ms] Max [ms] Relative
rubocop --server ... 190.9 ± 5.9 183.4 199.9 1.00
bin/exec-wrapper rubocop --server ... 200.2 ± 8.4 184.1 212.1 1.05 ± 0.05
chruby-exec 3.1.2 -- rubocop --server ... 210.5 ± 7.8 195.2 222.7 1.10 ± 0.05
bundle exec rubocop ... 709.4 ± 5.2 702.7 716.7 3.72 ± 0.12
Benchmark 1: bin/exec-wrapper rubocop --server ...
  Time (mean ± σ):     197.1 ms ±   4.9 ms    [User: 93.1 ms, System: 30.3 ms]
  Range (min … max):   186.4 ms … 202.3 ms    14 runs

Benchmark 2: rubocop --server ...
  Time (mean ± σ):     189.4 ms ±   7.3 ms    [User: 92.3 ms, System: 28.8 ms]
  Range (min … max):   173.7 ms … 200.5 ms    15 runs

Benchmark 3: bundle exec rubocop --server ...
  Time (mean ± σ):     706.4 ms ±   5.3 ms    [User: 567.1 ms, System: 64.8 ms]
  Range (min … max):   699.2 ms … 715.6 ms    10 runs

Benchmark 4: chruby-exec 3.1.2 -- rubocop ...
  Time (mean ± σ):     212.0 ms ±   5.2 ms    [User: 98.5 ms, System: 34.4 ms]
  Range (min … max):   203.9 ms … 219.4 ms    14 runs

Summary
  'rubocop --server ...
    1.04 ± 0.05 times faster than 'bin/exec-wrapper rubocop --server ...'
    1.12 ± 0.05 times faster than 'chruby-exec 3.1.2 -- rubocop --server ...'
    3.73 ± 0.15 times faster than 'bundle exec rubocop --server ...'

I would like to commit this pretty significant quality of life change, but I don't want to break anyone's machine by missing something in this script.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions