prometeu-studio/discussion/workflow/plans/PLN-0065-lsp-boundary-and-module-scaffolding.md
2026-05-05 15:50:55 +01:00

119 lines
5.0 KiB
Markdown

---
id: PLN-0065
ticket: studio-new-lsp-api-and-v1-boundary
title: LSP Boundary and Module Scaffolding
status: done
created: 2026-05-05
completed: 2026-05-05
tags: [studio, lsp, api, boundary, modules, architecture]
---
## Objective
Recreate `prometeu-lsp:prometeu-lsp-api` and `prometeu-lsp:prometeu-lsp-v1` with a structurally correct boundary that is ready for long-term maintenance, while intentionally keeping the initial server behavior minimal.
## Background
`DEC-0032` locks that:
- `lsp-api` is an internal Studio boundary, not a mirror of the LSP protocol;
- `lsp-v1` is the concrete LSP adapter and the only module allowed to depend on `LSP4J`;
- the current mock server shape MUST NOT be treated as the product pattern;
- wave 1 prioritizes architecture and lifecycle over semantic depth.
The repository already reserves `prometeu-lsp:*` in `settings.gradle.kts`, but the modules are currently empty shells after the cleanup.
## Scope
### Included
- Recreate Gradle/module structure for `prometeu-lsp-api` and `prometeu-lsp-v1`.
- Define the minimal internal API contract for server lifecycle by project.
- Establish package boundaries that keep protocol DTOs and `LSP4J` types out of `lsp-api`.
- Add boundary-oriented tests or build checks where feasible.
### Excluded
- Wiring the server into Studio project open/close.
- Rich semantic behavior, diagnostics, definition, symbols, or incremental analysis.
- Automation channel work for `compile/build/run/debug`.
## Non-Goals
- Full language feature implementation.
- Any attempt to preserve compatibility with the legacy removed `prometeu-lsp`.
- Transport changes in the VS Code extension.
## Execution Steps
### Step 1 - Recreate the Gradle modules with explicit dependency ownership
**What:** Reintroduce the `prometeu-lsp-api` and `prometeu-lsp-v1` modules as clean boundaries.
**How:** Restore the module directories and `build.gradle.kts` files, wire them in `settings.gradle.kts`, and keep dependencies explicit:
- `prometeu-lsp-api` depends only on stable internal modules it truly needs;
- `prometeu-lsp-v1` depends on `prometeu-lsp-api`, `compiler` services it consumes, and `LSP4J`;
- no other Studio module depends on `LSP4J`.
**File(s):** `settings.gradle.kts`, `prometeu-lsp/prometeu-lsp-api/build.gradle.kts`, `prometeu-lsp/prometeu-lsp-v1/build.gradle.kts`, affected root/module build files.
### Step 2 - Define the minimal internal lifecycle contract in `lsp-api`
**What:** Create the smallest stable API needed by the Studio host.
**How:** Add internal contracts such as a project-scoped `bootServer(project)` and `shutdownServer(project)` surface plus the minimal supporting DTO/entity types required by that lifecycle. Keep the API transport-agnostic and free of protocol DTOs.
**File(s):** `prometeu-lsp/prometeu-lsp-api/src/main/java/**`.
### Step 3 - Define the adapter shape in `lsp-v1`
**What:** Establish the internal code organization of the concrete adapter.
**How:** Create clear package slices inside `lsp-v1`, such as:
- lifecycle/bootstrap,
- server host/transport,
- protocol DTO mapping,
- compiler-facing service bridge.
The implementation may stay behaviorally dumb, but the structure MUST already reflect the final responsibility split.
**File(s):** `prometeu-lsp/prometeu-lsp-v1/src/main/java/**`.
### Step 4 - Add boundary conformance tests
**What:** Prevent architectural drift from day 1.
**How:** Add tests or static checks that fail if:
- `lsp-api` imports `LSP4J`;
- protocol DTOs leak into `lsp-api`;
- non-`lsp-v1` Studio modules start importing `LSP4J`.
**File(s):** `prometeu-lsp/prometeu-lsp-api/src/test/java/**`, `prometeu-lsp/prometeu-lsp-v1/src/test/java/**`, or build-level checks if that is cleaner.
## Test Requirements
### Unit Tests
- Verify the lifecycle contracts in `lsp-api` have deterministic defaults and null-safety.
- Verify `lsp-v1` module-local bootstrap pieces can be instantiated without a running Studio shell.
- Verify boundary checks catch `LSP4J` leakage.
### Integration Tests
- Run a root or targeted Gradle build proving the new modules compile and coexist with `prometeu-studio` and `prometeu-app`.
### Manual Verification
- Inspect the recreated module tree and confirm `lsp-api` contains no protocol or `LSP4J` types.
## Acceptance Criteria
- [x] `prometeu-lsp-api` and `prometeu-lsp-v1` exist again as active modules.
- [x] `lsp-api` exposes only internal lifecycle-oriented contracts.
- [x] `lsp-v1` is the only module allowed to depend on `LSP4J`.
- [x] The new module structure expresses clear responsibility boundaries even with dumb behavior.
- [x] Boundary conformance is covered by tests or equivalent build checks.
## Dependencies
- `DEC-0032` accepted and normatively locked.
- Current Gradle graph and module includes available for reactivation.
## Risks
- Reintroducing the modules too loosely can recreate the same ambiguity that killed the legacy stack.
- An underspecified API can force churn later; an oversized API can lock the wrong shape too early.
- Build-only enforcement may miss architectural drift unless the checks are explicit.