Packages
tz
0.28.2
0.28.2
0.28.1
0.28.0
0.27.3
0.27.2
0.27.1
0.27.0
0.26.6
0.26.5
0.26.4
0.26.3
0.26.2
0.26.1
0.26.0
0.25.1
0.25.0
0.24.0
0.23.0
0.22.0
0.21.1
0.21.0
0.20.1
0.20.0
0.19.0
0.17.0
0.16.2
0.16.1
0.16.0
0.15.0
0.14.0
0.13.0
0.12.0
0.11.0
0.10.0
0.9.0
0.8.2
0.8.1
0.8.0
0.7.3
0.7.2
0.7.1
0.7.0
0.6.0
0.5.0
0.4.0
0.3.0
0.2.0
0.1.0
Time zone support for Elixir
Current section
Files
Jump to
Current section
Files
lib/tz/iana_data_dir.ex
defmodule Tz.IanaDataDir do
@moduledoc false
require Logger
def dir(), do: Application.get_env(:tz, :data_dir) || to_string(:code.priv_dir(:tz))
def forced_iana_version(), do: Application.get_env(:tz, :iana_version)
defp latest_dir_name([]), do: nil
defp latest_dir_name(dir_names) do
Enum.max(dir_names)
end
defp relevant_dir_name([]), do: nil
defp relevant_dir_name(dir_names) do
if forced_version = forced_iana_version() do
Enum.find(dir_names, &(&1 == "tzdata#{forced_version}"))
else
latest_dir_name(dir_names)
end
end
defp list_dir_names(parent_dir) do
File.ls!(parent_dir)
|> Enum.filter(&Regex.match?(~r/^tzdata20[0-9]{2}[a-z]$/, &1))
end
def latest_tzdata_dir_name() do
latest_dir_name(list_dir_names(dir()))
end
def relevant_tzdata_dir_name() do
relevant_dir_name(list_dir_names(dir()))
end
def latest_tzdata_dir_path() do
if dir_name = latest_dir_name(list_dir_names(dir())) do
Path.join(dir(), dir_name)
end
end
def relevant_tzdata_dir_path() do
if dir_name = relevant_dir_name(list_dir_names(dir())) do
Path.join(dir(), dir_name)
end
end
def latest_tzdata_version() do
if dir_name = latest_dir_name(list_dir_names(dir())) do
"tzdata" <> version = dir_name
version
end
end
def relevant_tzdata_version() do
if dir_name = relevant_dir_name(list_dir_names(dir())) do
"tzdata" <> version = dir_name
version
end
end
def maybe_copy_iana_files_to_custom_dir() do
cond do
# no custom dir
to_string(:code.priv_dir(:tz)) == dir() ->
nil
# tzdata dir already exists
relevant_tzdata_dir_path() ->
nil
true ->
lib_dir_names = list_dir_names(to_string(:code.priv_dir(:tz)))
cond do
lib_dir_name = relevant_dir_name(lib_dir_names) ->
File.cp_r!(
Path.join(:code.priv_dir(:tz), lib_dir_name),
Path.join(dir(), lib_dir_name)
)
Logger.info(
"Moved #{Path.join(:code.priv_dir(:tz), lib_dir_name)} to #{Path.join(dir(), lib_dir_name)}"
)
lib_dir_name = latest_dir_name(lib_dir_names) ->
app_dir_name = latest_tzdata_dir_name()
if !app_dir_name || app_dir_name < lib_dir_name do
File.cp_r!(
Path.join(:code.priv_dir(:tz), lib_dir_name),
Path.join(dir(), lib_dir_name)
)
Logger.info(
"Moved #{Path.join(:code.priv_dir(:tz), lib_dir_name)} to #{Path.join(dir(), lib_dir_name)}"
)
end
true ->
raise "tzdata files not found"
end
end
end
def extract_tzdata_into_dir(version, content, dir \\ dir()) do
tmp_archive_path = Path.join(dir, "tzdata#{version}.tar.gz")
tzdata_dir_name = "tzdata#{version}"
:ok = File.write!(tmp_archive_path, content)
files_to_extract = [
~c"africa",
~c"antarctica",
~c"asia",
~c"australasia",
~c"backward",
~c"etcetera",
~c"europe",
~c"northamerica",
~c"southamerica",
~c"iso3166.tab",
~c"zone1970.tab"
]
:ok =
:erl_tar.extract(tmp_archive_path, [
:compressed,
{:cwd, Path.join(dir, tzdata_dir_name) |> String.to_charlist()},
{:files, files_to_extract}
])
:ok = File.rm!(tmp_archive_path)
Path.join(dir, tzdata_dir_name)
end
def delete_tzdata_dir(version) do
if version != forced_iana_version() do
Path.join(dir(), "tzdata#{version}")
|> File.rm_rf!()
end
end
end