示例#1
0
        /// <summary>Archives a Placement record.</summary>
        /// <param name="transaction">Commits or rejects a set of commands as a unit</param>
        /// <param name="placementId">The value for the PlacementId column.</param>
        /// <param name="rowVersion">The value for the RowVersion column.</param>
        /// <param name="archive">true to archive the object, false to unarchive it.</param>
        public static void Archive(Transaction transaction, int placementId, long rowVersion)
        {
            // Accessor for the Placement Table.
            ServerMarketData.PlacementDataTable placementTable = ServerMarketData.Placement;
            // Rule #1: Make sure the record exists before updating it.
            ServerMarketData.PlacementRow placementRow = placementTable.FindByPlacementId(placementId);
            if ((placementRow == null))
            {
                throw new Exception(string.Format("The Placement table does not have an element identified by {0}", placementId));
            }
            // Rule #2: Optimistic Concurrency Check
            if ((placementRow.RowVersion != rowVersion))
            {
                throw new System.Exception("This record is busy.  Please try again later.");
            }
            // Archive the child records.
            // Delete the record in the ADO database.
            transaction.DataRows.Add(placementRow);
            placementRow.Delete();
            // Archive the record in the SQL database.
            SqlCommand sqlCommand = new SqlCommand("update Placement set Archived = 1 where \"PlacementId\"=@placementId");

            sqlCommand.Connection  = transaction.SqlConnection;
            sqlCommand.Transaction = transaction.SqlTransaction;
            sqlCommand.Parameters.Add("@placementId", @placementId);
            sqlCommand.ExecuteNonQuery();
        }
示例#2
0
        /// <summary>Updates a Placement record.</summary>
        /// <param name="transaction">Commits or rejects a set of commands as a unit</param>
        /// <param name="placementId">The value for the PlacementId column.</param>
        /// <param name="blockOrderId">The value for the BlockOrderId column.</param>
        /// <param name="brokerId">The value for the BrokerId column.</param>
        /// <param name="timeInForceCode">The value for the TimeInForceCode column.</param>
        /// <param name="orderTypeCode">The value for the OrderTypeCode column.</param>
        /// <param name="rowVersion">The value for the RowVersion column.</param>
        /// <param name="isRouted">The value for the IsRouted column.</param>
        /// <param name="quantity">The value for the Quantity column.</param>
        /// <param name="price1">The value for the Price1 column.</param>
        /// <param name="price2">The value for the Price2 column.</param>
        public static void Update(Transaction transaction, int placementId, object blockOrderId, object brokerId, object timeInForceCode, object orderTypeCode, ref long rowVersion, object isRouted, object quantity, object price1, object price2)
        {
            // These values are provided by the server.
            DateTime modifiedTime    = DateTime.Now;
            int      modifiedLoginId = ServerMarketData.LoginId;

            // Rule #1: Make sure the record exists before updating it.
            ServerMarketData.PlacementRow placementRow = ServerMarketData.Placement.FindByPlacementId(placementId);
            if ((placementRow == null))
            {
                throw new Exception("This Placement has been deleted by someone else");
            }

            // Rule #2: The block order exist.
            ServerMarketData.BlockOrderRow blockOrderRow = ServerMarketData.BlockOrder.FindByBlockOrderId((int)blockOrderId);
            if (blockOrderRow == null)
            {
                throw new Exception("This block order has been deleted by someone else");
            }

            // Rule #3: The Block Order is active
            if (blockOrderRow.StatusCode == Shadows.Quasar.Common.Status.Closed ||
                blockOrderRow.StatusCode == Shadows.Quasar.Common.Status.Confirmed ||
                blockOrderRow.StatusCode == Shadows.Quasar.Common.Status.Pending)
            {
                throw new Exception("This order isn't active");
            }

            // Rule #4: Quantity executed doesn't exceed the quantity ordered.
            decimal quantityOrdered = 0.0M;

            foreach (ServerMarketData.OrderRow orderSumRow in blockOrderRow.GetOrderRows())
            {
                quantityOrdered += orderSumRow.Quantity;
            }
            decimal quantityPlaced = 0.0M;

            foreach (ServerMarketData.PlacementRow placementSumRow in blockOrderRow.GetPlacementRows())
            {
                quantityPlaced += placementSumRow.Quantity;
            }
            if (quantityPlaced - placementRow.Quantity + (decimal)quantity > quantityOrdered)
            {
                throw new Exception("The quantity placed is more than the quantity ordered.");
            }

            // Call the primitive library to handle the rest of the operation.
            Shadows.WebService.Core.Placement.Update(transaction, placementId, blockOrderId, brokerId, timeInForceCode, orderTypeCode,
                                                     ref rowVersion, null, isRouted, quantity, price1, price2, null, null, modifiedTime, modifiedLoginId);
        }
示例#3
0
        /// <summary>
        /// This thread takes placements off the queue and creates orders in the local order book for them.
        /// </summary>
        private static void PlacementHandler()
        {
            while (true)
            {
                // Wait here for the next tick to come in.
                Broker.placementQueue.WaitOne();

                // Get the next placement from the queue.
                int placementId = Broker.placementQueue.Dequeue();

                try
                {
                    // Lock the tables.
                    Debug.Assert(!ServerMarketData.AreLocksHeld);
                    ServerMarketData.BlockOrderLock.AcquireReaderLock(Timeout.Infinite);
                    ServerMarketData.PlacementLock.AcquireReaderLock(Timeout.Infinite);

                    // Find the placement row.
                    ServerMarketData.PlacementRow placementRow = ServerMarketData.Placement.FindByPlacementId(placementId);
                    if (placementRow == null)
                    {
                        return;
                    }

                    // Information about the security is found in the block.  It isn't part of the placement so a BlockOrder
                    // record is needed to get some of the ancillary data.
                    ServerMarketData.BlockOrderRow blockOrderRow = placementRow.BlockOrderRow;

                    // The execution quantity needs to be calculated to prevent over execution when the simulator is
                    // restarted.  Count up the quantity executed against this placement.  While this calcuation isn't
                    // perfect -- it will miss when there are multiple placements to the same broker -- it is good enough for
                    // the simulator to restart itself.
                    decimal quantityExecuted = 0.0M;
                    foreach (ServerMarketData.ExecutionRow executionRow in blockOrderRow.GetExecutionRows())
                    {
                        if (executionRow.BrokerId == placementRow.BrokerId)
                        {
                            quantityExecuted += executionRow.Quantity;
                        }
                    }
                }
                catch (Exception exception)
                {
                    // Write the error and stack trace out to the debug listener
                    Debug.WriteLine(String.Format("{0}, {1}", exception.Message, exception.StackTrace));
                }
                finally
                {
                    // Release the global tables.
                    if (ServerMarketData.BlockOrderLock.IsReaderLockHeld)
                    {
                        ServerMarketData.BlockOrderLock.ReleaseReaderLock();
                    }
                    if (ServerMarketData.PlacementLock.IsReaderLockHeld)
                    {
                        ServerMarketData.PlacementLock.ReleaseReaderLock();
                    }
                    Debug.Assert(!ServerMarketData.AreLocksHeld);
                }
            }
        }
示例#4
0
        /// <summary>
        /// This thread takes placements off the queue and creates orders in the local order book for them.
        /// </summary>
        private static void PlacementHandler()
        {
            while (true)
            {
                // Wait here for the next tick to come in.
                Broker.placementQueue.WaitOne();

                // Get the next placement from the queue.
                int placementId = Broker.placementQueue.Dequeue();

                try
                {
                    // Lock the Order Book.
                    Broker.orderBookLock.AcquireWriterLock(CommonTimeout.LockWait);

                    // Lock the tables.
                    Debug.Assert(!ServerMarketData.AreLocksHeld);
                    ServerMarketData.BlockOrderLock.AcquireReaderLock(Timeout.Infinite);
                    ServerMarketData.PlacementLock.AcquireReaderLock(Timeout.Infinite);

                    // Find the placement row.
                    ServerMarketData.PlacementRow placementRow = ServerMarketData.Placement.FindByPlacementId(placementId);
                    if (placementRow == null)
                    {
                        return;
                    }

                    // Information about the security is found in the block.  It isn't part of the placement so a BlockOrder
                    // record is needed to get some of the ancillary data.
                    ServerMarketData.BlockOrderRow blockOrderRow = placementRow.BlockOrderRow;

                    // The execution quantity needs to be calculated to prevent over execution when the simulator is
                    // restarted.  Count up the quantity executed against this placement.  While this calcuation isn't
                    // perfect -- it will miss when there are multiple placements to the same broker -- it is good enough for
                    // the simulator to restart itself.
                    decimal quantityExecuted = 0.0M;
                    foreach (ServerMarketData.ExecutionRow executionRow in blockOrderRow.GetExecutionRows())
                    {
                        if (executionRow.BrokerId == placementRow.BrokerId)
                        {
                            quantityExecuted += executionRow.Quantity;
                        }
                    }

                    // Create a new order book record and copy the data from the placement into the order.
                    OrderBook.OrderRow orderRow = Broker.orderBook.Order.NewOrderRow();
                    orderRow.BlockOrderId     = placementRow.BlockOrderId;
                    orderRow.BrokerId         = placementRow.BrokerId;
                    orderRow.SecurityId       = blockOrderRow.SecurityId;
                    orderRow.QuantityOrdered  = placementRow.Quantity;
                    orderRow.QuantityExecuted = quantityExecuted;
                    orderRow.TimeInForceCode  = placementRow.TimeInForceCode;
                    orderRow.OrderTypeCode    = placementRow.OrderTypeCode;
                    if (!placementRow.IsPrice1Null())
                    {
                        orderRow.Price1 = placementRow.Price1;
                    }
                    if (!placementRow.IsPrice2Null())
                    {
                        orderRow.Price2 = placementRow.Price2;
                    }

                    // Add the new record to the book and accept the changes.
                    Broker.orderBook.Order.AddOrderRow(orderRow);
                    orderRow.AcceptChanges();

                    // Signal to the execution thread that there are orders in the local book to be filled.
                    Broker.orderBookEvent.Set();
                }
                catch (Exception exception)
                {
                    // Write the error and stack trace out to the debug listener
                    Debug.WriteLine(String.Format("{0}, {1}", exception.Message, exception.StackTrace));
                }
                finally
                {
                    // Release the order book.
                    if (Broker.orderBookLock.IsWriterLockHeld)
                    {
                        Broker.orderBookLock.ReleaseWriterLock();
                    }

                    // Release the global tables.
                    if (ServerMarketData.BlockOrderLock.IsReaderLockHeld)
                    {
                        ServerMarketData.BlockOrderLock.ReleaseReaderLock();
                    }
                    if (ServerMarketData.PlacementLock.IsReaderLockHeld)
                    {
                        ServerMarketData.PlacementLock.ReleaseReaderLock();
                    }
                    Debug.Assert(!ServerMarketData.AreLocksHeld);
                }
            }
        }