feat: add fear and greed index dataflow
feat: add Binance single OHLCV for analysts
This commit is contained in:
parent
630e06f512
commit
1712851a07
|
|
@ -11,6 +11,7 @@ def create_fundamentals_analyst(llm, toolkit):
|
|||
company_name = state["company_of_interest"]
|
||||
|
||||
tools = [
|
||||
toolkit.get_binance_ohlcv,
|
||||
toolkit.get_fundamentals_openai
|
||||
]
|
||||
|
||||
|
|
|
|||
|
|
@ -10,11 +10,13 @@ def create_news_analyst(llm, toolkit):
|
|||
ticker = state["company_of_interest"]
|
||||
|
||||
tools = [
|
||||
toolkit.get_binance_ohlcv,
|
||||
# toolkit.get_global_news_openai,
|
||||
# toolkit.get_google_news,
|
||||
# toolkit.get_reddit_news,
|
||||
toolkit.get_blockbeats_news,
|
||||
toolkit.get_coindesk_news,
|
||||
toolkit.get_fear_and_greed_index
|
||||
]
|
||||
|
||||
system_message = (
|
||||
|
|
|
|||
|
|
@ -11,8 +11,10 @@ def create_social_media_analyst(llm, toolkit):
|
|||
company_name = state["company_of_interest"]
|
||||
|
||||
tools = [
|
||||
toolkit.get_stock_news_openai,
|
||||
toolkit.get_reddit_stock_info
|
||||
toolkit.get_binance_ohlcv,
|
||||
toolkit.get_fear_and_greed_index,
|
||||
# toolkit.get_stock_news_openai,
|
||||
# toolkit.get_reddit_stock_info
|
||||
]
|
||||
|
||||
system_message = (
|
||||
|
|
|
|||
|
|
@ -83,6 +83,26 @@ class Toolkit:
|
|||
coindesk_news_result = interface.get_coindesk_news(tickers, count)
|
||||
return coindesk_news_result
|
||||
|
||||
@staticmethod
|
||||
@tool
|
||||
def get_binance_ohlcv(
|
||||
symbol: Annotated[str, "ticker symbol of the asset"],
|
||||
interval: Annotated[
|
||||
str,
|
||||
"Interval for the data, e.g. '1m', '5m', '1h', '1d'",
|
||||
] = "15m",
|
||||
) -> str:
|
||||
"""
|
||||
Retrieve the latest OHLCV data from Binance for a given symbol and interval.
|
||||
Args:
|
||||
symbol (str): Ticker symbol of the asset, e.g. 'BTCUSDT'
|
||||
interval (str): Interval for the data, e.g. '1m', '5m', '1h', '1d'
|
||||
Returns:
|
||||
str: A formatted string containing the latest OHLCV data from Binance for the specified symbol and interval.
|
||||
"""
|
||||
binance_ohlcv_result = interface.get_binance_ohlcv(symbol, interval)
|
||||
return binance_ohlcv_result
|
||||
|
||||
@staticmethod
|
||||
@tool
|
||||
def get_binance_data(
|
||||
|
|
@ -102,7 +122,17 @@ class Toolkit:
|
|||
"""
|
||||
binance_data_result = interface.get_binance_data(symbol, interval)
|
||||
return binance_data_result
|
||||
|
||||
|
||||
@staticmethod
|
||||
@tool
|
||||
def get_fear_and_greed_index() -> str:
|
||||
"""
|
||||
Get current crypto market Fear and Greed Index. 0 means "Extreme Fear", while 100 means "Extreme Greed"
|
||||
Returns:
|
||||
str: A formatted string containing the current crypto market Fear and Greed Index.
|
||||
"""
|
||||
return interface.get_fear_and_greed_index()
|
||||
|
||||
@staticmethod
|
||||
@tool
|
||||
def get_reddit_news(
|
||||
|
|
|
|||
|
|
@ -5,10 +5,12 @@ from .binance_utils import *
|
|||
from .reddit_utils import fetch_top_from_category
|
||||
|
||||
from .interface import (
|
||||
get_binance_ohlcv,
|
||||
# News and sentiment functions
|
||||
get_blockbeats_news,
|
||||
get_coindesk_news,
|
||||
get_google_news,
|
||||
get_fear_and_greed_index,
|
||||
get_reddit_global_news,
|
||||
get_reddit_company_news,
|
||||
# Financial statements functions
|
||||
|
|
@ -20,10 +22,12 @@ from .interface import (
|
|||
)
|
||||
|
||||
__all__ = [
|
||||
"get_binance_ohlcv",
|
||||
# News and sentiment functions
|
||||
"get_blockbeats_news",
|
||||
"get_coindesk_news",
|
||||
"get_google_news",
|
||||
"get_fear_and_greed_index",
|
||||
"get_reddit_global_news",
|
||||
"get_reddit_company_news",
|
||||
# Financial statements functions
|
||||
|
|
|
|||
|
|
@ -0,0 +1,15 @@
|
|||
|
||||
import requests
|
||||
|
||||
def fetch_fear_and_greed_from_alternativeme():
|
||||
"""
|
||||
Fetch the Fear and Greed Index from Alternative.me API.
|
||||
Returns:
|
||||
list[str]: A list of fear and greed index values. Sorted by date in descending order.
|
||||
"""
|
||||
url = "https://api.alternative.me/fng/?limit=10"
|
||||
response = requests.get(url)
|
||||
if response.status_code == 200:
|
||||
data = response.json()
|
||||
if "data" in data and len(data["data"]) > 0:
|
||||
return [value["value"] for value in data["data"] if "value" in value]
|
||||
|
|
@ -3,6 +3,35 @@ from binance.um_futures import UMFutures
|
|||
|
||||
um_futures_client = UMFutures()
|
||||
|
||||
def check_symbol(fn):
|
||||
def wrapper(symbol: str, *args, **kwargs):
|
||||
symbol = symbol.upper()
|
||||
if not symbol.endswith("USDT") and not symbol.endswith("USDC"):
|
||||
symbol += "USDT"
|
||||
return fn(symbol, *args, **kwargs)
|
||||
return wrapper
|
||||
|
||||
@check_symbol
|
||||
def fetch_ohlcv_from_binance(symbol: str, interval: str):
|
||||
"""
|
||||
Fetch historical OHLCV (Open, High, Low, Close, Volume) data from Binance.
|
||||
|
||||
:param symbol: The trading pair symbol (e.g., 'BTCUSDT').
|
||||
:param interval: The time interval for the OHLCV data (e.g., '1m', '5m', '1h').
|
||||
:return: A dictionary containing the latest OHLCV data.
|
||||
"""
|
||||
data = um_futures_client.klines(symbol=symbol, interval=interval, limit=1)
|
||||
if isinstance(data, list) and len(data) > 0:
|
||||
ohlcv = data[0]
|
||||
return {
|
||||
"open": float(ohlcv[1]),
|
||||
"high": float(ohlcv[2]),
|
||||
"low": float(ohlcv[3]),
|
||||
"close": float(ohlcv[4]),
|
||||
"volume": float(ohlcv[5])
|
||||
}
|
||||
|
||||
@check_symbol
|
||||
def fetch_klines_from_binance(symbol: str, interval: str, limit: int = 75):
|
||||
"""
|
||||
Fetch historical klines (candlestick data) from Binance.
|
||||
|
|
@ -14,6 +43,7 @@ def fetch_klines_from_binance(symbol: str, interval: str, limit: int = 75):
|
|||
"""
|
||||
return um_futures_client.klines(symbol=symbol, interval=interval, limit=limit)
|
||||
|
||||
@check_symbol
|
||||
def fetch_depth_from_binance(symbol: str, limit: int = 50):
|
||||
"""
|
||||
Fetch the order book depth from Binance.
|
||||
|
|
@ -24,6 +54,7 @@ def fetch_depth_from_binance(symbol: str, limit: int = 50):
|
|||
"""
|
||||
return um_futures_client.depth(symbol=symbol, limit=limit)
|
||||
|
||||
@check_symbol
|
||||
def fetch_24hr_pricechange_from_binance(symbol: str):
|
||||
"""
|
||||
Fetch 24-hour ticker price change statistics from Binance.
|
||||
|
|
@ -33,6 +64,7 @@ def fetch_24hr_pricechange_from_binance(symbol: str):
|
|||
"""
|
||||
return um_futures_client.ticker_24hr_price_change(symbol=symbol)
|
||||
|
||||
@check_symbol
|
||||
def fetch_toplongshort_position_ratio_from_binance(symbol: str, period: str, limit: int = 50):
|
||||
"""
|
||||
Fetch the top long/short position ratio from Binance.
|
||||
|
|
@ -44,6 +76,7 @@ def fetch_toplongshort_position_ratio_from_binance(symbol: str, period: str, lim
|
|||
"""
|
||||
return um_futures_client.top_long_short_position_ratio(symbol=symbol, period=period, limit=limit)
|
||||
|
||||
@check_symbol
|
||||
def fetch_toplongshort_account_ratio_from_binance(symbol: str, period: str, limit: int = 50):
|
||||
"""
|
||||
Fetch the top long/short account ratio from Binance.
|
||||
|
|
@ -55,6 +88,7 @@ def fetch_toplongshort_account_ratio_from_binance(symbol: str, period: str, limi
|
|||
"""
|
||||
return um_futures_client.top_long_short_account_ratio(symbol=symbol, period=period, limit=limit)
|
||||
|
||||
@check_symbol
|
||||
def fetch_global_longshort_account_ratio_from_binance(symbol: str, period: str, limit: int = 50):
|
||||
"""
|
||||
Fetch the global long/short account ratio from Binance.
|
||||
|
|
@ -66,6 +100,7 @@ def fetch_global_longshort_account_ratio_from_binance(symbol: str, period: str,
|
|||
"""
|
||||
return um_futures_client.long_short_account_ratio(symbol=symbol, period=period, limit=limit)
|
||||
|
||||
@check_symbol
|
||||
def fetch_taker_longshort_ratio_from_binance(symbol: str, period: str, limit: int = 50):
|
||||
"""
|
||||
Fetch the taker long/short ratio from Binance.
|
||||
|
|
|
|||
|
|
@ -2,11 +2,9 @@ from typing import Annotated, Dict
|
|||
from .blockbeats_utils import fetch_news_from_blockbeats
|
||||
from .coindesk_utils import fetch_news_from_coindesk
|
||||
from .reddit_utils import fetch_top_from_category
|
||||
from .yfin_utils import *
|
||||
from .stockstats_utils import *
|
||||
from .googlenews_utils import *
|
||||
from .binance_utils import *
|
||||
from .finnhub_utils import get_data_in_range
|
||||
from .alternativeme_utils import fetch_fear_and_greed_from_alternativeme
|
||||
from dateutil.relativedelta import relativedelta
|
||||
from concurrent.futures import ThreadPoolExecutor
|
||||
from datetime import datetime
|
||||
|
|
@ -14,10 +12,14 @@ import json
|
|||
import os
|
||||
import pandas as pd
|
||||
from tqdm import tqdm
|
||||
import yfinance as yf
|
||||
from openai import OpenAI
|
||||
from .config import get_config, set_config, DATA_DIR
|
||||
|
||||
from warnings import deprecated
|
||||
from .yfin_utils import *
|
||||
from .stockstats_utils import *
|
||||
from .finnhub_utils import get_data_in_range
|
||||
import yfinance as yf
|
||||
|
||||
def get_blockbeats_news(count: Annotated[int, "news' count, no more than 30"] = 10):
|
||||
"""
|
||||
|
|
@ -66,6 +68,10 @@ def get_coindesk_news(
|
|||
|
||||
return f"## Coindesk News:\n\n{news_str}"
|
||||
|
||||
def get_fear_and_greed_index() -> str:
|
||||
fng = fetch_fear_and_greed_from_alternativeme()
|
||||
return f"""## Fear and Greed Index: {fng[0]}\n0 means \"Extreme Fear\", while 100 means \"Extreme Greed\"\nPrevious daily FnG: {','.join(fng[1:])}"""
|
||||
|
||||
def get_google_news(
|
||||
query: Annotated[str, "Query to search with"],
|
||||
curr_date: Annotated[str, "Curr date in yyyy-mm-dd format"],
|
||||
|
|
@ -200,6 +206,30 @@ def get_reddit_company_news(
|
|||
|
||||
return f"##{ticker} News Reddit, from {before} to {curr_date}:\n\n{news_str}"
|
||||
|
||||
def get_binance_ohlcv(
|
||||
symbol: Annotated[str, "ticker symbol of the asset"],
|
||||
interval: Annotated[str, "time interval for the data, e.g., '1m', '5m', '1h'"],
|
||||
) -> str:
|
||||
"""
|
||||
Fetch the latest OHLCV (Open, High, Low, Close, Volume) data from Binance for a given symbol and interval.
|
||||
|
||||
Args:
|
||||
symbol (str): The trading pair symbol (e.g., 'BTCUSDT').
|
||||
interval (str): The time interval for the OHLCV data (e.g., '1m', '5m', '1h').
|
||||
Returns:
|
||||
str: A formatted string containing the latest OHLCV data.
|
||||
"""
|
||||
symbol = symbol.upper().strip()
|
||||
if not symbol.endswith("USDT"):
|
||||
symbol += "USDT"
|
||||
|
||||
ohlcv = fetch_ohlcv_from_binance(symbol, interval)
|
||||
if ohlcv is dict:
|
||||
return (
|
||||
f"## {symbol} Futures **Latest OHLCV Data** in last {interval}:\n"
|
||||
f"Open: {ohlcv['open']}, High: {ohlcv['high']}, Low: {ohlcv['low']}, Close: {ohlcv['close']}, Volume: {ohlcv['volume']}\n"
|
||||
)
|
||||
|
||||
def get_binance_data(
|
||||
symbol: Annotated[str, "ticker symbol of the asset"],
|
||||
interval: Annotated[str, "time interval for the data, e.g., '1m', '5m', '1h'"],
|
||||
|
|
|
|||
|
|
@ -122,12 +122,15 @@ class TradingAgentsGraph:
|
|||
),
|
||||
"social": ToolNode(
|
||||
[
|
||||
self.toolkit.get_stock_news_openai,
|
||||
self.toolkit.get_reddit_stock_info,
|
||||
self.toolkit.get_binance_ohlcv,
|
||||
self.toolkit.get_fear_and_greed_index,
|
||||
# self.toolkit.get_stock_news_openai,
|
||||
# self.toolkit.get_reddit_stock_info,
|
||||
]
|
||||
),
|
||||
"news": ToolNode(
|
||||
[
|
||||
self.toolkit.get_binance_ohlcv,
|
||||
# self.toolkit.get_global_news_openai,
|
||||
# self.toolkit.get_google_news,
|
||||
self.toolkit.get_blockbeats_news,
|
||||
|
|
@ -137,6 +140,7 @@ class TradingAgentsGraph:
|
|||
),
|
||||
"fundamentals": ToolNode(
|
||||
[
|
||||
self.toolkit.get_binance_ohlcv,
|
||||
self.toolkit.get_fundamentals_openai
|
||||
]
|
||||
),
|
||||
|
|
|
|||
Loading…
Reference in New Issue