10
votes

Utilisation du titulaire de la clé de ressort avec des clés primaires générées par programmation

J'utilise NamedParameTejdbctOmbreTemplat pour effectuer une insertion dans une table. Le tableau utilise un prochain sur une séquence pour obtenir la clé primaire. Je veux ensuite que cet ID généré soit transmis à moi. J'utilise la mise en œuvre de la clé de la clé de printemps comme ceci: xxx

Cependant, lorsque j'exécute cette déclaration, je reçois: xxx

Toutes idées Il me manque?


0 commentaires

5 Réponses :


3
votes

Vous devez exécuter le jdbctemplate.Update (PreponStatementCreator P, Keyholder K) Code>.

La touche renvoyée de la base de données sera injectée dans le Objet du titulaire de la clé CODE> . P>

Exemple: P>

final String INSERT_ORDER_STATEMENT 
       = "insert into order (product_id, quantity) values(?, ?)";

KeyHolder keyHolder = new GeneratedKeyHolder();
    jdbcTemplate.update(new PreparedStatementCreator() {
        public PreparedStatement createPreparedStatement(
            Connection connection) throws SQLException {
                PreparedStatement ps = connection.prepareStatement(
                    INSERT_ORDER_STATEMENT, new String[] { "id" });
                ps.setInt(1, order.getProductId());
                ps.setInt(2, order.getQuantity());
                return ps;
            }
        }, keyHolder);


1 commentaires

Ceci est en train de retourner Rowid en titulaire et pas un nombre!



-4
votes

Je pense que vous utilisez la mauvaise méthode sur jdbctemplate . La seule des méthodes Mettre à jour qui semblerait correspondre à votre fragment de code est xxx

si oui, vous passez params et clé en tant que tableau VARGS de deux éléments et jdbctemplate traite la touche sous forme de paramètres de liaison normale et à l'interpréter mal.

Le seul public Methode de mise à jour sur jdbctemplate qui prend un porte-clés est xxx p> Vous devrez donc reformuler votre code pour l'utiliser.


1 commentaires

trompeur, vérifiez ci-dessous la réponse de Konstantin



22
votes

Il suffit de résoudre un problème similaire - avec Oracle, vous devez utiliser une autre méthode (à partir de NamedParameterjdbcoperations ) - xxx

avec des noms de keycolumns contenant des colonnes générées automatiquement, dans mon cas juste ["id"]. Sinon, tout ce que vous obtenez est Rowid. Voir Doc de printemps pour plus de détails.


1 commentaires

Merci à cette réponse la question meilleure que les réponses précédentes et résolvez mon problème



3
votes

Pas d'élaboration sur @konstantin Réponse: Voici un exemple de travail total: En supposant que la base de données est l'oracle et le nom de la colonne qui stocke généré ID est "généré" (peut être n'importe quel nom). Remarque: j'ai utilisé NamedParameterJDbctemPlappe.UPDate (....) Dans cet exemple, NOT PLUS JDBCTTELLALE CLASSE DE STREST.

       public Integer insertRecordReturnGeneratedId(final MyObject obj)
            {
            final String INSERT_QUERY = "INSERT INTO MY_TABLE  VALUES(GENERATED_ID_SEQ.NEXTVAL, :param1, :param2)";
            try
                {
                    MapSqlParameterSource parameters = new MapSqlParameterSource().addValue( "param1", obj.getField1() ).addValue( "param2",  obj.getField1() ) ;
                    final KeyHolder holder = new GeneratedKeyHolder();
                    this.namedParameterJdbcTemplate.update( INSERT_QUERY, parameters, holder, new String[] {"GENERATED_ID" } );
                    Number generatedId = holder.getKey();
                   // Note: USING holder.getKey("GENERATED_ID") IS ok TOO.
                    return generatedId.intValue();
                }
                catch( DataAccessException dataAccessException )
                {
        }
        }


0 commentaires

0
votes

avec MySQL

CREATE TABLE `vets` (
  `id` int(4) unsigned NOT NULL AUTO_INCREMENT,
  `first_name` varchar(30) DEFAULT NULL,
  `last_name` varchar(30) DEFAULT NULL,
  PRIMARY KEY (`id`),
  KEY `last_name` (`last_name`)
) ENGINE=InnoDB AUTO_INCREMENT=11 DEFAULT CHARSET=utf8;


public @Data class Vet {
    private int id;
    private String firstname;
    private String lastname;
}

@Repository
public class VetDaoImpl implements VetDao {
/** Logger. */
private static final Logger LOGGER = LoggerFactory.getLogger(VetDaoImpl.class);

private static final String INSERT_VET = "INSERT INTO vets (first_name, last_name) VALUES (:first_name, :last_name)";

@Autowired
private NamedParameterJdbcTemplate namedParameterJdbcTemplate;

@Override
public Number insertVet(final Vet vet) {
    MapSqlParameterSource paramSource = new MapSqlParameterSource();
    paramSource.addValue("first_name", vet.getFirstname());
    paramSource.addValue("last_name", vet.getLastname());
    KeyHolder keyHolder = new GeneratedKeyHolder();
    int nbRecord = namedParameterJdbcTemplate.update(INSERT_VET, paramSource, keyHolder, new String[] {"id" });
    LOGGER.info("insertVet: id ["+keyHolder.getKey()+"]");
    return nbRecord;
}
}


0 commentaires