diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index f178d5a0..d6ff38c7 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -82,7 +82,8 @@ jobs: ../tool/pub.sh run test - name: Install ObjectBox C library working-directory: objectbox_test - run: ../install.sh + # Use Sync-enabled library to at least partially run sync_test.dart + run: ../install.sh --sync - name: Library Test working-directory: objectbox_test # Set concurrency=1 to run only one test suite (== test file) at a time to make it easier to diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 4772d544..23d4c2fd 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -90,7 +90,8 @@ generator-integ-tests: - dart test --concurrency=1 --reporter expanded # ObjectBox tests - cd ../objectbox_test - - ../install.sh + # Use Sync-enabled library to at least partially run sync_test.dart + - ../install.sh --sync - dart pub get - dart run build_runner build # Set concurrency=1 to run only one test suite (== test file) at a time. diff --git a/dev-doc/updating-c-library.md b/dev-doc/updating-c-library.md index f880ca9c..22605439 100644 --- a/dev-doc/updating-c-library.md +++ b/dev-doc/updating-c-library.md @@ -19,17 +19,17 @@ for the binding update script (see below) and for Flutter (`flutter_libs` and `sync_flutter_libs` plugins) on Linux and Windows: ```bash -./tool/set-c-version.sh 4.3.1 +./tool/set-c-version.sh 5.0.0-rc ``` ```text -* Update ObjectBox database for Flutter Linux/Windows, Dart Native apps to [4.3.1](https://github.com/objectbox/objectbox-c/releases/tag/v4.3.1). +* Update ObjectBox database for Flutter Linux/Windows, Dart Native apps to [5.0.0-rc](https://github.com/objectbox/objectbox-c/releases/tag/v5.0.0-rc). ``` ```text -Update C library [4.3.0 -> 4.3.1] +Update C library [4.3.1 -> 5.0.0-rc] -Includes database 4.3.1-2025-07-28 +Includes database 5.0.0-2025-09-27 ``` ### Android @@ -37,19 +37,19 @@ Includes database 4.3.1-2025-07-28 For the Flutter plugins on Android ([view releases](https://github.com/objectbox/objectbox-java/releases)): ```bash -./tool/set-android-version.sh 4.3.1 +./tool/set-android-version.sh 5.0.1 ``` ```text -* Update ObjectBox database for Flutter Android apps to 4.3.1. +* Update ObjectBox database for Flutter Android apps to 5.0.1. If your project is [using Admin](https://docs.objectbox.io/data-browser#admin-for-android), make - sure to update to `io.objectbox:objectbox-android-objectbrowser:4.3.1` in `android/app/build.gradle`. + sure to update to `io.objectbox:objectbox-android-objectbrowser:5.0.1` in `android/app/build.gradle`. ``` ```text -Update Android library [4.3.0 -> 4.3.1] +Update Android library [4.3.1 -> 5.0.1] -Includes C API 4.3.1 and database 4.3.1-2025-08-02 +Includes C API 5.0.0 and database 5.0.0-2025-09-27 ``` Note: the embedded C API and ObjectBox version can be looked up @@ -60,18 +60,18 @@ from the relevant objectbox repository release tag (like `java-4.1.0`). For the Flutter plugins on iOS/macOS ([view releases](https://github.com/objectbox/objectbox-swift/releases)) ```bash -./tool/set-swift-version.sh 4.4.1 +./tool/set-swift-version.sh 5.0.0 ``` ```text -* Update ObjectBox database for Flutter iOS/macOS apps to 4.3.1. +* Update ObjectBox database for Flutter iOS/macOS apps to 5.0.0. For existing projects, run `pod repo update` and `pod update ObjectBox` in the `ios` or `macos` directories. ``` ```text -Update macOS/iOS library [4.3.0 -> 4.4.1] +Update macOS/iOS library [4.4.1 -> 5.0.0] -Includes C API 4.3.1 and database 4.3.1-2025-08-02 +Includes C API 5.0.0 and database 5.0.0-2025-09-27 ``` Note: the embedded C API and ObjectBox version can be looked up @@ -98,5 +98,5 @@ Then manually: - Commit as ```text -Update C-API [4.3.0 -> 4.3.1] +Update C-API [4.3.1 -> 5.0.0] ``` diff --git a/flutter_libs/android/build.gradle b/flutter_libs/android/build.gradle index 4c67fe77..b59d187d 100644 --- a/flutter_libs/android/build.gradle +++ b/flutter_libs/android/build.gradle @@ -50,6 +50,6 @@ android { // ObjectBox Android library that includes an ObjectBox C library version compatible with // the C API binding of the ObjectBox Dart package. // https://central.sonatype.com/search?q=g:io.objectbox%20objectbox-android - implementation "io.objectbox:objectbox-android:4.3.1" + implementation "io.objectbox:objectbox-android:5.0.1" } } diff --git a/flutter_libs/ios/objectbox_flutter_libs.podspec b/flutter_libs/ios/objectbox_flutter_libs.podspec index de5d2985..2cd75cfe 100644 --- a/flutter_libs/ios/objectbox_flutter_libs.podspec +++ b/flutter_libs/ios/objectbox_flutter_libs.podspec @@ -18,7 +18,7 @@ Pod::Spec.new do |s| s.source_files = 'Classes/**/*' s.dependency 'Flutter' - s.dependency 'ObjectBox', '4.4.1' + s.dependency 'ObjectBox', '5.0.0' # Flutter.framework does not contain a i386 slice. s.pod_target_xcconfig = { 'DEFINES_MODULE' => 'YES', 'EXCLUDED_ARCHS[sdk=iphonesimulator*]' => 'i386' } diff --git a/flutter_libs/linux/CMakeLists.txt b/flutter_libs/linux/CMakeLists.txt index d9aafb00..048129e5 100644 --- a/flutter_libs/linux/CMakeLists.txt +++ b/flutter_libs/linux/CMakeLists.txt @@ -47,7 +47,7 @@ target_link_libraries(${PLUGIN_NAME} PRIVATE PkgConfig::GTK) # ---------------------------------------------------------------------- # Download and add objectbox-c prebuilt library. -set(OBJECTBOX_VERSION 4.3.1) +set(OBJECTBOX_VERSION 5.0.0-rc) set(OBJECTBOX_ARCH ${CMAKE_SYSTEM_PROCESSOR}) if (${OBJECTBOX_ARCH} MATCHES "x86_64") diff --git a/flutter_libs/macos/objectbox_flutter_libs.podspec b/flutter_libs/macos/objectbox_flutter_libs.podspec index a32e4311..268985c9 100644 --- a/flutter_libs/macos/objectbox_flutter_libs.podspec +++ b/flutter_libs/macos/objectbox_flutter_libs.podspec @@ -18,7 +18,7 @@ Pod::Spec.new do |s| s.source_files = 'Classes/**/*' s.dependency 'FlutterMacOS' - s.dependency 'ObjectBox', '4.4.1' + s.dependency 'ObjectBox', '5.0.0' s.pod_target_xcconfig = { 'DEFINES_MODULE' => 'YES' } s.swift_version = '5.3' diff --git a/flutter_libs/windows/CMakeLists.txt b/flutter_libs/windows/CMakeLists.txt index 20be78ad..c4beb87a 100644 --- a/flutter_libs/windows/CMakeLists.txt +++ b/flutter_libs/windows/CMakeLists.txt @@ -56,7 +56,7 @@ set(objectbox_flutter_libs_bundled_libraries # ---------------------------------------------------------------------- # Download and add objectbox-c prebuilt library. -set(OBJECTBOX_VERSION 4.3.1) +set(OBJECTBOX_VERSION 5.0.0-rc) set(OBJECTBOX_ARCH ${CMAKE_SYSTEM_PROCESSOR}) if (${OBJECTBOX_ARCH} MATCHES "AMD64") diff --git a/install.sh b/install.sh index ac0d13c0..61428560 100755 --- a/install.sh +++ b/install.sh @@ -5,7 +5,7 @@ set -eu # It's important that the generated dart bindings and the c-api library version match. Dart won't error on C function # signature mismatch, leading to obscure memory bugs. # For how to upgrade the version see dev-doc/updating-c-library.md -cLibVersion=4.3.1 +cLibVersion=5.0.0-rc os=$(uname) cLibArgs="$*" diff --git a/objectbox/CHANGELOG.md b/objectbox/CHANGELOG.md index 67ebd72f..e9294c58 100644 --- a/objectbox/CHANGELOG.md +++ b/objectbox/CHANGELOG.md @@ -1,8 +1,26 @@ ## latest +### Sync + +- Support Sync server version 5.0. + - **User-Specific Data Sync**: support configuring [Sync filter](https://sync.objectbox.io/sync-server/sync-filters) + variables on `SyncClient`. + +### Other Changes + * Flutter packages are compiled with Android SDK 35 to support Android Gradle Plugin 8.13 [#755](https://github.com/objectbox/objectbox-dart/issues/755). They are also built using a language level of Java 11. +* Update ObjectBox database for Flutter Linux/Windows, Dart Native apps to [5.0.0-rc](https://github.com/objectbox/objectbox-c/releases/tag/v5.0.0-rc). + * ToOne relations: when deleting an object with an ID larger than the maximum 32-bit unsigned + integer (`4_294_967_295`) that is used as the target object of a ToOne, correctly re-set the + target ID of the ToOne to `0`. [#740](https://github.com/objectbox/objectbox-dart/issues/740) +* Update ObjectBox database for Flutter Android apps to 5.0.1. + If your project is [using Admin](https://docs.objectbox.io/data-browser#admin-for-android), make + sure to update to `io.objectbox:objectbox-android-objectbrowser:5.0.1` in `android/app/build.gradle`. +* Update ObjectBox database for Flutter iOS/macOS apps to 5.0.0. + For existing projects, run `pod repo update` and `pod update ObjectBox` in the `ios` or `macos` directories. +* Remove deprecated `contains` condition for `List` properties, use `containsElement` instead. ## 4.3.1 (2025-09-02) diff --git a/objectbox/example/flutter/objectbox_demo_relations/android/app/build.gradle b/objectbox/example/flutter/objectbox_demo_relations/android/app/build.gradle index 49233ab0..73cba5ee 100644 --- a/objectbox/example/flutter/objectbox_demo_relations/android/app/build.gradle +++ b/objectbox/example/flutter/objectbox_demo_relations/android/app/build.gradle @@ -83,5 +83,5 @@ dependencies { // Add the Android library with ObjectBox Admin only for debug builds. // Note: when the objectbox package updates, check if the Android // library below needs to be updated as well. - debugImplementation("io.objectbox:objectbox-android-objectbrowser:4.3.1") + debugImplementation("io.objectbox:objectbox-android-objectbrowser:5.0.1") } diff --git a/objectbox/lib/src/native/bindings/bindings.dart b/objectbox/lib/src/native/bindings/bindings.dart index 706fe06a..d4779a9b 100644 --- a/objectbox/lib/src/native/bindings/bindings.dart +++ b/objectbox/lib/src/native/bindings/bindings.dart @@ -96,14 +96,14 @@ ObjectBoxC? _tryObjectBoxLibFile() { // libraries. // Library | C API | Database // ------------------------|-------|----------------- -// C library 4.3.1 | 4.3.1 | 4.3.1-2025-07-28 -// Android library 4.3.1 | 4.3.1 | 4.3.1-2025-08-02 -// macOS/iOS library 4.4.1 | 4.3.1 | 4.3.1-2025-08-02 -var _obxCminMajor = 4; -var _obxCminMinor = 3; -var _obxCminPatch = 1; +// C library 5.0.0-rc | 5.0.0 | 5.0.0-2025-09-27 +// Android library 5.0.1 | 5.0.0 | 5.0.0-2025-09-27 +// macOS/iOS library 5.0.0 | 5.0.0 | 5.0.0-2025-09-27 +var _obxCminMajor = 5; +var _obxCminMinor = 0; +var _obxCminPatch = 0; // Require minimum database version guaranteeing actual C API availability. -var _obxDatabaseMinVersion = "4.3.1-2025-07-28"; +var _obxDatabaseMinVersion = "5.0.0-2025-09-27"; bool _isSupportedVersion(ObjectBoxC obxc) { // Require a minimum C API version diff --git a/objectbox/lib/src/native/bindings/objectbox-sync.h b/objectbox/lib/src/native/bindings/objectbox-sync.h index 0935e5f5..2c4f4287 100644 --- a/objectbox/lib/src/native/bindings/objectbox-sync.h +++ b/objectbox/lib/src/native/bindings/objectbox-sync.h @@ -34,7 +34,7 @@ #include "objectbox.h" #if defined(static_assert) || defined(__cplusplus) -static_assert(OBX_VERSION_MAJOR == 4 && OBX_VERSION_MINOR == 3 && OBX_VERSION_PATCH == 1, // NOLINT +static_assert(OBX_VERSION_MAJOR == 5 && OBX_VERSION_MINOR == 0 && OBX_VERSION_PATCH == 0, // NOLINT "Versions of objectbox.h and objectbox-sync.h files do not match, please update"); #endif @@ -201,6 +201,20 @@ OBX_C_API OBX_sync* obx_sync_urls(OBX_store* store, const char* server_urls[], s /// Stops and closes (deletes) the sync client, freeing its resources. OBX_C_API obx_err obx_sync_close(OBX_sync* sync); +/// Adds or replaces a sync filter variable value for the given name to the sync client. +/// Eventually existing values for the same name are replaced. +/// Client filter variables can be used in server-side sync filters to filter out objects that do not match the filter. +/// Filter variables must be added before login, e.g. before obx_sync_start() or setting credentials. +/// @param name non-NULL name of the filter variable +/// @param value non-NULL value of the filter variable +OBX_C_API obx_err obx_sync_filter_variables_put(OBX_sync* sync, const char* name, const char* value); + +/// Removes a previously added sync filter variable value. +OBX_C_API obx_err obx_sync_filter_variables_remove(OBX_sync* sync, const char* name); + +/// Removes all previously added sync filter variable values. +OBX_C_API obx_err obx_sync_filter_variables_remove_all(OBX_sync* sync); + /// Sets credentials to authenticate the client with the server. /// Any credentials that were set before are replaced; /// if you want to pass multiple credentials, use obx_sync_credentials_add() instead. diff --git a/objectbox/lib/src/native/bindings/objectbox.h b/objectbox/lib/src/native/bindings/objectbox.h index 872318cb..d5a6dbce 100644 --- a/objectbox/lib/src/native/bindings/objectbox.h +++ b/objectbox/lib/src/native/bindings/objectbox.h @@ -51,9 +51,9 @@ extern "C" { /// When using ObjectBox as a dynamic library, you should verify that a compatible version was linked using /// obx_version() or obx_version_is_at_least(). -#define OBX_VERSION_MAJOR 4 -#define OBX_VERSION_MINOR 3 -#define OBX_VERSION_PATCH 1 // values >= 100 are reserved for dev releases leading to the next minor/major increase +#define OBX_VERSION_MAJOR 5 +#define OBX_VERSION_MINOR 0 +#define OBX_VERSION_PATCH 0 // values >= 100 are reserved for dev releases leading to the next minor/major increase //---------------------------------------------- // Common types @@ -179,6 +179,8 @@ typedef enum { /// This is a free trial version; only applies to server builds (no trial builds for database and Sync clients). OBXFeature_Trial = 18, + /// Server-side filters to return individual data for each sync user (user-specific data). + OBXFeature_SyncFilters = 19, } OBXFeature; @@ -2121,7 +2123,7 @@ OBX_C_API obx_qb_cond obx_qb_less_or_equal_string(OBX_query_builder* builder, ob OBX_C_API obx_qb_cond obx_qb_in_strings(OBX_query_builder* builder, obx_schema_id property_id, const char* const values[], size_t count, bool case_sensitive); -/// For OBXPropertyType_StringVector - matches if at least one vector item equals the given value. +/// @deprecated Please use obx_qb_contains_element_string() instead. OBX_C_API obx_qb_cond obx_qb_any_equals_string(OBX_query_builder* builder, obx_schema_id property_id, const char* value, bool case_sensitive); diff --git a/objectbox/lib/src/native/bindings/objectbox_c.dart b/objectbox/lib/src/native/bindings/objectbox_c.dart index a3e029ac..fd01925c 100644 --- a/objectbox/lib/src/native/bindings/objectbox_c.dart +++ b/objectbox/lib/src/native/bindings/objectbox_c.dart @@ -4935,7 +4935,7 @@ class ObjectBoxC { int Function(ffi.Pointer, int, ffi.Pointer>, int, bool)>(); - /// For OBXPropertyType_StringVector - matches if at least one vector item equals the given value. + /// @deprecated Please use obx_qb_contains_element_string() instead. int qb_any_equals_string( ffi.Pointer builder, int property_id, @@ -8399,6 +8399,67 @@ class ObjectBoxC { late final _sync_close = _sync_closePtr.asFunction)>(); + /// Adds or replaces a sync filter variable value for the given name to the sync client. + /// Eventually existing values for the same name are replaced. + /// Client filter variables can be used in server-side sync filters to filter out objects that do not match the filter. + /// Filter variables must be added before login, e.g. before obx_sync_start() or setting credentials. + /// @param name non-NULL name of the filter variable + /// @param value non-NULL value of the filter variable + int sync_filter_variables_put( + ffi.Pointer sync1, + ffi.Pointer name, + ffi.Pointer value, + ) { + return _sync_filter_variables_put( + sync1, + name, + value, + ); + } + + late final _sync_filter_variables_putPtr = _lookup< + ffi.NativeFunction< + obx_err Function(ffi.Pointer, ffi.Pointer, + ffi.Pointer)>>('obx_sync_filter_variables_put'); + late final _sync_filter_variables_put = + _sync_filter_variables_putPtr.asFunction< + int Function(ffi.Pointer, ffi.Pointer, + ffi.Pointer)>(); + + /// Removes a previously added sync filter variable value. + int sync_filter_variables_remove( + ffi.Pointer sync1, + ffi.Pointer name, + ) { + return _sync_filter_variables_remove( + sync1, + name, + ); + } + + late final _sync_filter_variables_removePtr = _lookup< + ffi.NativeFunction< + obx_err Function(ffi.Pointer, + ffi.Pointer)>>('obx_sync_filter_variables_remove'); + late final _sync_filter_variables_remove = _sync_filter_variables_removePtr + .asFunction, ffi.Pointer)>(); + + /// Removes all previously added sync filter variable values. + int sync_filter_variables_remove_all( + ffi.Pointer sync1, + ) { + return _sync_filter_variables_remove_all( + sync1, + ); + } + + late final _sync_filter_variables_remove_allPtr = + _lookup)>>( + 'obx_sync_filter_variables_remove_all'); + late final _sync_filter_variables_remove_all = + _sync_filter_variables_remove_allPtr + .asFunction)>(); + /// Sets credentials to authenticate the client with the server. /// Any credentials that were set before are replaced; /// if you want to pass multiple credentials, use obx_sync_credentials_add() instead. @@ -10400,6 +10461,9 @@ abstract class OBXFeature { /// This is a free trial version; only applies to server builds (no trial builds for database and Sync clients). static const int Trial = 18; + + /// Server-side filters to return individual data for each sync user (user-specific data). + static const int SyncFilters = 19; } /// Log level as passed to obx_log_callback. @@ -11677,11 +11741,11 @@ class OBX_dart_finalizer extends ffi.Opaque {} typedef obx_dart_closer = ffi.NativeFunction native_object)>; -const int OBX_VERSION_MAJOR = 4; +const int OBX_VERSION_MAJOR = 5; -const int OBX_VERSION_MINOR = 3; +const int OBX_VERSION_MINOR = 0; -const int OBX_VERSION_PATCH = 1; +const int OBX_VERSION_PATCH = 0; const int OBX_ID_NEW = -1; diff --git a/objectbox/lib/src/native/query/query.dart b/objectbox/lib/src/native/query/query.dart index 9450cd7b..463b9531 100644 --- a/objectbox/lib/src/native/query/query.dart +++ b/objectbox/lib/src/native/query/query.dart @@ -433,11 +433,6 @@ class QueryStringVectorProperty extends QueryProperty> { QueryStringVectorProperty(super.model); - @Deprecated( - 'Use `containsElement` instead. Will be removed in a future release.') - Condition contains(String p, {bool? caseSensitive, String? alias}) => - containsElement(p, caseSensitive: caseSensitive, alias: alias); - /// Matches if at least one element of the list equals the given value. Condition containsElement(String value, {bool? caseSensitive, String? alias}) => diff --git a/objectbox/lib/src/native/sync.dart b/objectbox/lib/src/native/sync.dart index a6ddc0ba..246661fe 100644 --- a/objectbox/lib/src/native/sync.dart +++ b/objectbox/lib/src/native/sync.dart @@ -191,7 +191,8 @@ class SyncClient { /// Creates a Sync client associated with the given store and options. /// This does not initiate any connection attempts yet: call start() to do so. SyncClient._( - this._store, List serverUrls, List credentials) { + this._store, List serverUrls, List credentials, + {Map? filterVariables}) { if (serverUrls.isEmpty) { throw ArgumentError.value( serverUrls, "serverUrls", "Provide at least one server URL"); @@ -209,6 +210,8 @@ class SyncClient { C.sync_urls(InternalStoreAccess.ptr(_store), ptr, size), 'failed to create Sync client')); + filterVariables?.forEach(putFilterVariable); + if (credentials.length == 1) { setCredentials(credentials[0]); } else { @@ -258,6 +261,40 @@ class SyncClient { } } + /// Adds or replaces a [Sync filter](https://sync.objectbox.io/sync-server/sync-filters) + /// variable value for the given name. + /// + /// Eventually, existing values for the same name are replaced. + /// + /// Sync client filter variables can be used in server-side Sync filters to + /// filter out objects that do not match the filters. Filter variables must be + /// added before login, so before calling `start()`. + /// + /// See also [removeFilterVariable] and [removeAllFilterVariables]. + void putFilterVariable(String name, String value) { + withNativeString( + name, + (nameCStr) => withNativeString( + value, + (valueCStr) => checkObx( + C.sync_filter_variables_put(_ptr, nameCStr, valueCStr)))); + } + + /// Removes a previously added Sync filter variable value. + /// + /// See also [putFilterVariable] and [removeAllFilterVariables]. + void removeFilterVariable(String name) { + withNativeString(name, + (nameCStr) => checkObx(C.sync_filter_variables_remove(_ptr, nameCStr))); + } + + /// Removes all previously added Sync filter variable values. + /// + /// See also [putFilterVariable] and [removeFilterVariable]. + void removeAllFilterVariables() { + checkObx(C.sync_filter_variables_remove_all(_ptr)); + } + /// Configure authentication credentials, depending on your server config. void setCredentials(SyncCredentials creds) { if (creds is _SyncCredentialsNone) { @@ -697,22 +734,34 @@ class Sync { /// /// Before [SyncClient.start()], you can still configure some aspects of the /// client, e.g. its [SyncRequestUpdatesMode] mode. + /// + /// To configure [Sync filter](https://sync.objectbox.io/sync-server/sync-filters) + /// variables, pass variable names mapped to their value to [filterVariables]. + /// + /// Sync client filter variables can be used in server-side Sync filters to + /// filter out objects that do not match the filter. static SyncClient client( - Store store, String serverUrl, SyncCredentials credentials) => - clientMultiUrls(store, [serverUrl], credentials); + Store store, String serverUrl, SyncCredentials credentials, + {Map? filterVariables}) => + clientMultiUrls(store, [serverUrl], credentials, + filterVariables: filterVariables); /// Like [client], but accepts a list of credentials. /// /// When passing multiple credentials, does **not** support /// [SyncCredentials.none()]. static SyncClient clientMultiCredentials( - Store store, String serverUrl, List credentials) => - clientMultiCredentialsMultiUrls(store, [serverUrl], credentials); + Store store, String serverUrl, List credentials, + {Map? filterVariables}) => + clientMultiCredentialsMultiUrls(store, [serverUrl], credentials, + filterVariables: filterVariables); /// Like [client], but accepts a list of URLs to work with multiple servers. static SyncClient clientMultiUrls( - Store store, List serverUrls, SyncCredentials credentials) => - clientMultiCredentialsMultiUrls(store, serverUrls, [credentials]); + Store store, List serverUrls, SyncCredentials credentials, + {Map? filterVariables}) => + clientMultiCredentialsMultiUrls(store, serverUrls, [credentials], + filterVariables: filterVariables); /// Like [client], but accepts a list of credentials and a list of URLs to /// work with multiple servers. @@ -720,7 +769,8 @@ class Sync { /// When passing multiple credentials, does **not** support /// [SyncCredentials.none()]. static SyncClient clientMultiCredentialsMultiUrls( - Store store, List serverUrls, List credentials) { + Store store, List serverUrls, List credentials, + {Map? filterVariables}) { if (syncClientsStorage.containsKey(store)) { throw StateError('Only one sync client can be active for a store'); } diff --git a/objectbox_test/test/box_test.dart b/objectbox_test/test/box_test.dart index 90c1f923..2c783e5a 100644 --- a/objectbox_test/test/box_test.dart +++ b/objectbox_test/test/box_test.dart @@ -25,6 +25,32 @@ void main() { tearDown(() => env.closeAndDelete()); + test('target ID is reset when removing target object with large ID', () { + final modelABox = store.box(); + final modelBBox = store.box(); + + // final modelAdbId = 4294967295; // 32-bit unsigned integer MAX WORKS + final modelAdbId = 4294967295 + 1; // FAILS + + final modelB = ModelB()..modelA.target = ModelA(dbId: modelAdbId); + final modelBId = modelBBox.put(modelB); + // Need to put target object as using manually assigned IDs + modelABox.put(ModelA(dbId: modelAdbId)); + + // Check ToOne has target + final modelA = modelBBox.get(modelBId)!.modelA; + expect(modelA.targetId, modelAdbId, reason: "target ID doesn't match"); + expect(modelA.target, isNotNull); + + // Remove target object + expect(modelABox.remove(modelAdbId), true); + + // Check ToOne has no target + final modelARemoved = modelBBox.get(modelBId)!.modelA; + expect(modelARemoved.targetId, 0, reason: "target ID not 0"); + expect(modelARemoved.target, isNull); + }); + test('store box vending', () { final box1 = store.box(); expect(box1.isEmpty(), isTrue); diff --git a/objectbox_test/test/entity.dart b/objectbox_test/test/entity.dart index 2fef9ee1..ae2aa676 100644 --- a/objectbox_test/test/entity.dart +++ b/objectbox_test/test/entity.dart @@ -504,3 +504,21 @@ class RelatedNamedEntity { String? name; } + +@Entity() +class ModelA { + @Id(assignable: true) + int dbId; + + ModelA({required this.dbId}); +} + +@Entity() +class ModelB { + @Id() + int dbId; + + final modelA = ToOne(); + + ModelB({this.dbId = 0}); +} diff --git a/objectbox_test/test/objectbox-model.json b/objectbox_test/test/objectbox-model.json index fe686ec2..55cdc5f5 100644 --- a/objectbox_test/test/objectbox-model.json +++ b/objectbox_test/test/objectbox-model.json @@ -767,10 +767,46 @@ "targetId": "16:5931645853908059165" } ] + }, + { + "id": "17:1916197463975409850", + "lastPropertyId": "1:7361238329179935424", + "name": "ModelA", + "properties": [ + { + "id": "1:7361238329179935424", + "name": "dbId", + "type": 6, + "flags": 129 + } + ], + "relations": [] + }, + { + "id": "18:2680158095061865736", + "lastPropertyId": "2:533966917738031607", + "name": "ModelB", + "properties": [ + { + "id": "1:6351192468911651752", + "name": "dbId", + "type": 6, + "flags": 1 + }, + { + "id": "2:533966917738031607", + "name": "modelAId", + "indexId": "24:4321803250180166911", + "type": 11, + "flags": 520, + "relationTarget": "ModelA" + } + ], + "relations": [] } ], - "lastEntityId": "16:5931645853908059165", - "lastIndexId": "23:6649884639373473085", + "lastEntityId": "18:2680158095061865736", + "lastIndexId": "24:4321803250180166911", "lastRelationId": "2:313640065593441165", "lastSequenceId": "0:0", "modelVersion": 5, diff --git a/objectbox_test/test/sync_test.dart b/objectbox_test/test/sync_test.dart index 181083df..97979bf8 100644 --- a/objectbox_test/test/sync_test.dart +++ b/objectbox_test/test/sync_test.dart @@ -29,6 +29,11 @@ void main() { late TestEnv env2; int serverPort = 9999; + /// Returns a test server URL with the current [serverPort]. + serverUrl() { + return 'ws://127.0.0.1:$serverPort'; + } + setUp(() { env = TestEnv('sync'); store = env.store; @@ -47,7 +52,7 @@ void main() { // lambda to easily create clients in the tests below SyncClient createAuthenticatedClient( Store s, List credentials) => - Sync.clientMultiCredentials(s, 'ws://127.0.0.1:$serverPort', credentials); + Sync.clientMultiCredentials(s, serverUrl(), credentials); SyncClient createClient(Store s) => createAuthenticatedClient(s, [SyncCredentials.none()]); @@ -255,6 +260,29 @@ void main() { ]); }); + test('SyncClient filter variables', () { + final filterVariables = { + 'test-var-1': 'test value 1', + 'test-var-2': 'test value 2' + }; + SyncClient client = Sync.client( + store, serverUrl(), SyncCredentials.none(), + filterVariables: filterVariables); + addTearDown(() { + client.close(); + }); + + client.putFilterVariable('test-var-2', 'test value 2'); + client.removeFilterVariable('test-var-2'); + client.putFilterVariable('test-var-2', ''); + client.removeAllFilterVariables(); + + expect( + () => client.putFilterVariable('', 'value'), + throwsA(isA().having((e) => e.message, 'message', + contains('Filter variables must have a name')))); + }); + group('Server tests using sync-server in PATH', () { late SyncServer server; diff --git a/sync_flutter_libs/android/build.gradle b/sync_flutter_libs/android/build.gradle index dc9da2c6..7908e7f7 100644 --- a/sync_flutter_libs/android/build.gradle +++ b/sync_flutter_libs/android/build.gradle @@ -50,6 +50,6 @@ android { // ObjectBox Android library that includes an ObjectBox C library version compatible with // the C API binding of the ObjectBox Dart package. // https://central.sonatype.com/search?q=g:io.objectbox%20objectbox-sync-android - implementation "io.objectbox:objectbox-sync-android:4.3.1" + implementation "io.objectbox:objectbox-sync-android:5.0.1" } } diff --git a/sync_flutter_libs/ios/objectbox_sync_flutter_libs.podspec b/sync_flutter_libs/ios/objectbox_sync_flutter_libs.podspec index 546f49dd..65235159 100644 --- a/sync_flutter_libs/ios/objectbox_sync_flutter_libs.podspec +++ b/sync_flutter_libs/ios/objectbox_sync_flutter_libs.podspec @@ -18,7 +18,7 @@ Pod::Spec.new do |s| s.source_files = 'Classes/**/*' s.dependency 'Flutter' - s.dependency 'ObjectBox', '4.4.1-sync' + s.dependency 'ObjectBox', '5.0.0-sync' # Flutter.framework does not contain a i386 slice. s.pod_target_xcconfig = { 'DEFINES_MODULE' => 'YES', 'EXCLUDED_ARCHS[sdk=iphonesimulator*]' => 'i386' } diff --git a/sync_flutter_libs/linux/CMakeLists.txt b/sync_flutter_libs/linux/CMakeLists.txt index 70a5f349..5bfa0503 100644 --- a/sync_flutter_libs/linux/CMakeLists.txt +++ b/sync_flutter_libs/linux/CMakeLists.txt @@ -47,7 +47,7 @@ target_link_libraries(${PLUGIN_NAME} PRIVATE PkgConfig::GTK) # ---------------------------------------------------------------------- # Download and add objectbox-c prebuilt library. -set(OBJECTBOX_VERSION 4.3.1) +set(OBJECTBOX_VERSION 5.0.0-rc) set(OBJECTBOX_ARCH ${CMAKE_SYSTEM_PROCESSOR}) if (${OBJECTBOX_ARCH} MATCHES "x86_64") diff --git a/sync_flutter_libs/macos/objectbox_sync_flutter_libs.podspec b/sync_flutter_libs/macos/objectbox_sync_flutter_libs.podspec index 6cb77356..70ce33e5 100644 --- a/sync_flutter_libs/macos/objectbox_sync_flutter_libs.podspec +++ b/sync_flutter_libs/macos/objectbox_sync_flutter_libs.podspec @@ -14,7 +14,7 @@ Pod::Spec.new do |s| s.source_files = 'Classes/**/*' s.dependency 'FlutterMacOS' - s.dependency 'ObjectBox', '4.4.1-sync' + s.dependency 'ObjectBox', '5.0.0-sync' s.pod_target_xcconfig = { 'DEFINES_MODULE' => 'YES' } s.swift_version = '5.3' diff --git a/sync_flutter_libs/windows/CMakeLists.txt b/sync_flutter_libs/windows/CMakeLists.txt index 0a04131b..0ddd57b4 100644 --- a/sync_flutter_libs/windows/CMakeLists.txt +++ b/sync_flutter_libs/windows/CMakeLists.txt @@ -56,7 +56,7 @@ set(objectbox_sync_flutter_libs_bundled_libraries # ---------------------------------------------------------------------- # Download and add objectbox-c prebuilt library. -set(OBJECTBOX_VERSION 4.3.1) +set(OBJECTBOX_VERSION 5.0.0-rc) set(OBJECTBOX_ARCH ${CMAKE_SYSTEM_PROCESSOR}) if (${OBJECTBOX_ARCH} MATCHES "AMD64") diff --git a/tool/update-c-binding.sh b/tool/update-c-binding.sh index 050c2f62..935427f2 100755 --- a/tool/update-c-binding.sh +++ b/tool/update-c-binding.sh @@ -5,7 +5,7 @@ # copies the header files, makes some required modifications # and runs the ffigen binding generator on them. -cLibVersion=4.3.1 +cLibVersion=5.0.0-rc echo "Downloading C library source files from GitHub..." # Note: the release archives do not contain objectbox-dart.h, so get the full sources.