Skip to content

Saved connection#18

Merged
vimlinuz merged 12 commits intomainfrom
saved_connection
Dec 29, 2025
Merged

Saved connection#18
vimlinuz merged 12 commits intomainfrom
saved_connection

Conversation

@vimlinuz
Copy link
Copy Markdown
Owner

@vimlinuz vimlinuz commented Dec 29, 2025

list
handlers
type
that are required to view the saved connection are added with some of the refact

Summary by CodeRabbit

  • New Features
    • Added a "Saved Connections" view accessible with the 's' key.
    • Displays previously connected Wi‑Fi SSIDs with "LAST USED" timestamps in a two-column table and header.
    • Supports navigation (arrow keys and j/k), selection highlight with wrap-around, and Escape to close.

✏️ Tip: You can customize this high-level summary in your review settings.

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai bot commented Dec 29, 2025

📝 Walkthrough

Walkthrough

Adds a saved-connections feature: new module to fetch and store Wi‑Fi connections via nmcli, App state fields to show/select saved connections, event handling to open/navigate the list, run-loop integration, and UI rendering for a selectable saved-connections table.

Changes

Cohort / File(s) Summary
Core App State
src/apps/core.rs
Added mod saved_connection; and use crate::apps::core::saved_connection::SavedConnections;. Extended App with show_saved: bool and saved_connection: SavedConnections; initialized in Default.
Event Handling
src/apps/core/event_handlers.rs
Added key binding for Char('s') (Press) to call open_saved_list() and integrate saved-list toggle into existing event match.
Saved Connections Module
src/apps/core/saved_connection.rs
New module adding Connections and SavedConnections; fetch_saved_connections() runs nmcli and parses 802-11-wireless entries; includes handle_saved(), update_selected_saved_network(), open_saved_list(), close_saved_list().
Run Loop Integration
src/apps/core/run.rs
Added branch in main loop to call handle_saved() when show_saved is true (placed before delete confirmation handling).
UI Rendering
src/apps/core/widget.rs
Renders centered "Saved Connections" block when show_saved is true: header (SSID / LAST USED), two-column table, highlights selected row, and hides cursor during render.

Sequence Diagram(s)

sequenceDiagram
    participant User
    participant App
    participant SavedConnections
    participant nmcli
    participant UI

    User->>App: press 's'
    App->>App: handle_events() → open_saved_list()
    App->>SavedConnections: fetch_saved_connections()
    SavedConnections->>nmcli: execute nmcli (NAME,TYPE,TIMESTAMP-REAL)
    nmcli-->>SavedConnections: return output
    SavedConnections->>SavedConnections: parse & filter 802-11-wireless
    SavedConnections-->>App: populate connections

    User->>App: press 'j' / Down
    App->>App: handle_saved() → update_selected_saved_network(+1)
    App->>UI: request render of saved table
    UI->>User: display saved table with highlighted row

    User->>App: press Esc
    App->>App: close_saved_list() (show_saved = false)
    UI->>User: hide saved table
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Poem

🐰 I sniffed through nmcli's trail,
Found old SSIDs on the trail,
Press 's' to show, hop 'j' and 'k',
Magenta box lights the way,
A tiny rabbit hums: "Networks, hooray!"

Pre-merge checks and finishing touches

❌ Failed checks (1 warning, 1 inconclusive)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
Title check ❓ Inconclusive The pull request title 'Saved connection' is vague and generic. While it relates to the changeset, it lacks specificity about the actual functionality being introduced (e.g., adding saved Wi-Fi connections list popup, displaying saved networks, or viewing saved connections). Consider using a more descriptive title such as 'Add saved Wi-Fi connections list popup' or 'Implement UI for viewing saved network connections' to better convey the main change.
✅ Passed checks (1 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch saved_connection

📜 Recent review details

Configuration used: defaults

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 25e29f7 and b1181b1.

📒 Files selected for processing (1)
  • src/apps/core/widget.rs
🚧 Files skipped from review as they are similar to previous changes (1)
  • src/apps/core/widget.rs

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 5

📜 Review details

Configuration used: defaults

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 68b7010 and 2358c35.

📒 Files selected for processing (4)
  • src/apps/core.rs
  • src/apps/core/event_handlers.rs
  • src/apps/core/saved_connection.rs
  • src/apps/core/widget.rs
🧰 Additional context used
🧬 Code graph analysis (3)
src/apps/core.rs (1)
src/apps/handlers/status.rs (1)
  • default (13-19)
src/apps/core/widget.rs (1)
src/apps/core.rs (1)
  • default (29-42)
src/apps/core/saved_connection.rs (1)
src/apps/handlers/status.rs (1)
  • new (23-28)
🔇 Additional comments (6)
src/apps/core/event_handlers.rs (1)

101-107: LGTM! Key binding follows existing patterns.

The 's' key binding is correctly implemented and consistent with other key handlers in the file.

src/apps/core/widget.rs (1)

96-124: LGTM! Saved connections rendering follows established patterns.

The rendering block correctly overlays the main UI, applies appropriate styling, and uses the correct selection index from saved_connection.selected_index.

src/apps/core.rs (2)

3-3: LGTM! Module and import declarations are correct.

The new module is properly declared and the import follows the correct path structure.

Also applies to: 7-7


23-23: LGTM! Struct fields and initialization are correct.

The new fields are properly typed and initialized with appropriate default values.

Also applies to: 25-25, 39-40

src/apps/core/saved_connection.rs (2)

9-19: LGTM! Struct definitions are clear and appropriate.

The Connections and SavedConnections structs are well-defined with appropriate fields and derive traits.


123-140: LGTM! Helper methods are correctly implemented.

The navigation and list management methods properly handle bounds checking, wrap-around selection, and state management.

Comment on lines +23 to +27
pub fn fetch_saved_connections(&mut self) {
let output = Command::new("nmcli")
.args(["-t", "-f", "NAME,TYPE,TIMESTAMP-REAL", "connection", "show"])
.output()
.expect(" Failed to execute nmcli command");
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🔴 Critical

Replace panic with graceful error handling.

Using .expect() will cause the application to panic if the nmcli command fails or is not installed. Consider handling the error gracefully and setting an empty connections list instead.

🔎 Proposed fix
 pub fn fetch_saved_connections(&mut self) {
-    let output = Command::new("nmcli")
-        .args(["-t", "-f", "NAME,TYPE,TIMESTAMP-REAL", "connection", "show"])
-        .output()
-        .expect(" Failed to execute nmcli command");
+    let output = match Command::new("nmcli")
+        .args(["-t", "-f", "NAME,TYPE,TIMESTAMP-REAL", "connection", "show"])
+        .output() {
+        Ok(output) => output,
+        Err(_) => {
+            self.connections = Vec::new();
+            return;
+        }
+    };
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
pub fn fetch_saved_connections(&mut self) {
let output = Command::new("nmcli")
.args(["-t", "-f", "NAME,TYPE,TIMESTAMP-REAL", "connection", "show"])
.output()
.expect(" Failed to execute nmcli command");
pub fn fetch_saved_connections(&mut self) {
let output = match Command::new("nmcli")
.args(["-t", "-f", "NAME,TYPE,TIMESTAMP-REAL", "connection", "show"])
.output() {
Ok(output) => output,
Err(_) => {
self.connections = Vec::new();
return;
}
};

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

♻️ Duplicate comments (1)
src/apps/core/saved_connection.rs (1)

23-26: Replace panic with graceful error handling.

The .expect() call will crash the application if nmcli is unavailable or fails to execute. This was previously flagged as a critical issue.

🔎 Proposed fix
-    let output = Command::new("nmcli")
-        .args(["-t", "-f", "NAME,TYPE,TIMESTAMP-REAL", "connection", "show"])
-        .output()
-        .expect(" Failed to execute nmcli command");
+    let output = match Command::new("nmcli")
+        .args(["-t", "-f", "NAME,TYPE,TIMESTAMP-REAL", "connection", "show"])
+        .output() {
+        Ok(output) => output,
+        Err(_) => {
+            self.connections = Vec::new();
+            return;
+        }
+    };
🧹 Nitpick comments (1)
src/apps/core/saved_connection.rs (1)

78-82: Clarify or implement the 'd' key handler.

The empty handler for the 'd' key appears to be a placeholder. If this is intended for deleting saved connections, consider implementing it or leaving a TODO comment. If it's not needed, remove it.

Do you want me to help implement delete functionality for saved connections, or should this handler be removed?

📜 Review details

Configuration used: defaults

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 2358c35 and 25e29f7.

📒 Files selected for processing (2)
  • src/apps/core/run.rs
  • src/apps/core/saved_connection.rs
🔇 Additional comments (4)
src/apps/core/run.rs (1)

15-18: LGTM! Clean integration of saved connections popup handling.

The new branch follows the established pattern for popup handling in the run loop and integrates correctly with the saved connections feature.

src/apps/core/saved_connection.rs (3)

8-18: LGTM! Well-structured data models.

The Connections and SavedConnections structs are clean and appropriate for managing saved Wi-Fi network state.


117-125: LGTM! Correct wrap-around navigation logic.

The use of rem_euclid provides proper wrap-around behavior, and the empty list check prevents index errors.


126-133: LGTM! Clean popup state management.

Both open_saved_list and close_saved_list methods correctly manage the saved connections popup state.

Comment on lines +43 to +61
let connection_type = parts
.next()
.map(|s| {
if s.is_empty() {
"Unsecured".to_string()
} else {
s.to_string()
}
})
.unwrap_or("".to_string());

let last_used = parts.next().unwrap_or("").to_string();

if !ssid.is_empty()
&& !connection_type.is_empty()
&& connection_type == "802-11-wireless"
{
connections.push(Connections { ssid, last_used });
}
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🛠️ Refactor suggestion | 🟠 Major

Remove dead code: "Unsecured" mapping is never used.

Lines 43-52 map empty connection types to "Unsecured", but line 58 filters exclusively for "802-11-wireless", so these "Unsecured" entries are always filtered out. Either extend the filter to include unsecured connections or remove the unnecessary mapping logic.

🔎 Proposed fix: Remove the unused mapping
-    // if the connection type is empty, it means its unsecured
-    let connection_type = parts
-        .next()
-        .map(|s| {
-            if s.is_empty() {
-                "Unsecured".to_string()
-            } else {
-                s.to_string()
-            }
-        })
-        .unwrap_or("".to_string());
+    let connection_type = parts.next().unwrap_or("").to_string();
 
     let last_used = parts.next().unwrap_or("").to_string();
 
-    if !ssid.is_empty()
-        && !connection_type.is_empty()
-        && connection_type == "802-11-wireless"
-    {
+    if !ssid.is_empty() && connection_type == "802-11-wireless" {
         connections.push(Connections { ssid, last_used });
     }
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
let connection_type = parts
.next()
.map(|s| {
if s.is_empty() {
"Unsecured".to_string()
} else {
s.to_string()
}
})
.unwrap_or("".to_string());
let last_used = parts.next().unwrap_or("").to_string();
if !ssid.is_empty()
&& !connection_type.is_empty()
&& connection_type == "802-11-wireless"
{
connections.push(Connections { ssid, last_used });
}
let connection_type = parts.next().unwrap_or("").to_string();
let last_used = parts.next().unwrap_or("").to_string();
if !ssid.is_empty() && connection_type == "802-11-wireless" {
connections.push(Connections { ssid, last_used });
}
🤖 Prompt for AI Agents
In src/apps/core/saved_connection.rs around lines 43 to 61, the branch that maps
an empty connection type to "Unsecured" is dead because later code only accepts
"802-11-wireless"; remove that unused mapping by replacing the map/if block with
a simple parts.next().unwrap_or("".to_string()) (or similar direct assignment)
so connection_type contains the raw value, and keep the existing filter that
checks for "802-11-wireless"; alternatively, if you intended to accept unsecured
entries, extend the filter to also allow "Unsecured" instead of keeping the
mapping—pick one approach and remove the unreachable mapping logic accordingly.

@vimlinuz vimlinuz merged commit 4e8aa35 into main Dec 29, 2025
3 checks passed
@vimlinuz vimlinuz deleted the saved_connection branch December 29, 2025 14:42
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant