diff --git a/.envrc b/.envrc new file mode 100644 index 0000000..3550a30 --- /dev/null +++ b/.envrc @@ -0,0 +1 @@ +use flake diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 6e5d801..c915264 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -9,12 +9,22 @@ on: jobs: build: - runs-on: ubuntu-latest + runs-on: ${{ matrix.os }} name: Ruby ${{ matrix.ruby }} strategy: + fail-fast: false matrix: - ruby: - - '3.2.2' + include: + - ruby: '3.2.2' + os: ubuntu-latest + task: 'bundle exec rake' + - ruby: '2.6' + os: ubuntu-22.04 + task: 'bundle exec rspec' + gemfile: 'gemfiles/ruby26.gemfile' + + env: + BUNDLE_GEMFILE: ${{ github.workspace }}/${{ matrix.gemfile || 'Gemfile' }} steps: - uses: actions/checkout@v4 @@ -24,4 +34,4 @@ jobs: ruby-version: ${{ matrix.ruby }} bundler-cache: true - name: Run the default task - run: bundle exec rake + run: ${{ matrix.task }} diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 1e69962..a4fd59c 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -15,7 +15,7 @@ jobs: runs-on: ubuntu-latest container: - image: ghcr.io/tamatebako/tebako-ubuntu-20.04:latest + image: ghcr.io/tamatebako/tebako-ubuntu-20.04:0.12.6 steps: - name: Checkout diff --git a/.gitignore b/.gitignore index c49c127..a1f33bf 100644 --- a/.gitignore +++ b/.gitignore @@ -14,3 +14,6 @@ .irbrc rubyshell-*.gem + +/.direnv/ +/gemfiles/*.lock diff --git a/flake.lock b/flake.lock new file mode 100644 index 0000000..e2a5570 --- /dev/null +++ b/flake.lock @@ -0,0 +1,61 @@ +{ + "nodes": { + "flake-utils": { + "inputs": { + "systems": "systems" + }, + "locked": { + "lastModified": 1731533236, + "narHash": "sha256-l0KFg5HjrsfsO/JpG+r7fRrqm12kzFHyUHqHCVpMMbI=", + "owner": "numtide", + "repo": "flake-utils", + "rev": "11707dc2f618dd54ca8739b309ec4fc024de578b", + "type": "github" + }, + "original": { + "owner": "numtide", + "repo": "flake-utils", + "type": "github" + } + }, + "nixpkgs": { + "locked": { + "lastModified": 1789785513, + "narHash": "sha256-B44WL6h0XoLjJ41bUPJk0X5SDinLCII//6EcBLXKiJ0=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "20b1ddd1aa5ace70c9468305030aa4f9ef79671b", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixos-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "root": { + "inputs": { + "flake-utils": "flake-utils", + "nixpkgs": "nixpkgs" + } + }, + "systems": { + "locked": { + "lastModified": 1681028828, + "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", + "owner": "nix-systems", + "repo": "default", + "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e", + "type": "github" + }, + "original": { + "owner": "nix-systems", + "repo": "default", + "type": "github" + } + } + }, + "root": "root", + "version": 7 +} diff --git a/flake.nix b/flake.nix new file mode 100644 index 0000000..fd68b59 --- /dev/null +++ b/flake.nix @@ -0,0 +1,33 @@ +{ + description = "rubyshell development environment"; + + inputs = { + nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable"; + flake-utils.url = "github:numtide/flake-utils"; + }; + + outputs = { nixpkgs, flake-utils, ... }: + flake-utils.lib.eachDefaultSystem (system: + let + pkgs = import nixpkgs { inherit system; }; + ruby = pkgs.ruby_3_3; + in + { + devShells.default = pkgs.mkShell { + packages = [ + ruby + pkgs.bundler + pkgs.libyaml + pkgs.gnumake + pkgs.gcc + ]; + + shellHook = '' + export BUNDLE_PATH="$PWD/.bundle/vendor" + export BUNDLE_BIN="$PWD/.bundle/bin" + export GEM_HOME="$BUNDLE_PATH" + export PATH="$BUNDLE_BIN:$PWD/bin:$PATH" + ''; + }; + }); +} diff --git a/gemfiles/ruby26.gemfile b/gemfiles/ruby26.gemfile new file mode 100644 index 0000000..103cfe9 --- /dev/null +++ b/gemfiles/ruby26.gemfile @@ -0,0 +1,11 @@ +# frozen_string_literal: true + +# Minimal dependency set for the Ruby 2.6 compatibility job. +# The main Gemfile pulls in debug (needs >= 2.7) and rubocop, which do not +# install on 2.6; this one only carries what the specs need. +source "https://rubygems.org" + +gemspec path: ".." + +gem "rake", "~> 13.0" +gem "rspec", "~> 3.0" diff --git a/lib/rubyshell.rb b/lib/rubyshell.rb index 0dc63e1..c6f8436 100644 --- a/lib/rubyshell.rb +++ b/lib/rubyshell.rb @@ -67,6 +67,10 @@ def config(kwargs) module Kernel def sh(command = nil, *args, **kwargs, &block) if command + # On Ruby 2.6 an empty **kwargs is still passed along as a positional + # empty hash, which breaks arity for methods like OverwritedCommands#cd. + return RubyShell::Executor.send(command, *args) if kwargs.empty? + RubyShell::Executor.send(command, *args, **kwargs) elsif block.nil? RubyShell::Executor diff --git a/lib/rubyshell/chainer.rb b/lib/rubyshell/chainer.rb index 3097819..2ab7cf2 100644 --- a/lib/rubyshell/chainer.rb +++ b/lib/rubyshell/chainer.rb @@ -24,7 +24,7 @@ def shared_settings end def settings - @options.select { shared_settings.include?(_1.to_sym) }.transform_keys { :"_#{_1}" } + @options.select { |k, _v| shared_settings.include?(k.to_sym) }.transform_keys { |k| :"_#{k}" } end def method_missing(method_name, *args, &block) diff --git a/lib/rubyshell/parallel_executor.rb b/lib/rubyshell/parallel_executor.rb index ade812a..a699781 100644 --- a/lib/rubyshell/parallel_executor.rb +++ b/lib/rubyshell/parallel_executor.rb @@ -14,7 +14,7 @@ def shared_settings end def settings - @options.select { shared_settings.include?(_1.to_sym) }.transform_keys { :"_#{_1}" } + @options.select { |k, _v| shared_settings.include?(k.to_sym) }.transform_keys { |k| :"_#{k}" } end def _evaluate(&block) diff --git a/spec/spec_helper.rb b/spec/spec_helper.rb index 1f606bb..3d54b1b 100644 --- a/spec/spec_helper.rb +++ b/spec/spec_helper.rb @@ -1,7 +1,9 @@ # frozen_string_literal: true require "tmpdir" -require "debug" +# The debug gem requires Ruby >= 2.7. On 2.6 `require "debug"` would load the +# stdlib debugger (rdb) instead, which takes over the run on the first raise. +require "debug" if RUBY_VERSION >= "2.7" require_relative "../lib/rubyshell" RSpec.configure do |config|