Search in sources :

Example 1 with AccessCallback

use of org.hibernate.id.enhanced.AccessCallback in project hibernate-orm by hibernate.

the class MultipleHiLoPerTableGenerator method generate.

public synchronized Serializable generate(final SharedSessionContractImplementor session, Object obj) {
    DeprecationLogger.DEPRECATION_LOGGER.deprecatedTableGenerator(getClass().getName());
    final SqlStatementLogger statementLogger = session.getFactory().getServiceRegistry().getService(JdbcServices.class).getSqlStatementLogger();
    final SessionEventListenerManager statsCollector = session.getEventListenerManager();
    final WorkExecutorVisitable<IntegralDataTypeHolder> work = new AbstractReturningWork<IntegralDataTypeHolder>() {

        @Override
        public IntegralDataTypeHolder execute(Connection connection) throws SQLException {
            IntegralDataTypeHolder value = IdentifierGeneratorHelper.getIntegralDataTypeHolder(returnClass);
            int rows;
            do {
                final PreparedStatement queryPreparedStatement = prepareStatement(connection, query, statementLogger, statsCollector);
                try {
                    final ResultSet rs = executeQuery(queryPreparedStatement, statsCollector);
                    boolean isInitialized = rs.next();
                    if (!isInitialized) {
                        value.initialize(0);
                        final PreparedStatement insertPreparedStatement = prepareStatement(connection, insert, statementLogger, statsCollector);
                        try {
                            value.bind(insertPreparedStatement, 1);
                            executeUpdate(insertPreparedStatement, statsCollector);
                        } finally {
                            insertPreparedStatement.close();
                        }
                    } else {
                        value.initialize(rs, 0);
                    }
                    rs.close();
                } catch (SQLException sqle) {
                    LOG.unableToReadOrInitHiValue(sqle);
                    throw sqle;
                } finally {
                    queryPreparedStatement.close();
                }
                final PreparedStatement updatePreparedStatement = prepareStatement(connection, update, statementLogger, statsCollector);
                try {
                    value.copy().increment().bind(updatePreparedStatement, 1);
                    value.bind(updatePreparedStatement, 2);
                    rows = executeUpdate(updatePreparedStatement, statsCollector);
                } catch (SQLException sqle) {
                    LOG.error(LOG.unableToUpdateHiValue(tableName), sqle);
                    throw sqle;
                } finally {
                    updatePreparedStatement.close();
                }
            } while (rows == 0);
            return value;
        }
    };
    // maxLo < 1 indicates a hilo generator with no hilo :?
    if (maxLo < 1) {
        // keep the behavior consistent even for boundary usages
        IntegralDataTypeHolder value = null;
        while (value == null || value.lt(1)) {
            value = session.getTransactionCoordinator().createIsolationDelegate().delegateWork(work, true);
        }
        return value.makeValue();
    }
    return hiloOptimizer.generate(new AccessCallback() {

        public IntegralDataTypeHolder getNextValue() {
            return session.getTransactionCoordinator().createIsolationDelegate().delegateWork(work, true);
        }

        @Override
        public String getTenantIdentifier() {
            return session.getTenantIdentifier();
        }
    });
}
Also used : AbstractReturningWork(org.hibernate.jdbc.AbstractReturningWork) SQLException(java.sql.SQLException) Connection(java.sql.Connection) JdbcServices(org.hibernate.engine.jdbc.spi.JdbcServices) PreparedStatement(java.sql.PreparedStatement) AccessCallback(org.hibernate.id.enhanced.AccessCallback) ResultSet(java.sql.ResultSet) SqlStatementLogger(org.hibernate.engine.jdbc.spi.SqlStatementLogger) SessionEventListenerManager(org.hibernate.engine.spi.SessionEventListenerManager)

Example 2 with AccessCallback

use of org.hibernate.id.enhanced.AccessCallback in project uPortal by Jasig.

the class HibernateStyleCounterStore method getNextIdInternal.

private int getNextIdInternal(final Optimizer optimizer, final String counterName) {
    return (Integer) optimizer.generate(new AccessCallback() {

        @Override
        public IntegralDataTypeHolder getNextValue() {
            IntegralDataTypeHolder rslt = null;
            for (int i = 0; rslt == null && i < MAX_ATTEMPTS; i++) {
                rslt = transactionOperations.execute(new TransactionCallback<IntegralDataTypeHolder>() {

                    @Override
                    public IntegralDataTypeHolder doInTransaction(TransactionStatus status) {
                        final IntegralDataTypeHolder value = IdentifierGeneratorHelper.getIntegralDataTypeHolder(identifierType.getReturnedClass());
                        // Try and load the current value,
                        // returns true if the expected row
                        // exists, null otherwise
                        final boolean selected = jdbcOperations.query(SELECT_QUERY, new ResultSetExtractor<Boolean>() {

                            @Override
                            public Boolean extractData(ResultSet rs) throws SQLException, DataAccessException {
                                if (rs.next()) {
                                    value.initialize(rs, 1);
                                    return true;
                                }
                                return false;
                            }
                        }, counterName);
                        // it
                        if (!selected) {
                            value.initialize(initialValue);
                            jdbcOperations.update(INSERT_QUERY, new PreparedStatementSetter() {

                                @Override
                                public void setValues(PreparedStatement ps) throws SQLException {
                                    ps.setString(1, counterName);
                                    value.bind(ps, 2);
                                }
                            });
                        }
                        // Increment the counter row value
                        final IntegralDataTypeHolder updateValue = value.copy();
                        if (optimizer.applyIncrementSizeToSourceValues()) {
                            updateValue.add(incrementSize);
                        } else {
                            updateValue.increment();
                        }
                        // Update the counter row, if rows
                        // returns 0 the update failed due to a
                        // race condition, it will be retried
                        int rowsAltered = jdbcOperations.update(UPDATE_QUERY, new PreparedStatementSetter() {

                            @Override
                            public void setValues(PreparedStatement ps) throws SQLException {
                                updateValue.bind(ps, 1);
                                ps.setString(2, counterName);
                                value.bind(ps, 3);
                            }
                        });
                        return rowsAltered > 0 ? // Success
                        value : // Failed;  try again...
                        null;
                    }
                });
            }
            if (rslt == null) {
                throw new RuntimeException("Failed to fetch a new batch of sequence values after " + MAX_ATTEMPTS + " tries");
            }
            return rslt;
        }
    });
}
Also used : SQLException(java.sql.SQLException) TransactionStatus(org.springframework.transaction.TransactionStatus) PreparedStatementSetter(org.springframework.jdbc.core.PreparedStatementSetter) PreparedStatement(java.sql.PreparedStatement) AccessCallback(org.hibernate.id.enhanced.AccessCallback) TransactionCallback(org.springframework.transaction.support.TransactionCallback) ResultSet(java.sql.ResultSet) IntegralDataTypeHolder(org.hibernate.id.IntegralDataTypeHolder) DataAccessException(org.springframework.dao.DataAccessException)

Aggregations

PreparedStatement (java.sql.PreparedStatement)2 ResultSet (java.sql.ResultSet)2 SQLException (java.sql.SQLException)2 AccessCallback (org.hibernate.id.enhanced.AccessCallback)2 Connection (java.sql.Connection)1 JdbcServices (org.hibernate.engine.jdbc.spi.JdbcServices)1 SqlStatementLogger (org.hibernate.engine.jdbc.spi.SqlStatementLogger)1 SessionEventListenerManager (org.hibernate.engine.spi.SessionEventListenerManager)1 IntegralDataTypeHolder (org.hibernate.id.IntegralDataTypeHolder)1 AbstractReturningWork (org.hibernate.jdbc.AbstractReturningWork)1 DataAccessException (org.springframework.dao.DataAccessException)1 PreparedStatementSetter (org.springframework.jdbc.core.PreparedStatementSetter)1 TransactionStatus (org.springframework.transaction.TransactionStatus)1 TransactionCallback (org.springframework.transaction.support.TransactionCallback)1