forked from InsurNiffy/niff-Stellar-shurance
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathpremium.rs
More file actions
123 lines (114 loc) · 3.16 KB
/
Copy pathpremium.rs
File metadata and controls
123 lines (114 loc) · 3.16 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
use crate::types::{PolicyType, PremiumQuoteLineItem, RegionTier};
use soroban_sdk::{Env, String, Vec};
/// Base annual premium in stroops (1 XLM = 10_000_000 stroops).
#[allow(dead_code)]
const BASE: i128 = 10_000_000;
/// Returns the annual premium for the given risk profile.
/// Called from policy.rs once feat/policy-lifecycle lands.
#[allow(dead_code)]
pub fn compute_premium(
policy_type: &PolicyType,
region: &RegionTier,
age: u32,
risk_score: u32, // 1–10; higher = riskier
) -> i128 {
let type_factor: i128 = match policy_type {
PolicyType::Auto => 15,
PolicyType::Health => 20,
PolicyType::Property => 10,
};
let region_factor: i128 = match region {
RegionTier::Low => 8,
RegionTier::Medium => 10,
RegionTier::High => 14,
};
let age_factor: i128 = if age < 25 {
15
} else if age > 60 {
13
} else {
10
};
BASE * (type_factor + region_factor + age_factor + risk_score as i128) / 10
}
#[allow(dead_code)]
pub fn type_factor(policy_type: &PolicyType) -> i128 {
match policy_type {
PolicyType::Auto => 15,
PolicyType::Health => 20,
PolicyType::Property => 10,
}
}
#[allow(dead_code)]
pub fn region_factor(region: &RegionTier) -> i128 {
match region {
RegionTier::Low => 8,
RegionTier::Medium => 10,
RegionTier::High => 14,
}
}
#[allow(dead_code)]
pub fn age_factor(age: u32) -> i128 {
if age < 25 {
15
} else if age > 60 {
13
} else {
10
}
}
#[allow(dead_code)]
pub fn compute_premium_checked(
policy_type: &PolicyType,
region: &RegionTier,
age: u32,
risk_score: u32,
) -> Option<i128> {
let tf = type_factor(policy_type);
let rf = region_factor(region);
let af = age_factor(age);
let raw = tf
.checked_add(rf)?
.checked_add(af)?
.checked_add(risk_score as i128)?;
BASE.checked_mul(raw)?.checked_div(10)
}
#[allow(dead_code)]
pub fn build_line_items(
env: &Env,
policy_type: &PolicyType,
region: &RegionTier,
age: u32,
risk_score: u32,
) -> Option<Vec<PremiumQuoteLineItem>> {
let tf = type_factor(policy_type);
let rf = region_factor(region);
let af = age_factor(age);
let rsk = risk_score as i128;
let base_type = BASE.checked_mul(tf)?.checked_div(10)?;
let base_region = BASE.checked_mul(rf)?.checked_div(10)?;
let base_age = BASE.checked_mul(af)?.checked_div(10)?;
let base_risk = BASE.checked_mul(rsk)?.checked_div(10)?;
let mut items = Vec::new(env);
items.push_back(PremiumQuoteLineItem {
component: String::from_str(env, "type"),
factor: tf,
amount: base_type,
});
items.push_back(PremiumQuoteLineItem {
component: String::from_str(env, "region"),
factor: rf,
amount: base_region,
});
items.push_back(PremiumQuoteLineItem {
component: String::from_str(env, "age"),
factor: af,
amount: base_age,
});
items.push_back(PremiumQuoteLineItem {
component: String::from_str(env, "risk_score"),
factor: rsk,
amount: base_risk,
});
Some(items)
}