Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Modern Ruby + ActiveRecord, Update Travis Config #416

Merged
merged 12 commits into from
Oct 19, 2022
57 changes: 6 additions & 51 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -1,59 +1,14 @@
sudo: false
mvastola marked this conversation as resolved.
Show resolved Hide resolved
language: ruby
dist: focal
os: linux
cache: bundler
rvm:
- 2.0
- 2.1
- 2.2.2
- 2.3.0
- 2.4.0
- 2.5.0
- rbx
- 2.6.10
- 2.7.6
joshbranham marked this conversation as resolved.
Show resolved Hide resolved
env:
- ACTIVERECORD=3.0.0
- ACTIVERECORD=3.1.0
- ACTIVERECORD=3.2.0
- ACTIVERECORD=4.0.0
- ACTIVERECORD=4.1.0
- ACTIVERECORD=4.2.0
- ACTIVERECORD=5.0.0
- ACTIVERECORD=5.1.1
matrix:
exclude:
- rvm: 2.0
joshbranham marked this conversation as resolved.
Show resolved Hide resolved
env: ACTIVERECORD=5.0.0
- rvm: 2.0
env: ACTIVERECORD=5.1.1
- rvm: 2.1
env: ACTIVERECORD=5.0.0
- rvm: 2.1
env: ACTIVERECORD=5.1.1
- rvm: 2.4.0
env: ACTIVERECORD=3.0.0
- rvm: 2.4.0
env: ACTIVERECORD=3.1.0
- rvm: 2.4.0
env: ACTIVERECORD=3.2.0
- rvm: 2.4.0
env: ACTIVERECORD=4.0.0
- rvm: 2.4.0
env: ACTIVERECORD=4.1.0
- rvm: 2.5.0
env: ACTIVERECORD=3.0.0
- rvm: 2.5.0
env: ACTIVERECORD=3.1.0
- rvm: 2.5.0
env: ACTIVERECORD=3.2.0
- rvm: 2.5.0
env: ACTIVERECORD=4.0.0
- rvm: 2.5.0
env: ACTIVERECORD=4.1.0
- rvm: rbx
env: ACTIVERECORD=5.0.0
- rvm: rbx
env: ACTIVERECORD=5.1.1
allow_failures:
- rvm: rbx
- ACTIVERECORD=5.2.8
jobs:
fast_finish: true
addons:
code_climate:
Expand Down
11 changes: 2 additions & 9 deletions attr_encrypted.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -19,15 +19,12 @@ Gem::Specification.new do |s|
s.homepage = 'http://github.com/attr-encrypted/attr_encrypted'
s.license = 'MIT'

s.has_rdoc = false
s.rdoc_options = ['--line-numbers', '--inline-source', '--main', 'README.rdoc']

s.require_paths = ['lib']

s.files = `git ls-files`.split("\n")
s.test_files = `git ls-files -- test/*`.split("\n")

s.required_ruby_version = '>= 2.0.0'
s.required_ruby_version = '>= 2.6.0'

s.add_dependency('encryptor', ['~> 3.0.0'])
# support for testing with specific active record version
Expand All @@ -42,20 +39,16 @@ Gem::Specification.new do |s|
s.add_development_dependency('rake')
s.add_development_dependency('minitest')
s.add_development_dependency('sequel')
if RUBY_VERSION < '2.1.0'
s.add_development_dependency('nokogiri', '< 1.7.0')
s.add_development_dependency('public_suffix', '< 3.0.0')
end
if defined?(RUBY_ENGINE) && RUBY_ENGINE.to_sym == :jruby
s.add_development_dependency('activerecord-jdbcsqlite3-adapter')
s.add_development_dependency('jdbc-sqlite3', '< 3.8.7') # 3.8.7 is nice and broke
else
s.add_development_dependency('sqlite3')
end
s.add_development_dependency('dm-sqlite-adapter')
s.add_development_dependency('pry')
s.add_development_dependency('simplecov')
s.add_development_dependency('simplecov-rcov')
s.add_development_dependency("codeclimate-test-reporter", '<= 0.6.0')

s.cert_chain = ['certs/saghaulor.pem']
s.signing_key = File.expand_path("~/.ssh/gem-private_key.pem") if $0 =~ /gem\z/
Expand Down
25 changes: 16 additions & 9 deletions lib/attr_encrypted/adapters/active_record.rb
Original file line number Diff line number Diff line change
Expand Up @@ -53,28 +53,35 @@ def attr_encrypted(*attrs)
super
options = attrs.extract_options!
attr = attrs.pop
attribute attr if ::ActiveRecord::VERSION::STRING >= "5.1.0"
attribute attr
options.merge! encrypted_attributes[attr]

define_method("#{attr}_was") do
attribute_was(attr)
end

if ::ActiveRecord::VERSION::STRING >= "4.1"
define_method("#{attr}_changed?") do |options = {}|
attribute_changed?(attr, options)
end
else
define_method("#{attr}_changed?") do
attribute_changed?(attr)
end
define_method("#{attr}_changed?") do |options = {}|
attribute_changed?(attr, options)
end

define_method("#{attr}_change") do
attribute_change(attr)
end

define_method("#{attr}_with_dirtiness=") do |value|
## Source: https://github.com/priyankatapar/attr_encrypted/commit/7e8702bd5418c927a39d8dd72c0adbea522d5663
# In ActiveRecord 5.2+, due to changes to the way virtual
# attributes are handled, @attributes[attr].value is nil which
# breaks attribute_was. Setting it here returns us to the expected
# behavior.
if ::ActiveRecord::VERSION::STRING >= "5.2"
# This is needed support attribute_was before a record has
# been saved
set_attribute_was(attr, __send__(attr)) if value != __send__(attr)
# This is needed to support attribute_was after a record has
# been saved
@attributes.write_from_user(attr.to_s, value) if value != __send__(attr)
end
attribute_will_change!(attr) if value != __send__(attr)
__send__("#{attr}_without_dirtiness=", value)
end
Expand Down
98 changes: 47 additions & 51 deletions test/active_record_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -45,16 +45,14 @@ def create_tables

ActiveRecord::MissingAttributeError = ActiveModel::MissingAttributeError unless defined?(ActiveRecord::MissingAttributeError)

if ::ActiveRecord::VERSION::STRING > "4.0"
module Rack
module Test
class UploadedFile; end
end
module Rack
module Test
class UploadedFile; end
end

require 'action_controller/metal/strong_parameters'
end

require 'action_controller/metal/strong_parameters'

class Person < ActiveRecord::Base
self.attr_encrypted_options[:mode] = :per_attribute_iv_and_salt
attr_encrypted :email, key: SECRET_KEY
Expand Down Expand Up @@ -106,7 +104,6 @@ class PersonWithSerialization < ActiveRecord::Base
class UserWithProtectedAttribute < ActiveRecord::Base
self.table_name = 'users'
attr_encrypted :password, key: SECRET_KEY
attr_protected :is_admin if ::ActiveRecord::VERSION::STRING < "4.0"
end

class PersonUsingAlias < ActiveRecord::Base
Expand Down Expand Up @@ -221,52 +218,53 @@ def test_attribute_was_works_when_options_for_old_encrypted_value_are_different_
assert_equal pw.reverse, account.password
end

if ::ActiveRecord::VERSION::STRING > "4.0"
def test_should_assign_attributes
@user = UserWithProtectedAttribute.new(login: 'login', is_admin: false)
@user.attributes = ActionController::Parameters.new(login: 'modified', is_admin: true).permit(:login)
assert_equal 'modified', @user.login
if ::ActiveRecord::VERSION::STRING >= "5.2"
def test_should_create_will_save_change_to_predicate
person = Person.create!(email: 'test@example.com')
refute person.will_save_change_to_email?
person.email = 'test@example.com'
refute person.will_save_change_to_email?
person.email = 'test2@example.com'
assert person.will_save_change_to_email?
end

def test_should_not_assign_protected_attributes
@user = UserWithProtectedAttribute.new(login: 'login', is_admin: false)
@user.attributes = ActionController::Parameters.new(login: 'modified', is_admin: true).permit(:login)
assert !@user.is_admin?
def test_should_create_saved_change_to_predicate
person = Person.create!(email: 'test@example.com')
assert person.saved_change_to_email?
person.reload
person.email = 'test@example.com'
refute person.saved_change_to_email?
person.email = nil
refute person.saved_change_to_email?
person.email = 'test2@example.com'
refute person.saved_change_to_email?
person.save
assert person.saved_change_to_email?
end
end

def test_should_raise_exception_if_not_permitted
@user = UserWithProtectedAttribute.new(login: 'login', is_admin: false)
assert_raises ActiveModel::ForbiddenAttributesError do
@user.attributes = ActionController::Parameters.new(login: 'modified', is_admin: true)
end
end
def test_should_assign_attributes
@user = UserWithProtectedAttribute.new(login: 'login', is_admin: false)
@user.attributes = ActionController::Parameters.new(login: 'modified', is_admin: true).permit(:login)
assert_equal 'modified', @user.login
end

def test_should_raise_exception_on_init_if_not_permitted
assert_raises ActiveModel::ForbiddenAttributesError do
@user = UserWithProtectedAttribute.new ActionController::Parameters.new(login: 'modified', is_admin: true)
end
end
else
def test_should_assign_attributes
@user = UserWithProtectedAttribute.new(login: 'login', is_admin: false)
@user.attributes = { login: 'modified', is_admin: true }
assert_equal 'modified', @user.login
end
def test_should_not_assign_protected_attributes
@user = UserWithProtectedAttribute.new(login: 'login', is_admin: false)
@user.attributes = ActionController::Parameters.new(login: 'modified', is_admin: true).permit(:login)
assert !@user.is_admin?
end

def test_should_not_assign_protected_attributes
@user = UserWithProtectedAttribute.new(login: 'login', is_admin: false)
@user.attributes = { login: 'modified', is_admin: true }
assert !@user.is_admin?
def test_should_raise_exception_if_not_permitted
@user = UserWithProtectedAttribute.new(login: 'login', is_admin: false)
assert_raises ActiveModel::ForbiddenAttributesError do
@user.attributes = ActionController::Parameters.new(login: 'modified', is_admin: true)
end
end

def test_should_assign_protected_attributes
@user = UserWithProtectedAttribute.new(login: 'login', is_admin: false)
if ::ActiveRecord::VERSION::STRING > "3.1"
@user.send(:assign_attributes, { login: 'modified', is_admin: true }, without_protection: true)
else
@user.send(:attributes=, { login: 'modified', is_admin: true }, false)
end
assert @user.is_admin?
def test_should_raise_exception_on_init_if_not_permitted
assert_raises ActiveModel::ForbiddenAttributesError do
@user = UserWithProtectedAttribute.new ActionController::Parameters.new(login: 'modified', is_admin: true)
end
end

Expand All @@ -291,11 +289,9 @@ def test_should_allow_proc_based_mode
assert_nil @person.encrypted_credentials_iv
end

if ::ActiveRecord::VERSION::STRING > "3.1"
def test_should_allow_assign_attributes_with_nil
@person = Person.new
assert_nil(@person.assign_attributes nil)
end
def test_should_allow_assign_attributes_with_nil
@person = Person.new
assert_nil(@person.assign_attributes nil)
end

def test_that_alias_encrypts_column
Expand Down
22 changes: 15 additions & 7 deletions test/run.sh
Original file line number Diff line number Diff line change
@@ -1,12 +1,20 @@
#!/usr/bin/env sh -e
#!/usr/bin/env bash

for RUBY in 1.9.3 2.0.0 2.1 2.2
set -e

for RUBY in 2.6.10 2.7.6
do
for RAILS in 2.3.8 3.0.0 3.1.0 3.2.0 4.0.0 4.1.0 4.2.0
for ACTIVERECORD in 5.1.1 5.2.8
do
if [[ $RUBY -gt 1.9.3 && $RAILS -lt 4.0.0 ]]; then
continue
fi
RBENV_VERSION=$RUBY ACTIVERECORD=$RAILS bundle && bundle exec rake
echo ">>> Testing with Ruby ${RUBY} and ActiveRecord ${ACTIVERECORD}."
export RBENV_VERSION=$RUBY
export ACTIVERECORD=$ACTIVERECORD

rbenv install $RUBY --skip-existing
bundle install
bundle check
bundle exec rake test
rm Gemfile.lock
echo ">>> Finished testing with Ruby ${RUBY} and ActiveRecord ${ACTIVERECORD}."
done
done
7 changes: 2 additions & 5 deletions test/test_helper.rb
Original file line number Diff line number Diff line change
@@ -1,23 +1,20 @@
# frozen_string_literal: true

require 'pry'
require 'simplecov'
require 'simplecov-rcov'
require "codeclimate-test-reporter"

SimpleCov.formatter = SimpleCov::Formatter::MultiFormatter.new(
[
SimpleCov::Formatter::HTMLFormatter,
SimpleCov::Formatter::RcovFormatter,
CodeClimate::TestReporter::Formatter
SimpleCov::Formatter::RcovFormatter
]
)

SimpleCov.start do
add_filter 'test'
end

CodeClimate::TestReporter.start

require 'minitest/autorun'

# Rails 4.0.x pins to an old minitest
Expand Down