Estou usando JPA (EclipseLink) e Spring. Digamos que eu tenha uma entidade simples com um ID gerado automaticamente:
@Entity
public class ABC implements Serializable {
@Id
@GeneratedValue(strategy=GenerationType.IDENTITY)
private int id;
// ...
}
Na minha classe DAO, tenho um método de inserção que chama persist()
essa entidade. Eu quero que o método retorne o ID gerado para a nova entidade, mas quando eu testo, ele retorna em 0
vez disso.
public class ABCDao {
@PersistenceContext
EntityManager em;
@Transactional(readOnly=false)
public int insertABC(ABC abc) {
em.persist(abc);
// I WANT TO RETURN THE AUTO-GENERATED ID OF abc
// HOW CAN I DO IT?
return abc.id; // ???
}
}
Também tenho uma classe de serviço que envolve o DAO, se isso fizer diferença:
public class ABCService {
@Resource(name="ABCDao")
ABCDao abcDao;
public int addNewABC(ABC abc) {
return abcDao.insertABC(abc);
}
}
Respostas:
O ID só tem garantia de ser gerado no momento do flush. Persistir uma entidade apenas a torna "anexada" ao contexto de persistência. Portanto, libere o gerenciador de entidade explicitamente:
ou retornar a própria entidade em vez de seu ID. Quando a transação terminar, a liberação acontecerá e os usuários da entidade fora da transação verão o ID gerado na entidade.
fonte
@GeneratedValue
- o que quer que isso acarreteinsertABC
cria um novo objeto? Ou modificar o antigo?verifique se a notação @GeneratedValue está presente em sua classe de entidade. Isso informa à JPA sobre o comportamento gerado automaticamente de sua propriedade de entidade
fonte
Foi assim que eu fiz:
fonte
Você também pode usar GenerationType.TABLE em vez de IDENTITY, que só está disponível após a inserção.
fonte
Outra opção compatível com 4.0:
Antes de confirmar as alterações, você pode recuperar o
CayenneDataObject
(s) novo (s) objeto (s) da coleção associada ao contexto, assim:em seguida, acesse o
ObjectId
para cada um na coleção, como:Finalmente você pode iterar sob os valores, onde normalmente o ID gerado será o primeiro dos valores (para uma única chave de coluna) no Mapa retornado por
getIdSnapshot()
, ele contém também o (s) nome (s) da coluna associada ao PK como chave (s):fonte
É assim que eu fiz. Podes tentar
fonte
fonte
em.flush()
não éem.refresh(abc)
.