editor workspace foundation

This commit is contained in:
bQUARKz 2026-03-31 00:44:25 +01:00
parent 3a3bd407ce
commit 5f7e0e2bef
Signed by: bquarkz
SSH Key Fingerprint: SHA256:Z7dgqoglWwoK6j6u4QC87OveEq74WOhFN+gitsxtkf8
2 changed files with 158 additions and 0 deletions

View File

@ -0,0 +1,12 @@
{"type":"meta","next_id":{"DSC":12,"AGD":12,"DEC":9,"PLN":15,"LSN":26,"CLSN":1}}
{"type":"discussion","id":"DSC-0001","status":"done","ticket":"studio-docs-import","title":"Import docs/studio into discussion-framework artifacts","created_at":"2026-03-26","updated_at":"2026-03-26","tags":["studio","migration","discussion-framework","docs-import"],"agendas":[],"decisions":[],"plans":[],"lessons":[{"id":"LSN-0001","file":"discussion/lessons/DSC-0001-studio-docs-import/LSN-0001-assets-workspace-execution-wave-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0002","file":"discussion/lessons/DSC-0001-studio-docs-import/LSN-0002-bank-composition-editor-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0003","file":"discussion/lessons/DSC-0001-studio-docs-import/LSN-0003-mental-model-asset-mutations-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0004","file":"discussion/lessons/DSC-0001-studio-docs-import/LSN-0004-mental-model-assets-workspace-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0005","file":"discussion/lessons/DSC-0001-studio-docs-import/LSN-0005-mental-model-studio-events-and-components-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0006","file":"discussion/lessons/DSC-0001-studio-docs-import/LSN-0006-mental-model-studio-shell-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0007","file":"discussion/lessons/DSC-0001-studio-docs-import/LSN-0007-pack-wizard-shell-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0008","file":"discussion/lessons/DSC-0001-studio-docs-import/LSN-0008-project-scoped-state-and-activity-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0016","file":"discussion/lessons/DSC-0001-studio-docs-import/LSN-0016-studio-docs-import-pattern.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"}]}
{"type":"discussion","id":"DSC-0002","status":"open","ticket":"palette-management-in-studio","title":"Palette Management in Studio","created_at":"2026-03-26","updated_at":"2026-03-26","tags":["studio","legacy-import","palette-management","tile-bank","packer-boundary"],"agendas":[{"id":"AGD-0002","file":"AGD-0002-palette-management-in-studio.md","status":"open","created_at":"2026-03-26","updated_at":"2026-03-26"}],"decisions":[],"plans":[],"lessons":[]}
{"type":"discussion","id":"DSC-0003","status":"done","ticket":"packer-docs-import","title":"Import docs/packer into discussion-framework artifacts","created_at":"2026-03-26","updated_at":"2026-03-26","tags":["packer","migration","discussion-framework","docs-import"],"agendas":[],"decisions":[],"plans":[],"lessons":[{"id":"LSN-0009","file":"discussion/lessons/DSC-0003-packer-docs-import/LSN-0009-mental-model-packer-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0010","file":"discussion/lessons/DSC-0003-packer-docs-import/LSN-0010-asset-identity-and-runtime-contract-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0011","file":"discussion/lessons/DSC-0003-packer-docs-import/LSN-0011-foundations-workspace-runtime-and-build-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0012","file":"discussion/lessons/DSC-0003-packer-docs-import/LSN-0012-runtime-ownership-and-studio-boundary-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0013","file":"discussion/lessons/DSC-0003-packer-docs-import/LSN-0013-metadata-convergence-and-runtime-sink-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0014","file":"discussion/lessons/DSC-0003-packer-docs-import/LSN-0014-pack-wizard-summary-validation-and-pack-execution-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0015","file":"discussion/lessons/DSC-0003-packer-docs-import/LSN-0015-tile-bank-packing-contract-legacy.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"},{"id":"LSN-0017","file":"discussion/lessons/DSC-0003-packer-docs-import/LSN-0017-packer-docs-import-pattern.md","status":"done","created_at":"2026-03-26","updated_at":"2026-03-26"}]}
{"type":"discussion","id":"DSC-0004","status":"open","ticket":"tilemap-and-metatile-runtime-binary-layout","title":"Tilemap and Metatile Runtime Binary Layout","created_at":"2026-03-26","updated_at":"2026-03-26","tags":["packer","legacy-import","tilemap","metatile","runtime-layout"],"agendas":[{"id":"AGD-0004","file":"AGD-0004-tilemap-and-metatile-runtime-binary-layout.md","status":"open","created_at":"2026-03-26","updated_at":"2026-03-26"}],"decisions":[],"plans":[],"lessons":[]}
{"type":"discussion","id":"DSC-0005","status":"open","ticket":"variable-tile-bank-palette-serialization","title":"Variable Tile Bank Palette Serialization","created_at":"2026-03-26","updated_at":"2026-03-26","tags":["packer","legacy-import","tile-bank","palette-serialization","versioning"],"agendas":[{"id":"AGD-0005","file":"AGD-0005-variable-tile-bank-palette-serialization.md","status":"open","created_at":"2026-03-26","updated_at":"2026-03-26"}],"decisions":[],"plans":[],"lessons":[]}
{"type":"discussion","id":"DSC-0006","status":"done","ticket":"pbs-game-facing-asset-refs-and-call-result-discard","title":"PBS Game-Facing Asset References and Ignored Call Result Lowering","created_at":"2026-03-27","updated_at":"2026-03-30","tags":["compiler","pbs","ergonomics","lowering","runtime","asset-identity","expression-statements"],"agendas":[],"decisions":[],"plans":[],"lessons":[{"id":"LSN-0024","file":"discussion/lessons/DSC-0006-pbs-game-facing-asset-refs-and-call-result-discard/LSN-0024-addressable-surface-host-metadata-and-ignored-value-discipline.md","status":"done","created_at":"2026-03-30","updated_at":"2026-03-30"}]}
{"type":"discussion","id":"DSC-0007","status":"done","ticket":"pbs-learn-to-discussion-lessons-migration","title":"Migrate PBS Learn Documents into Discussion Lessons","created_at":"2026-03-27","updated_at":"2026-03-27","tags":["compiler","pbs","migration","discussion-framework","lessons","learn-prune"],"agendas":[],"decisions":[],"plans":[],"lessons":[{"id":"LSN-0018","file":"discussion/lessons/DSC-0007-pbs-learn-to-discussion-lessons-migration/LSN-0018-pbs-ast-and-parser-contract-legacy.md","status":"done","created_at":"2026-03-27","updated_at":"2026-03-27"},{"id":"LSN-0019","file":"discussion/lessons/DSC-0007-pbs-learn-to-discussion-lessons-migration/LSN-0019-pbs-name-resolution-and-linking-legacy.md","status":"done","created_at":"2026-03-27","updated_at":"2026-03-27"},{"id":"LSN-0020","file":"discussion/lessons/DSC-0007-pbs-learn-to-discussion-lessons-migration/LSN-0020-pbs-runtime-values-identity-memory-boundaries-legacy.md","status":"done","created_at":"2026-03-27","updated_at":"2026-03-27"},{"id":"LSN-0021","file":"discussion/lessons/DSC-0007-pbs-learn-to-discussion-lessons-migration/LSN-0021-pbs-diagnostics-and-conformance-governance-legacy.md","status":"done","created_at":"2026-03-27","updated_at":"2026-03-27"},{"id":"LSN-0022","file":"discussion/lessons/DSC-0007-pbs-learn-to-discussion-lessons-migration/LSN-0022-pbs-globals-lifecycle-and-published-entrypoint-legacy.md","status":"done","created_at":"2026-03-27","updated_at":"2026-03-27"}]}
{"type":"discussion","id":"DSC-0008","status":"done","ticket":"pbs-low-level-asset-manager-surface","title":"PBS Low-Level Asset Manager Surface for Runtime AssetManager","created_at":"2026-03-27","updated_at":"2026-03-27","tags":["compiler","pbs","runtime","asset-manager","host-abi","stdlib","asset"],"agendas":[],"decisions":[],"plans":[],"lessons":[{"id":"LSN-0023","file":"discussion/lessons/DSC-0008-pbs-low-level-asset-manager-surface/LSN-0023-lowassets-runtime-aligned-sdk-surface.md","status":"done","created_at":"2026-03-27","updated_at":"2026-03-27"}]}
{"type":"discussion","id":"DSC-0009","status":"open","ticket":"studio-debugger-workspace-integration","title":"Integrate ../debugger into Studio as a dedicated workspace","created_at":"2026-03-30","updated_at":"2026-03-30","tags":["studio","debugger","workspace","integration","shell"],"agendas":[{"id":"AGD-0009","file":"AGD-0009-studio-debugger-workspace-integration.md","status":"open","created_at":"2026-03-30","updated_at":"2026-03-30"}],"decisions":[],"plans":[],"lessons":[]}
{"type":"discussion","id":"DSC-0010","status":"in_progress","ticket":"studio-code-editor-workspace-foundations","title":"Establish Code Editor workspace foundations in Studio without LSP","created_at":"2026-03-30","updated_at":"2026-03-30","tags":["studio","editor","workspace","multi-frontend","lsp-deferred"],"agendas":[{"id":"AGD-0010","file":"AGD-0010-studio-code-editor-workspace-foundations.md","status":"accepted","created_at":"2026-03-30","updated_at":"2026-03-30"}],"decisions":[{"id":"DEC-0008","file":"DEC-0008-studio-code-editor-read-only-workspace-foundations.md","status":"accepted","created_at":"2026-03-30","updated_at":"2026-03-30","ref_agenda":"AGD-0010"}],"plans":[{"id":"PLN-0012","file":"PLN-0012-studio-code-editor-spec-propagation.md","status":"done","created_at":"2026-03-30","updated_at":"2026-03-30","ref_decisions":["DEC-0008"]},{"id":"PLN-0013","file":"PLN-0013-editor-workspace-layout-and-passive-surfaces.md","status":"done","created_at":"2026-03-30","updated_at":"2026-03-30","ref_decisions":["DEC-0008"]},{"id":"PLN-0014","file":"PLN-0014-project-navigator-snapshot-and-read-only-file-opening.md","status":"done","created_at":"2026-03-30","updated_at":"2026-03-30","ref_decisions":["DEC-0008"]}],"lessons":[]}
{"type":"discussion","id":"DSC-0011","status":"done","ticket":"compiler-analyze-compile-build-pipeline-split","title":"Split compiler pipeline into analyze, compile, and build entrypoints","created_at":"2026-03-30","updated_at":"2026-03-30","tags":["compiler","pipeline","artifacts","build","analysis"],"agendas":[],"decisions":[],"plans":[],"lessons":[{"id":"LSN-0025","file":"discussion/lessons/DSC-0011-compiler-analyze-compile-build-pipeline-split/LSN-0025-compiler-pipeline-entrypoints-and-result-boundaries.md","status":"done","created_at":"2026-03-30","updated_at":"2026-03-30"}]}

View File

@ -0,0 +1,146 @@
---
id: LSN-0026
ticket: studio-code-editor-workspace-foundations
title: Read-Only Editor Foundations and Semantic Deferral
created: 2026-03-31
tags: [studio, editor, workspace, read-only, navigator, tabs, lsp-deferred, ui-foundations]
---
## Context
Studio needed a real `Code Editor` workspace, but the team explicitly did not want the first wave to collapse UI structure, file management, write behavior, and language semantics into one premature implementation.
The discussion closed a narrower and more durable target:
- Studio owns the editorial workspace shell.
- The first wave is read-only.
- The workspace must still be useful enough to navigate a full project and open files.
- Semantic behavior such as diagnostics, symbols, completion, or other LSP-like surfaces must remain deferred.
This turned the problem from "build an editor" into "stabilize the workspace composition and file-management shell without hardcoding semantic ownership too early."
## Key Decisions
### Treat the First Editor Wave as an Editorial Shell, Not a Language Tool
**What:**
The first `Code Editor` wave is a Studio-owned read-only workspace foundation with:
- `Project Navigator`
- reserved `Outline` region
- responsive tab strip
- central read-only editor surface
- passive helper region
- passive status bar
**Why:**
The workspace needed to become structurally real before it could safely host future semantic providers.
By freezing the editorial shell first, the team avoided inventing incomplete semantic behavior just to justify the layout.
**Trade-offs:**
The result is intentionally incomplete as an editor.
It opens files and manages workspace composition, but it does not yet save, mark dirty state, or provide language-aware interactions.
### Separate Structural Project State from Open-Document Content State
**What:**
The final implementation keeps two different kinds of in-memory state:
- a structural project-tree snapshot for navigation and visual state
- read-only file buffers only for opened files
**Why:**
These are different responsibilities.
The navigator needs fast structural state over the whole project, while the editor only needs content snapshots for documents the user has actually opened.
**Trade-offs:**
This adds a small amount of model code up front, but it keeps the workspace testable and prevents the navigator from degenerating into ad hoc filesystem reads during rendering.
### Keep Semantic Ownership Deferred but Architectural Seams Open
**What:**
The workspace now reserves real regions for future semantic surfaces such as `Outline`, helper features, and later LSP-backed integrations, but those surfaces remain passive in this wave.
**Why:**
The important rule was not to "solve LSP later" by ignoring layout now.
The rule was to reserve the correct shell surfaces now without pretending semantic capability already exists.
**Trade-offs:**
The first implementation includes visible placeholders and passive chrome.
That can feel sparse, but it prevents later layout churn and keeps ownership boundaries explicit.
## Final Implementation
The Studio domain now has a dedicated `Code Editor` workspace specification and a concrete read-only implementation:
- `docs/specs/studio/5. Code Editor Workspace Specification.md` defines the normative first-wave contract.
- `EditorWorkspace` now mounts a left navigator column, reserved `Outline`, responsive tabs, read-only code area, helper region, and status bar.
- `EditorProjectSnapshotService` builds a full-project structural tree, including hidden files, folder-first ordering, alphabetical sorting, and frontend-root tagging from `prometeu.json`.
- `EditorOpenFileSession` keeps opened tabs session-local and read-only.
- unsupported or non-text files trigger an explicit modal instead of a fake preview.
- the navigator and status bar share a consistent visual language for folders, source roots, build directories, and `prometeu.json`.
## Patterns and Algorithms
### Pattern: Stabilize Workspace Chrome Before Semantic Capability
When a new workspace will eventually host rich language tooling, first define and implement:
1. shell composition
2. project navigation
3. document opening model
4. session-local view state
5. passive reserved regions for future semantic consumers
Only after those are stable should the team decide how semantic providers plug into the shell.
### Pattern: Make Read-Only a Deliberate First-Wave Contract
Read-only mode is not just a shortcut.
It is a way to avoid accidentally committing to:
- save semantics
- dirty tracking semantics
- conflict resolution UX
- write affordances
- or editor-to-filesystem mutation rules
until those deserve their own discussion.
### Pattern: Use Full-Project Visibility with Frontend-Aware Tagging
The navigator should not hide non-source files just because the selected frontend only cares about some roots.
A better pattern is:
- show the whole project
- tag the frontend-relevant roots
- and keep the filesystem as the source of truth
This preserves workspace usability without confusing project ownership with compiler ownership.
## Pitfalls
- Do not let passive first-wave regions start pretending they are semantic features.
- Do not reintroduce save or dirty indicators without an explicit decision revision.
- Do not make the navigator a filtered "source-only" view when the workspace is supposed to expose the real project.
- Do not collapse structural snapshot state and open-document content buffers into one model.
- Do not let visual polish quietly smuggle new product behavior into a read-only wave.
## References
- `DEC-0008` Read-only foundations for the Studio Code Editor workspace
- `PLN-0012` Propagate DEC-0008 into Studio shell and workspace specs
- `PLN-0013` Implement the read-only Code Editor workspace shell and passive surfaces
- `PLN-0014` Implement the Project Navigator snapshot and read-only file opening flow
- `docs/specs/studio/5. Code Editor Workspace Specification.md`
- `docs/specs/studio/1. Studio Shell and Workspace Layout Specification.md`
- `docs/specs/studio/2. Studio UI Foundations Specification.md`
- `prometeu-studio/src/main/java/p/studio/workspaces/editor/EditorWorkspace.java`
- `prometeu-studio/src/main/java/p/studio/workspaces/editor/EditorProjectSnapshotService.java`
- `prometeu-studio/src/main/java/p/studio/workspaces/editor/EditorOpenFileSession.java`
## Takeaways
- A good first editor wave can be structurally complete while still being intentionally read-only.
- Structural project navigation and opened-document content are different state models and should stay separate.
- Future semantic integration becomes easier when the shell reserves the right surfaces early but refuses to fake capability before the contract exists.