Fix Test Connection buttons needing a tab switch to activate
Root cause: on macOS, SecureField's bound value only commits when the field loses focus (Return, click-away, tab switch) — not on every keystroke like TextField. Every "Test Connection" button (Sync, Email, Paperless, Anytype, Jarvis) gated its .disabled(...) on a *Configured value fed by a SecureField-backed API key/token/password, so typing a key straight into the field left the button looking permanently disabled until something else forced a focus change. Moved the "configured" check from the disabled condition into each test function's action handler instead — by the time a click fires, the click itself has already moved focus away and committed the field's value, so the check now sees it correctly. Buttons stay clickable at all times (gated only by their own isTesting spinner state) and show a clear "Enter X first" message if config is actually incomplete.
This commit is contained in:
@@ -2131,7 +2131,7 @@ It's better to admit "I need more information" or "I cannot do that" than to fak
|
|||||||
Text("Test Connection")
|
Text("Test Connection")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
.disabled(isTestingSync || !settingsService.syncConfigured)
|
.disabled(isTestingSync)
|
||||||
if let result = syncTestResult {
|
if let result = syncTestResult {
|
||||||
Text(result)
|
Text(result)
|
||||||
.font(.system(size: 13))
|
.font(.system(size: 13))
|
||||||
@@ -2431,7 +2431,7 @@ It's better to admit "I need more information" or "I cannot do that" than to fak
|
|||||||
Text("Test Connection")
|
Text("Test Connection")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
.disabled(isTestingEmailConnection || !settingsService.emailServerConfigured)
|
.disabled(isTestingEmailConnection)
|
||||||
if let result = emailConnectionTestResult {
|
if let result = emailConnectionTestResult {
|
||||||
Text(result)
|
Text(result)
|
||||||
.font(.system(size: settingsService.guiTextSize - 1))
|
.font(.system(size: settingsService.guiTextSize - 1))
|
||||||
@@ -2714,7 +2714,7 @@ It's better to admit "I need more information" or "I cannot do that" than to fak
|
|||||||
Text("Test Connection")
|
Text("Test Connection")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
.disabled(isTestingPaperless || !settingsService.paperlessConfigured)
|
.disabled(isTestingPaperless)
|
||||||
if let result = paperlessTestResult {
|
if let result = paperlessTestResult {
|
||||||
Text(result)
|
Text(result)
|
||||||
.font(.system(size: 13))
|
.font(.system(size: 13))
|
||||||
@@ -2748,6 +2748,11 @@ It's better to admit "I need more information" or "I cannot do that" than to fak
|
|||||||
private func testPaperlessConnection() async {
|
private func testPaperlessConnection() async {
|
||||||
isTestingPaperless = true
|
isTestingPaperless = true
|
||||||
paperlessTestResult = nil
|
paperlessTestResult = nil
|
||||||
|
guard settingsService.paperlessConfigured else {
|
||||||
|
paperlessTestResult = "✗ Enter a base URL and API token first."
|
||||||
|
isTestingPaperless = false
|
||||||
|
return
|
||||||
|
}
|
||||||
let result = await PaperlessService.shared.testConnection()
|
let result = await PaperlessService.shared.testConnection()
|
||||||
await MainActor.run {
|
await MainActor.run {
|
||||||
switch result {
|
switch result {
|
||||||
@@ -2825,7 +2830,7 @@ It's better to admit "I need more information" or "I cannot do that" than to fak
|
|||||||
Text("Test Connection")
|
Text("Test Connection")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
.disabled(isTestingAnytype || !settingsService.anytypeMcpConfigured)
|
.disabled(isTestingAnytype)
|
||||||
if let result = anytypeTestResult {
|
if let result = anytypeTestResult {
|
||||||
Text(result)
|
Text(result)
|
||||||
.font(.system(size: 13))
|
.font(.system(size: 13))
|
||||||
@@ -2920,7 +2925,7 @@ It's better to admit "I need more information" or "I cannot do that" than to fak
|
|||||||
Text("Test Connection")
|
Text("Test Connection")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
.disabled(isTestingJarvis || !settingsService.jarvisConfigured)
|
.disabled(isTestingJarvis)
|
||||||
if let result = jarvisTestResult {
|
if let result = jarvisTestResult {
|
||||||
Text(result)
|
Text(result)
|
||||||
.font(.system(size: 13))
|
.font(.system(size: 13))
|
||||||
@@ -2951,6 +2956,11 @@ It's better to admit "I need more information" or "I cannot do that" than to fak
|
|||||||
private func testJarvisConnection() async {
|
private func testJarvisConnection() async {
|
||||||
isTestingJarvis = true
|
isTestingJarvis = true
|
||||||
jarvisTestResult = nil
|
jarvisTestResult = nil
|
||||||
|
guard settingsService.jarvisConfigured else {
|
||||||
|
jarvisTestResult = "✗ Enter a URL and API key first."
|
||||||
|
isTestingJarvis = false
|
||||||
|
return
|
||||||
|
}
|
||||||
let ok = await JarvisService.shared.testConnection()
|
let ok = await JarvisService.shared.testConnection()
|
||||||
await MainActor.run {
|
await MainActor.run {
|
||||||
jarvisTestResult = ok ? "✓ Connected" : "✗ Connection failed"
|
jarvisTestResult = ok ? "✓ Connected" : "✗ Connection failed"
|
||||||
@@ -2961,6 +2971,11 @@ It's better to admit "I need more information" or "I cannot do that" than to fak
|
|||||||
private func testAnytypeConnection() async {
|
private func testAnytypeConnection() async {
|
||||||
isTestingAnytype = true
|
isTestingAnytype = true
|
||||||
anytypeTestResult = nil
|
anytypeTestResult = nil
|
||||||
|
guard settingsService.anytypeMcpConfigured else {
|
||||||
|
anytypeTestResult = "✗ Enter an API key first."
|
||||||
|
isTestingAnytype = false
|
||||||
|
return
|
||||||
|
}
|
||||||
let result = await AnytypeMCPService.shared.testConnection()
|
let result = await AnytypeMCPService.shared.testConnection()
|
||||||
await MainActor.run {
|
await MainActor.run {
|
||||||
switch result {
|
switch result {
|
||||||
@@ -3389,6 +3404,12 @@ It's better to admit "I need more information" or "I cannot do that" than to fak
|
|||||||
isTestingEmailConnection = true
|
isTestingEmailConnection = true
|
||||||
emailConnectionTestResult = nil
|
emailConnectionTestResult = nil
|
||||||
|
|
||||||
|
guard settingsService.emailServerConfigured else {
|
||||||
|
emailConnectionTestResult = "✗ Enter your IMAP/SMTP host, username, and password first."
|
||||||
|
isTestingEmailConnection = false
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
do {
|
do {
|
||||||
let result = try await EmailService.shared.testConnection()
|
let result = try await EmailService.shared.testConnection()
|
||||||
emailConnectionTestResult = "✓ \(result)"
|
emailConnectionTestResult = "✓ \(result)"
|
||||||
@@ -3405,6 +3426,12 @@ It's better to admit "I need more information" or "I cannot do that" than to fak
|
|||||||
isTestingSync = true
|
isTestingSync = true
|
||||||
syncTestResult = nil
|
syncTestResult = nil
|
||||||
|
|
||||||
|
guard settingsService.syncConfigured else {
|
||||||
|
syncTestResult = "✗ Enter a repository URL and credentials first."
|
||||||
|
isTestingSync = false
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
do {
|
do {
|
||||||
let result = try await gitSync.testConnection()
|
let result = try await gitSync.testConnection()
|
||||||
syncTestResult = "✓ \(result)"
|
syncTestResult = "✓ \(result)"
|
||||||
|
|||||||
Reference in New Issue
Block a user