// detects whether the S-side Property represents the dependent side of an Association (e.g. for Split Entity or TPT or C-side Conditions) private static bool IsDependentSidePropertyInAssociation(Property storageProperty) { if (storageProperty == null || storageProperty.EntityModel.IsCSDL) { Debug.Fail( "should only receive a storage-side Property. Received property: " + (storageProperty == null ? "NULL" : storageProperty.ToPrettyString())); return true; // returning true will mean this table's SGP settings will not be adjusted } foreach (var propRef in storageProperty.GetAntiDependenciesOfType<PropertyRef>()) { var assoc = propRef.GetParentOfType(typeof(Association)) as Association; if (assoc == null) { // no Association parent - so ignore this PropertyRef continue; } foreach (var prop in assoc.DependentRoleProperties) { if (storageProperty.Equals(prop)) { // found storage property on the dependent side which is part of an association return true; } } } return false; }
private Property FindSSidePropInExistingArtifact(Property sSidePropInTempArtifact) { if (null == sSidePropInTempArtifact) { Debug.Fail("Null sSidePropInTempArtifact"); return null; } var existingArtifactSet = _preExistingModel.Artifact.ArtifactSet; if (null == existingArtifactSet) { Debug.Fail("Null ArtifactSet"); return null; } var sSidePropSymbolInTempArtifactSet = sSidePropInTempArtifact.NormalizedName; var sSidePropInExistingArtifact = existingArtifactSet.LookupSymbol(sSidePropSymbolInTempArtifactSet) as Property; if (null == sSidePropInTempArtifact) { Debug.Fail( "Cannot find matching Property for sSidePropInTempArtifact " + sSidePropInTempArtifact.ToPrettyString() + " in existing artifact"); return null; } return sSidePropInExistingArtifact; }
// detects whether the S-side Property is within the table which provides storage for a C-side non-root EntityType (e.g. in a TPT hierarchy) private static bool IsStorageForNonRootEntityType(Property storageProperty) { if (storageProperty == null || storageProperty.EntityModel.IsCSDL) { Debug.Fail( "should only receive a storage-side Property. Received property: " + (storageProperty == null ? "NULL" : storageProperty.ToPrettyString())); return true; // returning true will mean this table's SGP settings will not be adjusted } foreach (var sp in storageProperty.GetAntiDependenciesOfType<ScalarProperty>()) { var etm = sp.GetParentOfType(typeof(EntityTypeMapping)) as EntityTypeMapping; if (etm == null) { // no EntityTypeMapping parent - so don't count this mapping continue; } var etmKind = etm.Kind; if (EntityTypeMappingKind.Default != etmKind && EntityTypeMappingKind.IsTypeOf != etmKind) { // EntityTypeMapping is not for Default or IsTypeOf mapping - so don't count for finding the corresponding C-side EntityType continue; } var cSideEntityType = etm.FirstBoundConceptualEntityType; if (cSideEntityType != null && cSideEntityType.HasResolvableBaseType) { var inheritanceStrategy = ModelHelper.DetermineCurrentInheritanceStrategy(cSideEntityType); if (InheritanceMappingStrategy.TablePerType == inheritanceStrategy) { // C-side EntityType has TPT inheritance strategy and is not the base-most type in its inheritance hierarchy return true; } } } return false; }
/// <summary> /// In the existing artifact create a new C-side Property /// in the existing EntityType plus a mapping based on the /// C-side and S-side Properties in the temp artifact /// </summary> private Property CreateNewConceptualPropertyAndMapping( CommandProcessorContext cpc, Property cSidePropInTempArtifact, Property sSidePropInTempArtifact, EntityType existingEntityType) { Debug.Assert(cSidePropInTempArtifact != null, "Null C-side Property"); Debug.Assert(cSidePropInTempArtifact.EntityType.EntityModel.IsCSDL, "cSidePropInTempArtifact must be C-side"); Debug.Assert(sSidePropInTempArtifact != null, "Null S-side Property"); Debug.Assert(!sSidePropInTempArtifact.EntityType.EntityModel.IsCSDL, "sSidePropInTempArtifact must be S-side"); Debug.Assert(existingEntityType != null, "Null existing EntityType"); Debug.Assert(existingEntityType.EntityModel.IsCSDL, "Existing EntityType must be C-side"); var pcf = new PropertyClipboardFormat(cSidePropInTempArtifact); Debug.Assert( pcf != null, "Could not construct PropertyClipboardFormat for C-side Property " + cSidePropInTempArtifact.ToPrettyString()); if (null == pcf) { return null; } else { // store off matching S-side property in the existing // artifact for mapping below var sSidePropInExistingArtifact = FindSSidePropInExistingArtifact(sSidePropInTempArtifact); Debug.Assert( null != sSidePropInExistingArtifact, "Cannot find S-side Property matching the one in the temp artifact " + sSidePropInTempArtifact.ToPrettyString()); // create the C-side Property in the existing artifact var cmd = new CopyPropertyCommand(pcf, existingEntityType); CommandProcessor.InvokeSingleCommand(cpc, cmd); var cSidePropInExistingArtifact = cmd.Property; // now create the mapping for the C-side Property just created if (null != cSidePropInExistingArtifact && null != sSidePropInExistingArtifact) { var cmd2 = new CreateFragmentScalarPropertyCommand( existingEntityType, cSidePropInExistingArtifact, sSidePropInExistingArtifact); CommandProcessor.InvokeSingleCommand(cpc, cmd2); } return cSidePropInExistingArtifact; } }