Skip to content

Terminal renderer: an abap2UI5 app in a terminal (renderers/terminal/) - #3

Merged
oblomov-dev merged 1 commit into
mainfrom
claude/abap2ui5-project-brainstorm-nt7ifs
Oct 4, 2026
Merged

oblomov-dev merged 1 commit into
mainfrom
claude/abap2ui5-project-brainstorm-nt7ifs

Conversation

@oblomov-dev

Copy link
Copy Markdown
Member

Adds a terminal frontend for protocol 2. It is the third renderer after the UI5 SPA and Adaptive Cards, and like them it is checked by the frontend conformance suite.

What it is

  • renderers/terminal/: plain Node, no dependencies (ANSI and node:readline).
    • session.mjs: the transport from spec/transport.md: sap-contextid, CSRF, no retry, 120 s timeout, one roundtrip at a time, terminate HEAD. On an SAP system it adds basic auth, a cookie jar and keeps sap-client. It handles every follow-up action and keeps a hash history like the UI5 router's, so Back works.
    • app.mjs: the state machine. Keys: Tab, arrows, Enter, Space, Esc, Back, Page, F1, F4, Ctrl+U/R/C. A field edit is committed like a UI5 Input. Value helps show as an overlay. A status line shows key help and the actions it skipped.
    • render.mjs / mapping.mjs: all 65 portable controls. An unknown control shows as [? <control> - not rendered]. Field events (change, select, submit, search) fire with ${$parameters>/…}.
    • layout.mjs / text.mjs: wrapping, tables fitted to the width, frames, wide characters. It honours NO_COLOR and FORCE_COLOR, and control characters from the backend are always removed.
    • CLI: bin/abap2ui5-tui.mjs (abap2ui5-tui, with --print). Library export @abap2ui5/protocol/renderers/terminal.
  • renderers/common/: the parts of the Adaptive Cards renderer that don't depend on cards (view helpers, payload to request) move here and are shared by both. The card renderer re-exports them and its golden cards are unchanged.

Conformance

  • New adapter conformance/frontend/adapters/terminal.mjs that drives the app with real keystrokes.
  • Terminal: 72 pass, 0 fail, 9 skip (DOM, programmatic model edit, the UI5 and semantic profiles). All 4 router checks pass.
  • Suite change: portable.box-details no longer asks for a DOM, because it only reads the on-screen text. Adaptive Cards now runs it and passes (66 pass, 15 skip). The UI5 SPA result is unchanged.

Tests

  • test/terminal.test.mjs: 21 tests: golden screens for 8 cases (including width 40), keys down to the exact request body, value helps, the message box, cookies, auth, CSRF, contextid, NO_COLOR/FORCE_COLOR, control-character removal, the TTY loop with fake streams, the CLI, and a staleness check of the mapping table.
  • End to end in test/backends.test.mjs: against the node-runtime host it runs BIND (edit, press, the backend's summary shows on screen), ROUTE (nav, then Alt+Left restores the caller), NAV, and the CLI --print (matches the golden screen).
  • npm test 82/82 (UI5 SPA in Chromium and cap2UI5 included). npm run generate leaves no diff. lint:abap reports 0 issues.

Not verified

  • Not run against a real SAP system. Auth, cookies, CSRF and contextid are tested against the mock only.
  • No pseudo-terminal test, since that needs a native module.
  • RadioButton is not in portable profile v1, so it shows as a placeholder.

🤖 Generated with Claude Code

https://claude.ai/code/session_01Kz1J78phfNKbqUaq3VcP4U


Generated by Claude Code

- renderers/terminal/: a portable renderer for the terminal, pure Node, no
  dependencies. session.mjs speaks the protocol to any backend (node
  runtime, cap2UI5, an SAP ICF node: basic auth, cookies, CSRF token
  handshake, sap-contextid, terminate HEAD, the URL's query kept), runs the
  follow-up actions and keeps a hash history synchronised like the UI5
  router, so Back restores routes. app.mjs is the state machine (focus,
  in-place edits committed like a UI5 Input, pick lists, keys, frame() and
  print()), render.mjs + mapping.mjs map all 65 portable controls onto
  terminal widgets (unknown controls as reported placeholders), layout.mjs
  draws them at a width (wrapping, columns, tables, frames), text.mjs
  handles display width, sanitising, ellipsis, glyphs, ANSI and NO_COLOR,
  tty.mjs drives a real terminal. CLI abap2ui5-tui (package bin) with
  --print for logs, CI and screen readers; library export
  @abap2ui5/protocol/renderers/terminal. The README's mapping table is
  generated from mapping.mjs (scripts/render-terminal.mjs, npm run
  generate).
- renderers/common/: the render-agnostic half of the Adaptive Cards
  renderer (view helpers, payload -> request) moved out for both
  renderers; the card renderer re-exports it, its golden cards unchanged.
- Frontend adapter `terminal`, driven with keys through the state machine:
  72 pass, 0 fail, 9 skip (DOM, programmatic model edit; UI5 and semantic
  profiles), the router checks included. Pinned in test/frontend.test.mjs,
  RESULTS.md and the frontend README follow; CI uploads its report.
- portable.box-details no longer asks for a DOM - it reads only the text
  on screen; the Adaptive Cards renderer now runs and passes it.
- test/terminal.test.mjs: golden screens of recorded traffic, the keys
  down to the exact request body, the transport against a real-system-like
  backend, width, colors, sanitising, the TTY loop, the CLI, the mapping
  table; test/backends.test.mjs drives the renderer end to end against the
  node-runtime host after the backend suite.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Kz1J78phfNKbqUaq3VcP4U
@oblomov-dev
oblomov-dev merged commit f9210ea into main Oct 4, 2026
3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants