private void DiscoverRecordFields(Type recordType)
        {
            if (!IsDynamicObject)
            {
                KVPRecordFieldConfigurations.Clear();

                if (ChoTypeDescriptor.GetProperties(recordType).Where(pd => pd.Attributes.OfType <ChoKVPRecordFieldAttribute>().Any()).Any())
                {
                    foreach (PropertyDescriptor pd in ChoTypeDescriptor.GetProperties(recordType).Where(pd => pd.Attributes.OfType <ChoKVPRecordFieldAttribute>().Any()))
                    {
                        //if (!pd.PropertyType.IsSimple())
                        //    throw new ChoRecordConfigurationException("Property '{0}' is not a simple type.".FormatString(pd.Name));

                        var obj = new ChoKVPRecordFieldConfiguration(pd.Name, pd.Attributes.OfType <ChoKVPRecordFieldAttribute>().First());
                        obj.FieldType = pd.PropertyType;
                        KVPRecordFieldConfigurations.Add(obj);
                    }
                }
                else
                {
                    foreach (PropertyDescriptor pd in ChoTypeDescriptor.GetProperties(recordType))
                    {
                        //if (!pd.PropertyType.IsSimple())
                        //    throw new ChoRecordConfigurationException("Property '{0}' is not a simple type.".FormatString(pd.Name));

                        var obj = new ChoKVPRecordFieldConfiguration(pd.Name);
                        obj.FieldType = pd.PropertyType;
                        KVPRecordFieldConfigurations.Add(obj);
                    }
                }
            }
        }
 public ChoKVPRecordFieldConfiguration this[string name]
 {
     get
     {
         return(KVPRecordFieldConfigurations.Where(i => i.Name == name).FirstOrDefault());
     }
 }
 private void DiscoverRecordFields(Type recordType, bool clear = true)
 {
     if (clear)
     {
         KVPRecordFieldConfigurations.Clear();
     }
     DiscoverRecordFields(recordType, null,
                          ChoTypeDescriptor.GetProperties(recordType).Where(pd => pd.Attributes.OfType <ChoKVPRecordFieldAttribute>().Any()).Any());
 }
        internal ChoKVPRecordFieldConfiguration GetFieldConfiguration(string propertyName, ChoKVPRecordFieldAttribute attr = null, Attribute[] otherAttrs = null)
        {
            if (!KVPRecordFieldConfigurations.Any(fc => fc.Name == propertyName))
            {
                KVPRecordFieldConfigurations.Add(new ChoKVPRecordFieldConfiguration(propertyName, attr, otherAttrs));
            }

            return(KVPRecordFieldConfigurations.First(fc => fc.Name == propertyName));
        }
        public ChoKVPRecordConfiguration IgnoreField(string fieldName)
        {
            var fc = KVPRecordFieldConfigurations.Where(f => f.DeclaringMember == fieldName || f.FieldName == fieldName).FirstOrDefault();

            if (fc != null)
            {
                KVPRecordFieldConfigurations.Remove(fc);
            }

            return(this);
        }
        public ChoKVPRecordConfiguration IgnoreField <T, TProperty>(Expression <Func <T, TProperty> > field)
        {
            if (KVPRecordFieldConfigurations.Count == 0)
            {
                MapRecordFields <T>();
            }

            var fc = KVPRecordFieldConfigurations.Where(f => f.DeclaringMember == field.GetFullyQualifiedMemberName()).FirstOrDefault();

            if (fc != null)
            {
                KVPRecordFieldConfigurations.Remove(fc);
            }

            return(this);
        }
        public override void Validate(object state)
        {
            if (state == null)
            {
                base.Validate(state);

                if (Separator.IsNullOrWhiteSpace())
                {
                    throw new ChoRecordConfigurationException("Separator can't be null or whitespace.");
                }
                if (Separator == EOLDelimiter)
                {
                    throw new ChoRecordConfigurationException("Separator [{0}] can't be same as EODDelimiter [{1}]".FormatString(Separator, EOLDelimiter));
                }
                if (Separator.Contains(QuoteChar))
                {
                    throw new ChoRecordConfigurationException("QuoteChar [{0}] can't be one of Delimiter characters [{1}]".FormatString(QuoteChar, Separator));
                }
                if (Comments != null && Comments.Contains(Separator))
                {
                    throw new ChoRecordConfigurationException("One of the Comments contains Delimiter. Not allowed.");
                }
                if (RecordStart.IsNullOrWhiteSpace() && RecordEnd.IsNullOrWhiteSpace())
                {
                }
                else
                {
                    if (RecordStart.IsNullOrWhiteSpace())
                    {
                        throw new ChoRecordConfigurationException("RecordStart is missing.");
                    }
                    //else if (RecordEnd.IsNullOrWhiteSpace())
                    //    RecordEnd = RecordStart;
                    //throw new ChoRecordConfigurationException("RecordEnd is missing.");

                    if (RecordStart.Contains("*") || RecordStart.Contains("?"))
                    {
                        _isWildcardComparisionOnRecordStart = true;
                        _recordStartWildCard = new ChoWildcard(RecordStart);
                    }
                    if (!RecordEnd.IsNullOrWhiteSpace() && (RecordEnd.EndsWith("*") || RecordStart.Contains("?")))
                    {
                        _isWildcardComparisionOnRecordEnd = true;
                        _recordEndWildCard = new ChoWildcard(RecordEnd);
                    }
                }

                //Validate Header
                if (FileHeaderConfiguration != null)
                {
                    if (FileHeaderConfiguration.FillChar != null)
                    {
                        if (FileHeaderConfiguration.FillChar.Value == ChoCharEx.NUL)
                        {
                            throw new ChoRecordConfigurationException("Invalid '{0}' FillChar specified.".FormatString(FileHeaderConfiguration.FillChar));
                        }
                        if (Separator.Contains(FileHeaderConfiguration.FillChar.Value))
                        {
                            throw new ChoRecordConfigurationException("FillChar [{0}] can't be one of Delimiter characters [{1}]".FormatString(FileHeaderConfiguration.FillChar, Separator));
                        }
                        if (EOLDelimiter.Contains(FileHeaderConfiguration.FillChar.Value))
                        {
                            throw new ChoRecordConfigurationException("FillChar [{0}] can't be one of EOLDelimiter characters [{1}]".FormatString(FileHeaderConfiguration.FillChar.Value, EOLDelimiter));
                        }
                        if ((from comm in Comments
                             where comm.Contains(FileHeaderConfiguration.FillChar.Value.ToString())
                             select comm).Any())
                        {
                            throw new ChoRecordConfigurationException("One of the Comments contains FillChar. Not allowed.");
                        }
                    }
                }
            }
            else
            {
                string[] headers = state as string[];
                if (AutoDiscoverColumns &&
                    KVPRecordFieldConfigurations.Count == 0)
                {
                    AutoDiscoveredColumns = true;
                    if (headers != null && IsDynamicObject)
                    {
                        KVPRecordFieldConfigurations = (from header in headers
                                                        select new ChoKVPRecordFieldConfiguration(header)).ToList();
                    }
                    else
                    {
                        MapRecordFields(RecordType);
                    }
                }

                if (KVPRecordFieldConfigurations.Count <= 0)
                {
                    throw new ChoRecordConfigurationException("No record fields specified.");
                }

                //Validate each record field
                foreach (var fieldConfig in KVPRecordFieldConfigurations)
                {
                    fieldConfig.Validate(this);
                }

                //Check if any field has empty names
                if (KVPRecordFieldConfigurations.Where(i => i.FieldName.IsNullOrWhiteSpace()).Count() > 0)
                {
                    throw new ChoRecordConfigurationException("Some fields has empty field name specified.");
                }

                //Check field names for duplicate
                string[] dupFields = KVPRecordFieldConfigurations.GroupBy(i => i.FieldName, FileHeaderConfiguration.StringComparer)
                                     .Where(g => g.Count() > 1)
                                     .Select(g => g.Key).ToArray();

                if (dupFields.Length > 0 /* && !IgnoreDuplicateFields */)
                {
                    throw new ChoRecordConfigurationException("Duplicate field name(s) [Name: {0}] found.".FormatString(String.Join(",", dupFields)));
                }

                PIDict = new Dictionary <string, System.Reflection.PropertyInfo>();
                PDDict = new Dictionary <string, PropertyDescriptor>();
                foreach (var fc in KVPRecordFieldConfigurations)
                {
                    if (fc.PropertyDescriptor == null)
                    {
                        fc.PropertyDescriptor = ChoTypeDescriptor.GetProperties(RecordType).Where(pd => pd.Name == fc.Name).FirstOrDefault();
                    }
                    if (fc.PropertyDescriptor == null)
                    {
                        continue;
                    }

                    PIDict.Add(fc.PropertyDescriptor.Name, fc.PropertyDescriptor.ComponentType.GetProperty(fc.PropertyDescriptor.Name));
                    PDDict.Add(fc.PropertyDescriptor.Name, fc.PropertyDescriptor);
                }


                RecordFieldConfigurationsDict  = KVPRecordFieldConfigurations.Where(i => !i.Name.IsNullOrWhiteSpace()).GroupBy(i => i.Name).Select(g => g.First()).ToDictionary(i => i.Name, FileHeaderConfiguration.StringComparer);
                RecordFieldConfigurationsDict2 = KVPRecordFieldConfigurations.Where(i => !i.FieldName.IsNullOrWhiteSpace()).GroupBy(i => i.Name).Select(g => g.First()).ToDictionary(i => i.FieldName, FileHeaderConfiguration.StringComparer);
                AlternativeKeys = RecordFieldConfigurationsDict2.ToDictionary(kvp => kvp.Key, kvp => kvp.Value.Name, FileHeaderConfiguration.StringComparer);
                FCArray         = RecordFieldConfigurationsDict.ToArray();

                LoadNCacheMembers(KVPRecordFieldConfigurations);
            }
        }
 private void DiscoverRecordFields(Type recordType, string declaringMember, bool optIn = false)
 {
     if (!recordType.IsDynamicType())
     {
         Type pt = null;
         if (optIn) //ChoTypeDescriptor.GetProperties(recordType).Where(pd => pd.Attributes.OfType<ChoKVPRecordFieldAttribute>().Any()).Any())
         {
             foreach (PropertyDescriptor pd in ChoTypeDescriptor.GetProperties(recordType))
             {
                 pt = pd.PropertyType.GetUnderlyingType();
                 if (!pt.IsSimple() && !typeof(IEnumerable).IsAssignableFrom(pt))
                 {
                     DiscoverRecordFields(pt, declaringMember == null ? pd.Name : "{0}.{1}".FormatString(declaringMember, pd.Name), optIn);
                 }
                 else if (pd.Attributes.OfType <ChoKVPRecordFieldAttribute>().Any())
                 {
                     var obj = new ChoKVPRecordFieldConfiguration(pd.Name, pd.Attributes.OfType <ChoKVPRecordFieldAttribute>().First(), pd.Attributes.OfType <Attribute>().ToArray());
                     obj.FieldType          = pt;
                     obj.PropertyDescriptor = pd;
                     obj.DeclaringMember    = declaringMember == null ? null : "{0}.{1}".FormatString(declaringMember, pd.Name);
                     if (!KVPRecordFieldConfigurations.Any(c => c.Name == pd.Name))
                     {
                         KVPRecordFieldConfigurations.Add(obj);
                     }
                 }
             }
         }
         else
         {
             foreach (PropertyDescriptor pd in ChoTypeDescriptor.GetProperties(recordType))
             {
                 pt = pd.PropertyType.GetUnderlyingType();
                 if (pt != typeof(object) && !pt.IsSimple() && !typeof(IEnumerable).IsAssignableFrom(pt))
                 {
                     DiscoverRecordFields(pt, declaringMember == null ? pd.Name : "{0}.{1}".FormatString(declaringMember, pd.Name), optIn);
                 }
                 else
                 {
                     var obj = new ChoKVPRecordFieldConfiguration(pd.Name);
                     obj.FieldType          = pt;
                     obj.PropertyDescriptor = pd;
                     obj.DeclaringMember    = declaringMember == null ? null : "{0}.{1}".FormatString(declaringMember, pd.Name);
                     StringLengthAttribute slAttr = pd.Attributes.OfType <StringLengthAttribute>().FirstOrDefault();
                     if (slAttr != null && slAttr.MaximumLength > 0)
                     {
                         obj.Size = slAttr.MaximumLength;
                     }
                     DisplayAttribute dpAttr = pd.Attributes.OfType <DisplayAttribute>().FirstOrDefault();
                     if (dpAttr != null)
                     {
                         if (!dpAttr.ShortName.IsNullOrWhiteSpace())
                         {
                             obj.FieldName = dpAttr.ShortName;
                         }
                         else if (!dpAttr.Name.IsNullOrWhiteSpace())
                         {
                             obj.FieldName = dpAttr.Name;
                         }
                     }
                     DisplayFormatAttribute dfAttr = pd.Attributes.OfType <DisplayFormatAttribute>().FirstOrDefault();
                     if (dfAttr != null && !dfAttr.DataFormatString.IsNullOrWhiteSpace())
                     {
                         obj.FormatText = dfAttr.DataFormatString;
                     }
                     if (dfAttr != null && !dfAttr.NullDisplayText.IsNullOrWhiteSpace())
                     {
                         obj.NullValue = dfAttr.NullDisplayText;
                     }
                     if (!KVPRecordFieldConfigurations.Any(c => c.Name == pd.Name))
                     {
                         KVPRecordFieldConfigurations.Add(obj);
                     }
                 }
             }
         }
     }
 }
 public ChoKVPRecordConfiguration ClearFields()
 {
     //KVPRecordFieldConfigurationsForType.Clear();
     KVPRecordFieldConfigurations.Clear();
     return(this);
 }