This is an automated email from the ASF dual-hosted git repository.
asf-gitbox-commits pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/cayenne.git
The following commit(s) were added to refs/heads/master by this push:
new 244fdb7d8 ai-plugin - clarifying cgen flow
244fdb7d8 is described below
commit 244fdb7d8c36c29a3e528ad708c57da6b3fbfa45
Author: Andrus Adamchik <[email protected]>
AuthorDate: Sun May 24 18:04:02 2026 -0400
ai-plugin - clarifying cgen flow
---
ai-plugin/references/cgen-config.md | 42 ++++++++++++++++++++++++++++++----
ai-plugin/skills/cayenne-cgen/SKILL.md | 33 ++++++++------------------
2 files changed, 47 insertions(+), 28 deletions(-)
diff --git a/ai-plugin/references/cgen-config.md
b/ai-plugin/references/cgen-config.md
index cd8c22b8d..08ab76be0 100644
--- a/ai-plugin/references/cgen-config.md
+++ b/ai-plugin/references/cgen-config.md
@@ -49,7 +49,7 @@ Note the **different namespace** for `<cgen>`
(`http://cayenne.apache.org/schema
| Field | Default | Meaning |
|---|---|---|
-| `<destDir>` | — | Output directory, **relative to the project XML
directory** (the directory containing `cayenne-*.xml`). Typical values: `.`,
`../java`, `../../main/java`. Absolute paths also work. |
+| `<destDir>` | — | Output directory, **relative to the directory containing
`*.map.xml`**. Typical values: `.`, `../java`, `../../main/java`. |
| `<mode>` | `entity` | What to generate. `entity` = per-entity classes. `all`
= per-entity classes + a single DataMap class with named-query helpers. |
### Pairs vs single class
@@ -107,13 +107,45 @@ The MCP tool:
1. Loads the project at `projectPath`.
2. Finds the named DataMap (`dataMap` argument).
3. Reads its embedded `<cgen>` block.
-4. Resolves `destDir` relative to the project file.
+4. Resolves `destDir` relative to the `*.map.xml` file.
5. Runs the generator. Returns a JSON object listing files `written`, files
`skipped` (already up-to-date), and any `errors`.
If the DataMap has no `<cgen>` block, the tool returns an error and the user
must add one — typically via the `cayenne-modeling` skill or the Modeler GUI.
-## Recommended starting config
+## Determining `destDir`
+
+`destDir` is relative to the directory that contains `*.map.xml`.
+
+**Before writing the default config, inspect the project tree** to find the
Java source root and express it as a relative path from the map file's
directory. Do not blindly paste `../java`.
+
+### Standard Maven layout
+
+Map files are frequently placed in a package subdirectory under `resources/`
rather than directly in `resources/` itself. Count the directory levels between
`resources/` and the map file and add that many extra `../` segments.
+
+| Map file location | `destDir` |
+|---|---|
+| `src/main/resources/mydb.map.xml` | `../java` |
+| `src/main/resources/com/mydb.map.xml` | `../../java` |
+| `src/main/resources/com/example/mydb.map.xml` | `../../../java` |
+| `src/main/resources/com/example/app/mydb.map.xml` | `../../../../java` |
+| `src/test/resources/mydb.map.xml` | `../java` |
+| `src/test/resources/com/example/app/mydb.map.xml` | `../../../../java` |
+
+The rule: one `../` to escape `resources/`, then one `../` per package
segment, then `java`. Always verify by resolving the resulting path mentally
before writing it.
+### Non-standard layouts
+
+If the project doesn't follow Maven conventions, locate the actual Java
sources:
+
+1. Look for existing `.java` files or a `src/` directory near the map file.
+2. Compute the relative path from the map file's directory to that sources
root.
+3. If no Java sources exist yet, ask the user where generated classes should
go.
+
+### Distinguishing main vs test maps
+
+If the map file lives under a test resource directory (`src/test/resources/`,
`test/`, or a path containing `test`), the generated classes belong in the test
source tree. Point `destDir` there rather than at the main sources — test
entity classes mixed into `src/main/java/` are a common mistake.
+
+## Recommended starting config
```xml
<cgen xmlns="http://cayenne.apache.org/schema/12/cgen">
@@ -125,10 +157,12 @@ If the DataMap has no `<cgen>` block, the tool returns an
error and the user mus
</cgen>
```
-Assuming the project XML lives at `src/main/resources/cayenne-mydb.xml`, this
writes to `src/main/java/<package>/`.
+The `../java` value above assumes a standard Maven layout
(`src/main/resources/` or `src/test/resources/`). Adjust if the project uses a
non-standard layout — see "Determining `destDir`" above.
## Anti-patterns
- Setting `<makePairs>false</makePairs>` to "simplify" — you lose the ability
to add user code without it being overwritten on the next cgen run.
- Editing `_<Entity>.java` files (the superclasses). They are regenerated.
Customize `<Entity>.java` (the subclass) instead.
- `<destDir>` as an absolute path checked into source — breaks reproducibility
for other developers. Use a relative path.
+- Pasting `../java` blindly without checking the actual project layout.
Inspect the tree first; see "Determining `destDir`" above.
+- Pointing a test DataMap's `destDir` at `src/main/java/` — test entity
classes belong in the test source tree.
diff --git a/ai-plugin/skills/cayenne-cgen/SKILL.md
b/ai-plugin/skills/cayenne-cgen/SKILL.md
index 8c9ee054b..5a7ed1912 100644
--- a/ai-plugin/skills/cayenne-cgen/SKILL.md
+++ b/ai-plugin/skills/cayenne-cgen/SKILL.md
@@ -23,7 +23,7 @@ description: "Use this skill whenever the user wants to
(re)generate Cayenne ent
-->
# cayenne-cgen
-Run Cayenne's class generator on a DataMap via the `mcp__cayenne__cgen_run`
MCP tool. Reads the embedded `<cgen>` block in the DataMap to determine
destination, mode, templates, etc.
+Run Cayenne's class generator on a DataMap via the `mcp__cayenne__cgen_run`
MCP tool. The tool reads the embedded `<cgen>` block in the DataMap to
determine destination, mode, templates, etc.; if no block is present the tool
reports an error and the skill adds a default one then retries.
## Required reading
@@ -42,26 +42,7 @@ Locate the descriptor via `project-layout.md`. If multiple
descriptors exist, as
If the user named the DataMap directly (e.g. "regenerate classes for the
customers DataMap"), use that. If they said "regenerate everything" and there
are multiple DataMaps, run `cgen_run` once per DataMap in sequence (the tool
generates per-DataMap).
-## Step 2 — Verify `<cgen>` block exists
-
-Before calling the tool, check the target DataMap for a `<cgen
xmlns="http://cayenne.apache.org/schema/12/cgen">` block. If missing:
-
-1. Don't call `cgen_run` blindly — it will return an error.
-2. Either:
- - **Add a minimal block** by delegating to the `cayenne-modeling` skill.
Use the starter config from `cgen-config.md`:
- ```xml
- <cgen xmlns="http://cayenne.apache.org/schema/12/cgen">
- <destDir>../java</destDir>
- <mode>entity</mode>
- <makePairs>true</makePairs>
- <usePkgPath>true</usePkgPath>
- <createPKProperties>true</createPKProperties>
- </cgen>
- ```
- Confirm `destDir` with the user — it's relative to the project XML
directory and decides where generated `.java` files land.
- - Or, if the user prefers the GUI, suggest the `cayenne-modeler` skill and
tell them to configure the DataMap's "Class Generation" tab.
-
-## Step 3 — Call `cgen_run`
+## Step 2 — Call `cgen_run`
```
mcp__cayenne__cgen_run({
@@ -72,7 +53,11 @@ mcp__cayenne__cgen_run({
If the tool is not available (MCP server not registered), surface
`cayenne-mcp-server/README.md` and stop. **Do not** suggest `mvn cayenne:cgen`
or the Gradle cgen task.
-## Step 4 — Surface the result
+If the tool errors because no `<cgen>` block is present in the DataMap, add a
minimal one using the starting config approach from `cgen-config.md`
+
+If the `destDir` can't be determined reliably (non-standard project layout,
empty project, etc.), conform it with the user
+
+## Step 3 — Surface the result
The tool returns structured JSON. Report:
@@ -82,14 +67,14 @@ The tool returns structured JSON. Report:
If `writtenCount` is 0 and `skippedCount` covers everything, say so — it means
everything is already up-to-date and no work was needed.
-## Step 5 — Next steps
+## Step 4 — Next steps
- If new `_<Entity>.java` superclass files were generated, gently remind the
user not to edit those — they will be overwritten next run. User code goes in
the matching `<Entity>.java` subclass.
- If the user just ran reverse engineering, this skill is the natural
follow-up. Cross-link back to `cayenne-modeling` if they need to tweak
names/types before regenerating.
## Anti-patterns
-- **Do not** call `cgen_run` without verifying the `<cgen>` block exists — the
tool returns an error and confuses the user.
+- **Do not** pre-check the DataMap for a `<cgen>` block before calling
`cgen_run`. Call the tool first; add the default config only if the tool
reports it is missing.
- **Do not** suggest Maven (`mvn cayenne:cgen`) or Gradle (`cayenneCgen`)
goals when MCP is unavailable. Those build plugins are out of scope. Point at
MCP setup instead.
- **Do not** edit `_<Entity>.java` files. Generated superclasses. Edit
`<Entity>.java` subclasses.
- **Do not** confuse `projectPath` and `dataMap` arguments. `projectPath` is a
file system path to `cayenne-*.xml`. `dataMap` is a logical name (e.g. `mydb`),
not a path to `mydb.map.xml`.