ruby-on-rails - RSpec PostgreSQL 结果不一致运行所有/单个测试
问题描述
我在使用 PostgreSQL 数据库测试我的应用程序时遇到了问题。在我们当前的设置中,我们使用 PostgreSQL 作为我们的生产环境,使用 SQLite3 作为我们的开发和测试环境。因为这可能导致意外行为,所以开发和测试环境需要切换到 PostgreSQL。
切换测试环境是最困难的部分。一些测试在运行单个规范文件时运行正确,但在使用 Guard 一起运行所有测试时失败。在我的开发中手动运行测试时,它的行为符合预期。
这是一个例子。失败的测试是我切换到第二个用户并测试@items 是否包含任何内容的最后一个测试。它返回一个空的空数组。
# /spec/controllers/materials_controller_spec.rb
describe MaterialsController do
def create_users
@user_1 = FactoryBot.create(:user)
@user_2 = FactoryBot.create(:user)
@admin = FactoryBot.create(:super_admin)
@private_group = Group.find_or_create_by(name: "Private")
@shared_group = Group.find_or_create_by(name: "Shared")
@project_group = Group.find_or_create_by(name: "Project")
@project = FactoryBot.create(:project)
@user_1.projects << @project
@user_2.projects << @project
sign_in @user_1
end
def create_my_private_material
@my_private_material = FactoryBot.create(:material, user: @user_1, group: @private_group, name: "Test01")
end
def create_my_private_material_2
@my_private_material_2 = FactoryBot.create(:material, user: @user_1, group: @private_group)
end
def create_your_private_material
@your_private_material = FactoryBot.create(:material, user: @user_2, group: @private_group)
end
def create_my_project_material
@my_project_material = FactoryBot.create(:material, user: @user_1, group: @project_group, project: @project)
end
def create_your_shared_material
@your_shared_material = FactoryBot.create(:material, user: @user_2, group: @shared_group)
end
def create_all_materials
create_my_private_material
create_my_private_material_2
create_your_private_material
create_my_project_material
create_your_shared_material
end
describe "GET #index" do
before do
create_users
create_all_materials
end
context "as material owner" do
it "renders the index template" do
get :index
expect(assigns(:items)).to contain_exactly(@my_project_material, @my_private_material_2, @my_private_material)
expect(response).to render_template("index")
end
end
context "as being the owner and a current project set using the project scope" do
before do
@user_1.current_project_id = @project.id
@user_1.save
end
it "should assing only the the materials the belong to the current project" do
get :index, params: { scope: 'project' }
expect(assigns(:items)).to contain_exactly(@my_project_material)
end
end
context "as not being the material owner and no default project" do
before do
sign_out @user_1
sign_in @user_2
end
it "filters out the materials based on group and project" do
get :index
expect(assigns(:items)).to contain_exactly(@your_private_material, @your_shared_material)
end
end
context "as not being the owner, with a current project and using the project scope" do
before do
@user_2.current_project_id = @project.id
@user_2.save
sign_out @user_1
sign_in @user_2
end
it "should assign only the materials the belong to the project" do
get :index, params: { scope: 'project', project_id: @project.id }
expect(assigns(:items)).to contain_exactly(@my_project_material)
end
end
end
我做了一些调试,发现了几件事:
- 运行所有测试时,测试中的错误是一致的。
- 添加
DatabaseCleaner.clean_with :truncation
before 块似乎可以修复一些测试。 - 更改允许到测试数据库的连接数
1
确实适用于控制器测试,但在我的功能测试中是一个问题,因为它似乎至少需要连接。
所以这个问题似乎与 PostgreSQL 数据库能够处理多个请求的优势有关。但是我不明白运行一个测试会通过但运行所有测试会失败一些测试。我在互联网上四处搜索以找到类似的相关问题,但可以找到任何好的帖子或问题。
如果需要,我可以发布也失败的不同测试,但我认为这都与同一个问题有关。
有什么建议么?
解决方案
推荐阅读
- python - PYQT5 QMainWindow setCentralWidget 由多个框布局组成
- jquery - 多个引导轮播不会同时进行
- scala - 如何在 Scala 中将字符串读取为多边形(在 Databricks 上)
- amazon-web-services - 将 StackName 附加到 Cloudformation 资源
- wcf - wcf - 如何处理具有共享相同操作的多个端点的服务
- react-native - 在移动设备上注销 Okta 托管的登录页面(React Native)
- python - 获取数据框列表并按变量分组,并使用该变量作为字典的键
- python - 用opencv找到相机中心
- python - 无法将 Keras 模型转换为 tflite
- git - Git在某个提交的文件中搜索字符串