Разрешить выполнение запросов Ecto немедленно в тестовой среде?
Я хотел бы написать тесты для проверки того, что запросы SQL в моем приложении возвращают данные, соответствующие определенным ограничениям: а именно, что возвращаемые значения представлены в порядке убывания вставки. В приложении я использую timestamps()
в моих схемах включить inserted_at
поле к БД, и запросы к нему в моих запросах (SELECT … ORDER BY inserted_at DESC
).
Моя проблема возникает в моих тестах: если у меня есть тестовый код, как
person1_params = %{name: "Tidehunter"}
{:ok, tidehunter} = People.create_person(person1_params)
person2_params = %{name: "Kunkka"}
{:ok, kunkka} = People.create_person(person2_params)
person3_params = %{name: "Windrunner"}
{:ok, windrunner} = People.create_person(person3_params)
и я хотел бы отстаивать их порядок, как
people = People.get_in_order_of_recency()
assert Enum.at(people, 0).name == "Windrunner"
это терпит неудачу, хотя в ручных тестах все это, кажется, работает. При осмотре я вижу, что inserted_at
для всех трех записей одинаково. Я пытался добавить :timer.sleep()
звонки, но это не меняет результат, предлагая некоторую группировку или лень на уровне Ecto/Postgrex.
"Самое простое" решение, о котором я мог подумать, - это какой-то способ "заставить" транзакцию произойти на месте вызова, чтобы я мог :timer.sleep(1)
между ними, давая мне отчетливый inserted_at
поля (таким образом, название вопроса), но рискуя проблемой XY, я открыт для других предложений. Спасибо!
2 ответа
Поскольку кажется, что вы пытаетесь протестировать метод get_in_order_of_recency, а не функции datetime вашей базы данных / ecto, вы можете использовать псевдоним <MYPROJ>.Repo
а затем сделать что-то вроде:
Repo.insert!(%People{inserted_at: ~N[2019-01-01 00:00:10], name: "Tidehunter"})
Repo.insert!(%People{inserted_at: ~N[2019-01-01 00:00:11], name: "Kunkka"})
Repo.insert!(%People{inserted_at: ~N[2019-01-01 00:00:12], name: "Windrunner"})
В вашем тесте вместо использования интерфейса создания. Что позволит вам убедиться, что ваш метод правильно извлекает людей в нужном вам порядке.
В качестве альтернативы, сочтите тестовый сбой законным. Ваш желаемый порядок не сохраняется, когда несколько записей вводятся одновременно. В качестве исправления добавьте идентификатор в качестве второго столбца для упорядочения в порядке убывания, что обеспечит соблюдение порядка, который вы ищете.
Вы тестируете Ecto
и ваш драйвер SQL. Вы не должны этого делать, это бессмысленно.
Единственное, что вы можете проверить здесь (хотя я уверен, что это также избыточно), это то, что inserted_at
поле заполняется.
Ecto.Query.order_by/3
работает; если вы не доверяете этому, вам лучше использовать какую-нибудь другую библиотеку.