From 8e28340556870f2f50a52f01d1aadebb27aa40da Mon Sep 17 00:00:00 2001 From: will89 Date: Wed, 30 Mar 2022 14:10:45 -0400 Subject: [PATCH] Add rails 7 support and add ruby 3.1 to tests (#36) --- .circleci/config.yml | 35 +++++------ .rubocop.yml | 5 +- Appraisals | 30 +++------- CHANGELOG.md | 5 ++ gemfiles/rails_4.2.gemfile | 9 --- gemfiles/rails_5.0.gemfile | 9 --- gemfiles/rails_6.0.gemfile | 4 +- gemfiles/rails_6.1.gemfile | 4 +- .../{rails_5.1.gemfile => rails_7.0.gemfile} | 4 +- .../global_context_registry.rb | 7 ++- lib/rails_multitenant/version.rb | 2 +- rails_multitenant.gemspec | 8 +-- spec/item_spec.rb | 37 +++++++----- .../global_context_registry/current_spec.rb | 58 ++++++++++++------- .../global_context_registry_spec.rb | 6 ++ spec/rails_multitenant_spec.rb | 4 +- 16 files changed, 115 insertions(+), 112 deletions(-) delete mode 100644 gemfiles/rails_4.2.gemfile delete mode 100644 gemfiles/rails_5.0.gemfile rename gemfiles/{rails_5.1.gemfile => rails_7.0.gemfile} (59%) diff --git a/.circleci/config.yml b/.circleci/config.yml index ba79406..05cb746 100644 --- a/.circleci/config.yml +++ b/.circleci/config.yml @@ -2,14 +2,14 @@ version: 2.1 jobs: lint: docker: - - image: salsify/ruby_ci:2.5.8 + - image: salsify/ruby_ci:2.7.5 working_directory: ~/rails-multitenant steps: - checkout - restore_cache: keys: - - v1-gems-ruby-2.5.8-{{ checksum "rails_multitenant.gemspec" }}-{{ checksum "Gemfile" }} - - v1-gems-ruby-2.5.8- + - v1-gems-ruby-2.7.5-{{ checksum "rails_multitenant.gemspec" }}-{{ checksum "Gemfile" }} + - v1-gems-ruby-2.7.5- - run: name: Install Gems command: | @@ -18,7 +18,7 @@ jobs: bundle clean fi - save_cache: - key: v1-gems-ruby-2.5.8-{{ checksum "rails_multitenant.gemspec" }}-{{ checksum "Gemfile" }} + key: v1-gems-ruby-2.7.5-{{ checksum "rails_multitenant.gemspec" }}-{{ checksum "Gemfile" }} paths: - "vendor/bundle" - "gemfiles/vendor/bundle" @@ -69,27 +69,20 @@ workflows: matrix: parameters: gemfile: - - "gemfiles/rails_4.2.gemfile" - - "gemfiles/rails_5.0.gemfile" - - "gemfiles/rails_5.1.gemfile" - "gemfiles/rails_5.2.gemfile" - "gemfiles/rails_6.0.gemfile" - "gemfiles/rails_6.1.gemfile" + - "gemfiles/rails_7.0.gemfile" ruby_version: - - "2.5.8" - - "2.6.6" - - "2.7.2" - - "3.0.0" + - "2.7.5" + - "3.0.3" + - "3.1.1" exclude: - - gemfile: "gemfiles/rails_4.2.gemfile" - ruby_version: "2.7.2" - - gemfile: "gemfiles/rails_4.2.gemfile" - ruby_version: "3.0.0" - - gemfile: "gemfiles/rails_5.0.gemfile" - ruby_version: "3.0.0" - - gemfile: "gemfiles/rails_5.1.gemfile" - ruby_version: "3.0.0" - gemfile: "gemfiles/rails_5.2.gemfile" - ruby_version: "3.0.0" + ruby_version: "3.0.3" + - gemfile: "gemfiles/rails_5.2.gemfile" + ruby_version: "3.1.1" + - gemfile: "gemfiles/rails_6.0.gemfile" + ruby_version: "3.0.3" - gemfile: "gemfiles/rails_6.0.gemfile" - ruby_version: "3.0.0" + ruby_version: "3.1.1" diff --git a/.rubocop.yml b/.rubocop.yml index 4b29136..0e3926b 100644 --- a/.rubocop.yml +++ b/.rubocop.yml @@ -2,9 +2,10 @@ inherit_gem: salsify_rubocop: conf/rubocop.yml AllCops: - TargetRubyVersion: 2.4 + TargetRubyVersion: 2.7 Exclude: - - 'gemfiles/*' + - 'gemfiles/**/*' + - 'vendor/**/*' Metrics/LineLength: Enabled: true diff --git a/Appraisals b/Appraisals index 2ca99a1..5adca0d 100644 --- a/Appraisals +++ b/Appraisals @@ -1,33 +1,21 @@ # frozen_string_literal: true -appraise 'rails-4.2' do - gem 'sqlite3', '~> 1.3.6' - gem 'activerecord', '4.2.11.1' - gem 'activesupport', '4.2.11.1' -end - -appraise 'rails-5.0' do - gem 'sqlite3', '~> 1.3.6' - gem 'activerecord', '5.0.7.2' - gem 'activesupport', '5.0.7.2' -end - -appraise 'rails-5.1' do - gem 'activerecord', '5.1.7' - gem 'activesupport', '5.1.7' -end - appraise 'rails-5.2' do gem 'activerecord', '5.2.4.4' gem 'activesupport', '5.2.4.4' end appraise 'rails-6.0' do - gem 'activerecord', '6.0.3.4' - gem 'activesupport', '6.0.3.4' + gem 'activerecord', '~> 6.0.4' + gem 'activesupport', '~> 6.0.4' end appraise 'rails-6.1' do - gem 'activerecord', '6.1.0' - gem 'activesupport', '6.1.0' + gem 'activerecord', '~> 6.1.5' + gem 'activesupport', '~> 6.1.5' +end + +appraise 'rails-7.0' do + gem 'activerecord', '~> 7.0.2' + gem 'activesupport', '~> 7.0.2' end diff --git a/CHANGELOG.md b/CHANGELOG.md index db8c959..5154b86 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,10 @@ # Changelog +### 0.16.0 +* Add support for Rails 7.0. +* Drop unsupported rails versions < 5.2 +* Drop unsupported ruby versions < 2.7 + ### 0.15.0 * Add support for Rails 6.1. diff --git a/gemfiles/rails_4.2.gemfile b/gemfiles/rails_4.2.gemfile deleted file mode 100644 index 4e5e427..0000000 --- a/gemfiles/rails_4.2.gemfile +++ /dev/null @@ -1,9 +0,0 @@ -# This file was generated by Appraisal - -source "https://rubygems.org" - -gem "sqlite3", "~> 1.3.6" -gem "activerecord", "4.2.11.1" -gem "activesupport", "4.2.11.1" - -gemspec path: "../" diff --git a/gemfiles/rails_5.0.gemfile b/gemfiles/rails_5.0.gemfile deleted file mode 100644 index fb544f8..0000000 --- a/gemfiles/rails_5.0.gemfile +++ /dev/null @@ -1,9 +0,0 @@ -# This file was generated by Appraisal - -source "https://rubygems.org" - -gem "sqlite3", "~> 1.3.6" -gem "activerecord", "5.0.7.2" -gem "activesupport", "5.0.7.2" - -gemspec path: "../" diff --git a/gemfiles/rails_6.0.gemfile b/gemfiles/rails_6.0.gemfile index b940ab3..9b80006 100644 --- a/gemfiles/rails_6.0.gemfile +++ b/gemfiles/rails_6.0.gemfile @@ -2,7 +2,7 @@ source "https://rubygems.org" -gem "activerecord", "6.0.3.4" -gem "activesupport", "6.0.3.4" +gem "activerecord", "~> 6.0.4" +gem "activesupport", "~> 6.0.4" gemspec path: "../" diff --git a/gemfiles/rails_6.1.gemfile b/gemfiles/rails_6.1.gemfile index 47c6201..6d39250 100644 --- a/gemfiles/rails_6.1.gemfile +++ b/gemfiles/rails_6.1.gemfile @@ -2,7 +2,7 @@ source "https://rubygems.org" -gem "activerecord", "6.1.0" -gem "activesupport", "6.1.0" +gem "activerecord", "~> 6.1.5" +gem "activesupport", "~> 6.1.5" gemspec path: "../" diff --git a/gemfiles/rails_5.1.gemfile b/gemfiles/rails_7.0.gemfile similarity index 59% rename from gemfiles/rails_5.1.gemfile rename to gemfiles/rails_7.0.gemfile index 19897a8..151f898 100644 --- a/gemfiles/rails_5.1.gemfile +++ b/gemfiles/rails_7.0.gemfile @@ -2,7 +2,7 @@ source "https://rubygems.org" -gem "activerecord", "5.1.7" -gem "activesupport", "5.1.7" +gem "activerecord", "~> 7.0.2" +gem "activesupport", "~> 7.0.2" gemspec path: "../" diff --git a/lib/rails_multitenant/global_context_registry.rb b/lib/rails_multitenant/global_context_registry.rb index 106344b..3156c72 100644 --- a/lib/rails_multitenant/global_context_registry.rb +++ b/lib/rails_multitenant/global_context_registry.rb @@ -48,8 +48,8 @@ def merge!(values) # Duplicate the registry def duplicate_registry - globals.each_with_object({}) do |(key, value), result| - result[key] = value.nil? || value.is_a?(Integer) ? value : value.dup + globals.transform_values do |value| + value.nil? || value.is_a?(Integer) ? value : value.dup end end @@ -87,7 +87,8 @@ def replace_registry(registry) # Run a block of code that disregards scoping during read queries def with_unscoped_queries - with_merged_registry(__use_unscoped_queries: true) do + # disabling Style/ExplicitBlockArgument for performance reasons + with_merged_registry(__use_unscoped_queries: true) do # rubocop:disable Style/ExplicitBlockArgument yield end end diff --git a/lib/rails_multitenant/version.rb b/lib/rails_multitenant/version.rb index 70327b9..f87a7b7 100644 --- a/lib/rails_multitenant/version.rb +++ b/lib/rails_multitenant/version.rb @@ -1,5 +1,5 @@ # frozen_string_literal: true module RailsMultitenant - VERSION = '0.15.0' + VERSION = '0.16.0' end diff --git a/rails_multitenant.gemspec b/rails_multitenant.gemspec index 90ddf81..cfae685 100644 --- a/rails_multitenant.gemspec +++ b/rails_multitenant.gemspec @@ -24,10 +24,10 @@ Gem::Specification.new do |spec| spec.files = Dir['lib/**/*.rb', 'LICENSE.txt'] spec.require_paths = ['lib'] - spec.required_ruby_version = '>= 2.4.0' + spec.required_ruby_version = '>= 2.7.0' - spec.add_dependency 'activerecord', '>= 4.2', '< 6.2' - spec.add_dependency 'activesupport', '>= 4.2', '< 6.2' + spec.add_dependency 'activerecord', '>= 5.2', '< 7.1' + spec.add_dependency 'activesupport', '>= 5.2', '< 7.1' spec.add_development_dependency 'appraisal' spec.add_development_dependency 'coveralls' @@ -35,7 +35,7 @@ Gem::Specification.new do |spec| spec.add_development_dependency 'rake', '>= 12.0' spec.add_development_dependency 'rspec', '~> 3.8.0' spec.add_development_dependency 'rspec_junit_formatter' - spec.add_development_dependency 'salsify_rubocop', '0.63.0' + spec.add_development_dependency 'salsify_rubocop', '~> 1.0.1' spec.add_development_dependency 'simplecov', '~> 0.15.1' spec.add_development_dependency 'sqlite3', '~> 1.4.0' end diff --git a/spec/item_spec.rb b/spec/item_spec.rb index ed6510b..cbf9c18 100644 --- a/spec/item_spec.rb +++ b/spec/item_spec.rb @@ -7,6 +7,24 @@ describe Item do let!(:item1) { Item.create! } + let(:dependent_class) do + Class.new do + include RailsMultitenant::GlobalContextRegistry::Current + global_context_dependent_on Organization + + def self.name + 'DependentClass' + end + end + end + + let(:sub_organization) do + Class.new(Organization) do + def self.name + 'SubOrganization' + end + end + end let!(:org2) { Organization.create! } let!(:item2) { org2.as_current { Item.create! } } @@ -46,15 +64,6 @@ end end - class DependentClass - include RailsMultitenant::GlobalContextRegistry::Current - global_context_dependent_on Organization - end - - class SubOrganization < Organization - - end - describe ".as_current" do it "returns the correct items with an org supplied" do Organization.as_current(org2) do @@ -77,18 +86,18 @@ class SubOrganization < Organization DependentModel.current = DependentModel.create! dependent = DependentModel.current - SubOrganization.create!.as_current do + sub_organization.create!.as_current do expect(DependentModel.current).not_to equal(dependent) end end it "invalidates dependent objects" do - dependent = DependentClass.current + dependent = dependent_class.new + dependent_class.current = dependent - SubOrganization.create!.as_current do - expect(DependentClass.current).not_to equal(dependent) + sub_organization.create!.as_current do + expect(dependent_class.current).not_to equal(dependent) end end end - end diff --git a/spec/rails_multitenant/global_context_registry/current_spec.rb b/spec/rails_multitenant/global_context_registry/current_spec.rb index 3382430..6652579 100644 --- a/spec/rails_multitenant/global_context_registry/current_spec.rb +++ b/spec/rails_multitenant/global_context_registry/current_spec.rb @@ -1,39 +1,55 @@ # frozen_string_literal: true -describe RailsMultitenant::GlobalContextRegistry::Current do +class TestClass + include RailsMultitenant::GlobalContextRegistry::Current + provide_default :new - class TestClass - include RailsMultitenant::GlobalContextRegistry::Current - provide_default :new + attr_accessor :id - attr_accessor :id + def initialize(id: :default) + @id = id + end +end - def initialize(id: :default) - @id = id +describe RailsMultitenant::GlobalContextRegistry::Current do + let(:sub_class) do + Class.new(TestClass) do + def self.name + 'SubClass' + end end end - class SubClass < TestClass - end + let(:dependent_class) do + Class.new do + include RailsMultitenant::GlobalContextRegistry::Current + provide_default { new } + global_context_dependent_on TestClass - class DependentClass - include RailsMultitenant::GlobalContextRegistry::Current - provide_default { new } - global_context_dependent_on TestClass + def self.name + 'DependentClass' + end + end end - class NoDefaultTestClass - include RailsMultitenant::GlobalContextRegistry::Current + let(:no_default_test_class) do + Class.new do + include RailsMultitenant::GlobalContextRegistry::Current + + def self.name + 'NoDefaultTestClass' + end + end end describe "current" do it "returns default value when supplied" do expect(TestClass.current.id).to eq(:default) - expect(SubClass.current.id).to eq(:default) + expect(sub_class.current.id).to eq(:default) end it "returns nil when no default supplied" do - expect(NoDefaultTestClass.current).to be_nil + expect(no_default_test_class.current).to be_nil end end @@ -43,8 +59,8 @@ class NoDefaultTestClass end it "raises an error when current not set" do - NoDefaultTestClass.clear_current! - expect { NoDefaultTestClass.current! }.to raise_error('No current NoDefaultTestClass set') + no_default_test_class.clear_current! + expect { no_default_test_class.current! }.to raise_error('No current NoDefaultTestClass set') end end @@ -56,9 +72,9 @@ class NoDefaultTestClass end it "clears dependencies" do - dependent = DependentClass.current + dependent = dependent_class.current TestClass.current = TestClass.new - expect(DependentClass.current).not_to equal(dependent) + expect(dependent_class.current).not_to equal(dependent) end end diff --git a/spec/rails_multitenant/global_context_registry_spec.rb b/spec/rails_multitenant/global_context_registry_spec.rb index 8be3da1..851ab89 100644 --- a/spec/rails_multitenant/global_context_registry_spec.rb +++ b/spec/rails_multitenant/global_context_registry_spec.rb @@ -62,9 +62,11 @@ specify do expect(old_registry).to eq(foo: 'bar') end + specify do expect(RailsMultitenant::GlobalContextRegistry.get(:foo)).to be_nil end + specify do RailsMultitenant::GlobalContextRegistry.replace_registry(old_registry) expect(RailsMultitenant::GlobalContextRegistry.get(:foo)).to eq 'bar' @@ -76,9 +78,11 @@ specify do expect(old_registry).to eq(foo: 'bar') end + specify do expect(RailsMultitenant::GlobalContextRegistry.get(:foo)).to be_nil end + specify do expect(RailsMultitenant::GlobalContextRegistry.get(:bar)).to eq 'foo' end @@ -95,9 +99,11 @@ def setup_registry; end specify do expect(RailsMultitenant::GlobalContextRegistry.new_registry).to eq dupe end + specify do expect(RailsMultitenant::GlobalContextRegistry.new_registry.object_id).not_to eq dupe.object_id end + specify do expect(RailsMultitenant::GlobalContextRegistry.get(:foo).object_id).not_to eq dupe[:foo].object_id end diff --git a/spec/rails_multitenant_spec.rb b/spec/rails_multitenant_spec.rb index b970789..8a5b544 100644 --- a/spec/rails_multitenant_spec.rb +++ b/spec/rails_multitenant_spec.rb @@ -28,9 +28,11 @@ it "RailsMultitenant.fetch checks and sets the GlobalContextRegistry" do RailsMultitenant::GlobalContextRegistry[:organization_id] = nil + # False positive from rubocop + # rubocop:disable Style/RedundantFetchBlock expect(RailsMultitenant.fetch(:organization_id) { 'Salsify Anarchists' }).to eq('Salsify Anarchists') - expect(RailsMultitenant.fetch(:organization_id) { 'Salsify Crypto Anarchists' }).to eq('Salsify Anarchists') + # rubocop:enable Style/RedundantFetchBlock end it "RailsMultitenant.delete removes from the GlobalContextRegistry" do