Skip to content

Commit 14734c6

Browse files
committed
feat: implement PaymentTimeoutService to handle transaction tracking, automated retries, and gas price bumping for chain payments.
1 parent d2cc210 commit 14734c6

22 files changed

Lines changed: 106 additions & 77 deletions

backend/services/accessControl.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,9 @@
55
*/
66

77
import { randomUUID } from 'crypto';
8-
import { AuditService } from './auditService';
9-
import { AlertingService } from './alerting';
10-
import type { Alert } from './types';
8+
import { AuditService } from './shared/auditService';
9+
import { AlertingService } from './notification/alerting';
10+
import type { Alert } from './shared/types';
1111

1212
// ─── Resource & Action Types ──────────────────────────────────────────────────
1313

backend/services/affiliate/AffiliateService.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
1-
import { AuditService } from '../auditService';
2-
import type { AuditAction } from '../auditTypes';
1+
import { AuditService } from '../shared/auditService';
2+
import type { AuditAction } from '../shared/auditTypes';
33
import {
44
Affiliate,
55
AffiliateProgram,

backend/services/paymentTimeoutService.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,8 @@
99
* - Stuck transaction alerting
1010
*/
1111

12-
import type { AlertingService } from './alerting';
13-
import type { Alert } from './types';
12+
import type { AlertingService } from './notification/alerting';
13+
import type { Alert } from './shared/types';
1414

1515
// ── Chain timeout configuration ───────────────────────────────────────────────
1616

backend/services/shared/__tests__/accessControl.test.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
1-
import { AccessControlService, ROLE_HIERARCHY, ROLE_PERMISSIONS } from '../accessControl';
1+
import { AccessControlService, ROLE_HIERARCHY, ROLE_PERMISSIONS } from '../../accessControl';
22
import { AuditService } from '../auditService';
3-
import { AlertingService } from '../alerting';
3+
import { AlertingService } from '../../notification/alerting';
44

55
describe('AccessControlService', () => {
66
let svc: AccessControlService;

backend/services/shared/__tests__/auditService.test.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { AlertingService } from '../alerting';
1+
import { AlertingService } from '../../notification/alerting';
22
import { AuditService } from '../auditService';
33

44
const SECRET = 'test-secret-key';

backend/services/shared/auditService.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import { createHmac, randomUUID } from 'crypto';
22
import AsyncStorage from '@react-native-async-storage/async-storage';
3-
import type { AlertingService, AlertDispatcher } from './alerting';
3+
import type { AlertingService, AlertDispatcher } from '../notification/alerting';
44
import type {
55
AuditAction,
66
AuditArchiveEntry,

contracts/api/src/auth.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,7 @@ pub fn create_api_key(
6060
.get(&DataKey::OwnerKeys(owner.clone()))
6161
.unwrap_or(Vec::new(env));
6262
assert!(
63-
(owner_keys.len() as u32) < MAX_KEYS_PER_OWNER,
63+
owner_keys.len() < MAX_KEYS_PER_OWNER,
6464
"Max keys per owner reached"
6565
);
6666
let mut new_owner_keys = owner_keys;

contracts/api/src/ratelimit.rs

Lines changed: 3 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -52,15 +52,9 @@ pub fn check_rate_limit(env: &Env, key: &ApiKey, now: u64) -> RateLimitStatus {
5252
SECS_PER_DAY,
5353
);
5454

55-
let exceeded = if min_count > cfg.requests_per_minute {
56-
true
57-
} else if hour_count > cfg.requests_per_hour {
58-
true
59-
} else if day_count > cfg.requests_per_day {
60-
true
61-
} else {
62-
false
63-
};
55+
let exceeded = min_count > cfg.requests_per_minute
56+
|| hour_count > cfg.requests_per_hour
57+
|| day_count > cfg.requests_per_day;
6458

6559
if exceeded {
6660
let reset_at = core::cmp::min(core::cmp::min(min_reset, hour_reset), day_reset);

contracts/api/src/test.rs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
21
use soroban_sdk::{testutils::Address as _, testutils::Ledger as _, Address, Bytes, BytesN, Env};
32
use subtrackr_types::{ApiKeyConfig, ApiKeyStatus, RateLimitConfig, TimeRange, UsageTier};
43

@@ -48,7 +47,7 @@ fn test_create_api_key() {
4847

4948
let (key_id, raw_key) = client.create_api_key(&owner, &default_config(&env));
5049
assert!(key_id >= 1, "Key id should be >= 1");
51-
assert!(raw_key.len() > 0, "Raw key bytes should not be empty");
50+
assert!(!raw_key.is_empty(), "Raw key bytes should not be empty");
5251

5352
let stored = client.get_api_key(&key_id).unwrap();
5453
assert_eq!(stored.id, key_id);

contracts/fraud/src/lib.rs

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -239,10 +239,6 @@ fn build_evidence(
239239
.device_fingerprint
240240
.clone()
241241
.unwrap_or_else(|| String::from_str(env, "unknown"));
242-
let trusted = profile
243-
.trusted_device_fingerprint
244-
.clone()
245-
.unwrap_or_else(|| String::from_str(env, "unknown"));
246242
evidence.push_back(subtrackr_types::FraudEvidence {
247243
label: String::from_str(env, "device mismatch"),
248244
value: current,
@@ -661,7 +657,7 @@ impl SubTrackrFraud {
661657
}
662658

663659
if let Some(case) = review_case_for_subscription(&env, score.subscription_id) {
664-
if case.evidence.len() == 0 {
660+
if case.evidence.is_empty() {
665661
pending_evidence += 1;
666662
}
667663
if case.status == FraudReviewStatus::Dismissed {
@@ -670,7 +666,7 @@ impl SubTrackrFraud {
670666
recent_cases.push_back(case);
671667
} else if score.total_score >= REVIEW_THRESHOLD {
672668
let case = persist_case(&env, &score, FraudReviewStatus::Pending);
673-
if case.evidence.len() == 0 {
669+
if case.evidence.is_empty() {
674670
pending_evidence += 1;
675671
}
676672
recent_cases.push_back(case);

0 commit comments

Comments
 (0)