Skip to content

Commit 403d6ca

Browse files
authored
fix bill recalculation after expiration (#498)
1 parent 5a0211b commit 403d6ca

File tree

3 files changed

+168
-14
lines changed

3 files changed

+168
-14
lines changed

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
# 0.3.10
22

3+
* Fix a small issue, where bills were recalculated instead of taken from cache, once their payment/sell/recourse/accept requests expired
34
* Change behaviour of request to pay
45
* it's now possible to req to pay before the maturity date
56
* The actual payment expiry still only happens 2 workdays after the end of the maturity date,

crates/bcr-ebill-api/src/service/bill_service/data_fetching.rs

Lines changed: 34 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -502,7 +502,12 @@ impl BillService {
502502
) -> Result<bool> {
503503
let mut invalidate_and_recalculate = false;
504504
let acceptance = &bill.status.acceptance;
505-
if acceptance.requested_to_accept && !acceptance.accepted && !acceptance.rejected_to_accept
505+
// if it was requested, but not "finished" (accepted, rejected, or expired), we have to
506+
// check if the deadline expired and recalculate
507+
if acceptance.requested_to_accept
508+
&& !acceptance.accepted
509+
&& !acceptance.rejected_to_accept
510+
&& !acceptance.request_to_accept_timed_out
506511
{
507512
if let Some(time_of_request_to_accept) = acceptance.time_of_request_to_accept {
508513
if util::date::check_if_deadline_has_passed(
@@ -515,8 +520,14 @@ impl BillService {
515520
}
516521
}
517522

523+
// if it was requested, but not "finished" (paid, rejected, or expired), we have to
524+
// check if the deadline expired and recalculate
518525
let payment = &bill.status.payment;
519-
if payment.requested_to_pay && !payment.paid && !payment.rejected_to_pay {
526+
if payment.requested_to_pay
527+
&& !payment.paid
528+
&& !payment.rejected_to_pay
529+
&& !payment.request_to_pay_timed_out
530+
{
520531
if let Some(time_of_request_to_pay) = payment.time_of_request_to_pay {
521532
let deadline_base = get_expiration_deadline_base_for_req_to_pay(
522533
time_of_request_to_pay,
@@ -530,19 +541,29 @@ impl BillService {
530541
) {
531542
invalidate_and_recalculate = true;
532543
}
533-
// req to pay has expired (after maturity date)
534-
if util::date::check_if_deadline_has_passed(
535-
time_of_request_to_pay,
536-
current_timestamp,
537-
PAYMENT_DEADLINE_SECONDS,
538-
) {
539-
invalidate_and_recalculate = true;
544+
// if it was req to pay and is currently waiting, we have to check, if it's expired
545+
// once it's expired, we don't have to check this anymore
546+
if let Some(BillCurrentWaitingState::Payment(_)) = bill.current_waiting_state {
547+
// req to pay has expired (before maturity date)
548+
if util::date::check_if_deadline_has_passed(
549+
time_of_request_to_pay,
550+
current_timestamp,
551+
PAYMENT_DEADLINE_SECONDS,
552+
) {
553+
invalidate_and_recalculate = true;
554+
}
540555
}
541556
}
542557
}
543558

544559
let sell = &bill.status.sell;
545-
if sell.offered_to_sell && !sell.sold && !sell.rejected_offer_to_sell {
560+
// if it was requested, but not "finished" (sold, rejected, or expired), we have to
561+
// check if the deadline expired and recalculate
562+
if sell.offered_to_sell
563+
&& !sell.sold
564+
&& !sell.rejected_offer_to_sell
565+
&& !sell.offer_to_sell_timed_out
566+
{
546567
if let Some(time_of_last_offer_to_sell) = sell.time_of_last_offer_to_sell {
547568
if util::date::check_if_deadline_has_passed(
548569
time_of_last_offer_to_sell,
@@ -555,9 +576,12 @@ impl BillService {
555576
}
556577

557578
let recourse = &bill.status.recourse;
579+
// if it was requested, but not "finished" (recoursed, rejected, or expired), we have to
580+
// check if the deadline expired and recalculate
558581
if recourse.requested_to_recourse
559582
&& !recourse.recoursed
560583
&& !recourse.rejected_request_to_recourse
584+
&& !recourse.request_to_recourse_timed_out
561585
{
562586
if let Some(time_of_last_request_to_recourse) =
563587
recourse.time_of_last_request_to_recourse

crates/bcr-ebill-api/src/service/bill_service/mod.rs

Lines changed: 133 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -168,8 +168,8 @@ pub mod tests {
168168
use bcr_ebill_core::{
169169
ValidationError,
170170
bill::{
171-
BillAcceptanceStatus, BillPaymentStatus, BillRecourseStatus, BillSellStatus,
172-
PastPaymentStatus, RecourseReason,
171+
BillAcceptanceStatus, BillCurrentWaitingState, BillPaymentStatus, BillRecourseStatus,
172+
BillSellStatus, BillWaitingForPaymentState, PastPaymentStatus, RecourseReason,
173173
},
174174
blockchain::{
175175
Blockchain,
@@ -4233,6 +4233,14 @@ pub mod tests {
42334233
.check_requests_for_expiration(&bill_payment, 1731593928)
42344234
.unwrap()
42354235
);
4236+
bill_payment.status.payment.request_to_pay_timed_out = true;
4237+
// if it already timed out, we don't need to check anymore
4238+
assert!(
4239+
!service
4240+
.check_requests_for_expiration(&bill_payment, 1731593928)
4241+
.unwrap()
4242+
);
4243+
bill_payment.status.payment.request_to_pay_timed_out = false;
42364244
assert!(
42374245
!service
42384246
.check_requests_for_expiration(&bill_payment, 1431593928)
@@ -4244,10 +4252,37 @@ pub mod tests {
42444252
.check_requests_for_expiration(&bill_payment, 1531593929)
42454253
.unwrap()
42464254
);
4247-
// 2 days after req to pay, but not yet 2 days after end of day maturity date, req expired
4255+
bill_payment.current_waiting_state = Some(BillCurrentWaitingState::Payment(
4256+
BillWaitingForPaymentState {
4257+
time_of_request: 1531593928,
4258+
payer: empty_identity_public_data(),
4259+
payee: empty_identity_public_data(),
4260+
currency: "sat".into(),
4261+
sum: "10".into(),
4262+
link_to_pay: String::default(),
4263+
address_to_pay: String::default(),
4264+
mempool_link_for_address_to_pay: String::default(),
4265+
},
4266+
));
4267+
// req to pay expired, but not yet 2 days after end of day maturity date
4268+
// current waiting state set, so wasnt recalculated yet
42484269
assert!(
42494270
service
4250-
.check_requests_for_expiration(&bill_payment, 1531780429)
4271+
.check_requests_for_expiration(
4272+
&bill_payment,
4273+
1531593929 + PAYMENT_DEADLINE_SECONDS + 1
4274+
)
4275+
.unwrap()
4276+
);
4277+
bill_payment.current_waiting_state = None;
4278+
// req to pay expired, but not yet 2 days after end of day maturity date
4279+
// but no current waiting state, so was already checked
4280+
assert!(
4281+
!service
4282+
.check_requests_for_expiration(
4283+
&bill_payment,
4284+
1531593929 + PAYMENT_DEADLINE_SECONDS + 1
4285+
)
42514286
.unwrap()
42524287
);
42534288
// after req to pay, and after end of day maturity date, payment expired
@@ -4262,6 +4297,22 @@ pub mod tests {
42624297
.check_requests_for_expiration(&bill_payment, 1531593929)
42634298
.unwrap()
42644299
);
4300+
bill_payment.status.payment.rejected_to_pay = true;
4301+
// already rejected, no need to check anymore
4302+
assert!(
4303+
!service
4304+
.check_requests_for_expiration(&bill_payment, 1831593928)
4305+
.unwrap()
4306+
);
4307+
bill_payment.status.payment.rejected_to_pay = false;
4308+
bill_payment.status.payment.paid = true;
4309+
// already paid, no need to check anymore
4310+
assert!(
4311+
!service
4312+
.check_requests_for_expiration(&bill_payment, 1831593928)
4313+
.unwrap()
4314+
);
4315+
bill_payment.status.payment.paid = false;
42654316

42664317
let mut bill_acceptance = get_baseline_cached_bill(TEST_BILL_ID.to_string());
42674318
bill_acceptance.status.acceptance = BillAcceptanceStatus {
@@ -4277,6 +4328,36 @@ pub mod tests {
42774328
.check_requests_for_expiration(&bill_acceptance, 1731593928)
42784329
.unwrap()
42794330
);
4331+
bill_acceptance
4332+
.status
4333+
.acceptance
4334+
.request_to_accept_timed_out = true;
4335+
// already expired, no need to check anymore
4336+
assert!(
4337+
!service
4338+
.check_requests_for_expiration(&bill_acceptance, 1731593928)
4339+
.unwrap()
4340+
);
4341+
bill_acceptance
4342+
.status
4343+
.acceptance
4344+
.request_to_accept_timed_out = false;
4345+
bill_acceptance.status.acceptance.rejected_to_accept = true;
4346+
// already rejected, no need to check anymore
4347+
assert!(
4348+
!service
4349+
.check_requests_for_expiration(&bill_acceptance, 1731593928)
4350+
.unwrap()
4351+
);
4352+
bill_acceptance.status.acceptance.rejected_to_accept = false;
4353+
bill_acceptance.status.acceptance.accepted = true;
4354+
// already accepted, no need to check anymore
4355+
assert!(
4356+
!service
4357+
.check_requests_for_expiration(&bill_acceptance, 1731593928)
4358+
.unwrap()
4359+
);
4360+
bill_acceptance.status.acceptance.accepted = false;
42804361

42814362
let mut bill_sell = get_baseline_cached_bill(TEST_BILL_ID.to_string());
42824363
bill_sell.status.sell = BillSellStatus {
@@ -4293,6 +4374,31 @@ pub mod tests {
42934374
.unwrap()
42944375
);
42954376

4377+
bill_sell.status.sell.offer_to_sell_timed_out = true;
4378+
// already expired, no need to check anymore
4379+
assert!(
4380+
!service
4381+
.check_requests_for_expiration(&bill_sell, 1731593928)
4382+
.unwrap()
4383+
);
4384+
bill_sell.status.sell.offer_to_sell_timed_out = false;
4385+
bill_sell.status.sell.rejected_offer_to_sell = true;
4386+
// already rejected, no need to check anymore
4387+
assert!(
4388+
!service
4389+
.check_requests_for_expiration(&bill_sell, 1731593928)
4390+
.unwrap()
4391+
);
4392+
bill_sell.status.sell.rejected_offer_to_sell = false;
4393+
bill_sell.status.sell.sold = true;
4394+
// already sold, no need to check anymore
4395+
assert!(
4396+
!service
4397+
.check_requests_for_expiration(&bill_sell, 1731593928)
4398+
.unwrap()
4399+
);
4400+
bill_sell.status.sell.sold = false;
4401+
42964402
let mut bill_recourse = get_baseline_cached_bill(TEST_BILL_ID.to_string());
42974403
bill_recourse.status.recourse = BillRecourseStatus {
42984404
time_of_last_request_to_recourse: Some(1531593928),
@@ -4307,5 +4413,28 @@ pub mod tests {
43074413
.check_requests_for_expiration(&bill_recourse, 1731593928)
43084414
.unwrap()
43094415
);
4416+
bill_recourse.status.recourse.request_to_recourse_timed_out = true;
4417+
// already expired, no need to check anymore
4418+
assert!(
4419+
!service
4420+
.check_requests_for_expiration(&bill_recourse, 1731593928)
4421+
.unwrap()
4422+
);
4423+
bill_recourse.status.recourse.rejected_request_to_recourse = true;
4424+
// already rejected, no need to check anymore
4425+
assert!(
4426+
!service
4427+
.check_requests_for_expiration(&bill_recourse, 1731593928)
4428+
.unwrap()
4429+
);
4430+
bill_recourse.status.recourse.rejected_request_to_recourse = false;
4431+
bill_recourse.status.recourse.recoursed = true;
4432+
// already recoursed, no need to check anymore
4433+
assert!(
4434+
!service
4435+
.check_requests_for_expiration(&bill_recourse, 1731593928)
4436+
.unwrap()
4437+
);
4438+
bill_recourse.status.recourse.recoursed = false;
43104439
}
43114440
}

0 commit comments

Comments
 (0)