Я пытаюсь использовать Faker
в FactoryBot
в моих тестах Rails API.
Проблема, с которой я сталкиваюсь, продолжает вызывать эту ошибку:
KeyError:
Trait not registered: "first_name"
Пока что как я могу сказать, я все настроил правильно, по крайней мере, на основе документов Faker'd. Насколько я могу судить, у меня есть две фактические черты, valid_user
и invalid_user
, которые я установил так ...
let(:valid_attributes) { FactoryBot.attributes_for :api_v1_user, :valid_user }
let(:invalid_attributes) { FactoryBot.attributes_for :api_v1_user, :invalid_user }
, которые связаны с фабрикой :api_v1_user
.
Что я пропустил или сделал неправильно?
Полная ошибка:
8) /api/v1/users PATCH /update with invalid parameters renders a JSON response with errors for the api/v1_user
Failure/Error: let(:invalid_attributes) { FactoryBot.attributes_for(:api_v1_user, :invalid_user) }
KeyError:
Trait not registered: "first_name"
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/activesupport-6.0.2.2/lib/active_support/hash_with_indifferent_access.rb:191:in `fetch'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/activesupport-6.0.2.2/lib/active_support/hash_with_indifferent_access.rb:191:in `fetch'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/registry.rb:23:in `find'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/decorator.rb:10:in `method_missing'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/internal.rb:49:in `trait_by_name'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition.rb:114:in `trait_by_name'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition.rb:106:in `block in base_traits'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition.rb:106:in `map'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition.rb:106:in `base_traits'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition.rb:51:in `block in compile'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition.rb:50:in `compile'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition.rb:130:in `aggregate_from_traits_and_self'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition.rb:34:in `to_create'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/trait.rb:17:in `to_create'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition.rb:135:in `map'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition.rb:135:in `aggregate_from_traits_and_self'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition.rb:34:in `to_create'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/definition_hierarchy.rb:16:in `build_from_definition'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/factory.rb:125:in `build_hierarchy'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/factory.rb:88:in `compile'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/factory.rb:32:in `run'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/factory_runner.rb:29:in `block in run'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/activesupport-6.0.2.2/lib/active_support/notifications.rb:182:in `instrument'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/factory_runner.rb:28:in `run'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/factory_bot-5.1.2/lib/factory_bot/strategy_syntax_method_registrar.rb:20:in `block in define_singular_strategy_method'
# ./spec/requests/api/v1/users_spec.rb:6:in `block (2 levels) in <top (required)>'
# ./spec/requests/api/v1/users_spec.rb:92:in `block (4 levels) in <top (required)>'
# ./spec/rails_helper.rb:19:in `block (3 levels) in <top (required)>'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/database_cleaner-1.8.4/lib/database_cleaner/generic/base.rb:16:in `cleaning'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/database_cleaner-1.8.4/lib/database_cleaner/configuration.rb:87:in `block (2 levels) in cleaning'
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/database_cleaner-1.8.4/lib/database_cleaner/configuration.rb:88:in `cleaning'
# ./spec/rails_helper.rb:18:in `block (2 levels) in <top (required)>'
# ------------------
# --- Caused by: ---
# KeyError:
# key not found: "first_name"
# /home/etherk1ll/.rvm/gems/ruby-2.7.0/gems/activesupport-6.0.2.2/lib/active_support/hash_with_indifferent_access.rb:191:in `fetch'
spec/factories/api/v1/users.rb
Требуется «Факер»
FactoryBot.define do
factory :api_v1_user, class: 'Api::V1::User' do
trait :valid_user do
first_name { Faker::Name.first_name }
second_name { Faker::Name.second_name }
username { Faker::Internet.username }
email { Faker::Internet.safe_email }
password { Faker::Internet.password(min_length: 8) }
end
trait :invalid_user do
first_name nil
end
end
end
rails_helper.rb
# This file is copied to spec/ when you run 'rails generate rspec:install'
require 'spec_helper'
ENV['RAILS_ENV'] ||= 'test'
require File.expand_path('../config/environment', __dir__)
# Prevent database truncation if the environment is production
abort("The Rails environment is running in production mode!") if Rails.env.production?
require 'rspec/rails'
RSpec.configure do |config|
config.use_transactional_fixtures = false
DatabaseCleaner.strategy = :truncation
config.around(:each) do |example|
DatabaseCleaner.cleaning do
example.run
end
end
config.before(:all) do
DatabaseCleaner.start
end
config.after(:all) do
DatabaseCleaner.clean
end
end
users_spec.rb
Усечено
RSpec.describe "/api/v1/users", type: :request do
let(:valid_attributes) { FactoryBot.attributes_for :api_v1_user, :valid_user }
let(:invalid_attributes) { FactoryBot.attributes_for :api_v1_user, :invalid_user }
let(:valid_headers) {
{}
}
describe "PATCH /update" do
context "with invalid parameters" do
it "renders a JSON response with errors for the api/v1_user" do
user = Api::V1::User.create! valid_attributes
patch api_v1_user_url(user),
params: { api_v1_user: invalid_attributes }, headers: valid_headers, as: :json
expect(response).to have_http_status(:unprocessable_entity)
expect(response.content_type).to eq("application/json")
end
end
end
end