199 votes

Quelqu'un peut-il s'il vous plaît expliquer mappedBy en veille prolongée?

Je suis nouvelle mise en veille prolongée et que vous devez utiliser 1-de Nombreux et Nombreuses-1 relation. C'est un bi-directionnelle de la relation dans mes objets, de sorte que je peux traverser dans les deux sens. mappedBy est recommandé d'aller à ce sujet. Cependant, je ne pouvais pas le comprendre. Quelqu'un peut-il svp me l'expliquer,

  • quelle est la méthode recommandée pour l'utiliser ?
  • a quoi sert-il de résoudre ?

Pour l'amour de mon exemple, voici mes classes avec des annotations:

  • Airline POSSÈDE de nombreux AirlineFlights
  • Nombre AirlineFlights appartiennent à UN Airline

Compagnie aérienne:

@Entity 
@Table(name="Airline")
public class Airline {
    private Integer idAirline;
    private String name;

    private String code;

    private String aliasName;
    private Set<AirlineFlight> airlineFlights = new HashSet<AirlineFlight>(0);

    public Airline(){}

    public Airline(String name, String code, String aliasName, Set<AirlineFlight> flights) {
        setName(name);
        setCode(code);
        setAliasName(aliasName);
        setAirlineFlights(flights);
    }

    @Id
    @GeneratedValue(strategy=GenerationType.IDENTITY)
    @Column(name="IDAIRLINE", nullable=false)
    public Integer getIdAirline() {
        return idAirline;
    }

    private void setIdAirline(Integer idAirline) {
        this.idAirline = idAirline;
    }

    @Column(name="NAME", nullable=false)
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = DAOUtil.convertToDBString(name);
    }

    @Column(name="CODE", nullable=false, length=3)
    public String getCode() {
        return code;
    }
    public void setCode(String code) {
        this.code = DAOUtil.convertToDBString(code);
    }

    @Column(name="ALIAS", nullable=true)
    public String getAliasName() {
        return aliasName;
    }
    public void setAliasName(String aliasName) {
        if(aliasName != null)
            this.aliasName = DAOUtil.convertToDBString(aliasName);
    }

    @OneToMany(fetch=FetchType.LAZY, cascade = {CascadeType.ALL})
    @JoinColumn(name="IDAIRLINE")
    public Set<AirlineFlight> getAirlineFlights() {
        return airlineFlights;
    }

    public void setAirlineFlights(Set<AirlineFlight> flights) {
        this.airlineFlights = flights;
    }
}

AirlineFlights:

@Entity
@Table(name="AirlineFlight")
public class AirlineFlight {
    private Integer idAirlineFlight;
    private Airline airline;
    private String flightNumber;

    public AirlineFlight(){}

    public AirlineFlight(Airline airline, String flightNumber) {
        setAirline(airline);
        setFlightNumber(flightNumber);
    }

    @Id
    @GeneratedValue(generator="identity")
    @GenericGenerator(name="identity", strategy="identity")
    @Column(name="IDAIRLINEFLIGHT", nullable=false)
    public Integer getIdAirlineFlight() {
        return idAirlineFlight;
    }
    private void setIdAirlineFlight(Integer idAirlineFlight) {
        this.idAirlineFlight = idAirlineFlight;
    }

    @ManyToOne(fetch=FetchType.LAZY)
    @JoinColumn(name="IDAIRLINE", nullable=false)
    public Airline getAirline() {
        return airline;
    }
    public void setAirline(Airline airline) {
        this.airline = airline;
    }

    @Column(name="FLIGHTNUMBER", nullable=false)
    public String getFlightNumber() {
        return flightNumber;
    }
    public void setFlightNumber(String flightNumber) {
        this.flightNumber = DAOUtil.convertToDBString(flightNumber);
    }
}

EDIT:

Schéma de base de données:

AirlineFlights a la idAirline comme ForeignKey et de la compagnie Aérienne n'a pas de idAirlineFlights. De ce fait, AirlineFlights que le propriétaire/l'identification de l'entité ?

Théoriquement, je tiens compagnie à être le propriétaire de airlineFlights.

enter image description here

295voto

Kurt Du Bois Points 3045

MappedBy signale en hibernation que la clé de la relation est de l'autre côté.

Cela signifie que même si vous liez 2 tables ensemble, une seule de ces tables a une contrainte de clé étrangère sur l’autre. MappedBy vous permet de créer un lien depuis la table ne contenant pas la contrainte vers l'autre table.

156voto

Affe Points 24993

En spécifiant l' @JoinColumn sur les deux modèles, vous n'avez pas une relation. Vous avez deux une façon de relations, et un très déroutant de cartographie de là. Vous dites à la fois les modèles qu'ils "possèdent" le IDAIRLINE colonne. Vraiment un seul d'entre eux en fait! Le "normal", c'est de prendre l' @JoinColumn off de l' @OneToMany côté entièrement, et au lieu d'ajouter mappedBy à l' @OneToMany.

@OneToMany(fetch=FetchType.LAZY, cascade = {CascadeType.ALL}, mappedBy="airline")
public Set<AirlineFlight> getAirlineFlights() {
    return airlineFlights;
}

Qui indique à Hibernate "Aller en chercher plus sur le haricot propriété nommée "compagnie aérienne" sur la chose j'ai une collection de trouver la configuration."

14voto

Hari Krishna Points 91

L'annotation @JoinColumn indique que cette entité est le propriétaire de la relation. C'est-à-dire que la table correspondante a une colonne avec une clé étrangère à la table référencée, alors que l'attribut mappedBy indique que l'entité de ce côté est l'inverse de la relation et que le propriétaire réside dans l'entité "autre".

En particulier, pour le code dans la question, les annotations correctes ressembleraient à ceci:

 @Entity
public class Company {
    @OneToMany(fetch = FetchType.LAZY, mappedBy = "company")
    private List<Branch> branches;
}

@Entity
public class Branch {
    @ManyToOne(fetch = FetchType.LAZY)
    @JoinColumn(name = "companyId")
    private Company company;
}
 

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X