Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -1279,11 +1279,23 @@ private void InitializeJsonColumn(
columnOperation.ClrType = typeof(string);
columnOperation.DefaultValue = inline || isNullable
? null
: "{}";
: IsJsonCollectionColumn(jsonColumn) ? "[]" : "{}";

columnOperation.AddAnnotations(migrationsAnnotations);
}

private static bool IsJsonCollectionColumn(JsonColumn jsonColumn)
=> jsonColumn.Table.ComplexTypeMappings.Any(
m => m.TypeBase is IComplexType ct
&& ct.GetContainerColumnName() == jsonColumn.Name
&& ct.ComplexProperty.IsCollection
&& !ct.ComplexProperty.DeclaringType.IsMappedToJson())
|| jsonColumn.Table.EntityTypeMappings.Any(
m => m.TypeBase is IEntityType et
&& et.GetContainerColumnName() == jsonColumn.Name
&& et.FindOwnership() is { IsUnique: false, PrincipalEntityType: var principal }
&& !principal.IsMappedToJson());

#endregion

#region IKey
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10007,6 +10007,202 @@ public virtual void Convert_table_from_owned_to_complex_properties_mapped_to_jso
Assert.Empty);
#pragma warning restore EF8001 // Owned JSON entities are obsolete

[ConditionalFact]
public virtual void Add_complex_collection_mapped_to_json_uses_empty_array_as_default_value()
=> Execute(
_ => { },
source =>
{
source.Entity(
"Entity", e =>
{
e.Property<int>("Id").ValueGeneratedOnAdd();
e.HasKey("Id");
});
},
target =>
{
target.Entity(
"Entity", e =>
{
e.Property<int>("Id").ValueGeneratedOnAdd();
e.HasKey("Id");

e.ComplexCollection<List<MyJsonComplex>, MyJsonComplex>(
"ComplexCollection", cp =>
{
cp.IsRequired();
cp.ToJson("json_collection");
cp.Property(x => x.Value);
cp.Property(x => x.Date);
});
});
},
upOps =>
{
Assert.Equal(1, upOps.Count);

var operation = Assert.IsType<AddColumnOperation>(upOps[0]);
Assert.Equal("Entity", operation.Table);
Assert.Equal("json_collection", operation.Name);
Assert.Equal("[]", operation.DefaultValue);
},
downOps =>
{
Assert.Equal(1, downOps.Count);
Assert.IsType<DropColumnOperation>(downOps[0]);
});

[ConditionalFact]
public virtual void Add_complex_reference_with_nested_collection_mapped_to_json_uses_empty_object_as_default_value()
=> Execute(
_ => { },
source =>
{
source.Entity(
"Entity", e =>
{
e.Property<int>("Id").ValueGeneratedOnAdd();
e.HasKey("Id");
});
},
target =>
{
target.Entity(
"Entity", e =>
{
e.Property<int>("Id").ValueGeneratedOnAdd();
e.HasKey("Id");

e.ComplexProperty<MyJsonComplex>(
"ComplexReference", cp =>
{
cp.IsRequired();
cp.ToJson("json_reference");
cp.Property(x => x.Value);
cp.Property(x => x.Date);
cp.ComplexCollection(
x => x.NestedCollection, nc => { });
});
});
},
upOps =>
{
Assert.Equal(1, upOps.Count);

var operation = Assert.IsType<AddColumnOperation>(upOps[0]);
Assert.Equal("Entity", operation.Table);
Assert.Equal("json_reference", operation.Name);
Assert.Equal("{}", operation.DefaultValue);
},
downOps =>
{
Assert.Equal(1, downOps.Count);
Assert.IsType<DropColumnOperation>(downOps[0]);
});

#pragma warning disable EF8001 // Owned JSON entities are obsolete
[ConditionalFact]
public virtual void Add_owned_collection_mapped_to_json_has_nullable_column()
=> Execute(
_ => { },
source =>
{
source.Entity(
"Entity", e =>
{
e.Property<int>("Id").ValueGeneratedOnAdd();
e.HasKey("Id");
});
},
target =>
{
target.Entity(
"Entity", e =>
{
e.Property<int>("Id").ValueGeneratedOnAdd();
e.HasKey("Id");

e.OwnsMany(
"Owned", "json_collection", o =>
{
o.ToJson();
o.Property<string>("Value");
o.Property<DateTime>("Date");
});
});
},
upOps =>
{
Assert.Equal(1, upOps.Count);

var operation = Assert.IsType<AddColumnOperation>(upOps[0]);
Assert.Equal("Entity", operation.Table);
Assert.Equal("json_collection", operation.Name);
// Owned collections are always nullable (IsUnique is false), so no default value
Assert.True(operation.IsNullable);
Assert.Null(operation.DefaultValue);
},
downOps =>
{
Assert.Equal(1, downOps.Count);
Assert.IsType<DropColumnOperation>(downOps[0]);
});
#pragma warning restore EF8001 // Owned JSON entities are obsolete

#pragma warning disable EF8001 // Owned JSON entities are obsolete
[ConditionalFact]
public virtual void Add_owned_reference_with_nested_collection_mapped_to_json_uses_empty_object_as_default_value()
=> Execute(
_ => { },
source =>
{
source.Entity(
"Entity", e =>
{
e.Property<int>("Id").ValueGeneratedOnAdd();
e.HasKey("Id");
});
},
target =>
{
target.Entity(
"Entity", e =>
{
e.Property<int>("Id").ValueGeneratedOnAdd();
e.HasKey("Id");

e.OwnsOne(
"Owned", "json_reference", o =>
{
o.ToJson();
o.Property<string>("Value");
o.OwnsMany(
"Nested", "NestedCollection", n =>
{
n.Property<int>("Number");
});
});

e.Navigation("json_reference").IsRequired();
});
},
upOps =>
{
Assert.Equal(1, upOps.Count);

var operation = Assert.IsType<AddColumnOperation>(upOps[0]);
Assert.Equal("Entity", operation.Table);
Assert.Equal("json_reference", operation.Name);
Assert.Equal("{}", operation.DefaultValue);
},
downOps =>
{
Assert.Equal(1, downOps.Count);
Assert.IsType<DropColumnOperation>(downOps[0]);
});
#pragma warning restore EF8001 // Owned JSON entities are obsolete

[ConditionalFact]
public virtual void Noop_on_complex_properties()
=> Execute(
Expand Down
Loading