mirror of
https://github.com/samsonjs/vibetunnel.git
synced 2026-04-27 15:17:38 +00:00
Ensure tailscale can be disabled when not running
This commit is contained in:
parent
8814f2623f
commit
459cf52ef6
2 changed files with 160 additions and 82 deletions
|
|
@ -311,7 +311,59 @@ private struct TailscaleIntegrationSection: View {
|
||||||
.buttonStyle(.link)
|
.buttonStyle(.link)
|
||||||
.controlSize(.small)
|
.controlSize(.small)
|
||||||
}
|
}
|
||||||
} else if tailscaleService.isRunning {
|
} else if !tailscaleService.isRunning {
|
||||||
|
// Show Tailscale preferences even when not running
|
||||||
|
VStack(alignment: .leading, spacing: 12) {
|
||||||
|
// Tailscale Serve toggle - always available when installed
|
||||||
|
HStack {
|
||||||
|
Toggle("Enable Tailscale Serve Integration", isOn: $tailscaleServeEnabled)
|
||||||
|
.onChange(of: tailscaleServeEnabled) { _, newValue in
|
||||||
|
logger.info("Tailscale Serve integration \(newValue ? "enabled" : "disabled")")
|
||||||
|
// Restart server to apply the new setting
|
||||||
|
Task {
|
||||||
|
await serverManager.restart()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Spacer()
|
||||||
|
|
||||||
|
// Show status when enabled but not running
|
||||||
|
if tailscaleServeEnabled {
|
||||||
|
HStack(spacing: 4) {
|
||||||
|
Image(systemName: "exclamationmark.triangle.fill")
|
||||||
|
.foregroundColor(.orange)
|
||||||
|
Text("Tailscale not running")
|
||||||
|
.font(.caption)
|
||||||
|
.foregroundColor(.orange)
|
||||||
|
}
|
||||||
|
.frame(height: 16)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Show action button to start Tailscale
|
||||||
|
if tailscaleService.isInstalled && !tailscaleService.isRunning {
|
||||||
|
Button(action: {
|
||||||
|
tailscaleService.openTailscaleApp()
|
||||||
|
}, label: {
|
||||||
|
HStack(spacing: 4) {
|
||||||
|
Image(systemName: "play.circle")
|
||||||
|
Text("Start Tailscale")
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.buttonStyle(.borderedProminent)
|
||||||
|
.controlSize(.small)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Show help text about what will happen when enabled
|
||||||
|
if tailscaleServeEnabled {
|
||||||
|
Text("Tailscale Serve will activate automatically when Tailscale is running.")
|
||||||
|
.font(.caption)
|
||||||
|
.foregroundColor(.secondary)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// Tailscale is running - show full interface
|
||||||
|
VStack(alignment: .leading, spacing: 12) {
|
||||||
// Tailscale Serve toggle
|
// Tailscale Serve toggle
|
||||||
HStack {
|
HStack {
|
||||||
Toggle("Enable Tailscale Serve Integration", isOn: $tailscaleServeEnabled)
|
Toggle("Enable Tailscale Serve Integration", isOn: $tailscaleServeEnabled)
|
||||||
|
|
@ -410,6 +462,7 @@ private struct TailscaleIntegrationSection: View {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
} header: {
|
} header: {
|
||||||
Text("Tailscale Integration")
|
Text("Tailscale Integration")
|
||||||
.font(.headline)
|
.font(.headline)
|
||||||
|
|
|
||||||
|
|
@ -88,6 +88,11 @@ struct AccessModeView: View {
|
||||||
@AppStorage(AppConstants.UserDefaultsKeys.tailscaleServeEnabled)
|
@AppStorage(AppConstants.UserDefaultsKeys.tailscaleServeEnabled)
|
||||||
private var tailscaleServeEnabled = false
|
private var tailscaleServeEnabled = false
|
||||||
|
|
||||||
|
@Environment(TailscaleService.self)
|
||||||
|
private var tailscaleService
|
||||||
|
@Environment(TailscaleServeStatusService.self)
|
||||||
|
private var tailscaleServeStatus
|
||||||
|
|
||||||
var body: some View {
|
var body: some View {
|
||||||
VStack(alignment: .leading, spacing: 8) {
|
VStack(alignment: .leading, spacing: 8) {
|
||||||
HStack {
|
HStack {
|
||||||
|
|
@ -95,14 +100,14 @@ struct AccessModeView: View {
|
||||||
.font(.callout)
|
.font(.callout)
|
||||||
Spacer()
|
Spacer()
|
||||||
|
|
||||||
if tailscaleServeEnabled {
|
if shouldLockToLocalhost {
|
||||||
// When Tailscale Serve is enabled, force localhost mode
|
// Only lock when Tailscale Serve is actually working
|
||||||
Text("Localhost")
|
Text("Localhost")
|
||||||
.foregroundColor(.secondary)
|
.foregroundColor(.secondary)
|
||||||
|
|
||||||
Image(systemName: "lock.shield.fill")
|
Image(systemName: "lock.shield.fill")
|
||||||
.foregroundColor(.blue)
|
.foregroundColor(.blue)
|
||||||
.help("Tailscale Serve requires localhost binding for security")
|
.help("Tailscale Serve active - locked to localhost for security")
|
||||||
} else {
|
} else {
|
||||||
Picker("", selection: $accessModeString) {
|
Picker("", selection: $accessModeString) {
|
||||||
ForEach(DashboardAccessMode.allCases, id: \.rawValue) { mode in
|
ForEach(DashboardAccessMode.allCases, id: \.rawValue) { mode in
|
||||||
|
|
@ -117,7 +122,20 @@ struct AccessModeView: View {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if tailscaleServeEnabled && accessMode == .network {
|
// Show warning when Tailscale Serve is enabled but not working
|
||||||
|
if tailscaleServeEnabled && !shouldLockToLocalhost {
|
||||||
|
HStack(spacing: 4) {
|
||||||
|
Image(systemName: "exclamationmark.triangle.fill")
|
||||||
|
.foregroundColor(.orange)
|
||||||
|
.font(.caption)
|
||||||
|
Text("Tailscale Serve enabled but not active - using selected access mode")
|
||||||
|
.font(.caption)
|
||||||
|
.foregroundColor(.secondary)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Show info when Tailscale Serve is active and locked
|
||||||
|
if shouldLockToLocalhost && accessMode == .network {
|
||||||
HStack(spacing: 4) {
|
HStack(spacing: 4) {
|
||||||
Image(systemName: "info.circle.fill")
|
Image(systemName: "info.circle.fill")
|
||||||
.foregroundColor(.blue)
|
.foregroundColor(.blue)
|
||||||
|
|
@ -129,6 +147,13 @@ struct AccessModeView: View {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Only lock to localhost when Tailscale Serve is enabled AND actually working
|
||||||
|
private var shouldLockToLocalhost: Bool {
|
||||||
|
tailscaleServeEnabled &&
|
||||||
|
tailscaleService.isRunning &&
|
||||||
|
tailscaleServeStatus.isRunning
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// MARK: - Port Configuration View
|
// MARK: - Port Configuration View
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue