/// <summary> /// add a function that detects end of data for a specific entity /// </summary> /// <typeparam name="TEntity">parsed entity type</typeparam> /// <param name="context">the excel context tracking the entity</param> /// <param name="endDelimiter">function that detects non-data rows</param> /// <returns></returns> public static ExcelContext AddEndDelimiter <TEntity>(this ExcelContext context, Expression <Func <TEntity, bool> > endDelimiter) where TEntity : class, new() { var typeBuilder = context.GetExcelEntityTypeBuilder <TEntity>(); typeBuilder.LastRowWhen(endDelimiter); return(context); }
/// <summary> /// Extension method to <see cref="ExcelContext"/> to add domain objects that use the Attribute /// interface <see cref="ExcelColumnConfigurationAttribute"/> for column configuration /// </summary> /// <typeparam name="TEntity">type of entity configured with attributes</typeparam> /// <param name="context">the context that should track the entity</param> /// <returns></returns> public static ExcelContext BuildAttributedEntity <TEntity>(this ExcelContext context) where TEntity : class, new() { var typeBuilder = new ExcelEntityBuilder <TEntity>(); var typeBuilderType = typeBuilder.GetType(); var entityType = typeof(TEntity); var entityProperties = entityType.GetProperties(); //iterate through all properties of the entity foreach (var targetProp in entityProperties) { var allCustomAttributes = targetProp.GetCustomAttributes(true); //property is marked as audit attribute var excelAuditAttribute = allCustomAttributes.FirstOrDefault(x => x.GetType() == typeof(ExcelAuditAttribute)) as ExcelAuditAttribute; if (excelAuditAttribute != null) { switch (excelAuditAttribute.AuditProperty) { case ExcelAuditProperties.RowId: //use the fluent api to track the audit property typeBuilder.RowIdWithPropertyName(targetProp.Name); break; default: throw new NotSupportedException($"The audit property type '{excelAuditAttribute.AuditProperty}' is not supported by the method '{nameof(ExcelContextExtensions.BuildAttributedEntity)}'."); } continue; } //property is marked with a data attribute var excelConfigAttribute = allCustomAttributes.FirstOrDefault(x => x.GetType() == typeof(ExcelColumnConfigurationAttribute)) as ExcelColumnConfigurationAttribute; if (excelConfigAttribute != null) { //add the property as via the generic api method //this requires ad-hoc reflection based method construction from generic to type of property var genericMethod = typeBuilderType.GetMethod(nameof(ExcelEntityBuilder <TEntity> .PropertyWithPropertyName), BindingFlags.Instance | BindingFlags.NonPublic); var typedGenericMethod = genericMethod.MakeGenericMethod(targetProp.PropertyType); var propertyBuilder = typedGenericMethod.Invoke(typeBuilder, new object[] { targetProp.Name }); ///configuration property can be accessed from the non generic base class ((ExcelPropertyBuilder)propertyBuilder).Configuration = excelConfigAttribute.Configuration; } } try { context.ModelBuilder.Entities.Add(entityType, typeBuilder); } catch (ArgumentException e) { throw new ArgumentException($"The type '{typeof(TEntity)}' was already configured as a mapped entity in the excel context."); } context.ValidateModel(); return(context); }