rusticity_term/dynamodb/
items.rs1use super::actions::is_items_tab;
3use crate::app::{App, Service};
4use crate::keymap::Mode;
5use crate::ui::dynamodb::{self, ItemOperation, ItemProjection, State};
6use rusticity_core::dynamodb::{DdbItemCursor, DdbItemsPage};
7
8#[derive(Clone, Debug, PartialEq)]
9pub struct ItemRequestContext {
10 pub profile: String,
11 pub region: String,
12 pub account_id: String,
13 pub role_arn: String,
14 pub table: String,
15 pub index: Option<String>,
16 pub keys: Vec<String>,
17 pub partition_type: String,
18 pub operation: ItemOperation,
19 pub projection: ItemProjection,
20 pub query: Option<String>,
22}
23
24pub fn context(app: &App) -> Option<ItemRequestContext> {
25 let table = dynamodb::current_table(app)?;
26 let state = &app.dynamodb_state;
27 Some(ItemRequestContext {
28 profile: app.profile.clone(),
29 region: app.config.region.clone(),
30 account_id: app.config.account_id.clone(),
31 role_arn: app.config.role_arn.clone(),
32 table: table.name.clone(),
33 index: dynamodb::selected_item_index(table, state.item_index),
34 keys: dynamodb::selected_key_attributes(table, state.item_index),
35 partition_type: dynamodb::key_attribute_type(&dynamodb::selected_partition_key_label(
36 table,
37 state.item_index,
38 )),
39 operation: state.item_operation,
40 projection: state.item_projection,
41 query: (state.item_operation == ItemOperation::Query).then(|| state.item_filter.clone()),
42 })
43}
44
45pub fn can_load_more(app: &App) -> bool {
46 let state = &app.dynamodb_state;
47 app.current_service == Service::DynamoDbTables
48 && is_items_tab(app)
49 && !state.items_loading
50 && state.items_cursor.is_some()
51 && state.items_context.is_some()
52 && state.items_context == context(app)
53}
54
55pub fn results_complete(app: &App) -> bool {
58 let state = &app.dynamodb_state;
59 !state.items_loading
60 && !state.items_failed
61 && state.items_cursor.is_none()
62 && state.items_context.is_some()
63 && state.items_context == context(app)
64 && (state.item_operation != ItemOperation::Query || !state.item_filter.is_empty())
65}
66
67pub fn needs_load(app: &App) -> bool {
68 let state = &app.dynamodb_state;
69 if !is_items_tab(app) || app.mode == Mode::ErrorModal {
70 return false;
71 }
72 if state.items_loading {
73 return true;
74 }
75 if app.mode == Mode::FilterInput {
76 return false;
77 }
78 if state.items_context.is_some() && state.items_context != context(app) {
81 return true;
82 }
83 state.item_operation == ItemOperation::Query
84 && !state.item_filter.is_empty()
85 && state.executed_query != state.item_filter
86}
87
88pub fn load_more(app: &mut App) {
89 if app.mode == Mode::Normal && can_load_more(app) {
90 app.dynamodb_state.items_append = true;
91 app.dynamodb_state.items_loading = true;
92 }
93}
94
95pub fn retry(app: &mut App) {
96 app.dynamodb_state.items_loading = true;
99}
100
101impl State {
102 pub fn clear_items_result(&mut self) {
103 self.items.reset();
104 self.items.items.clear();
105 self.items_cursor = None;
106 self.items_context = None;
107 self.items_append = false;
108 self.items_failed = false;
109 self.items_loading = false;
110 self.executed_query.clear();
111 }
112
113 pub fn begin_items_request(&mut self, context: ItemRequestContext) -> Option<DdbItemCursor> {
114 self.items_append = self.items_append
115 && self.items_context.as_ref() == Some(&context)
116 && self.items_cursor.is_some();
117 if !self.items_append {
118 self.items.reset();
119 self.items.items.clear();
120 self.items_cursor = None;
121 }
122 self.executed_query = context.query.clone().unwrap_or_default();
125 self.items_context = Some(context);
126 self.items_failed = false;
127 self.items_loading = true;
128 self.items_cursor.clone()
129 }
130
131 pub fn finish_items_request(&mut self, page: DdbItemsPage) {
132 self.items.items.extend(page.items);
133 self.items_cursor = page.next_cursor;
134 self.items_loading = false;
135 self.items_append = false;
136 self.items_failed = false;
137 }
138
139 pub fn fail_items_request(&mut self) {
140 self.items_loading = false;
141 self.items_failed = true;
142 }
144}
145
146#[cfg(test)]
147mod tests;