1package app
2
3import (
4 "context"
5 "database/sql"
6
7 "github.com/kujtimiihoxha/termai/internal/config"
8 "github.com/kujtimiihoxha/termai/internal/db"
9 "github.com/kujtimiihoxha/termai/internal/logging"
10 "github.com/kujtimiihoxha/termai/internal/lsp"
11 "github.com/kujtimiihoxha/termai/internal/lsp/watcher"
12 "github.com/kujtimiihoxha/termai/internal/message"
13 "github.com/kujtimiihoxha/termai/internal/permission"
14 "github.com/kujtimiihoxha/termai/internal/pubsub"
15 "github.com/kujtimiihoxha/termai/internal/session"
16 "github.com/kujtimiihoxha/termai/internal/tui/util"
17)
18
19type App struct {
20 Context context.Context
21
22 Sessions session.Service
23 Messages message.Service
24 Permissions permission.Service
25
26 LSPClients map[string]*lsp.Client
27
28 Logger logging.Interface
29
30 Status *pubsub.Broker[util.InfoMsg]
31 ceanups []func()
32}
33
34func New(ctx context.Context, conn *sql.DB) *App {
35 cfg := config.Get()
36 q := db.New(conn)
37 log := logging.NewLogger(logging.Options{
38 Level: cfg.Log.Level,
39 })
40 sessions := session.NewService(ctx, q)
41 messages := message.NewService(ctx, q)
42
43 app := &App{
44 Context: ctx,
45 Sessions: sessions,
46 Messages: messages,
47 Permissions: permission.NewPermissionService(),
48 Logger: log,
49 Status: pubsub.NewBroker[util.InfoMsg](),
50 LSPClients: make(map[string]*lsp.Client),
51 }
52
53 for name, client := range cfg.LSP {
54 lspClient, err := lsp.NewClient(client.Command, client.Args...)
55 app.ceanups = append(app.ceanups, func() {
56 lspClient.Close()
57 })
58 workspaceWatcher := watcher.NewWorkspaceWatcher(lspClient)
59 if err != nil {
60 log.Error("Failed to create LSP client for", name, err)
61 continue
62 }
63
64 _, err = lspClient.InitializeLSPClient(ctx, config.WorkingDirectory())
65 if err != nil {
66 log.Error("Initialize failed", "error", err)
67 continue
68 }
69 go workspaceWatcher.WatchWorkspace(ctx, config.WorkingDirectory())
70 app.LSPClients[name] = lspClient
71 }
72 return app
73}
74
75func (a *App) Close() {
76 for _, cleanup := range a.ceanups {
77 cleanup()
78 }
79 for _, client := range a.LSPClients {
80 client.Close()
81 }
82 a.Logger.Info("App closed")
83}