Вот другой подход, использующий эту идею я уже упоминал в другом post. На самом деле очень просто разбить метод Crack двумя способами и обработчиками OnMessageTo и OnMessageFrom. Модифицированная реализация вспомогательного класса MessageCracker выше знает направление сообщения, хотя, безусловно, его можно улучшить.
В вашей заявке, реализации, как это (не полный код):
public class MyFixApplication: DirectedMessageCracker, Application
{
...
public void FromAdmin(Message msg, SessionID sessionId)
{
CrackFrom(msg, sessionId);
}
public void ToAdmin(Message msg, SessionID sessionId)
{
CrackTo(msg, sessionId);
}
public void OnMessageTo(Logon msg, SessionID sessionId)
{
//Treat the outgoing message, set user, password, etc
}
public void OnMessageFrom(Allocation msg, SessionID sessionId)
{
//Treat the incoming Allocation message
}
...and so on
и модифицированный MessageCracker:
using System;
using System.Collections.Generic;
using System.Reflection;
namespace QuickFix
{
/// <summary>
/// Helper class for delegating message types for various FIX versions to
/// type-safe OnMessage methods, supports handling of incoming and outgoing messages separatelly
/// </summary>
public abstract class DirectedMessageCracker
{
private readonly Dictionary<Type, MethodInfo> _toHandlerMethods = new Dictionary<Type, MethodInfo>();
private readonly Dictionary<Type, MethodInfo> _fromHandlerMethods = new Dictionary<Type, MethodInfo>();
protected DirectedMessageCracker()
{
Initialize(this);
}
private void Initialize(Object messageHandler)
{
var handlerType = messageHandler.GetType();
var methods = handlerType.GetMethods();
foreach (var m in methods)
{
if (IsToHandlerMethod(m))
_toHandlerMethods[m.GetParameters()[0].ParameterType] = m;
else if (IsFromHandlerMethod(m))
_fromHandlerMethods[m.GetParameters()[0].ParameterType] = m;
}
}
static public bool IsToHandlerMethod(MethodInfo m)
{
return IsHandlerMethod("OnMessageTo", m);
}
static public bool IsFromHandlerMethod(MethodInfo m)
{
return IsHandlerMethod("OnMessageFrom", m);
}
static public bool IsHandlerMethod(string searchMethodName, MethodInfo m)
{
return (m.IsPublic
&& m.Name.StartsWith(searchMethodName)
&& m.GetParameters().Length == 2
&& m.GetParameters()[0].ParameterType.IsSubclassOf(typeof(Message))
&& typeof(SessionID).IsAssignableFrom(m.GetParameters()[1].ParameterType)
&& m.ReturnType == typeof(void));
}
/// <summary>
/// Process ("crack") a FIX message and call the registered handlers for that type, if any
/// </summary>
/// <param name="handlerMethods"></param>
/// <param name="message"></param>
/// <param name="sessionID"></param>
private void Crack(IDictionary<Type, MethodInfo> handlerMethods, Message message, SessionID sessionID)
{
var messageType = message.GetType();
MethodInfo handler;
if (handlerMethods.TryGetValue(messageType, out handler))
handler.Invoke(this, new object[] { message, sessionID });
else
throw new UnsupportedMessageType();
}
/// <summary>
/// Process ("crack") an INCOMING FIX message and call the registered handlers for that type, if any
/// </summary>
/// <param name="message"></param>
/// <param name="sessionID"></param>
public void CrackFrom(Message message, SessionID sessionID)
{
Crack(_fromHandlerMethods, message, sessionID);
}
/// <summary>
/// Process ("crack") an OUTGOING FIX message and call the registered handlers for that type, if any
/// </summary>
/// <param name="message"></param>
/// <param name="sessionID"></param>
public void CrackTo(Message message, SessionID sessionID)
{
Crack(_toHandlerMethods, message, sessionID);
}
}
}
Вы также можете пропустить трещину вместо того, чтобы выбросить исключение в случае вы не хотите внедрять все возможные обработчики сообщений, просто удалив throw new UnsupportedMessageType();
из метода трещины.
Еще одна идея - разбить трещины на сообщения администратора/приложения.
Это преждевременная оптимизация. Сделайте это первым. Отложите исследования эффективности, пока не узнаете, что вам это нужно. –
Извините, мой комментарий был слишком тупым. Я хотел сказать, что если у вас проблемы с производительностью, эта небольшая синтаксическая обработка строк вряд ли будет вашей основной причиной. Не беспокойтесь о том, чтобы оптимизировать вещи, пока не появится доказательство того, что это проблема. –
Это совершенно не связано с производительностью. Мне нужно проверить, является ли исходящее сообщение логином, чтобы добавить имя пользователя и пароль. –