microsoft/qlib · error · ValueError
trade date is not tradable date
Error message
trade date is not tradable date
What it means
Raised by OnlineOperator.init (qlib/contrib/online/operator.py) when the requested trade date is not in qlib's trading calendar (is_tradable_date returns False). Online operations (generate orders, execute, check) must run on a trading day known to the provider's calendar. Note the message itself has a formatting bug: it uses .format() on a string with no {} placeholder, so the date is not shown.
Source
Thrown at qlib/contrib/online/operator.py:63
path : str
Path to save user account.
date : str (YYYY-MM-DD)
Trade date, when the generated order list will be traded.
Return
----------
um: UserManager()
pred_date: pd.Timestamp
trade_date: pd.Timestamp
"""
qlib.init_from_yaml_conf(client)
um = UserManager(user_data_path=pathlib.Path(path))
um.load_users()
if not date:
trade_date, pred_date = None, None
else:
trade_date = pd.Timestamp(date)
if not is_tradable_date(trade_date):
raise ValueError("trade date is not tradable date".format(trade_date.date()))
pred_date = get_pre_trading_date(trade_date, future=True)
return um, pred_date, trade_date
def add_user(self, id, config, path, date):
"""Add a new user into the a folder to run 'online' module.
Parameters
----------
id : str
User id, should be unique.
config : str
The file path (yaml) of user config
path : str
Path to save user account.
date : str (YYYY-MM-DD)
The date that user account was added.
"""
create_user_folder(path)
View on GitHub (pinned to 79633dd950)
Solutions
- Pass the last trading day at or before your date: trade_date = D.calendar(end_time=date)[-1], then use that.
- Check tradability first: from qlib.contrib.online.operator import is_tradable_date; skip if not tradable.
- Verify qlib.init was pointed at the right provider/calendar (client config) for the market you trade.
Example fix
# before op.execute(date="2021-10-03", ...) # Sunday -> ValueError: trade date is not tradable date # after from qlib.data import D trade_date = D.calendar(end_time="2021-10-04")[-1] # rolls back to last trading day op.execute(date=str(trade_date.date()), ...)
Defensive patterns
Strategy: validation
Validate before calling
from qlib.data import D
from qlib.contrib.online.operator import is_tradable_date
trade_date = D.calendar(end_time=date)[-1]
if not is_tradable_date(trade_date):
raise RuntimeError(f"{trade_date} not tradable; check provider calendar")
op.execute(date=str(trade_date.date()), ...) Try / catch
try:
op.execute(date=date, ...)
except ValueError as e:
if "not tradable" in str(e):
date = str(D.calendar(end_time=date)[-1].date())
op.execute(date=date, ...)
else:
raise Prevention
- Always roll dates back with D.calendar(end_time=...)[-1] before online ops.
- Schedule jobs on trading days derived from the calendar, not raw weekdays.
- Confirm provider/market calendar matches the instruments you trade.
When it happens
Trigger: Calling operator methods (execute/order/check) with date= set to a weekend or holiday for the active market, or a date outside the calendar range of the initialized provider.
Common situations: Cron jobs scheduled on calendar days that land on non-trading days; running against a CN-market calendar with US dates or vice versa; using a date beyond the local data dump's calendar end.
Related errors
- add date is not tradable date
- The account data is not newest! last trading date {}, today
- inner_order_indicators is necessary in un-atomic executor
- unknown loss `%s`
- unknown metric `%s`
AI-assisted analysis of microsoft/qlib@79633dd950 (2026-08-15).
Data as JSON: /api/errors/8adb10b51798bb62.
Report an issue: GitHub.