Créer un adaptateur de persistance JPA

VérifiéSûr

Génère ou met à jour les fichiers d'adaptateur de persistance JPA (entité, repository, mapper, adaptateur) pour un agrégat du domaine.

Spar Skills Guide Bot
DeveloppementIntermédiaire
03/08/2026
Claude Code
#kotlin#spring-data-jpa#hexagonal-architecture#persistence#code-scaffolding

Recommandé pour

Synthèse automatique

Génère ou met à jour les quatre fichiers Kotlin/JPA (entité, dépôt Spring Data, mapper et adaptateur) nécessaires pour implémenter un port de dépôt sortant d'un agrégat métier.

Points forts

  • Produit les quatre fichiers en une seule passe et ne complète que les méthodes ou champs manquants dans les fichiers existants.
  • Applique des conventions cohérentes : mapper en objet singleton, colonnes en snake_case, énumérations stockées en chaîne, JpaRepository<Entité, UUID>.
  • Accepte un fichier de port précis ou recherche et propose les ports sortants disponibles.
  • Impose l'implémentation de toutes les méthodes du port et distingue le comportement de find (exception) et de search (null).

Limites

  • Le SKILL.md s'arrête au début de l'étape 2 (détermination du package), donc la procédure de résolution du package et du source root est incomplète ; les motifs complets renvoient à une référence externe.
  • Suppose une stack Kotlin, Spring Data JPA et une architecture hexagonale ; inutilisable pour d'autres technologies.
  • Ne décrit ni tests, ni validation, ni migrations de schéma ou génération de base de données.
Quand l'utiliser

À utiliser pour ajouter ou mettre à jour la couche de persistance d'un agrégat métier disposant déjà d'un port de dépôt sortant dans un projet Kotlin/Spring en architecture hexagonale.

Quand l'éviter

À ne pas utiliser pour un stockage non JPA, un projet non Kotlin, ou lorsqu'aucun port sortant ni agrégat métier n'existe encore.

Analyse de sécurité

Sûr
Score qualité88/100

The skill only uses Read, Write, and Glob to inspect and generate Kotlin/Spring persistence-layer files within the repository. It contains no destructive commands, network access, credential handling, obfuscated payloads, or attempts to alter agent safety behavior. File-writing is legitimate and bounded to the described adapter package.

Aucun point d'attention détecté

Comment cette analyse est faite

Exemples

Scaffold from a port file
Create a persistence adapter for services/example-service/src/main/kotlin/com/example/newsletter/application/port/outbound/NewsletterSubscriptionRepository.kt
Discover outbound ports
Scaffold the persistence layer for one of my outbound repository ports — list the candidates first so I can choose.
Update an existing adapter
Update the existing JPA persistence adapter for the Order aggregate and add any missing port methods and entity fields.

name: create-persistence-adapter argument-hint: "[<path-to-Repository-port-file-or-domain-entity>]" allowed-tools: Read, Write, Glob description: Scaffold or update a complete JPA persistence adapter (outbound adapter) — entity, JPA repository, mapper, and adapter class — for a domain aggregate. Use when the user asks to "create a persistence adapter", "generate a JPA adapter", "scaffold the persistence layer", or "create an outbound db adapter". Accepts a repository port file or domain entity; generates all four files at once; updates existing files by adding missing methods or fields.

Skill: create-persistence-adapter

Generates or updates up to four files per aggregate in adapter/outbound/db/:

  • *Entity.kt — JPA entity mapping the aggregate to a database table
  • *JpaRepository.kt — Spring Data JpaRepository interface
  • *EntityMapper.kt — singleton object for entity ↔ domain conversion
  • *PersistenceAdapter.kt — @Component implementing the outbound repository port

If any files already exist, the skill reads them, compares against the port interface and domain entity, and applies only what is missing or outdated.

Full code patterns: see references/full-pattern.md

Pattern

Trigger: "Create a persistence adapter for newsletter subscription"
Input:   services/example-service/src/main/kotlin/.../port/outbound/NewsletterSubscriptionRepository.kt
Output — four files under adapter/outbound/db/:
  NewsletterSubscriptionEntity.kt          – @Entity data class
  NewsletterSubscriptionJpaRepository.kt   – JpaRepository interface
  NewsletterSubscriptionEntityMapper.kt    – object with toDomain / toEntity
  NewsletterSubscriptionPersistenceAdapter.kt – @Component implementing the port

What is a Persistence Adapter?

A persistence adapter is an outbound adapter. It acts as the interaction layer between your application and the database. Your code calls it via a port interface. It handles the translation between domain objects and the underlying storage mechanism (JPA/Spring Data).

IMPORTANT

  • Implement every method defined in the outbound repository port interface
  • find throws NoSuchElementException when the entity is not found; search returns null
  • All entity ↔ domain mapping goes through the singleton mapper object — never inline conversion.
  • The mapper is a Kotlin object (singleton), not a class or a companion object
  • Column names use snake_case; the @Entity(name = ...) value matches the database table name
  • Enum fields use @Enumerated(EnumType.STRING) — never store the ordinal
  • The JPA repository extends JpaRepository<EntityClass, UUID>
  • It adds adds one findBy<IdField> method returning a nullable entity for kotlin-friendly find

Instructions

Step 1 – Resolve the input source

Two possible inputs:

Option A – Repository port file path provided (a .kt file under port/outbound/):

  1. Read the file. Extract: interface name, all method signatures (names, parameter types, return types).
  2. Derive the aggregate name by stripping the Repository suffix (e.g. NewsletterSubscriptionRepository → NewsletterSubscription).
  3. Find the domain aggregate: Glob **/domain/<AggregateName>.kt. Read it to discover all fields.
  4. If you can't find the matching aggregate or port pause the execution
  5. Then ask the developer to provide correct information

Option B – No argument provided:

  • Search: Glob **/application/port/outbound/**/*.kt.
  • Filter the files to include only ones that could match as a port for a repository.
  • If no files are found, inform the developer that no outbound port files were discovered, ask them to provide the port file path directly, then proceed as Option A. -
  • If files were found list those files and ask the user which one to scaffold.
  • Proceed as Option A once the user selects a file.

Step 2 – Determine the target package and source root

Derive the base package from the repository port package (e.g. io.miragon.example.application.port.outbound → base: io.miragon.example).

Adapter package: <base>.adapter.outbound.db.

Determine the source root from the port file path (e.g. services/example-service/src/main/kotlin/).

Target directory: <source-root>/<base-package-path>/adapter/outbound/db/

Step 3 – Check existing files and determine should-state for each

Derive the four class names from the aggregate name (e.g. NewsletterSubscription):

  • Entity: NewsletterSubscriptionEntity
  • JPA Repository: NewsletterSubscriptionJpaRepository
  • Mapper: NewsletterSubscriptionEntityMapper
  • Adapter: NewsletterSubscriptionPersistenceAdapter

Check which of these files already exist at the target directory. For each file, determine its should-state as follows:

3.1 Entity (<AggregateName>Entity.kt)

Read the domain aggregate class. For each field:

  • Map domain value objects to their primitive type (e.g. Email(val value: String) → String, SubscriptionId(val value: UUID) → UUID)
  • Derive the column name as snake_case of the field name (e.g. registrationDate → registration_date, newsletterId → newsletter_id)
  • Mark enum fields with @Enumerated(EnumType.STRING)
  • Mark the ID field with @Id and @Column(name = "<id-column>", nullable = false)

Derive the table name as snake_case of the aggregate class name (e.g. NewsletterSubscription → newsletter_subscription).

Should-state: data class with @Entity(name = "table_name"), one column per aggregate field, correct annotations.

If file exists: compare fields against the domain aggregate. Add missing fields, correct outdated column names or annotations. Preserve any custom annotations already present.

If file does not exist: generate from the should-state above.

3.2 JPA Repository (<AggregateName>JpaRepository.kt)

Should-state: interface extending JpaRepository<EntityClass, UUID> with exactly one findBy<IdField>(id: UUID): EntityClass? query method.

If the file exists: check if any query methods are missing based on the port interface. Add them.

If file does not exist: generate from the should-state above.

3.3 Mapper (<AggregateName>EntityMapper.kt)

Should-state: object with two functions:

  • toDomain(entity: EntityClass): DomainClass — wraps each primitive in its domain value object
  • toEntity(domain: DomainClass): EntityClass — extracts .value from each domain value object

If a file exists: check for missing field mappings and add them.

If file does not exist: generate from the should-state above.

3.4 Adapter (<AggregateName>PersistenceAdapter.kt)

Should-state: @Component class implementing the repository port, constructor-injected JPA repository, all port methods delegating through the mapper:

  • find → throws NoSuchElementException when not found
  • search → returns null when not found
  • save → delegates to repository.save(...)
  • delete → delegates to repository.deleteById(id.value)

If file exists: compare against all port methods. Add any missing ones, preserving existing business logic.

If file does not exist: generate from the should-state above.

Step 4 – Write all files

Apply all creations and updates identified in Step 3. Use references/full-pattern.md as a concrete reference.

Step 5 – Report

List each file created, updated, or skipped (if nothing changed) and remind the developer to:

  1. Add a database migration (Flyway/Liquibase) if a new table is introduced
  2. Run /test-persistence-adapter to generate unit tests for the adapter
  3. Wire the adapter into the application service via the port interface (automatic via Spring if the package is within the base component-scan path)

Du fichier au premier essai

Le téléchargement contient exactement le contenu affiché sur cette fiche. Cette copie peut différer de la dernière version du dépôt source.

Consulter la source et ses fichiers annexes

Ce téléchargement contient uniquement SKILL.md. Les scripts, références, modèles et dépendances éventuels ne sont pas inclus. Récupérez les fichiers nécessaires depuis la source en conservant leur arborescence avant de poursuivre.

1. Télécharger le fichier

Télécharger SKILL.md

Depuis la racine d’un projet de test, enregistrez le fichier sous .skill-downloads/create-jpa-persistence-adapter-mscrezqb/SKILL.md, ou utilisez la commande suivante. Ce dossier sert à examiner la skill avant son installation.

Commande pour macOS/Linux ou WSL : un shell POSIX et curl sont nécessaires. Sous Windows sans WSL, utilisez le bouton de téléchargement et créez le dossier manuellement.

mkdir -p '.skill-downloads/create-jpa-persistence-adapter-mscrezqb' && curl --fail --show-error --location 'https://skills-guides.com/api/skills/create-jpa-persistence-adapter-mscrezqb/download' --output '.skill-downloads/create-jpa-persistence-adapter-mscrezqb/SKILL.md.part' && mv '.skill-downloads/create-jpa-persistence-adapter-mscrezqb/SKILL.md.part' '.skill-downloads/create-jpa-persistence-adapter-mscrezqb/SKILL.md'

2. Vérifier les prérequis

Lisez SKILL.md avant de l’utiliser. Si le fichier cite des scripts ou services externes, examinez-les et préparez les accès nécessaires dans votre environnement de test.

Outils déclarés par l’auteur (à vérifier dans votre agent) : Read, Write, Glob

Aucune section de prérequis reconnue dans ce fichier. Cela ne signifie pas qu’il est autonome : les bibliothèques, outils et accès peuvent être cités ailleurs dans le contenu ou dans le dépôt source.

Les plateformes de la fiche sont des indications du catalogue. Les chemins ci-dessous suivent la documentation des outils ; ils ne prouvent pas que cette skill y a été exécutée. Aucune version minimale de ces outils n’est attestée pour cette fiche.

3. Charger la skill

Après vérification, copiez le dossier complet dans le projet avec l’une des commandes ci-dessous, puis ouvrez une nouvelle session de l’outil. La commande s’arrête si un dossier du même nom existe déjà : comparez les fichiers avant de le remplacer.

Claude Code
test -f '.skill-downloads/create-jpa-persistence-adapter-mscrezqb/SKILL.md' && test -s '.skill-downloads/create-jpa-persistence-adapter-mscrezqb/SKILL.md' && mkdir -p '.claude/skills' && test ! -e '.claude/skills/create-persistence-adapter' && cp -R '.skill-downloads/create-jpa-persistence-adapter-mscrezqb' '.claude/skills/create-persistence-adapter'

OpenSkills

OpenSkills doit déjà être installé. La procédure locale install/read est contrôlée avec OpenSkills 1.5.0, qui exige Node.js ≥ 20.6.0. Aucun slug du catalogue n’est résolu automatiquement.

Installation officielle d’OpenSkills
openskills install './.skill-downloads/create-jpa-persistence-adapter-mscrezqb'

openskills read 'create-jpa-persistence-adapter-mscrezqb'

La lecture doit afficher le contenu du fichier installé et son dossier de base. Elle ne lance ni la skill ni ses dépendances.

Pour un agent qui lit AGENTS.md, synchronisez ensuite l’index. Cette commande modifie AGENTS.md : relisez le diff avant de l’utiliser.

openskills sync

Mode manuel ou autre outil : joignez SKILL.md à une conversation, ou ouvrez-le dans un agent capable de lire les fichiers. Ajoutez les ressources annexes nécessaires. Il n’existe pas de dossier universel reconnu par tous les outils.

4. Faire un premier essai

Utilisez une entrée courte et fictive : un endpoint d’API, un petit document ou un brief d’interface. Dans une nouvelle conversation, joignez le fichier ou donnez son chemin à l’agent, puis adaptez cette demande :

Lis .skill-downloads/create-jpa-persistence-adapter-mscrezqb/SKILL.md et applique ses instructions à cet exemple : [décrire une entrée de test]. Indique les fichiers, dépendances ou accès qui manquent. Produis le résultat demandé par la skill sans inventer de données ni exécuter de script non examiné.

Résultat attendu : une sortie correspondant aux instructions de la skill, ou une liste précise des prérequis manquants. Une simple confirmation de lecture ne valide pas le premier usage. Si une ressource externe est indisponible, ce parcours reste à tester.

Skills similaires