Ruby   发布时间:2022-04-03  发布网站:大佬教程  code.js-code.com
大佬教程收集整理的这篇文章主要介绍了ruby-on-rails – 使用Shoulda对Rails模型重构rspec测试大佬教程大佬觉得挺不错的,现在分享给大家,也给大家做个参考。
通过回答 another StackOverflow question on attribute accessibility tests(并认为它们相当棒极了),在学习了 shoulda-matchers后,我决定尝试重构 The Rails Tutorial中的模型测试,以使它们更加简洁和彻底.我这样做是因为模块 Shoulda::Matchers::ActiveRecordShoulda::Matchers::ActiveModel的文档以及 this StackOverflow answer在模型中进行测试的一些灵感.但是,还有一些我不太清楚的事情,我想知道这些测试如何能够更好地进行.

我将使用Rails教程中的用户规范作为我的例子,因为它是最详细的,并且涵盖了许多可以改进的领域.以下代码示例已从原来的user_spec.rb更改,并将代码替换为描述“微孔关联”行.针对user.rb型号的规格测试,其工厂定义在factories.rb.

规格/型号/ user_spec.rb

@H_874_6@# == scheR_614_11845@a Information # # Table name: users # # id :Integer not null,priMary key # name :string(255) # email :string(255) # created_at :datetiR_614_11845@e not null # updated_at :datetiR_614_11845@e not null # password_digest :string(255) # remember_token :string(255) # admin :Boolean default(false) # # Indexes # # index_users_on_email (email) UNIQUE # index_users_on_remember_token (remember_token) # require 'spec_Helper' describe User do let(:user) { FactoryGirl.create(:user) } subject { user } describe "database scheR_614_11845@a" do it { should have_db_column(:id).of_type(:Integer) .with_options(null: falsE) } it { should have_db_column(:Name).of_type(:string) } it { should have_db_column(:email).of_type(:string) } it { should have_db_column(:created_at).of_type(:datetiR_614_11845@E) .with_options(null: falsE) } it { should have_db_column(:updated_at).of_type(:datetiR_614_11845@E) .with_options(null: falsE) } it { should have_db_column(:password_digest).of_type(:string) } it { should have_db_column(:remember_token).of_type(:string) } it { should have_db_column(:admin).of_type(:Boolean) .with_options(default: falsE) } it { should have_db_index(:email).unique(true) } it { should have_db_index(:remember_token) } end describe "associations" do it { should have_many(:microposts).dependent(:destroy) } it { should have_many(:relationships).dependent(:destroy) } it { should have_many(:followed_users).through(:relationships) } it { should have_many(:reverse_relationships).class_name("Relationship") .dependent(:destroy) } it { should have_many(:followers).through(:reverse_relationships) } end describe "model attributes" do it { should respond_to(:Name) } it { should respond_to(:email) } it { should respond_to(:password_digest) } it { should respond_to(:remember_token) } it { should respond_to(:admin) } it { should respond_to(:microposts) } it { should respond_to(:relationships) } it { should respond_to(:followed_users) } it { should respond_to(:reverse_relationships) } it { should respond_to(:followers) } end describe "virtual attributes and methods from has_secure_password" do it { should respond_to(:password) } it { should respond_to(:password_confirmation) } it { should respond_to(:authenticatE) } end describe "accessible attributes" do it { should_not allow_mass_assignment_of(:password_digest) } it { should_not allow_mass_assignment_of(:remember_token) } it { should_not allow_mass_assignment_of(:admin) } end describe "instance methods" do it { should respond_to(:feed) } it { should respond_to(:following?) } it { should respond_to(:follow!) } it { should respond_to(:unfollow!) } end describe "initial state" do it { should be_valid } it { should_not be_admin } its(:remember_token) { should_not be_blank } its(:email) { should_not =~ /\p{Upper}/ } end describe "validations" do context "for name" do it { should validate_presence_of(:Name) } it { should_not allow_value(" ").for(:Name) } it { should ensure_length_of(:Name).is_at_most(50) } end context "for email" do it { should validate_presence_of(:email) } it { should_not allow_value(" ").for(:email) } it { should validate_uniqueness_of(:email).case_insensitive } context "when email format is invalid" do addresses = %w[user@foo,com user_at_foo.org example.user@foo.] addresses.each do |invalid_address| it { should_not allow_value(invalid_address).for(:email) } end end context "when email format is valid" do addresses = %w[user@foo.COM A_US-ER@f.b.org frst.lst@foo.jp a+b@baz.cn] addresses.each do |valid_address| it { should allow_value(valid_address).for(:email) } end end end context "for password" do it { should ensure_length_of(:password).is_at_least(6) } it { should_not allow_value(" ").for(:password) } context "when password doesn't match confirmation" do it { should_not allow_value("mismatch").for(:password) } end end context "for password_confirmation" do it { should validate_presence_of(:password_confirmation) } end end # ... end

关于这些测试的一些具体问题:

>是否值得测试数据库模式? StackOverflow answer mentioned above中的评论说:“我只测试与行为相关的事情,我不认为存在列或索引行为.除非有人故意删除它们,否则数据库列不会消失,而是可以防止与代码审查和信任“,我同意,但有什么有效的原因为什么数据库模式的结构将被测试,从而证明存在的Shoulda :: Matchers :: ActiveRecord模块?也许只是重要的指标值得测试?
>应该在“关联”下应该有__any测试替换它们相应的应该在“模型属性”下进行测试?我不知道应该有__any测试只是在模型文件中查找相关的has_many声明,或者实际上执行与respond_to相同的功能.
>您有任何其他意见/建议,使这些测试更简洁/可读/彻底,内容和结构?

解决方法

1)Shoulda :: Matchers :: ActiveRecord模块在其中比只有列和索引匹配器更多.我会在 included classes稍微挖一圈,看看你能找到什么.这是have_many,belongs_to等来自哪里.对于记录来说,在大部分的内容中,我看不到什么价值.

2)是的,诸如has_many之类的宏比一个模型是否响应一个方法测试的更多.从source code起,你可以看到它正在测试的内容:

@H_874_6@def matches?(subject) @subject = subject association_exists? && macro_correct? && foreign_key_exists? && through_association_valid? && dependent_correct? && class_name_correct? && order_correct? && conditions_correct? && join_table_exists? && validate_correct? end

3)使测试更可读和/或简洁绝对是一个主观问题来回答.每个人都会给你一个不同的答案,这取决于他们的背景和经验.我会亲自摆脱所有的respond_to测试,并用具有价值的测试代替它们.当有人看着你的测试时,他们应该能够理解该类的公共API.当我看到你的对象响应“像以下”一样的时候,我可以做出假设,但是真的不知道这是什么意思.是否有争议?它是否返回一个布尔值?对象跟着什么还是跟着对象的东西?

大佬总结

以上是大佬教程为你收集整理的ruby-on-rails – 使用Shoulda对Rails模型重构rspec测试全部内容,希望文章能够帮你解决ruby-on-rails – 使用Shoulda对Rails模型重构rspec测试所遇到的程序开发问题。

如果觉得大佬教程网站内容还不错,欢迎将大佬教程推荐给程序员好友。

本图文内容来源于网友网络收集整理提供,作为学习参考使用,版权属于原作者。
如您有任何意见或建议可联系处理。小编QQ:384754419,请注明来意。