2012-04-10 3 views
2

EDIT her die Github Seite wollen, wenn die Menschen einen Blick https://github.com/brandongrossutti/EventStoreC# dynamische Keyword und Thread-Sicherheit

ich eine sehr seltsame Frage und kippe habe haben, ganz die Ursache Figur. Ich habe einen Zeromq-Abonnenten auf einem eigenen Thread. Wenn es eine Nachricht bekommt es einen Delegierten ruft und geht dann in eine message die schließlich zu diesem dynamischen Anruf bekommt

private void OnEvent(IEvent @event, bool isNew) 
    { 
     string eventName = "On" + @event.GetType().Name.Replace("Event", ""); 
     dynamic inheritingClass = this; 
     MethodInfo method = inheritingClass.GetType().GetMethod(eventName); 
     method.Invoke(inheritingClass, new object[] { @event }); 
     if (isNew)_uncommitedEvents.Add(@event); 
    } 

es stirbt auf der invoke und der Call-Stack und Ausnahme nicht eine Sache zeigen. Wenn ich langsam durchtrete, scheint es gut zu funktionieren. Sehr verwirrt.

Dank im Voraus

EDIT:

heren der schlecht für den Thread geschrieben Code, der die Teilnehmer

private readonly IHandlerResolver _resolver; 
    private readonly Thread _subscriberThread; 

    public MessageSubscriber(OnTheWireBusConfiguration configuration, IHandlerResolver resolver) 
    { 
     _resolver = resolver; 

     _subscriberThread = new Thread(RecieveMessages); 
     _subscriberThread.Start(new object[] { configuration, resolver, new Action<Message>(ProcessMessage) }); 
    } 

    private static void RecieveMessages(object o) 
    { 
     object[] obj = o as object[]; 
     OnTheWireBusConfiguration configuration = (OnTheWireBusConfiguration)obj[0]; 
     IHandlerResolver resolver = (IHandlerResolver)obj[1]; 
     Action<Message> handlerDelegate = (Action<Message>) obj[2]; 
     using (var context = new Context(configuration.MaxThreads)) 
     { 
      using (Socket subscriber = context.Socket(SocketType.SUB)) 
      { 
       subscriber.Subscribe("", Encoding.Unicode); 
       subscriber.Connect("tcp://localhost:5565"); 

       while (true) 
       { 
        byte[] buffer = subscriber.Recv(); 
        Message message = (Message) configuration.Deserialize(buffer); 
        Console.WriteLine(message); 
        handlerDelegate(message); 
        //resolver.ExecuteHandler(message); 
       } 
      } 
     } 
    } 

    public void ProcessMessage(Message message) 
    { 
     _resolver.ExecuteHandler(message); 
    } 

EDIT # 2 Call Stack

GHI beginnt. EventRepository.dll! GHI.EventRepository.AggregateRoot.OnEvent (GHI.EventRepository.IEvent even t, bool isNew) Zeile 39 C# GHI.EventRepository.dll! GHI.EventRepository.AggregateRoot.OnEvent (Ereignis GHI.EventRepository.IEvent) Zeile 29 + 0x12 Byte C# GHI.TestDomain.dll! GHI.TestDomain.Model.TestAggregateRoot .TestAggregateRoot (System.Guid id) Linie 15 + 0x59 Bytes C# GHI.TestDomain.dll! GHI.TestDomain.Handlers.CreateNewTestAggregateRootCommandHandler.HandleMessage (GHI.TestDomain.Messages.CreateNewTestAggregateRootCommand Nachricht) Linie 20 + 0x62 Bytes C# [native nach Verwalteter Übergang]
GHI.Bus.dll! GHI.Bus.HandlerResolver.ExecuteHandler (Nachricht GHI.Bus.Message) Zeile 40 + 0x95 Byte C# GHI.Bus.ZeroMQ.dll! GHI.Bus.ZeroMQ.MessageSubscriber.ProcessMessage (GHI.Bus.Message Nachricht) Zeile 48 + 0x38 Bytes C# GHI.Bus.ZeroMQ.dll! GHI.Bus.ZeroMQ.Mess ageSubscriber.RecieveMessages (object o) Linie 39 + 0x13 Bytes C# mscorlib.dll! System.Threading.ExecutionContext.runTryCode (Objekt userdata) + 0x173 Bytes
[Native nach Managed Transition]
[Managed auf einheitlichen Übergang]
mscorlib.dll! System.Threading.ExecutionContext.Run (System.Threading.ExecutionContext ExecutionContext, System.Threading.ContextCallback Rückruf, Objektzustand, bool preserveSyncCtx) + 0xEB Bytes
mscorlib.dll! System.Threading.ExecutionContext.Run (System .Threading.ExecutionContext executionContext, System.Threading.ContextCallback-Callback, Objektstatus) + 0x3b bytes
mscorlib.dll! System.Threading.ThreadHelper.ThreadStart (Objektobjekt) + 0x5d Bytes [Native nach Managed Transition]
[Appdomain Übergang]
[Native nach Managed Transition]

ich dies auf Github Pop kann, wenn einfacher

EDIT # 4 Dank für everyones helfen, froh Ich könnte das dynamische Schlüsselwort aus diesem Code entfernen. Dynamische war nicht das Problem es meine Verriegelungs Weg nach oben der Stapel war, nochmals vielen Dank, ich habe thos upvoted, die dynamische Ausgabe erwähnt und wird die Antwort unter

+1

„Call-Stack und Ausnahme nicht eine Sache zeigen“? Was zeigen sie dann? – Gabe

+0

Ausdruck kann nicht ausgewertet werden, da der Code optimiert ist oder ein nativer Rahmen über dem Aufrufstapel liegt. –

+2

"Es stirbt." Können Sie uns die Ergebnisse der Autopsie mitteilen? –

Antwort

2

Ich bin nicht vertraut mit zeromq, aber Blick auf Ihre OnEvent akzeptieren Methode, sehe ich nicht dynamic wie nötig. Was passiert, wenn Sie dynamic nicht verwenden und die Methode damit ersetzen?

private void OnEvent(IEvent @event, bool isNew) 
{ 
    string eventName = "On" + @event.GetType().Name.Replace("Event", ""); 
    MethodInfo method = this.GetType().GetMethod(eventName); 
    method.Invoke(this, new object[] { @event }); 
    if (isNew)_uncommitedEvents.Add(@event); 
} 

Wenn sich das Verhalten nicht ändert, liegt das Problem möglicherweise anderswo.

(wahrscheinlich wollen eine if(method != null) um die Invoke hinzuzufügen, wenn Sie absolut sicher sind, wird es dort die ganze Zeit sein.)

+0

GetType() wird nicht den tatsächlichen Typ, der diese Klasse erbt, also der Grund für den dynamischen Aufruf, die On ..... Methode ist nur für die Klasse, die von dort erbt –

+0

Ja wird es. Ich denke, du verwechselst 'foo.GetType()' mit 'typeof (Foo)'. '@ event.GetType()' gibt 'IEvent' nicht zurück, es gibt die implementierende Klasse zurück; Der Aufruf von 'this.GetType()' funktioniert auf die gleiche Weise. –

+0

i stand korrigiert –