Search in sources :

Example 1 with MapQueryLazyWorker

use of org.apache.ignite.internal.processors.query.h2.twostep.MapQueryLazyWorker in project ignite by apache.

the class GridMapQueryExecutor method onQueryRequest0.

/**
 * @param node Node authored request.
 * @param reqId Request ID.
 * @param segmentId index segment ID.
 * @param schemaName Schema name.
 * @param qrys Queries to execute.
 * @param cacheIds Caches which will be affected by these queries.
 * @param topVer Topology version.
 * @param partsMap Partitions map for unstable topology.
 * @param parts Explicit partitions for current node.
 * @param pageSize Page size.
 * @param distributedJoinMode Query distributed join mode.
 * @param lazy Streaming flag.
 */
private void onQueryRequest0(final ClusterNode node, final long reqId, final int segmentId, final String schemaName, final Collection<GridCacheSqlQuery> qrys, final List<Integer> cacheIds, final AffinityTopologyVersion topVer, final Map<UUID, int[]> partsMap, final int[] parts, final int pageSize, final DistributedJoinMode distributedJoinMode, final boolean enforceJoinOrder, final boolean replicated, final int timeout, final Object[] params, boolean lazy) {
    if (lazy && MapQueryLazyWorker.currentWorker() == null) {
        // Lazy queries must be re-submitted to dedicated workers.
        MapQueryLazyWorkerKey key = new MapQueryLazyWorkerKey(node.id(), reqId, segmentId);
        MapQueryLazyWorker worker = new MapQueryLazyWorker(ctx.igniteInstanceName(), key, log, this);
        worker.submit(new Runnable() {

            @Override
            public void run() {
                onQueryRequest0(node, reqId, segmentId, schemaName, qrys, cacheIds, topVer, partsMap, parts, pageSize, distributedJoinMode, enforceJoinOrder, replicated, timeout, params, true);
            }
        });
        if (lazyWorkerBusyLock.enterBusy()) {
            try {
                MapQueryLazyWorker oldWorker = lazyWorkers.put(key, worker);
                if (oldWorker != null)
                    oldWorker.stop();
                IgniteThread thread = new IgniteThread(worker);
                thread.start();
            } finally {
                lazyWorkerBusyLock.leaveBusy();
            }
        } else
            log.info("Ignored query request (node is stopping) [nodeId=" + node.id() + ", reqId=" + reqId + ']');
        return;
    }
    // Prepare to run queries.
    GridCacheContext<?, ?> mainCctx = !F.isEmpty(cacheIds) ? ctx.cache().context().cacheContext(cacheIds.get(0)) : null;
    MapNodeResults nodeRess = resultsForNode(node.id());
    MapQueryResults qr = null;
    List<GridReservable> reserved = new ArrayList<>();
    try {
        if (topVer != null) {
            // Reserve primary for topology version or explicit partitions.
            if (!reservePartitions(cacheIds, topVer, parts, reserved)) {
                // Unregister lazy worker because re-try may never reach this node again.
                if (lazy)
                    stopAndUnregisterCurrentLazyWorker();
                sendRetry(node, reqId, segmentId);
                return;
            }
        }
        qr = new MapQueryResults(h2, reqId, qrys.size(), mainCctx, MapQueryLazyWorker.currentWorker());
        if (nodeRess.put(reqId, segmentId, qr) != null)
            throw new IllegalStateException();
        // Prepare query context.
        GridH2QueryContext qctx = new GridH2QueryContext(ctx.localNodeId(), node.id(), reqId, segmentId, replicated ? REPLICATED : MAP).filter(h2.backupFilter(topVer, parts)).partitionsMap(partsMap).distributedJoinMode(distributedJoinMode).pageSize(pageSize).topologyVersion(topVer).reservations(reserved);
        Connection conn = h2.connectionForSchema(schemaName);
        H2Utils.setupConnection(conn, distributedJoinMode != OFF, enforceJoinOrder);
        GridH2QueryContext.set(qctx);
        // qctx is set, we have to release reservations inside of it.
        reserved = null;
        try {
            if (nodeRess.cancelled(reqId)) {
                GridH2QueryContext.clear(ctx.localNodeId(), node.id(), reqId, qctx.type());
                nodeRess.cancelRequest(reqId);
                throw new QueryCancelledException();
            }
            // Run queries.
            int qryIdx = 0;
            boolean evt = mainCctx != null && mainCctx.events().isRecordable(EVT_CACHE_QUERY_EXECUTED);
            for (GridCacheSqlQuery qry : qrys) {
                ResultSet rs = null;
                // If we are not the target node for this replicated query, just ignore it.
                if (qry.node() == null || (segmentId == 0 && qry.node().equals(ctx.localNodeId()))) {
                    rs = h2.executeSqlQueryWithTimer(conn, qry.query(), F.asList(qry.parameters(params)), true, timeout, qr.queryCancel(qryIdx));
                    if (evt) {
                        ctx.event().record(new CacheQueryExecutedEvent<>(node, "SQL query executed.", EVT_CACHE_QUERY_EXECUTED, CacheQueryType.SQL.name(), mainCctx.name(), null, qry.query(), null, null, params, node.id(), null));
                    }
                    assert rs instanceof JdbcResultSet : rs.getClass();
                }
                qr.addResult(qryIdx, qry, node.id(), rs, params);
                if (qr.cancelled()) {
                    qr.result(qryIdx).close();
                    throw new QueryCancelledException();
                }
                // Send the first page.
                sendNextPage(nodeRess, node, qr, qryIdx, segmentId, pageSize);
                qryIdx++;
            }
            // All request results are in the memory in result set already, so it's ok to release partitions.
            if (!lazy)
                releaseReservations();
        } catch (Throwable e) {
            releaseReservations();
            throw e;
        }
    } catch (Throwable e) {
        if (qr != null) {
            nodeRess.remove(reqId, segmentId, qr);
            qr.cancel(false);
        }
        // Unregister worker after possible cancellation.
        if (lazy)
            stopAndUnregisterCurrentLazyWorker();
        if (X.hasCause(e, GridH2RetryException.class))
            sendRetry(node, reqId, segmentId);
        else {
            U.error(log, "Failed to execute local query.", e);
            sendError(node, reqId, e);
            if (e instanceof Error)
                throw (Error) e;
        }
    } finally {
        if (reserved != null) {
            // Release reserved partitions.
            for (int i = 0; i < reserved.size(); i++) reserved.get(i).release();
        }
    }
}
Also used : ArrayList(java.util.ArrayList) Connection(java.sql.Connection) GridH2RetryException(org.apache.ignite.internal.processors.query.h2.opt.GridH2RetryException) GridReservable(org.apache.ignite.internal.processors.cache.distributed.dht.GridReservable) ResultSet(java.sql.ResultSet) JdbcResultSet(org.h2.jdbc.JdbcResultSet) IgniteThread(org.apache.ignite.thread.IgniteThread) GridCacheSqlQuery(org.apache.ignite.internal.processors.cache.query.GridCacheSqlQuery) QueryCancelledException(org.apache.ignite.cache.query.QueryCancelledException) GridH2QueryContext(org.apache.ignite.internal.processors.query.h2.opt.GridH2QueryContext) JdbcResultSet(org.h2.jdbc.JdbcResultSet)

Example 2 with MapQueryLazyWorker

use of org.apache.ignite.internal.processors.query.h2.twostep.MapQueryLazyWorker in project ignite by apache.

the class IgniteH2Indexing method executeSqlQuery.

/**
 * Executes sql query statement.
 *
 * @param conn Connection,.
 * @param stmt Statement.
 * @param timeoutMillis Query timeout.
 * @param cancel Query cancel.
 * @return Result.
 * @throws IgniteCheckedException If failed.
 */
private ResultSet executeSqlQuery(final Connection conn, final PreparedStatement stmt, int timeoutMillis, @Nullable GridQueryCancel cancel) throws IgniteCheckedException {
    final MapQueryLazyWorker lazyWorker = MapQueryLazyWorker.currentWorker();
    if (cancel != null) {
        cancel.set(new Runnable() {

            @Override
            public void run() {
                if (lazyWorker != null) {
                    lazyWorker.submit(new Runnable() {

                        @Override
                        public void run() {
                            cancelStatement(stmt);
                        }
                    });
                } else
                    cancelStatement(stmt);
            }
        });
    }
    Session ses = H2Utils.session(conn);
    if (timeoutMillis > 0)
        ses.setQueryTimeout(timeoutMillis);
    if (lazyWorker != null)
        ses.setLazyQueryExecution(true);
    try {
        return stmt.executeQuery();
    } catch (SQLException e) {
        // Throw special exception.
        if (e.getErrorCode() == ErrorCode.STATEMENT_WAS_CANCELED)
            throw new QueryCancelledException();
        throw new IgniteCheckedException("Failed to execute SQL query. " + e.getMessage(), e);
    } finally {
        if (timeoutMillis > 0)
            ses.setQueryTimeout(0);
        if (lazyWorker != null)
            ses.setLazyQueryExecution(false);
    }
}
Also used : IgniteCheckedException(org.apache.ignite.IgniteCheckedException) SQLException(java.sql.SQLException) IgniteSQLException(org.apache.ignite.internal.processors.query.IgniteSQLException) GridPlainRunnable(org.apache.ignite.internal.util.lang.GridPlainRunnable) MapQueryLazyWorker(org.apache.ignite.internal.processors.query.h2.twostep.MapQueryLazyWorker) QueryCancelledException(org.apache.ignite.cache.query.QueryCancelledException) Session(org.h2.engine.Session)

Aggregations

QueryCancelledException (org.apache.ignite.cache.query.QueryCancelledException)2 Connection (java.sql.Connection)1 ResultSet (java.sql.ResultSet)1 SQLException (java.sql.SQLException)1 ArrayList (java.util.ArrayList)1 IgniteCheckedException (org.apache.ignite.IgniteCheckedException)1 GridReservable (org.apache.ignite.internal.processors.cache.distributed.dht.GridReservable)1 GridCacheSqlQuery (org.apache.ignite.internal.processors.cache.query.GridCacheSqlQuery)1 IgniteSQLException (org.apache.ignite.internal.processors.query.IgniteSQLException)1 GridH2QueryContext (org.apache.ignite.internal.processors.query.h2.opt.GridH2QueryContext)1 GridH2RetryException (org.apache.ignite.internal.processors.query.h2.opt.GridH2RetryException)1 MapQueryLazyWorker (org.apache.ignite.internal.processors.query.h2.twostep.MapQueryLazyWorker)1 GridPlainRunnable (org.apache.ignite.internal.util.lang.GridPlainRunnable)1 IgniteThread (org.apache.ignite.thread.IgniteThread)1 Session (org.h2.engine.Session)1 JdbcResultSet (org.h2.jdbc.JdbcResultSet)1