Skip to content

Commit

Permalink
Add missing docs and specs. Closes #5
Browse files Browse the repository at this point in the history
  • Loading branch information
kipcole9 committed Aug 3, 2021
1 parent 29fdfcd commit 0f85246
Show file tree
Hide file tree
Showing 6 changed files with 190 additions and 28 deletions.
8 changes: 8 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,13 @@
# Changelog

## Cldr_Currencies v2.11.1

This is the changelog for Cldr_Currencies v2.11.1 released on August 4th, 2021. For older changelogs please consult the release tag on [GitHub](https://github.com/elixir-cldr/cldr_currencies/tags)

### Bug Fixes

* Add missing docs and specs. Thanks to @tcitworld for the report. Closes #5.

## Cldr_Currencies v2.11.0

This is the changelog for Cldr_Currencies v2.11.0 released on July 1st, 2021. For older changelogs please consult the release tag on [GitHub](https://github.com/elixir-cldr/cldr_currencies/tags)
Expand Down
182 changes: 167 additions & 15 deletions lib/cldr/currency.ex
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,8 @@ defmodule Cldr.Currency do

@type filter :: list(currency_status | code) | currency_status | code

@type territory :: atom() | String.t()

@type t :: %__MODULE__{
code: code,
alt_code: code,
Expand Down Expand Up @@ -53,8 +55,6 @@ defmodule Cldr.Currency do
from: nil,
to: nil

alias Cldr.LanguageTag

@table_options [:set, {:read_concurrency, true}]
@default_options [quiet: true]

Expand Down Expand Up @@ -636,6 +636,37 @@ defmodule Cldr.Currency do
@territory_currencies
end

@doc """
Returns a list of currencies associated with
a given territory.
## Arguments
* `territory` is any valid ISO 3166 Alpha-2 territory code.
See `Cldr.validate_territory/1`.
## Returns
* `{:ok, map}` where `map` has as its key a `t:Cldr.Currency`
struct and the value is a map of validity dates for that
currency; or
* `{:error, {exception, reason}}`
## Example
iex> Cldr.Currency.territory_currencies(:LT)
{:ok, %{
EUR: %{from: ~D[2015-01-01], to: nil},
LTL: %{from: nil, to: ~D[2014-12-31]},
LTT: %{from: nil, to: ~D[1993-06-25]},
SUR: %{from: nil, to: ~D[1992-10-01]}
}}
"""
@spec territory_currencies(territory()) ::
{:ok, map()} | {:error, {module(), String.t()}}

def territory_currencies(territory) do
with {:ok, territory} <- Cldr.validate_territory(territory),
{:ok, currencies} <- Map.fetch(territory_currencies(), territory) do
Expand All @@ -650,6 +681,36 @@ defmodule Cldr.Currency do
end
end

@doc """
Returns a list of currencies associated with
a given territory.
## Arguments
* `territory` is any valid ISO 3166 Alpha-2 territory code.
See `Cldr.validate_territory/1`.
## Returns
* `map` where `map` has as its key a `t:Cldr.Currency`
struct and the value is a map of validity dates for that
currency; or
* raises an exception
## Example
iex> Cldr.Currency.territory_currencies!(:LT)
%{
EUR: %{from: ~D[2015-01-01], to: nil},
LTL: %{from: nil, to: ~D[2014-12-31]},
LTT: %{from: nil, to: ~D[1993-06-25]},
SUR: %{from: nil, to: ~D[1992-10-01]}
}
"""
@spec territory_currencies!(territory()) :: map() | no_return()

def territory_currencies!(territory) do
case territory_currencies(territory) do
{:ok, currencies} -> currencies
Expand Down Expand Up @@ -776,7 +837,7 @@ defmodule Cldr.Currency do
## Arguments
* `currency_or_currency_code` is a `binary` or `atom` representation
of an ISO 4217 currency code, or a `%Cldr.Currency{}` struct.
of an ISO 4217 currency code, or a `t:Cldr.Currency` struct.
* `backend` is any module that includes `use Cldr` and therefore
is a `Cldr` backend module
Expand Down Expand Up @@ -1092,7 +1153,7 @@ defmodule Cldr.Currency do
"""
@spec currency_strings!(
Cldr.LanguageTag.t() | Cldr.Locale.locale_name(),
LanguageTag.t() | Locale.locale_name(),
only :: filter(),
except :: filter()
) ::
Expand Down Expand Up @@ -1137,6 +1198,9 @@ defmodule Cldr.Currency do
["au$", "aud", "澳大利亚元"]
"""
@spec strings_for_currency(t(), LanguageTag.t | Locale.locale_name, Cldr.backend) ::
[String.t()]

def strings_for_currency(currency, locale, backend) do
module = Module.concat(backend, Currency)

Expand All @@ -1153,7 +1217,7 @@ defmodule Cldr.Currency do
## Arguments
* `currency` is a `Cldr.Currency.t`, a list of `Cldr.Currency.t` or a
* `currency` is a `t:Cldr.Currency`, a list of `t:Cldr.Currency` or a
map where the values of each item is a `Cldr.Currency.t`
* `only` is `:all`, `:current`, `:historic`, `:tender`
Expand All @@ -1166,7 +1230,7 @@ defmodule Cldr.Currency do
## Currency Status
A currency may be in current use, of historic interest only. It
A currency may be in current use or of historic interest only. It
may or may not be legal tender. And it may mostly be used as a financial
instrument. To help return the most useful currencies the
currency status code acts as follows:
Expand All @@ -1185,11 +1249,7 @@ defmodule Cldr.Currency do
financial instruments.
"""
@spec currency_filter(
Cldr.Currency.t() | [Cldr.Currency.t()] | map(),
Cldr.Currency.currency_status()
) :: list(Cldr.Currency.t())

@spec currency_filter(t() | [t()] | map(), currency_status()) :: list(t())
def currency_filter(currencies, only \\ :all, except \\ nil)

def currency_filter(currencies, :all, nil) do
Expand Down Expand Up @@ -1219,15 +1279,15 @@ defmodule Cldr.Currency do
expand_filter(currencies, :only, only) -- expand_filter(currencies, :except, except)
end

def expand_filter(currencies, :only, [:all]) do
defp expand_filter(currencies, :only, [:all]) do
currencies
end

def expand_filter(_currencies, :except, [nil]) do
defp expand_filter(_currencies, :except, [nil]) do
[]
end

def expand_filter(currencies, _, filter_list) do
defp expand_filter(currencies, _, filter_list) do
Enum.flat_map(filter_list, fn filter ->
case filter do
:historic ->
Expand Down Expand Up @@ -1264,29 +1324,120 @@ defmodule Cldr.Currency do
|> Enum.uniq()
end

@doc """
Returns a boolean indicating if a given
currency is historic.
Historic means that the currency is no longer
in use.
## Arguments
* `currency` is a `t:Cldr.Currency`
## Returns
* `true` or `false`
"""
@spec historic?(currency :: t()) :: boolean()
def historic?(%Cldr.Currency{} = currency) do
is_nil(currency.iso_digits) ||
(is_integer(currency.to) && currency.to < Date.utc_today().year)
end

@doc """
Returns a boolean indicating if a given
currency is legal tender.
Legal tender is anything recognized by law
as a means to settle a public or private debt or
meet a financial obligation.
## Arguments
* `currency` is a `t:Cldr.Currency`
## Returns
* `true` or `false`
"""
@spec tender?(currency :: t()) :: boolean()
def tender?(%Cldr.Currency{} = currency) do
!!currency.tender
end

@doc """
Returns a boolean indicating if a given
currency is current.
Current means that the currency is in current
use.
## Arguments
* `currency` is a `t:Cldr.Currency`
## Returns
* `true` or `false`
"""
@spec current?(currency :: t()) :: boolean()
def current?(%Cldr.Currency{} = currency) do
!is_nil(currency.iso_digits) && is_nil(currency.to)
end

@doc """
Returns a boolean indicating if a given
currency is annotated.
Annotated means that the currency description
has annotations (comments inside parenthesis).
This is mostly found in currency codes used as
financial instruments (not legal tender).
## Arguments
* `currency` is a `t:Cldr.Currency`
## Returns
* `true` or `false`
"""
@spec annotated?(currency :: t()) :: boolean()
def annotated?(%Cldr.Currency{} = currency) do
String.contains?(currency.name, "(")
end

@doc """
Returns a boolean indicating if a given
currency is unannotated.
Annotated means that the currency description
has annotations (comments inside parenthesis).
This is mostly found in currency codes used as
financial instruments (not legal tender).
## Arguments
* `currency` is a `t:Cldr.Currency`
## Returns
* `true` or `false`
"""
@spec unannotated?(currency :: t()) :: boolean()
def unannotated?(%Cldr.Currency{} = currency) do
!String.contains?(currency.name, "(")
!annotated?(currency)
end

# Sort the list by string. If the string is the same
# then sort historic currencies after the current one

@doc false
def string_comparator({k, v1}, {k, v2}, currencies) do
cond do
Expand All @@ -1313,6 +1464,7 @@ defmodule Cldr.Currency do

# The strategy is to remove the duplicate string from the
# currency that is historic.

@doc false
def remove_duplicate_strings(strings, currencies) do
strings
Expand Down
8 changes: 5 additions & 3 deletions lib/cldr/eternal.ex
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@ defmodule Cldr.Eternal do
alias Cldr.Eternal.Table
alias Cldr.Eternal.Supervisor, as: Sup

@type table :: number | atom

# Return values of `start_link` functions
@type on_start ::
{:ok, pid} | :ignore | {:error, {:already_started, pid} | {:shutdown, term} | term}
Expand Down Expand Up @@ -93,7 +95,7 @@ defmodule Cldr.Eternal do
iex> Cldr.Eternal.heir(:my_table)
"""
@spec heir(table :: Table.t()) :: any()
@spec heir(table :: table()) :: any()
def heir(table) when is_table(table),
do: :ets.info(table, :heir)

Expand All @@ -105,7 +107,7 @@ defmodule Cldr.Eternal do
iex> Cldr.Eternal.owner(:my_table)
"""
@spec owner(table :: Table.t()) :: any()
@spec owner(table :: table()) :: any()
def owner(table) when is_table(table),
do: :ets.info(table, :owner)

Expand All @@ -120,7 +122,7 @@ defmodule Cldr.Eternal do
:ok
"""
@spec stop(table :: Table.t()) :: :ok
@spec stop(table :: table()) :: :ok
def stop(table) when is_table(table) do
name = Table.to_name(table)
proc = GenServer.whereis(name)
Expand Down
14 changes: 7 additions & 7 deletions lib/cldr/eternal/table.ex
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,11 @@ defmodule Cldr.Eternal.Table do
@type t :: number | atom

@doc """
Converts a table name to a valid Supervisor name.
Because tables can be integer references, we convert this to an atom only if
the `create` flag is set to true. Otherwise, we attempt to convert to an existing
name (as it should have already been created).
Converts a table name to a valid Supervisor name.
Because tables can be integer references, we convert this to an atom only if
the `create` flag is set to true. Otherwise, we attempt to convert to an existing
name (as it should have already been created).
"""
@spec to_name(name :: number | atom, create :: true | false) :: name :: atom | nil
def to_name(name, create \\ false)
Expand All @@ -35,8 +35,8 @@ defmodule Cldr.Eternal.Table do
end

@doc """
Determines whether a value is a table or not. Tables can be either atoms or
integer values.
Determines whether a value is a table or not. Tables can be either atoms or
integer values.
"""
defmacro is_table(val) do
quote do
Expand Down
2 changes: 1 addition & 1 deletion mix.exs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
defmodule Cldr.Currencies.MixProject do
use Mix.Project

@version "2.11.0"
@version "2.11.1"

def project do
[
Expand Down
Loading

0 comments on commit 0f85246

Please sign in to comment.