Ruby on Rails 插件 - 在 class 中添加验证无法正常工作

Ruby on Rails plugin - Adding validation in class doesn't work properly

我制作了一个小的 DRY 插件,稍后我想在我的一些 类(如剧院、咖啡店、餐厅等)中使用它。所有这些 类 都包含一个地址,因此,我制作了一个带有 act_as_address 方法的地址模型插件,这些 类以避免编写重复代码。

类 将包含对地址字段的一些验证(如存在和长度),我在 [=25= 中使用了 class_eval ]act_as_address 在地址模型中将这些验证写入 类。然而,它似乎不起作用。

这是我的代码和测试:

# structure.sql
create table addresses (
  some_info varchar(25)
  # other attrs
);

create table theatres (
  id integer,
  primary key (id)
) inherits (addresses);


# act_as_address.rb
module Address
  module ActsAsAddress
    extend ActiveSupport::Concern

    include do
    end

    module ClassMethods
      def acts_as_address
        class_eval do <<-EVAL
        validates :some_info, presence: true
        # some other validations, methods etc.
        EVAL
        end
      end
    end
  end
end

ActiveRecord::Base.send :include, Address::ActsAsAddress

# theatre.rb
class Theatre < ActiveRecord::Base
  acts_as_address
end

# address.rb
require 'address/acts_as_address'

module Address
end

# acts_as_address_test.rb
require File.expand_path('../test_helper', __FILE__)

class ActsAsAddressTest < ActiveSupport::TestCase
  test "should not be valid" do
    assert_not Theatre.create(:some_info => nil).valid?, 
      "some_info was valid with nil value"
  end
end

测试结果如下:

  1) Failure:
ActsAsAddressTest#test_should_not_be_valid [acts_as_address_test.rb:16]:
some_info was valid with nil value

有人能帮我吗? class_eval 是这里的问题吗?我在 Rails 上使用 Ruby 4.

您也许可以这样做:

module Address
  module ActsAsAddress
    extend ActiveSupport::Concern

    module ClassMethods
      def acts_as_address
        validates :some_info, presence: true
      end
    end
  end
end