SimpleJdbcCall игнорируя размер выборки JdbcTemplate - PullRequest
3 голосов
/ 09 марта 2010

Мы вызываем хранимую процедуру pl / sql через Spring SimpleJdbcCall, набор размеров выборки в JdbcTemplate игнорируется SimpleJdbcCall. Размер выборки результирующего набора строк установлен на 10, хотя мы установили размер выборки jdbctemplate равным 200. Любая идея, почему это происходит и как это исправить?

Распечатал размер выборки набора результатов в rowmapper в следующем фрагменте кода - как только это 200, а в другой раз 10, хотя я использую один и тот же JdbcTemplate в обоих случаях.

Это прямое выполнение через jdbctemplate возвращает размер выборки 200 в преобразователе строк

    jdbcTemplate = new JdbcTemplate(ds);
    jdbcTemplate.setResultsMapCaseInsensitive(true);
    jdbcTemplate.setFetchSize(200);

    List temp = jdbcTemplate.query("select 1 from dual", new ParameterizedRowMapper() {
        public Object mapRow(ResultSet resultSet, int i) throws SQLException {
            System.out.println("Direct template : " + resultSet.getFetchSize());
            return new String(resultSet.getString(1));
        }
    });

Это выполнение через SimpleJdbcCall всегда возвращает размер выборки 10 в rowmapper

jdbcCall = new SimpleJdbcCall(jdbcTemplate).withSchemaName(schemaName)
                .withCatalogName(catalogName).withProcedureName(functionName);
jdbcCall.returningResultSet((String) outItValues.next(), new        ParameterizedRowMapper<Map<String, Object>>() {
                public Map<String, Object> mapRow(ResultSet rs, int row) throws SQLException {
                   System.out.println("Through simplejdbccall " + rs.getFetchSize());
                    return extractRS(rs, row);
                }
            });
outputList = (List<Map<String, Object>>) jdbcCall.executeObject(List.class, inParam);

Ответы [ 3 ]

4 голосов
/ 09 марта 2010

Я не уверен, насколько доверять методу getFetchSize() на ResultSet. JdbcTemplate вызывает setFetchSize() на Statement и предполагает, что драйвер JDBC сделает с ним все правильно, включая распространение его на все ResultSet объекты. Похоже, что драйвер Oracle JDBC в этом случае не является.

Причина, по которой вы получаете различное поведение от двух подходов, состоит в том, что выполнение простого SELECT - JdbcTemplate является простым JDBC, тогда как ResultSet, который вы возвращаете из SimpleJdbcCall, получается как параметр OUT для вызова , Последнее является более сложным, и кажется, что информация теряется.

В качестве обходного пути, вы пытались назвать ResultSet.setFetchSize() самостоятельно? Это может не сработать, но оно того стоит. Вы также можете отправить вопрос по номеру http://jira.springsource.org/, чтобы узнать, считают ли они, что уровень JDBC в Spring может решить эту проблему прозрачно.

2 голосов
/ 01 апреля 2010

Если вы хотите ограничить число строк, возвращаемых с Oracle, вы должны использовать запрос на выборку и указать начальное и конечное количество строк, например:

SELECT * FROM (SELECT ROWNUM as id, demo.* FROM DEMO_TABLE demo)
WHERE id >= startRowNumber AND id <= stopRowNumber; 

Если вам не нужен какой-либо специфичный для Oracle код, вам следует рассмотреть JPA вместо JDBC:

Query selectQuery = entityManager.createQuery(queryString);
selectQuery.setMaxResults(maxNumberOfElements);
selectQuery.setFirstResult(startRowNumber);
List demoList = entityManager.getResultList(queryString);
0 голосов
/ 10 марта 2010

Не прямой ответ, но полезная вещь, я думаю. Когда вы создаете объекты классов Spring вручную, большинство людей, как правило, забывают вызвать метод afterPropertiesSet () (который вызывается Spring для выполнения любой инициализации).

Я проверил jdbcTemplate.afterPropertiesSet (), кажется, он только устанавливает транслятор исключений и источник данных.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...