awsim_secretsmanager/
authz.rs1use awsim_core::{AccountRegionStore, ResourcePolicyLookup, SecretLookup};
2use awsim_iam_policy::PolicyDocument;
3
4use crate::state::SecretsState;
5
6pub struct SecretsManagerResourcePolicyLookup {
7 store: AccountRegionStore<SecretsState>,
8}
9
10impl SecretsManagerResourcePolicyLookup {
11 pub fn new(store: AccountRegionStore<SecretsState>) -> Self {
12 Self { store }
13 }
14}
15
16fn extract_secret_key(arn: &str) -> Option<String> {
17 let rest = arn.strip_prefix("arn:aws:secretsmanager:")?;
18 let parts: Vec<&str> = rest.splitn(3, ':').collect();
19 if parts.len() < 3 {
20 return None;
21 }
22 let resource = parts[2];
23 let after_secret = resource.strip_prefix("secret:")?;
24 Some(after_secret.to_string())
25}
26
27pub struct SecretsManagerSecretLookup {
32 store: AccountRegionStore<SecretsState>,
33}
34
35impl SecretsManagerSecretLookup {
36 pub fn new(store: AccountRegionStore<SecretsState>) -> Self {
37 Self { store }
38 }
39}
40
41impl SecretLookup for SecretsManagerSecretLookup {
42 fn secret_exists(&self, secret_ref: &str, account: &str, region: &str) -> bool {
43 let state = self.store.get(account, region);
44 if state.secrets.contains_key(secret_ref) {
45 return true;
46 }
47 if let Some(stored_key) = extract_secret_key(secret_ref) {
51 if state.secrets.contains_key(&stored_key) {
52 return true;
53 }
54 let bare = stored_key
55 .rsplit_once('-')
56 .map(|(n, _)| n.to_string())
57 .unwrap_or(stored_key);
58 if state.secrets.contains_key(&bare) {
59 return true;
60 }
61 }
62 state.secrets.iter().any(|e| e.value().arn == secret_ref)
64 }
65}
66
67impl ResourcePolicyLookup for SecretsManagerResourcePolicyLookup {
68 fn lookup(&self, resource_arn: &str) -> Option<PolicyDocument> {
69 for (_, state) in self.store.iter_all() {
70 for entry in state.secrets.iter() {
71 if entry.value().arn == resource_arn {
72 let name = entry.key();
73 if let Some(raw) = state.resource_policies.get(name) {
74 return awsim_iam_policy::parse(raw.value()).ok();
75 }
76 return None;
77 }
78 }
79 if let Some(suffixed) = extract_secret_key(resource_arn) {
80 let bare_name = suffixed
81 .rsplit_once('-')
82 .map(|(n, _)| n)
83 .unwrap_or(&suffixed);
84 if let Some(raw) = state.resource_policies.get(bare_name) {
85 return awsim_iam_policy::parse(raw.value()).ok();
86 }
87 }
88 }
89 None
90 }
91}