Skip to content

Commit

Permalink
Metadata: Allow creating shadow navigation on shadow entity types
Browse files Browse the repository at this point in the history
  • Loading branch information
smitpatel committed Apr 22, 2016
1 parent 99d5630 commit 9d53615
Show file tree
Hide file tree
Showing 8 changed files with 464 additions and 107 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -467,7 +467,16 @@ protected virtual void GenerateForeignKey(
stringBuilder
.AppendLine()
.Append("b.HasOne(")
.Append(_code.Literal(foreignKey.PrincipalEntityType.Name))
.Append(_code.Literal(foreignKey.PrincipalEntityType.Name));

if (foreignKey.DependentToPrincipal != null)
{
stringBuilder
.Append(", ")
.Append(_code.Literal(foreignKey.DependentToPrincipal.Name));
}

stringBuilder
.Append(")")
.AppendLine();

Expand All @@ -476,7 +485,16 @@ protected virtual void GenerateForeignKey(
if (foreignKey.IsUnique)
{
stringBuilder
.AppendLine(".WithOne()")
.Append(".WithOne(");

if (foreignKey.PrincipalToDependent != null)
{
stringBuilder
.Append(_code.Literal(foreignKey.PrincipalToDependent.Name));
}

stringBuilder
.AppendLine(")")
.Append(".HasForeignKey(")
.Append(_code.Literal(foreignKey.DeclaringEntityType.Name))
.Append(", ")
Expand All @@ -499,7 +517,16 @@ protected virtual void GenerateForeignKey(
else
{
stringBuilder
.AppendLine(".WithMany()")
.Append(".WithMany(");

if (foreignKey.PrincipalToDependent != null)
{
stringBuilder
.Append(_code.Literal(foreignKey.PrincipalToDependent.Name));
}

stringBuilder
.AppendLine(")")
.Append(".HasForeignKey(")
.Append(string.Join(", ", foreignKey.Properties.Select(p => _code.Literal(p.Name))))
.Append(")");
Expand Down
34 changes: 22 additions & 12 deletions src/Microsoft.EntityFrameworkCore/Metadata/Internal/EntityType.cs
Original file line number Diff line number Diff line change
Expand Up @@ -848,18 +848,28 @@ public virtual Navigation AddNavigation(
Debug.Assert((pointsToPrincipal ? foreignKey.DeclaringEntityType : foreignKey.PrincipalEntityType) == this,
"EntityType mismatch");

Navigation.IsCompatible(
name,
this,
pointsToPrincipal ? foreignKey.PrincipalEntityType : foreignKey.DeclaringEntityType,
!pointsToPrincipal && !foreignKey.IsUnique,
shouldThrow: true);

// TODO: use this value for IsCompatible call
var navigationProperty = ClrType.GetPropertiesInHierarchy(name).FirstOrDefault();
Debug.Assert(navigationProperty != null);

var navigation = new Navigation(navigationProperty, foreignKey);
Navigation navigation = null;

if (ClrType != null)
{
Navigation.IsCompatible(
name,
this,
pointsToPrincipal ? foreignKey.PrincipalEntityType : foreignKey.DeclaringEntityType,
!pointsToPrincipal && !foreignKey.IsUnique,
shouldThrow: true);

// TODO: use this value for IsCompatible call
var navigationProperty = ClrType.GetPropertiesInHierarchy(name).FirstOrDefault();
Debug.Assert(navigationProperty != null);

navigation = new Navigation(navigationProperty, foreignKey);
}
else
{
navigation = new Navigation(name, foreignKey);
}

_navigations.Add(name, navigation);

PropertyMetadataChanged();
Expand Down
17 changes: 11 additions & 6 deletions src/Microsoft.EntityFrameworkCore/Metadata/Internal/Navigation.cs
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,15 @@ public Navigation([NotNull] PropertyInfo navigationProperty, [NotNull] ForeignKe
ForeignKey = foreignKey;
}

public Navigation([NotNull] string navigationName, [NotNull] ForeignKey foreignKey)
{
Check.NotEmpty(navigationName, nameof(navigationName));
Check.NotNull(foreignKey, nameof(foreignKey));

Name = navigationName;
ForeignKey = foreignKey;
}

public virtual string Name { get; }
public virtual ForeignKey ForeignKey { get; }

Expand Down Expand Up @@ -96,12 +105,8 @@ public static bool IsCompatible(
var sourceClrType = sourceType.ClrType;
if (sourceClrType == null)
{
if (shouldThrow)
{
throw new InvalidOperationException(
CoreStrings.NavigationOnShadowEntity(navigationPropertyName, sourceType.DisplayName()));
}
return false;
// Navigation defined on shadow entity type.
return true;
}

var targetClrType = targetType.ClrType;
Expand Down

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 0 additions & 3 deletions src/Microsoft.EntityFrameworkCore/Properties/CoreStrings.resx
Original file line number Diff line number Diff line change
Expand Up @@ -231,9 +231,6 @@
<data name="DuplicateNavigation" xml:space="preserve">
<value>The navigation property '{navigation}' cannot be added to the entity type '{entityType}' because a navigation property with the same name already exists on entity type '{duplicateEntityType}'.</value>
</data>
<data name="NavigationOnShadowEntity" xml:space="preserve">
<value>The navigation property '{navigation}' cannot be added to the entity type '{entityType}' because the entity type is defined in shadow state and navigations properties cannot be added to shadow state.</value>
</data>
<data name="NoClrNavigation" xml:space="preserve">
<value>The navigation property '{navigation}' cannot be added to the entity type '{entityType}' because there is no corresponding CLR property on the underlying type and navigations properties cannot be added to shadow state.</value>
</data>
Expand Down
Loading

0 comments on commit 9d53615

Please sign in to comment.