Skip to content

Commit 6d099a4

Browse files
committed
[edit] extract Header component, merge ConnectionStatusBar and StatusBar into Components namespace
1 parent 91ec418 commit 6d099a4

12 files changed

Lines changed: 138 additions & 93 deletions
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
using Spectre.Console;
2+
3+
namespace EtcdTerminal.App.Components;
4+
5+
public static class Header
6+
{
7+
public static void Render()
8+
{
9+
AnsiConsole.Write(new FigletText("etcd-terminal").Color(Color.OrangeRed1).Centered());
10+
}
11+
}
Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
using EtcdTerminal.Models;
2+
using Simplify.System;
3+
4+
namespace EtcdTerminal.App.Components;
5+
6+
public static class StatusBar
7+
{
8+
public static void Render(EtcdConnectionConfig? config = null)
9+
{
10+
var bgSeq = "\x1b[48;2;27;28;30m";
11+
var fgSeq = "\x1b[38;2;210;210;210m";
12+
var greenSeq = "\x1b[38;2;0;200;0m";
13+
var resetSeq = "\x1b[0m";
14+
var fill = new string(' ', Console.WindowWidth);
15+
16+
var left = " (\u2191/\u2193 navigate, Enter confirm, Esc back) ";
17+
var version = GetVersion();
18+
19+
string content;
20+
if (config is not null)
21+
{
22+
var connStr = config.ConnectionString.Length > 50
23+
? config.ConnectionString[..50] + "..."
24+
: config.ConnectionString;
25+
var auth = config.IsAuthenticationEnabled
26+
? $" \x1b[38;2;128;128;128m│\x1b[38;2;210;210;210m {config.Username}"
27+
: "";
28+
var right = $"{greenSeq}\u25cf{fgSeq} {config.Name} \x1b[38;2;128;128;128m│\x1b[38;2;210;210;210m {connStr}{auth} v{version} ";
29+
var pad = Console.WindowWidth - left.Length - GetVisibleLength(right);
30+
if (pad < 1) pad = 1;
31+
content = bgSeq + fgSeq + left + new string(' ', pad) + right + resetSeq;
32+
}
33+
else
34+
{
35+
var right = $"v{version} ";
36+
var pad = Console.WindowWidth - left.Length - right.Length;
37+
if (pad < 1) pad = 1;
38+
content = bgSeq + fgSeq + left + new string(' ', pad) + right + resetSeq;
39+
}
40+
41+
Console.CursorTop = Console.WindowHeight - 3;
42+
Console.CursorLeft = 0;
43+
Console.Write(bgSeq + fill + resetSeq);
44+
45+
Console.CursorTop = Console.WindowHeight - 2;
46+
Console.CursorLeft = 0;
47+
Console.Write(content);
48+
49+
Console.CursorTop = Console.WindowHeight - 1;
50+
Console.CursorLeft = 0;
51+
Console.Write(bgSeq + fill + resetSeq);
52+
}
53+
54+
private static string GetVersion()
55+
{
56+
var version = AssemblyInfo.Entry.Version;
57+
58+
return $"{version.Major}.{version.Minor}" + (version.Build != 0 ? "." + version.Build : "");
59+
}
60+
61+
private static int GetVisibleLength(string s)
62+
{
63+
var len = 0;
64+
for (var i = 0; i < s.Length; i++)
65+
{
66+
if (s[i] == '\x1b')
67+
while (i < s.Length && s[i] != 'm') i++;
68+
else
69+
len++;
70+
}
71+
return len;
72+
}
73+
}

src/EtcdTerminal.App/Engine/Menu.cs

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
using EtcdTerminal;
2-
using EtcdTerminal.App.Modules;
2+
using EtcdTerminal.App.Components;
3+
using EtcdTerminal.Models;
34
using System.Text.RegularExpressions;
45

56
namespace EtcdTerminal.App.Engine;
@@ -10,7 +11,7 @@ public static class Menu
1011
private const string _emptyIndent = " ";
1112
private const string _clearAnsi = "\x1b[J";
1213

13-
public static string? Show(string title, IEnumerable<string> choices, Func<string, string>? displayConverter = null)
14+
public static string? Show(string title, IEnumerable<string> choices, Func<string, string>? displayConverter = null, EtcdConnectionConfig? config = null)
1415
{
1516
var items = choices.ToList();
1617
var index = 0;
@@ -51,7 +52,7 @@ public static class Menu
5152
}
5253

5354
var menuEnd = Console.CursorTop;
54-
StatusBar.Render();
55+
StatusBar.Render(config);
5556
Console.CursorTop = menuEnd;
5657
Console.CursorLeft = 0;
5758

src/EtcdTerminal.App/Modules/ConnectionStatusBar.cs

Lines changed: 0 additions & 29 deletions
This file was deleted.

src/EtcdTerminal.App/Modules/StatusBar.cs

Lines changed: 0 additions & 26 deletions
This file was deleted.

src/EtcdTerminal.App/Screens/InstanceSelectionScreen.cs

Lines changed: 2 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
1+
using EtcdTerminal.App.Components;
12
using EtcdTerminal.App.Engine;
23
using EtcdTerminal.Models;
3-
using Simplify.System;
44
using Spectre.Console;
55

66
namespace EtcdTerminal.App.Screens;
@@ -12,7 +12,6 @@ public sealed class InstanceSelectionScreen(IConnectionConfigRepository _configR
1212
private const string ConnectedSuccess = "[green]Connected successfully![/]";
1313
private const string NameEmpty = "[red]Instance name cannot be empty.[/]";
1414
private const string InvalidConnStr = "[red]Invalid connection string. Must be a valid http or https URL.[/]";
15-
private const string ConsoleClientDesc = "[grey]Console client for etcd v3+[/]";
1615
private const string ManageConnections = "Manage Connections";
1716
private const string AddInstance = "Add Instance";
1817
private const string RemoveInstance = "Remove Instance";
@@ -32,14 +31,7 @@ public sealed class InstanceSelectionScreen(IConnectionConfigRepository _configR
3231
while (true)
3332
{
3433
AnsiConsole.Clear();
35-
36-
AnsiConsole.Write(new FigletText("etcd-terminal").Color(Color.OrangeRed1).Centered());
37-
38-
AnsiConsole.Write(Align.Center(new Markup($"[grey]Version: [/][white]{GetVersion()}[/]")));
39-
Console.WriteLine();
40-
41-
AnsiConsole.Write(Align.Center(new Markup(ConsoleClientDesc)));
42-
Console.WriteLine();
34+
Header.Render();
4335

4436
var instances = _configRepo.LoadInstances();
4537

@@ -213,10 +205,4 @@ private void RemoveInstanceInteractive(IReadOnlyList<EtcdConnectionConfig> insta
213205
Console.ReadKey(true);
214206
}
215207

216-
private string GetVersion()
217-
{
218-
var version = AssemblyInfo.Entry.Version;
219-
220-
return $"{version.Major}.{version.Minor}" + (version.Build != 0 ? "." + version.Build : "");
221-
}
222208
}

src/EtcdTerminal.App/Screens/KeyBrowseScreen.cs

Lines changed: 24 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
using EtcdTerminal;
22
using EtcdTerminal.App.Engine;
3-
using EtcdTerminal.App.Modules;
3+
using EtcdTerminal.App.Components;
44
using EtcdTerminal.Models;
55
using Spectre.Console;
66

@@ -201,7 +201,7 @@ private async Task MainLoopAsync()
201201
private void Render()
202202
{
203203
AnsiConsole.Clear();
204-
ConnectionStatusBar.Render(_config);
204+
Header.Render();
205205

206206
Console.Write(new string(' ', LinePadding));
207207
RenderSearchBar();
@@ -215,6 +215,8 @@ private void Render()
215215

216216
RenderActionBar();
217217

218+
StatusBar.Render(_config);
219+
218220
Console.CursorTop = SearchBarRow;
219221
Console.CursorLeft = _searchEndCol;
220222
}
@@ -290,7 +292,11 @@ private async Task EditKeyAsync()
290292
return;
291293

292294
AnsiConsole.Clear();
293-
ConnectionStatusBar.Render(_config);
295+
Header.Render();
296+
var savedTop = Console.CursorTop;
297+
StatusBar.Render(_config);
298+
Console.CursorTop = savedTop;
299+
Console.CursorLeft = 0;
294300
AnsiConsole.MarkupLine($"Editing key: [cyan]{Markup.Escape(_selectedKey.Key)}[/]");
295301
AnsiConsole.MarkupLine($"Current value: [green]{Markup.Escape(TruncateText(_selectedKey.Value, EditValueMaxLength))}[/]");
296302
Console.WriteLine();
@@ -303,7 +309,11 @@ private async Task EditKeyAsync()
303309
var result = await _etcdClient.UpdateKeyAsync(_selectedKey.Key, newValue);
304310

305311
AnsiConsole.Clear();
306-
ConnectionStatusBar.Render(_config);
312+
Header.Render();
313+
savedTop = Console.CursorTop;
314+
StatusBar.Render(_config);
315+
Console.CursorTop = savedTop;
316+
Console.CursorLeft = 0;
307317

308318
if (result)
309319
{
@@ -326,7 +336,11 @@ private async Task DeleteKeyAsync()
326336
return;
327337

328338
AnsiConsole.Clear();
329-
ConnectionStatusBar.Render(_config);
339+
Header.Render();
340+
var savedTop = Console.CursorTop;
341+
StatusBar.Render(_config);
342+
Console.CursorTop = savedTop;
343+
Console.CursorLeft = 0;
330344
AnsiConsole.MarkupLine($"Delete key: [red]{Markup.Escape(_selectedKey.Key)}[/]");
331345
Console.WriteLine();
332346

@@ -338,7 +352,11 @@ private async Task DeleteKeyAsync()
338352
var result = await _etcdClient.DeleteKeyAsync(_selectedKey.Key);
339353

340354
AnsiConsole.Clear();
341-
ConnectionStatusBar.Render(_config);
355+
Header.Render();
356+
savedTop = Console.CursorTop;
357+
StatusBar.Render(_config);
358+
Console.CursorTop = savedTop;
359+
Console.CursorLeft = 0;
342360

343361
if (result)
344362
{

src/EtcdTerminal.App/Screens/KeyCreateScreen.cs

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
using EtcdTerminal;
22
using EtcdTerminal.App.Engine;
3-
using EtcdTerminal.App.Modules;
3+
using EtcdTerminal.App.Components;
44
using EtcdTerminal.Models;
55
using Spectre.Console;
66

@@ -16,7 +16,11 @@ public sealed class KeyCreateScreen(IEtcdClient _etcdClient)
1616
public async Task ShowAsync(EtcdConnectionConfig config)
1717
{
1818
AnsiConsole.Clear();
19-
ConnectionStatusBar.Render(config);
19+
Header.Render();
20+
var savedTop = Console.CursorTop;
21+
StatusBar.Render(config);
22+
Console.CursorTop = savedTop;
23+
Console.CursorLeft = 0;
2024

2125
var key = Prompt.Ask(EnterKeyPrompt);
2226

src/EtcdTerminal.App/Screens/MainScreen.cs

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
using EtcdTerminal;
22
using EtcdTerminal.App.Engine;
3-
using EtcdTerminal.App.Modules;
3+
using EtcdTerminal.App.Components;
44
using EtcdTerminal.Models;
55
using Spectre.Console;
66

@@ -19,7 +19,7 @@ public async Task ShowAsync(EtcdConnectionConfig config)
1919
while (true)
2020
{
2121
AnsiConsole.Clear();
22-
ConnectionStatusBar.Render(config);
22+
Header.Render();
2323

2424
var choice = Menu.Show(
2525
"",
@@ -31,7 +31,8 @@ public async Task ShowAsync(EtcdConnectionConfig config)
3131
"Manage Roles",
3232
"View Permissions",
3333
"Disconnect"
34-
});
34+
},
35+
config: config);
3536

3637
if (choice is null)
3738
{

src/EtcdTerminal.App/Screens/PermissionViewScreen.cs

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
using EtcdTerminal;
22
using EtcdTerminal.App.Engine;
3-
using EtcdTerminal.App.Modules;
3+
using EtcdTerminal.App.Components;
44
using EtcdTerminal.Models;
55
using Spectre.Console;
66

@@ -14,7 +14,11 @@ public sealed class PermissionViewScreen(IEtcdClient _etcdClient)
1414
public async Task ShowAsync(EtcdConnectionConfig config)
1515
{
1616
AnsiConsole.Clear();
17-
ConnectionStatusBar.Render(config);
17+
Header.Render();
18+
var savedTop = Console.CursorTop;
19+
StatusBar.Render(config);
20+
Console.CursorTop = savedTop;
21+
Console.CursorLeft = 0;
1822

1923
await AnsiConsole.Status()
2024
.StartAsync(LoadingPermissions, async ctx =>

0 commit comments

Comments
 (0)