using System; using System.Collections; using System.Collections.Generic; using System.IO; using System.Linq.Expressions; using System.Reflection; using System.Text; namespace InABox.Core { [UserTracking(false)] public class ExportColumn : Entity, ILicense { public string Property { get; set; } public string Name { get; set; } public string Format { get; set; } } public abstract class AbstractExporter { protected static PropertyInfo GetProperty(Expression> expression) { var member = expression.Body as MemberExpression; if (member == null) { var unary = expression.Body as UnaryExpression; member = (MemberExpression)unary.Operand; } return (PropertyInfo)member.Member; } public abstract void Export(Stream stream, IEnumerable items, Dictionary>> expressions); public abstract void Export(Stream stream, IEnumerable items, Dictionary properties); public abstract void Export(Stream stream, IEnumerable items, IEnumerable columns); public abstract void Export(Stream stream, CoreTable table); public void Export(Stream stream, IEnumerable items) { var expressions = new Dictionary>>(); var properties = typeof(T).GetTypeInfo().GetProperties(); foreach (var propInfo in properties) { var parameter = Expression.Parameter(typeof(T)); var property = Expression.Property(parameter, propInfo); var conversion = Expression.Convert(property, typeof(object)); var lambda = Expression.Lambda>(conversion, parameter); expressions[propInfo.Name] = lambda; } Export(stream, items, expressions); } } public abstract class DelimitedExporter : AbstractExporter { protected char Delimiter = char.MinValue; public override void Export(Stream stream, IEnumerable items, Dictionary>> expressions) { using (var sw = new StreamWriter(stream, Encoding.Unicode)) { var row = new List(); foreach (var column in expressions.Keys) row.Add(column); sw.WriteLine(string.Join(Convert.ToString(Delimiter), row)); foreach (var item in items) { row.Clear(); foreach (var column in expressions.Keys) { var expression = expressions[column]; if (expression != null) { var f = expression.Compile(); var o = f.Invoke(item); row.Add(o != null ? o.ToString() : ""); } else { row.Add(""); } } sw.WriteLine(string.Join(Convert.ToString(Delimiter), row)); } } } public override void Export(Stream stream, IEnumerable items, Dictionary properties) { using (var sw = new StreamWriter(stream, Encoding.Unicode)) { var row = new List(); foreach (var column in properties.Keys) row.Add(column); sw.WriteLine(string.Join(Convert.ToString(Delimiter), row)); foreach (var item in items) { row.Clear(); foreach (var column in properties.Keys) { var property = properties[column]; if (!string.IsNullOrEmpty(property)) { var o = CoreUtils.GetPropertyValue(item, property); row.Add(o != null ? o.ToString() : ""); } else { row.Add(""); } } sw.WriteLine(string.Join(Convert.ToString(Delimiter), row)); } } } public override void Export(Stream stream, IEnumerable items, IEnumerable columns) { using (var sw = new StreamWriter(stream, Encoding.Unicode)) { var row = new List(); foreach (var column in columns) row.Add(column.Name); sw.WriteLine(string.Join(Convert.ToString(Delimiter), row)); if (items != null) foreach (var item in items) { row.Clear(); foreach (var column in columns) { var property = column.Property; if (!string.IsNullOrEmpty(property)) { var o = CoreUtils.GetPropertyValue(item, property); var fmt = "{0" + (string.IsNullOrWhiteSpace(column.Format) ? "" : ":" + column.Format) + "}"; row.Add(o != null ? string.Format(fmt, o) : ""); } else { row.Add(""); } } sw.WriteLine(string.Join(Convert.ToString(Delimiter), row)); } } } public override void Export(Stream stream, CoreTable table) { using var sw = new StreamWriter(stream, Encoding.Unicode); var row = new List(); foreach (var column in table.Columns) row.Add(column.ColumnName); sw.WriteLine(string.Join(Convert.ToString(Delimiter), row)); foreach (var datarow in table.Rows) { row.Clear(); foreach (var column in table.Columns) { var o = datarow[column.ColumnName]; row.Add(o != null ? o.ToString() : ""); } sw.WriteLine(string.Join(Convert.ToString(Delimiter), row)); } } } public class CSVExporter : DelimitedExporter { public CSVExporter() { Delimiter = ','; } } public class TabExporter : DelimitedExporter { public TabExporter() { Delimiter = '\t'; } } }