Membership Fee Type Resource & Settings closes #278 #291
1 changed files with 45 additions and 19 deletions
|
|
@ -50,14 +50,47 @@ defmodule Mv.MembershipFees.CalendarCycles do
|
||||||
|
|
||||||
## Parameters
|
## Parameters
|
||||||
|
|
||||||
- `date` - The date for which to find the cycle start (used as default if `reference_date` not provided)
|
- `date` - Ignored in this 3-argument version (kept for API consistency)
|
||||||
- `interval` - The interval type (`:monthly`, `:quarterly`, `:half_yearly`, `:yearly`)
|
- `interval` - The interval type (`:monthly`, `:quarterly`, `:half_yearly`, `:yearly`)
|
||||||
- `reference_date` - The reference date to use for calculation (defaults to `date`)
|
- `reference_date` - The date used to determine which cycle to calculate
|
||||||
|
|
||||||
## Returns
|
## Returns
|
||||||
|
|
||||||
The start date of the cycle containing the reference date.
|
The start date of the cycle containing the reference date.
|
||||||
|
|
||||||
|
## Examples
|
||||||
|
|
||||||
|
iex> Mv.MembershipFees.CalendarCycles.calculate_cycle_start(~D[2024-03-15], :monthly, ~D[2024-05-20])
|
||||||
|
~D[2024-05-01]
|
||||||
|
|
||||||
|
iex> Mv.MembershipFees.CalendarCycles.calculate_cycle_start(~D[2024-03-15], :quarterly, ~D[2024-05-20])
|
||||||
|
~D[2024-04-01]
|
||||||
|
"""
|
||||||
|
@spec calculate_cycle_start(Date.t(), interval(), Date.t()) :: Date.t()
|
||||||
|
def calculate_cycle_start(_date, interval, reference_date) do
|
||||||
|
case interval do
|
||||||
|
:monthly -> monthly_cycle_start(reference_date)
|
||||||
|
:quarterly -> quarterly_cycle_start(reference_date)
|
||||||
|
:half_yearly -> half_yearly_cycle_start(reference_date)
|
||||||
|
:yearly -> yearly_cycle_start(reference_date)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
@doc """
|
||||||
|
Calculates the start date of the cycle that contains the given date.
|
||||||
|
|
||||||
|
This is a convenience function that calls `calculate_cycle_start/3` with `date` as both
|
||||||
|
the input and reference date.
|
||||||
|
|
||||||
|
## Parameters
|
||||||
|
|
||||||
|
- `date` - The date used to determine which cycle to calculate
|
||||||
|
- `interval` - The interval type (`:monthly`, `:quarterly`, `:half_yearly`, `:yearly`)
|
||||||
|
|
||||||
|
## Returns
|
||||||
|
|
||||||
|
The start date of the cycle containing the given date.
|
||||||
|
|
||||||
## Examples
|
## Examples
|
||||||
|
|
||||||
iex> Mv.MembershipFees.CalendarCycles.calculate_cycle_start(~D[2024-03-15], :monthly)
|
iex> Mv.MembershipFees.CalendarCycles.calculate_cycle_start(~D[2024-03-15], :monthly)
|
||||||
|
|
@ -71,20 +104,7 @@ defmodule Mv.MembershipFees.CalendarCycles do
|
||||||
|
|
||||||
iex> Mv.MembershipFees.CalendarCycles.calculate_cycle_start(~D[2024-12-15], :yearly)
|
iex> Mv.MembershipFees.CalendarCycles.calculate_cycle_start(~D[2024-12-15], :yearly)
|
||||||
~D[2024-01-01]
|
~D[2024-01-01]
|
||||||
|
|
||||||
iex> Mv.MembershipFees.CalendarCycles.calculate_cycle_start(~D[2024-03-15], :monthly, ~D[2024-05-20])
|
|
||||||
~D[2024-05-01]
|
|
||||||
"""
|
"""
|
||||||
@spec calculate_cycle_start(Date.t(), interval(), Date.t()) :: Date.t()
|
|
||||||
def calculate_cycle_start(_date, interval, reference_date) do
|
|
||||||
case interval do
|
|
||||||
:monthly -> monthly_cycle_start(reference_date)
|
|
||||||
:quarterly -> quarterly_cycle_start(reference_date)
|
|
||||||
:half_yearly -> half_yearly_cycle_start(reference_date)
|
|
||||||
:yearly -> yearly_cycle_start(reference_date)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
@spec calculate_cycle_start(Date.t(), interval()) :: Date.t()
|
@spec calculate_cycle_start(Date.t(), interval()) :: Date.t()
|
||||||
def calculate_cycle_start(date, interval) do
|
def calculate_cycle_start(date, interval) do
|
||||||
calculate_cycle_start(date, interval, date)
|
calculate_cycle_start(date, interval, date)
|
||||||
|
|
@ -203,7 +223,13 @@ defmodule Mv.MembershipFees.CalendarCycles do
|
||||||
end
|
end
|
||||||
|
|
||||||
@doc """
|
@doc """
|
||||||
Checks if the cycle was just completed (ended before or on the given date, but is the most recent completed cycle).
|
Checks if the cycle is the last completed cycle.
|
||||||
|
|
||||||
|
A cycle is considered the last completed cycle if:
|
||||||
|
- The cycle has ended (cycle_end < today)
|
||||||
|
- The next cycle has not ended yet (today <= next_end)
|
||||||
|
|
||||||
|
In other words: `cycle_end < today <= next_end`
|
||||||
|
|
||||||
## Parameters
|
## Parameters
|
||||||
|
|
||||||
|
|
@ -213,7 +239,7 @@ defmodule Mv.MembershipFees.CalendarCycles do
|
||||||
|
|
||||||
## Returns
|
## Returns
|
||||||
|
|
||||||
`true` if the cycle ended before or on the given date and is the last completed cycle, `false` otherwise.
|
`true` if the cycle is the last completed cycle, `false` otherwise.
|
||||||
|
|
||||||
## Examples
|
## Examples
|
||||||
|
|
||||||
|
|
@ -230,11 +256,11 @@ defmodule Mv.MembershipFees.CalendarCycles do
|
||||||
def last_completed_cycle?(cycle_start, interval, today) do
|
def last_completed_cycle?(cycle_start, interval, today) do
|
||||||
cycle_end = calculate_cycle_end(cycle_start, interval)
|
cycle_end = calculate_cycle_end(cycle_start, interval)
|
||||||
|
|
||||||
# Cycle must have ended (before or on the given date)
|
# Cycle must have ended (cycle_end < today)
|
||||||
case Date.compare(today, cycle_end) do
|
case Date.compare(today, cycle_end) do
|
||||||
:gt ->
|
:gt ->
|
||||||
# Check if this is the most recent completed cycle
|
# Check if this is the most recent completed cycle
|
||||||
# by verifying that the next cycle hasn't ended yet
|
# by verifying that the next cycle hasn't ended yet (today <= next_end)
|
||||||
next_start = next_cycle_start(cycle_start, interval)
|
next_start = next_cycle_start(cycle_start, interval)
|
||||||
next_end = calculate_cycle_end(next_start, interval)
|
next_end = calculate_cycle_end(next_start, interval)
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue