Add automated test coverage (CTest is currently empty) #1

Open
opened 2026-09-07 11:27:57 -06:00 by Agent · 1 comment
Owner

No automated tests exist anywhere in the project; CTest is not configured.

Priority target: RdpSessionBackend (src/rdp_session_backend.cpp, ~1809 lines), the largest and most complex file in the codebase, driving the embedded FreeRDP client lifecycle. Also needs coverage for ProfileRepository (SQLite CRUD/migrations) and SshSessionBackend.

Scope:

  • Wire up CTest in CMakeLists.txt
  • Add unit tests for profile repository CRUD/migrations
  • Add tests for session backend state transitions (connect/disconnect/reconnect/failed)
  • Add regression coverage before declaring RDP/SSH backends stable
No automated tests exist anywhere in the project; CTest is not configured. Priority target: `RdpSessionBackend` (src/rdp_session_backend.cpp, ~1809 lines), the largest and most complex file in the codebase, driving the embedded FreeRDP client lifecycle. Also needs coverage for `ProfileRepository` (SQLite CRUD/migrations) and `SshSessionBackend`. Scope: - Wire up CTest in CMakeLists.txt - Add unit tests for profile repository CRUD/migrations - Add tests for session backend state transitions (connect/disconnect/reconnect/failed) - Add regression coverage before declaring RDP/SSH backends stable
Author
Owner

Progress

  • Wired up CTest (ORBITHUB_BUILD_TESTS option, gated on Qt6::Test being found -- gracefully skipped otherwise so it can't break app-only builds).
  • Added tests/test_profile_repository.cpp: 21 Qt Test cases covering CRUD, validation rules (missing name/host/username, invalid port, SSH private-key-required, duplicate name), search/sort, tag normalization, and folder create/list/normalize -- each against an isolated temporary SQLite file (ProfileRepository gained a databasePathOverride constructor for this).
  • Caught and fixed a real bug in the process: normalizedTags()'s result was bound directly without the nonNullTrimmed() null-guard every other field already uses. Creating a profile with no tags at all hit the tags NOT NULL constraint and silently failed -- this affects the Import Profiles feature (#17) too, for any export where a profile has no tags key.
  • Confirmed ctest --test-dir build runs clean, and packaging builds (build-deb.sh) are unaffected (test binary isn't installed/packaged).

Still open

  • SshSessionBackend / RdpSessionBackend state-transition coverage (connect/disconnect/reconnect/failed) is not started. This is a much bigger lift than ProfileRepository was -- both backends are tightly coupled to real network I/O and their own worker threads, so testing them meaningfully will need a testability pass first (likely extracting the pure state-machine logic behind a seam that can run without an actual SSH/RDP connection) rather than just writing tests against the current shape. Leaving this issue open for that.
## Progress - Wired up CTest (`ORBITHUB_BUILD_TESTS` option, gated on `Qt6::Test` being found -- gracefully skipped otherwise so it can't break app-only builds). - Added `tests/test_profile_repository.cpp`: 21 Qt Test cases covering CRUD, validation rules (missing name/host/username, invalid port, SSH private-key-required, duplicate name), search/sort, tag normalization, and folder create/list/normalize -- each against an isolated temporary SQLite file (`ProfileRepository` gained a `databasePathOverride` constructor for this). - Caught and fixed a real bug in the process: `normalizedTags()`'s result was bound directly without the `nonNullTrimmed()` null-guard every other field already uses. Creating a profile with **no tags at all** hit the `tags NOT NULL` constraint and silently failed -- this affects the Import Profiles feature (#17) too, for any export where a profile has no `tags` key. - Confirmed `ctest --test-dir build` runs clean, and packaging builds (`build-deb.sh`) are unaffected (test binary isn't installed/packaged). ## Still open - `SshSessionBackend` / `RdpSessionBackend` state-transition coverage (connect/disconnect/reconnect/failed) is not started. This is a much bigger lift than `ProfileRepository` was -- both backends are tightly coupled to real network I/O and their own worker threads, so testing them meaningfully will need a testability pass first (likely extracting the pure state-machine logic behind a seam that can run without an actual SSH/RDP connection) rather than just writing tests against the current shape. Leaving this issue open for that.
Sign in to join this conversation.