Overall Statistics
Total Trades
58
Average Win
0.02%
Average Loss
-0.02%
Compounding Annual Return
-75.682%
Drawdown
3.400%
Expectancy
-0.816
Net Profit
-1.807%
Sharpe Ratio
-4.77
Loss Rate
89%
Win Rate
11%
Profit-Loss Ratio
0.65
Alpha
-2.305
Beta
126.987
Annual Standard Deviation
0.189
Annual Variance
0.036
Information Ratio
-4.831
Tracking Error
0.189
Treynor Ratio
-0.007
Total Fees
$321.90
from datetime import timedelta
import decimal as d

class BasicTemplateFuturesAlgorithm(QCAlgorithm):

    def Initialize(self):
        self.SetStartDate(2013, 10, 07)
        self.SetEndDate(2013, 10, 11)
        self.SetCash(1000000)

        # Subscribe and set our expiry filter for the futures chain
        futureCL = self.AddFuture(Futures.Energies.CrudeOilWTI)
        futureCL.SetFilter(timedelta(0), timedelta(182))

        self.entry_ticket = None


    def OnData(self,slice):
        if self.entry_ticket is None:
            for chain in slice.FutureChains:
                 # Get contracts expiring no earlier than in 90 days
                contracts = filter(lambda x: x.Expiry > self.Time + timedelta(90), chain.Value)

                # if there is any contract, trade the front contract
                if len(contracts) == 0: continue
                front = sorted(contracts, key = lambda x: x.Expiry, reverse=True)[0]
                price = self.Securities[front.Symbol].Price
                
                # Place limit order below market price. Wait for rebound to buy 
                self.entry_ticket = self.LimitOrder(front.Symbol, 3, price - d.Decimal(0.01))


    def OnOrderEvent(self, orderEvent):
        #self.Log(str(orderEvent))
        if orderEvent.Status != OrderStatus.Filled:
            return
        
        if self.entry_ticket is not None:
            # When entry order is filled, place TP and SL orders
            if orderEvent.OrderId == self.entry_ticket.OrderId:
                price = orderEvent.FillPrice
                self.LimitOrder(orderEvent.Symbol, -3, price + d.Decimal(0.04))
                self.StopMarketOrder(orderEvent.Symbol, -3, price - d.Decimal(0.03))
            # Otherwise, one of the exit orders was filled, so cancel the open orders
            else:
                self.Transactions.CancelOpenOrders(orderEvent.Symbol)
                self.entry_ticket = None