1

I have my POST method which I use to trigger the sending of an email

[HttpPost]
public HttpResponseMessage Post(IEmail model)
{
    SendAnEmailPlease(model);
}

I have many types of email to send so I abstract away to an interface so I only need one post method

 config.BindParameter(typeof(IEmail), new EmailModelBinder());

I have my model binder which gets hit fine

public class EmailModelBinder : IModelBinder
{
    public bool BindModel(
        HttpActionContext actionContext, 
        ModelBindingContext bindingContext )
    {
        // Logic here           

        return false;
    }
}

I'm struggling with the logic for turning the bindingContext.PropertyMetadata into one of my email POCOs

public IDictionary<string, ModelMetadata> PropertyMetadata { get; }     

In the PropertyMetadata I'm passing the object type as a string which I think I could use to create a class with the Activator.CreateInstance method.

eg: EmailType = MyProject.Models.Email.AccountVerificationEmail

Is there an easy way to accomplish this?


Related questions

Community
  • 1
  • 1
Neil
  • 5,179
  • 8
  • 48
  • 87

1 Answers1

1

Here's the solution I came up with, might be useful to someone else out there.

public class EmailModelBinder : IModelBinder
{
    public bool BindModel(
        HttpActionContext actionContext, 
        ModelBindingContext bindingContext)
    {
        string body = actionContext.Request.Content
                       .ReadAsStringAsync().Result;

        Dictionary<string, string> values = 
            JsonConvert.DeserializeObject<Dictionary<string, string>>(body);

        var entity = Activator.CreateInstance(
            typeof(IEmail).Assembly.FullName, 
            values.FirstOrDefault(x => x.Key == "ObjectType").Value
            ).Unwrap();

        JsonConvert.PopulateObject(body, entity);

        bindingContext.Model = (IEmail)entity;

        return true;
    }
}
Neil
  • 5,179
  • 8
  • 48
  • 87