| name | paw-tp2-migration |
| description | Use when planning, implementing, auditing, or reviewing PAW TPE2/TP2 migration from TP1 JDBC persistence to JPA/Hibernate while preserving product behavior, data, deployability, and prior feedback corrections. Use for entity mapping, Spring ORM config, EntityManager DAOs, transaction manager changes, schema/data migration risk, fetch/cascade reviews, generated SQL/performance audits, and persistence tests. |
Paw TP2 Migration
Overview
Use this when the user says the PAW project is in TPE2/TP2, asks for Hibernate/JPA/ORM work, or wants to migrate persistence away from TP1 JDBC. The goal is a controlled persistence migration that preserves existing product behavior and server data, not a broad rewrite of webapp or product surface.
Read references/migration-rules.md before editing or judging migration work.
Required First Pass
- Confirm the stage is
TPE2/TP2 or the user explicitly asked for Hibernate/JPA.
- Read the app
CLAUDE.md, PAW-Wiki/docs/CLAUDE.md, PAW-Wiki/docs/index.md, and PAW-Wiki/docs/wiki/resumen-clases-paw-2026.md.
- Read
PAW-Wiki/docs/wiki/resumen-enunciado-tpe2.md as the delivery contract, then read PAW-Wiki/docs/wiki/tp1-vs-tpe2-final.md, paw-unidad-09-hibernate-jpa.md, hibernate-jpa.md, persistencia-jdbc.md, transactional.md, criterios-evaluacion.md, calendario-entregas.md, and testing-unitario.md.
- If the migration depends on transaction/proxy behavior, also read
PAW-Wiki/docs/wiki/paw-unidad-08-aop-transacciones.md.
- Capture baseline code, schema, production/deploy assumptions, tests, and prior catedra feedback for the slice being migrated.
- State which product behavior and data must stay identical, which feedback items must be corrected, and which persistence mechanics are allowed to change.
First TP2 Session Checklist
When the user says TP1 is finished and they are starting TP2, do this before editing:
- Inventory current JDBC DAOs, DAO contracts, schema scripts, row mappers, service callers, and persistence tests.
- Inventory TPE1 feedback/corrections and mark which items are blockers for TP2 readiness.
- Identify the smallest safe first aggregate to migrate.
- Decide whether JDBC and JPA implementations will coexist temporarily, and how Spring bean selection will be explicit.
- Plan entity mappings against the existing schema and existing data before adding Hibernate config.
- Define verification gates for the slice: focused persistence test, affected service tests, package/deploy-sensitive gate if wiring changed, then wider Maven gate.
Migration Workflow
- Audit existing JDBC DAO contracts, SQL, schema, row mappings, service callers, deployed data assumptions, and tests.
- Decide whether contracts stay stable or need explicit service-facing changes. Prefer stable contracts unless the user approved a product change.
- Map entities deliberately: ids/sequences, table/column names, nullability, enum storage, legacy rows, constraints, and relationships.
- Configure Spring ORM and
JpaTransactionManager only after the entity/DAO slice is defined.
- Implement one DAO or aggregate at a time with
EntityManager.
- Review generated SQL, fetch behavior, cascades, orphan removal, and lazy loading boundaries.
- Define additive data/schema migrations before enabling runtime schema behavior; avoid destructive auto-generation.
- Update tests to prove persisted state, service behavior, and no regression of corrected feedback, not just compilation.
- Run the smallest Maven gate first, then widen when contracts, wiring, packaging, or deploy behavior changed.
JPA Pagination Rule
For paginated TP2/JPA searches that load entities and relationships, do not trust a
single entity query with SQL LIMIT/JPA pagination over joined rows. The PAW
notes warn that the limit applies to SQL rows, which may not match the number of
root entities when one entity expands into several relationship rows.
Use the catedra pattern from PAW-Wiki/docs/raw/pdfs/PAW - Apuntes.pdf, page
81:
- Run a native or id-only query with the exact filters and ordering to obtain
only the root entity ids for the requested page.
- Apply
setFirstResult((page - 1) * pageSize) and
setMaxResults(pageSize) to that id query.
- Run a JPA entity query to load the entities for those ids and fetch/populate
the relationships needed by the caller.
- Preserve the id-query order explicitly after the JPA
IN (:ids) load, because
IN does not guarantee result order.
- Compute total counts with a separate count query over root entities using the
same filters, not by counting fetched relationship rows.
This two-step id-page-then-entity-load pattern is the default for PAW TP2 list
pages with relationship-heavy entities. The same idea can also be used in JDBC.
Coordination
- Use
$paw-models-layer for entity/model annotations and enum/nullability choices.
- Use
$paw-persistence-contracts-layer when DAO interfaces change.
- Use
$paw-persistence-layer for JPA DAO implementation, Spring ORM config, schema, and persistence tests.
- Use
$paw-services-layer when transaction boundaries or managed entity behavior affects service logic.
- Use
$paw-testing-layer for JPA persistence tests, generated SQL checks, and verification gates.
Stop Conditions
Ask before proceeding when:
- The user has not confirmed TP2 and the task would introduce JPA/Hibernate.
- Schema generation or migration can rewrite/drop production/server data.
- A lazy-loading strategy would require OpenEntityManagerInView or longer-lived sessions.
- A contract change would force broad webapp or product behavior changes.
- Dependency versions are unclear; do not copy old PDF versions as current guidance.
- The requested shortcut would skip required TPE1 feedback corrections, demo readiness, or deploy verification.
Verification
Use repo-specific commands where available:
mvn -pl models test
mvn -pl persistence-contracts -am test
mvn -pl persistence -am test
mvn -pl services -am test
mvn -pl webapp -am test
mvn clean test
mvn clean package
For a narrow DAO test:
mvn -pl persistence -am -Dtest=<PersistenceTestName> test
For TP2 closeout, also verify the deliverable shape when wiring or packaging changed:
mvn clean package
jar tf webapp/target/webapp.war | head