photon_backend/retention/
partition.rs1use std::collections::HashSet;
4
5use crate::handler_registry::HandlerRegistry;
6use crate::retention::config::RetentionPolicy;
7use crate::retention::hook::RetentionHook;
8
9#[derive(Debug, Clone, PartialEq, Eq, Hash)]
11pub struct TopicPartition {
12 pub topic_name: String,
14 pub topic_key: Option<String>,
16}
17
18impl TopicPartition {
19 pub fn new(topic_name: impl Into<String>, topic_key: Option<String>) -> Self {
21 Self {
22 topic_name: topic_name.into(),
23 topic_key,
24 }
25 }
26}
27
28#[derive(Debug, Clone, PartialEq, Eq, Hash)]
30pub struct SubscriptionPartition {
31 pub subscription_name: String,
33 pub topic_name: String,
35 pub topic_key: Option<String>,
37}
38
39pub fn known_subscriptions(
41 policy: &RetentionPolicy,
42 hook: Option<&dyn RetentionHook>,
43) -> Vec<SubscriptionPartition> {
44 let mut seen = HashSet::new();
45 let mut out = Vec::new();
46
47 let registry = HandlerRegistry::auto_discover();
48 for handler in registry.iter() {
49 let entry = SubscriptionPartition {
50 subscription_name: handler.subscription_name.to_string(),
51 topic_name: handler.topic_name.to_string(),
52 topic_key: None,
53 };
54 if seen.insert(entry.clone()) {
55 out.push(entry);
56 }
57 }
58
59 for entry in &policy.extra_subscriptions {
60 if seen.insert(entry.clone()) {
61 out.push(entry.clone());
62 }
63 }
64
65 if let Some(h) = hook {
66 for entry in h.extra_subscriptions() {
67 if seen.insert(entry.clone()) {
68 out.push(entry);
69 }
70 }
71 }
72
73 out
74}
75
76pub fn subscriptions_for_partition<'a>(
78 subs: &'a [SubscriptionPartition],
79 topic: &str,
80 topic_key: Option<&str>,
81) -> Vec<&'a SubscriptionPartition> {
82 subs.iter()
83 .filter(|s| {
84 s.topic_name == topic
85 && match (&s.topic_key, topic_key) {
86 (None, _) => true,
87 (Some(sk), Some(tk)) => sk == tk,
88 (Some(_), None) => false,
89 }
90 })
91 .collect()
92}
93
94pub fn merge_partitions(sources: impl IntoIterator<Item = TopicPartition>) -> Vec<TopicPartition> {
96 let mut seen = HashSet::new();
97 let mut out = Vec::new();
98 for part in sources {
99 if seen.insert(part.clone()) {
100 out.push(part);
101 }
102 }
103 out
104}