Files
Claro/tools/validate_lsp_helper.py
T

67 lines
2.3 KiB
Python

#!/usr/bin/env python3
import json
import os
import subprocess
import sys
import tempfile
from pathlib import Path
ROOT = Path(__file__).resolve().parents[1]
HELPER = ROOT / "support" / "lsp" / "claro_lsp_stub.py"
EXE = ROOT / ("claro.exe" if os.name == "nt" else "claro")
def fail(message):
raise SystemExit(message)
def run_helper(*args):
result = subprocess.run([sys.executable, str(HELPER), *args], cwd=ROOT, text=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
if result.returncode != 0:
fail(result.stdout)
return result.stdout
def main():
if not HELPER.exists():
fail(f"Missing LSP helper: {HELPER}")
if not EXE.exists():
fail(f"Missing Claro executable: {EXE}")
metadata = json.loads(run_helper("metadata"))
if metadata.get("language") != "Claro":
fail("metadata must describe Claro")
if ".claro" not in metadata.get("file_extensions", []):
fail("metadata must include .claro")
if not any(cmd.get("name") == "typecheck" for cmd in metadata.get("commands", [])):
fail("metadata must include typecheck command")
completions = json.loads(run_helper("completions"))
if "SAY" not in completions.get("keywords", []):
fail("completions must include SAY")
if "LIST OF TEXT" not in completions.get("types", []):
fail("completions must include typed containers")
with tempfile.TemporaryDirectory() as td:
bad = Path(td) / "bad_lsp.claro"
bad.write_text("SET score AS NUMBER TO 1\nSET score TO \"oops\"\n", encoding="utf-8")
diagnostics = json.loads(run_helper("diagnostics", str(bad)))
if not diagnostics:
fail("diagnostics must report type errors")
first = diagnostics[0]
for key in ["source", "file", "line", "severity", "message"]:
if key not in first:
fail(f"diagnostic is missing {key}")
if first["source"] != "claro typecheck":
fail("type mismatch should come from claro typecheck")
if first["line"] != 2:
fail(f"expected type diagnostic on line 2, got {first['line']}")
if "NUMBER" not in first["message"] or "TEXT" not in first["message"]:
fail(f"diagnostic should preserve type mismatch message: {first['message']}")
print("LSP helper validation OK")
if __name__ == "__main__":
main()