ollien

ollien

Using Timex in a unit test

I run my unit tests with mix test --no-start, as I don’t want my application to start when I run my unit tests. However, I also want to test some code that uses Timex for a calculation. If I naively attempt to use Timex in my test, I get the following

    test "can get next instance of time in a trivial instance" do
      next_occurrence =
        Util.Time.get_next_occurrence_of_time(~D[2022-01-01], ~T[13:37:00], "America/New_York")

      assert next_occurrence == Timex.to_datetime({{2022, 1, 1}, {13, 37, 0}}, "America/New_York")
    end
  1) test get_next_occurrence_of_time can get next instance of time in a trivial instance (PillminderTest.Util.Time)
     test/pillminder/util/time_test.exs:8
     ** (ArgumentError) errors were found at the given arguments:
     
       * 1st argument: the table identifier does not refer to an existing ETS table
     
     code: assert next_occurrence == Timex.to_datetime({{2022, 1, 1}, {13, 37, 0}}, "America/New_York")
     stacktrace:
       (stdlib 3.17.2.1) :ets.lookup(:tzdata_current_release, :release_version)
       (tzdata 1.1.1) lib/tzdata/release_reader.ex:74: Tzdata.ReleaseReader.current_release_from_table/0
       (tzdata 1.1.1) lib/tzdata/release_reader.ex:17: Tzdata.ReleaseReader.simple_lookup/1
       (tzdata 1.1.1) lib/tzdata/release_reader.ex:9: Tzdata.ReleaseReader.zone_and_link_list/0
       (tzdata 1.1.1) lib/tzdata.ex:61: Tzdata.zone_exists?/1
       (timex 3.7.9) lib/timezone/timezone.ex:230: Timex.Timezone.name_of/1
       (timex 3.7.9) lib/timezone/timezone.ex:262: Timex.Timezone.get/2
       (timex 3.7.9) lib/timezone/timezone.ex:585: Timex.Timezone.convert/2
       (timex 3.7.9) lib/datetime/erlang.ex:46: Timex.Protocol.Tuple.to_datetime/2
       test/pillminder/util/time_test.exs:12: (test)

I can understand why this might be; tzdata likely needs to be started in order to read from this ETS table. I’m not sure the best way to fix this, because

  1. If I remove --no-start, my application will start, which has side effects I don’t want to produce just by running my unit tests.
  2. Even if I somehow prevent my application from running (is there a way?), but allow Timex to run tzdata, I’m still going to have side effects in my tests, Timex will need to update the timezone database before running my tests; I try to keep my unit tests free of network calls wherever I can.

How can I best deal with this? Is perhaps there some way I can “mock” the tzdata, or somehow pre-seed it for my unit tests?

Thanks!

Marked As Solved

ollien

ollien

Thanks for the suggestions! Looking at the tzdata docs it turns out you can also store the ets table locally, so I checked that into a testdata directory (originally in ./deps/tzdata/priv) and then added the following to test.exs

import Config

config :tzdata,
  data_dir: "./test/testdata/tzdata",
  autoupdate: :disabled,
  # Definitely a hack, but tzdata uses this key to determine which http client it uses, so if it
  # actually tries to use hackney, it will get an error
  http_client: nil

and made added Application.ensure_all_started(:tzdata) to my test setup.

Also Liked

trisolaran

trisolaran

Hi @ollien and welcome!

You should be able to turn off tzdata automatic updates in your tests by setting:

config :tzdata, :autoupdate, :disabled

in your test.exs config (GitHub - lau/tzdata: tzdata for Elixir. Born from the Calendar library.)

Btw: you can now do time zone conversions directly in Elixir with the tzdata library without Timex: GitHub - lau/tzdata: tzdata for Elixir. Born from the Calendar library.

Where Next?

Popular in Questions Top

JDanielMartinez
Hi! May someone helps me, please! I have two apps into an umbrella project: the first one is Database, which manages queries, and the se...
New
gshaw
What is the idiomatic way of matching for not nil in Elixir? E.g., First way: defp halt_if_not_signed_in(conn, signed_in_account) when...
New
lk-geimfari
What is most correct way to open, read and parse JSON file with poison? For example if we have example.json file in root of some projec...
New
vertexbuffer
Hello, can anybody help here..? I have a list of players and I what to delete an element, but every for loop the list is reverting to ori...
New
chensan
I have a User schema with a :from_id field set to type :string: defmodule TweetBot.Repo.Migrations.CreateUsers do use Ecto.Migration ...
New
fireproofsocks
Forgive me if this is obvious, but how does one delete a database record WITHOUT selecting it first? https://hexdocs.pm/ecto/Ecto.Repo.h...
New
johnnyicon
Hi all, I've just started learning Elixir and Phoenix Framework, so please pardon my n00bness at this stage. I'm trying to use Postg...
New
chrisalley
ExUnit now has describe blocks which is a welcome addition coming from RSpec. In the docs, it states that nested hierarchies of describe ...
New
Mooodi
Given a string, how can I get access to its character by index? Enum.at("my_string", 2) doesn't work. Or rather, not char, but a substr...
New
idi527
I’ve been re-reading swift book again and noticed that multiline strings there don’t have a trailing line break, unlike in elixir iex(2)...
New

Other popular topics Top

lessless
I believe there are people here who are dealing with CSV files import on the daily basis, and since Excel is a really popular tool there ...
New
albydarned
Hello all! I am typing this post from my new MacBook Pro with the M1 chip. I’m loving it so far, and will probably use it as my daily dr...
New
jononomo
I am trying to figure out how Mix knows whether the environment is test, dev, or prod -- where is this set? Thanks.
New
vac
Hi, I'm quite new in Elixir and I'm trying to format a string to a PEM format. I have the certificate value like MIIDBTCCAe2...... and ...
New
qwerescape
Is there a way to get the call stack or stack trace at any point in the code? Not from exceptions, but an expression that returns how the...
New
ovidiubadita
Hey all, I discovered Elixir and I love it. I always wanted to learn a functional programming and I intended to go for Haskell, but afte...
New
romenigld
I am trying to run a deploy with docker and I successfully runned with this command: docker build -t romenigld/blog-prod . but when I t...
New
Nvim
Elixir appears to be a superior language to Python. I don’t see any advantage of Python over Elixir. Are there any?
New
siddhant3030
Hi, I have to write a raw query for one of my project. But till now I have used ecto queries and don’t have much experience writing raw ...
New
vrod
I am using the Starship cross-shell prompt – it seems pretty nice, but I get some errors: [WARN] - (starship::utils): Executing command ...
New

We're in Beta

About us Mission Statement