732 lines
41 KiB
Markdown
732 lines
41 KiB
Markdown
# Strict Qt6 Migration Prompt: Merge of feature/migrate-lts-projects-and-application (+ contained feature/migrate-lts-tools-d-and-l), cherry-pick 5501d1e50, and feature/qt6-migration-basis-modules-merge-viewer-validation
|
||
|
||
This prompt is binding task context. Keep changes minimal, scoped, and reproducible.
|
||
The only allowed outcome is a branch
|
||
`feature/qt6-migration-projects-app-tools-viewer-validation` that contains, in order:
|
||
|
||
1. a cherry-pick commit of `5501d1e50` (`origin/bugfix/dds-fix-pre-existing-errors`), and
|
||
2. a merge commit with parents `origin/feature/migrate-lts-projects-and-application` and
|
||
`origin/feature/qt6-migration-basis-modules-merge-viewer-validation`
|
||
|
||
— such that the result contains the full work of `feature/migrate-lts-tools-d-and-l`,
|
||
`feature/migrate-lts-projects-and-application`, the cherry-picked commit, and the
|
||
viewer-validation branch, and preserves the legacy code behavior of every migrated file.
|
||
|
||
## Required base prompts
|
||
|
||
Before making changes, read and apply:
|
||
|
||
- ./prompts/combined-migration-subfolder-rti-compact.prompt.md
|
||
- ./prompts/commit-policy.prompt.md (repository mapping, pre-commit checks, per-repo commits)
|
||
|
||
If a base prompt is stricter, follow it. This prompt overrides it only for:
|
||
|
||
- build variants: use ON variants only for `BUILD_RTI`/`BUILD_GRANTLEE`, never OFF
|
||
- commit message format: max 2 lines, no co-author/co-authored-by/bot attribution lines
|
||
(see "Commits")
|
||
|
||
## Task
|
||
|
||
Produce the result branch from three inputs (the tools branch is already contained — see
|
||
below — so exactly two operations are performed: one cherry-pick, one merge):
|
||
|
||
- **ours (merge target base):** `feature/migrate-lts-projects-and-application`
|
||
remote tip at prompt writing (2026-09-27): `b18844a20` ("Document GROUP10 validation
|
||
results", Torsten Wierschin, 2026-09-25)
|
||
- **tools branch (verification only — already contained):**
|
||
`feature/migrate-lts-tools-d-and-l`
|
||
remote tip at prompt writing: `2b8f3f02c` ("Add Group 9 (R,S,T,V,W) LTS Tools migration
|
||
support", 2026-09-24). **Verified 2026-09-27:** `git merge-base
|
||
origin/feature/migrate-lts-tools-d-and-l origin/feature/migrate-lts-projects-and-application`
|
||
equals the tools tip `2b8f3f02c` — the tools branch is an **ancestor** of the projects
|
||
tip. No merge is needed; the procedure below only verifies the containment.
|
||
- **cherry-pick:** `5501d1e50` ("Qt6 Migration: Update stub headers to include generated
|
||
files", Torsten Wierschin, 2026-09-22) — the tip of
|
||
`origin/bugfix/dds-fix-pre-existing-errors` (single commit after its fork point
|
||
`0997dcba7`)
|
||
- **theirs (branch to merge in):** `feature/qt6-migration-basis-modules-merge-viewer-validation`
|
||
remote tip at prompt writing: `9c1ac7cbe` ("Merge
|
||
feature/lts-viewer-validation-testing-phase into feature/qt6-migration-basis-modules-merge",
|
||
berrux_dev, 2026-09-27)
|
||
- **merge base (projects × viewer-validation):** `fd3e5e838` ("Add --build-viewer-only
|
||
option to skip Groups 1-4 and build Viewer targets only", 2026-09-23)
|
||
- **result branch:** `feature/qt6-migration-projects-app-tools-viewer-validation`
|
||
(does not exist yet; create it from `origin/feature/migrate-lts-projects-and-application`)
|
||
|
||
All work happens in the repository `./qt-migration-legatus` (it is a separate git
|
||
repository; never commit its changes into the workspace root or the legacy repository).
|
||
|
||
## Branches and trees
|
||
|
||
Working repository:
|
||
|
||
- `./qt-migration-legatus`
|
||
|
||
Trees:
|
||
|
||
- Legacy Qt5 source tree (read-only reference, never modify):
|
||
`./qt-migration-legatus/qt5-before/qt5-legatus-legacy`
|
||
- Qt6 target tree (the only tree that is modified):
|
||
`./qt-migration-legatus/qt6-after/qt6-migrated-legatus`
|
||
|
||
Before starting:
|
||
|
||
1. `git fetch origin` in `./qt-migration-legatus`.
|
||
2. Verify all four refs still match the hashes above:
|
||
- `git rev-parse origin/feature/migrate-lts-projects-and-application` → `b18844a20`
|
||
- `git rev-parse origin/feature/migrate-lts-tools-d-and-l` → `2b8f3f02c`
|
||
- `git rev-parse origin/bugfix/dds-fix-pre-existing-errors` → `5501d1e50`
|
||
- `git rev-parse origin/feature/qt6-migration-basis-modules-merge-viewer-validation` → `9c1ac7cbe`
|
||
3. Re-verify the tools containment: `git merge-base --is-ancestor
|
||
origin/feature/migrate-lts-tools-d-and-l origin/feature/migrate-lts-projects-and-application`
|
||
must exit 0. If any tip moved or the containment check fails, recompute the merge
|
||
base, re-run the dry run (step 3 of the procedure), and record the new state before
|
||
touching anything.
|
||
4. Verify the working tree of `./qt-migration-legatus` is clean (`git status --short`).
|
||
Do not overwrite uncommitted user changes; if they block safe work, report the
|
||
blocker. (Known state at prompt writing: the main worktree is on
|
||
`feature/qt6-migration-basis-modules-merge-viewer-validation` at `9c1ac7cbe`, clean.)
|
||
|
||
## What each side contains
|
||
|
||
Understand all three inputs before resolving anything. The result must keep the work of
|
||
ALL of them.
|
||
|
||
**projects side (ours, 8 commits after the merge base, 47 files):**
|
||
|
||
- `9f0076a19` — LTS Tools Group 6 (D&L directories) Qt6 migration: `GROUP6_TARGETS`
|
||
(dbAdministration, SettingsRemover, dbUpdate, tDataSampleGenerator,
|
||
tDataSampleReceiver, DateTimeSyncer, ddsview, displayPanelSimulator, LicenceEditor,
|
||
localDomainFinder, **LogViewer**)
|
||
- `db8adbfe3` — Tools Group 7 (A,B,C,E,I directories)
|
||
- `1e1a3e6f3` — Group 8 (J,M,N,P,Q) build script support + CTest infrastructure
|
||
(34 files under `tests/`: `tests/CMakeLists.txt` + `test_<Tool>.cpp` registrations)
|
||
- `2b8f3f02c` — Tools Group 9 (R,S,T,V,W) — **this is the tip of
|
||
`feature/migrate-lts-tools-d-and-l` (the "alle Tools" branch); Groups 6–9 together are
|
||
the complete LTS Tools migration**
|
||
- `168d03866` — GROUP10 (LTS Projects: 9 project plugin targets — ProjectGuezPlugin,
|
||
ProjectQatarMOUTPlugin, ProjectQatarPlugin, ProjectLegatusPlugin, ProjectDemoPlugin,
|
||
ProjectL400P2Plugin, ProjectComMasterPlugin, ProjectAhtcPlugin, ProjectEtsPlugin) and
|
||
GROUP11 (LTS Application: OperatorApplication, thp_viewer, aarApp)
|
||
- `97a9992ce` / `4d6bef5fa` — GROUP7–11 default initializations + Docker env passthrough
|
||
(`-e BUILD_GROUP6..11`)
|
||
- `b18844a20` — `GROUP10_VALIDATION_RESULTS.md`: GROUP10 validated with
|
||
`BUILD_RTI=ON BUILD_GRANTLEE=ON BUILD_ARCGIS=ON`; **GROUP11 blocked by a pre-existing
|
||
`svcPdmClient` (Services/ProjectDataManagement) Qt6 MOC failure** (base state, see
|
||
"Tests")
|
||
- touched `Lts/Tools/{ConfigX,DBAdministration,DBUpdate,ProjectSettingsEditor}` sources
|
||
(Qt6 fixes) and `new_docker_build.sh` (+186/−1: Groups 6–11 usage/env/arg-parsing,
|
||
GROUP6–11 target arrays, `run_build_group` calls, log_group lines for Groups 7–11 —
|
||
**Group 6 has no log_group line on this side**)
|
||
|
||
**viewer-validation side (theirs, 52 commits after the merge base, 1313 files):**
|
||
|
||
- the full `feature/qt6-migration-basis-modules-merge` work: complete Qt6/rtiddsgen 7.7
|
||
migration of residual Lts services/proxies/plugins (incl. the ProjectDataManagement
|
||
service sources — `a41001955`), codegen fixes, Qt6::SerialPort IMPORTED target,
|
||
GROUP3 full migrated-service target set (~200 targets incl. per-service tests and the
|
||
PDM block `svcPdmCommon/Client/Server`, `svcProjectDataManagement`, `pdmTests`)
|
||
- docker-script unification: `new_docker_build.sh` single validation script
|
||
(`docker_build.sh` deleted and must stay deleted), consolidated single GROUP4 array
|
||
(DDS tests `ddsGenericDataTests`/`ddsDataTopicTests`/`ddsFunctionTopicTests` +
|
||
Lts/Proxies) and single Group-4 `run_build_group` call, `--cmake_build_flags` option,
|
||
prebuilt image `legatus-qt6-prebuilt:latest`
|
||
- viewer-validation features: `--build-viewer-only`, `--codification`, KDReports-qt6
|
||
detection (`cmake/FindKDReports.cmake`), build-parts `BUILD_SV/WS/AAR`,
|
||
`LtsDataViewTest`/`LtsFileDialogTest` auto-exit adaptations (CI `QTimer` 1000 ms,
|
||
`QT_QPA_PLATFORM=offscreen`, `TIMEOUT 30`)
|
||
- **stub relocation (`4223ca2ff`): the `include/*/*_dtc.h` stub headers were moved from
|
||
`qt6-after/qt6-migrated-legatus/include/` to
|
||
`qt6-after/qt6-migrated-legatus/.forward-declarations/include/`** — 111 files deleted
|
||
from the old location; `BUILD_STATUS_REPORT.md` added
|
||
- follow-up fixes: `ci/allowed_signers` principal format (`e748e82c8`), record_replay
|
||
`fromQVariant` + PPM MOC exclusion (`36f077bce`), viewer-validation merge
|
||
(`c664611b8` + `9c1ac7cbe`)
|
||
|
||
**cherry-pick `5501d1e50` (1 commit, 40 files):** updates the 38 stub headers
|
||
(`include/*/*_dtc.h` + `pdm_enums.hpp` + `ppm.hpp` + `include/ParticipantManagement/
|
||
ppm_types.h`) so they include the generated files from `build4/Lts/Proxies/*`, updates
|
||
the real service source `Lts/Services/ParticipantManagement/ppm_types.h`, and adds
|
||
`BUILD_STATUS_REPORT.md`. Note on the service source: the viewer-validation side made
|
||
the same change to it (both sides converge to byte-identical content at their tips —
|
||
verified 2026-09-27), so it auto-merges cleanly (it is not among the dry-run conflicts).
|
||
**Supersession fact (verified 2026-09-27):** the viewer-validation side already carries
|
||
the same change as `4223ca2ff` (same author, same subject) applied to the relocated
|
||
`.forward-declarations/include/` location: for `include/FileManagement/flm_dtc.h` and
|
||
`include/ParticipantManagement/ppm_types.h` the patches are byte-identical except the
|
||
path prefix, and the final content of `ppm_types.h` at the theirs tip equals the
|
||
content produced by `5501d1e50`. `BUILD_STATUS_REPORT.md` is byte-identical between
|
||
`5501d1e50` and the theirs tip. See "Cherry-pick handling".
|
||
|
||
## Cherry-pick handling (5501d1e50) — required sequence
|
||
|
||
The cherry-pick must **exist as a commit in the result history** (do not merely document
|
||
it as superseded and skip it). Perform it FIRST, onto the clean projects base, where it
|
||
applies cleanly (verified 2026-09-27: `git cherry-pick 5501d1e50` onto `b18844a20`
|
||
succeeds without conflicts, producing commit `e07bc9a91` in the test run):
|
||
|
||
1. `git cherry-pick -n -x 5501d1e50` (no conflicts expected; if any, stop and report —
|
||
it applied cleanly on 2026-09-27)
|
||
2. Commit it signed, keeping the **original author** (Torsten Wierschin — the author of
|
||
the work; `git cherry-pick` already sets the author from the source commit; do not
|
||
reset it), with the original subject and body **minus the
|
||
`Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>` line**
|
||
(repository policy: no co-author/co-authored-by/bot attribution lines), and with the
|
||
cherry-pick reference line (`(cherry picked from commit 5501d1e50...)`) kept. Max 2
|
||
lines of your own wording do not apply to the body of a cherry-picked message — the
|
||
original body is preserved verbatim (minus the bot line) so the change stays
|
||
attributable.
|
||
3. Only then start the merge (step 4 of the procedure).
|
||
|
||
Consequence of this order (verified by dry run 2026-09-27): the subsequent merge produces
|
||
**24 modify/delete conflicts** on the old-location stub files (modified by the
|
||
cherry-pick on ours side, deleted by the relocation on theirs side). Their resolution is
|
||
mechanical and safe — keep the deletion — because the updated content already exists at
|
||
the new location. Before resolving, verify that per file (record any MISMATCH as a
|
||
blocker):
|
||
|
||
```bash
|
||
MB=qt6-after/qt6-migrated-legatus
|
||
for f in $(git diff --name-only --diff-filter=U | grep '^qt6-after/qt6-migrated-legatus/include/'); do
|
||
rel=${f#$MB/include/}
|
||
git show origin/feature/qt6-migration-basis-modules-merge-viewer-validation:"$MB/.forward-declarations/include/$rel" > /tmp/newloc 2>/dev/null || { echo "MISSING-NEW-LOC: $f"; continue; }
|
||
git show 5501d1e50:"$f" > /tmp/oldloc
|
||
cmp -s /tmp/oldloc /tmp/newloc || echo "MISMATCH: $f"
|
||
done
|
||
```
|
||
|
||
Then resolve each with `git rm <file>` (keep deletion; the `.forward-declarations/`
|
||
copy is the canonical one). The 24 expected files (dry run 2026-09-27):
|
||
`{AlarmManagement/alm, AreaEffectSimulation/aes, AssetManagement/asm,
|
||
AudioVideoManagement/avm, Buildings/bld, CentralEffectSimulation/ces,
|
||
ComponentMonitor/cmo, Core/core, EffectShowClient/esc, EffectShowManagement/esm,
|
||
Evaluations/evl, ExerciseManagement/exm, GuezIedManagement/gim, GuezNasat/gna,
|
||
NotificationManagement/nom, OcSituationServer/oss, ScenarioManagement/scm,
|
||
SituationReplay/srp, SituationReplayManagement/srm, Skeleton/skl,
|
||
SoundManagement/som, TrainingAreaBase/tab, TrainingAreaBaseOC/taboc}_dtc.h` plus
|
||
`ProjectDataManagement/pdm_enums.hpp`.
|
||
|
||
The other 14 cherry-pick stub files (`{CodificationManagement/cod,
|
||
ExerciseEventManagement/eem, FileManagement/flm, InfrastructureManagement/ism,
|
||
MeteoDataManagement/mdm, MarkerManagement/mrk, Messaging/msg,
|
||
OperatorManagement/opm, PresentationManagement/pre, ReportManagement/rep,
|
||
TargetManagement/tgt, WarehouseGuez/whg}_dtc.h` + `ParticipantManagement/ppm.hpp` +
|
||
`ParticipantManagement/ppm_types.h`) were **not** relocated by the theirs side, so they
|
||
stay at the old `include/` location with the cherry-pick's update — expected outcome,
|
||
do not "fix" it (the old `include/` tree legitimately remains in the tree; relocated
|
||
copies also exist at the new location for them — pre-existing pattern on the theirs
|
||
side).
|
||
|
||
## Known conflict surface (dry run 2026-09-27)
|
||
|
||
A dry run of the full sequence (cherry-pick onto `b18844a20`, then
|
||
`git merge --no-commit --no-ff origin/feature/qt6-migration-basis-modules-merge-viewer-validation`
|
||
in a throwaway worktree) found:
|
||
|
||
- **1 content conflict (UU):** `qt6-after/qt6-migrated-legatus/new_docker_build.sh`
|
||
(3 conflict hunks — recipe below)
|
||
- **24 modify/delete conflicts (UD):** the old-location stub files listed above
|
||
- **auto-merged (verified in the dry run, keep as-is unless a check below fails):**
|
||
- `new_docker_build.sh` all other regions: `GROUP3_TARGETS` = theirs' expanded
|
||
179-target service set (incl. the PDM block), single consolidated
|
||
`GROUP4_TARGETS` (DDS tests + Proxies), the four-way GROUP5 conditional
|
||
(BUILD_ARCGIS × BUILD_VIEWER_ONLY), the GROUP6–11 arrays + `run_build_group`
|
||
calls for Groups 1,4,2,3,5,6,7,8,9,10,11, the `BUILD_GROUP6..11` container
|
||
defaults (1–3 ON, 4–11 OFF), the `-e BUILD_GROUP1..11` docker passthrough, and the
|
||
`BUILD_VIEWER_ONLY` switch block
|
||
- `qt6-after/qt6-migrated-legatus/tests/CMakeLists.txt` (both sides changed it:
|
||
theirs' test additions + ours' 34 tool-test registrations — verify after the merge
|
||
that both sets of registrations are present)
|
||
- `BUILD_STATUS_REPORT.md` (byte-identical on both sides → no conflict)
|
||
- `Lts/Services/ParticipantManagement/ppm_types.h` (cherry-pick's change on ours
|
||
side converges to byte-identical content with the theirs-side change → no
|
||
conflict; verify after the merge that the merged content equals the content at
|
||
`5501d1e50`)
|
||
- all 1313 theirs-side files (services/proxies/viewer rewrites,
|
||
`.forward-declarations/` tree, `BUILD_STATUS_REPORT.md`)
|
||
|
||
Re-run the dry run after the fetch and treat its output as authoritative; the list above
|
||
is the expected starting point. If the dry run shows additional conflicts, resolve them
|
||
with the four-version method (see below) and record them in the final report.
|
||
|
||
## Conflict resolution rules
|
||
|
||
These rules exist to guarantee: the merged tree keeps all three inputs' functionality
|
||
and no file's behavior deviates from the legacy Qt5 behavior beyond the approved
|
||
Qt6/C++17/rtiddsgen adaptations.
|
||
|
||
General:
|
||
|
||
- Resolve semantically, never mechanically. For every conflicted hunk read four
|
||
versions: the merge-base version, ours, theirs, and the legacy Qt5 equivalent (for
|
||
`new_docker_build.sh` there is no legacy counterpart — pure Qt6 build machinery — so
|
||
use the merge-base version as the third reference).
|
||
- Never take `ours` or `theirs` wholesale unless you prove the losing side had no
|
||
unique changes: `git diff <merge-base>..theirs -- <file>` (or `..ours`) must show
|
||
nothing that the kept version lacks. Record the proof in the final report.
|
||
- No behavior-changing edits beyond the merge itself. No refactoring, no style cleanup,
|
||
no warning suppression, no new features.
|
||
|
||
`new_docker_build.sh` (the single content conflict) — required merge recipe, 3 hunks:
|
||
|
||
1. **Usage text (~line 48):** keep OURS' six `--group6 … --group11` usage lines AND
|
||
THEIRS' corrected `--build-viewer-only` line
|
||
(`Build only Viewer module targets (skip Groups 1-4, implies --group5 --codification; ctest runs)`)
|
||
— do **not** keep ours' stale `--build-viewer-only` line
|
||
(`… implies --group5 --no-ctest`), which contradicts the handler (it sets
|
||
`RUN_CTEST=ON`; the corrected theirs line was already validated in the
|
||
viewer-validation merge).
|
||
2. **`export` line (~line 898):** union of both lists, i.e. exactly:
|
||
`export BUILD_ALL BUILD_RTI BUILD_GRANTLEE BUILD_ARCGIS BUILD_CODIFICATION BUILD_GROUP1 BUILD_GROUP2 BUILD_GROUP3 BUILD_GROUP4 BUILD_GROUP5 BUILD_GROUP6 BUILD_GROUP7 BUILD_GROUP8 BUILD_GROUP9 BUILD_GROUP10 BUILD_GROUP11 BUILD_VIEWER_ONLY RUN_CTEST TESTS_ONLY INTEGRATION_TEST USE_PREBUILT_IMAGE BUILD_PREBUILT_IMAGE DELETE_PREBUILT_IMAGE DOCKER_IMAGE CMAKE_BUILD_FLAGS`
|
||
3. **`log_group` banner lines (~line 1053):** keep THEIRS' lines for Groups 1, 2, 3
|
||
(the corrected `Build Group 3 (application + service targets)` label), 4
|
||
(`Build Group 4 (DDS tests + Proxies)`) and 5 (`Build Group 5 (Viewer)`), plus
|
||
OURS' lines for Groups 7, 8, 9, 10, 11, in that order. Optionally (text-only,
|
||
non-behavioral) add the missing ours-side Group 6 line
|
||
`log_group "Build Group 6 (LTS Tools)" "$BUILD_GROUP6"` so every group with a
|
||
`run_build_group` call has a banner line — record if added.
|
||
|
||
Post-resolution script checks (record in the final report):
|
||
|
||
- `bash -n` on the host script and on the extracted container-side script
|
||
- `--help` renders and lists `--group6..--group11`, `--build-viewer-only`,
|
||
`--codification`, `--cmake_build_flags`; an unknown option is still rejected
|
||
- target-set check: `GROUP3_TARGETS` = 179 targets and still contains the PDM block
|
||
(`svcPdmCommon/Client/Server`, `svcProjectDataManagement`, `pdmTests`);
|
||
`GROUP4_TARGETS` single array containing `ddsGenericDataTests`,
|
||
`ddsDataTopicTests`, `ddsFunctionTopicTests`; GROUP5 four-way conditional intact;
|
||
GROUP6–11 arrays, `run_build_group` calls, container defaults and `-e` passthrough all
|
||
present
|
||
- the `BUILD_VIEWER_ONLY` block still switches Groups 1–4 OFF / Group 5 ON before the
|
||
`run_build_group` calls (Groups 6–11 remain OFF by default in that mode)
|
||
- the prebuilt image name is `legatus-qt6-prebuilt:latest` everywhere (no second name);
|
||
no reference to `docker_build.sh` remains; the container-side script still starts
|
||
with `set -euo pipefail`
|
||
|
||
CMake conflicts: none in the dry run. If the re-run shows new CMake conflicts (e.g. in
|
||
`tests/CMakeLists.txt`): take the union of both sides' targets, dependencies, include
|
||
directories, and link libraries; keep the `Qt6::SerialPort` manual IMPORTED target and
|
||
the GROUP5/Viewer wiring (theirs) side by side with the GROUP6–11 tool-test
|
||
registrations (ours). After resolving, verify with a fresh configure that both sides'
|
||
targets/options exist.
|
||
|
||
## Mandatory build variants
|
||
|
||
Only these variants are valid:
|
||
|
||
- `BUILD_RTI=ON`
|
||
- `BUILD_GRANTLEE=ON`
|
||
|
||
Forbidden: `BUILD_RTI=OFF`, `BUILD_GRANTLEE=OFF`.
|
||
|
||
- Do not implement, fix, preserve, test, or validate OFF variants of
|
||
`BUILD_RTI`/`BUILD_GRANTLEE`. Do not add CMake logic, tests, stubs, or fallbacks for
|
||
them. Validation must use `BUILD_RTI=ON` and `BUILD_GRANTLEE=ON`.
|
||
- `BUILD_ARCGIS`: the projects side validated GROUP10/GROUP11 with
|
||
`BUILD_ARCGIS=ON` (`GROUP10_VALIDATION_RESULTS.md`) and
|
||
`external/ArcGIS/MapsSDK_Qt_300.0.0` exists at the pipeline root (mounted to the
|
||
container's `/workspace/external`). Use `BUILD_ARCGIS=ON` in the coverage run that
|
||
builds GROUP10/GROUP11 (run 2 below) and leave it at its default OFF in the other
|
||
runs. This is not an RTI/Grantlee OFF variant; the prohibition above does not apply.
|
||
- The viewer-validation side options `BUILD_VIEWER_ONLY` (default OFF),
|
||
`BUILD_CODIFICATION` (default OFF), `BUILD_SV`/`BUILD_WS`/`BUILD_AAR` (default ON)
|
||
and the projects side `BUILD_GROUP6..11` (default OFF) are design features: keep
|
||
their defaults and semantics as-is; do not flip them.
|
||
|
||
## Preservation rules
|
||
|
||
Preserve module removals from commit `92ad7d468` ("remove all unneeded module listed
|
||
from Niklas"): do not restore removed modules, files, targets, directories, or
|
||
dependencies — on any side.
|
||
|
||
Preserve LogViewer reinsert from commit `1fa789767` ("Added LogViewer again"): do not
|
||
remove, disable, or break LogViewer integration. Note: `LogViewer` is a GROUP6 target
|
||
on the projects side — it must survive in `GROUP6_TARGETS` after the merge.
|
||
|
||
Preserve prior IDL warning fixes from commit `be912de9d`: do not reintroduce multiple
|
||
enum definitions, duplicate enumerators, or builtin type/keyword collisions.
|
||
|
||
Preserve the ON-variant-only decisions already made on all branches.
|
||
|
||
Preserve the docker-script unification: `docker_build.sh` stays deleted;
|
||
`new_docker_build.sh` remains the single validation script; the GROUP3 service target
|
||
set, the consolidated GROUP4 array, the GROUP6–11 groups, and the viewer-only/
|
||
codification options all survive the script merge (see the merge recipe above).
|
||
|
||
Preserve the stub relocation decision: the `.forward-declarations/` tree is the
|
||
canonical location for relocated stubs; the 24 old-location stubs deleted by the
|
||
viewer-validation side stay deleted (see "Cherry-pick handling"); the 14 non-relocated
|
||
cherry-picked stubs stay at the old `include/` location.
|
||
|
||
Preserve the projects side artifacts: the 34 `tests/*` tool-test files and their
|
||
`tests/CMakeLists.txt` registrations, `GROUP10_VALIDATION_RESULTS.md`, and the
|
||
`Lts/Tools/{ConfigX,DBAdministration,DBUpdate,ProjectSettingsEditor}` Qt6 fixes.
|
||
|
||
## Stubs and forward declarations
|
||
|
||
Any required existing stub, compatibility declaration, or forward declaration must live
|
||
only under:
|
||
|
||
- `./qt-migration-legatus/qt6-after/qt6-migrated-legatus/forward-declarations/`
|
||
- `./qt-migration-legatus/qt6-after/qt6-migrated-legatus/.forward-declarations/include/`
|
||
|
||
- Do not leave such files in service directories unless they are real service source
|
||
files.
|
||
- Do not create or keep stubs for forbidden OFF variants.
|
||
- Do not use stubs as replacements for real RTI, ndsgen, KTextTemplate, or Grantlee
|
||
outputs in ON builds.
|
||
- Report every moved, removed, or newly referenced stub/forward declaration.
|
||
- This merge resolves 24 stub files to deletion (keep-theirs) and leaves 14 updated
|
||
stubs at the old `include/` location (pre-existing pattern) — both are the intended
|
||
outcomes; see "Cherry-pick handling".
|
||
|
||
## Qt link rules
|
||
|
||
No active target in the merged tree may link Qt5 imported targets.
|
||
|
||
Search the merged tree for and fix active uses of: `Qt5::`, `find_package(Qt5`, `QT5_`,
|
||
`Qt5Core`, `Qt5Widgets`, `Qt5Network`.
|
||
|
||
Regression check specific to this merge: the projects side touched
|
||
`tests/CMakeLists.txt`, `Lts/Tools/*` sources and `new_docker_build.sh`; the
|
||
viewer-validation side touched cmake infrastructure (`cmake/NGLMacros.cmake`,
|
||
`cmake/FindKDReports.cmake`, root `CMakeLists.txt`). After the merge, re-run the search
|
||
over ALL files touched by the merge (auto-merged files included), not just the
|
||
conflicted ones; the legacy `QT5_WRAP_UI`/`QT5_ADD_RESOURCES` function-name calls
|
||
(compat shim) are allowed and pre-exist on both sides — imported-target links are not.
|
||
|
||
## Legacy comparison (required validation step)
|
||
|
||
This step proves the merge did not change code behavior.
|
||
|
||
For every file you edit during conflict resolution (expected:
|
||
`new_docker_build.sh` only — the 24 stub deletions are covered by the per-file
|
||
content check in "Cherry-pick handling"):
|
||
|
||
1. Read the legacy Qt5 source at the same relative path in
|
||
`./qt-migration-legatus/qt5-before/qt5-legatus-legacy`. If the file does not exist
|
||
there (pure Qt6 build machinery — expected for `new_docker_build.sh`), say so and
|
||
compare against the merge base instead.
|
||
2. Produce three diffs: merge-base vs legacy (or: skip with justification), ours vs
|
||
merge-base, theirs vs merge-base.
|
||
3. Produce the audit diff: merged result vs merge base.
|
||
4. Classify every hunk of the audit diff into exactly one category:
|
||
- `qt6-api`: mandatory Qt5→Qt6 API adaptation
|
||
- `rtiddsgen-api`: generated-API adaptation
|
||
- `build`: CMake/docker/test-infra change with no runtime semantics
|
||
- `merge-union`: line present because both branches required it
|
||
- `semantic-change`: anything else
|
||
5. Every `semantic-change` hunk is a failure of this merge unless you can point to the
|
||
legacy source line that implements the same behavior. Fix it back to the legacy
|
||
semantics (with approved adaptations) or report it as a blocker. Do not silently
|
||
accept `semantic-change` hunks. (For `new_docker_build.sh`, `build`/`merge-union`
|
||
are the expected categories; a `semantic-change` there means a behavior of one
|
||
side's script was silently dropped.)
|
||
6. Record the per-file hunk classification (counts per category is sufficient; list
|
||
every `semantic-change` hunk explicitly) in the final report.
|
||
|
||
Additional equivalence checks on the merged tree:
|
||
|
||
- CMake option union: `BUILD_VIEWER_ONLY`, `BUILD_CODIFICATION`, `BUILD_SV/WS/AAR`,
|
||
`BUILD_GROUP6..11`, the `Qt6::SerialPort` IMPORTED target, GROUP5/Viewer wiring, and
|
||
GROUP6–11 wiring all exist after the auto-merge (auto-merged files are not re-read by
|
||
default — verify them).
|
||
- CTest registration union: `tests/CMakeLists.txt` contains BOTH the theirs-side
|
||
registrations (e.g. `LtsDataViewTest`, `LtsFileDialogTest`, service tests) AND the
|
||
ours-side 34 tool-test registrations.
|
||
- `LtsDataViewTest` registration: `add_test` present, `QT_QPA_PLATFORM=offscreen` test
|
||
property present, auto-exit `QTimer` present in `test.cpp`.
|
||
- `BUILD_STATUS_REPORT.md` and `GROUP10_VALIDATION_RESULTS.md` both present in the
|
||
merged tree.
|
||
- Docker build script: every target group, apt package, and build option both sides
|
||
added is present (see the script checks in the merge recipe); the container-side
|
||
script still starts with `set -euo pipefail`.
|
||
|
||
## Code generation rules
|
||
|
||
If generated files are required (not expected for this merge):
|
||
|
||
- reconstruct the real legacy generation flow
|
||
- generate into the build tree
|
||
- consume from the build tree
|
||
- list complete OUTPUT and BYPRODUCTS
|
||
- set correct DEPENDS and MAIN_DEPENDENCY where useful
|
||
- use deterministic WORKING_DIRECTORY
|
||
- use VERBATIM
|
||
- wire generated sources with target_sources
|
||
- wire generated include dirs with target_include_directories
|
||
- ensure compilation depends on generation
|
||
- ensure incremental rebuilds trigger on input/template changes
|
||
|
||
Never commit generated .idl, .h, .hpp, or .cpp outputs. Never consume generated outputs
|
||
from the source tree. Never fabricate generated outputs.
|
||
|
||
## Tests
|
||
|
||
- All three sides' test suites must build and run; this merge adds no new feature tests
|
||
of its own.
|
||
- The ours-side 34 `tests/test_<Tool>.cpp` tool tests (Groups 6–9) must be built and
|
||
registered in the merged `tests/CMakeLists.txt`; run them in the coverage run (run 2
|
||
below). If a tool test requires external hardware/services, classify Not Run/Timeout
|
||
as base state (record the reason) — do not make them pass by weakening the test.
|
||
- Keep the theirs-side `LtsDataViewTest` adaptations (auto-exit timer, offscreen
|
||
property, unconditional link) — they are what make the viewer-only ctest pass in CI.
|
||
- **Known base-state blocker (GROUP11):** the projects side documents
|
||
(`GROUP10_VALIDATION_RESULTS.md`) that GROUP11 (OperatorApplication, thp_viewer,
|
||
aarApp) is blocked by a pre-existing `svcPdmClient` Qt6 MOC failure. The
|
||
viewer-validation side completed the residual Lts service migration
|
||
(`a41001955`, incl. ProjectDataManagement service sources) and the PPM MOC exclusion
|
||
(`36f077bce`), so the blocker may be RESOLVED in the merged tree. In run 2, build
|
||
GROUP11 and record which: (a) `svcPdmClient` now builds — blocker cleared by the
|
||
theirs-side service work (success, document it), or (b) it still fails with the same
|
||
MOC error — base-state blocker, record it in the final report as remaining (do not
|
||
fix it in this merge).
|
||
- If a conflict resolution changed C++ semantics (it should not), add CTest tests under
|
||
`./qt-migration-legatus/qt6-after/qt6-migrated-legatus/tests/` that pin the legacy
|
||
behavior, registered with CTest, running with `BUILD_RTI=ON` and `BUILD_GRANTLEE=ON`,
|
||
policy-compatible names (`test_<name>.cpp`, …).
|
||
- No OFF-variant tests of `BUILD_RTI`/`BUILD_GRANTLEE`. No host-local paths.
|
||
|
||
## Docker and CI
|
||
|
||
Authoritative migration Dockerfile:
|
||
|
||
- `./app/Dockerfile`
|
||
|
||
Authoritative validation script (single script; `docker_build.sh` was merged into it
|
||
and deleted):
|
||
|
||
- `./qt-migration-legatus/qt6-after/qt6-migrated-legatus/new_docker_build.sh`
|
||
|
||
Validation container expectations:
|
||
|
||
- repository root at `/workspace` (the script's documented mount path)
|
||
- external dependencies under `/workspace/external` (including
|
||
`external/rti_connext_dds-7.7.0`, `external/ArcGIS` where the scripts expect them)
|
||
- `./rti_license.dat` mounted read-only if RTI requires it
|
||
- no developer-local paths
|
||
- the prebuilt image `legatus-qt6-prebuilt:latest` exists (6.23 GB at prompt writing)
|
||
and is required for KDReports-qt6 (runs 2/3 use `--use-prebuilt-image
|
||
--docker-image legatus-qt6-prebuilt:latest`; run 1 may use the base image)
|
||
|
||
Jenkins CI must be able to discover and run the merged test set. Inspect and minimally
|
||
update only if needed:
|
||
|
||
- `./qt-migration-legatus/ci/Dockerfile.*`
|
||
- `./qt-migration-legatus/ci/check_pr_policies.py`
|
||
|
||
Known pre-existing blocker (do not fix in this merge, record in the final report):
|
||
`ci/check_pr_policies.py` currently exits 1 because a series of ancestor commits (33
|
||
unsigned commits on `feature/qt6-migration-basis-modules-merge-viewer-validation` since
|
||
merge base `ed9fc51e7`, e.g. `36f077bce`, `b6a97c39e`, `fd3e5e838`; plus the
|
||
projects-side commits `b18844a20`, `4d6bef5fa`, … which carry no SSH signature
|
||
accepted by `ci/allowed_signers`) fail the signature gate. Fixing it requires
|
||
re-signing/history rewrite of source-branch commits, which is out of scope here. The
|
||
new commits created by THIS task must be signed and verify Good.
|
||
|
||
## Required procedure
|
||
|
||
1. Read the base prompts. Run `git fetch origin` and verify the four ref hashes, the
|
||
tools containment check, and the merge base (step 2 of "Branches and trees").
|
||
2. Create/checkout `feature/qt6-migration-projects-app-tools-viewer-validation` from
|
||
`origin/feature/migrate-lts-projects-and-application` in `./qt-migration-legatus`
|
||
(working tree must be clean).
|
||
3. Re-run the dry run of the full sequence in a throwaway worktree
|
||
(cherry-pick `5501d1e50`, then `git merge --no-commit --no-ff
|
||
origin/feature/qt6-migration-basis-modules-merge-viewer-validation`); confirm the
|
||
conflict list (expected: 1 UU content conflict + 24 UD modify/delete conflicts).
|
||
4. Cherry-pick `5501d1e50` (see "Cherry-pick handling", steps 1–2).
|
||
5. Run the real merge: `git merge --no-ff
|
||
origin/feature/qt6-migration-basis-modules-merge-viewer-validation` (do not
|
||
auto-commit; resolve first).
|
||
6. Run the 24-file stub content check, resolve the 24 UD conflicts as deletions, and
|
||
resolve the `new_docker_build.sh` content conflict hunk by hunk using the four-
|
||
version method and the merge recipe above.
|
||
7. Run the legacy comparison audit (previous section) over every resolved/edited file.
|
||
8. Run the regression checks: Qt5 links, removed modules, LogViewer (incl. the GROUP6
|
||
entry), IDL warnings, stub locations, ON-variant-only CMake, docker script
|
||
integrity (bash -n, --help, target-set and GROUP4/GROUP6–11 checks), CMake option
|
||
union, CTest registration union (both sides' registrations in
|
||
`tests/CMakeLists.txt`).
|
||
9. Validate in Docker with `BUILD_RTI=ON` and `BUILD_GRANTLEE=ON` — all three runs
|
||
below (run 2 additionally with `BUILD_ARCGIS=ON`).
|
||
10. Run CTest in each validated build (executed as part of the docker runs).
|
||
11. Check Jenkins/policy compatibility (record the pre-existing signature blocker).
|
||
12. Create the merge commit (see Commits).
|
||
13. Report factual status.
|
||
|
||
Do not push. The result stays local on
|
||
`feature/qt6-migration-projects-app-tools-viewer-validation` until the user says
|
||
otherwise.
|
||
|
||
## Required validation
|
||
|
||
From `./qt-migration-legatus/qt6-after/qt6-migrated-legatus`, run (in order):
|
||
|
||
```bash
|
||
# 1. Full default run (groups 1–3: DDS core, migration_tests, full migrated-service set)
|
||
BUILD_RTI=ON BUILD_GRANTLEE=ON ./new_docker_build.sh
|
||
|
||
# 2. Coverage run: Proxies + Viewer + ALL Tools groups (6–9) + Projects (10)
|
||
# + Application (11) + codification; ArcGIS ON because the projects side
|
||
# validated GROUP10/11 with BUILD_ARCGIS=ON and external/ArcGIS is mounted
|
||
BUILD_RTI=ON BUILD_GRANTLEE=ON BUILD_ARCGIS=ON ./new_docker_build.sh \
|
||
--use-prebuilt-image --docker-image legatus-qt6-prebuilt:latest \
|
||
--group4 --group5 --group6 --group7 --group8 --group9 --group10 --group11 --codification
|
||
|
||
# 3. Viewer-only run (validates the theirs-side feature end to end)
|
||
BUILD_RTI=ON BUILD_GRANTLEE=ON ./new_docker_build.sh --build-viewer-only \
|
||
--use-prebuilt-image --docker-image legatus-qt6-prebuilt:latest
|
||
```
|
||
|
||
If a direct clean build is useful, use:
|
||
|
||
```bash
|
||
cmake -S /workspace/qt-migration-legatus/qt6-after/qt6-migrated-legatus -B /workspace/build-projects-tools-viewer-rti-on-grantlee-on -G Ninja -DCMAKE_BUILD_TYPE=Debug -DBUILD_RTI=ON -DBUILD_GRANTLEE=ON
|
||
cmake --build /workspace/build-projects-tools-viewer-rti-on-grantlee-on --parallel
|
||
ctest --test-dir /workspace/build-projects-tools-viewer-rti-on-grantlee-on --output-on-failure
|
||
```
|
||
|
||
CTest baseline: ctest exits with code 8 when tests are "Not Run". The pre-existing Not
|
||
Run class (duplicate `_gtest` registrations, sibling targets of OFF groups, hardware-
|
||
dependent tests such as `taboc_serialtest`, `bld_bsm_test`) is not a failure. In
|
||
addition, the following six were documented as base-state first-run failures in the
|
||
viewer-validation merge's final report
|
||
(`./prompts/merge-lts-viewer-validation-into-basis-modules-merge.FINAL-REPORT.md`) and
|
||
remain base-state here: `ddsFunctionTopicTests` (deterministic FTS/FTC signal defect),
|
||
`bld_bsm_test`/`taboc_serialtest` (hardware waits), `bld_vwm_test`/`bld_vwm_xml_test`
|
||
(manual-test data absent from the repo), `LtsFileDialogTest` (GUI blocks on DDS init
|
||
before the CI auto-exit timer fires). Treat only NEW `***Failed`/`***Timeout` entries
|
||
beyond these as merge regressions: fix or report as a blocker.
|
||
|
||
Mandatory positive checks:
|
||
|
||
- Run 2: GROUP10 must build (the projects side validated it — regression if it breaks);
|
||
GROUP6–9 tool targets must build; the 34 tool tests must at least be registered;
|
||
`LtsDataViewTest` must run and pass (where built); the GROUP11 outcome must be
|
||
classified per "Tests".
|
||
- Run 3: `LtsDataViewTest` (and `LtsFileDialogTest` where built) MUST run and pass —
|
||
if it does not, that is a merge regression: fix it or report it as a blocker.
|
||
- If a previously passing test becomes Not Run or Failed after the merge, that is a
|
||
merge regression: fix it or report it as a blocker.
|
||
|
||
Do not run or validate OFF variants of `BUILD_RTI`/`BUILD_GRANTLEE`.
|
||
|
||
## Commits
|
||
|
||
Two commits are created on the result branch:
|
||
|
||
1. **Cherry-pick commit** of `5501d1e50` (see "Cherry-pick handling"): keeps the
|
||
original author (Torsten Wierschin — the author of the work), keeps the original
|
||
subject and body minus the `Co-authored-by: Copilot` line, and keeps the
|
||
`(cherry picked from commit …)` reference line. Signed.
|
||
2. **Merge commit**: single author — the user's git identity. The user is the only
|
||
author; do not add any co-author, co-authored-by, or bot attribution lines of any
|
||
kind. Message: maximum 2 lines (one subject line plus at most one short body line),
|
||
no blank-line separators, no extra metadata. Subject example:
|
||
`Merge feature/qt6-migration-basis-modules-merge-viewer-validation into feature/migrate-lts-projects-and-application`
|
||
body line example:
|
||
`Cherry-picks 5501d1e50 (stub-header updates, superseded by 4223ca2ff relocation); resolves 1 content + 24 modify/delete conflicts; validates BUILD_RTI=ON BUILD_GRANTLEE=ON incl. Tools Groups 6-11.`
|
||
|
||
- The repository has `commit.gpgsign=false`: sign every created commit explicitly
|
||
(`git commit -S`, `git cherry-pick -S` or the two-step form from "Cherry-pick
|
||
handling"). Follow `./prompts/commit-policy.prompt.md` for repository mapping and
|
||
pre-commit checks. If it requires signed commits and signing is not configured in
|
||
this repository context, stop and report the exact reason instead of committing
|
||
unsigned.
|
||
- If a conflict resolution requires an additional fix commit, the same 2-line /
|
||
single-author (user) / no-attribution / signed rules apply.
|
||
|
||
## Success criteria
|
||
|
||
Success requires:
|
||
|
||
- `feature/qt6-migration-projects-app-tools-viewer-validation` contains the
|
||
cherry-pick commit of `5501d1e50` (signed, original author, no bot attribution line)
|
||
and a merge commit (signed, user as sole author) with parents
|
||
`origin/feature/migrate-lts-projects-and-application` (or its verified successor tip)
|
||
and `origin/feature/qt6-migration-basis-modules-merge-viewer-validation` (or its
|
||
verified successor tip)
|
||
- the tools containment is re-verified (`2b8f3f02c` is an ancestor of the projects
|
||
base) and recorded
|
||
- `new_docker_build.sh` resolved hunk by hunk with the merge recipe; resolution
|
||
evidence and the post-resolution script checks recorded
|
||
- the 24 stub modify/delete conflicts resolved as deletions after the per-file
|
||
content check (no MISMATCH); the 14 non-relocated cherry-picked stubs documented as
|
||
staying at the old location
|
||
- both sides' functionality preserved: GROUP6–11 target sets, the 34 tool-test
|
||
registrations, `GROUP10_VALIDATION_RESULTS.md`, and the `Lts/Tools` fixes from the
|
||
projects side; the full migrated-service set, GROUP3 service target set,
|
||
consolidated GROUP4 array, docker-script unification, `--build-viewer-only`,
|
||
`--codification`, KDReports wiring, and the `LtsDataViewTest`/`LtsFileDialogTest`
|
||
adaptations from the viewer-validation side
|
||
- legacy comparison audit done for every resolved file; zero unexplained
|
||
`semantic-change` hunks
|
||
- configure, build, and CTest pass with `BUILD_RTI=ON` and `BUILD_GRANTLEE=ON` in all
|
||
three validation runs (GROUP11 classified per "Tests"; the six documented base-state
|
||
first-run failures may remain, all others must pass)
|
||
- Jenkins/policy discovery accepts the merged test set (or the pre-existing signature
|
||
blocker is recorded as the only failure); the new commits verify signed Good
|
||
- no active Qt5 imported target links remain in the merged tree
|
||
- generated outputs are build-tree only, freshly produced, never committed or consumed
|
||
from the source tree; no fake generated files, dummy files, mocks, placeholders, or
|
||
stubbed generated outputs
|
||
- required stubs/forward declarations only in allowed directories; `docker_build.sh`
|
||
stays deleted
|
||
- removed modules remain removed; LogViewer preserved (incl. the GROUP6 target)
|
||
- no OFF-variant logic, tests, or stubs introduced for `BUILD_RTI`/`BUILD_GRANTLEE`
|
||
- no push performed
|
||
|
||
## If blocked
|
||
|
||
Do not fake success. Report:
|
||
|
||
- failing command
|
||
- key error output
|
||
- affected file/branch
|
||
- category: project, path, merge, cherry-pick, CMake, Qt API, codegen, Docker,
|
||
RTI/license, Grantlee/KTextTemplate, KDReports, ArcGIS, test, CTest, Jenkins CI,
|
||
stub relocation, or environment
|
||
- which side (ours/theirs/cherry-pick) the problematic hunk came from
|
||
- what was resolved safely
|
||
- what remains blocked
|
||
- whether stale artifacts were ruled out
|
||
- whether generated files were involved
|
||
- exact missing files, targets, or generator step
|
||
- whether tests and CTest integration succeeded
|
||
- whether Docker validation and Jenkins discovery succeeded
|
||
- the legacy comparison status for the unresolved files
|
||
|
||
## Final report
|
||
|
||
Keep it short. Include:
|
||
|
||
- status: validated, partially validated, or blocked
|
||
- both commit hashes (cherry-pick, merge), the merge's two parents, the branch name
|
||
- tools containment re-verification result
|
||
- cherry-pick evidence: clean apply on the projects base, per-file content check
|
||
output (24/24 MATCH expected), the 14 non-relocated files documented
|
||
- per-conflicted-file resolution: file, method (union / four-version semantic / merge
|
||
recipe / keep-deletion), and the one-line reason
|
||
- `new_docker_build.sh` merge evidence: ours-side additions kept (Groups 6–11 usage/
|
||
arrays/calls/passthrough), theirs-side additions kept (viewer-only, codification,
|
||
build-parts, prebuilt image name, `--cmake_build_flags`, corrected usage line), the
|
||
three resolved hunks, and the post-resolution script checks
|
||
- legacy comparison audit summary: per-file hunk counts by category, and every
|
||
`semantic-change` hunk with its justification or fix
|
||
- files changed beyond the conflicted set (expected: none — the 24 stub deletions and
|
||
the auto-merged theirs-side files excepted)
|
||
- CTest registration union check result (both sides' registrations in
|
||
`tests/CMakeLists.txt`; `LtsDataViewTest` property/auto-exit)
|
||
- Docker and Jenkins CI changes (incl. the recorded pre-existing signature blocker)
|
||
- Qt5 references removed or remaining
|
||
- confirmation that removed modules were not restored, LogViewer was preserved (incl.
|
||
the GROUP6 target), and `docker_build.sh` stayed deleted
|
||
- GROUP11 classification (svcPdmClient blocker cleared by the theirs-side service work,
|
||
or still base-state)
|
||
- exact validation commands and results for all three runs
|
||
- remaining blockers or risks
|
||
|
||
## Summary
|
||
- Write Summary for all migrated and merge branche like this example (MIGRATION_SUMMARY_Z_AND_PROXIES.md)
|