Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Java: Общие вопросы > Hibernate выводит одну строку несколько раз.


Автор: dEEp 21.5.2009, 19:01
Код

        Session session = HibernateUtil.getSessionFactory().getCurrentSession();
        session.beginTransaction();
        List list = session.createQuery("from Edge as edge where edge.id = ?").setInteger(0, 820521).list();
        session.getTransaction().commit();
        for (int i = 0; i < list.size(); i++) {
            Edge edge = (Edge) list.get(i);
            System.out.println("id: " + edge.getId() +
                            " x: " + edge.getX() +
                            " y: " + edge.getY());
        }
        HibernateUtil.getSessionFactory().close();


думаю в коде всё ясно. пытаемся получить все записи, удовлетворяющие запросу. Дело в том, что получаю результат:

Код

id: 820521 x: -3003.62 y: 6307.59
id: 820521 x: -3003.62 y: 6307.59
id: 820521 x: -3003.62 y: 6307.59


А кординаты должны быть разные. В базе всё хорошо. Пробовал сделать аналогично сделать вывод с использвоанием Spring'a, так там всё хорошо.

Кстати говоря, кол-во строк нормальное. Т.е. должны быть выведены 3 строки с одинаковым естесственно id и разными координатами.

У кого-нибудь есть мысли, почему так возникает?
Если нужны конф.файлы - выложу. 

Автор: AntonSaburov 21.5.2009, 19:13
Похоже,  что джойнится еще одна таблица из-за какой-нибудь связи. Хорошо бы посмотреть оригинальный SQL, который генерится.

Мы решали что-то вроде

Criteria cr = session.createCriteria(StockTable.class);        
cr.setResultTransformer(CriteriaSpecification.DISTINCT_ROOT_ENTITY);



Автор: dEEp 21.5.2009, 19:22
а генерит он вот что:
Код

select edge0_.id as id0_, edge0_.x as x0_, edge0_.y as y0_
from v_road_graph edge0_ 
where edge0_.id=?


т.е. всё хорошо.


Edge.hbm.xml

Код

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
        "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
        "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">

<hibernate-mapping>

    <class name="com.msi.tsp.graph.pojo.Edge" table="v_road_graph">
        <id name="id" column="id"/>
        <property name="x" column="x"/>
        <property name="y" column="y"/>
    </class>

</hibernate-mapping>



hibernate.cfg.xml

Код

<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE hibernate-configuration PUBLIC
        "-//Hibernate/Hibernate Configuration DTD 3.0//EN"
        "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">

<hibernate-configuration>
    <session-factory>
        <property name="connection.driver_class">oracle.jdbc.driver.OracleDriver</property>
        <property name="connection.url">jdbc:oracle:thin:@[вырезано]</property>
        <property name="connection.username">[вырезано]</property>
        <property name="connection.password">[вырезано]</property>
        <property name="dialect">org.hibernate.dialect.OracleDialect</property>
        <property name="current_session_context_class">thread</property>
        <property name="show_sql">true</property>
        <mapping resource="Edge.hbm.xml"/>
    </session-factory>
</hibernate-configuration>


про "Criteria..." понял. Но это не помогло.

Код

cr.setResultTransformer(CriteriaSpecification.DISTINCT_ROOT_ENTITY);

это убрал. мне как раз и нужны эти 3 записи, но с разными координатами. А так получится запись будет одна.

Автор: dEEp 21.5.2009, 19:56
люди, хотя бы скажите что это может быть. вряд ли джойнится лишняя таблица. я полагаю что это специфика hibernate. возможно он полагает, что если поиск идёт по id, то запись будет одна. тогда странно, что выводит её трижды.

Автор: Старовъръ 22.5.2009, 00:23
Кто ж делает Id неуникальным? Без нормьного id падает производительность да и логика страдает)) Создай нормальный id, а если тебе еще какой-то вторичный id нужен, то сделай еще одно поле в классе.

Автор: Kangaroo 22.5.2009, 03:04
Включи полные логи Хайбернета и попробуй проследить по ним весь путь - от выполнения запроса до сохранения результа в список.

Автор: dEEp 22.5.2009, 12:56
Цитата(Kangaroo @  22.5.2009,  03:04 Найти цитируемый пост)
Включи полные логи Хайбернета и попробуй проследить по ним весь путь - от выполнения запроса до сохранения результа в список. 

пока этого не делал, но сделаю. Сейчас объяснили, что это из-за ключа, который не является уникальным. Предложили сделать объединение через composite-id, но пока не разобрался как и чего с ним делать.

Цитата(Старовъръ @  22.5.2009,  00:23 Найти цитируемый пост)
Кто ж делает Id неуникальным? Без нормьного id падает производительность да и логика страдает)) Создай нормальный id, а если тебе еще какой-то вторичный id нужен, то сделай еще одно поле в классе. 

о да! а то я не знаю что id должен быть уникальным. вы как ребёнку объясняете. Вот такой есть id и его править не могу. Вообще базу трогать не могу. Моя задача подрубиться к базе через Hibernate. А до того что там в базе написано всё криво - мне нет дела. На Spring'ах вообще пробелм не возникает. Но нужен Hibernate.

Автор: AntonSaburov 22.5.2009, 13:01
А на одноколесном велосипеде вокруг мира не надо ? smile
У каждого пакета и технолоогии есть определенные ограничения. И если у тебя ID не уникальный - то Hibernate тут работать нормально не сможет. Либо пиши свой собсвтенный.
Как-то странно выглядит - надо на Hibernate и все тут. Кстати причем тут Spring - я не понял. 

Автор: dEEp 22.5.2009, 13:09
Цитата(AntonSaburov @  22.5.2009,  13:01 Найти цитируемый пост)
А на одноколесном велосипеде вокруг мира не надо ? 

такой задачи не стояло. smile

Цитата(AntonSaburov @  22.5.2009,  13:01 Найти цитируемый пост)
У каждого пакета и технолоогии есть определенные ограничения. И если у тебя ID не уникальный - то Hibernate тут работать нормально не сможет. Либо пиши свой собсвтенный.

сказали composite-id спасёт. тем более учитывая то, что максимум что от базы надо - выборка с параметром и всё.

Цитата(AntonSaburov @  22.5.2009,  13:01 Найти цитируемый пост)
Как-то странно выглядит - надо на Hibernate и все тут. 

Ну как сказали, так и делаю. 

Цитата(AntonSaburov @  22.5.2009,  13:01 Найти цитируемый пост)
Кстати причем тут Spring - я не понял.  

JdbcTemplate (http://static.springframework.org/spring/docs/2.5.x/reference/jdbc.html)

Автор: Старовъръ 22.5.2009, 13:26
Цитата

JdbcTemplate (http://static.springframework.org/spring/docs/2.5.x/reference/jdbc.html) 
Ну это собственно не Спринг спасает, а ЖДБС.
Цитата

Ну как сказали, так и делаю.
А намекнуть директору(или кому еще) нельзя насчет "неактуальности" принятого решения?
В Хибернете есть возможность делать sql-запросы. Look http://swik.net/Hibernate/Using+SQL+From+Within+Hibernate. Полагаю это может спасти

Автор: dEEp 22.5.2009, 13:30
Цитата(Старовъръ @  22.5.2009,  13:26 Найти цитируемый пост)
Ну это собственно не Спринг спасает, а ЖДБС.

Ну это понятно. Там по сути более "крутой" jdbc.

Цитата(Старовъръ @  22.5.2009,  13:26 Найти цитируемый пост)
А намекнуть директору(или кому еще) нельзя насчет "неактуальности" принятого решения? 

нужно обоснование. в документации hibernate я не нашёл, что он не умеет работать с таблицами, в которых ключ не уникален. если найти мануал, то можно попытать удачу.

Цитата(Старовъръ @  22.5.2009,  13:26 Найти цитируемый пост)

В Хибернете есть возможность делать sql-запросы. Look here. Полагаю это может спасти 

проблемы это не решает. так я мог бы и с JDBC решить всё.

Автор: Старовъръ 22.5.2009, 13:50
Цитата

нужно обоснование. в документации hibernate я не нашёл, что он не умеет работать с таблицами, в которых ключ не уникален. если найти мануал, то можно попытать удачу.
http://www.velocityreviews.com/forums/t140092-hibernate-to-legacy-db-with-no-id-columns.html вроде об этом.
Цитата

проблемы это не решает. так я мог бы и с JDBC решить всё. 
Ты ж говорил, что обязательно нужен Хибернет!

Автор: dEEp 22.5.2009, 13:53
Цитата(Старовъръ @  22.5.2009,  13:50 Найти цитируемый пост)
Вот вроде об этом.

читаю...

Цитата(Старовъръ @  22.5.2009,  13:50 Найти цитируемый пост)
Ты ж говорил, что обязательно нужен Хибернет! 

ну мог бы, но не делаю из-за жестких требований.

Автор: dEEp 22.5.2009, 15:19
Всё ребят. Спасибо вам всем большое. Сейчас правят базу. Будет уникальный id. Спасение нашлось. =)

Поднял бы вам всем репутацию, но не могу. Постов мало.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)