Skip to content

Commit

Permalink
Merge branch 'main' into ni/obfuscation
Browse files Browse the repository at this point in the history
  • Loading branch information
nirinchev authored May 21, 2024
2 parents 57424c9 + 1298cb1 commit b91e683
Show file tree
Hide file tree
Showing 5 changed files with 1,579 additions and 1,564 deletions.
17 changes: 16 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,15 +3,30 @@
### Enhancements
* Added support for `Migration.FindInNewRealm` which is a helper that allows you to lookup the object in the post-migration Realm that corresponds to an object from the pre-migration Realm. (Issue [#3600](https://github.com/realm/realm-dotnet/issues/3600))
* Added `[System.Reflection.Obfuscation]` on the generated `RealmSchema` field to improve compatibility with obfuscation tools that change field and property names of generated classes. (Issue [#3574](https://github.com/realm/realm-dotnet/issues/3574))
* Added support for list and dictionaries of `RealmValue` (`IList<RealmValue>` and `IDictionary<string, RealmValue>`) to be contained in a `RealmValue`. Lists and dictionaries can contain an arbitrary number of collections themselves. It is possible to convert an existing collection to a `RealmValue` using the new static methods `RealmValue.List` and `RealmValue.Dictionary` or using the implicit operators if converting from common types like `List`, `RealmValue[]` or `Dictionary`. Finally, it is possible to obtain the contained collections by using the new conversion method `AsList` and `AsDictionary`. For example:

```csharp
var list = new List<RealmValue> { 1, true, "stringVal" };

var rvo = realm.Write(() =>
{
return realm.Add(new RealmValueObject { RealmValueProperty = list});
});

var retrievedList = rvo.RealmValueProperty.AsList();
```
(PR [#3441](https://github.com/realm/realm-dotnet/pull/3441))

### Fixed
* Accessing `App.CurrentUser` from within a `User.Changed` notification would deadlock. (Core 14.7.0)
* Inserting the same link to the same key in a dictionary more than once would incorrectly create multiple backlinks to the object. This did not appear to cause any crashes later, but would have affected the value returned by `RealmObject.BacklinksCount` and queries involving backlinks counts. (Core 14.7.0)
* Fixed an issue that would cause `RealmObject.DynamicApi.GetList/Set/Dictionary` to fail when the collection contains primitive values. (Issue [#3597](https://github.com/realm/realm-dotnet/issues/3597))

### Compatibility
* Realm Studio: 15.0.0 or later.

### Internal
* Using Core x.y.z.
* Using Core 14.7.0.

## 12.1.0 (2024-05-01)

Expand Down
48 changes: 24 additions & 24 deletions Realm/Realm/DatabaseTypes/RealmValue.cs
Original file line number Diff line number Diff line change
Expand Up @@ -217,7 +217,7 @@ private RealmValue(IDictionary<string, RealmValue> dict) : this()
/// <returns> A new RealmValue representing the input list. </returns>
/// <remarks> Once created, this RealmValue will just wrap the input collection.
/// After the object containing this RealmValue gets managed this value will be a Realm list.</remarks>
internal static RealmValue List(IList<RealmValue> value) => new(value);
public static RealmValue List(IList<RealmValue> value) => new(value);

/// <summary>
/// Gets a RealmValue representing a dictionary.
Expand All @@ -226,7 +226,7 @@ private RealmValue(IDictionary<string, RealmValue> dict) : this()
/// <returns> A new RealmValue representing the input dictionary. </returns>
/// <remarks> Once created, this RealmValue will just wrap the input collection.
/// After the object containing this RealmValue gets managed this value will be a Realm dictionary.</remarks>
internal static RealmValue Dictionary(IDictionary<string, RealmValue> value) => new(value);
public static RealmValue Dictionary(IDictionary<string, RealmValue> value) => new(value);

internal static RealmValue Create<T>(T value, RealmValueType type)
{
Expand Down Expand Up @@ -510,7 +510,7 @@ public string AsString()
/// </summary>
/// <exception cref="InvalidOperationException">Thrown if the underlying value is not of type <see cref="RealmValueType.List"/>.</exception>
/// <returns> A list representing the value stored in the database.</returns>
internal IList<RealmValue> AsList()
public IList<RealmValue> AsList()
{
EnsureType("List", RealmValueType.List);
return _listValue!;
Expand All @@ -521,7 +521,7 @@ internal IList<RealmValue> AsList()
/// </summary>
/// <exception cref="InvalidOperationException">Thrown if the underlying value is not of type <see cref="RealmValueType.Dictionary"/>.</exception>
/// <returns> A dictionary representing the value stored in the database.</returns>
internal IDictionary<string, RealmValue> AsDictionary()
public IDictionary<string, RealmValue> AsDictionary()
{
EnsureType("Dictionary", RealmValueType.Dictionary);
return _dictionaryValue!;
Expand Down Expand Up @@ -1448,26 +1448,26 @@ public override int GetHashCode()
/// <returns>A <see cref="RealmValue"/> containing the supplied <paramref name="val"/>.</returns>
public static implicit operator RealmValue(RealmObjectBase? val) => val == null ? Null : Object(val);

///// <summary>
///// Implicitly constructs a <see cref="RealmValue"/> from <see cref="System.Collections.Generic.List{T}">List&lt;RealmValue&gt;?</see>.
///// </summary>
///// <param name="val">The value to store in the <see cref="RealmValue"/>.</param>
///// <returns>A <see cref="RealmValue"/> containing the supplied <paramref name="val"/>.</returns>
//public static implicit operator RealmValue(List<RealmValue>? val) => val == null ? Null : List(val);

///// <summary>
///// Implicitly constructs a <see cref="RealmValue"/> from <see cref="RealmValue">RealmValue[]?</see>.
///// </summary>
///// <param name="val">The value to store in the <see cref="RealmValue"/>.</param>
///// <returns>A <see cref="RealmValue"/> containing the supplied <paramref name="val"/>.</returns>
//public static implicit operator RealmValue(RealmValue[]? val) => val == null ? Null : List(val);

///// <summary>
///// Implicitly constructs a <see cref="RealmValue"/> from <see cref="System.Collections.Generic.Dictionary{TKey, TValue}">Dictionary&lt;string, RealmValue&gt;</see>.
///// </summary>
///// <param name="val">The value to store in the <see cref="RealmValue"/>.</param>
///// <returns>A <see cref="RealmValue"/> containing the supplied <paramref name="val"/>.</returns>
//public static implicit operator RealmValue(Dictionary<string, RealmValue>? val) => val == null ? Null : Dictionary(val);
/// <summary>
/// Implicitly constructs a <see cref="RealmValue"/> from <see cref="System.Collections.Generic.List{T}">List&lt;RealmValue&gt;?</see>.
/// </summary>
/// <param name="val">The value to store in the <see cref="RealmValue"/>.</param>
/// <returns>A <see cref="RealmValue"/> containing the supplied <paramref name="val"/>.</returns>
public static implicit operator RealmValue(List<RealmValue>? val) => val == null ? Null : List(val);

/// <summary>
/// Implicitly constructs a <see cref="RealmValue"/> from <see cref="RealmValue">RealmValue[]?</see>.
/// </summary>
/// <param name="val">The value to store in the <see cref="RealmValue"/>.</param>
/// <returns>A <see cref="RealmValue"/> containing the supplied <paramref name="val"/>.</returns>
public static implicit operator RealmValue(RealmValue[]? val) => val == null ? Null : List(val);

/// <summary>
/// Implicitly constructs a <see cref="RealmValue"/> from <see cref="System.Collections.Generic.Dictionary{TKey, TValue}">Dictionary&lt;string, RealmValue&gt;</see>.
/// </summary>
/// <param name="val">The value to store in the <see cref="RealmValue"/>.</param>
/// <returns>A <see cref="RealmValue"/> containing the supplied <paramref name="val"/>.</returns>
public static implicit operator RealmValue(Dictionary<string, RealmValue>? val) => val == null ? Null : Dictionary(val);

private void EnsureType(string target, RealmValueType type)
{
Expand Down
Loading

0 comments on commit b91e683

Please sign in to comment.