houdini/spec/lib/query/query_recurring_donations_spec.rb
Bradley M. Kuhn 6772312ea7 Relicense all .rb files under new project license.
The primary license of the project is changing to:
  AGPL-3.0-or-later WITH Web-Template-Output-Additional-Permission-3.0-or-later

with some specific files to be licensed under the one of two licenses:
   CC0-1.0
   LGPL-3.0-or-later

This commit is one of the many steps to relicense the entire codebase.

Documentation granting permission for this relicensing (from all past
contributors who hold copyrights) is on file with Software Freedom
Conservancy, Inc.
2018-03-25 15:10:40 -04:00

231 lines
10 KiB
Ruby

# License: AGPL-3.0-or-later WITH Web-Template-Output-Additional-Permission-3.0-or-later
require 'rails_helper'
# Note that the recurring donation used in these tests is created on 2020-01-01 and the first charge is created on that date
describe QueryRecurringDonations do
around(:each) {|example|
Timecop.freeze(2020, 4, 5) do
example.run
end
}
describe '.monthly_total' do
let(:nonprofit) {Qx.insert_into(:nonprofits).values(name: SecureRandom.uuid).ts.returning('*').execute.first}
let(:rec_dons) do
Qx.insert_into('recurring_donations').values([
{active: true, amount: 4000, interval: 1, time_unit: 'month'},
{active: true, amount: 1000, interval: 2, time_unit: 'week'},
{active: false, amount: 10000, interval: 1, time_unit: 'month'}
]).common_values({nonprofit_id: nonprofit['id']}).ts.returning("*").execute
end
it 'adds up the total for all active recurring donations' do
rec_dons
sum = QueryRecurringDonations.monthly_total(nonprofit['id'])
expect(sum).to eq(rec_dons[0]['amount'] + rec_dons[1]['amount'])
end
end
describe '.is_due?' do
let(:nonprofit) {force_create(:nonprofit)}
let(:supporter) {force_create(:supporter, nonprofit: nonprofit)}
let(:donation) {
force_create(:donation, amount: 1000, supporter: supporter, recurring: true, nonprofit: nonprofit)
}
let(:defaults) {{amount: 1000, interval: 1, time_unit: 'month', nonprofit: nonprofit, supporter: supporter, active: true, donation: donation}}
def create_recdon(params)
force_create(:recurring_donation, defaults.merge(params))
end
it 'when inactive, is not due' do
rd = create_recdon(active: false)
expect(QueryRecurringDonations.is_due?(rd.id)).to eq(false)
end
it 'when it hits max n_failures, is not due' do
rd = create_recdon(n_failures: 3)
expect(QueryRecurringDonations.is_due?(rd.id)).to eq(false)
end
it 'is due when it has no charges' do
rd = create_recdon({})
expect(QueryRecurringDonations.is_due?(rd.id)).to eq(true)
end
it 'is not due when it has a charge this month' do
rd = create_recdon({})
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'pending').ts.ex
expect(QueryRecurringDonations.is_due?(rd['id'])).to be false
end
it 'is due when it has charges && when monthly && not paid this month && not paid last month' do
rd = create_recdon({})
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'pending').ts.ex
Timecop.freeze(2.months.from_now) do
expect(QueryRecurringDonations.is_due?(rd['id'])).to be true
end
end
it 'is due when monthly && no paydate && last charge was last month && last charge created at day <= today' do
rd = create_recdon({})
Timecop.freeze(Time.parse("2020-01-01")) do
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'pending').ts.ex
end
Timecop.freeze(Time.parse("2020-02-01")) do
expect(QueryRecurringDonations.is_due?(rd['id'])).to be true
end
end
it 'is due when monthly && paydate present && last charge was last month && paydate <= today' do
rd = create_recdon({paydate: 10})
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'pending').ts.ex
Timecop.freeze(1.month.from_now.change(day: 10)) do
expect(QueryRecurringDonations.is_due?(rd['id'])).to be true
end
end
it 'is due when not monthly and the timespan is 3 days and it is 3 days later' do
rd = create_recdon({time_unit: 'day', interval: 3})
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'pending').ts.ex
Timecop.freeze(3.days.from_now) do
expect(QueryRecurringDonations.is_due?(rd['id'])).to be true
end
end
it 'is due when not monthly and the timespan is 2 weeks and it is 2 weeks later' do
rd = create_recdon({time_unit: 'week', interval: 2})
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'pending').ts.ex
Timecop.freeze(2.weeks.from_now) do
expect(QueryRecurringDonations.is_due?(rd['id'])).to be true
end
end
it 'is due when not monthly and the timespan is 1 year and it is 1 year later' do
rd = create_recdon({time_unit: 'year', interval: 1})
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'pending').ts.ex
Timecop.freeze(1.year.from_now) do
expect(QueryRecurringDonations.is_due?(rd['id'])).to be true
end
end
it 'is not due when not monthly and it is not a timespan later' do
rd = create_recdon({time_unit: 'day', interval: 3})
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'pending').ts.ex
Timecop.freeze(2.days.from_now) do
expect(QueryRecurringDonations.is_due?(rd['id'])).to be false
end
end
it 'is not due when monthly and has been paid this month' do
rd = create_recdon({})
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'pending').ts.ex
expect(QueryRecurringDonations.is_due?(rd['id'])).to be false
end
it 'is not due when monthly and no paydate and today is < last charge created_at day' do
rd = create_recdon({})
Timecop.freeze(Time.parse("2020-01-02")) do
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'pending').ts.ex
end
Timecop.freeze(Time.parse("2020-02-01")) do
expect(QueryRecurringDonations.is_due?(rd['id'])).to be false
end
end
it 'is not due when monthly an a paydate is present and today < paydate' do
rd = create_recdon({paydate: 2})
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'pending').ts.ex
Timecop.freeze(1.month.from_now.change(day: 1)) do
expect(QueryRecurringDonations.is_due?(rd['id'])).to be false
end
end
it 'is due when monthly and there are only failed charges this month' do
rd = create_recdon({})
Qx.insert_into(:charges).values(donation_id: rd['donation_id'], amount: 1000, supporter_id: supporter['id'], nonprofit_id: nonprofit['id'], status: 'failed').ts.ex
Timecop.freeze(1.month.from_now) do
expect(QueryRecurringDonations.is_due?(rd['id'])).to be true
end
end
end
describe '.for_export_enumerable' do
before :each do
@nonprofit = force_create(:nonprofit, name: "npo1");
@supporters = [ force_create(:supporter, name: "supporter-0", nonprofit: @nonprofit),
force_create(:supporter, name: "supporter-1", nonprofit: @nonprofit)]
@recurring_donations = [force_create(:recurring_donation, amount: 1000, active: false, n_failures: 0, nonprofit: @nonprofit, donation: force_create(:donation), edit_token: "edit_token_1"),
force_create(:recurring_donation, amount: 2000, active: true, n_failures: 3, nonprofit: @nonprofit, donation: force_create(:donation), edit_token: "edit_token_2"),
force_create(:recurring_donation, amount: 3000, active: true, n_failures: 0, nonprofit: @nonprofit, donation: force_create(:donation), edit_token: "edit_token_3"),
force_create(:recurring_donation, amount: 400, active: false, n_failures: 3, nonprofit: @nonprofit, donation: force_create(:donation), edit_token: "edit_token_4")]
@root_url ='https://localhost:8080'
end
let(:headers) { MockHelpers.recurring_donation_export_headers}
it 'finishes recurring donation export' do
rows = QueryRecurringDonations::for_export_enumerable(@nonprofit.id, {}).to_a
expect(rows.length).to eq(5)
expect(rows[0]).to eq(headers)
end
it 'retrieves active' do
rows = QueryRecurringDonations::for_export_enumerable(@nonprofit.id, {:active_and_not_failed => true, :root_url => 'https://localhost:8080/'}).to_a
expect(rows.length).to eq(2)
expect(rows[0]).to eq(headers)
expect(rows[1][1]).to eq("$30.00")
expect(rows[1][-1]).to eq(MockHelpers.generate_expected_rd_management_url(@root_url,@recurring_donations[2]))
end
it 'retrieves cancelled' do
rows = QueryRecurringDonations::for_export_enumerable(@nonprofit.id, {:active_and_not_failed => false, :root_url => 'https://localhost:8080/'}).to_a
expect(rows.length).to eq(2)
expect(rows[0]).to eq(headers)
expect(rows[1][1]).to eq("$10.00")
expect(rows[1][-1]).to eq('')
end
it 'retrieves failed' do
rows = QueryRecurringDonations::for_export_enumerable(@nonprofit.id, {:failed => true, :root_url => 'https://localhost:8080/'}).to_a
expect(rows.length).to eq(3)
expect(rows[0]).to eq(headers)
expect(rows[1][1]).to eq("$20.00")
expect(rows[2][1]).to eq("$4.00")
expect(rows[1][-1]).to eq(MockHelpers.generate_expected_rd_management_url(@root_url,@recurring_donations[1]))
expect(rows[2][-1]).to eq('')
end
it 'retrieves not-failed' do
rows = QueryRecurringDonations::for_export_enumerable(@nonprofit.id, {:failed => false, :root_url => 'https://localhost:8080/'}).to_a
expect(rows.length).to eq(3)
expect(rows[0]).to eq(headers)
expect(rows[1][1]).to eq("$10.00")
expect(rows[2][1]).to eq("$30.00")
expect(rows[1][-1]).to eq('')
expect(rows[2][-1]).to eq(MockHelpers.generate_expected_rd_management_url(@root_url,@recurring_donations[2]))
end
end
end # describe