using System; using System.Collections.Generic; using System.Linq; using Newtonsoft.Json.Linq; using NzbDrone.Common.EnsureThat; using NzbDrone.Common.Extensions; using NzbDrone.Common.Reflection; using NzbDrone.Core.Annotations; namespace NzbDrone.Api.ClientSchema { public static class SchemaBuilder { public static List ToSchema(object model) { Ensure.That(model, () => model).IsNotNull(); var properties = model.GetType().GetSimpleProperties(); var result = new List(properties.Count); foreach (var propertyInfo in properties) { var fieldAttribute = propertyInfo.GetAttribute(false); if (fieldAttribute != null) { var field = new Field { Name = propertyInfo.Name, Label = fieldAttribute.Label, HelpText = fieldAttribute.HelpText, HelpLink = fieldAttribute.HelpLink, Order = fieldAttribute.Order, Advanced = fieldAttribute.Advanced, Type = fieldAttribute.Type.ToString().ToLowerInvariant() }; var value = propertyInfo.GetValue(model, null); if (value != null) { field.Value = value; } if (fieldAttribute.Type == FieldType.Select) { field.SelectOptions = GetSelectOptions(fieldAttribute.SelectOptions); } result.Add(field); } } return result.OrderBy(r => r.Order).ToList(); } public static object ReadFromSchema(List fields, Type targetType) { Ensure.That(targetType, () => targetType).IsNotNull(); var properties = targetType.GetSimpleProperties(); var target = Activator.CreateInstance(targetType); foreach (var propertyInfo in properties) { var fieldAttribute = propertyInfo.GetAttribute(false); if (fieldAttribute != null) { var field = fields.Find(f => f.Name == propertyInfo.Name); if (propertyInfo.PropertyType == typeof(int)) { var value = Convert.ToInt32(field.Value); propertyInfo.SetValue(target, value, null); } else if (propertyInfo.PropertyType == typeof(long)) { var value = Convert.ToInt64(field.Value); propertyInfo.SetValue(target, value, null); } else if (propertyInfo.PropertyType == typeof(int?)) { var value = field.Value.ToString().ParseInt32(); propertyInfo.SetValue(target, value, null); } else if (propertyInfo.PropertyType == typeof(Nullable)) { var value = field.Value.ToString().ParseInt64(); propertyInfo.SetValue(target, value, null); } else if (propertyInfo.PropertyType == typeof(IEnumerable)) { IEnumerable value; if (field.Value.GetType() == typeof(JArray)) { value = ((JArray)field.Value).Select(s => s.Value()); } else { value = field.Value.ToString().Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries).Select(s => Convert.ToInt32(s)); } propertyInfo.SetValue(target, value, null); } else if (propertyInfo.PropertyType == typeof(IEnumerable)) { IEnumerable value; if (field.Value.GetType() == typeof(JArray)) { value = ((JArray)field.Value).Select(s => s.Value()); } else { value = field.Value.ToString().Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries); } propertyInfo.SetValue(target, value, null); } else { propertyInfo.SetValue(target, field.Value, null); } } } return target; } public static T ReadFromSchema(List fields) { return (T)ReadFromSchema(fields, typeof(T)); } private static List GetSelectOptions(Type selectOptions) { var options = from Enum e in Enum.GetValues(selectOptions) select new SelectOption { Value = Convert.ToInt32(e), Name = e.ToString() }; return options.OrderBy(o => o.Value).ToList(); } } }