/// <summary> /// Shuts down the TT API /// </summary> public void Dispose() { lock (m_lock) { if (!m_disposed) { // Unattached callbacks and dispose of all subscriptions if (plsList != null) { for (int i = 0; i < plsList.Count; i++) { plsList[i].Update -= pls_Update; plsList[i].Dispose(); plsList[i] = null; } } if (ics != null) { ics.InstrumentsUpdated -= ics_InstrumentsUpdated; ics.Dispose(); ics = null; } // Begin shutdown the TT API TTAPI.ShutdownCompleted += new EventHandler(TTAPI_ShutdownCompleted); TTAPI.Shutdown(); m_disposed = true; } } }
/// <summary> /// Subscribe to the instrument catalog for a given option. /// </summary> /// <param productName="product">Product to subscribe to.</param> private void SubscribeToInstrumentCatalog(Product product) { log.Info($"Suscribe to product: {product.Name}"); InstrumentCatalogSubscription instrumentCatalogSubscription = new InstrumentCatalogSubscription(product, Dispatcher.Current); instrumentCatalogSubscription.InstrumentsUpdated += InstrumentsUpdated; instrumentCatalogSubscription.Start(); }
//TA.TickerheadConverters.ConvertFromDB2TT(TickerHead) void pls_Update(object sender, ProductLookupSubscriptionEventArgs e) { if (e.Error == null) { Console.WriteLine("Product Found: {0}", e.Product.Name); InstrumentCatalogSubscription ics = new InstrumentCatalogSubscription(e.Product, Dispatcher.Current); ics.InstrumentsUpdated += new EventHandler <InstrumentCatalogUpdatedEventArgs>(ics_InstrumentsUpdated); ics.Start(); } else { Console.WriteLine(e.Error.Message); } }
public void Subscribe2InstrumentCatalogs(object sender, ProductLookupSubscriptionEventArgs e) { if (e.Error == null) { Console.WriteLine("Product Found: {0}", e.Product.Name); InstrumentCatalogSubscription ICS = new InstrumentCatalogSubscription(e.Product, Dispatcher.Current); IcsDictionary.Add(e.Product.Key, ICS); ICS.InstrumentsUpdated += new EventHandler <InstrumentCatalogUpdatedEventArgs>(ICUEventHandler); ICS.Start(); } else { Console.WriteLine(e.Error.Message); } }
/// <summary> /// InstrumentCatalogSubscription InstrumentsUpdated event. /// </summary> private void InstrumentsUpdated(object sender, InstrumentCatalogUpdatedEventArgs e) { InstrumentCatalogSubscription instrumentCatalogSubscription = sender as InstrumentCatalogSubscription; if (instrumentCatalogSubscription?.Instruments?.Values != null) { foreach (Instrument instru in instrumentCatalogSubscription.Instruments.Values) { if (!_availableInstrumentDico.ContainsKey(instru.Key.SeriesKey)) { _availableInstrumentDico.Add(instru.Key.SeriesKey, instru); InstrumentDetails instruDetails = instru.InstrumentDetails; DataUpdateEvent?.Invoke(this, instruDetails.Key.SeriesKey, instruDetails.ExpirationDate.ToDateTime(), instruDetails.StrikePrice, instruDetails.OptionType.ToString().ToUpper(), instruDetails.Name, instru.Product.Type.Name, instru.Product.Name); } } } }
/// <summary> /// Subscribe to the instrument catalog for a given product. /// </summary> /// <param name="product">Product to subscribe to.</param> private void subscribeToInstrumentCatalog(Product product) { if (!m_instrumentCatalogSubscriptionList.ContainsKey(product)) { // Create and start an instrument catalog subscription. InstrumentCatalogSubscription instrumentCatalogSubscription = new InstrumentCatalogSubscription(product, Dispatcher.Current); instrumentCatalogSubscription.InstrumentsUpdated += new EventHandler <InstrumentCatalogUpdatedEventArgs>(instrumentsUpdated); instrumentCatalogSubscription.Start(); // Track this subscription for cleanup. m_instrumentCatalogSubscriptionList.Add(product, instrumentCatalogSubscription); } else { // The instrument subscription was already made. Update the view. updateInstrumentTreeViewNodes(m_instrumentCatalogSubscriptionList[product]); } }
/// <summary> /// Update the instrument tree view nodes for a given product. /// </summary> /// <param name="instrumentCatalogSubscription">InstrumentCatalogSubscription</param> private void updateInstrumentTreeViewNodes(InstrumentCatalogSubscription instrumentCatalogSubscription) { treeViewProductList.BeginUpdate(); TreeNode updatedNode = null; // Find the product in the tree view for the selected product tree view node. foreach (TreeNode node in treeViewProductList.Nodes) { if (String.Equals((node.Tag as Product).Name, instrumentCatalogSubscription.Product.Name)) { updatedNode = node; break; } } // updatedNode should never be null. if (updatedNode == null) { return; } // Clear out any items currently in the node. ("Loading ...") updatedNode.Nodes.Clear(); // Insert the instruments as child nodes within the product tree view node. foreach (Instrument instr in instrumentCatalogSubscription.Instruments.Values) { TreeNode node = updatedNode.Nodes.Add(instr.GetFormattedName(InstrumentNameFormat.Normal)); node.ImageIndex = node.SelectedImageIndex = GetImageCode(instr.Product.Type); // Add tooltip text from the Definition node.ToolTipText = instr.GetFormattedName(InstrumentNameFormat.Short) + "\r\n" + instr.InstrumentDetails.Currency + "\r\n" + instr.InstrumentDetails.TickSize.Numerator.ToString() + " / " + instr.InstrumentDetails.TickSize.Numerator.ToString(); node.Tag = instr; } Cursor = Cursors.Default; treeViewProductList.EndUpdate(); }
//////////////////////////////////////////////////////////////////////////////////////////////////// /// <summary> Event notification for status of authentication. </summary> //////////////////////////////////////////////////////////////////////////////////////////////////// public void m_api_TTAPIStatusUpdate(object sender, TTAPIStatusUpdateEventArgs e) { Console.WriteLine("TTAPIStatusUpdate: {0}", e); if (e.IsReady == false) { // TODO: Do any connection lost processing here return; } // TODO: Do any connection up processing here // note: can happen multiple times with your application life cycle WorkerDispatcher dispatcher = new WorkerDispatcher("InstCat"); dispatcher.Run(); InstrumentCatalogSubscription asSpreads = new InstrumentCatalogSubscription(Product.Autospreader, dispatcher); asSpreads.OnData += OnSpreadDefinitionNotification; asSpreads.Start(); }
public void Dispose() { lock (m_Lock) { if (!m_isDisposed) { if (m_instCatSubscription != null) { m_instCatSubscription.OnData -= OnSpreadDefinitionNotification; m_instCatSubscription.Dispose(); m_instCatSubscription = null; } m_isDisposed = true; } TTAPI.Shutdown(); } }
/// <summary> /// Subscribe to the instrument catalog for a given product. /// </summary> /// <param name="product">Product to subscribe to.</param> private void subscribeToInstrumentCatalog(Product product) { if (!m_instrumentCatalogSubscriptionList.ContainsKey(product)) { // Create and start an instrument catalog subscription. InstrumentCatalogSubscription instrumentCatalogSubscription = new InstrumentCatalogSubscription(product, Dispatcher.Current); instrumentCatalogSubscription.InstrumentsUpdated += new EventHandler<InstrumentCatalogUpdatedEventArgs>(instrumentsUpdated); instrumentCatalogSubscription.Start(); // Track this subscription for cleanup. m_instrumentCatalogSubscriptionList.Add(product, instrumentCatalogSubscription); } else { // The instrument subscription was already made. Update the view. updateInstrumentTreeViewNodes(m_instrumentCatalogSubscriptionList[product]); } }
/// <summary> /// Shuts down the TT API /// </summary> public void Dispose() { lock (m_lock) { if (!m_disposed) { // Unattached callbacks and dispose of all subscriptions if (pls != null) { pls.Update -= pls_Update; pls.Dispose(); pls = null; } if (ics != null) { ics.InstrumentsUpdated -= ics_InstrumentsUpdated; ics.Dispose(); ics = null; } // Begin shutdown the TT API TTAPI.ShutdownCompleted += new EventHandler(TTAPI_ShutdownCompleted); TTAPI.Shutdown(); m_disposed = true; } } }
}//Job // ***************************************************************** // **** Job Processing Methods **** // ***************************************************************** /// <summary> /// Called by the thread's dispatcher after an outside thread has pushed a new Job. /// </summary> private void ProcessAJob() { if (m_isDisposing) { return; } Job aJob; while (m_InQueue.TryDequeue(out aJob)) // NET 4.5 concurrent queue. No locking needed. { m_WorkQueue.Enqueue(aJob); // push onto my private queue. } // // Process the jobs now. // while (m_WorkQueue.Count > 0) { Job job = m_WorkQueue.Dequeue(); if (job.Product != null) { // if (string.IsNullOrEmpty(job.SeriesName)) { // User wants all instruments assoc with this product. // // Process Instrument Catalog requests // InstrumentCatalogSubscription instrumentSub = null; if (!m_InstrumentCatalogs.TryGetValue(job.Product.Key, out instrumentSub)) { // Failed to find a subscription. Create a new one! instrumentSub = new InstrumentCatalogSubscription(job.Product, m_Dispatcher); instrumentSub.InstrumentsUpdated += InstrumentCatalog_InstrumentsUpdated; instrumentSub.Start(); // submit the request. m_InstrumentCatalogs.Add(job.Product.Key, instrumentSub); // store the catalog object Log.NewEntry(LogLevel.Minor, "{0}: Subscribing to instr catalog for {1}.", this.Name, job.Product.Name); } } else { // User requested Instrument info using the ProductKey and a series Name only. (Not instr Key). //InstrumentLookupSubscription lookup = null; Log.NewEntry(LogLevel.Major, "{0}: InstrumentLookup {1} {2}.", this.Name, job.Product, job.SeriesName); InstrumentLookupSubscription subscriber = new InstrumentLookupSubscription(m_TTServices.session, m_Dispatcher, job.Product.Key, job.SeriesName); subscriber.Update += new EventHandler <InstrumentLookupSubscriptionEventArgs>(InstrumentLookup_InstrumentUpdated); //m_InstrumentLookupsUnknown.Add(job.InstrumentKey, subscriber); subscriber.Start(); } } else if (job.InstrumentKey != null && job.Settings == null && !job.IsTimeAndSales) { // // Process an Instrument information request // InstrumentLookupSubscription lookup = null; if (!m_InstrumentLookups.TryGetValue(job.InstrumentKey, out lookup)) { Log.NewEntry(LogLevel.Major, "{0}: InstrumentLookup {1}.", this.Name, job.InstrumentKey); InstrumentLookupSubscription subscriber = new InstrumentLookupSubscription(m_TTServices.session, m_Dispatcher, job.InstrumentKey); subscriber.Update += new EventHandler <InstrumentLookupSubscriptionEventArgs>(InstrumentLookup_InstrumentUpdated); m_InstrumentLookups.Add(job.InstrumentKey, subscriber); subscriber.Start(); } else { Log.NewEntry(LogLevel.Major, "{0}: InstrumentLookup {1} already submitted.", this.Name, job.InstrumentKey); } } else if (job.InstrumentKey != null) { // // Subscribe to an instrument price // Instrument instrument = null; InstrumentCatalogSubscription catalog = null; // First, find instrument catalog for this instr. InstrumentLookupSubscription instrumentSub = null; // or find a specific instrument subscription. //InstrumentDetails instrumentDetails = null; //UVProd.InstrumentName instrumentName ; if (m_InstrumentLookups.TryGetValue(job.InstrumentKey, out instrumentSub)) { instrument = instrumentSub.Instrument; } else if (m_InstrumentCatalogs.TryGetValue(job.InstrumentKey.ProductKey, out catalog)) { catalog.Instruments.TryGetValue(job.InstrumentKey, out instrument); } //else if (m_KeyToInstruments.TryGetValue(job.InstrumentKey, out instrumentName) && m_InstrumentDetails.TryGetValue(instrumentName, out instrumentDetails)) //{ // m_InstrumentLookups.TryGetValue(job.InstrumentKey, out instrumentSub) //} else { Log.NewEntry(LogLevel.Minor, "{0}: I failed to find instrument key {1}.", this.Name, job.InstrumentKey.ToString()); return; } if (instrument != null) { if (!job.IsTimeAndSales) { // this is a market data subscription request - Subscribe or update pre-existing subscription. PriceSubscription priceSub = null; if (!m_PriceSubscriptions.TryGetValue(instrument.Key, out priceSub)) { // Can't find a subscription, so create one. Log.NewEntry(LogLevel.Major, "{0}: Creating new subscription for {1} with settings {2}.", this.Name, instrument.Name, job.Settings.PriceData); priceSub = new PriceSubscription(instrument, Dispatcher.Current); m_PriceSubscriptions.Add(instrument.Key, priceSub); // add to our list of subscription objects. if (!m_InstrKeyToVolume.ContainsKey(instrument.Key)) { m_InstrKeyToVolume.Add(instrument.Key, new int[4]); // create a new array for volume aggregations } priceSub.FieldsUpdated += new FieldsUpdatedEventHandler(PriceSubscription_Updated); // attach my handler to it. priceSub.Settings = job.Settings; priceSub.Start(); } else { Log.NewEntry(LogLevel.Major, "{0}: Found old subscription for {1}. Overwriting settings {2}.", this.Name, instrument.Name, job.Settings.ToString()); priceSub.Settings = job.Settings; priceSub.Start(); } } else { // this is a time and sales data request TimeAndSalesSubscription timeAndSalesSub = null; if (!m_TimeAndSalesSubscriptions.TryGetValue(instrument.Key, out timeAndSalesSub)) { // Can't find a subscription, so create one. Log.NewEntry(LogLevel.Major, "{0}: Creating new time and sales subscription for {1}", this.Name, instrument.Name); timeAndSalesSub = new TimeAndSalesSubscription(instrument, Dispatcher.Current); m_TimeAndSalesSubscriptions.Add(instrument.Key, timeAndSalesSub); // add to our list of subscription objects. if (!m_InstrKeyToVolume.ContainsKey(instrument.Key)) { m_InstrKeyToVolume.Add(instrument.Key, new int[4]); // create a new array for volume aggregations } timeAndSalesSub.Update += new EventHandler <TimeAndSalesEventArgs>(TimeAndSalesSubscription_Updated); // attach my handler to it. timeAndSalesSub.Start(); } else { Log.NewEntry(LogLevel.Major, "{0}: Found existing time and sales subscription for {1}.", this.Name, instrument.Name, job.Settings.ToString()); } } } } } //wend Job in WorkQueue. } //ProcessAJob()
/// <summary> /// InstrumentCatalogSubscription InstrumentsUpdated event. /// </summary> private void instrumentsUpdated(object sender, InstrumentCatalogUpdatedEventArgs e) { InstrumentCatalogSubscription instrumentCatalogSubscription = sender as InstrumentCatalogSubscription; updateInstrumentTreeViewNodes(instrumentCatalogSubscription); }
}//Job // ***************************************************************** // **** Job Processing Methods **** // ***************************************************************** /// <summary> /// Called by the thread's dispatcher after an outside thread has pushed a new Job. /// </summary> private void ProcessAJob() { if (m_isDisposing) { return; } Job aJob; while (m_InQueue.TryDequeue(out aJob)) // NET 4.5 concurrent queue. No locking needed. { m_WorkQueue.Enqueue(aJob); // push onto my private queue. } // // Process the jobs now. // while (m_WorkQueue.Count > 0) { Job job = m_WorkQueue.Dequeue(); if (job.Product != null) { // // Process Instrument Catalog requests // InstrumentCatalogSubscription instrumentSub = null; if (!m_InstrumentCatalogs.TryGetValue(job.Product.Key, out instrumentSub)) { // Failed to find a subscription. Create a new one! instrumentSub = new InstrumentCatalogSubscription(job.Product, m_Dispatcher); instrumentSub.InstrumentsUpdated += InstrumentCatalog_InstrumentsUpdated; instrumentSub.Start(); // submit the request. m_InstrumentCatalogs.Add(job.Product.Key, instrumentSub); // store the catalog object Log.NewEntry(LogLevel.Minor, "{0}: Subscribing to instr catalog for {1}.", this.Name, job.Product.Name); } } else if (job.InstrumentKey != null && job.Settings == null) { // // Process an Instrument information request // InstrumentLookupSubscription lookup = null; if (!m_InstrumentLookups.TryGetValue(job.InstrumentKey, out lookup)) { Log.NewEntry(LogLevel.Major, "{0}: InstrumentLookup {1}.", this.Name, job.InstrumentKey); InstrumentLookupSubscription subscriber = new InstrumentLookupSubscription(m_TTServices.session, m_Dispatcher, job.InstrumentKey); subscriber.Update += new EventHandler <InstrumentLookupSubscriptionEventArgs>(InstrumentLookup_InstrumentUpdated); m_InstrumentLookups.Add(job.InstrumentKey, subscriber); subscriber.Start(); } else { Log.NewEntry(LogLevel.Major, "{0}: InstrumentLookup {1} already submitted.", this.Name, job.InstrumentKey); } } else if (job.InstrumentKey != null) { // // Subscribe to an instrument // Instrument instrument = null; InstrumentCatalogSubscription catalog = null; // First, find instrument catalog for this instr. InstrumentLookupSubscription instrumentSub = null; // or find a specific instrument subscription. if (m_InstrumentLookups.TryGetValue(job.InstrumentKey, out instrumentSub)) { instrument = instrumentSub.Instrument; } else if (m_InstrumentCatalogs.TryGetValue(job.InstrumentKey.ProductKey, out catalog)) { catalog.Instruments.TryGetValue(job.InstrumentKey, out instrument); } else { Log.NewEntry(LogLevel.Minor, "{0}: I failed to find instrument key {1}.", this.Name, job.InstrumentKey.ToString()); return; } if (instrument != null) { // Subscribe or update pre-existing subscription. PriceSubscription priceSub = null; if (!m_PriceSubscriptions.TryGetValue(instrument.Key, out priceSub)) { // Can't find a subscription, so create one. Log.NewEntry(LogLevel.Major, "{0}: Creating new subscription for {1} with settings {2}.", this.Name, instrument.Name, job.Settings.PriceData); priceSub = new PriceSubscription(instrument, Dispatcher.Current); m_PriceSubscriptions.Add(instrument.Key, priceSub); // add to our list of subscription objects. priceSub.FieldsUpdated += new FieldsUpdatedEventHandler(PriceSubscription_Updated); // attach my handler to it. priceSub.Settings = job.Settings; priceSub.Start(); } else { Log.NewEntry(LogLevel.Major, "{0}: Found old subscription for {1}. Overwriting settings {2}.", this.Name, instrument.Name, job.Settings.ToString()); priceSub.Settings = job.Settings; priceSub.Start(); } } } } //wend Job in WorkQueue. } //ProcessAJob()
void pls_Update(object sender, ProductLookupSubscriptionEventArgs e) { if (e.Error == null) { Console.WriteLine("Product Found: {0}", e.Product.Name); InstrumentCatalogSubscription ics = new InstrumentCatalogSubscription(e.Product, Dispatcher.Current); ics.InstrumentsUpdated += new EventHandler<InstrumentCatalogUpdatedEventArgs>(ics_InstrumentsUpdated); ics.Start(); } else { Console.WriteLine(e.Error.Message); } }
public void Subscribe2InstrumentCatalogs(object sender, ProductLookupSubscriptionEventArgs e) { if (e.Error == null) { Console.WriteLine("Product Found: {0}", e.Product.Name); InstrumentCatalogSubscription ICS = new InstrumentCatalogSubscription(e.Product, Dispatcher.Current); IcsDictionary.Add(e.Product.Key, ICS); ICS.InstrumentsUpdated += new EventHandler<InstrumentCatalogUpdatedEventArgs>(ICUEventHandler); ICS.Start(); } else { Console.WriteLine(e.Error.Message); } }