Wire GX→LAIN runtime into CLI as 'lain' command

Add new command: gx lain <path.gx> [-m/--mode MODE]

Features:
- Execute .gx files through GX→LAIN runtime
- Display fused symbol, output text, diagnostics
- Configurable cognitive mode (default: analyze)
- Structured error reporting

Usage:
  gx lain sample_code.gx
  gx lain sample_code.gx -m synthesize

All integration tests still passing (18/18).
This commit is contained in:
GlyphRunner System
2026-05-20 13:56:49 -04:00
parent af1265d2b2
commit 4e11cd990d
3 changed files with 53 additions and 0 deletions
+47
View File
@@ -4,6 +4,7 @@ from pathlib import Path
from gx_compiler.compiler import GXCompiler, CompilerError from gx_compiler.compiler import GXCompiler, CompilerError
from runtime_executor.integration import run_gx_with_summary from runtime_executor.integration import run_gx_with_summary
from runtime_executor.gx_loader import load_gx, GXLoaderError from runtime_executor.gx_loader import load_gx, GXLoaderError
from gx_lain.runtime import execute_gx_path as lain_execute_gx_path
def cmd_compile(source_path: str, output_path: str = None) -> int: def cmd_compile(source_path: str, output_path: str = None) -> int:
@@ -129,3 +130,49 @@ def cmd_summary(gx_path: str) -> int:
except Exception as e: except Exception as e:
print(f"Error: {e}", file=sys.stderr) print(f"Error: {e}", file=sys.stderr)
return 1 return 1
def cmd_lain(gx_path: str, mode: str = "analyze") -> int:
try:
gx = Path(gx_path)
if not gx.exists():
print(f"Error: File not found: {gx_path}", file=sys.stderr)
return 1
print(f"Executing {gx_path} through GX→LAIN runtime (mode: {mode})")
result = lain_execute_gx_path(
gx_path,
context={"cognitive_mode": mode}
)
# Print output text
print()
print(result["output_text"])
print()
# Print fused symbol
print("[Fused Symbol]")
print(f" {result['fused_symbol']['summary']}")
if result['fused_symbol']['key_points']:
print(f" Key points: {', '.join(result['fused_symbol']['key_points'])}")
print()
# Print diagnostics summary
print("[Diagnostics]")
elapsed = result['diagnostics']['elapsed']
print(f" Elapsed: {elapsed:.4f}s")
print(f" Interface: v{result['diagnostics']['interface_version']}")
if result['diagnostics']['errors']:
print(f" Errors: {len(result['diagnostics']['errors'])}")
for err in result['diagnostics']['errors']:
print(f" - {err['type']}: {err['message']}")
return 1
return 0
except Exception as e:
print(f"Error: {e}", file=sys.stderr)
return 1
+2
View File
@@ -16,6 +16,8 @@ def dispatch(args) -> int:
return commands.cmd_inspect(args.path) return commands.cmd_inspect(args.path)
elif args.command == "summary": elif args.command == "summary":
return commands.cmd_summary(args.path) return commands.cmd_summary(args.path)
elif args.command == "lain":
return commands.cmd_lain(args.path, args.mode)
else: else:
print(f"Error: Unknown command: {args.command}", file=sys.stderr) print(f"Error: Unknown command: {args.command}", file=sys.stderr)
return 1 return 1
+4
View File
@@ -22,4 +22,8 @@ def build_parser() -> argparse.ArgumentParser:
summary_parser = subparsers.add_parser("summary", help="Show .gx file summary") summary_parser = subparsers.add_parser("summary", help="Show .gx file summary")
summary_parser.add_argument("path", help=".gx file to summarize") summary_parser.add_argument("path", help=".gx file to summarize")
lain_parser = subparsers.add_parser("lain", help="Execute .gx through LAIN runtime")
lain_parser.add_argument("path", help=".gx file to execute")
lain_parser.add_argument("-m", "--mode", default="analyze", help="Cognitive mode (default: analyze)")
return parser return parser