[jOOQ/jOOQ#12574] Add ExecuteContext::resultLevel and ::recordLevel to indicate the Result and Record nesting level

This commit is contained in:
Lukas Eder 2021-10-29 10:18:33 +02:00
parent a53a981331
commit a32222163c
6 changed files with 81 additions and 27 deletions

View File

@ -48,6 +48,7 @@ import java.util.stream.Collector;
import org.jooq.conf.Settings;
import org.jooq.conf.StatementType;
import org.jooq.exception.DataAccessException;
import org.jooq.impl.DSL;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@ -222,6 +223,15 @@ public interface ExecuteContext extends Scope {
*/
void resultSet(ResultSet resultSet);
/**
* The 0-based record nesting level for {@link #record()}, relevant when nested
* result events are triggered via
* {@link ExecuteListener#resultStart(ExecuteContext)} and
* {@link ExecuteListener#resultEnd(ExecuteContext)}, e.g. in the presence
* of {@link DSL#multiset(Select)}.
*/
int recordLevel();
/**
* The last record that was fetched from the result set, or
* <code>null</code> if no record has been fetched.
@ -269,6 +279,15 @@ public interface ExecuteContext extends Scope {
*/
int @NotNull [] batchRows();
/**
* The 0-based result nesting level for {@link #result()}, relevant when nested
* result events are triggered via
* {@link ExecuteListener#resultStart(ExecuteContext)} and
* {@link ExecuteListener#resultEnd(ExecuteContext)}, e.g. in the presence
* of {@link DSL#multiset(Select)}.
*/
int resultLevel();
/**
* The last result that was fetched from the result set, or
* <code>null</code> if no result has been fetched, including when results

View File

@ -813,6 +813,9 @@ public interface ExecuteListener extends EventListener, Serializable {
* is about to be fetched.</li>
* <li>{@link ExecuteContext#result()}: The set of records that are about to
* be fetched.</li>
* <li>{@link ExecuteContext#resultLevel()}: The result nesting level, in
* case the upcoming {@link ExecuteContext#result()} is a
* {@link DSL#multiset(Select)} or other type of nested result.</li>
* <li>{@link ExecuteContext#sqlWarning()}: The {@link SQLWarning} that was
* emitted by the database or <code>null</code> if no warning was
* emitted.</li>
@ -878,6 +881,10 @@ public interface ExecuteListener extends EventListener, Serializable {
* is about to be fetched.</li>
* <li>{@link ExecuteContext#record()}: The <code>Record</code> that is
* about to be fetched.</li>
* <li>{@link ExecuteContext#recordLevel()}: The record nesting level, in
* case the upcoming {@link ExecuteContext#record()} is a {@link Row} or
* other type of nested record. The level is also increased if a record is
* contained in a nested {@link ExecuteContext#result()}.</li>
* <li>{@link ExecuteContext#sqlWarning()}: The {@link SQLWarning} that was
* emitted by the database or <code>null</code> if no warning was
* emitted.</li>
@ -924,6 +931,10 @@ public interface ExecuteListener extends EventListener, Serializable {
* is about to be fetched.</li>
* <li>{@link ExecuteContext#record()}: The last <code>Record</code> that
* was fetched.</li>
* <li>{@link ExecuteContext#recordLevel()}: The record nesting level, in
* case the upcoming {@link ExecuteContext#record()} is a {@link Row} or
* other type of nested record. The level is also increased if a record is
* contained in a nested {@link ExecuteContext#result()}.</li>
* <li>{@link ExecuteContext#sqlWarning()}: The {@link SQLWarning} that was
* emitted by the database or <code>null</code> if no warning was
* emitted.</li>
@ -972,6 +983,9 @@ public interface ExecuteListener extends EventListener, Serializable {
* was fetched.</li>
* <li>{@link ExecuteContext#result()}: The set of records that were
* fetched.</li>
* <li>{@link ExecuteContext#resultLevel()}: The result nesting level, in
* case the upcoming {@link ExecuteContext#result()} is a
* {@link DSL#multiset(Select)} or other type of nested result.</li>
* <li>{@link ExecuteContext#sqlWarning()}: The {@link SQLWarning} that was
* emitted by the database or <code>null</code> if no warning was
* emitted.</li>

View File

@ -105,20 +105,21 @@ class DefaultExecuteContext implements ExecuteContext {
private final String[] batchSQL;
private final int[] batchRows;
// Transient attributes (created afresh per execution)
transient ConnectionProvider connectionProvider;
private transient Connection connection;
private transient SettingsEnabledConnection wrappedConnection;
private transient PreparedStatement statement;
private transient int statementExecutionCount;
private transient ResultSet resultSet;
private transient Record record;
private transient Result<?> result;
private transient int rows = -1;
private transient RuntimeException exception;
private transient SQLException sqlException;
private transient SQLWarning sqlWarning;
private transient String[] serverOutput;
ConnectionProvider connectionProvider;
private Connection connection;
private SettingsEnabledConnection wrappedConnection;
private PreparedStatement statement;
private int statementExecutionCount;
private ResultSet resultSet;
private Record record;
private Result<?> result;
int recordLevel;
int resultLevel;
private int rows = -1;
private RuntimeException exception;
private SQLException sqlException;
private SQLWarning sqlWarning;
private String[] serverOutput;
// ------------------------------------------------------------------------
// XXX: Static utility methods for handling blob / clob lifecycle
@ -591,6 +592,11 @@ class DefaultExecuteContext implements ExecuteContext {
return record;
}
@Override
public final int recordLevel() {
return recordLevel;
}
@Override
public final int rows() {
return rows;
@ -622,6 +628,11 @@ class DefaultExecuteContext implements ExecuteContext {
return result;
}
@Override
public final int resultLevel() {
return resultLevel;
}
@Override
public final RuntimeException exception() {
return exception;

View File

@ -223,22 +223,29 @@ final class ExecuteListeners implements ExecuteListener {
for (ExecuteListener listener : listeners[0])
listener.resultStart(ctx);
((DefaultExecuteContext) ctx).resultLevel++;
}
@Override
public final void recordStart(ExecuteContext ctx) {
for (ExecuteListener listener : listeners[0])
listener.recordStart(ctx);
((DefaultExecuteContext) ctx).recordLevel++;
}
@Override
public final void recordEnd(ExecuteContext ctx) {
((DefaultExecuteContext) ctx).recordLevel--;
for (ExecuteListener listener : listeners[1])
listener.recordEnd(ctx);
}
@Override
public final void resultEnd(ExecuteContext ctx) {
((DefaultExecuteContext) ctx).resultLevel--;
resultStart = false;
for (ExecuteListener listener : listeners[1])

View File

@ -142,6 +142,11 @@ final class SimpleExecuteContext extends AbstractScope implements ExecuteContext
throw new UnsupportedOperationException("Not implemented");
}
@Override
public final int recordLevel() {
throw new UnsupportedOperationException("Not implemented");
}
@Override
public final Record record() {
throw new UnsupportedOperationException("Not implemented");
@ -167,6 +172,11 @@ final class SimpleExecuteContext extends AbstractScope implements ExecuteContext
throw new UnsupportedOperationException("Not implemented");
}
@Override
public final int resultLevel() {
throw new UnsupportedOperationException("Not implemented");
}
@Override
public final Result<?> result() {
throw new UnsupportedOperationException("Not implemented");

View File

@ -65,8 +65,6 @@ import org.jooq.impl.DSL;
import org.jooq.impl.DefaultExecuteListener;
import org.jooq.impl.DefaultVisitListener;
import org.jetbrains.annotations.NotNull;
/**
* A default {@link ExecuteListener} that just logs events to java.util.logging,
* log4j, or slf4j using the {@link JooqLogger}
@ -131,19 +129,13 @@ public class LoggerListener extends DefaultExecuteListener {
}
}
// [#12564] Make sure we don't log any nested-level results or records
int recordLevel = 0;
int resultLevel = 0;
@Override
public void recordStart(ExecuteContext ctx) {
recordLevel++;
}
@SuppressWarnings("unchecked")
@Override
public void recordEnd(ExecuteContext ctx) {
if (--recordLevel > 0)
// [#12564] Make sure we don't log any nested-level results or records
if (ctx.recordLevel() > 0)
return;
if (log.isTraceEnabled() && ctx.record() != null)
@ -163,7 +155,6 @@ public class LoggerListener extends DefaultExecuteListener {
@Override
public void resultStart(ExecuteContext ctx) {
resultLevel++;
// [#10019] Don't buffer any records if it isn't needed
ctx.data(DO_BUFFER, false);
@ -171,7 +162,9 @@ public class LoggerListener extends DefaultExecuteListener {
@Override
public void resultEnd(ExecuteContext ctx) {
if (--resultLevel > 0)
// [#12564] Make sure we don't log any nested-level results or records
if (ctx.resultLevel() > 0)
return;
if (ctx.result() != null && log.isDebugEnabled()) {