如何定义可被ex_machina的params_for识别的工厂?已定义却无法找到
问题原因
测试代码仅通过use ExMachina.Ecto引入基础功能,但未关联自定义的Booking.Factory模块。ExMachina默认只会在当前测试模块内查找工厂定义,无法识别外部Booking.Factory里的practitioner_factory函数。而IEx中能正常运行,是因为你直接通过Booking.Factory.practitioner_factory!明确指定了工厂所在模块,绕过了这个匹配逻辑。
解决方法
以下三种方式任选其一即可:
方法1:在测试模块中导入Factory模块
添加import Booking.Factory,让测试模块直接调用Factory内的工厂函数:
defmodule Booking.PractitionersTest do use ExUnit.Case, async: true use Booking.DataCase use ExMachina.Ecto import Booking.Factory alias Ecto.Changeset alias Booking.Practitioners.Practitioner test "is valid from the factory" do new_practitioner = params_for(:practitioner) changeset = Practitioner.changeset(Practitioner, new_practitioner) assert changeset.valid? end end
方法2:在测试模块中use自定义Factory
由于Booking.Factory已经集成了ExMachina.Ecto,测试模块可直接use Booking.Factory继承所有工厂功能:
defmodule Booking.PractitionersTest do use ExUnit.Case, async: true use Booking.DataCase use Booking.Factory alias Ecto.Changeset alias Booking.Practitioners.Practitioner test "is valid from the factory" do new_practitioner = params_for(:practitioner) changeset = Practitioner.changeset(Practitioner, new_practitioner) assert changeset.valid? end end
方法3:调用params_for时指定工厂模块
如果不想修改测试模块的引入语句,可在调用时明确指定Factory模块:
defmodule Booking.PractitionersTest do use ExUnit.Case, async: true use Booking.DataCase use ExMachina.Ecto alias Ecto.Changeset alias Booking.Practitioners.Practitioner test "is valid from the factory" do new_practitioner = Booking.Factory.params_for(:practitioner) changeset = Practitioner.changeset(Practitioner, new_practitioner) assert changeset.valid? end end
注:测试代码中第24行的Practitioner需要提前通过alias引入,否则会出现模块未定义错误,上述示例已补充该逻辑。
内容的提问来源于stack exchange,提问作者martins
相关产品推荐
相关产品推荐

