Adding methods and property to manually control write transactions (#1216)

* Adding methods and property to manually control write transactions
This commit is contained in:
Kenneth Geisshirt 2017-08-21 17:48:53 +02:00 committed by GitHub
parent bd28c05936
commit 85fb49b354
6 changed files with 115 additions and 2 deletions

View File

@ -4,13 +4,14 @@ X.Y.Z Release notes
* None * None
### Enhancements ### Enhancements
* Added methods `Realm.beginTransaction()`, `Realm.commitTransaction()`, `Realm.cancelTransaction()` to manually control write transactions.
* Added property `Realm.isInTransaction` which indicates if write transaction is in progress.
* Added `shouldCompactOnLaunch` to configuration (#507). * Added `shouldCompactOnLaunch` to configuration (#507).
* Added `Realm.compact()` for manually compacting Realm files. * Added `Realm.compact()` for manually compacting Realm files.
### Bug fixes ### Bug fixes
* None * None
1.10.3 Release notes (2017-8-16) 1.10.3 Release notes (2017-8-16)
============================================================= =============================================================
### Breaking changes ### Breaking changes
@ -20,7 +21,7 @@ X.Y.Z Release notes
* None * None
### Bug fixes ### Bug fixes
* none * None
1.10.2 Release notes (2017-8-16) 1.10.2 Release notes (2017-8-16)

View File

@ -64,6 +64,14 @@ class Realm {
*/ */
get schemaVersion() {} get schemaVersion() {}
/**
* Indicates if this Realm is in a write transaction.
* @type {boolean}
* @readonly
* @since 1.10.3
*/
get isInTransaction() {}
/** /**
* Gets the sync session if this is a synced Realm * Gets the sync session if this is a synced Realm
* @type {Session} * @type {Session}
@ -184,6 +192,22 @@ class Realm {
write(callback) {} write(callback) {}
/** /**
* Initiate a write transaction.
* @throws {Error} When already in write transaction
*/
beginTransaction() {}
/**
* Commit a write transaction.
*/
commitTransaction() {}
/**
* Cancel a write transaction.
*/
cancelTransaction() {}
/*
* Replaces all string columns in this Realm with a string enumeration column and compacts the * Replaces all string columns in this Realm with a string enumeration column and compacts the
* database file. * database file.
* *

View File

@ -58,6 +58,7 @@ function setupRealm(realm, realmId) {
'schema', 'schema',
'schemaVersion', 'schemaVersion',
'syncSession', 'syncSession',
'isInTransaction',
].forEach((name) => { ].forEach((name) => {
Object.defineProperty(realm, name, {get: util.getterForProperty(name)}); Object.defineProperty(realm, name, {get: util.getterForProperty(name)});
}); });
@ -133,6 +134,9 @@ util.createMethods(Realm.prototype, objectTypes.REALM, [
'deleteAll', 'deleteAll',
'write', 'write',
'compact', 'compact',
'beginTransaction',
'commitTransaction',
'cancelTransaction',
], true); ], true);
const Sync = { const Sync = {

16
lib/index.d.ts vendored
View File

@ -358,6 +358,7 @@ declare class Realm {
readonly readOnly: boolean; readonly readOnly: boolean;
readonly schema: Realm.ObjectSchema[]; readonly schema: Realm.ObjectSchema[];
readonly schemaVersion: number; readonly schemaVersion: number;
readonly isInTransaction: boolean;
readonly syncSession: Realm.Sync.Session | null; readonly syncSession: Realm.Sync.Session | null;
@ -454,6 +455,21 @@ declare class Realm {
*/ */
write(callback: () => void): void; write(callback: () => void): void;
/**
* @returns void
*/
beginTransaction(): void;
/**
* @returns void
*/
commitTransaction(): void;
/**
* @returns void
*/
cancelTransaction(): void;
/** /**
* @returns boolean * @returns boolean
*/ */

View File

@ -171,6 +171,9 @@ public:
static void delete_one(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &); static void delete_one(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &);
static void delete_all(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &); static void delete_all(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &);
static void write(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &); static void write(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &);
static void begin_transaction(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue&);
static void commit_transaction(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue&);
static void cancel_transaction(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue&);
static void add_listener(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &); static void add_listener(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &);
static void wait_for_download_completion(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &); static void wait_for_download_completion(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &);
static void remove_listener(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &); static void remove_listener(ContextType, FunctionType, ObjectType, size_t, const ValueType[], ReturnValue &);
@ -185,6 +188,7 @@ public:
static void get_schema_version(ContextType, ObjectType, ReturnValue &); static void get_schema_version(ContextType, ObjectType, ReturnValue &);
static void get_schema(ContextType, ObjectType, ReturnValue &); static void get_schema(ContextType, ObjectType, ReturnValue &);
static void get_read_only(ContextType, ObjectType, ReturnValue &); static void get_read_only(ContextType, ObjectType, ReturnValue &);
static void get_is_in_transaction(ContextType, ObjectType, ReturnValue &);
#if REALM_ENABLE_SYNC #if REALM_ENABLE_SYNC
static void get_sync_session(ContextType, ObjectType, ReturnValue &); static void get_sync_session(ContextType, ObjectType, ReturnValue &);
#endif #endif
@ -221,6 +225,9 @@ public:
{"delete", wrap<delete_one>}, {"delete", wrap<delete_one>},
{"deleteAll", wrap<delete_all>}, {"deleteAll", wrap<delete_all>},
{"write", wrap<write>}, {"write", wrap<write>},
{"beginTransaction", wrap<begin_transaction>},
{"commitTransaction", wrap<commit_transaction>},
{"cancelTransaction", wrap<cancel_transaction>},
{"addListener", wrap<add_listener>}, {"addListener", wrap<add_listener>},
{"removeListener", wrap<remove_listener>}, {"removeListener", wrap<remove_listener>},
{"removeAllListeners", wrap<remove_all_listeners>}, {"removeAllListeners", wrap<remove_all_listeners>},
@ -234,6 +241,7 @@ public:
{"schemaVersion", {wrap<get_schema_version>, nullptr}}, {"schemaVersion", {wrap<get_schema_version>, nullptr}},
{"schema", {wrap<get_schema>, nullptr}}, {"schema", {wrap<get_schema>, nullptr}},
{"readOnly", {wrap<get_read_only>, nullptr}}, {"readOnly", {wrap<get_read_only>, nullptr}},
{"isInTransaction", {wrap<get_is_in_transaction>, nullptr}},
#if REALM_ENABLE_SYNC #if REALM_ENABLE_SYNC
{"syncSession", {wrap<get_sync_session>, nullptr}}, {"syncSession", {wrap<get_sync_session>, nullptr}},
#endif #endif
@ -558,6 +566,11 @@ void RealmClass<T>::get_read_only(ContextType ctx, ObjectType object, ReturnValu
return_value.set(get_internal<T, RealmClass<T>>(object)->get()->config().read_only()); return_value.set(get_internal<T, RealmClass<T>>(object)->get()->config().read_only());
} }
template<typename T>
void RealmClass<T>::get_is_in_transaction(ContextType ctx, ObjectType object, ReturnValue &return_value) {
return_value.set(get_internal<T, RealmClass<T>>(object)->get()->is_in_transaction());
}
#if REALM_ENABLE_SYNC #if REALM_ENABLE_SYNC
template<typename T> template<typename T>
void RealmClass<T>::get_sync_session(ContextType ctx, ObjectType object, ReturnValue &return_value) { void RealmClass<T>::get_sync_session(ContextType ctx, ObjectType object, ReturnValue &return_value) {
@ -811,6 +824,30 @@ void RealmClass<T>::write(ContextType ctx, FunctionType, ObjectType this_object,
realm->commit_transaction(); realm->commit_transaction();
} }
template<typename T>
void RealmClass<T>::begin_transaction(ContextType ctx, FunctionType, ObjectType this_object, size_t argc, const ValueType arguments[], ReturnValue &return_value) {
validate_argument_count(argc, 0);
SharedRealm realm = *get_internal<T, RealmClass<T>>(this_object);
realm->begin_transaction();
}
template<typename T>
void RealmClass<T>::commit_transaction(ContextType ctx, FunctionType, ObjectType this_object, size_t argc, const ValueType arguments[], ReturnValue &return_value) {
validate_argument_count(argc, 0);
SharedRealm realm = *get_internal<T, RealmClass<T>>(this_object);
realm->commit_transaction();
}
template<typename T>
void RealmClass<T>::cancel_transaction(ContextType ctx, FunctionType, ObjectType this_object, size_t argc, const ValueType arguments[], ReturnValue &return_value) {
validate_argument_count(argc, 0);
SharedRealm realm = *get_internal<T, RealmClass<T>>(this_object);
realm->cancel_transaction();
}
template<typename T> template<typename T>
void RealmClass<T>::add_listener(ContextType ctx, FunctionType, ObjectType this_object, size_t argc, const ValueType arguments[], ReturnValue &return_value) { void RealmClass<T>::add_listener(ContextType ctx, FunctionType, ObjectType this_object, size_t argc, const ValueType arguments[], ReturnValue &return_value) {
validate_argument_count(argc, 2); validate_argument_count(argc, 2);

View File

@ -945,6 +945,37 @@ module.exports = {
TestCase.assertTrue(realm.empty); TestCase.assertTrue(realm.empty);
}, },
testManualTransaction: function() {
const realm = new Realm({schema: [schemas.TestObject]});
TestCase.assertTrue(realm.empty);
realm.beginTransaction();
realm.create('TestObject', {doubleCol: 3.1415});
realm.commitTransaction();
TestCase.assertEqual(realm.objects('TestObject').length, 1);
},
testCancelTransaction: function() {
const realm = new Realm({schema: [schemas.TestObject]});
TestCase.assertTrue(realm.empty);
realm.beginTransaction();
realm.create('TestObject', {doubleCol: 3.1415});
realm.cancelTransaction();
TestCase.assertTrue(realm.empty);
},
testIsInTransaction: function() {
const realm = new Realm({schema: [schemas.TestObject]});
TestCase.assertTrue(!realm.isInTransaction);
realm.beginTransaction();
TestCase.assertTrue(realm.isInTransaction);
realm.cancelTransaction();
TestCase.assertTrue(!realm.isInTransaction);
},
testCompact: function() { testCompact: function() {
var wasCalled = false; var wasCalled = false;
const count = 1000; const count = 1000;