4.1 Transacties en database-integriteit

De normale werking van een database is wanneer deze elke minuut duizenden verzoeken ontvangt van honderden verschillende clients. In dit geval doen zich vaak situaties voor wanneer dezelfde gegevens worden benaderd via verschillende zoekopdrachten.

Minder vaak, maar nogmaals, van tijd tot tijd zijn er situaties waarin een verzoek een bepaalde regel leest en een ander verzoek deze tegelijkertijd wijzigt. Stel je voor wat er gebeurt als iemand een regel leest die maar half is veranderd? Niets goeds.

Dit probleem wordt op verschillende manieren opgelost. Ten eerste kunt u gewoon de lijn vergrendelen die verandert. Zowel om te lezen als om te schrijven. Deze methode werkt, maar de snelheid van de basis lijdt er enorm onder.

De tweede manier is om de string alleen te vergrendelen om te schrijven. Er zal echter nog steeds een probleem zijn wanneer iemand de gedeeltelijk gewijzigde regel probeert te lezen. Conclusie - er mag geen situatie zijn waarin de regel gedeeltelijk wordt gewijzigd.

Daarom bedachten ze een derde methode: transacties. Een transactie is een groep acties die allemaal samen of helemaal niet worden uitgevoerd. Er kan geen situatie zijn waarin een deel van de acties werd uitgevoerd en het tweede deel niet. Als het niet mogelijk is om alle wijzigingen door te voeren, worden alle reeds aangebrachte wijzigingen ongedaan gemaakt.

Met elke moderne SQL-server kunt u alleen gegevens in transacties wijzigen. U opent een transactie, brengt wijzigingen aan in een willekeurig aantal tabellen en legt de transactie vast. SQL Server probeert vervolgens wijzigingen aan te brengen. Als alles in orde is, worden ze toegevoegd aan de algemene database. Als er problemen waren, worden alle wijzigingen geannuleerd.

Hibernate gebruikt dit paradigma ook. Daarom zagen we in de vorige lezing dat bij het opslaan van het object Employee in de database eerst een transactie werd geopend en na het opslaan werd deze gecommit.

We zullen dieper op dit onderwerp ingaan, maar voor nu, weet gewoon waarom transacties nodig zijn en waar ze gewoonlijk worden gebruikt.

4.2 Voorwerpen krijgen

Als Hibernate een verzoek uitvoert om gegevens op te halen, is het niet nodig om expliciet een transactie te openen. Hibernate zal dit zelf doen als het dat nodig acht: het heeft zijn instellingen, evenals de instellingen van de SQL-server.

We zullen analyseren hoe we met de database moeten werken. En de eenvoudigste daarvan is een object ophalen op basis van zijn ID . Gebruik hiervoor de methode get()op het sessieobject . De algemene vorm van een dergelijk verzoek:

Class Name = session.get(Class.class, ID);

Voorbeeld:

public User getUserById(Integer id) {
    try (Session session = sessionFactory.openSession()) {
        User user = session.get(User.class, id);
        return user;
    }
}

4.3 Objecten opslaan (toevoegen).

Als u uw object in de database wilt opslaan, wordt er een query uitgevoerd op SQL-niveauINVOEGEN. Daarom moeten uw acties als een afzonderlijke transactie worden uitgevoerd. Het is ook beter om de methode persist()van het sessieobject voor persistentie te gebruiken .

De algemene vorm van een dergelijk verzoek:

session.persist(An object);

De methode persist()verandert niet alleen de basis, maar ook het object zelf. Het punt is dat wanneer we een object aan de database toevoegen, dit object nog geen eigen ID heeft voordat het wordt toegevoegd . Nou ja, meestal zo, hoewel er nuances zijn. En na het toevoegen heeft het object al een ID .

public boolean saveUser(User user) {
    try (Session session = sessionFactory.openSession()) {
            Transaction transaction = session.beginTransaction();
            session.persist(user);
            transaction.commit();
            return true;
    }
    catch() {
    return false;
   	}
}

Het Session- object heeft ook een methode save()die een vergelijkbare functie vervult. Het is alleen dat de methode save()de oude Hibernate-standaard is en de methode persist()de JPA-standaard.

4.4 Objecten verwijderen

Als u een bestaand object wilt verwijderen, dan is dat heel eenvoudig. Om dit te doen heeft het sessieobject een speciale methode - remove().

De algemene vorm van een dergelijk verzoek:

session.remove(An object);

En laten we natuurlijk de code schrijven met een voorbeeld:

public boolean removeUser(User user) {
    try (Session session = sessionFactory.openSession()) {
            Transaction transaction = session.beginTransaction();
            session.remove(user);
            transaction.commit();
            return true;
    }
    catch() {
    return false;
   	}
}

Waarom is het zo moeilijk, vraag je?

Ten eerste hebben wijzigingen in de database altijd andere en niet altijd voor de hand liggende gevolgen. En ten tweede kan er aan dit object onderliggende objecten gekoppeld zijn, enz. Scenario's voor het verwijderen zijn dus vaak niet triviaal.