Spring framework
                     Motto: Musíte rozbít vejce když chcete udělat omeletu




                Spring framework training materials by Roman Pichlík is licensed under a Creative Commons Attribution-ShareAlike 3.0 Unported License.

Sunday 13 May 2012
Přístup k datům
             Jak efektivně používat Spring framework pro přístup k datům




Sunday 13 May 2012
Práce s daty

                     • Různé oblasti
                      • Definice datového zdroje
                      • Údržba zdrojů
                      • Ošetření výjimek
                      • Řízení transakcí


Sunday 13 May 2012

- bez ohledu na použiti konkretního frameworku
Definice datového zdroje




Sunday 13 May 2012
• Datasource je beana
                        • java.sql.Datasource
                     • Lokální/Poskytovaný
                      • JNDI aplikačního serveru



Sunday 13 May 2012

- datasource participuje v dependency injection jako jákákoliv jiná beana
Lokální datasource

  <bean id="dataSource"
     class="org.apache.commons.dbcp.BasicDataSource"
     destroy-method="close">
    <property name="driverClassName" value="org.hsqldb.jdbcDriver"/>
    <property name="url" value="jdbc:hsqldb:mem:test"/>
    <property name="username" value="sa"/>
    <property name="password" value=""/>
  </bean>
      •      Connection pool s využitím

           •         Apache DBCP http://commons.apache.org/dbcp/

           •         Pozor na DBCP v produkci

                •      http://blog.novoj.net/2010/02/07/commons-dbcp-industrialni-
                       standard-s-chybami/
Sunday 13 May 2012

- zduraznit, ze nezalezi na tom odkud pochazi trida, ktera reprezentuje datasource
- DBCP alternativy C3PO, pool aplikacniho serveru (pokud to neni Tomcat)
Lokální ds. pro embedded DB
      • Spring 3.x namespace embedded DB
                • HSQL, H2, Derby
                • Inicializace skripty
       <jdbc:embedded-database id="dataSource">
               <jdbc:script location="classpath:schema.sql"/>
               <jdbc:script location="classpath:test-data.sql"/>
       </jdbc:embedded-database>



       EmbeddedDatabaseBuilder builder = new EmbeddedDatabaseBuilder();
       EmbeddedDatabase db =
            builder.setType(H2).addScript("schema.sql").addScript("test-data.sql").build();
       // do stuff against the db (EmbeddedDatabase extends javax.sql.DataSource)
       db.shutdown()
Sunday 13 May 2012

- rozsiritelne, muznost konfigurovat jinou embedded DB
- programový i deklarativní způsob
Data Access Object
      • Návrhový vzor pro
        přístup k datům

      • Pouze DAO
        implementuje logiku pro
        práci s DB

      • Motivace

           • změna implementace

           • odpovědnost v jedné
             vrstvě
Sunday 13 May 2012
Implementační možnosti
                     • Přímé použití JDBC
                     • ORM či Semi-ORM framework
                      • JPA, Hibernate, iBatis, JDO...
                     • Co budeme řešit
                      • Konfigurace
                      • Resource management
                      • Exception handling
Sunday 13 May 2012

- Spring všechny tyto věci řeší za nás
- poskytuje high level API, které odstiňuje
JDBC




Sunday 13 May 2012
Co obnáší práce s JDBC

                     • Získání databázového připojení
                     • Vytvoření java.sql.Statement
                     • Nastavení parametru
                     • Vykonání
                     • Procházení výsledků a zpracování


Sunday 13 May 2012
Jak vypadá typický kód
  Connection con = null;
  PreparedStatement ps = null;                    • Kde jsou problémy?
  ResultSet rs = null;
  try{
       con = getConnection();                      • NPE ignorujte
       ps = con.prepareStatement("select * x");
       rs = ps.executeQuery();
       while(rs.next()){
           //zpracuj hodnoty
       }
  } catch(SQLException e) {
  	 throw new RuntimeException(e);
  } finally {
     try {
     	 rs.close();
         ps.close();
         con.close();
     } catch(SQLException e) {}
  }	




Sunday 13 May 2012
Jak vypadá typický kód
  Connection con = null;
  PreparedStatement ps = null;                    • Kde jsou problémy?
  ResultSet rs = null;
  try{
       con = getConnection();                      • Často se opakující kód
       ps = con.prepareStatement("select * x");
       rs = ps.executeQuery();
       while(rs.next()){
           //zpracuj hodnoty
                                                     • Návrhový vzor
       }
  } catch(SQLException e) {
                                                       Copy&Paste
  	 throw new RuntimeException(e);
  } finally {
     try {                                         • Uvolnění zdrojů
     	 rs.close();
         ps.close();
         con.close();                              • Míchání odpovědností
     } catch(SQLException e) {}
  }	

                                                   • Vykonání/Zpracování
                                                     výsledku
Sunday 13 May 2012
Jak vypadá typický kód
  Connection con = null;
                                                               r u
                                                           o
  PreparedStatement ps = null;                    • Kde jsou problémy?
  ResultSet rs = null;
  try{
                                       v                 z
                                     m
       con = getConnection();                      • Často se opakující kód
                                   é • Návrhový vzor
       ps = con.prepareStatement("select * x");
       rs = ps.executeQuery();
                                  v
                                 o h od
                                h t Copy&Paste
       while(rs.next()){


                               r e
           //zpracuj hodnoty
       }
  } catch(SQLException e) {  v
                           á m
  } finally {             n e • Uvolnění zdrojů
  	 throw new RuntimeException(e);


                         v at
                       je pl
     try {


                      í m
     	 rs.close();


                     n e
         ps.close();


                    e T
         con.close();               • Míchání odpovědností
  }	
                 e š
     } catch(SQLException e) {}



                Ř                   • Vykonání/Zpracování
                                                      výsledku
Sunday 13 May 2012
Template method
                     • Společný kód v
                       předkovi

                     • Potomek přepisuje
                       jenom to je pro něj
                       specifické

                       • zpracování
                         výsledků




Sunday 13 May 2012
JDBC se Springem




Sunday 13 May 2012
Klíčové abstrakce


  org.springframework.jdbc.core.JdbcTemplate

  org.springframework.jdbc.core.support.JdbcDaoSupport




Sunday 13 May 2012

- resource management
- exception handling
JdbcTemplate
                     • Centrální třídá pro práci s JDBC
                     • Thread safe
                     • Překlad výjimek
                     • Resource management
                     • Alternativy
                      •   org.springframework.jdbc.core.simple.SimpleJdbcTe
                          mplate

                      •   org.springframework.jdbc.core.namedparam.NamedPar
                          ameterJdbcTemplate
Sunday 13 May 2012
Ukázky




Sunday 13 May 2012
SQL
  int rowCount =
           jdbcTemplate.queryForInt("select count(0) from t_accrual");

  int countOfActorsNamedJoe =
           jdbcTemplate.queryForInt(
              "select count(0) from t_actors where first_name = ?",
              new Object[]{"Joe"}
           );
  	 	
  Actor actor =
      (Actor) jdbcTemplate.queryForObject(
        "select first_name, surname from t_actor where id = ?",
  	     new Object[]{new Long(1212)},
  	     new RowMapper() {
  	         public Object mapRow(ResultSet rs, int rowNum) throws SQLException {
  	             Actor actor = new Actor();
  	 	 	         actor.setFirstName(rs.getString("first_name"));
  	 	 	         actor.setSurname(rs.getString("surname"));
  	 	 	         return actor;
            }
  	     });
Sunday 13 May 2012
DML a DDL
  jdbcTemplate.update(
     "insert into t_actor (first_name, surname) values (?, ?)",
      new Object[] {"Leonor", "Watling"});


  jdbcTemplate.execute(
     "create table mytable (id integer, name varchar(100))");




Sunday 13 May 2012
Pojmenované parametry

  NamedParameterJdbcTemplate namedParameterJdbcTemplate =
                                                 new NamedParameterJdbcTemplate(dataSource);
  String sql = "select count(0) from T_ACTOR where first_name = :first_name";
  Map namedParameters = new HashMap();
  namedParameters.put("first_name", firstName);
  int count = namedParameterJdbcTemplate.queryForInt(sql, namedParameters);




Sunday 13 May 2012
Podpora generik

  simpleJdbcTemplate = new SimpleJdbcTemplate(dataSource);
  String sql = "select id, first_name, last_name from T_ACTOR where id = ?";

  ParameterizedRowMapper<Actor> mapper = new ParameterizedRowMapper<Actor>() {
      	 public Actor mapRow(ResultSet rs, int rowNum) throws SQLException {
          Actor actor = new Actor();
          actor.setId(rs.getLong("id"));
          actor.setFirstName(rs.getString("first_name"));
          actor.setLastName(rs.getString("last_name"));
              return actor;
          }
      };

  Actor actor = simpleJdbcTemplate.queryForObject(sql, mapper, id);




Sunday 13 May 2012
Překlad výjimek
                     • Spring překládá checked výjimky
                       DAO tříd na vlastní rodinu
                       runtime výjimek




Sunday 13 May 2012

- překlad podle vendor codes
Překlad SQLException
                     • SQLException
                      • Spring zpracuje error code
                        • Namapování na konkrétní
                          DataAccessException
                     • Rozšiřitelné
                      • custom kódy z triggeru

Sunday 13 May 2012
Přidání custom error kódu

                     • classpath kontext v rootu sql-error-
                       codes.xml




Sunday 13 May 2012

default org/springframework/jdbc/support/sql-error-codes.xml
sql-error-codes.xml do rootu classpath
zkopirovat z originalu beanu/DB kterou chceme zmenit
Autom. překlad @Repository
          • Post-processor zajišťující         @Repository
                                               public class ProductDaoImpl implements
            automatický překlad                ProductDao {
            vyjímek na @Repository                   // class body here...
            třídách
                                               }

                • PersistenceExceptionTra
                  nslationPostProcessor        <beans>

                                                 <!--
                                                  Exception translation bean post processor
                • vytváří proxy                  -->
                                                 <bean
                                               class="org.springframework.dao.annotation.Pe
                                               rsistenceExceptionTranslationPostProcessor"/
                                               >

                                                   <bean class="product.ProductDaoImpl"/>

                                               </beans>


Sunday 13 May 2012

využití v případě, že pracujeme přímo s JDBC, Hibernatem, JPA případně dalšími
technologiemi podporovanými Spring frameworkem
SimpleJdbcInsert

  insertActor =
        new SimpleJdbcInsert(dataSource).withTableName("t_actor");

  Map<String, Object> parameters = new HashMap<String, Object>(3);
  parameters.put("id", actor.getId());
  parameters.put("first_name", actor.getFirstName());
  parameters.put("last_name", actor.getLastName());
  insertActor.execute(parameters);




Sunday 13 May 2012
Co dál


                     • BLOB/CLOB handling
                     • Connection extractor
                     • Podpora volání stored procedures
                     • ...


Sunday 13 May 2012
Batch updates

                     • Více update/insert příkazů
                      • menší počet round-trips do DB
                      • DB může lépe optimalizovat
                     • Použití pokud pracujeme s jednou
                       tabulkou


Sunday 13 May 2012
Batch updates




                         batch size=25


Sunday 13 May 2012
Batch updates - JdbcTemplate




Sunday 13 May 2012
BatchSqlUpdate




Sunday 13 May 2012
DAO Support
      • JdbcDaoSupport,
      • HibernateDaoSupport
      • JpaDaoSupport...
      • Každý z těchto objektů obsahuje třídu
        založenou na vzoru TemplateMethod
      • JdbcTemplate, HibernateTemplate

Sunday 13 May 2012

- automaticky preklad vyjimek
JPA




Sunday 13 May 2012
JPA == ORM
                     • ORM
                      • Object To Relational Mapping
                     • Snaží se řešit střet dvou světů
                      • Objektového a Relačního
                     • Není specifické pro Javu
                      • každý jazyk/platforma má svůj
                        ORM framework
Sunday 13 May 2012

- snaží se pomáhat při prekonávání rozdílů mezi Objektovým a Relačním světem
- odstínění od konkrétní databázove technologie
ORM přibližuje oba světy
          Svět objektů                               Svět relací a tabulek
                public class User {
                    private List<Order> orders;
                    private String email;
                    private String name;
                                                               User
                    private Address address;                       1
                                                                   *

                     private class Address {
                         private String street;
                                                              Order
                         private String zipCode;                   1

                     }                                             *

                }
                                                                Item
                public class Order {
                    private List<Item> orderItems;
                    private long number;
                }

                public class Item {
                    private long id;
                    private String name;
                }
Sunday 13 May 2012
ORM přibližuje oba světy
               Svět objektů                        ORM Svět relací a tabulek
                     public class User {
                         private List<Order> orders;
                         private String email;
                         private String name;
                                                                  User
                         private Address address;                     1
                                                                      *


                                                                  Order
                         private class Address {
                             private String street;
                             private String zipCode;                  1

                         }                                            *

                     }
                                                                   Item
                     public class Order {
                         private List<Item> orderItems;
                         private long number;
                     }

                     public class Item {
                         private long id;
                         private String name;
                     }
Sunday 13 May 2012
Agenda
                     • Představení JPA
                      • koncepce
                      • mapování
                      • dotazy
                     • Konfigurace EntityManageru
                     • Implementace JPA DAO

Sunday 13 May 2012
Koncept

                     • EntityManager
                      • Reprezentuje jednotku práce
                      • Umožňuje řídit lifeczcle
                        persistentních objektů
                       • vznik, aktualizaci, smazání


Sunday 13 May 2012
Koncept

                     • EntityManagerFactory
                       • thread-safe objekt
                       • reprezentuje jeden datový zdroj (DB)
                       • faktory pro EntityManager
                     • PersistenceUnit (persistence.xml)
                       • združuje skupinu persistentních tříd
                       • umožňue napojení na transakční
                         infrastrukturu
                       • konfiguruje JPA poskytovatele

Sunday 13 May 2012

persistence.xml musi lezet v rootu classpath
PersistentContext a EntityManager




Sunday 13 May 2012

- entity manager umoznuje pristup k persistentnimu contextu
- persistentni context predstavuje in-memory stav pers. entit a stara se o jeho synchronizaci
s databází
EntityManager API
            Metoda v EntityManager API                Popis                          SQL příkaz

                                         Přidání instance entity do
  persist(Entity instance)                                                 insert into table
                                         PersistenContext
                                         Odstranění entity z
  remove(Entity instance)                                                  delete from table where id=?
                                         PersistentContext
                                         Nahrání podle primárního
  find(Entity class, Primary key)                                          select * from table where id=?
                                         klíče
                                         Aktualizace stavu entity v
  merge(Entity instance)                                                   update table set ... where id=?
                                         PersistentContext
                                         Vytvoří objekt reprezentující
  createQuery(String jpql)
                                         dotaz
                                         Vynutí synchronizaci
  flush()
                                         PersistenContext s databází
                                         Transakce, zjištování existence
  další metody
                                         entity atd.


Sunday 13 May 2012
JPA Providers

                     • Implementace JPA specifikace
                      • EclipseLink/Toplink
                       • referenční implementace
                      • Apache OpenJPA
                      • Hibernate EntityManager


Sunday 13 May 2012
Hibernate JPA

                     • Hibernate EntityManager
                      • bridge pro JPA rozhrani
                     • Starý dobrý Hibernate pod
                       kapotou
                     • Lze používat Hibernate anotace
                       nad rámec JPA specifikace

Sunday 13 May 2012
JPA mapování
                     • Metadata pro popis vztahu
                      • Entita/Tabulka
                      • Field/Sloupec
                      • Vazby (one2one, one2many)
                      • Využití smart defaults
                        • pokud DB schéma
                          koresponduje s obj. modelem
Sunday 13 May 2012
Co můžeme anotovat
                     • Třídy
                      • propojení na tabulku
                      • aplikuje se na celou třídu pokud
                        na fieldech neřekneme jinak
                     • Fieldy
                      • propojení na sloupečky
                      • všechny fieldy jsou persitentí
                        • @Transient - exclude
Sunday 13 May 2012
Jednoduché mapování




Sunday 13 May 2012
Relační mapování




Sunday 13 May 2012

- podporovany vsechny mozne i nemozne způsoby mapování
JPA a dotazy


                     • Získání entity podle primárního
                       klíče
                     • Použití JPQL
                     • Použití SQL



Sunday 13 May 2012

- při použití SQL padá výhoda odstínění od konkrétní databáze, přesto je to někdy nutné
- pokud už musíte držte SQL kód na jednom místě
Získání entity primarním klíčem




Sunday 13 May 2012
Získání dotazem




Sunday 13 May 2012
Konfigurace EntityManagerFactory ve
                           Springu

                     • LocalEntityManagerFactoryBean
                     • LocalContainerEntityManagerFact
                       oryBean
                     • JNDI lookup
                     • Všechny vyžadují persisten.xml
                       pro konfiguraci

Sunday 13 May 2012
persistence.xml


                     • Vždy na classpath v META-INF
                     • Specifikuje persistence unit a
                       vendor konfiguraci




Sunday 13 May 2012
LocalEntityManagerFactoryBean



                     • Standalone aplikace, testy
                     • Nelze specifikovat datasource
                     • JPA provider určen z
                      •   META-INF/services/javax.persistence.spi.PersistenceProvider




Sunday 13 May 2012
LocalContainerEntityManagerFactoryBean

                 • Plně konfigurovatelné do nejmenších detailů
                     • Datasource a Vendor specific konfigurace




Sunday 13 May 2012
Jak funguje factory beana




Sunday 13 May 2012
JNDI lookup

                     • EntityManagerFactory se získá z
                       JNDI
                     • Použití v případe deploymentu do
                       AS




Sunday 13 May 2012
Implementace DAO

                     • Žadná závislost na Spring třídách
                      • nemusíme dědit
                      • inject @PersistentContext
                      • překlad vyjímek přes
                        • PersistentExceptionTranslationPostProces
                          sor


Sunday 13 May 2012
Ukázka DAO s překladem výjimek

                     @Repository
                     public class UserJPADao implements UserDao{

                         @PersitenceContext
                         private EntityManager entityManager;

                         public void saveUser(User user) {
                             entityManager.persiste(user);
                         }
                     }




Sunday 13 May 2012
• springdao projekt

                     • dodejte chybějící implementaci do

                       •   cz.sweb.pichlik.springdao.hibernate.UserStorageDaoHibernate


                       •   cz.sweb.pichlik.springdao.jdbc.UserStorageDaoJdbc



                     • samozřejmostí je zelený test

                       •   cz.sweb.pichlik.springdao.UserStorageDaoTest


                       •   cz.sweb.pichlik.springdao.hibernate.UserStorageDaoHibernateTest




Sunday 13 May 2012

ukazata konfiguraci Springu

Spring dao

  • 1.
    Spring framework Motto: Musíte rozbít vejce když chcete udělat omeletu Spring framework training materials by Roman Pichlík is licensed under a Creative Commons Attribution-ShareAlike 3.0 Unported License. Sunday 13 May 2012
  • 2.
    Přístup k datům Jak efektivně používat Spring framework pro přístup k datům Sunday 13 May 2012
  • 3.
    Práce s daty • Různé oblasti • Definice datového zdroje • Údržba zdrojů • Ošetření výjimek • Řízení transakcí Sunday 13 May 2012 - bez ohledu na použiti konkretního frameworku
  • 4.
  • 5.
    • Datasource jebeana • java.sql.Datasource • Lokální/Poskytovaný • JNDI aplikačního serveru Sunday 13 May 2012 - datasource participuje v dependency injection jako jákákoliv jiná beana
  • 6.
    Lokální datasource <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close"> <property name="driverClassName" value="org.hsqldb.jdbcDriver"/> <property name="url" value="jdbc:hsqldb:mem:test"/> <property name="username" value="sa"/> <property name="password" value=""/> </bean> • Connection pool s využitím • Apache DBCP http://commons.apache.org/dbcp/ • Pozor na DBCP v produkci • http://blog.novoj.net/2010/02/07/commons-dbcp-industrialni- standard-s-chybami/ Sunday 13 May 2012 - zduraznit, ze nezalezi na tom odkud pochazi trida, ktera reprezentuje datasource - DBCP alternativy C3PO, pool aplikacniho serveru (pokud to neni Tomcat)
  • 7.
    Lokální ds. proembedded DB • Spring 3.x namespace embedded DB • HSQL, H2, Derby • Inicializace skripty <jdbc:embedded-database id="dataSource"> <jdbc:script location="classpath:schema.sql"/> <jdbc:script location="classpath:test-data.sql"/> </jdbc:embedded-database> EmbeddedDatabaseBuilder builder = new EmbeddedDatabaseBuilder(); EmbeddedDatabase db = builder.setType(H2).addScript("schema.sql").addScript("test-data.sql").build(); // do stuff against the db (EmbeddedDatabase extends javax.sql.DataSource) db.shutdown() Sunday 13 May 2012 - rozsiritelne, muznost konfigurovat jinou embedded DB - programový i deklarativní způsob
  • 8.
    Data Access Object • Návrhový vzor pro přístup k datům • Pouze DAO implementuje logiku pro práci s DB • Motivace • změna implementace • odpovědnost v jedné vrstvě Sunday 13 May 2012
  • 9.
    Implementační možnosti • Přímé použití JDBC • ORM či Semi-ORM framework • JPA, Hibernate, iBatis, JDO... • Co budeme řešit • Konfigurace • Resource management • Exception handling Sunday 13 May 2012 - Spring všechny tyto věci řeší za nás - poskytuje high level API, které odstiňuje
  • 10.
  • 11.
    Co obnáší práces JDBC • Získání databázového připojení • Vytvoření java.sql.Statement • Nastavení parametru • Vykonání • Procházení výsledků a zpracování Sunday 13 May 2012
  • 12.
    Jak vypadá typickýkód Connection con = null; PreparedStatement ps = null; • Kde jsou problémy? ResultSet rs = null; try{ con = getConnection(); • NPE ignorujte ps = con.prepareStatement("select * x"); rs = ps.executeQuery(); while(rs.next()){ //zpracuj hodnoty } } catch(SQLException e) { throw new RuntimeException(e); } finally { try { rs.close(); ps.close(); con.close(); } catch(SQLException e) {} } Sunday 13 May 2012
  • 13.
    Jak vypadá typickýkód Connection con = null; PreparedStatement ps = null; • Kde jsou problémy? ResultSet rs = null; try{ con = getConnection(); • Často se opakující kód ps = con.prepareStatement("select * x"); rs = ps.executeQuery(); while(rs.next()){ //zpracuj hodnoty • Návrhový vzor } } catch(SQLException e) { Copy&Paste throw new RuntimeException(e); } finally { try { • Uvolnění zdrojů rs.close(); ps.close(); con.close(); • Míchání odpovědností } catch(SQLException e) {} } • Vykonání/Zpracování výsledku Sunday 13 May 2012
  • 14.
    Jak vypadá typickýkód Connection con = null; r u o PreparedStatement ps = null; • Kde jsou problémy? ResultSet rs = null; try{ v z m con = getConnection(); • Často se opakující kód é • Návrhový vzor ps = con.prepareStatement("select * x"); rs = ps.executeQuery(); v o h od h t Copy&Paste while(rs.next()){ r e //zpracuj hodnoty } } catch(SQLException e) { v á m } finally { n e • Uvolnění zdrojů throw new RuntimeException(e); v at je pl try { í m rs.close(); n e ps.close(); e T con.close(); • Míchání odpovědností } e š } catch(SQLException e) {} Ř • Vykonání/Zpracování výsledku Sunday 13 May 2012
  • 15.
    Template method • Společný kód v předkovi • Potomek přepisuje jenom to je pro něj specifické • zpracování výsledků Sunday 13 May 2012
  • 16.
  • 17.
    Klíčové abstrakce org.springframework.jdbc.core.JdbcTemplate org.springframework.jdbc.core.support.JdbcDaoSupport Sunday 13 May 2012 - resource management - exception handling
  • 18.
    JdbcTemplate • Centrální třídá pro práci s JDBC • Thread safe • Překlad výjimek • Resource management • Alternativy • org.springframework.jdbc.core.simple.SimpleJdbcTe mplate • org.springframework.jdbc.core.namedparam.NamedPar ameterJdbcTemplate Sunday 13 May 2012
  • 19.
  • 20.
    SQL introwCount = jdbcTemplate.queryForInt("select count(0) from t_accrual"); int countOfActorsNamedJoe = jdbcTemplate.queryForInt( "select count(0) from t_actors where first_name = ?", new Object[]{"Joe"} ); Actor actor = (Actor) jdbcTemplate.queryForObject( "select first_name, surname from t_actor where id = ?", new Object[]{new Long(1212)}, new RowMapper() { public Object mapRow(ResultSet rs, int rowNum) throws SQLException { Actor actor = new Actor(); actor.setFirstName(rs.getString("first_name")); actor.setSurname(rs.getString("surname")); return actor; } }); Sunday 13 May 2012
  • 21.
    DML a DDL jdbcTemplate.update( "insert into t_actor (first_name, surname) values (?, ?)", new Object[] {"Leonor", "Watling"}); jdbcTemplate.execute( "create table mytable (id integer, name varchar(100))"); Sunday 13 May 2012
  • 22.
    Pojmenované parametry NamedParameterJdbcTemplate namedParameterJdbcTemplate = new NamedParameterJdbcTemplate(dataSource); String sql = "select count(0) from T_ACTOR where first_name = :first_name"; Map namedParameters = new HashMap(); namedParameters.put("first_name", firstName); int count = namedParameterJdbcTemplate.queryForInt(sql, namedParameters); Sunday 13 May 2012
  • 23.
    Podpora generik simpleJdbcTemplate = new SimpleJdbcTemplate(dataSource); String sql = "select id, first_name, last_name from T_ACTOR where id = ?"; ParameterizedRowMapper<Actor> mapper = new ParameterizedRowMapper<Actor>() { public Actor mapRow(ResultSet rs, int rowNum) throws SQLException { Actor actor = new Actor(); actor.setId(rs.getLong("id")); actor.setFirstName(rs.getString("first_name")); actor.setLastName(rs.getString("last_name")); return actor; } }; Actor actor = simpleJdbcTemplate.queryForObject(sql, mapper, id); Sunday 13 May 2012
  • 24.
    Překlad výjimek • Spring překládá checked výjimky DAO tříd na vlastní rodinu runtime výjimek Sunday 13 May 2012 - překlad podle vendor codes
  • 25.
    Překlad SQLException • SQLException • Spring zpracuje error code • Namapování na konkrétní DataAccessException • Rozšiřitelné • custom kódy z triggeru Sunday 13 May 2012
  • 26.
    Přidání custom errorkódu • classpath kontext v rootu sql-error- codes.xml Sunday 13 May 2012 default org/springframework/jdbc/support/sql-error-codes.xml sql-error-codes.xml do rootu classpath zkopirovat z originalu beanu/DB kterou chceme zmenit
  • 27.
    Autom. překlad @Repository • Post-processor zajišťující @Repository public class ProductDaoImpl implements automatický překlad ProductDao { vyjímek na @Repository // class body here... třídách } • PersistenceExceptionTra nslationPostProcessor <beans> <!-- Exception translation bean post processor • vytváří proxy --> <bean class="org.springframework.dao.annotation.Pe rsistenceExceptionTranslationPostProcessor"/ > <bean class="product.ProductDaoImpl"/> </beans> Sunday 13 May 2012 využití v případě, že pracujeme přímo s JDBC, Hibernatem, JPA případně dalšími technologiemi podporovanými Spring frameworkem
  • 28.
    SimpleJdbcInsert insertActor= new SimpleJdbcInsert(dataSource).withTableName("t_actor"); Map<String, Object> parameters = new HashMap<String, Object>(3); parameters.put("id", actor.getId()); parameters.put("first_name", actor.getFirstName()); parameters.put("last_name", actor.getLastName()); insertActor.execute(parameters); Sunday 13 May 2012
  • 29.
    Co dál • BLOB/CLOB handling • Connection extractor • Podpora volání stored procedures • ... Sunday 13 May 2012
  • 30.
    Batch updates • Více update/insert příkazů • menší počet round-trips do DB • DB může lépe optimalizovat • Použití pokud pracujeme s jednou tabulkou Sunday 13 May 2012
  • 31.
    Batch updates batch size=25 Sunday 13 May 2012
  • 32.
    Batch updates -JdbcTemplate Sunday 13 May 2012
  • 33.
  • 34.
    DAO Support • JdbcDaoSupport, • HibernateDaoSupport • JpaDaoSupport... • Každý z těchto objektů obsahuje třídu založenou na vzoru TemplateMethod • JdbcTemplate, HibernateTemplate Sunday 13 May 2012 - automaticky preklad vyjimek
  • 35.
  • 36.
    JPA == ORM • ORM • Object To Relational Mapping • Snaží se řešit střet dvou světů • Objektového a Relačního • Není specifické pro Javu • každý jazyk/platforma má svůj ORM framework Sunday 13 May 2012 - snaží se pomáhat při prekonávání rozdílů mezi Objektovým a Relačním světem - odstínění od konkrétní databázove technologie
  • 37.
    ORM přibližuje obasvěty Svět objektů Svět relací a tabulek public class User { private List<Order> orders; private String email; private String name; User private Address address; 1 * private class Address { private String street; Order private String zipCode; 1 } * } Item public class Order { private List<Item> orderItems; private long number; } public class Item { private long id; private String name; } Sunday 13 May 2012
  • 38.
    ORM přibližuje obasvěty Svět objektů ORM Svět relací a tabulek public class User { private List<Order> orders; private String email; private String name; User private Address address; 1 * Order private class Address { private String street; private String zipCode; 1 } * } Item public class Order { private List<Item> orderItems; private long number; } public class Item { private long id; private String name; } Sunday 13 May 2012
  • 39.
    Agenda • Představení JPA • koncepce • mapování • dotazy • Konfigurace EntityManageru • Implementace JPA DAO Sunday 13 May 2012
  • 40.
    Koncept • EntityManager • Reprezentuje jednotku práce • Umožňuje řídit lifeczcle persistentních objektů • vznik, aktualizaci, smazání Sunday 13 May 2012
  • 41.
    Koncept • EntityManagerFactory • thread-safe objekt • reprezentuje jeden datový zdroj (DB) • faktory pro EntityManager • PersistenceUnit (persistence.xml) • združuje skupinu persistentních tříd • umožňue napojení na transakční infrastrukturu • konfiguruje JPA poskytovatele Sunday 13 May 2012 persistence.xml musi lezet v rootu classpath
  • 42.
    PersistentContext a EntityManager Sunday13 May 2012 - entity manager umoznuje pristup k persistentnimu contextu - persistentni context predstavuje in-memory stav pers. entit a stara se o jeho synchronizaci s databází
  • 43.
    EntityManager API Metoda v EntityManager API Popis SQL příkaz Přidání instance entity do persist(Entity instance) insert into table PersistenContext Odstranění entity z remove(Entity instance) delete from table where id=? PersistentContext Nahrání podle primárního find(Entity class, Primary key) select * from table where id=? klíče Aktualizace stavu entity v merge(Entity instance) update table set ... where id=? PersistentContext Vytvoří objekt reprezentující createQuery(String jpql) dotaz Vynutí synchronizaci flush() PersistenContext s databází Transakce, zjištování existence další metody entity atd. Sunday 13 May 2012
  • 44.
    JPA Providers • Implementace JPA specifikace • EclipseLink/Toplink • referenční implementace • Apache OpenJPA • Hibernate EntityManager Sunday 13 May 2012
  • 45.
    Hibernate JPA • Hibernate EntityManager • bridge pro JPA rozhrani • Starý dobrý Hibernate pod kapotou • Lze používat Hibernate anotace nad rámec JPA specifikace Sunday 13 May 2012
  • 46.
    JPA mapování • Metadata pro popis vztahu • Entita/Tabulka • Field/Sloupec • Vazby (one2one, one2many) • Využití smart defaults • pokud DB schéma koresponduje s obj. modelem Sunday 13 May 2012
  • 47.
    Co můžeme anotovat • Třídy • propojení na tabulku • aplikuje se na celou třídu pokud na fieldech neřekneme jinak • Fieldy • propojení na sloupečky • všechny fieldy jsou persitentí • @Transient - exclude Sunday 13 May 2012
  • 48.
  • 49.
    Relační mapování Sunday 13May 2012 - podporovany vsechny mozne i nemozne způsoby mapování
  • 50.
    JPA a dotazy • Získání entity podle primárního klíče • Použití JPQL • Použití SQL Sunday 13 May 2012 - při použití SQL padá výhoda odstínění od konkrétní databáze, přesto je to někdy nutné - pokud už musíte držte SQL kód na jednom místě
  • 51.
    Získání entity primarnímklíčem Sunday 13 May 2012
  • 52.
  • 53.
    Konfigurace EntityManagerFactory ve Springu • LocalEntityManagerFactoryBean • LocalContainerEntityManagerFact oryBean • JNDI lookup • Všechny vyžadují persisten.xml pro konfiguraci Sunday 13 May 2012
  • 54.
    persistence.xml • Vždy na classpath v META-INF • Specifikuje persistence unit a vendor konfiguraci Sunday 13 May 2012
  • 55.
    LocalEntityManagerFactoryBean • Standalone aplikace, testy • Nelze specifikovat datasource • JPA provider určen z • META-INF/services/javax.persistence.spi.PersistenceProvider Sunday 13 May 2012
  • 56.
    LocalContainerEntityManagerFactoryBean • Plně konfigurovatelné do nejmenších detailů • Datasource a Vendor specific konfigurace Sunday 13 May 2012
  • 57.
    Jak funguje factorybeana Sunday 13 May 2012
  • 58.
    JNDI lookup • EntityManagerFactory se získá z JNDI • Použití v případe deploymentu do AS Sunday 13 May 2012
  • 59.
    Implementace DAO • Žadná závislost na Spring třídách • nemusíme dědit • inject @PersistentContext • překlad vyjímek přes • PersistentExceptionTranslationPostProces sor Sunday 13 May 2012
  • 60.
    Ukázka DAO spřekladem výjimek @Repository public class UserJPADao implements UserDao{ @PersitenceContext private EntityManager entityManager; public void saveUser(User user) { entityManager.persiste(user); } } Sunday 13 May 2012
  • 61.
    • springdao projekt • dodejte chybějící implementaci do • cz.sweb.pichlik.springdao.hibernate.UserStorageDaoHibernate • cz.sweb.pichlik.springdao.jdbc.UserStorageDaoJdbc • samozřejmostí je zelený test • cz.sweb.pichlik.springdao.UserStorageDaoTest • cz.sweb.pichlik.springdao.hibernate.UserStorageDaoHibernateTest Sunday 13 May 2012 ukazata konfiguraci Springu