fix: 修复若干问题,添加java lsp

This commit is contained in:
2026-02-15 22:41:24 +08:00
parent eab464060b
commit 00b0d825d8
264 changed files with 1036 additions and 309 deletions

View File

@@ -8,6 +8,8 @@ import (
"strings"
"sync"
"time"
"go.uber.org/zap"
)
var ErrUnsupportedLanguage = errors.New("unsupported language")
@@ -38,12 +40,13 @@ type ClientFactory func(ctx context.Context, spec LanguageServerSpec, workspaceD
// ManagerConfig 控制会话池容量、TTL 与实例信息。
type ManagerConfig struct {
WorkspaceDir string // LSP 进程工作区目录。
MaxSessions int // 本实例会话上限。
SessionTTL time.Duration // 会话空闲超时。
CleanupInterval time.Duration // 会话清理周期。
InstanceID string // 当前实例 ID。
Registry SessionRegistry // 可选分布式会话注册中心。
WorkspaceDir string // LSP 进程工作区目录。
MaxSessions int // 本实例会话上限。
SessionTTL time.Duration // 会话空闲超时。
CleanupInterval time.Duration // 会话清理周期。
InstanceID string // 当前实例 ID。
Registry SessionRegistry // 可选分布式会话注册中心。
SessionInitTimeout time.Duration // LSP 客户端初始化超时(独立于请求超时)。
}
// Manager 按 language/session 复用 LSP 会话,并负责清理与淘汰。
@@ -92,6 +95,9 @@ func NewManager(config ManagerConfig, specs []LanguageServerSpec, factory Client
if config.CleanupInterval <= 0 {
config.CleanupInterval = 2 * time.Minute
}
if config.SessionInitTimeout <= 0 {
config.SessionInitTimeout = 60 * time.Second
}
if strings.TrimSpace(config.InstanceID) == "" {
config.InstanceID = "instance-local"
}
@@ -116,6 +122,34 @@ func NewManager(config ManagerConfig, specs []LanguageServerSpec, factory Client
return m
}
// WarmUp 预热指定语言的 LSP 会话,使首次请求无需等待冷启动。
func (m *Manager) WarmUp(ctx context.Context, languages ...string) {
targets := languages
if len(targets) == 0 {
targets = make([]string, 0, len(m.specByLang))
for lang := range m.specByLang {
targets = append(targets, lang)
}
}
for _, lang := range targets {
lang = normalizeLanguage(lang)
spec, ok := m.specByLang[lang]
if !ok {
continue
}
sessionKey := buildSessionKey(lang, "default")
_, err := m.getOrCreateSession(ctx, sessionKey, "default", spec)
if err != nil {
zap.L().Warn("warm-up failed",
zap.String("language", lang),
zap.Error(err),
)
} else {
zap.L().Info("warm-up succeeded", zap.String("language", lang))
}
}
}
// Complete 处理补全请求,包含语言匹配、会话归属、会话复用/创建。
func (m *Manager) Complete(ctx context.Context, req Request) (Response, error) {
language := normalizeLanguage(req.Language)
@@ -253,7 +287,11 @@ func (m *Manager) getOrCreateSession(
}
m.mu.Unlock()
client, err := m.newClient(ctx, spec, m.config.WorkspaceDir)
// 使用独立超时创建 LSP 客户端,避免被较短的请求超时截断。
initCtx, initCancel := context.WithTimeout(context.Background(), m.config.SessionInitTimeout)
defer initCancel()
client, err := m.newClient(initCtx, spec, m.config.WorkspaceDir)
if err != nil {
return nil, err
}