refactor: restructure project layout
- Move main process to electron/main/ - Move preload to electron/preload/ - Add shared types in electron/shared/ - Split redis-service into modular redis/ directory - Flatten renderer to src/ (remove src/renderer/ nesting) - Update electron.vite.config.ts paths - Update tsconfig paths - Output to electron-dist/
This commit is contained in:
@@ -0,0 +1,182 @@
|
||||
// src/renderer/src/stores/connection.ts
|
||||
import { defineStore } from 'pinia'
|
||||
import { ref, computed } from 'vue'
|
||||
|
||||
export interface ConnectionConfig {
|
||||
id: string
|
||||
name: string
|
||||
host: string
|
||||
port: number
|
||||
auth: string
|
||||
username: string
|
||||
tls: boolean
|
||||
tlsCaPath: string
|
||||
tlsCertPath: string
|
||||
tlsKeyPath: string
|
||||
sshEnabled: boolean
|
||||
sshHost: string
|
||||
sshPort: number
|
||||
sshUsername: string
|
||||
sshPassword: string
|
||||
sshPrivateKeyPath: string
|
||||
cluster: boolean
|
||||
sentinelMasterName: string
|
||||
separator: string
|
||||
order: number
|
||||
createdAt: number
|
||||
color?: string
|
||||
}
|
||||
|
||||
export const useConnectionStore = defineStore('connection', () => {
|
||||
const connections = ref<ConnectionConfig[]>([])
|
||||
const activeId = ref<string | null>(null)
|
||||
const connecting = ref(false)
|
||||
const error = ref<string | null>(null)
|
||||
const serverInfo = ref<string | null>(null)
|
||||
const healthOk = ref(true)
|
||||
let healthTimer: ReturnType<typeof setInterval> | null = null
|
||||
|
||||
const activeConnection = computed(() =>
|
||||
connections.value.find((c: ConnectionConfig) => c.id === activeId.value) ?? null
|
||||
)
|
||||
const isConnected = computed(() => activeId.value !== null)
|
||||
|
||||
async function loadConnections() {
|
||||
connections.value = await window.electronAPI.storage.getConnections()
|
||||
}
|
||||
|
||||
async function saveConnection(conn: ConnectionConfig) {
|
||||
if (conn.auth && !conn.auth.startsWith('enc:')) {
|
||||
conn.auth = 'enc:' + await window.electronAPI.credential.encrypt(conn.auth)
|
||||
}
|
||||
connections.value = await window.electronAPI.storage.saveConnection(conn)
|
||||
}
|
||||
|
||||
async function deleteConnection(id: string) {
|
||||
if (activeId.value === id) await disconnect()
|
||||
connections.value = await window.electronAPI.storage.deleteConnection(id)
|
||||
}
|
||||
|
||||
async function reorderConnections(ids: string[]) {
|
||||
connections.value = await window.electronAPI.storage.reorderConnections(ids)
|
||||
}
|
||||
|
||||
async function connect(conn: ConnectionConfig) {
|
||||
connecting.value = true
|
||||
error.value = null
|
||||
try {
|
||||
let auth = conn.auth
|
||||
if (auth.startsWith('enc:')) {
|
||||
auth = await window.electronAPI.credential.decrypt(auth.slice(4))
|
||||
}
|
||||
const result = await window.electronAPI.redis.connect(conn.id, {
|
||||
host: conn.host,
|
||||
port: conn.port,
|
||||
password: auth || undefined,
|
||||
username: conn.username || undefined,
|
||||
tls: conn.tls,
|
||||
})
|
||||
if (result.success) {
|
||||
activeId.value = conn.id
|
||||
serverInfo.value = await window.electronAPI.redis.getInfo(conn.id)
|
||||
startHealthCheck(conn.id)
|
||||
} else {
|
||||
error.value = result.error || 'Connection failed'
|
||||
}
|
||||
} catch (err: any) {
|
||||
error.value = err.message
|
||||
} finally {
|
||||
connecting.value = false
|
||||
}
|
||||
}
|
||||
|
||||
async function disconnect() {
|
||||
stopHealthCheck()
|
||||
if (activeId.value) {
|
||||
await window.electronAPI.redis.disconnect(activeId.value)
|
||||
activeId.value = null
|
||||
serverInfo.value = null
|
||||
}
|
||||
}
|
||||
|
||||
function startHealthCheck(connId: string) {
|
||||
stopHealthCheck()
|
||||
healthOk.value = true
|
||||
healthTimer = setInterval(async () => {
|
||||
try {
|
||||
const ok = await window.electronAPI.redis.isConnected(connId)
|
||||
healthOk.value = ok
|
||||
if (!ok && activeId.value === connId) {
|
||||
// Connection lost
|
||||
error.value = 'Connection lost'
|
||||
}
|
||||
} catch {
|
||||
healthOk.value = false
|
||||
}
|
||||
}, 5000)
|
||||
}
|
||||
|
||||
function stopHealthCheck() {
|
||||
if (healthTimer) {
|
||||
clearInterval(healthTimer)
|
||||
healthTimer = null
|
||||
}
|
||||
}
|
||||
|
||||
async function testConnection(opts: {
|
||||
host: string; port: number; auth?: string; username?: string; tls?: boolean
|
||||
}): Promise<{ success: boolean; error?: string }> {
|
||||
if (!window.electronAPI) {
|
||||
return { success: false, error: 'Electron API not ready' }
|
||||
}
|
||||
const testId = `test_${Date.now()}`
|
||||
try {
|
||||
const result = await window.electronAPI.redis.connect(testId, {
|
||||
host: opts.host,
|
||||
port: opts.port,
|
||||
password: opts.auth || undefined,
|
||||
username: opts.username || undefined,
|
||||
tls: opts.tls,
|
||||
})
|
||||
if (result.success) {
|
||||
await window.electronAPI.redis.disconnect(testId)
|
||||
return { success: true }
|
||||
}
|
||||
return { success: false, error: result.error }
|
||||
} catch (err: any) {
|
||||
return { success: false, error: err.message }
|
||||
}
|
||||
}
|
||||
|
||||
async function exportConnections(): Promise<string> {
|
||||
const data = JSON.stringify(connections.value, null, 2)
|
||||
return data
|
||||
}
|
||||
|
||||
async function importConnections(jsonStr: string): Promise<number> {
|
||||
try {
|
||||
const imported = JSON.parse(jsonStr) as ConnectionConfig[]
|
||||
if (!Array.isArray(imported)) throw new Error('Invalid format')
|
||||
let count = 0
|
||||
for (const conn of imported) {
|
||||
if (conn.id && conn.name && conn.host) {
|
||||
const exists = connections.value.find((c: ConnectionConfig) => c.id === conn.id)
|
||||
if (!exists) {
|
||||
await saveConnection(conn)
|
||||
count++
|
||||
}
|
||||
}
|
||||
}
|
||||
return count
|
||||
} catch (err: any) {
|
||||
throw new Error('Import failed: ' + err.message)
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
connections, activeId, connecting, error, serverInfo, healthOk,
|
||||
activeConnection, isConnected,
|
||||
loadConnections, saveConnection, deleteConnection, reorderConnections,
|
||||
connect, disconnect, testConnection, exportConnections, importConnections,
|
||||
}
|
||||
})
|
||||
Reference in New Issue
Block a user