2015-04-30 1 views
3

Je me connecte à plusieurs API qui utilisent toutes FXI4.2 mais maintenant je souhaite me connecter à une autre qui utilise sa propre version de FIX4.4.QuickFix/N comment mieux gérer plusieurs versions FIX

J'ai une application de routeur qui envoie des ordres aux différentes API et il semblerait que j'ai besoin de dupliquer toutes mes méthodes (par exemple OnMessage(), NewSingleOrder etc) pour faire face aux 2 protocoles FIX.

Y a-t-il une façon plus intelligente de faire ceci pour éviter cette duplication? Modérateurs: Je sais que c'est un peu ouvert maintenant, mais je vais ajouter quelques extraits de code une fois que je reçois un feedback initial.

public void OnMessage(QuickFix.FIX42.MarketDataIncrementalRefresh message, SessionID sessionID) 
{ 
    int count = message.NoMDEntries.getValue(); 
    QuickFix.FIX42.MarketDataSnapshotFullRefresh.NoMDEntriesGroup repeatingMDItem = new QuickFix.FIX42.MarketDataSnapshotFullRefresh.NoMDEntriesGroup(); 

    DateTime sourceDT = DateTime.ParseExact(message.Header.GetField(52), "yyyyMMdd-HH:mm:ss.fff", ci); 
    DateTime dt = TimeZoneInfo.ConvertTimeToUtc(sourceDT, utcZone); 
    DateTime nowUTC = TimeZoneInfo.ConvertTime(DateTime.UtcNow, utcZone, utcZone); 
    TimeSpan diffToUK = nowUTC - dt; 

    for (int i = 1; i <= count; i++) 
    { 

     message.GetGroup(i, repeatingMDItem); 

     String symbol = repeatingMDItem.GetField(55); 

     int tickBandNoDecPlaces = int.Parse(repeatingMDItem.GetField(5071)); 
     masterForm.MDATA.AddData(symbol, tickBandNoDecPlaces, sourceDT); 
    } 
} 

FIX44 acceptera-t-il tous les FIX précédents?

Comment puis-je ignorer la version FIX?

 public void OnMessage(QuickFix.FIX42.MarketDataSnapshotFullRefresh message, SessionID sessionID) 
     { 
      OnMessageAgnostic(message, sessionID); 
     } 

     public void OnMessage(QuickFix.FIX44.MarketDataSnapshotFullRefresh message, SessionID sessionID) 
     { 
      OnMessageAgnostic(message, sessionID); 
     } 

     public int FixVersion(QuickFix.Message message) 
     { 
       switch (message.GetString(8)) // BeginString 
        { 
         case Values.BeginString_FIX42: 
          return 42; 
         case Values.BeginString_FIX44: 
          return 44; 
         default: 
          throw new NotSupportedException("This version of FIX is unsupported"); 
        } 
     } 

     public void OnMessageAgnostic(QuickFix.Message message, SessionID sessionID) 
     { 

      int count; 
      if (FixVersion(message)==44) 
      { 
        count = ((QuickFix.FIX44.MarketDataSnapshotFullRefresh)message).NoMDEntries.getValue(); 
      } 
     } 

Répondre

2

Le problème est que est que les types de messages FIX de différentes versions n'ont pas de relation à l'exception de leur classe de base - au plus bas niveau, tous les messages FIX dérivent de Message. Vous devez extraire les informations dont vous avez besoin d'un message, l'empaqueter de manière à ce qu'il soit indépendant de la version (dans la mesure du possible), puis écrire du code contre ces structures de données indépendantes de la version.

Je vous suggère de laisser le pirate message faire le filtrage initial pour vous, si vous êtes OK pour laisser gérer cela, et puis enfilez le message à un gestionnaire qui peut faire face à ce type particulier de message:

public void OnMessage(QuickFix.FIX42.MarketDataIncrementalRefresh message, SessionID sessionID) 
{ 
    this.marketDataIncrementalRefreshHandler.Handle(message); 
} 

public void OnMessage(QuickFix.FIX44.MarketDataIncrementalRefresh message, SessionID sessionID) 
{ 
    this.marketDataIncrementalRefreshHandler.Handle(message); 
} 

... elsewhere ... 

public interface FixMessageHandler 
{ 
    void Handle(Message msg); 
} 

public class MarketDataIncrementalRefreshHandler : FixMessageHandler 
{ 
    public void Handle(Message msg) 
    { 
     DateTime sourceDT = DateTime.ParseExact(message.Header.GetField(52), "yyyyMMdd-HH:mm:ss.fff", ci); 
     DateTime dt = TimeZoneInfo.ConvertTimeToUtc(sourceDT, utcZone); 
     DateTime nowUTC = TimeZoneInfo.ConvertTime(DateTime.UtcNow, utcZone, utcZone); 
     TimeSpan diffToUK = nowUTC - dt; 

     var noMDEntriesGroups = this.GetAllNoMDEntries(msg) 
     foreach (var noMDEntriesGroup in noMDEntriesGroups) 
     { 
      masterForm.MDATA.AddData(
       noMDEntriesGroup.Symbol, 
       noMDEntriesGroup.TickBandNoDecPlaces, 
       sourceDT); 
     } 
    } 

    private IEnumerable<NoMDEntriesGroup> GetAllNoMDEntries(Message msg) 
    { 
     switch (message.GetString(8)) // BeginString 
     { 
      case Values.BeginString_FIX42: 
       return this.GetAllNoMDEntries((QuickFix.FIX42.MarketDataSnapshotFullRefresh)msg); 
      case Values.BeginString_FIX44: 
       return this.GetAllNoMDEntries((QuickFix.FIX44.MarketDataSnapshotFullRefresh)msg); 
      default: 
       throw new NotSupportedException("This version of FIX is unsupported"); 
     } 
    } 

    private IEnumerable<NoMDEntriesGroup> GetAllNoMDEntries(QuickFix.FIX42.MarketDataSnapshotFullRefresh msg) 
    { 
     int count = message.NoMDEntries.getValue(); 
     QuickFix.FIX42.MarketDataSnapshotFullRefresh.NoMDEntriesGroup repeatingMDItem = new QuickFix.FIX42.MarketDataSnapshotFullRefresh.NoMDEntriesGroup(); 
     for (int i = 1; i <= count; i++) 
     { 
      message.GetGroup(i, repeatingMDItem); 

      yield return new NoMDEntriesGroup 
      { 
       Symbol = repeatingMDItem.GetField(55), 
       TickBandNoDecPlaces = int.Parse(repeatingMDItem.GetField(5071) 
      }; 
     } 
    } 

    private IEnumerable<NoMDEntriesGroup> GetAllNoMDEntries(QuickFix.FIX44.MarketDataSnapshotFullRefresh msg) 
    { 
     // Should be practically identical to the above version, with 4.4 subbed for 4.2 
    } 

    private class NoMDEntriesGroup 
    { 
     public string Symbol { get; set; } 
     public int TickBandNoDecPlaces { get; set; } 
    } 
} 
+0

Oui, je vois. En outre, au lieu de votre classe MarketDataIncrementalRefreshHandler(). Je pourrais juste passer comme Quickfix.Message et jeter quand j'ai besoin de la version spécifique ... – ManInMoon

+0

Vous pourriez, oui. Cela va rendre votre classe dérivée de 'Application' très grande, cependant. Et vous ne pouvez lancer à partir de 'Quickfix.Message' après que le message a été fissuré. –

+0

voir modifier s'il vous plaît. Cela me permet de lancer seulement quand j'ai besoin de traiter des bits spécifiques à la version. Le reste du code peut être le même – ManInMoon