Back to Community
Buy in the morning, sell at close.

Hi everyone, this is my first post. I'm still learning zipline.

I'm trying to create a simple backtest to buy(open) in the morning(near) and close the position at close(near).

def initialize(context):
context.asset = symbol('ibm')
schedule_function(morning, date_rule = date_rules.every_day(), time_rule = time_rules.market_open(minutes=1))
schedule_function(end_of_day, date_rule = date_rules.every_day(), time_rule = time_rules.market_close(minutes=1))

def morning(context, data):
order_target_percent(context.asset, 1.0)

def end_of_day(context, data):
order_target_percent(context.asset, -1.0)

def handle_data(context, data):
pass

The results seem to suggest that I open and close at the same price everytime. I think I'm in a daily mode, but maybe I need to switch to a min mode? Note: I'm currently running it locally on zipline. I don't want to cheat the system. Basically I need the system to use the open price for the buy and the close price for the sell.

I'll continue to read/search the forum, but so far I don't have solution to this somewhat simple question.

Thanks,

11 responses

I copied in your code and it seems to work. What exactly seems to be the issue?

Clone Algorithm
13
Loading...
Total Returns
--
Alpha
--
Beta
--
Sharpe
--
Sortino
--
Max Drawdown
--
Benchmark Returns
--
Volatility
--
Returns 1 Month 3 Month 6 Month 12 Month
Alpha 1 Month 3 Month 6 Month 12 Month
Beta 1 Month 3 Month 6 Month 12 Month
Sharpe 1 Month 3 Month 6 Month 12 Month
Sortino 1 Month 3 Month 6 Month 12 Month
Volatility 1 Month 3 Month 6 Month 12 Month
Max Drawdown 1 Month 3 Month 6 Month 12 Month
def initialize(context):
    context.asset = symbol('ibm')
    set_benchmark(symbol('ibm'))
    schedule_function(morning, date_rule = date_rules.every_day(), time_rule = time_rules.market_open(minutes=1))
    schedule_function(end_of_day, date_rule = date_rules.every_day(), time_rule = time_rules.market_close(minutes=1))

def morning(context, data):
    order_target_percent(context.asset, 1.0)

def end_of_day(context, data):
    order_target_percent(context.asset, -1.0)

def handle_data(context, data):
    pass
There was a runtime error.

Thanks, I too just ran it on Quantopian and it works as it should.
I guess my problem is how I'm running it locally via zipline.

This is where I'm calling it in my python code.
capital_base = 10000
start = datetime(2010, 1, 1, 0, 0, 0, 0, pytz.utc)
end = datetime(2016, 1, 1, 0, 0, 0, 0, pytz.utc)
perf = run_algorithm(start = start, end = end, initialize=initialize, capital_base=capital_base, handle_data=handle_data, analyze=analyze, bundle = 'quantopian-quandl')

How do I make zipline run locally the same as Quatopian? <-- I think this is my question.
Thanks,

Clone Algorithm
9
Loading...
Total Returns
--
Alpha
--
Beta
--
Sharpe
--
Sortino
--
Max Drawdown
--
Benchmark Returns
--
Volatility
--
Returns 1 Month 3 Month 6 Month 12 Month
Alpha 1 Month 3 Month 6 Month 12 Month
Beta 1 Month 3 Month 6 Month 12 Month
Sharpe 1 Month 3 Month 6 Month 12 Month
Sortino 1 Month 3 Month 6 Month 12 Month
Volatility 1 Month 3 Month 6 Month 12 Month
Max Drawdown 1 Month 3 Month 6 Month 12 Month
def initialize(context):
    context.asset = symbol('ibm')
    schedule_function(morning, date_rule = date_rules.every_day(), time_rule = time_rules.market_open(minutes=1))
    schedule_function(end_of_day, date_rule = date_rules.every_day(), time_rule = time_rules.market_close(minutes=1))

def morning(context, data):
    order_target_percent(context.asset,  1.0)
    
def end_of_day(context, data):
    order_target_percent(context.asset,  -1.0)
    
def handle_data(context, data):
    pass
There was a runtime error.

Why do you need the last pass statement BTW? Thanks

Zipline version of your code would look similar to this notebook, but not exactly the same. There you'd need to load data from your data source instead of using get_pricing.

Loading notebook preview...

Sol - In Python you need a pass(do nothing) statement if you define something but don't use it. For example in a function/method, if, and for. Otherwise you'll get an error.
Ed - Thanks I'll look into this tonight.
My thoughts are that since zipline uses daily resolution(because the data it uses is daily(bring your own data)), the morning and end_of_day methods are getting called at the same "time" only once per day. Therefore using the same price. At this point I'm thinking either I cheat and somehow use the open price for the morning and the close for the end of day. If anyone knows how to change the price that the open() uses I'll set it to the correct value. Or I'll try and find min resolution data somewhere. Again, I don't need min resolution, I only need the open and close of the day. I have an IB account that I've used it to get data before, but I thought it only goes back 1 or 2 years. Another way, might be to alter daily data to have an extra line per day for open and close.

In order to buy at the beginning of the day and sell at the end of the day (ie hold no position overnight), the code should be:


def end_of_day(context, data):  
    order_target_percent(context.asset, 0.0)  

The current algo has

def end_of_day(context, data):  
    order_target_percent(context.asset, -1.0)  

which actually goes short every evening.

Thanks Dan your right about that(0.0 vs -1.0) I meant 0.0.

So I went ahead and purchased some min level data. Does anyone have an example of using their own data locally via zipline?
Per the documentation I've loaded it into a dataframe and pass it into run_algo(data=mydataframe,...other settings..) , but I don't see info about column naming. I've tried using open, high, low, close, volume, datetime. But so far it seems to not pass a validation step. The error was cryptic about zeros.

If anyone has an good example of using their own data, can you please throw me a bone. Again, I doing this via python running locally via zipline(run_algo and setting 'data=my_dataframe').
Thanks,

Hi Russ,

I'd suggest you to look at zipline google group for this info. It's full of similar questions, but i don't remember if I saw at least one answer. This is one of many examples: https://groups.google.com/forum/#!topic/zipline/pmE4-SMKg20

Please, let me know if you manage to get it working. I'm also interested in running Quantopian algos locally, but I don't have minute data yet.
May I ask you where did you buy your data? Is it dividend and split adjusted? Did you buy it from the same data provider as Quantopian buys its data?

Thanks,

Ed - Thanks for the link to the google group. So I found a number of messages talking about loading local csv min data, but none of them seem to work. I'm not sure if it's a version issue, some of the messages were before v1 of zipline. I wish I could have one working example or some more documentation about it. I'm going to continue to try, but I feel like I'm guessing at this point. I'll start a message thread there as it's more of a zipline than a quantopian thing. I saw others are asking for a working example as well.

As for data, I don't want to plug anybody or product, but I'll say that I purchased a third party tool to allow me to download min data from my broker. I'm not sure how far back I can go. But I was able to get the 2 years I requested. Not dividend or split adjusted.

Hi Russ,

I'm also going to experiment with loading minute data to zipline. As I don't have minute data my plan is to convert data from daily time frame(yahoo) or 5 minute time frame(http://stooq.com/db/h/) to minute time frame. I don't need accurate data as my algo makes trade decisions based on daily historical data. As soon as I have data in minute time frame I'll try to load it into zipline.

I'm a daily person as well, I do all my buys in the morning. Then normally I adjust my stops each day till I'm stopped out. But using daily data, I wasn't able to have zipline(using the built in bundles) use the open (morning) as my buys. If you want some min test data(spy), email me at [email protected]_delete_hoo.com.