4. díl - Databáze v Java JDBC - INSERT, UPDATE, DELETE a COUNT

Java Databáze Databáze v Java JDBC - INSERT, UPDATE, DELETE a COUNT

ONEbit hosting Unicorn College Tento obsah je dostupný zdarma v rámci projektu IT lidem. Vydávání, hosting a aktualizace umožňují jeho sponzoři.

V minulém dílu našeho seriálu tutoriálů o databázích v Javě jsme pomocí JDBC naprogramovali jednoduchý slovníček a naučili jsme se bránit útoku SQL Injection. Dnes budeme s JDBC pokračovat.

Vkládání, mazání a editace hodnot

Základní databázové operace se často označují zkratkou CRUD. Jedná se o operace Create (vytvořit), Read (číst), Update (aktualizovat), Delete (odstranit). Minule jsme si ukázali operaci Read. Již víme, že data z databáze čteme příkazem SELECT a z Java kolekce ResultSet.

INSERT

Vyzvěme uživatele k zadání slovíčka anglicky a česky. Nové slovíčko vložíme do databáze.

Scanner scanner = new Scanner(System.in, "Windows-1250");
System.out.println("Zadej nové slovíčko anglicky:");
String anglicky = scanner.nextLine();
System.out.println("Zadej nové slovíčko česky:");
String cesky = scanner.nextLine();
try (Connection spojeni = DriverManager.getConnection("jdbc:mysql://localhost/slovnicek_db?user=root&password=");
        PreparedStatement dotaz = spojeni.prepareStatement("INSERT INTO slovo (anglicky, cesky) VALUES (?, ?)");) {
        dotaz.setString(1, anglicky);
        dotaz.setString(2, cesky);
        int radku = dotaz.executeUpdate();
        System.out.println(radku);
} catch (SQLException ex) {
        System.out.println("Chyba při komunikaci s databází");
}

SQL dotaz pro vložení nového řádku do tabulky začíná příkazem INSERT INTO, následuje název tabulky. V závorkách vypíšeme názvy sloupců, do kterých vkládáme hodnoty. Za klauzuli VALUES vypíšeme opět do závorky hodnoty. Nemělo by vás překvapit, že použijeme opět parametry.

Dotaz spustíme metodou executeUpdate(). Ta se používá v případě, kdy měníme data v databázi. Metoda vrací počet ovlivněných řádků, pro ověření, že vložení proběhlo, si je vypišme do konzole.

Vložení řádku do MySQL databáze v Javě pomocí JDBC

ExecuteUpdate() vrátila hodnotu 1. Můžeme spustit původní kód naší aplikace, který vypisoval všechna slovíčka nebo k zobrazení dat použít NetBeans. Vidíme, že klávesnice je nově mezi slovíčky:

Výpis MySQL tabulky v NetBeans

DELETE

Přejděme k mazání záznamů. Oproti vkládání není v podstatě žádný rozdíl, jen jsem chtěl, abychom si pro úplnost ukázali všechny dotazy z CRUD.

Scanner scanner = new Scanner(System.in, "Windows-1250");
System.out.println("Zadej anglické slovíčko, které chceš vymazat:");
String anglicky = scanner.nextLine();
try (Connection spojeni = DriverManager.getConnection("jdbc:mysql://localhost/slovnicek_db?user=root&password=");
        PreparedStatement dotaz = spojeni.prepareStatement("DELETE FROM slovo WHERE anglicky=?");) {
        dotaz.setString(1, anglicky);
        int radku = dotaz.executeUpdate();
        System.out.println(radku);
} catch (SQLException ex) {
        System.out.println("Chyba při komunikaci s databází");
}

Java kód se vůbec nezměnil. SQL dotaz začíná DELETE FROM a pokračuje názvem tabulky. Následuje podmínka WHERE, kterou již dobře známe. Nikdy na podmínku v příkazu DELETE nezapomeňte, jinak dojte k vymazání všech záznamů v tabulce! Aplikaci opět vyzkoušejme:

Vymazání záznamu v MySQL databáze v Javě pomocí JDBC

Zkontrolujte si, že klávesnice mezi slovíčky již opravdu není. Můžeme zkusit i zadat neexistující slovíčko k vymazání, počet ovlivněných řádků bude 0.

Vymazání záznamu v MySQL databáze v Javě pomocí JDBC

UPDATE

Naši čtveřici dotazů zakončeme příkazem UPDATE, který vyvolá změnu. Naučme aplikaci měnit český překlad nějakého anglického slova:

Scanner scanner = new Scanner(System.in, "Windows-1250");
System.out.println("Zadej anglické slovíčko, u kterého chceš upravit překlad:");
String anglicky = scanner.nextLine();
System.out.println("Zadej nový překlad:");
String cesky = scanner.nextLine();
try (Connection spojeni = DriverManager.getConnection("jdbc:mysql://localhost/slovnicek_db?user=root&password=");
        PreparedStatement dotaz = spojeni.prepareStatement("UPDATE slovo SET cesky=? WHERE anglicky=?");) {
        dotaz.setString(1, cesky);
        dotaz.setString(2, anglicky);
        int radku = dotaz.executeUpdate();
        System.out.println(radku);
} catch (SQLException ex) {
        System.out.println("Chyba při komunikaci s databází");
}

Java kód je opět nezměněný (pouze jsme přidali parametr). SQL dotaz začíná UPDATE, následuje název tabulky a dále klauzule SET. Po ní název sloupce, rovnítko a nová hodnota. Pokud bychom potřebovali updatovat více sloupců, zapíšeme to např. takto:

UPDATE slovo SET cesky=?, anglicky=? WHERE id=?

Stejně jako u DELETE nikdy nesmíme zapomenout na kaluzuli WHERE, jinak se updatují všechny řádky v tabulce.

Aplikaci opět vyzkoušejme:

Update MySQL databáze v Javě JDBC

Zkontrolujte si, že se překlad změnil.

Počet řádků

Často nás v našich aplikacích bude zajímat počet řádků v tabulce. Slouží k tomu SQL klauzule COUNT. Ukažme si, jak se používá:

try (Connection spojeni = DriverManager.getConnection("jdbc:mysql://localhost/slovnicek_db?user=root&password=");
        PreparedStatement dotaz = spojeni.prepareStatement("SELECT COUNT(*) FROM slovo");) {
        ResultSet vysledek = dotaz.executeQuery();
        vysledek.next();
        System.out.println(vysledek.getInt(1));
} catch (SQLException ex) {
        System.out.println("Chyba při komunikaci s databází");
}

K dotázání na počet řádků použijeme příkaz SELECT. Klauzule COUNT nám vrátí tzv. agregovanou hodnotu. Agregovaná znamená, že je získaná z více sloupců. Takové hodnoty jsou např. počet, součet a průměr. Hvězdička v závorce označuje, že nás zajímají všechny sloupce. Pokud bychom místo ní uvedli název sloupce, počítaly by se jen ty řádky, kde je tento sloupec vyplněný (není v něm hodnota NULL). Samozřejmě bychom mohli dodat klauzuli WHERE a spočítat jen ty řádky, které splňují nějakou podmínku (např. anglické slovo začíná na A).

Výsledek jednoduše uložíme do ResultSetu, metodou next() se přesuneme na první řádek a vypíšeme první sloupec.

Výsledek:

Získání počtu záznamů v MySQL databází v Javě JDBC

Bez znalosti klauzule COUNT by vás možná napadlo napsat takovýto kód:

// Tento kód je neefektivní

try (Connection spojeni = DriverManager.getConnection("jdbc:mysql://localhost/slovnicek_db?user=root&password=");
        PreparedStatement dotaz = spojeni.prepareStatement("SELECT * FROM slovo");) {
        ResultSet vysledek = dotaz.executeQuery();
        vysledek.last();
        System.out.println(vysledek.getRow());
} catch (SQLException ex) {
        System.out.println("Chyba při komunikaci s databází");
}

Z databáze vybereme všechna slovíčka, která se přenesou do naší aplikace. Metodou last() se v ResultSetu přesuneme na poslední řádek a poté vrátíme jeho číslo. Nutně dostaneme počet řádků v tabulce.

Vrácený výsledek je sice stejný, takže by se mohlo zdát, že je vše v pořádku. Ale ono není. Přenos dat zabere nějaký čas a také je potřeba je mít v paměti. Nakonec jen řádky spočítáme a data ani nepoužijeme. Představte si, že je ve slovníčku milion slovíček. To opravdu není efektivní řešení.

Ještě jsme nezmínili použití zpětných uvozovek v dotazech. Pokud název nějakého sloupce koliduje s klíčovým slovem z SQL (např. se sloupec jmenuje where), dáme ho do zpětných uvozovek. Píší se tou klávesou pod escape. Často se setáte s konvencí, kde se takto označují všechny názvy:

UPDATE `slovo` SET `cesky`=?, `anglicky`=? WHERE `id`=?

Dnešní projekt je se zdrojovými kódy jako vždy v příloze ke stažení.


 

Stáhnout

Staženo 207x (17.35 kB)
Aplikace je včetně zdrojových kódů v jazyce java

 

  Aktivity (1)

Článek pro vás napsal David Čápka
Avatar
Autor pracuje jako softwarový architekt a pedagog na projektu ITnetwork.cz (a jeho zahraničních verzích). Velmi si váží svobody podnikání v naší zemi a věří, že když se člověk neštítí práce, tak dokáže úplně cokoli.
Unicorn College Autor se informační technologie naučil na Unicorn College - prestižní soukromé vysoké škole IT a ekonomie.

Jak se ti líbí článek?
Celkem (4 hlasů) :
55555


 



 

 

Komentáře

Avatar
Milan Gallas
Redaktor
Avatar
Milan Gallas:

V tom příkladu - počet řádků máš SQL injekci. Přidáváš tam tabulku osoby přímo. Měl bys tu tabulku dosadit jako parametr metodou set.

 
Odpovědět 22.4.2014 22:44
Avatar
Milan Gallas
Redaktor
Avatar
Milan Gallas:

Tak jsem to zkoušel a celkově mi dělá problém přidat tabulku jako parametr do sql dotazu. Mám jednoduchou metodu

public int count(String table) throws SQLException{
        PreparedStatement ps =
                connection.prepareStatement("SELECT * FROM ? WHERE id = ?");
        ps.setString(1, table);
        ps.setInt(2, 2);
       ResultSet result = ps.executeQuery();
         result.next();
        return result.getInt(1);
    }

Metoda je celkem nesmyslná. Ber to prostě jako příklad.

píše mi to, že mám syntatickou chybu v SQL poblíž - SELECT * FROM programatori WHERE id = 2

Editováno 22.4.2014 22:54
 
Odpovědět 22.4.2014 22:53
Avatar
Matěj Kripner
Redaktor
Avatar
Matěj Kripner:

Zdravím, co vše musím udělat pro to, abych mohl program spustit i na PC bez nainstalované databáze? Dík.

Odpovědět 12.6.2014 15:50
"We reject kings, presidents and voting. We believe in rough consensus and running code" David Clark
Avatar
David Čápka
Tým ITnetwork
Avatar
Odpovídá na Matěj Kripner
David Čápka:

Musíš použít např. SQLite, která se nemusí instalovat.

Odpovědět  +1 12.6.2014 15:53
Miluji svou práci a zdejší komunitu, baví mě se rozvíjet, děkuji každému členovi za to, že zde působí.
Avatar
Milan Křepelka
Redaktor
Avatar
Odpovídá na Matěj Kripner
Milan Křepelka:

Existují databázové stroje které není potřeba instalovat

http://en.wikipedia.org/…ded_database

Zajímavá volba může být i

http://www.db4o.com/

Když člověk tak nějak nebazíruje na SQL

 
Odpovědět 12.6.2014 15:56
Avatar
Matěj Kripner
Redaktor
Avatar
Odpovědět 12.6.2014 16:13
"We reject kings, presidents and voting. We believe in rough consensus and running code" David Clark
Avatar
Milan Křepelka
Redaktor
Avatar
Odpovídá na Matěj Kripner
Milan Křepelka:

SQL Lite není dobrá volba jako databázový stroj. Ono je to opravdu až příliš mnoho Lite.

 
Odpovědět 13.6.2014 11:10
Avatar
David Čápka
Tým ITnetwork
Avatar
Odpovídá na Milan Křepelka
David Čápka:

SQLite se používá docela dost, záleží na co ji chceš. Pro robustní firemní aplikaci je to špatná volba, ale pro nějakou jednoduchou evidenci naopak velmi dobrá.

Odpovědět 13.6.2014 12:44
Miluji svou práci a zdejší komunitu, baví mě se rozvíjet, děkuji každému členovi za to, že zde působí.
Avatar
santa580
Člen
Avatar
santa580:

Ahoj, mám problém s diakritikou, dělám si databazi jako svůj objekt a mám tento kod na zapis(stejný jako v tutorialu) a když slovíčko přídám je bez diakritiky např. (moře se mi napíše jako mo?e) áéíý funguje. Nevíte čím by to mohlo být?

 public void Zapis(String s1, String s2)
    {
        try (Connection spojeni = DriverManager.getConnection("jdbc:mysql://localhost/slovnicek_db?user=root&password=");
        PreparedStatement dotaz = spojeni.prepareStatement("INSERT INTO slovo (anglicky, cesky) VALUES (?, ?)");) {
        dotaz.setString(1, s1);
        dotaz.setString(2, s2);
            System.out.println(s1 + " " + s2);  //zkoušel jsem to vypsat do console, při vstupu chyba není..
        int radku = dotaz.executeUpdate();
        System.out.println(radku);
} catch (SQLException ex) {
        System.err.println("Do databáze se nepovedlo zapsat!" + ex);
}
    }
 
Odpovědět 12.11.2015 14:10
Avatar
santa580
Člen
Avatar
Odpovídá na santa580
santa580:

Ještě bych dodal že kodování mám v databázi nastavené na utf8_general_ci, fakt nikoho nenapadá čím by to mohlo být?

 
Odpovědět 14.11.2015 21:45
Děláme co je v našich silách, aby byly zdejší diskuze co nejkvalitnější. Proto do nich také mohou přispívat pouze registrovaní členové. Pro zapojení do diskuze se přihlas. Pokud ještě nemáš účet, zaregistruj se, je to zdarma.

Zobrazeno 10 zpráv z 10.