views:

21

answers:

0

I am building an app where we are pulling messages off of MSMQ. The idea is to then take that message find a handler for it and process the message.

The method that is doing the retrieval and kicking off the processing looks like this

private void DoWork(object state)
{
    var mq = MessageQueue.Exists(QueueName)
                 ? new MessageQueue(QueueName)
                 : MessageQueue.Create(QueueName);

    var message = mq.Receive();
    message.Formatter = new XmlMessageFormatter
                            {TargetTypes = new[] 
                                {typeof(Envelope<SerializableDictionary<string, dynamic>>)}};
    var handler = _handlerMap[message.Label];
    handler.Handle(message.Body);
    ThreadPool.QueueUserWorkItem(DoWork);

The Handler being returned is an inheritor of an abstract base class and here are those to classes

public abstract class MessageHandler<T>
    {
        protected abstract JobStatus ProcessMessage(Envelope<T> envelope);

        private IContext Context { get; set; }

        protected MessageHandler()
        {
            Context = new ContextBuilder().CreateContext();
        }

        public void Handle(Envelope<T> envelope)
        {
            var job = Context.Jobs
                      .First(repoJob => repoJob.Name.Equals(envelope.MessageId));
            AddLogToJob(job, JobStatus.InProgress);
            var status = ProcessMessage(envelope);
            AddLogToJob(job, status);
        }

        private void AddLogToJob(Job job, JobStatus status)
        {
            job.JobLogs.Add(new JobLog { JobId = job.Id, StatusId = status.Id });
            Context.SaveChanges();
        }
    }
}

Here is the specific handler

public class MappingHandler<T> : MessageHandler<IDictionary<string, dynamic>>
{
    public DictionaryMapper<T> Mapper { get; set; }
    public Func<T> Constructor { get; set; }

    protected override JobStatus ProcessMessage(
            Envelope<IDictionary<string, dynamic>> envelope)
    {
        Mapper.Map(envelope.Payload, Constructor());
        return JobStatus.Completed;
    }
}

When I try to actually run the process when it reaches the handler.Handle(message.Body) line it throws a RuntimeBinderException. I haven't worked with dynamics much so it could likely be something in there, but everything I see in the debugger makes me think it should be working.