Merge pull request #479 from realm/al-muti-realm
fix for setting properties to objects from other realms
This commit is contained in:
commit
3901bf53dc
|
@ -8,7 +8,7 @@ x.x.x Release notes (yyyy-MM-dd)
|
||||||
* Added `objectForPrimaryKey(type, key)` method to `Realm`
|
* Added `objectForPrimaryKey(type, key)` method to `Realm`
|
||||||
|
|
||||||
### Bugfixes
|
### Bugfixes
|
||||||
* None
|
* Fix for crash when setting object properties to objects from other Realms
|
||||||
|
|
||||||
0.13.2 Release notes (2016-5-26)
|
0.13.2 Release notes (2016-5-26)
|
||||||
=============================================================
|
=============================================================
|
||||||
|
|
|
@ -106,7 +106,10 @@ struct NativeAccessor {
|
||||||
static size_t to_object_index(ContextType ctx, SharedRealm realm, ValueType &value, const std::string &type, bool try_update) {
|
static size_t to_object_index(ContextType ctx, SharedRealm realm, ValueType &value, const std::string &type, bool try_update) {
|
||||||
ObjectType object = Value::validated_to_object(ctx, value);
|
ObjectType object = Value::validated_to_object(ctx, value);
|
||||||
if (Object::template is_instance<RealmObjectClass<T>>(ctx, object)) {
|
if (Object::template is_instance<RealmObjectClass<T>>(ctx, object)) {
|
||||||
return get_internal<T, RealmObjectClass<T>>(object)->row().get_index();
|
auto realm_object = get_internal<T, RealmObjectClass<T>>(object);
|
||||||
|
if (realm_object->realm() == realm) {
|
||||||
|
return realm_object->row().get_index();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
auto object_schema = realm->config().schema->find(type);
|
auto object_schema = realm->config().schema->find(type);
|
||||||
|
@ -117,13 +120,19 @@ struct NativeAccessor {
|
||||||
auto child = realm::Object::create<ValueType>(ctx, realm, *object_schema, static_cast<ValueType>(object), try_update);
|
auto child = realm::Object::create<ValueType>(ctx, realm, *object_schema, static_cast<ValueType>(object), try_update);
|
||||||
return child.row().get_index();
|
return child.row().get_index();
|
||||||
}
|
}
|
||||||
static size_t to_existing_object_index(ContextType ctx, ValueType &value) {
|
static size_t to_existing_object_index(ContextType ctx, SharedRealm realm, ValueType &value) {
|
||||||
ObjectType object = Value::validated_to_object(ctx, value);
|
ObjectType object = Value::validated_to_object(ctx, value);
|
||||||
if (Object::template is_instance<RealmObjectClass<T>>(ctx, object)) {
|
if (!Object::template is_instance<RealmObjectClass<T>>(ctx, object)) {
|
||||||
return get_internal<T, RealmObjectClass<T>>(object)->row().get_index();
|
|
||||||
}
|
|
||||||
throw std::runtime_error("object is not a Realm Object");
|
throw std::runtime_error("object is not a Realm Object");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
auto realm_object = get_internal<T, RealmObjectClass<T>>(object);
|
||||||
|
if (realm_object->realm() != realm) {
|
||||||
|
throw std::runtime_error("Realm object is from another Realm");
|
||||||
|
|
||||||
|
}
|
||||||
|
return realm_object->row().get_index();
|
||||||
|
}
|
||||||
static ValueType from_object(ContextType ctx, realm::Object realm_object) {
|
static ValueType from_object(ContextType ctx, realm::Object realm_object) {
|
||||||
return RealmObjectClass<T>::create_instance(ctx, std::move(realm_object));
|
return RealmObjectClass<T>::create_instance(ctx, std::move(realm_object));
|
||||||
}
|
}
|
||||||
|
|
|
@ -119,7 +119,7 @@ typename T::Object ResultsClass<T>::create_filtered(ContextType ctx, const U &co
|
||||||
}
|
}
|
||||||
|
|
||||||
parser::Predicate predicate = parser::parse(query_string);
|
parser::Predicate predicate = parser::parse(query_string);
|
||||||
query_builder::ArgumentConverter<ValueType, ContextType> converter(ctx, args);
|
query_builder::ArgumentConverter<ValueType, ContextType> converter(ctx, realm, args);
|
||||||
query_builder::apply_predicate(query, predicate, converter, *realm->config().schema, object_schema.name);
|
query_builder::apply_predicate(query, predicate, converter, *realm->config().schema, object_schema.name);
|
||||||
|
|
||||||
return create_instance(ctx, realm, object_schema, std::move(query));
|
return create_instance(ctx, realm, object_schema, std::move(query));
|
||||||
|
|
|
@ -107,7 +107,7 @@ namespace realm {
|
||||||
static ValueType from_object(ContextType ctx, Object);
|
static ValueType from_object(ContextType ctx, Object);
|
||||||
|
|
||||||
// object index for an existing object
|
// object index for an existing object
|
||||||
static size_t to_existing_object_index(ContextType ctx, ValueType &val);
|
static size_t to_existing_object_index(ContextType ctx, SharedRealm realm, ValueType &val);
|
||||||
|
|
||||||
// list value acessors
|
// list value acessors
|
||||||
static size_t list_size(ContextType ctx, ValueType &val);
|
static size_t list_size(ContextType ctx, ValueType &val);
|
||||||
|
|
|
@ -50,7 +50,8 @@ class Arguments {
|
||||||
template<typename ValueType, typename ContextType>
|
template<typename ValueType, typename ContextType>
|
||||||
class ArgumentConverter : public Arguments {
|
class ArgumentConverter : public Arguments {
|
||||||
public:
|
public:
|
||||||
ArgumentConverter(ContextType context, std::vector<ValueType> arguments) : m_arguments(arguments), m_ctx(context) {}
|
ArgumentConverter(ContextType context, SharedRealm realm, std::vector<ValueType> arguments)
|
||||||
|
: m_arguments(arguments), m_ctx(context), m_realm(std::move(realm)) {}
|
||||||
|
|
||||||
using Accessor = realm::NativeAccessor<ValueType, ContextType>;
|
using Accessor = realm::NativeAccessor<ValueType, ContextType>;
|
||||||
virtual bool bool_for_argument(size_t argument_index) { return Accessor::to_bool(m_ctx, argument_at(argument_index)); }
|
virtual bool bool_for_argument(size_t argument_index) { return Accessor::to_bool(m_ctx, argument_at(argument_index)); }
|
||||||
|
@ -60,12 +61,13 @@ class ArgumentConverter : public Arguments {
|
||||||
virtual std::string string_for_argument(size_t argument_index) { return Accessor::to_string(m_ctx, argument_at(argument_index)); }
|
virtual std::string string_for_argument(size_t argument_index) { return Accessor::to_string(m_ctx, argument_at(argument_index)); }
|
||||||
virtual std::string binary_for_argument(size_t argument_index) { return Accessor::to_binary(m_ctx, argument_at(argument_index)); }
|
virtual std::string binary_for_argument(size_t argument_index) { return Accessor::to_binary(m_ctx, argument_at(argument_index)); }
|
||||||
virtual Timestamp timestamp_for_argument(size_t argument_index) { return Accessor::to_timestamp(m_ctx, argument_at(argument_index)); }
|
virtual Timestamp timestamp_for_argument(size_t argument_index) { return Accessor::to_timestamp(m_ctx, argument_at(argument_index)); }
|
||||||
virtual size_t object_index_for_argument(size_t argument_index) { return Accessor::to_existing_object_index(m_ctx, argument_at(argument_index)); }
|
virtual size_t object_index_for_argument(size_t argument_index) { return Accessor::to_existing_object_index(m_ctx, m_realm, argument_at(argument_index)); }
|
||||||
virtual bool is_argument_null(size_t argument_index) { return Accessor::is_null(m_ctx, argument_at(argument_index)); }
|
virtual bool is_argument_null(size_t argument_index) { return Accessor::is_null(m_ctx, argument_at(argument_index)); }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::vector<ValueType> m_arguments;
|
std::vector<ValueType> m_arguments;
|
||||||
ContextType m_ctx;
|
ContextType m_ctx;
|
||||||
|
SharedRealm m_realm;
|
||||||
|
|
||||||
ValueType &argument_at(size_t index) {
|
ValueType &argument_at(size_t index) {
|
||||||
if (index >= m_arguments.size()) {
|
if (index >= m_arguments.size()) {
|
||||||
|
|
|
@ -328,6 +328,17 @@ module.exports = {
|
||||||
TestCase.assertEqual(obj.arrayCol[0].doubleCol, 3);
|
TestCase.assertEqual(obj.arrayCol[0].doubleCol, 3);
|
||||||
TestCase.assertEqual(obj.arrayCol[1].doubleCol, 1);
|
TestCase.assertEqual(obj.arrayCol[1].doubleCol, 1);
|
||||||
TestCase.assertEqual(obj.arrayCol[2].doubleCol, 2);
|
TestCase.assertEqual(obj.arrayCol[2].doubleCol, 2);
|
||||||
|
|
||||||
|
// set object from another realm
|
||||||
|
var another = new Realm({path: 'another.realm', schema: realm.schema});
|
||||||
|
var anotherObj;
|
||||||
|
another.write(function() {
|
||||||
|
anotherObj = another.create('TestObject', {doubleCol: 3});
|
||||||
|
});
|
||||||
|
realm.write(function() {
|
||||||
|
obj.objectCol = anotherObj;
|
||||||
|
});
|
||||||
|
TestCase.assertEqual(obj.objectCol.doubleCol, 3);
|
||||||
},
|
},
|
||||||
testEnumerablePropertyNames: function() {
|
testEnumerablePropertyNames: function() {
|
||||||
var realm = new Realm({schema: [schemas.BasicTypes]});
|
var realm = new Realm({schema: [schemas.BasicTypes]});
|
||||||
|
|
|
@ -130,6 +130,7 @@ module.exports = {
|
||||||
|
|
||||||
testResultsFiltered: function() {
|
testResultsFiltered: function() {
|
||||||
var realm = new Realm({schema: [schemas.PersonObject, schemas.DefaultValues, schemas.TestObject]});
|
var realm = new Realm({schema: [schemas.PersonObject, schemas.DefaultValues, schemas.TestObject]});
|
||||||
|
|
||||||
realm.write(function() {
|
realm.write(function() {
|
||||||
realm.create('PersonObject', {name: 'Ari', age: 10});
|
realm.create('PersonObject', {name: 'Ari', age: 10});
|
||||||
realm.create('PersonObject', {name: 'Tim', age: 11});
|
realm.create('PersonObject', {name: 'Tim', age: 11});
|
||||||
|
@ -155,9 +156,13 @@ module.exports = {
|
||||||
|
|
||||||
TestCase.assertEqual(realm.objects('PersonObject').filtered('name = $0', 'Tim').length, 1);
|
TestCase.assertEqual(realm.objects('PersonObject').filtered('name = $0', 'Tim').length, 1);
|
||||||
TestCase.assertEqual(realm.objects('PersonObject').filtered('age > $1 && age < $0', 13, 10).length, 3);
|
TestCase.assertEqual(realm.objects('PersonObject').filtered('age > $1 && age < $0', 13, 10).length, 3);
|
||||||
|
|
||||||
TestCase.assertThrows(function() {
|
TestCase.assertThrows(function() {
|
||||||
realm.objects('PersonObject').filtered('age > $2 && age < $0', 13, 10)
|
realm.objects('PersonObject').filtered('age > $2 && age < $0', 13, 10)
|
||||||
});
|
});
|
||||||
|
TestCase.assertThrows(function() {
|
||||||
|
realm.objects('PersonObject').filtered("invalidQuery");
|
||||||
|
});
|
||||||
|
|
||||||
realm.write(function() {
|
realm.write(function() {
|
||||||
realm.create('DefaultValuesObject', {'dateCol': new Date(3)});
|
realm.create('DefaultValuesObject', {'dateCol': new Date(3)});
|
||||||
|
@ -167,9 +172,19 @@ module.exports = {
|
||||||
|
|
||||||
TestCase.assertEqual(realm.objects('DefaultValuesObject').filtered('dateCol > $0', new Date(4)).length, 1);
|
TestCase.assertEqual(realm.objects('DefaultValuesObject').filtered('dateCol > $0', new Date(4)).length, 1);
|
||||||
TestCase.assertEqual(realm.objects('DefaultValuesObject').filtered('dateCol <= $0', new Date(4)).length, 2);
|
TestCase.assertEqual(realm.objects('DefaultValuesObject').filtered('dateCol <= $0', new Date(4)).length, 2);
|
||||||
|
},
|
||||||
|
|
||||||
|
testResultsFilteredByForeignObject: function() {
|
||||||
|
var realm = new Realm({schema: [schemas.LinkTypes, schemas.TestObject]});
|
||||||
|
var realm2 = new Realm({path: '2.realm', schema: realm.schema});
|
||||||
|
var object;
|
||||||
|
|
||||||
|
realm2.write(function() {
|
||||||
|
object = realm2.create('TestObject', {doubleCol: 1});
|
||||||
|
});
|
||||||
|
|
||||||
TestCase.assertThrows(function() {
|
TestCase.assertThrows(function() {
|
||||||
realm.objects('PersonObject').filtered("invalidQuery");
|
realm.objects('LinkTypesObject').filtered('objectCol = $0', object);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue