Add progress-handler support to JNI wrapper1. Correct the return type of the extended_result_codes() JNI binding and expose it to wrapper1.

FossilOrigin-Name: 6c0acfdce2160d8db261a59677cec571b6abc333481525b1ec975d98e88bec88
This commit is contained in:
stephan 2023-11-05 01:39:29 +00:00
parent 0ee7ae72a1
commit 9a26589940
8 changed files with 142 additions and 78 deletions

View File

@ -3596,12 +3596,14 @@ S3JniApi(sqlite3_normalized_sql(),jstring,1normalized_1sql)(
#endif
}
S3JniApi(sqlite3_extended_result_codes(),jboolean,1extended_1result_1codes)(
S3JniApi(sqlite3_extended_result_codes(),jint,1extended_1result_1codes)(
JniArgsEnvClass, jobject jpDb, jboolean onoff
){
sqlite3 * const pDb = PtrGet_sqlite3(jpDb);
int const rc = pDb ? sqlite3_extended_result_codes(pDb, onoff ? 1 : 0) : 0;
return rc ? JNI_TRUE : JNI_FALSE;
int const rc = pDb
? sqlite3_extended_result_codes(pDb, onoff ? 1 : 0)
: SQLITE_MISUSE;
return rc;
}
S3JniApi(sqlite3_finalize(),jint,1finalize)(

View File

@ -1402,9 +1402,9 @@ JNIEXPORT jint JNICALL Java_org_sqlite_jni_capi_CApi_sqlite3_1extended_1errcode
/*
* Class: org_sqlite_jni_capi_CApi
* Method: sqlite3_extended_result_codes
* Signature: (Lorg/sqlite/jni/capi/sqlite3;Z)Z
* Signature: (Lorg/sqlite/jni/capi/sqlite3;Z)I
*/
JNIEXPORT jboolean JNICALL Java_org_sqlite_jni_capi_CApi_sqlite3_1extended_1result_1codes
JNIEXPORT jint JNICALL Java_org_sqlite_jni_capi_CApi_sqlite3_1extended_1result_1codes
(JNIEnv *, jclass, jobject, jboolean);
/*

View File

@ -890,7 +890,7 @@ public final class CApi {
return sqlite3_extended_errcode(db.getNativePointer());
}
public static native boolean sqlite3_extended_result_codes(
public static native int sqlite3_extended_result_codes(
@NotNull sqlite3 db, boolean on
);

View File

@ -213,61 +213,6 @@ public final class Sqlite implements AutoCloseable {
return CApi.sqlite3_sourceid();
}
/**
Output object for use with status() and libStatus().
*/
public static final class Status {
/** The current value for the requested status() or libStatus() metric. */
long current;
/** The peak value for the requested status() or libStatus() metric. */
long peak;
};
/**
As per sqlite3_status64(), but returns its current and high-water
results as a Status object. Throws if the first argument is
not one of the STATUS_... constants.
*/
public static Status libStatus(int op, boolean resetStats){
org.sqlite.jni.capi.OutputPointer.Int64 pCurrent =
new org.sqlite.jni.capi.OutputPointer.Int64();
org.sqlite.jni.capi.OutputPointer.Int64 pHighwater =
new org.sqlite.jni.capi.OutputPointer.Int64();
checkRc2( CApi.sqlite3_status64(op, pCurrent, pHighwater, resetStats) );
final Status s = new Status();
s.current = pCurrent.value;
s.peak = pHighwater.value;
return s;
}
/**
As per sqlite3_status64(), but returns its current and high-water
results as a Status object. Throws if the first argument is
not one of the DBSTATUS_... constants or on any other misuse.
*/
public Status status(int op, boolean resetStats){
org.sqlite.jni.capi.OutputPointer.Int32 pCurrent =
new org.sqlite.jni.capi.OutputPointer.Int32();
org.sqlite.jni.capi.OutputPointer.Int32 pHighwater =
new org.sqlite.jni.capi.OutputPointer.Int32();
checkRc( CApi.sqlite3_db_status(thisDb(), op, pCurrent, pHighwater, resetStats) );
final Status s = new Status();
s.current = pCurrent.value;
s.peak = pHighwater.value;
return s;
}
@Override public void close(){
if(null!=this.db){
synchronized(nativeToWrapper){
nativeToWrapper.remove(this.db);
}
this.db.close();
this.db = null;
}
}
/**
Returns the value of the native library's build-time value of the
SQLITE_THREADSAFE build option.
@ -325,6 +270,61 @@ public final class Sqlite implements AutoCloseable {
return 0==CApi.sqlite3_strlike(glob, txt, escChar);
}
/**
Output object for use with status() and libStatus().
*/
public static final class Status {
/** The current value for the requested status() or libStatus() metric. */
long current;
/** The peak value for the requested status() or libStatus() metric. */
long peak;
};
/**
As per sqlite3_status64(), but returns its current and high-water
results as a Status object. Throws if the first argument is
not one of the STATUS_... constants.
*/
public static Status libStatus(int op, boolean resetStats){
org.sqlite.jni.capi.OutputPointer.Int64 pCurrent =
new org.sqlite.jni.capi.OutputPointer.Int64();
org.sqlite.jni.capi.OutputPointer.Int64 pHighwater =
new org.sqlite.jni.capi.OutputPointer.Int64();
checkRc2( CApi.sqlite3_status64(op, pCurrent, pHighwater, resetStats) );
final Status s = new Status();
s.current = pCurrent.value;
s.peak = pHighwater.value;
return s;
}
/**
As per sqlite3_db_status(), but returns its current and
high-water results as a Status object. Throws if the first
argument is not one of the DBSTATUS_... constants or on any other
misuse.
*/
public Status status(int op, boolean resetStats){
org.sqlite.jni.capi.OutputPointer.Int32 pCurrent =
new org.sqlite.jni.capi.OutputPointer.Int32();
org.sqlite.jni.capi.OutputPointer.Int32 pHighwater =
new org.sqlite.jni.capi.OutputPointer.Int32();
checkRc( CApi.sqlite3_db_status(thisDb(), op, pCurrent, pHighwater, resetStats) );
final Status s = new Status();
s.current = pCurrent.value;
s.peak = pHighwater.value;
return s;
}
@Override public void close(){
if(null!=this.db){
synchronized(nativeToWrapper){
nativeToWrapper.remove(this.db);
}
this.db.close();
this.db = null;
}
}
/**
Returns this object's underlying native db handle, or null if
this instance has been closed. This is very specifically not
@ -379,6 +379,19 @@ public final class Sqlite implements AutoCloseable {
}
}
/**
Toggles the use of extended result codes on or off. By default
they are turned off, but they can be enabled by default by
including the OPEN_EXRESCODE flag when opening a database.
Because this API reports db-side errors using exceptions,
enabling this may change the values returned by
SqliteException.errcode().
*/
public void useExtendedResultCodes(boolean on){
checkRc( CApi.sqlite3_extended_result_codes(thisDb(), on) );
}
/**
prepFlags must be 0 or a bitmask of the PREPARE_... constants.
@ -1278,7 +1291,7 @@ public final class Sqlite implements AutoCloseable {
Analog to sqlite3_busy_handler(). If b is null then any
current handler is cleared.
*/
void setBusyHandler( BusyHandler b ){
public void setBusyHandler( BusyHandler b ){
org.sqlite.jni.capi.BusyHandlerCallback bhc = null;
if( null!=b ){
bhc = new org.sqlite.jni.capi.BusyHandlerCallback(){
@ -1328,7 +1341,7 @@ public final class Sqlite implements AutoCloseable {
handle is only manipulated via the high-level API, this caveat
does not apply.
*/
CommitHook setCommitHook( CommitHook c ){
public CommitHook setCommitHook( CommitHook c ){
CommitHookProxy chp = null;
if( null!=c ){
chp = new CommitHookProxy(c);
@ -1377,7 +1390,7 @@ public final class Sqlite implements AutoCloseable {
handle is only manipulated via the high-level API, this caveat
does not apply.
*/
RollbackHook setRollbackHook( RollbackHook c ){
public RollbackHook setRollbackHook( RollbackHook c ){
RollbackHookProxy chp = null;
if( null!=c ){
chp = new RollbackHookProxy(c);
@ -1426,7 +1439,7 @@ public final class Sqlite implements AutoCloseable {
handle is only manipulated via the high-level API, this caveat
does not apply.
*/
UpdateHook setUpdateHook( UpdateHook c ){
public UpdateHook setUpdateHook( UpdateHook c ){
UpdateHookProxy chp = null;
if( null!=c ){
chp = new UpdateHookProxy(c);
@ -1438,4 +1451,35 @@ public final class Sqlite implements AutoCloseable {
: null;
}
/**
Callback interface for use with setProgressHandler().
*/
public interface ProgressHandler {
/**
Must behave as documented for the C-level sqlite3_progress_handler()
callback. If it throws, the exception is translated into
a db-level error.
*/
int call();
}
/**
Analog to sqlite3_progress_handler(), sets the current progress
handler or clears it if p is null.
Note that this API, in contrast to setUpdateHook(),
setRollbackHook(), and setCommitHook(), cannot return the
previous handler. That inconsistency is part of the lower-level C
API.
*/
public void setProgressHandler( int n, ProgressHandler p ){
org.sqlite.jni.capi.ProgressHandlerCallback phc = null;
if( null!=p ){
phc = new org.sqlite.jni.capi.ProgressHandlerCallback(){
@Override public int call(){ return p.call(); }
};
}
CApi.sqlite3_progress_handler( thisDb(), n, phc );
}
}

View File

@ -50,7 +50,7 @@ public final class SqliteException extends java.lang.RuntimeException {
/**
Records the current error state of db (which must not be null and
must refer to an opened db object). Note that this does NOT close
must refer to an opened db object). Note that this does not close
the db.
Design note: closing the db on error is really only useful during

View File

@ -870,6 +870,24 @@ public class Tester2 implements Runnable {
db.close();
}
private void testProgress(){
final Sqlite db = openDb();
final ValueHolder<Integer> counter = new ValueHolder<>(0);
db.setProgressHandler(1, new Sqlite.ProgressHandler(){
@Override public int call(){
++counter.value;
return 0;
}
});
execSql(db, "SELECT 1; SELECT 2;");
affirm( counter.value > 0 );
int nOld = counter.value;
db.setProgressHandler(0, null);
execSql(db, "SELECT 1; SELECT 2;");
affirm( nOld == counter.value );
db.close();
}
private void runTests(boolean fromThread) throws Exception {
List<java.lang.reflect.Method> mlist = testMethods;
affirm( null!=mlist );

View File

@ -1,5 +1,5 @@
C Add\supdate-hook\ssupport\sto\sJNI\swrapper1.
D 2023-11-05T01:14:07.152
C Add\sprogress-handler\ssupport\sto\sJNI\swrapper1.\sCorrect\sthe\sreturn\stype\sof\sthe\sextended_result_codes()\sJNI\sbinding\sand\sexpose\sit\sto\swrapper1.
D 2023-11-05T01:39:29.450
F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
F LICENSE.md df5091916dbb40e6e9686186587125e1b2ff51f022cc334e886c19a0e9982724
@ -241,8 +241,8 @@ F ext/icu/sqliteicu.h fa373836ed5a1ee7478bdf8a1650689294e41d0c89c1daab26e9ae78a3
F ext/jni/GNUmakefile 36919b7c4fb8447da4330df9996c7b064b766957f8b7be214a30eab55a8b8072
F ext/jni/README.md ef9ac115e97704ea995d743b4a8334e23c659e5534c3b64065a5405256d5f2f4
F ext/jni/jar-dist.make 030aaa4ae71dd86e4ec5e7c1e6cd86f9dfa47c4592c070d2e35157e42498e1fa
F ext/jni/src/c/sqlite3-jni.c e24804e86759c0680064aacc46ab901d9b2b1a44eba312bcc9a387f15f044d12
F ext/jni/src/c/sqlite3-jni.h 1c45fd4689cec42f3d84d2fee41bb494016a12fcb5fd80291095590666a14015
F ext/jni/src/c/sqlite3-jni.c b98d822a35ef4438023c3c14816b5ac17bdbd23bc838ff80b6463c3146a75d14
F ext/jni/src/c/sqlite3-jni.h 03f66d3b43359dacd7c2c9407d78274dbdb027bc7610985011bf2b462222414e
F ext/jni/src/org/sqlite/jni/annotation/NotNull.java a99341e88154e70447596b1af6a27c586317df41a7e0f246fd41370cd7b723b2
F ext/jni/src/org/sqlite/jni/annotation/Nullable.java 0b1879852707f752512d4db9d7edd0d8db2f0c2612316ce1c832715e012ff6ba
F ext/jni/src/org/sqlite/jni/annotation/package-info.java 977b374aed9d5853cbf3438ba3b0940abfa2ea4574f702a2448ee143b98ac3ca
@ -251,7 +251,7 @@ F ext/jni/src/org/sqlite/jni/capi/AggregateFunction.java 0b72cdff61533b564d65b63
F ext/jni/src/org/sqlite/jni/capi/AuthorizerCallback.java 7ed409d5449684616cc924534e22ff6b07d361f12ad904b69ecb10e0568a8013
F ext/jni/src/org/sqlite/jni/capi/AutoExtensionCallback.java 74cc4998a73d6563542ecb90804a3c4f4e828cb4bd69e61226d1a51f4646e759
F ext/jni/src/org/sqlite/jni/capi/BusyHandlerCallback.java 7b8e19810c42b0ad21a04b5d8c804b32ee5905d137148703f16a75b612c380ca
F ext/jni/src/org/sqlite/jni/capi/CApi.java 4043d709626079cce6d524ef49122b934c043022bd88bc1e72eb697ac8df86e7
F ext/jni/src/org/sqlite/jni/capi/CApi.java a6d4fdd35e4fcfe95c61e343eb389cfaab3d5166e9670730aef14240a982b97b
F ext/jni/src/org/sqlite/jni/capi/CallbackProxy.java 57e2d275dcebe690b1fc1f3d34eb96879b2d7039bce30b563aee547bf45d8a8b
F ext/jni/src/org/sqlite/jni/capi/CollationCallback.java e29bcfc540fdd343e2f5cca4d27235113f2886acb13380686756d5cabdfd065a
F ext/jni/src/org/sqlite/jni/capi/CollationNeededCallback.java 5bfa226a8e7a92e804fd52d6e42b4c7b875fa7a94f8e2c330af8cc244a8920ab
@ -296,9 +296,9 @@ F ext/jni/src/org/sqlite/jni/test-script-interpreter.md f9f25126127045d051e918fe
F ext/jni/src/org/sqlite/jni/wrapper1/AggregateFunction.java d5c108b02afd3c63c9e5e53f71f85273c1bfdc461ae526e0a0bb2b25e4df6483
F ext/jni/src/org/sqlite/jni/wrapper1/ScalarFunction.java 43c43adfb7866098aadaaca1620028a6ec82d5193149970019b1cce9eb59fb03
F ext/jni/src/org/sqlite/jni/wrapper1/SqlFunction.java 2833afdb9af5c1949bb35f4c926a5351fba9d1cdf0996864caa7b47827a346c7
F ext/jni/src/org/sqlite/jni/wrapper1/Sqlite.java 12f55248d500c0cf4148757adb442303831632edaa738a41d82708643ba42418
F ext/jni/src/org/sqlite/jni/wrapper1/SqliteException.java 929a1e2ab4e135fbbae7f0d2d609f77cfbbc60bbec7ba789ce23d9c73bc6156e
F ext/jni/src/org/sqlite/jni/wrapper1/Tester2.java 4cb3bebcd44f4289fa8075477583b6c508832288f7b18d6101d2ec23309ee4cf
F ext/jni/src/org/sqlite/jni/wrapper1/Sqlite.java 923c885609ca9e6793636fc17787d0058c80ce1d7ba5a69eb40e68cc299892d1
F ext/jni/src/org/sqlite/jni/wrapper1/SqliteException.java 982538ddb4c0719ef87dfa664cd137b09890b546029a7477810bd64d4c47ee35
F ext/jni/src/org/sqlite/jni/wrapper1/Tester2.java 822cf3d66beb1efcac1792c8652cbebb80ae998275a33337de46fde1670e0008
F ext/jni/src/org/sqlite/jni/wrapper1/ValueHolder.java 7b89a7391f771692c5b83b0a5b86266abe8d59f1c77d7a0eccc9b79f259d79af
F ext/jni/src/org/sqlite/jni/wrapper1/WindowFunction.java c7d1452f9ff26175b3c19bbf273116cc2846610af68e01756d755f037fe7319f
F ext/jni/src/tests/000-000-sanity.test c3427a0e0ac84d7cbe4c95fdc1cd4b61f9ddcf43443408f3000139478c4dc745
@ -2142,8 +2142,8 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93
F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc
F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e
F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0
P ff3d44fe42528d96533d22c7807472df89bca18f1def23b018e2f407318143f8
R 100ace4e28cdce95fe3bed6faf77a591
P 6c584cf27179d16deee84e9699493cf29bebef123fa2a7493aad0324bead1618
R dafa52fdba2c999e04b851e5ec6214ab
U stephan
Z dbd53c8956790cde47b0f616fa6677f5
Z 824d9a7ed24ad4091f85bc7e5264c033
# Remove this line to create a well-formed Fossil manifest.

View File

@ -1 +1 @@
6c584cf27179d16deee84e9699493cf29bebef123fa2a7493aad0324bead1618
6c0acfdce2160d8db261a59677cec571b6abc333481525b1ec975d98e88bec88