private void AddSharesAndCalculateNewAverageCostBasis(string symbol, int quantity, float price_per_share, DateTimeOffset purchased_at) { //Check if we already have a holding like this EquityHolding nh = null; foreach (EquityHolding h in EquityHoldings) { if (h.Symbol.ToUpper() == symbol.ToUpper()) { nh = h; } } //Create a new one if we couldn't find this holding that already exists. if (nh == null) { nh = new EquityHolding(); nh.Symbol = symbol.ToUpper().Trim(); nh.Quantity = 0; nh.AverageCostBasis = 0; EquityHoldings.Add(nh); } //Calculate the new Average Per Share Cost basis float CurrentTotalCost = nh.AverageCostBasis * nh.Quantity; float NewTotalCost = price_per_share * quantity; float NewAvgCostBasis = (CurrentTotalCost + NewTotalCost) / (quantity + nh.Quantity); nh.AverageCostBasis = NewAvgCostBasis; //add the shares we are buying to the balane nh.Quantity = nh.Quantity + quantity; //Log the transaction EquityTransaction et = new EquityTransaction(); et.TransactedOn = purchased_at; et.Quantity = quantity; et.StockSymbol = symbol.ToUpper().Trim(); et.OrderType = TransactionType.Buy; et.PriceExecutedAt = price_per_share; EquityTransactionLog.Add(et); }
public async Task TradeEquityAsync(string symbol, int quantity, TransactionType order_type) { Equity e = Equity.Create(symbol); try { await e.DownloadSummaryAsync(); } catch { throw new Exception("Critical error while fetching equity '" + symbol + "'. Does this equity exist?"); } if (order_type == TransactionType.Buy) { //Be sure we have enough cash to buy float cash_needed = e.Summary.Price * quantity; if (Cash < cash_needed) { throw new Exception("You do not have enough cash to execute this buy order of " + symbol.ToUpper() + ". Cash needed: $" + cash_needed.ToString("#,##0.00") + ". Cash balance: $" + Cash.ToString("#,##0.00")); } AddSharesAndCalculateNewAverageCostBasis(symbol.ToUpper().Trim(), quantity, e.Summary.Price, DateTimeOffset.Now); //Edit cash and add the shares we are buying to the balane Cash = Cash - cash_needed; } else if (order_type == TransactionType.Sell) { //Find our holding EquityHolding eh = null; foreach (EquityHolding ceh in EquityHoldings) { if (ceh.Symbol.ToUpper() == symbol.ToUpper()) { eh = ceh; } } //Throw an error if we do not have any of those shares. if (eh == null) { throw new Exception("You do not have any shares of " + symbol.ToUpper() + " to sell."); } //Throw an error if we do not have enough shares if (eh.Quantity < quantity) { throw new Exception("You do not have " + quantity.ToString() + " shares to sell! You only have " + eh.Quantity.ToString() + " shares."); } //Execute the transaction Cash = Cash + (quantity * e.Summary.Price); eh.Quantity = eh.Quantity - quantity; //Save the transaction log EquityTransaction et = new EquityTransaction(); et.UpdateTransactionTime(); et.StockSymbol = symbol.ToUpper().Trim(); et.OrderType = TransactionType.Sell; et.Quantity = quantity; et.PriceExecutedAt = e.Summary.Price; EquityTransactionLog.Add(et); //Remove the holding if it now 0 if (eh.Quantity == 0) { EquityHoldings.Remove(eh); } } //Take out the commission (if any) if (TradeCost > 0) { EditCash(TradeCost * -1, CashTransactionType.TradingRelatedCharge); } }