Parhaat käytännöt monelle yhdistykselle, joilla on Hibernate ja yhteinen edustajakokous

monelle yhdistykselle ovat yksi yleisimmin käytetyistä yhdistyksistä yhteisen edustajakokouksen ja Hibernaten kanssa. Voit löytää paljon esimerkkejä heille reaalimaailmassa, ja voit kartoittaa niitä yhteisen edustajakokouksen ja Hibernate kuin uni – tai kaksisuuntainen yhdistys verkkotunnuksen malli.

mutta luultavasti tiedät myös, että nämä kuvaukset tarjoavat useita sudenkuoppia. Tässä artikkelissa, näytän sinulle 5 parhaita käytäntöjä, jotka auttavat sinua välttämään nämä sudenkuopat ja toteuttaa tehokkaita kartoituksia. Opit Kyllä:

  • yhdistyksesi tehokkain tietotyyppi
  • miksi tarvitset hyödyllisyysmenetelmiä yhdistyksesi hallintaan
  • oikea hakutyyppi tehokkaaseen yhdistämiseen
  • milloin ja miten kyselykohtaista hakua käytetään
  • CascadeType, jota kannattaa välttää hinnalla millä hyvänsä
  • en sukella perustason moneen kartoitukseen. Jos et ole aivan varma, miten luoda tällainen kartoitus, tutustu moneen-to-moneen osioon yhdistykseni kartoitusoppaassa.

    yhdistyksesi tehokkain tietotyyppi

    YouTube-video

    useimmat kehittäjät eivät juurikaan mieti a-monelle assosiaation tietotyyppiä. He vain valitsevat Jaavan.util.Luettelo, koska se on yksinkertainen ja ei suorita tarkastuksia välttää päällekkäisyyksiä.

    se on OK, jos toteuttaa Perusjavan luokan tai mallintaa One-to-Many / Many-to-One-assosiaation. Listaa ei kuitenkaan kannata koskaan käyttää, jos mallintaa moneen yhdistykseen.

    @Entitypublic class Book {// DON'T DO THIS!!!@ManyToMany@JoinTable(name = "book_author", joinColumns = { @JoinColumn(name = "fk_book") }, inverseJoinColumns = { @JoinColumn(name = "fk_author") })private List<Author> authors = new ArrayList<Author>();...}

    Hibernate käsittelee monien Javaan yhdistettyjen suhteiden operaatioita.util.Lista hyvin tehoton.

    em = emf.createEntityManager();em.getTransaction().begin();// Get Book entity with 2 Authorsb = em.find(Book.class, 1L);// Remove one of the Authorb.getAuthors().remove(a);em.getTransaction().commit();em.close();

    se poistaa ensin kaikki tietueet assosiaatiotaulukosta ennen kuin se lisää kaikki jäljellä olevat.

    09:54:28,876 DEBUG - update Book set title=?, version=? where id=? and version=?09:54:28,878 DEBUG - delete from book_author where fk_book=?09:54:28,882 DEBUG - insert into book_author (fk_book, fk_author) values (?, ?)

    kannattaa sen sijaan mallintaa moneen assosiaatioon Jaava.util.Asettaa.

    @Entitypublic class Book {@ManyToMany@JoinTable(name = "book_author", joinColumns = { @JoinColumn(name = "fk_book") }, inverseJoinColumns = { @JoinColumn(name = "fk_author") })private Set<Author> authors = new HashSet<Author>();...}

    Hibernate hoitaa sitten yhdistyksen poistotoimet paljon paremmin. Nyt se vain poistaa liitolta odotetut ennätykset ja pitää muut koskemattomina.

    10:00:37,709 DEBUG - update Book set title=?, version=? where id=? and version=?10:00:37,711 DEBUG - delete from book_author where fk_book=? and fk_author=?

    Why you need utility methods to management your association

    kaksisuuntaiset assosiaatiot on kartoitettu entiteetti-attribuutiksi suhteiden molemmissa päissä. Niin, edellisessä esimerkissä, sinulla on kirjailijat attribuutti kirja entity, ja kirjat attribuutti kirjailija entity. Tämä tekee jpql: n tai Criteriaqueryn toteuttamisesta erittäin mukavaa, koska voit käyttää näitä attribuutteja LIITTYMISLAUSEKKEEN määrittelyyn.

    mutta assosiaation lisääminen tai poistaminen monimutkaistuu. Muutos on aina tehtävä yhdistyksen molemmissa päissä. Jos esimerkiksi haluat lisätä kirjan tekijälle, sinun on lisättävä se tekijäobjektin books-attribuuttiin, ja sinun on myös lisättävä tekijä the authors-attribuutti kirjakokonaisuuteen. Muussa tapauksessa nykyinen pysyvyyskontekstisi sisältää epäjohdonmukaisia tietoja, joita käytät nykyisen tapahtumasi päättymiseen saakka.

    Book b = new Book();b.setTitle("Hibernate Tips - More than 70 solutions to common Hibernate problems");em.persist(b);Author a = em.find(Author.class, 1L);a.getBooks().add(b);b.getAuthors().add(a);

    tekijän ja kirjan kokonaisuuksien Hyödyllisyysmenetelmät tekevät päivittämisestä ja poistamisesta paljon helpompaa. Näissä menetelmissä suoritat vaaditut operaatiot molemmille yksiköille.

    @Entitypublic class Author {@ManyToMany(mappedBy = "authors")private Set<Book> books = new HashSet<Book>();...public void addBook(Book book) {this.books.add(book);book.getAuthors().add(this);}public void removeBook(Book book) {this.books.remove(book);book.getAuthors().remove(this);}}

    oikea FetchType tehokkaaseen kartoitukseen

    YouTube-video

    Tämä on nopea. Sinun pitäisi aina käyttää FetchType.Laiska moneen seuraan. Se kertoo pysyvyyden tarjoaja ei noutaa liittyvät yhteisöt tietokannasta ennen kuin käytät niitä. Se on yleensä silloin, kun soitat sen getter menetelmä ensimmäistä kertaa.

    onneksi se on oletusarvo kaikille-monille yhdistyksille. Varmista, ettet muuta sitä.

    ja jos haluat oppia lisää yhteisen edustajakokouksen eri Fetchtypeistä, katso Esittelyäni yhteisen edustajakokouksen Fetchtypesistä.

    milloin ja miten kyselykohtaista noutoa käytetään

    Jos käytät Fetchtypea.Laiska, sinun täytyy tietää kyselykohtaisesta hakemisesta. Muuten, sovellus on hyvin hidas, koska olet luonut paljon n + 1 select kysymyksiä.

    YouTube-video

    kun lataat olion ja käytät kyselykohtaista noutoa, kerrot Hibernatelle, mitkä yhdistykset se alustaa kullekin noudetulle oliolle. Sen jälkeen se laajentaa kyselysi SELECT-lauseketta niin, että se sisältää näiden muiden entiteettien kartoittamat sarakkeet ja alustaa assosiaatiot. Ja koska assosiaatiot on jo alustettu, Hibernaten ei tarvitse tehdä lisäkyselyä, kun käytät sen getter-menetelmää ensimmäistä kertaa.

    voit toteuttaa kyselykohtaisen noudon usealla eri tavalla. Yksinkertaisin on JOIN FETCH-lauseke, jonka näytän sinulle täällä. Mutta voit myös käyttää @NamedEntityGraph tai EntityGraph, jonka selitin aiemmissa artikkeleissa.

    JOIN FETCH-lausekkeen määritelmä on lähes identtinen JPQL-kyselyssä olevan yksinkertaisen JOIN-lausekkeen kanssa. Sinun tarvitsee vain lisätä hakusana.

    Author a = em.createQuery("SELECT a FROM Author a JOIN FETCH a.books WHERE a.id = 1", Author.class).getSingleResult();

    siltikin JOIN ja JOIN FETCH-lauseke näyttävät hyvin samanlaisilta, JOIN FETCH-lausekkeella on paljon suurempi vaikutus generoituun SQL-kyselyyn. Se ei vain saa käännetty SQL liittyä, koska se on tapauksessa JPQL liittyä lauseke, se myös pakottaa pysyvyys tarjoaja laajentaa SELECT lausekkeen kaikki sarakkeet, jotka on kartoitettu liittyvä yhteisö.

    16:21:03,046 DEBUG SQL:94 - select author0_.id as id1_0_0_, book2_.id as id1_1_1_, author0_.firstName as firstNam2_0_0_, author0_.lastName as lastName3_0_0_, author0_.version as version4_0_0_, book2_.format as format2_1_1_, book2_.publishingDate as publishi3_1_1_, book2_.title as title4_1_1_, book2_.version as version5_1_1_, books1_.author_id as author_i2_2_0__, books1_.book_id as book_id1_2_0__ from Author author0_ inner join book_author books1_ on author0_.id=books1_.author_id inner join Book book2_ on books1_.book_id=book2_.id where author0_.id=1

    Kaskadetyyppi, jota sinun tulisi välttää hinnalla millä hyvänsä

    jos aktivoit kaskadoinnin johonkin assosiaatioon, pysyvyyden tarjoajasi soveltaa yhteisölle suorittamiasi operaatioita kaikkiin liitännäisyhteisöihin. Jos se tekee niin kaikille toiminnoille tai vain muutamille valituille, riippuu asetetusta Cascadetypestä.

    YouTube-video

    tuo saattaa kuulostaa hämmästyttävältä idealta, joka tekee oman bisneslogiikan toteuttamisesta paljon helpompaa. Eikä se ole täysin väärin.

    mutta vältä CascadeTypes REMOVE Ja ALL, joka sisältää REMOVE, monelle-to-monelle assosiaatiolle. Parhaassa tapauksessa se aiheuttaa vain suorituskykyongelmia, mutta pahimmassa tapauksessa se saattaa myös poistaa enemmän levyjä kuin oli tarkoitus.

    selitin edellisessä kirjoituksessa sekä sudenkuopat että niiden ratkaisun hyvin yksityiskohtaisesti. Tai jos haluat pitää sen yksinkertaisena, laukaise tarvittavat tiedot ohjelmallisesti liitännäisyksiköistä. Tämä saattaa vaatia muutaman rivin koodia, mutta se välttää odottamattomia sivuvaikutuksia.

    johtopäätös

    reaalimaailmasta löytyy paljon esimerkkejä monelle yhdistykselle, ja niitä voi helposti kartoittaa JPA: n ja Hibernaten avulla. Valitettavasti näissä yksinkertaisissa kartoituksissa piilee muutama sudenkuoppa, jotka voi välttää noudattamalla näitä 5 parasta käytäntöä:

    1. malliyhdistykset jaavana.util.Asettaa.
    2. tarjoavat hyödyllisyysmenetelmiä, joilla yhteisö voidaan lisätä tai poistaa yhdistyksestä.
    3. käytä aina Fetchtypeä.Laiska, mikä on oletus, välttää suorituskyvyn ongelmia.
    4. käytä kyselykohtaista hakua välttääksesi n+1 select-ongelmat.
    5. Älä käytä CascadeTypes REMOVEA ja kaikkea.

    Vastaa

    Sähköpostiosoitettasi ei julkaista.