1use std::collections::BTreeMap;
10use std::sync::Arc;
11
12use chrono::{DateTime, Utc};
13use parking_lot::RwLock;
14use serde::{Deserialize, Serialize};
15
16pub type SharedConfigState = Arc<RwLock<ConfigAccounts>>;
17
18pub fn resource_key(resource_type: &str, resource_id: &str) -> String {
20 format!("{resource_type}\u{1}{resource_id}")
21}
22
23#[derive(Debug, Default, Clone, Serialize, Deserialize)]
24pub struct ConfigAccounts {
25 pub accounts: BTreeMap<String, AccountState>,
26}
27
28impl ConfigAccounts {
29 pub fn new() -> Self {
30 Self::default()
31 }
32
33 pub fn account_mut(&mut self, account_id: &str) -> &mut AccountState {
34 self.accounts.entry(account_id.to_string()).or_default()
35 }
36
37 pub fn account(&self, account_id: &str) -> Option<&AccountState> {
38 self.accounts.get(account_id)
39 }
40}
41
42#[derive(Debug, Default, Clone, Serialize, Deserialize)]
43pub struct AccountState {
44 pub recorders: BTreeMap<String, ConfigurationRecorder>,
46 pub delivery_channels: BTreeMap<String, DeliveryChannel>,
48 pub rules: BTreeMap<String, ConfigRule>,
50 pub config_items: BTreeMap<String, Vec<ConfigurationItem>>,
53 pub evaluations: BTreeMap<String, BTreeMap<String, EvaluationResult>>,
56 pub conformance_packs: BTreeMap<String, ConformancePack>,
58 pub org_rules: BTreeMap<String, OrganizationConfigRule>,
60 pub org_conformance_packs: BTreeMap<String, OrganizationConformancePack>,
62 pub aggregators: BTreeMap<String, ConfigurationAggregator>,
64 pub aggregation_authorizations: BTreeMap<String, AggregationAuthorization>,
66 pub retention_configurations: BTreeMap<String, RetentionConfiguration>,
69 pub stored_queries: BTreeMap<String, StoredQuery>,
71 pub remediation_configs: BTreeMap<String, RemediationConfiguration>,
73 pub remediation_exceptions: BTreeMap<String, RemediationException>,
75 #[serde(default)]
79 pub remediation_executions: BTreeMap<String, RemediationExecutionStatus>,
80 pub resource_evaluations: BTreeMap<String, ResourceEvaluation>,
82 pub tags: BTreeMap<String, BTreeMap<String, String>>,
84}
85
86#[derive(Debug, Clone, Serialize, Deserialize)]
89pub struct ConfigurationRecorder {
90 pub name: String,
91 pub role_arn: String,
92 #[serde(default)]
94 pub recording_group: Option<serde_json::Value>,
95 #[serde(default)]
96 pub recording_mode: Option<serde_json::Value>,
97 #[serde(default)]
100 pub arn: Option<String>,
101 #[serde(default)]
102 pub service_principal: Option<String>,
103 pub recording: bool,
105 pub last_start_time: Option<DateTime<Utc>>,
106 pub last_stop_time: Option<DateTime<Utc>>,
107 pub last_status: String,
108 pub last_status_change_time: Option<DateTime<Utc>>,
109}
110
111#[derive(Debug, Clone, Serialize, Deserialize)]
112pub struct DeliveryChannel {
113 pub name: String,
114 pub s3_bucket_name: Option<String>,
115 pub s3_key_prefix: Option<String>,
116 pub s3_kms_key_arn: Option<String>,
117 pub sns_topic_arn: Option<String>,
118 #[serde(default)]
119 pub config_snapshot_delivery_properties: Option<serde_json::Value>,
120 pub last_status: String,
121}
122
123#[derive(Debug, Clone, Serialize, Deserialize)]
126pub struct ConfigurationItem {
127 pub version: String,
128 pub account_id: String,
129 pub configuration_item_capture_time: DateTime<Utc>,
130 pub configuration_item_status: String,
133 pub configuration_state_id: String,
134 pub arn: String,
135 pub resource_type: String,
136 pub resource_id: String,
137 #[serde(default)]
138 pub resource_name: Option<String>,
139 pub aws_region: String,
140 pub availability_zone: String,
141 pub resource_creation_time: Option<DateTime<Utc>>,
142 #[serde(default)]
143 pub tags: BTreeMap<String, String>,
144 pub configuration: String,
147 #[serde(default)]
148 pub supplementary_configuration: BTreeMap<String, String>,
149 #[serde(default)]
154 pub externally_recorded: bool,
155}
156
157#[derive(Debug, Clone, Serialize, Deserialize)]
160pub struct ConfigRule {
161 pub name: String,
162 pub arn: String,
163 pub rule_id: String,
164 #[serde(default)]
165 pub description: Option<String>,
166 #[serde(default)]
168 pub scope: Option<serde_json::Value>,
169 pub source: serde_json::Value,
172 #[serde(default)]
173 pub input_parameters: Option<String>,
174 #[serde(default)]
175 pub maximum_execution_frequency: Option<String>,
176 pub state: String,
178 #[serde(default)]
179 pub created_by: Option<String>,
180 #[serde(default)]
181 pub evaluation_modes: Option<serde_json::Value>,
182 pub last_updated: DateTime<Utc>,
183 pub first_activated_time: Option<DateTime<Utc>>,
185 pub last_successful_evaluation_time: Option<DateTime<Utc>>,
186 pub last_successful_invocation_time: Option<DateTime<Utc>>,
187}
188
189#[derive(Debug, Clone, Serialize, Deserialize)]
190pub struct EvaluationResult {
191 pub resource_type: String,
192 pub resource_id: String,
193 pub rule_name: String,
194 pub compliance_type: String,
196 pub annotation: Option<String>,
197 pub result_recorded_time: DateTime<Utc>,
198 pub config_rule_invoked_time: DateTime<Utc>,
199 pub ordering_timestamp: DateTime<Utc>,
200}
201
202#[derive(Debug, Clone, Serialize, Deserialize)]
205pub struct ConformancePack {
206 pub name: String,
207 pub arn: String,
208 pub id: String,
209 pub delivery_s3_bucket: Option<String>,
210 pub delivery_s3_key_prefix: Option<String>,
211 #[serde(default)]
212 pub input_parameters: Vec<serde_json::Value>,
213 pub template_body: Option<String>,
214 pub template_s3_uri: Option<String>,
215 #[serde(default)]
216 pub template_ssm_document_details: Option<serde_json::Value>,
217 pub last_update_requested_time: DateTime<Utc>,
218 pub created_by: Option<String>,
219 #[serde(default)]
221 pub rule_names: Vec<String>,
222}
223
224#[derive(Debug, Clone, Serialize, Deserialize)]
225pub struct OrganizationConfigRule {
226 pub name: String,
227 pub arn: String,
228 #[serde(default)]
229 pub managed_rule_metadata: Option<serde_json::Value>,
230 #[serde(default)]
231 pub custom_rule_metadata: Option<serde_json::Value>,
232 #[serde(default)]
233 pub custom_policy_rule_metadata: Option<serde_json::Value>,
234 #[serde(default)]
235 pub excluded_accounts: Vec<String>,
236 pub last_update_time: DateTime<Utc>,
237}
238
239#[derive(Debug, Clone, Serialize, Deserialize)]
240pub struct OrganizationConformancePack {
241 pub name: String,
242 pub arn: String,
243 pub delivery_s3_bucket: Option<String>,
244 pub delivery_s3_key_prefix: Option<String>,
245 #[serde(default)]
246 pub input_parameters: Vec<serde_json::Value>,
247 pub template_body: Option<String>,
248 pub template_s3_uri: Option<String>,
249 #[serde(default)]
250 pub excluded_accounts: Vec<String>,
251 pub last_update_time: DateTime<Utc>,
252}
253
254#[derive(Debug, Clone, Serialize, Deserialize)]
257pub struct ConfigurationAggregator {
258 pub name: String,
259 pub arn: String,
260 #[serde(default)]
261 pub account_aggregation_sources: Vec<serde_json::Value>,
262 #[serde(default)]
263 pub organization_aggregation_source: Option<serde_json::Value>,
264 pub creation_time: DateTime<Utc>,
265 pub last_updated_time: DateTime<Utc>,
266 pub created_by: Option<String>,
267}
268
269#[derive(Debug, Clone, Serialize, Deserialize)]
270pub struct AggregationAuthorization {
271 pub arn: String,
272 pub authorized_account_id: String,
273 pub authorized_aws_region: String,
274 pub creation_time: DateTime<Utc>,
275}
276
277#[derive(Debug, Clone, Serialize, Deserialize)]
280pub struct RetentionConfiguration {
281 pub name: String,
282 pub retention_period_in_days: i64,
283}
284
285#[derive(Debug, Clone, Serialize, Deserialize)]
286pub struct StoredQuery {
287 pub id: String,
288 pub name: String,
289 pub arn: String,
290 pub description: Option<String>,
291 pub expression: Option<String>,
292}
293
294#[derive(Debug, Clone, Serialize, Deserialize)]
295pub struct RemediationConfiguration {
296 pub config_rule_name: String,
297 pub arn: String,
298 pub target_type: String,
299 pub target_id: String,
300 #[serde(default)]
301 pub target_version: Option<String>,
302 #[serde(default)]
303 pub parameters: Option<serde_json::Value>,
304 #[serde(default)]
305 pub resource_type: Option<String>,
306 #[serde(default)]
307 pub automatic: bool,
308 #[serde(default)]
309 pub execution_controls: Option<serde_json::Value>,
310 #[serde(default)]
311 pub maximum_automatic_attempts: Option<i64>,
312 #[serde(default)]
313 pub retry_attempt_seconds: Option<i64>,
314 pub created_by_service: Option<String>,
315}
316
317#[derive(Debug, Clone, Serialize, Deserialize)]
318pub struct RemediationException {
319 pub config_rule_name: String,
320 pub resource_type: String,
321 pub resource_id: String,
322 pub message: Option<String>,
323 pub expiration_time: Option<DateTime<Utc>>,
324}
325
326#[derive(Debug, Clone, Serialize, Deserialize)]
332pub struct RemediationExecutionStatus {
333 pub config_rule_name: String,
334 pub resource_type: String,
335 pub resource_id: String,
336 pub state: String,
338 pub invocation_time: DateTime<Utc>,
339 pub last_updated_time: DateTime<Utc>,
340}
341
342#[derive(Debug, Clone, Serialize, Deserialize)]
343pub struct ResourceEvaluation {
344 pub resource_evaluation_id: String,
345 pub evaluation_mode: String,
346 pub time_stamp: DateTime<Utc>,
347 pub status: String,
349 #[serde(default)]
350 pub resource_details: Option<serde_json::Value>,
351 #[serde(default)]
352 pub evaluation_context: Option<serde_json::Value>,
353 #[serde(default)]
354 pub evaluation_results: Vec<EvaluationResult>,
355}
356
357#[derive(Clone, Serialize, Deserialize)]
360pub struct ConfigSnapshot {
361 pub schema_version: u32,
362 #[serde(default)]
363 pub accounts: Option<ConfigAccounts>,
364}
365
366pub const CONFIG_SNAPSHOT_SCHEMA_VERSION: u32 = 1;