13 KiB
13 KiB
In [ ]:
from v2realbot.tools.loadbatch import load_batch from v2realbot.utils.utils import zoneNY import pandas as pd import numpy as np from datetime import timedelta, datetime import vectorbtpro as vbt import os from itables import init_notebook_mode, show init_notebook_mode(all_interactive=True) vbt.settings.set_theme("dark") vbt.settings['plotting']['layout']['width'] = 1280 vbt.settings.plotting.auto_rangebreaks = True # Set the option to display with pagination pd.set_option('display.notebook_repr_html', True) pd.set_option('display.max_rows', 10) # Number of rows per page # Alpaca API credentials ALPACA_API_KEY = os.environ.get('ACCOUNT1_PAPER_API_KEY') ALPACA_API_SECRET = os.environ.get('ACCOUNT1_PAPER_SECRET_KEY') # Initialize Alpaca data client alpaca_data = vbt.AlpacaData.set_custom_settings(client_config=dict( api_key=ALPACA_API_KEY, secret_key=ALPACA_API_SECRET ) )
Fetch Data¶
In [ ]:
# Define the symbol, start, and end dates for your data symbol = 'BAC' start_date = datetime.now() - timedelta(days=10) # Last 30 days end_date = datetime.now() - timedelta(days=1) # yesterday time_interval = '1T' # 1-minute intervals '1 minute' basic_data = vbt.AlpacaData.pull(["BAC"], start=start_date, end=end_date, timeframe=time_interval, tz="America/New_York") basic_data = basic_data.transform(lambda x: x.between_time("9:30","16:00")) #basic_data.data["BAC"].vbt.ohlcv.plot()
filter dates¶
In [ ]:
#filter na dny # dates_of_interest = pd.to_datetime(['2024-04-22', '2024-04-23']).tz_localize('US/Eastern') # filtered_df = df.loc[df.index.normalize().isin(dates_of_interest)] # df = filtered_df # df.info() basic_data.data["BAC"]
In [ ]:
m1_data = basic_data[['Open', 'High', 'Low', 'Close', 'Volume']] m1_data.data["BAC"] #m5_data = m1_data.resample("5T") #m5_data.data["BAC"].head(10) m15_data = m1_data.resample("15T") m15_data = m15_data.transform(lambda x: x.between_time("9:30","15:59")) m15 = m15_data.data["BAC"] m15.vbt.ohlcv.plot() m15 # m1_data.wrapper.index # m1_resampler = m1_data.wrapper.get_resampler("1T") # m1_resampler.index_difference(reverse=True) # m5_resampler.prettify()
Calculate VWAP¶
In [ ]:
#WWAP vbt.phelp(vbt.VWAP.run) close = m1_data.close high = m1_data.high low = m1_data.low volume = m1_data.volume vwapD = vbt.VWAP.run(high, low, close, volume, anchor="D") # vwapT = vbt.VWAP.run(high, low, close, volume, anchor="T") #vwap.vwap fig = m1_data.data["BAC"].vbt.ohlcv.plot() vwapD.vwap.vbt.plot(fig=fig) #vwapT.vwap.vbt.plot(fig=fig) fig.show() vwapD.vwap #vwap = vbt.VWAP.run()
In [ ]:
m1_data.data["BAC"]
defining ENTRY WINDOW and forced EXIT window¶
In [ ]:
#m1_data.data["BAC"].info() import datetime # Define the market open and close times market_open = datetime.time(9, 30) market_close = datetime.time(16, 0) entry_window_opens = 1 entry_window_closes = 350 forced_exit_start = 360 forced_exit_end = 390 forced_exit = m1_data.symbol_wrapper.fill(False) entry_window_open= m1_data.symbol_wrapper.fill(False) # Calculate the time difference in minutes from market open for each timestamp elapsed_min_from_open = (forced_exit.index.hour - market_open.hour) * 60 + (forced_exit.index.minute - market_open.minute) entry_window_open[(elapsed_min_from_open >= entry_window_opens) & (elapsed_min_from_open < entry_window_closes)] = True forced_exit[(elapsed_min_from_open >= forced_exit_start) & (elapsed_min_from_open < forced_exit_end)] = True #entry_window_open.info() # forced_exit.tail(100)
In [ ]:
close = m1_data.close rsi = vbt.RSI.run(close, window=14) long_entries = (rsi.rsi.vbt.crossed_below(28) & entry_window_open) long_exits = (rsi.rsi.vbt.crossed_above(70) | forced_exit) #long_entries.info() #number of trues and falses in long_entries #long_entries.value_counts() long_exits.value_counts()
In [ ]:
close
In [ ]:
def plot_rsi(rsi, close, entries, exits): fig = vbt.make_subplots(rows=1, cols=1, shared_xaxes=True, specs=[[{"secondary_y": True}]], vertical_spacing=0.02, subplot_titles=("RSI", "Price" )) close.vbt.plot(fig=fig, add_trace_kwargs=dict(secondary_y=True)) rsi.plot(fig=fig, add_trace_kwargs=dict(secondary_y=False)) entries.vbt.signals.plot_as_entries(close, fig=fig, add_trace_kwargs=dict(secondary_y=True)) exits.vbt.signals.plot_as_exits(close, fig=fig, add_trace_kwargs=dict(secondary_y=True)) return fig plot_rsi(rsi, close, long_entries, long_exits)
In [ ]:
rsi.rsi
In [ ]:
vbt.phelp(vbt.Portfolio.from_signals)
In [ ]:
sl_stop = np.arange(0.03/100, 0.4/100, 0.05/100).tolist() # Using the round function sl_stop = [round(val, 4) for val in sl_stop] print(sl_stop) sl_stop = vbt.Param(sl_stop) #np.nan mean s no stoploss pf = vbt.Portfolio.from_signals(close=close, entries=long_entries, exits=long_exits, sl_stop=sl_stop, tp_stop = sl_stop, fees=0.0167/100, freq="1s") #sl_stop=sl_stop, tp_stop = sl_stop, pf.stats()
In [ ]:
pf[(0.0003,0.0018)].plot()
In [ ]:
pf[0.03].plot_trade_signals()
pristup k pf jako multi index¶
In [ ]:
#pf[0.03].plot() #pf.order_records pf[(0.03)].stats()
In [ ]:
#zgrupovane statistiky stats_df = pf.stats([ 'total_return', 'total_trades', 'win_rate', 'expectancy' ], agg_func=None) stats_df stats_df.nlargest(10, 'Total Return [%]') #stats_df.info()
In [ ]:
pf[(0.0011,0.0013000000000000002)].plot()
In [ ]:
from pandas.tseries.offsets import DateOffset temp_data = basic_data['2024-4-22'] temp_data res1m = temp_data[["Open", "High", "Low", "Close", "Volume"]] # Define a custom date offset that starts at 9:30 AM and spans 4 hours custom_offset = DateOffset(hours=4, minutes=30) # res1m = res1m.get().resample("4H").agg({ # "Open": "first", # "High": "max", # "Low": "min", # "Close": "last", # "Volume": "sum" # }) res4h = res1m.resample("1h", resample_kwargs=dict(origin="start")) res4h.data res15m = res1m.resample("15T", resample_kwargs=dict(origin="start")) res15m.data["BAC"]
In [ ]:
@vbt.njit def long_entry_place_func_nb(c, low, close, time_in_ns, rsi14, window_open, window_close): market_open_minutes = 570 # 9 hours * 60 minutes + 30 minutes for out_i in range(len(c.out)): i = c.from_i + out_i current_minutes = vbt.dt_nb.hour_nb(time_in_ns[i]) * 60 + vbt.dt_nb.minute_nb(time_in_ns[i]) #print("current_minutes", current_minutes) # Calculate elapsed minutes since market open at 9:30 AM elapsed_from_open = current_minutes - market_open_minutes elapsed_from_open = elapsed_from_open if elapsed_from_open >= 0 else 0 #print( "elapsed_from_open", elapsed_from_open) #elapsed_from_open = elapsed_minutes_from_open_nb(time_in_ns) in_window = elapsed_from_open > window_open and elapsed_from_open < window_close #print("in_window", in_window) # if in_window: # print("in window") if in_window and rsi14[i] > 60: # and low[i, c.col] <= hit_price: # and hour == 9: # (4)! return out_i return -1 @vbt.njit def long_exit_place_func_nb(c, high, close, time_index, tp, sl): # (5)! entry_i = c.from_i - c.wait entry_price = close[entry_i, c.col] hit_price = entry_price * (1 + tp) stop_price = entry_price * (1 - sl) for out_i in range(len(c.out)): i = c.from_i + out_i last_bar_of_day = vbt.dt_nb.day_changed_nb(time_index[i], time_index[i + 1]) #print(next_day) if last_bar_of_day: #pokud je dalsi next day, tak zavirame posledni print("ted",out_i) return out_i if close[i, c.col] >= hit_price or close[i, c.col] <= stop_price : return out_i return -1
In [ ]:
df = pd.DataFrame(np.random.random(size=(5, 10)), columns=list('abcdefghij')) df
In [ ]:
df.sum()