private object AssembleHref( ResourceProfileData profileData, ResourceClassBase resource, AssociationView association = null) { if (resource.IsAggregateRoot()) { return(new { StandardLink = new { ResourceName = resource.Name, ResourceBaseRoute = GetResourceCollectionRelativeRoute(resource as Resource), } }); } if (association == null) { return(ResourceRenderer.DoNotRenderProperty); } return(new { StandardLink = new { Rel = association.OtherEntity.Name, ResourceBaseRoute = $"/{association.OtherEntity.SchemaUriSegment()}/{association.OtherEntity.PluralName.ToCamelCase()}", } }); }
public object InheritedNavigableOneToOnes(ResourceProfileData profileData, ResourceClassBase resourceClass) { var embeddedObjectPairs = Resources.GetMemberItemPairs(resourceClass, r => r?.EmbeddedObjects); return(embeddedObjectPairs .Where(x => x.Underlying.IsInherited) .OrderBy(x => x.Underlying.PropertyName) .Select( x => new { JsonPropertyName = x.Underlying.JsonPropertyName, EmbeddedObjectInterfaceNamespacePrefix = GetContextualNamespacePrefix(x.Underlying.ObjectType), EmbeddedObjectInterfaceType = "I" + x.Underlying.PropertyName, EmbeddedObjectTypeNamespace = $"{Namespaces.Resources.RelativeNamespace}.{resourceClass.Entity.BaseEntity.Name}.{resourceClass.Entity.BaseEntity.SchemaProperCaseName()}.", EmbeddedObjectType = x.Underlying.PropertyName, PropertyName = x.Underlying.PropertyName, BaseEntityNamespacePrefix = $"{Namespaces.Entities.Common.RelativeNamespace}.{resourceClass.Entity.BaseEntity.SchemaProperCaseName()}.", BaseEntityName = resourceClass.Entity.BaseEntity.Name, Standard = x.Current != null, Null = x.Current == null }) .ToList()); }
public object InheritedCollections( ResourceProfileData profileData, ResourceClassBase resource, TemplateContext templateContext) { if (resource.IsDescriptorEntity()) { return(ResourceRenderer.DoRenderProperty); } string ns = profileData.GetProfileNamespace(resource); var activeResource = profileData.GetProfileActiveResource(resource); return(activeResource.IsDerived && activeResource.Collections.Any() ? new { Inherited = activeResource.Collections .Where(x => x.IsInherited) .OrderBy(x => x.PropertyName) .Select( x => new { BaseEntity = $"{resource.Entity.BaseEntity.Name}.{resource.Entity.BaseEntity.SchemaProperCaseName()}", BaseEntityInterfaceName = $"I{resource.Entity.BaseEntity.Name}", ItemTypeNamespacePrefix = GetContextualNamespacePrefix(x.ItemType), ItemType = x.ItemType.Name, Collection = x.ItemType.PluralName, PropertyName = x.PropertyName, JsonPropertyName = x.IsDerivedEntityATypeEntity() ? x.Association.OtherEntity.PluralName.ToCamelCase() : x.JsonPropertyName, PropertyFieldName = x.ItemType.PluralName.ToCamelCase(), ParentName = x.ParentFullName.Name, PropertyNamespace = ns, ResourceName = resource.Name, Standard = profileData.IsIncluded(resource, x) && !profileData.IsFilteredCollection(resource, x), Null = !profileData.IsIncluded(resource, x), Filtered = profileData.IsIncluded(resource, x) && profileData.IsFilteredCollection( resource, x) }) .ToList() } : ResourceRenderer.DoNotRenderProperty); }
private object AssembleConstructor(ResourceProfileData profileData, ResourceClassBase resource) { string ns = profileData.GetProfileNamespace(resource); var activeResource = profileData.GetProfileActiveResource(resource); return(activeResource.Collections.Any() ? new { Inherited = resource.IsDerived && activeResource.Collections.Any(x => x.IsInherited) ? ResourceRenderer.DoRenderProperty : ResourceRenderer.DoNotRenderProperty, InheritedCollections = resource.Collections .Where(x => x.IsInherited) .Select( x => new { BaseEntity = $"{resource.Entity.BaseEntity.Name}.{resource.Entity.BaseEntity.SchemaProperCaseName()}", PropertyName = x.ItemType.PluralName, PropertyNamespace = ns, CollectionName = x.ItemType.Name }) .ToList(), Standard = resource.Collections.Any(x => !x.IsInherited) ? ResourceRenderer.DoRenderProperty : ResourceRenderer.DoNotRenderProperty, Collections = resource.Collections .Where( x => !x.IsInherited && profileData.IsIncluded(resource, x) && TemplateContext.ShouldRenderResourceClass( x.ItemType)) .Select( x => new { PropertyName = x.ItemType.PluralName, PropertyNamespace = ns, CollectionName = x.ItemType.Name }) .ToList() } : ResourceRenderer.DoNotRenderProperty); }
private ResourceClassBase GetContextualParent( ResourceChildItem resourceChildItem, ResourceProfileData profileData) { if (resourceChildItem == null) { return(null); } if (profileData.IsBaseResource && resourceChildItem.IsInheritedChildItem) { return(profileData.ContextualRootResource.AllContainedItemTypes.Single( x => x.FullName == resourceChildItem.FullName) .Parent); } return(resourceChildItem.Parent); }
public object Collections( ResourceProfileData profileData, ResourceClassBase resourceClass, TemplateContext TemplateContext) { var collectionPairs = Resources.GetMemberItemPairs(resourceClass, r => r?.Collections); string ns = profileData.GetProfileNamespace(resourceClass); return(collectionPairs .Where( itemPair => !itemPair.Underlying.IsInherited) .OrderBy(x => x.Underlying.PropertyName) .Select( itemPair => new { ItemTypeNamespacePrefix = GetContextualNamespacePrefix(itemPair.Underlying.ItemType), ItemType = itemPair.Underlying.ItemType.Name, Collection = itemPair.Underlying.ItemType.PluralName, PropertyName = itemPair.Underlying.PropertyName, JsonPropertyName = itemPair.Underlying.JsonPropertyName, PropertyFieldName = itemPair.Underlying.ItemType.PluralName.ToCamelCase(), ParentName = itemPair.Underlying.ParentFullName.Name, PropertyNamespace = ns, Standard = // It's included itemPair.Current != null // It's not filtered && !itemPair.Current.ValueFilters.Any(), Null = itemPair.Current == null, Filtered = // It's included itemPair.Current != null // It's filtered && itemPair.Current.ValueFilters.Any(), BaseEntity = resourceClass.Name }) .ToList()); }
public object NavigableOneToOnes(ResourceProfileData profileData, ResourceClassBase resourceClass) { var embeddedObjectPairs = Resources.GetMemberItemPairs(resourceClass, r => r?.EmbeddedObjects); return(embeddedObjectPairs .Where(x => !x.Underlying.IsInherited) .OrderBy(x => x.Underlying.PropertyName) .Select( x => new { JsonPropertyName = x.Underlying.JsonPropertyName, EmbeddedObjectNamespacePrefix = GetContextualNamespacePrefix(x.Underlying.ObjectType), EmbeddedObjectType = x.Underlying.PropertyName, PropertyName = x.Underlying.PropertyName, ParentName = resourceClass.Name, Standard = x.Current != null, Null = x.Current == null }) .ToList()); }
public object AssembleInheritedProperties( ResourceProfileData profileData, ResourceClassBase resource) { if (profileData == null) { throw new ArgumentNullException(nameof(profileData)); } if (resource == null) { throw new ArgumentNullException(nameof(resource)); } IList <ResourcePropertyData> includedProperties = null; if (profileData.HasProfile) { includedProperties = (resource.Name == profileData.SuppliedResource.Name ? profileData.UnfilteredResource : resource).InheritedProperties() .Where(x => !x.IsIdentifying && !x.PropertyName.Equals("Id")) .OrderBy(x => x.PropertyName) .Select( x => new ResourcePropertyData { Property = x, IsStandardProperty = !profileData.IsIncluded(resource, x) }) .ToList(); } else { includedProperties = resource.InheritedProperties() .OrderBy(x => x.PropertyName) .Where(x => !x.IsIdentifying && !x.PropertyName.Equals("Id")) .Select( x => new ResourcePropertyData { Property = x, IsStandardProperty = false }) .ToList(); } var propertiesToRender = new List <PropertyData>(); if (resource.IsDescriptorEntity() && resource.InheritedProperties() .Any(x => !x.IsIdentifying && !x.PropertyName.Equals("Id"))) { propertiesToRender.AddRange( includedProperties.Select( x => { var propertyData = x.IsStandardProperty ? PropertyData.CreateNullProperty(x.Property) : PropertyData.CreateStandardProperty(x.Property); propertyData[ResourceRenderer.MiscellaneousComment] = "// NOT in a reference, NOT a lookup column "; return(propertyData); })); } else if (resource.IsDerived) { propertiesToRender.AddRange( includedProperties.Select( x => x.IsStandardProperty ? PropertyData.CreateNullProperty(x.Property) : PropertyData.CreateStandardProperty(x.Property))); } return(propertiesToRender.Any() ? new { Properties = CreatePropertyDtos(propertiesToRender) } : ResourceRenderer.DoNotRenderProperty); }
public object OnDeserialize(ResourceProfileData profileData, ResourceClassBase resource, TemplateContext TemplateContext) { bool shouldRender = !(profileData.HasProfile && !profileData.HasNavigableChildren(resource)); if (!profileData.HasProfile && !(resource.Collections.Any() || !resource.IsAggregateRoot() && resource.HasBackReferences())) { shouldRender = false; } if (!shouldRender) { return(ResourceRenderer.DoNotRenderProperty); } if (resource.IsDerived && !resource.IsDescriptorEntity()) { return(new { Inherited = resource.Collections.Any(x => x.IsInherited) ? ResourceRenderer.DoRenderProperty : ResourceRenderer.DoNotRenderProperty, InheritedCollections = resource.Collections.Where(x => x.IsInherited) .OrderBy(x => x.PropertyName) .Select( x => new { PropertyFieldName = x.ItemType.PluralName.ToCamelCase() }) .ToList(), Standard = resource.Collections.Any(x => !x.IsInherited) ? ResourceRenderer.DoRenderProperty : ResourceRenderer.DoNotRenderProperty, Collections = resource.Collections .Where(x => !x.IsInherited && TemplateContext.ShouldRenderEntity(x.ItemType.Entity)) .OrderBy(x => x.PropertyName) .Select( x => new { ItemType = x.ItemType.Name, Collection = x.ItemType.PluralName, PropertyName = x.PropertyName, // using the property name so we do not break the data member contract // from the original template. JsonPropertyName = x.PropertyName .TrimPrefix(x.ParentFullName.Name) .ToCamelCase(), PropertyFieldName = x.ItemType.PluralName.ToCamelCase(), ParentName = x.ParentFullName.Name }) .ToList() }); } if (resource.Collections.Any(c => profileData.IsIncluded(resource, c)) || !resource.IsAggregateRoot() && resource.References.Any(x => profileData.IsIncluded(resource, x))) { return(new { BackRef = !resource.IsAggregateRoot() && resource.HasBackReferences() ? ResourceRenderer.DoRenderProperty : ResourceRenderer.DoNotRenderProperty, BackRefCollections = resource.References .Where(x => profileData.IsIncluded(resource, x)) .OrderBy(x => x.PropertyName) .Select( x => new { ReferenceTypeName = x.ReferenceTypeName, PropertyFieldName = x.PropertyName.ToCamelCase() }) .ToList(), Standard = resource.Collections.Any(x => !x.IsInherited) ? ResourceRenderer.DoRenderProperty : ResourceRenderer.DoNotRenderProperty, Collections = resource.Collections .OrderBy(x => x.PropertyName) .Select( x => new { ItemType = x.ItemType.Name, Collection = x.ItemType.PluralName, PropertyName = x.PropertyName, // using the property name so we do not break the data member contract // from the original template. JsonPropertyName = x.PropertyName .TrimPrefix(x.ParentFullName.Name) .ToCamelCase(), PropertyFieldName = x.ItemType.PluralName.ToCamelCase(), ParentName = x.ParentFullName.Name }) .ToList(), Inherited = resource.Collections.Any(x => x.IsInherited) ? ResourceRenderer.DoRenderProperty : ResourceRenderer.DoNotRenderProperty, InheritedCollections = resource.Collections.Where(x => x.IsInherited) .OrderBy(x => x.PropertyName) .Select(x => new { PropertyFieldName = x.ItemType.PluralName.ToCamelCase() }) .ToList() }); } return(ResourceRenderer.DoNotRenderProperty); }
public object References(ResourceProfileData profileData, ResourceClassBase resource, TemplateContext TemplateContext) { var activeResource = profileData.GetProfileActiveResource(resource); var references = activeResource.References .ToList(); if (!references.Any(x => profileData.IsIncluded(resource, x))) { return(ResourceRenderer.DoNotRenderProperty); } if (activeResource.IsAggregateRoot() || !activeResource.HasBackReferences()) { return(new { Collections = references .Where(x => profileData.IsIncluded(resource, x)) .OrderBy(x => x.PropertyName) .Select( x => { bool renderNamespace = !(x.Association.IsSelfReferencing || x.Association.IsSelfReferencingManyToMany) || x.Association.OtherEntity.IsAbstract || !x.Association.OtherEntity.IsSameAggregate( resource.Entity); string referenceName = !renderNamespace ? x.ReferenceTypeName : $"{x.ReferencedResourceName}.{x.ReferencedResource.Entity.SchemaProperCaseName()}.{x.ReferenceTypeName}"; return new { Reference = new { ReferencedResourceName = x.ReferencedResourceName, ReferenceTypeName = !x.ReferencedResource.Entity .IsExtensionEntity && !x.ReferenceTypeName.Replace("Reference", string.Empty) .Equals(resource.Name) && !x.ReferenceTypeName.Replace("Reference", string.Empty) .Equals((resource as ResourceChildItem)?.Parent.Name) ? $"{x.ReferencedResourceName}.{EdFiConventions.ProperCaseName}.{x.ReferenceTypeName}" : referenceName, Name = x.ParentFullName.Name, // using the property name so we do not break the data member contract // from the original template. JsonPropertyName = x.PropertyName.ToCamelCase(), PropertyName = x.PropertyName, PropertyFieldName = x.PropertyName.ToCamelCase(), IsRequired = x.IsRequired, IsIdentifying = x.Association.IsIdentifying }, Standard = ResourceRenderer.DoRenderProperty }; } ) .ToList() }); } return(new { Collections = activeResource.References .OrderBy(x => x.PropertyName) .Select( x => new { Reference = new { ReferencedResourceName = x.ReferencedResourceName, ReferenceTypeName = x.ReferenceTypeName, Name = x.ParentFullName.Name, JsonPropertyName = x.JsonPropertyName, PropertyName = x.PropertyName, PropertyFieldName = x.PropertyName.ToCamelCase(), IsRequired = x.IsRequired, IsIdentifying = x.Association.IsIdentifying, BackReferenceType = string.Format( "{0}To{1}Reference", x.Association.ThisEntity.Name, x.Association.OtherEntity.Name) }, Backref = ResourceRenderer.DoRenderProperty } ) .ToList() }); }
public object CreatePutPostRequestValidator( ResourceProfileData profileData, ResourceClassBase resource, TemplateContext templateContext) { var resourceChildItem = resource as ResourceChildItem; return(new PutPostRequestValidator { EntityName = resource.Name, Collections = resource.Collections // TODO: Remove this filter with dynamic profiles .Where(collection => !profileData.HasProfile || profileData.IsIncluded(resource, collection)) .Select( collection => new PutPostRequestValidatorCollectionProperty { PropertyName = collection.PropertyName, PropertyFieldNamePrefix = collection.PropertyName.ToCamelCase(), ItemTypeName = collection.ItemType.Name, Namespace = collection.ParentFullName.Name != resource.Name ? string.Format( "{0}.{1}.{2}", collection.ParentFullName.Name, profileData.HasProfile ? resource.SchemaProperCaseName : resource.Entity.BaseEntity.SchemaProperCaseName(), profileData.ProfilePropertyNamespaceSection) : ResourceRenderer.DoNotRenderProperty }), HasProfileItemFilterValidations = profileData.HasProfile && profileData.IsWritable && profileData.HasFilteredCollection() && GetItemFilterValidations().Any(), ProfileItemFilterValidations = GetItemFilterValidations(), KeyUnificationValidations = new KeyUnificationValidation { ResourceClassName = resource.Name, ParentResourceClassName = resourceChildItem?.Parent.Name, UnifiedProperties = resource.AllProperties // TODO: Remove this filter with dynamic profiles .Where(rp => !profileData.HasProfile || profileData.IsIncluded(resource, rp)) .Where(rp => rp.IsUnified()) .Select(rp => new UnifiedProperty { UnifiedPropertyName = rp.PropertyName, UnifiedJsonPropertyName = rp.JsonPropertyName, UnifiedCSharpPropertyType = rp.PropertyType.ToCSharp(), UnifiedPropertyIsFromParent = rp.EntityProperty.IncomingAssociations .Any(a => a.IsNavigable), UnifiedPropertyParentPath = resourceChildItem != null && resourceChildItem.IsResourceExtension ? string.Join( string.Empty, resourceChildItem.GetLineage().TakeWhile(l => !l.IsResourceExtension) .Select(l => "." + l.Name)) : null, References = rp.EntityProperty.IncomingAssociations .Where(a => !a.IsNavigable && rp.Parent.ReferenceByName.ContainsKey(a.Name + "Reference")) .Select(a => new { Reference = rp.Parent.ReferenceByName[a.Name + "Reference"], OtherEntityPropertyName = a.PropertyMappings.Where(pm => pm.ThisProperty.Equals(rp.EntityProperty)).Select(pm => pm.OtherProperty.PropertyName).Single(), }) // TODO: Remove this filter with dynamic profiles .Where(x => !profileData.HasProfile || profileData.IsIncluded(resource, x.Reference)) .Select(x => new { Reference = x.Reference, ReferenceProperty = (x.Reference.ReferenceTypeProperties .SingleOrDefault(rtp => rtp.EntityProperty.PropertyName == x.OtherEntityPropertyName) // Deal with the special case of the re-pointing of the identifying property from USI to UniqueId in Person entities ?? x.Reference.ReferenceTypeProperties .Single(rtp => rtp.EntityProperty.PropertyName == EdFi.Ods.Common.Specifications.UniqueIdSpecification.GetUniqueIdPropertyName(x.OtherEntityPropertyName))) }) .Select(x => new UnifiedReferenceProperty { ReferenceName = x.Reference.PropertyName, ReferenceJsonName = x.Reference.JsonPropertyName, ReferencePropertyName = x.ReferenceProperty.PropertyName, ReferenceJsonPropertyName = x.ReferenceProperty.JsonPropertyName }) }) } }); IEnumerable <ItemFilterValidation> GetItemFilterValidations() { return(resource.Collections .Where(x => profileData.IsFilteredCollection(resource, x)) .OrderBy(x => x.PropertyName) .SelectMany( x => profileData.GetFilteredCollection(resource, x) .ValueFilters .Select( y => new ItemFilterValidation { PropertyName = x.PropertyName, ValidatorName = x.ItemType.Name, ValidatorPropertyName = y.PropertyName, PropertyFieldName = x.ItemType.Name.ToCamelCase(), Filters = string.Join(", ", y.Values.Select(s => string.Format("'{0}'", s))), ProfileName = profileData.ProfileName }))); } }
public object FilteredDelegates(ResourceProfileData profileData, ResourceClassBase resourceClass) { var collectionPairs = Resources.GetMemberItemPairs(resourceClass, r => r?.Collections); if (!collectionPairs.Any()) { return(ResourceRenderer.DoNotRenderProperty); } var toRender = new List <object>(); //unfiltered objects toRender.AddRange( collectionPairs.Where(x => x.Current == null || !x.Current.ValueFilters.Any()) .Select( x => new { ItemTypeNamespacePrefix = x.Underlying.ItemType.GetNamespacePrefix(), ItemType = x.Underlying.ItemType.Name, PropertyName = x.Underlying.ItemType.Name, ParentName = resourceClass.IsDerived && !resourceClass.IsDescriptorEntity() ? resourceClass.Entity.Aggregate.Name : x.Underlying.ParentFullName.Name, Standard = ResourceRenderer.DoRenderProperty })); // filtered objects toRender.AddRange( collectionPairs .Where(x => x.Current != null && x.Current.ValueFilters.Any()) .OrderBy(x => x.Underlying.PropertyName) .Select( x => new { ItemTypeNamespacePrefix = x.Underlying.ItemType.GetNamespacePrefix(), ItemType = x.Underlying.ItemType.Name, PropertyName = x.Underlying.ItemType.Name, ParentName = resourceClass.IsDerived && !resourceClass.IsDescriptorEntity() ? resourceClass.Entity.Aggregate.Name : x.Underlying.ParentFullName.Name, FilteredValues = x.Current.ValueFilters .SelectMany( y => y.Values.Select( z => new { FilteredPropertyName = y.PropertyName, FilteredValue = z, NotFirst = z != y.Values.First(), IsIncluded = y.FilterMode == ItemFilterMode.IncludeOnly, IsLast = z == y.Values.Last() })), Filtered = ResourceRenderer.DoRenderProperty })); return(toRender.Any() ? toRender : ResourceRenderer.DoNotRenderProperty); }
private object CreateContextSpecificResourceReferences(ResourceProfileData profileData, ResourceClassBase resource) { if (resource.IsAggregateRoot() || !resource.HasBackReferences()) { return(ResourceRenderer.DoNotRenderProperty); } var externalAssociations = resource.ExternalReferenceAssociations() .ToList(); var refs = externalAssociations.Select( av => new { ContextSpecificResourceReference = new { NamespacePrefix = resource.GetNamespacePrefix(), ReferenceName = string.Format( "{0}To{1}", av.ThisEntity.Name, av.OtherEntity.Name), // Leaving this member definition inline as this entire method // is to be deprecated in the future. ContextualReferenceIdentifier = av.ThisProperties .Where(p => (p.IsUnified && p.IsIdentifying)) .Select( p => av.PropertyMappingByThisName[p.PropertyName] .OtherProperty .ToResourceProperty(resource)) .OrderBy(p => p.PropertyName) .Select(p => new { PropertyName = p.PropertyName, JsonPropertyName = p.JsonPropertyName, PropertyType = p.PropertyType.ToCSharp(), // Use GetLineage to build the property path, in reverse order, skipping the first since that's the BackReference itself PropertyPathToRoot = "BackReference." + string.Join(".", ((ResourceChildItem)resource).GetLineage().Reverse().Skip(1).Select(l => l.Name)) }), ReferenceIdentifiers = _resourcePropertyRenderer.AssembleIdentifiers( profileData, resource, av), Href = AssembleHref(profileData, resource, av), HasDiscriminator = av.OtherEntity.HasDiscriminator(), ThisEntityName = av.ThisEntity.Name, OtherEntityName = av.OtherEntity.Name, BackReference = string.Format( "backreference.{0}.", (resource as ResourceChildItem)?.Parent.Name), ReferenceFullyDefined = _resourcePropertyRenderer .AssembleReferenceFullyDefined( resource, av) } } ) .ToList(); return(refs); }
public object SynchronizationSourceSupport( ResourceProfileData profileData, ResourceClassBase resourceClass, TemplateContext TemplateContext) { var collectionPairs = Resources.GetMemberItemPairs(resourceClass, r => r?.Collections); var synchSupportCollections = collectionPairs.Select( itemPair => { bool isExcluded = itemPair.Current == null; return(new { ParentName = resourceClass.IsDerived ? resourceClass.Name : itemPair.Underlying.Parent.Name, PropertyName = itemPair.Underlying.ItemType.PluralName, IsExcluded = isExcluded }); }); // Properties var allPossibleProperties = resourceClass.FilterContext.UnfilteredResourceClass?.AllProperties ?? resourceClass.AllProperties; var currentProperties = resourceClass.AllProperties; var propertyPairs = (from p in allPossibleProperties join c in currentProperties on p.PropertyName equals c.PropertyName into leftJoin from _c in leftJoin.DefaultIfEmpty() where p.IsSynchronizable() orderby p.PropertyName select new { UnderlyingProperty = p, CurrentProperty = _c }) .ToList(); var synchSupportProperties = propertyPairs.Select( x => { bool isExcluded = x.CurrentProperty == null; return(new { ParentName = x.UnderlyingProperty.Parent != null ? x.UnderlyingProperty.Parent.Name : resourceClass.Name, PropertyName = x.UnderlyingProperty.PropertyName, IsExcluded = isExcluded }); }) .ToList(); // Embedded Objects var allPossibleEmbeddedObjects = resourceClass.FilterContext.UnfilteredResourceClass?.EmbeddedObjects ?? resourceClass.EmbeddedObjects; var currentEmbeddedObjects = resourceClass.EmbeddedObjects; var embeddedObjectPairs = (from p in allPossibleEmbeddedObjects join c in currentEmbeddedObjects on p.PropertyName equals c.PropertyName into leftJoin from _c in leftJoin.DefaultIfEmpty() orderby p.PropertyName select new { UnderlyingEmbeddedObject = p, CurrentEmbeddedObject = _c }) .ToList(); var synchSupportEmbeddedObjects = embeddedObjectPairs.Select( x => new { ParentName = x.UnderlyingEmbeddedObject.Parent.Name, PropertyName = x.UnderlyingEmbeddedObject.PropertyName, IsExcluded = x.CurrentEmbeddedObject == null }); var synchSupportMembers = synchSupportCollections .Concat(synchSupportProperties) .Concat(synchSupportEmbeddedObjects) .ToList(); if (!synchSupportMembers.Any()) { return(ResourceRenderer.DoNotRenderProperty); } int horizontalSpaceAllocation = synchSupportMembers.Max(x => x.PropertyName.Length) + "IsSupported".Length + 1; return (synchSupportMembers .OrderBy(x => x.PropertyName) .Distinct() .Select( x => new { ParentName = x.ParentName, PropertyName = x.PropertyName, SourceSupport = string.Format("Is{0}Supported", x.PropertyName) .PadRight(horizontalSpaceAllocation), IsExcluded = x.IsExcluded }) .ToList()); }
private object CreateContextualResourceClasses( ResourceProfileData profileData, string contextualSchemaPhysicalName) { var contextualItemFullNames = new HashSet <FullName>(profileData.ContextualRootResource.AllContainedItemTypes.Select(x => x.FullName)); var resourceClasses = // Create the model for the root class of the resource (if it should be rendered in the current context) (TemplateContext.ShouldRenderResourceClass(profileData.ContextualRootResource) && profileData.ContextualRootResource.FullName.Schema == contextualSchemaPhysicalName ? new[] { CreateResourceClass(profileData, profileData.ContextualRootResource) } : new object[0]) // Add in all the Contained Item Types for the resource .Concat( profileData.SuppliedResource .AllContainedItemTypes // Where the item should be generated for the current resource namespace context .Where(x => contextualItemFullNames.Contains(x.FullName)) // Only render items for resource classes that are in the same schema for the code generation context .Where(x => TemplateContext.ShouldRenderResourceClass(x)) .Where(x => x.FullName.Schema == contextualSchemaPhysicalName) // When generating non-Ed-Fi schema for an Ed-Fi resource, only include resource extension classes, otherwise only include non-resource-extension classes. .Where( x => x.IsResourceExtension == (profileData.ContextualRootResource.IsEdFiStandardResource && contextualSchemaPhysicalName != EdFiConventions.PhysicalSchemaName)) .Where( x => { // For contexts where the root resource class is derived, don't render inherited children if (profileData.IsDerived) { return(!x.IsInheritedChildItem); } // For contexts where the root resource class is a base class, only render its children // if the concrete version of the resource needs it. if (profileData.IsBaseResource) { return(profileData.SuppliedResource .AllContainedItemTypes.Any( i => x.FullName == i.FullName)); } return(true); }) .OrderBy(x => x.Name) .Select(x => CreateResourceClass(profileData, x))) .ToList(); return(resourceClasses.Any() ? resourceClasses .Select( rc => new { ResourceClass = rc }) .ToList() : ResourceRenderer.DoNotRenderProperty); }
public object AssembleIdentifiers( ResourceProfileData profileData, ResourceClassBase resource, AssociationView association = null) { if (profileData == null) { throw new ArgumentNullException(nameof(profileData)); } if (resource == null) { throw new ArgumentNullException(nameof(resource)); } if (!resource.IdentifyingProperties.Any() && association == null) { return(ResourceRenderer.DoNotRenderProperty); } IList <ResourceProperty> properties; var activeResource = profileData.GetProfileActiveResource(resource); if (resource.IsAggregateRoot()) { properties = activeResource.IdentifyingProperties .OrderBy(x => x.PropertyName) .ToList(); } else { if (association != null) { properties = association.ThisProperties .Where(x => !(x.IsUnified && x.IsIdentifying)) .Select( x => association.PropertyMappingByThisName[x.PropertyName] .OtherProperty .ToResourceProperty(resource)) .OrderBy(x => x.PropertyName) .ToList(); } else { properties = resource.IdentifyingProperties .Where(x => !x.EntityProperty.IsLocallyDefined) .OrderBy(x => x.PropertyName) .ToList(); } } ResourceProperty first = properties.FirstOrDefault(); ResourceProperty last = properties.LastOrDefault(); return(properties.Any() ? properties.Select( y => new PropertyData(y) { IsFirstProperty = y == first, IsLastProperty = y == last }.Render()) .ToList() : ResourceRenderer.DoNotRenderProperty); }
private object CreateResourceClass(ResourceProfileData profileData, ResourceClassBase resourceClass) { // NOTE model matching if (resourceClass.IsAbstract()) { return(new { ResourceReference = new { ReferenceName = resourceClass.Name, ReferenceIdentifiers = _resourcePropertyRenderer.AssembleIdentifiers(profileData, resourceClass), Href = AssembleHref(profileData, resourceClass), HasDiscriminator = resourceClass.HasDiscriminator() }, ShouldRenderClass = false, HasDiscriminator = resourceClass.HasDiscriminator() }); } var parentResource = (resourceClass as ResourceChildItem)?.Parent; // NOTE model matching if (parentResource != null && parentResource.IsAbstract() && parentResource.Entity?.IsSameAggregate(resourceClass.Entity) != true) { return(new { ShouldRenderClass = false }); } object putPostRequestValidator = _resourceCollectionRenderer.CreatePutPostRequestValidator(profileData, resourceClass, TemplateContext); // Contextual parent handling var resourceAsChildItem = resourceClass as ResourceChildItem; var contextualParent = GetContextualParent(resourceAsChildItem, profileData); var parentProperCaseSchemaName = contextualParent?.ResourceModel.SchemaNameMapProvider .GetSchemaMapByPhysicalName(contextualParent.FullName.Schema) .ProperCaseName; var collections = _resourceCollectionRenderer.Collections(profileData, resourceClass, TemplateContext); return(new { ShouldRenderClass = true, ResourceReference = resourceClass.IsAggregateReference() ? new { ReferenceName = resourceClass.Name, ReferenceIdentifiers = _resourcePropertyRenderer .AssembleIdentifiers(profileData, resourceClass), Href = AssembleHref(profileData, resourceClass) } : ResourceRenderer.DoNotRenderProperty, ContextSpecificResourceReferences = CreateContextSpecificResourceReferences(profileData, resourceClass), ClassName = resourceClass.Name, EntityName = resourceClass.Name, Constructor = AssembleConstructor(profileData, resourceClass), HasCollections = ((IList)collections).Count > 0, Collections = collections, Identifiers = _resourcePropertyRenderer.AssemblePrimaryKeys(profileData, resourceClass, TemplateContext), NonIdentifiers = _resourcePropertyRenderer.AssembleProperties(resourceClass), InheritedProperties = _resourcePropertyRenderer.AssembleInheritedProperties(profileData, resourceClass), InheritedCollections = _resourceCollectionRenderer.InheritedCollections(profileData, resourceClass, TemplateContext), OnDeserialize = _resourceCollectionRenderer.OnDeserialize(profileData, resourceClass, TemplateContext), Guid = resourceClass.IsAggregateRoot() ? new { ResourceName = resourceClass.Name, GuidConverterTypeName = "GuidConverter" } : ResourceRenderer.DoNotRenderProperty, NavigableOneToOnes = _resourceCollectionRenderer.NavigableOneToOnes(profileData, resourceClass), InheritedNavigableOneToOnes = _resourceCollectionRenderer.InheritedNavigableOneToOnes(profileData, resourceClass), SynchronizationSourceSupport = _resourceCollectionRenderer .SynchronizationSourceSupport(profileData, resourceClass, TemplateContext), Versioning = resourceClass.IsAggregateRoot() ? ResourceRenderer.DoRenderProperty : ResourceRenderer.DoNotRenderProperty, References = _resourceCollectionRenderer.References(profileData, resourceClass, TemplateContext), FQName = resourceClass.FullName, IsAbstract = resourceClass.IsAbstract(), IsAggregateRoot = resourceClass.IsAggregateRoot(), DerivedName = resourceClass.IsDerived ? $@", {EdFiConventions.BuildNamespace( Namespaces.Entities.Common.RelativeNamespace, resourceClass.Entity.BaseEntity.SchemaProperCaseName()) }.I{resourceClass.Entity.BaseEntity.Name}" : ResourceRenderer.DoNotRenderProperty, ParentName = contextualParent?.Name, ParentFieldName = contextualParent?.Name.ToCamelCase(), InterfaceParentFieldName = contextualParent?.Name, ParentNamespacePrefix = parentProperCaseSchemaName == null ? null : $"{Namespaces.Entities.Common.RelativeNamespace}.{parentProperCaseSchemaName}.", IsBaseClassConcrete = resourceClass.Entity != null && resourceClass.Entity.IsDerived && resourceClass.Entity.BaseEntity != null && !resourceClass.Entity.BaseEntity.IsAbstractRequiringNoCompositeId(), DerivedBaseTypeName = resourceClass.IsDerived && resourceClass.Entity != null ? resourceClass.Entity.BaseEntity?.Name : ResourceRenderer.DoNotRenderProperty, FilteredDelegates = _resourceCollectionRenderer.FilteredDelegates(profileData, resourceClass), ShouldRenderValidator = putPostRequestValidator != ResourceRenderer.DoNotRenderProperty, Validator = putPostRequestValidator, IsExtendable = resourceClass.IsExtendable(), IsProfileProject = TemplateContext.IsProfiles, HasSupportedExtensions = profileData.SuppliedResource.Extensions.Any(), SupportedExtensions = profileData.SuppliedResource.Extensions .Select(e => new { ExtensionName = TemplateContext.GetSchemaProperCaseNameForExtension(e) }), IsEdFiResource = resourceClass.IsEdFiResource(), NamespacePrefix = resourceClass.GetNamespacePrefix(), HasDiscriminator = resourceClass.HasDiscriminator(), // Foreign Key Discriminators should not have any profile applied to this, as this data is required for links ResourceReferences = CreateResourceReferences(resourceClass) }); }
public object AssemblePrimaryKeys( ResourceProfileData profileData, ResourceClassBase resourceClass, TemplateContext templateContext) { if (profileData == null) { throw new ArgumentNullException(nameof(profileData)); } if (resourceClass == null) { throw new ArgumentNullException(nameof(resourceClass)); } if (templateContext == null) { throw new ArgumentNullException(nameof(templateContext)); } var pks = new List <object>(); var activeResource = profileData.GetProfileActiveResource(resourceClass); var filteredResource = profileData.GetContainedResource(resourceClass) ?? resourceClass; if (resourceClass is ResourceChildItem) { pks.Add( new { HasParent = ResourceRenderer.DoRenderProperty, Property = new { PropertyName = resourceClass.GetResourceInterfaceName( templateContext.GetSchemaProperCaseNameForResource(resourceClass), templateContext.IsProfiles, templateContext.IsExtension), ReferencesWithUnifiedKey = resourceClass.References .Where(@ref => @ref.Properties.Any(rp => rp.IsUnified())) .Select(@ref => new { ReferencePropertyName = @ref.PropertyName, ReferenceFieldName = @ref.PropertyName.ToCamelCase(), UnifiedKeyProperties = @ref.Properties .Where(rp => rp.IsUnified()) .Select(rp => new { UnifiedKeyPropertyName = rp.PropertyName }) }) } }); } var props = new List <PropertyData>(); foreach (var property in activeResource.AllProperties .Where(x => x.IsIdentifying) .OrderBy(x => x.PropertyName)) { if (activeResource.IsDescriptorEntity()) { props.Add(PropertyData.CreateDerivedProperty(property)); continue; } if (activeResource.IsAggregateRoot()) { if (resourceClass.IsDerived) { props.Add(AssembleDerivedProperty(property)); } else { props.Add( property.IsPersonOrUsi() && !templateContext.IsExtension ? PropertyData.CreateUsiPrimaryKey(property) : property.HasAssociations() && !property.IsDirectLookup ? PropertyData.CreateReferencedProperty(property, resource: filteredResource) : PropertyData.CreateStandardProperty(property)); } } else { // non aggregate root if (activeResource.References.Any()) { if (property.IsPersonOrUsi()) { props.Add(PropertyData.CreateUsiPrimaryKey(property)); continue; } if (resourceClass.HasBackReferences() && resourceClass.BackReferencedProperties() .Contains(property, ModelComparers.ResourcePropertyNameOnly)) { continue; } props.Add( property.HasAssociations() && !property.IsDirectLookup ? PropertyData.CreateReferencedProperty(property) : PropertyData.CreateStandardProperty(property)); } else { props.Add(PropertyData.CreateStandardProperty(property)); } } } pks.AddRange(CreatePropertyDtos(props)); return(pks.Any() ? new { Properties = pks } : ResourceRenderer.DoNotRenderProperty); }
private IEnumerable <object> CreateResourceContextModels(ResourceProfileData profileData) { // Create the context for the main resource var resourceContext = new { ResourceName = profileData.ResourceName, ResourceClassesNamespace = EdFiConventions.CreateResourceNamespace( profileData.ContextualRootResource, profileData.ProfileNamespaceName, profileData.ReadableWritableContext, profileData.ConcreteResourceContext), ResourceClasses = CreateContextualResourceClasses( profileData, profileData.ContextualRootResource.FullName.Schema), IsAbstract = profileData.IsAbstract }; if (resourceContext.ResourceClasses != ResourceRenderer.DoNotRenderProperty) { yield return(resourceContext); } // Process resources based on Ed-Fi standard resources for possible resource extensions if (profileData.ContextualRootResource.IsEdFiStandardResource) { // Get all the extension physical schema names present on the current resource model string[] extensionSchemaPhysicalNames = !profileData.ContextualRootResource.IsEdFiStandardResource ? new string[0] : profileData.ContextualRootResource.AllContainedItemTypes .Select(i => i.FullName.Schema) .Except( new[] { EdFiConventions.PhysicalSchemaName }) .ToArray(); // Process each extension schema with an individual namespace foreach (string extensionSchemaPhysicalName in extensionSchemaPhysicalNames) { string extensionSchemaProperCaseName = TemplateContext.DomainModelProvider.GetDomainModel() .SchemaNameMapProvider .GetSchemaMapByPhysicalName(extensionSchemaPhysicalName) .ProperCaseName; var extensionContext = new { ResourceName = profileData.ResourceName, ResourceClassesNamespace = EdFiConventions.CreateResourceNamespace( profileData.ContextualRootResource, profileData.ProfileNamespaceName, profileData.ReadableWritableContext, profileData.ConcreteResourceContext, extensionSchemaProperCaseName), ResourceClasses = CreateContextualResourceClasses( profileData, extensionSchemaPhysicalName), IsAbstract = profileData.IsAbstract }; if (extensionContext.ResourceClasses != ResourceRenderer.DoNotRenderProperty) { yield return(extensionContext); } } } }