chore: cargo fmt
This commit is contained in:
+11
-26
@@ -316,7 +316,7 @@ impl DockerData {
|
|||||||
self.gui_state.lock().remove_loading(loading_uuid);
|
self.gui_state.lock().remove_loading(loading_uuid);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Initialize docker container data, before any messages are received
|
/// Initialize docker container data, before any messages are received
|
||||||
async fn initialise_container_data(&mut self) {
|
async fn initialise_container_data(&mut self) {
|
||||||
self.gui_state.lock().status_push(Status::Init);
|
self.gui_state.lock().status_push(Status::Init);
|
||||||
let loading_uuid = Uuid::new_v4();
|
let loading_uuid = Uuid::new_v4();
|
||||||
@@ -341,7 +341,7 @@ impl DockerData {
|
|||||||
self.stop_loading_spin(&loading_spin, loading_uuid);
|
self.stop_loading_spin(&loading_spin, loading_uuid);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Set the global error as the dockererror, and set gui_state to errro
|
/// Set the global error as the docker error, and set gui_state to error
|
||||||
fn set_error(&mut self, error: DockerControls) {
|
fn set_error(&mut self, error: DockerControls) {
|
||||||
self.app_data
|
self.app_data
|
||||||
.lock()
|
.lock()
|
||||||
@@ -349,13 +349,13 @@ impl DockerData {
|
|||||||
self.gui_state.lock().status_push(Status::Error);
|
self.gui_state.lock().status_push(Status::Error);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Execute docker commands, will start and stop the loading spinner
|
/// Execute a docker command, will start and stop the loading spinner, and set correct error
|
||||||
async fn exec_docker(
|
async fn exec_docker(
|
||||||
&mut self,
|
&mut self,
|
||||||
docker_fn: impl Future<Output = Result<(), bollard::errors::Error>>,
|
docker_fn: impl Future<Output = Result<(), bollard::errors::Error>> + Send,
|
||||||
uuid: Uuid,
|
|
||||||
control: DockerControls,
|
control: DockerControls,
|
||||||
) {
|
) {
|
||||||
|
let uuid = Uuid::new_v4();
|
||||||
let loading_spin = self.loading_spin(uuid).await;
|
let loading_spin = self.loading_spin(uuid).await;
|
||||||
if docker_fn.await.is_err() {
|
if docker_fn.await.is_err() {
|
||||||
self.set_error(control);
|
self.set_error(control);
|
||||||
@@ -366,21 +366,15 @@ impl DockerData {
|
|||||||
/// Handle incoming messages, container controls & all container information update
|
/// Handle incoming messages, container controls & all container information update
|
||||||
async fn message_handler(&mut self) {
|
async fn message_handler(&mut self) {
|
||||||
while let Some(message) = self.receiver.recv().await {
|
while let Some(message) = self.receiver.recv().await {
|
||||||
let loading_uuid = Uuid::new_v4();
|
|
||||||
let docker = Arc::clone(&self.docker);
|
let docker = Arc::clone(&self.docker);
|
||||||
match message {
|
match message {
|
||||||
DockerMessage::Pause(id) => {
|
DockerMessage::Pause(id) => {
|
||||||
self.exec_docker(
|
self.exec_docker(docker.pause_container(id.get()), DockerControls::Pause)
|
||||||
docker.pause_container(id.get()),
|
.await;
|
||||||
loading_uuid,
|
|
||||||
DockerControls::Pause,
|
|
||||||
)
|
|
||||||
.await;
|
|
||||||
}
|
}
|
||||||
DockerMessage::Restart(id) => {
|
DockerMessage::Restart(id) => {
|
||||||
self.exec_docker(
|
self.exec_docker(
|
||||||
docker.restart_container(id.get(), None),
|
docker.restart_container(id.get(), None),
|
||||||
loading_uuid,
|
|
||||||
DockerControls::Restart,
|
DockerControls::Restart,
|
||||||
)
|
)
|
||||||
.await;
|
.await;
|
||||||
@@ -388,26 +382,17 @@ impl DockerData {
|
|||||||
DockerMessage::Start(id) => {
|
DockerMessage::Start(id) => {
|
||||||
self.exec_docker(
|
self.exec_docker(
|
||||||
docker.start_container(id.get(), None::<StartContainerOptions<String>>),
|
docker.start_container(id.get(), None::<StartContainerOptions<String>>),
|
||||||
loading_uuid,
|
|
||||||
DockerControls::Start,
|
DockerControls::Start,
|
||||||
)
|
)
|
||||||
.await;
|
.await;
|
||||||
}
|
}
|
||||||
DockerMessage::Stop(id) => {
|
DockerMessage::Stop(id) => {
|
||||||
self.exec_docker(
|
self.exec_docker(docker.stop_container(id.get(), None), DockerControls::Stop)
|
||||||
docker.stop_container(id.get(), None),
|
.await;
|
||||||
loading_uuid,
|
|
||||||
DockerControls::Stop,
|
|
||||||
)
|
|
||||||
.await;
|
|
||||||
}
|
}
|
||||||
DockerMessage::Unpause(id) => {
|
DockerMessage::Unpause(id) => {
|
||||||
self.exec_docker(
|
self.exec_docker(docker.unpause_container(id.get()), DockerControls::Unpause)
|
||||||
docker.unpause_container(id.get()),
|
.await;
|
||||||
loading_uuid,
|
|
||||||
DockerControls::Unpause,
|
|
||||||
)
|
|
||||||
.await;
|
|
||||||
self.update_everything().await;
|
self.update_everything().await;
|
||||||
}
|
}
|
||||||
DockerMessage::Update => self.update_everything().await,
|
DockerMessage::Update => self.update_everything().await,
|
||||||
|
|||||||
@@ -69,7 +69,7 @@ impl InputHandler {
|
|||||||
.lock()
|
.lock()
|
||||||
.status_contains(&[Status::Error, Status::Help]);
|
.status_contains(&[Status::Error, Status::Help]);
|
||||||
if !error_or_help {
|
if !error_or_help {
|
||||||
self.mouse_press(mouse_event)
|
self.mouse_press(mouse_event);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -105,7 +105,7 @@ impl InputHandler {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// If the info box sleep handle is currently being executed, as in m is pressed twice within a 4000ms window
|
// If the info box sleep handle is currently being executed, as in 'm' is pressed twice within a 4000ms window
|
||||||
// then cancel the first handle, as a new handle will be invoked
|
// then cancel the first handle, as a new handle will be invoked
|
||||||
if let Some(info_sleep_timer) = self.info_sleep.as_ref() {
|
if let Some(info_sleep_timer) = self.info_sleep.as_ref() {
|
||||||
info_sleep_timer.abort();
|
info_sleep_timer.abort();
|
||||||
@@ -134,21 +134,21 @@ impl InputHandler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Send a quit message to docker, to abort all spawns, if an error is return, set is_running to false here instead
|
/// Send a quit message to docker, to abort all spawns, if an error is return, set is_running to false here instead
|
||||||
|
/// If gui_status is Error or Init, then just set the is_running to false immediately, for a quicker exit
|
||||||
async fn quit(&self) {
|
async fn quit(&self) {
|
||||||
let error_init = self
|
let error_init = self
|
||||||
.gui_state
|
.gui_state
|
||||||
.lock()
|
.lock()
|
||||||
.status_contains(&[Status::Error, Status::Init]);
|
.status_contains(&[Status::Error, Status::Init]);
|
||||||
if error_init {
|
if error_init || self.docker_sender.send(DockerMessage::Quit).await.is_err() {
|
||||||
self.is_running.store(false, Ordering::SeqCst);
|
self.is_running.store(false, Ordering::SeqCst);
|
||||||
} else if self.docker_sender.send(DockerMessage::Quit).await.is_err() {
|
|
||||||
self.is_running.store(false, Ordering::SeqCst)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Handle any keyboard button events
|
/// Handle any keyboard button events
|
||||||
#[allow(clippy::too_many_lines)]
|
#[allow(clippy::too_many_lines)]
|
||||||
async fn button_press(&mut self, key_code: KeyCode) {
|
async fn button_press(&mut self, key_code: KeyCode) {
|
||||||
|
// TODO - refactor this to a single call, maybe return Error, Help or Normal
|
||||||
let contains_error = self.gui_state.lock().status_contains(&[Status::Error]);
|
let contains_error = self.gui_state.lock().status_contains(&[Status::Error]);
|
||||||
let contains_help = self.gui_state.lock().status_contains(&[Status::Help]);
|
let contains_help = self.gui_state.lock().status_contains(&[Status::Help]);
|
||||||
|
|
||||||
|
|||||||
+17
-21
@@ -45,29 +45,25 @@ async fn main() {
|
|||||||
let (docker_sx, docker_rx) = tokio::sync::mpsc::channel(16);
|
let (docker_sx, docker_rx) = tokio::sync::mpsc::channel(16);
|
||||||
|
|
||||||
// Create docker daemon handler, and only spawn up the docker data handler if ping returns non-error
|
// Create docker daemon handler, and only spawn up the docker data handler if ping returns non-error
|
||||||
match Docker::connect_with_socket_defaults() {
|
if let Ok(docker) = Docker::connect_with_socket_defaults() {
|
||||||
Ok(docker) => match docker.ping().await {
|
if docker.ping().await.is_ok() {
|
||||||
Ok(_) => {
|
let docker = Arc::new(docker);
|
||||||
let docker = Arc::new(docker);
|
let is_running = Arc::clone(&is_running);
|
||||||
let is_running = Arc::clone(&is_running);
|
tokio::spawn(DockerData::init(
|
||||||
tokio::spawn(DockerData::init(
|
args,
|
||||||
args,
|
docker_app_data,
|
||||||
docker_app_data,
|
docker,
|
||||||
docker,
|
docker_gui_state,
|
||||||
docker_gui_state,
|
docker_rx,
|
||||||
docker_rx,
|
is_running,
|
||||||
is_running,
|
));
|
||||||
));
|
} else {
|
||||||
}
|
|
||||||
Err(_) => {
|
|
||||||
app_data.lock().set_error(AppError::DockerConnect);
|
|
||||||
docker_gui_state.lock().status_push(Status::DockerConnect)
|
|
||||||
}
|
|
||||||
},
|
|
||||||
Err(_) => {
|
|
||||||
app_data.lock().set_error(AppError::DockerConnect);
|
app_data.lock().set_error(AppError::DockerConnect);
|
||||||
docker_gui_state.lock().status_push(Status::DockerConnect)
|
docker_gui_state.lock().status_push(Status::DockerConnect);
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
app_data.lock().set_error(AppError::DockerConnect);
|
||||||
|
docker_gui_state.lock().status_push(Status::DockerConnect);
|
||||||
}
|
}
|
||||||
let input_app_data = Arc::clone(&app_data);
|
let input_app_data = Arc::clone(&app_data);
|
||||||
|
|
||||||
|
|||||||
@@ -51,7 +51,9 @@ fn generate_block<'a>(
|
|||||||
gui_state: &Arc<Mutex<GuiState>>,
|
gui_state: &Arc<Mutex<GuiState>>,
|
||||||
panel: SelectablePanel,
|
panel: SelectablePanel,
|
||||||
) -> Block<'a> {
|
) -> Block<'a> {
|
||||||
gui_state.lock().update_map(Region::Panel(panel), area);
|
gui_state
|
||||||
|
.lock()
|
||||||
|
.update_heading_map(Region::Panel(panel), area);
|
||||||
let current_selected_panel = gui_state.lock().selected_panel;
|
let current_selected_panel = gui_state.lock().selected_panel;
|
||||||
let title = match panel {
|
let title = match panel {
|
||||||
SelectablePanel::Containers => {
|
SelectablePanel::Containers => {
|
||||||
@@ -466,7 +468,9 @@ pub fn heading_bar<B: Backend>(
|
|||||||
// draw the actual header blocks
|
// draw the actual header blocks
|
||||||
for (index, (paragraph, header, _)) in header_data.into_iter().enumerate() {
|
for (index, (paragraph, header, _)) in header_data.into_iter().enumerate() {
|
||||||
let rect = headers_section[index];
|
let rect = headers_section[index];
|
||||||
gui_state.lock().update_map(Region::Header(header), rect);
|
gui_state
|
||||||
|
.lock()
|
||||||
|
.update_heading_map(Region::Header(header), rect);
|
||||||
f.render_widget(paragraph, rect);
|
f.render_widget(paragraph, rect);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -501,7 +505,7 @@ fn max_line_width(text: &str) -> usize {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Draw the help box in the centre of the screen
|
/// Draw the help box in the centre of the screen
|
||||||
/// TODO this is message, should make every line it's own renderable span
|
/// TODO should make every line it's own renderable span
|
||||||
pub fn help_box<B: Backend>(f: &mut Frame<'_, B>) {
|
pub fn help_box<B: Backend>(f: &mut Frame<'_, B>) {
|
||||||
let title = format!(" {} ", VERSION);
|
let title = format!(" {} ", VERSION);
|
||||||
|
|
||||||
|
|||||||
+9
-7
@@ -173,7 +173,7 @@ impl fmt::Display for Loading {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// The application can be in these four states
|
/// The application gui state can be in multiple of these four states at the same time
|
||||||
/// Various functions (e.g input handler), operate differently depending upon current Status
|
/// Various functions (e.g input handler), operate differently depending upon current Status
|
||||||
#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq)]
|
#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq)]
|
||||||
pub enum Status {
|
pub enum Status {
|
||||||
@@ -237,7 +237,7 @@ impl GuiState {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Insert, or updates header area panel into heading_map
|
/// Insert, or updates header area panel into heading_map
|
||||||
pub fn update_map(&mut self, region: Region, area: Rect) {
|
pub fn update_heading_map(&mut self, region: Region, area: Rect) {
|
||||||
match region {
|
match region {
|
||||||
Region::Header(header) => self
|
Region::Header(header) => self
|
||||||
.heading_map
|
.heading_map
|
||||||
@@ -252,16 +252,19 @@ impl GuiState {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn status_push(&mut self, status: Status) {
|
/// Check if the current gui_status contains any of the given status'
|
||||||
self.status.insert(status);
|
pub fn status_contains(&self, status: &[Status]) -> bool {
|
||||||
|
status.iter().any(|i| self.status.contains(i))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Remove a gui_status into the current gui_status hashset
|
||||||
pub fn status_del(&mut self, status: Status) {
|
pub fn status_del(&mut self, status: Status) {
|
||||||
self.status.remove(&status);
|
self.status.remove(&status);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn status_contains(&self, status: &[Status]) -> bool {
|
/// Insert a gui_status into the current gui_status hashset
|
||||||
status.iter().any(|i| self.status.contains(i))
|
pub fn status_push(&mut self, status: Status) {
|
||||||
|
self.status.insert(status);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Change to next selectable panel
|
/// Change to next selectable panel
|
||||||
@@ -281,7 +284,6 @@ impl GuiState {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// If is_loading has any entries, return the current loading_icon, else an emtpy string
|
/// If is_loading has any entries, return the current loading_icon, else an emtpy string
|
||||||
// Option<String>?
|
|
||||||
pub fn get_loading(&mut self) -> String {
|
pub fn get_loading(&mut self) -> String {
|
||||||
if self.is_loading.is_empty() {
|
if self.is_loading.is_empty() {
|
||||||
String::from(" ")
|
String::from(" ")
|
||||||
|
|||||||
@@ -83,10 +83,7 @@ async fn run_app<B: Backend + Send>(
|
|||||||
update_duration: Duration,
|
update_duration: Duration,
|
||||||
) -> Result<(), AppError> {
|
) -> Result<(), AppError> {
|
||||||
let input_poll_rate = std::time::Duration::from_millis(75);
|
let input_poll_rate = std::time::Duration::from_millis(75);
|
||||||
|
|
||||||
// Check for docker connect errors before attempting to draw the gui
|
|
||||||
let status_dockerconnect = gui_state.lock().status_contains(&[Status::DockerConnect]);
|
let status_dockerconnect = gui_state.lock().status_contains(&[Status::DockerConnect]);
|
||||||
|
|
||||||
if status_dockerconnect {
|
if status_dockerconnect {
|
||||||
let mut seconds = 5;
|
let mut seconds = 5;
|
||||||
loop {
|
loop {
|
||||||
@@ -139,7 +136,6 @@ async fn run_app<B: Backend + Send>(
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// }
|
|
||||||
}
|
}
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user