org.hibernate.MappingException: Typ konnte nicht bestimmt werden für: java.util.Set [duplicate]

Lesezeit: 9 Minuten

Obwohl diese Frage oft gestellt wurde und ich bereits alle Vorschläge verwendet habe, erhalte ich immer noch diesen Fehler.

Die User.java ist

@Entity
@Table(name = "USER")
public class User implements UserDetails, Serializable {

    private static final long serialVersionUID = 2L;

    @Id
    @Column(name = "USER_ID")
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private long id;
    @Column(name = "USERNAME")
    private String username;
    @Column(name = "PASSWORD")
    private String password;
    @Column(name = "NAME")
    private String name;
    @Column(name = "EMAIL")
    private String email;
    @Column(name = "LOCKED")
    private boolean locked;
    @OneToMany(cascade=CascadeType.ALL, fetch = FetchType.EAGER)
    @ElementCollection(targetClass=Role.class)
    @Column(name = "ROLE_ID")
    private Set<Role> roles;

    @Override
    public GrantedAuthority[] getAuthorities() {
        List<GrantedAuthorityImpl> list = new ArrayList<GrantedAuthorityImpl>(0);
        for (Role role : roles) {
            list.add(new GrantedAuthorityImpl(role.getRole()));
        }
        return (GrantedAuthority[]) list.toArray(new GrantedAuthority[list.size()]);
    }

    @Override
    public boolean isAccountNonExpired() {
        return true;
    }

    @Override
    public boolean isAccountNonLocked() {
        return !isLocked();
    }

    @Override
    public boolean isCredentialsNonExpired() {
        return true;
    }

    @Override
    public boolean isEnabled() {
        return true;
    }

    public long getId() {
        return id;
    }

    public void setId(long id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }

    public boolean isLocked() {
        return locked;
    }

    public void setLocked(boolean locked) {
        this.locked = locked;
    }

    @Override
    public String getUsername() {
        return username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    @Override
    public String getPassword() {
        return password;
    }

    public void setPassword(String password) {
        this.password = password;
    }

    public void setRoles(Set<Role> roles) {
        this.roles = roles;
    }

    public Set<Role> getRoles() {
        return roles;
    }
}

Und die Role.java ist

@Entity
@Table(name="ROLE")
public class Role implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name="ROLE_ID")
    private long id;
    @Column(name="USERNAME")
    private String username;
    @Column(name="ROLE")
    private String role;


    public long getId() {
        return id;
    }

    public void setId(long id) {
        this.id = id;
    }

    public String getUsername() {
        return username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    public String getRole() {
        return role;
    }

    public void setRole(String role) {
        this.role = role;
    }
}

Dies ist mein erster Versuch, mit JPA eine Hibernate-Annotation durchzuführen. Daher sind alle Vorschläge sehr hilfreich.

Für den Ruhezustand sind die Abhängigkeiten der pom.xml:

    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate</artifactId>
        <version>3.5.4-Final</version>
        <type>pom</type>
        <scope>compile</scope>
    </dependency>
    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate-annotations</artifactId>
        <version>3.5.4-Final</version>
        <type>jar</type>
        <scope>compile</scope>
    </dependency>

    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate-core</artifactId>
        <version>3.5.4-Final</version>
        <type>jar</type>
        <scope>compile</scope>
    </dependency>
    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate-validator</artifactId>
        <version>3.1.0.GA</version>
        <type>jar</type>
        <scope>compile</scope>
    </dependency>
    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate-entitymanager</artifactId>
        <version>3.5.4-Final</version>
        <type>jar</type>
        <scope>compile</scope>
    </dependency>

Ich habe keine Ahnung von dem Fehler.

Vielen Dank.

  • Sie dürfen in diesem Fall nur @ManyToOne mit @JoinColumn verwenden, da Role eine Entität ist. Sie verwenden @ElementCollection und @Column nur, wenn die Sammlung grundlegende Typen (Integer, String, Date usw.) oder einbettbare Typen enthält. Sehen Sie sich Beispiele in der JPA 2.0-Spezifikation an, wenn Sie möchten. Sie kombinieren Anmerkungen, die nie zusammen verwendet werden, und dies könnte die Ursache des Problems sein.

    – Edwin Dalorzo

    29. Mai 2011 um 13:37 Uhr


Benutzer-Avatar
Avadhuta

Ich habe das gleiche Problem mit @ManyToOne Säule. Es wurde gelöst … auf dumme Weise. Ich hatte alle anderen Anmerkungen für öffentliche Getter-Methoden, weil sie von der übergeordneten Klasse überschrieben wurden. Aber das letzte Feld wurde wie in allen anderen Klassen in meinem Projekt für private Variable kommentiert. Also ich habe das gleiche bekommen MappingException ohne Grund.

Lösung: Ich habe alle Anmerkungen bei öffentlichen Getter-Methoden platziert. Ich nehme an, Hibernate kann keine Fälle behandeln, in denen Annotationen für private Felder und öffentliche Getter in einer Klasse gemischt sind.

  • Auch meiden lombok für diese Klassen, weil es ändert, wohin die Anmerkungen gehen müssen.

    – nanotek

    1. März um 17:12

Benutzer-Avatar
Biggy_java2

Hinzufügen der @ElementCollection zum Listenfeld löste dieses Problem:

@Column
@ElementCollection(targetClass=Integer.class)
private List<Integer> countries;

  • Was? Das bezieht sich nicht auf die Frage.

    – dwjohnston

    25. Juli 2016 um 1:05 Uhr

  • Habe es für mich gelöst, ohne targetClass anzugeben 🙂

    – hughjdavey

    18. Januar 2018 um 13:28 Uhr

  • (targetClass=Integer.class) wird in diesem Fall nicht benötigt. Dies ist nur erforderlich, wenn Ihre Liste generischer Art ist

    – ACV

    15. September 2019 um 21:40 Uhr

  • Sie müssen nicht angeben @Column standardmäßig ist es @Column auf jedem Datenelement

    – Zahid Khan

    10. Februar 2021 um 4:35 Uhr

Benutzer-Avatar
Whiskysierra

Meine Vermutung ist, dass Sie eine verwenden Set<Role> in dem User Klasse mit kommentiert @OneToMany. Was bedeutet eins User hat viele Roles. Aber auf dem gleichen Feld verwenden Sie die @Column Anmerkung, die keinen Sinn macht. Eins-zu-viele-Beziehungen werden mithilfe einer separaten Join-Tabelle oder einer Join-Spalte auf der Viele-Seite verwaltet, was in diesem Fall die Role-Klasse wäre. Verwenden @JoinColumn Anstatt von @Column würde wahrscheinlich das Problem beheben, aber es scheint semantisch falsch zu sein. Ich denke, die Beziehung zwischen Rolle und Benutzer sollte viele-zu-viele sein.

  • @ElementCollection sieht dort auch seltsam aus. Was ist der Zweck?

    – Whiskysierra

    28. Mai 2011 um 20:20 Uhr

  • Wechsel zu @OneToMany(cascade=CascadeType.ALL, targetEntity=Role.class, mappedBy=”user”, fetch = FetchType.EAGER) @JoinColumn(name=”ROLE_ID”) private Set roles; hat das Problem nicht gelöst. Ich habe einen anderen Thread gesehen, in dem empfohlen wird, @ElementCollection zu verwenden, deshalb verwende ich es.

    – Tapas Bose

    28. Mai 2011 um 20:33 Uhr


  • Die elementCollection wird nicht für Komponenten verwendet? Objekte, deren Lebenszyklus der besitzenden Entität folgt?

    – Konstantin

    28. Mai 2011 um 21:26 Uhr

Hatte dieses Problem erst heute und stellte fest, dass ich versehentlich die Annotation @ManyToMany über der Annotation @JoinTable weggelassen hatte.

Benutzer-Avatar
Konstantin

Ich sage nicht, dass Ihre Zuordnung richtig oder falsch ist, aber ich denke, Hibernate möchte eine Instanz des Satzes, in der Sie das Feld deklarieren.

@OneToMany(cascade=CascadeType.ALL, fetch = FetchType.EAGER)
//@ElementCollection(targetClass=Role.class)
@Column(name = "ROLE_ID")
private Set<Role> roles = new HashSet<Role>();

  • Ich habe es nach deiner Anleitung gemacht. Aber nicht gelöst. Wenn Sie möchten, kann ich den vollständigen Stacktrace posten.

    – Tapas Bose

    28. Mai 2011 um 21:16 Uhr

  • Es ist nicht erforderlich, @ElementCollection im Rollensatz zu verwenden, da die Rolle eine Entität ist. Sie müssen in diesem Fall nur @ManyToOne verwenden. Die JPA 2.0-Spezifikation gibt eindeutig an, dass @ElementCollection für grundlegende Typen und Embeddables vorgesehen ist. Außerdem müssen Sie die Spalteninformationen mit @JoinColumn und nicht mit @Column angeben. Letzteres würde mit @ElementCollection verwendet werden, aber nicht mit @ManyToOne.

    – Edwin Dalorzo

    29. Mai 2011 um 13:34 Uhr

  • Posten Sie sicher den Stacktrace und den Edalorzo. Ich weiß, dass Sie Recht haben

    – Konstantin

    29. Mai 2011 um 19:20 Uhr

Benutzer-Avatar
naXa steht zur Ukraine

Ich hatte ein ähnliches Problem. Ich fand das Problem, dass ich die Anmerkungen mischte, einige davon über den Attributen und einige von ihnen über öffentlichen Methoden. Ich habe sie einfach alle über Attribute gesetzt und es funktioniert.

  • Ich habe es nach deiner Anleitung gemacht. Aber nicht gelöst. Wenn Sie möchten, kann ich den vollständigen Stacktrace posten.

    – Tapas Bose

    28. Mai 2011 um 21:16 Uhr

  • Es ist nicht erforderlich, @ElementCollection im Rollensatz zu verwenden, da die Rolle eine Entität ist. Sie müssen in diesem Fall nur @ManyToOne verwenden. Die JPA 2.0-Spezifikation gibt eindeutig an, dass @ElementCollection für grundlegende Typen und Embeddables vorgesehen ist. Außerdem müssen Sie die Spalteninformationen mit @JoinColumn und nicht mit @Column angeben. Letzteres würde mit @ElementCollection verwendet werden, aber nicht mit @ManyToOne.

    – Edwin Dalorzo

    29. Mai 2011 um 13:34 Uhr

  • Posten Sie sicher den Stacktrace und den Edalorzo. Ich weiß, dass Sie Recht haben

    – Konstantin

    29. Mai 2011 um 19:20 Uhr

Benutzer-Avatar
Tapas Bose

Lösung:

@Entity
@Table(name = "USER")
@Access(AccessType.FIELD)
public class User implements UserDetails, Serializable {

    private static final long serialVersionUID = 2L;

    @Id
    @Column(name = "USER_ID", updatable=false, nullable=false)
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private long id;

    @Column(name = "USERNAME")
    private String username;

    @Column(name = "PASSWORD")
    private String password;

    @Column(name = "NAME")
    private String name;

    @Column(name = "EMAIL")
    private String email;

    @Column(name = "LOCKED")
    private boolean locked;

    @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER, targetEntity = Role.class)
    @JoinTable(name = "USER_ROLE", joinColumns = { @JoinColumn(name = "USER_ID") }, inverseJoinColumns = { @JoinColumn(name = "ROLE_ID") })
    private Set<Role> roles;

    @Override
    public GrantedAuthority[] getAuthorities() {
        List<GrantedAuthorityImpl> list = new ArrayList<GrantedAuthorityImpl>(0);
        for (Role role : roles) {
            list.add(new GrantedAuthorityImpl(role.getRole()));
        }
        return (GrantedAuthority[]) list.toArray(new GrantedAuthority[list.size()]);
    }

    @Override
    public boolean isAccountNonExpired() {
        return true;
    }

    @Override
    public boolean isAccountNonLocked() {
        return !isLocked();
    }

    @Override
    public boolean isCredentialsNonExpired() {
        return true;
    }

    @Override
    public boolean isEnabled() {
        return true;
    }

    public long getId() {
        return id;
    }

    public void setId(long id) {
        this.id = id;
    }

    @Override
    public String getUsername() {
        return username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    @Override
    public String getPassword() {
        return password;
    }

    public void setPassword(String password) {
        this.password = password;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }

    public boolean isLocked() {
        return locked;
    }

    public void setLocked(boolean locked) {
        this.locked = locked;
    }

    public Set<Role> getRoles() {
        return roles;
    }

    public void setRoles(Set<Role> roles) {
        this.roles = roles;
    }
}

Role.java wie oben.

  • Es wäre viel besser, wenn Sie sagen würden, was geändert werden muss (und erklären, warum), anstatt den vollständigen Code zu posten. Man muss zwei Dateien Zeile für Zeile vergleichen, um den Unterschied zu finden.

    – Jamol

    13. Juli 2011 um 5:23 Uhr

  • Beim Vergleich der Dateien habe ich die folgenden Unterschiede festgestellt: 1. Er hat @Access(AccessType.FIELD) zur Klasse hinzugefügt. 2. @ElementColection für Set-Rollen wurde durch @JoinTable(…) ersetzt.

    – Marco

    21. März 2012 um 22:20 Uhr


1256630cookie-checkorg.hibernate.MappingException: Typ konnte nicht bestimmt werden für: java.util.Set [duplicate]

This website is using cookies to improve the user-friendliness. You agree by using the website further.

Privacy policy