trader_agents_performance / tabs /trader_plots.py
cyberosa
adding new weekly and daily graphs
efabdf9
raw
history blame
11.2 kB
import gradio as gr
import pandas as pd
import plotly.express as px
trader_metric_choices = [
"mech calls",
"bet amount",
"earnings",
"net earnings",
"ROI",
"nr_trades",
]
default_trader_metric = "ROI"
def get_metrics_text() -> gr.Markdown:
metric_text = """
## Metrics at the graph
These metrics are computed weekly. The statistical measures are:
* min, max, 25th(q1), 50th(median) and 75th(q2) percentiles
* the upper and lower fences to delimit possible outliers
* the average values as the dotted lines
"""
return gr.Markdown(metric_text)
def get_interpretation_text() -> gr.Markdown:
interpretation_text = """
## Meaning of KL-divergence values
* Y = 0.05129
* Market accuracy off by 5%
* Y = 0.1053
* Market accuracy off by 10%
* Y = 0.2876
* Market accuracy off by 25%
* Y = 0.5108
* Market accuracy off by 40%
* Y = 1.2040
* Market accuracy off by 70%
* Y = 2.3026
* Market accuracy off by 90%
"""
return gr.Markdown(interpretation_text)
def plot_trader_metrics_by_market_creator(
metric_name: str, traders_df: pd.DataFrame
) -> gr.Plot:
"""Plots the weekly trader metrics."""
if metric_name == "mech calls":
metric_name = "mech_calls"
column_name = "nr_mech_calls"
yaxis_title = "Total nr of mech calls per trader"
elif metric_name == "ROI":
column_name = "roi"
yaxis_title = "Total ROI (net profit/cost)"
elif metric_name == "bet amount":
metric_name = "bet_amount"
column_name = metric_name
yaxis_title = "Total bet amount per trader (xDAI)"
elif metric_name == "net earnings":
metric_name = "net_earnings"
column_name = metric_name
yaxis_title = "Total net profit per trader (xDAI)"
elif metric_name == "nr_trades":
column_name = metric_name
yaxis_title = "Total nr of trades per trader"
else: # earnings
column_name = metric_name
yaxis_title = "Total gross profit per trader (xDAI)"
traders_filtered = traders_df[["month_year_week", "market_creator", column_name]]
fig = px.box(
traders_filtered,
x="month_year_week",
y=column_name,
color="market_creator",
color_discrete_sequence=["purple", "goldenrod", "darkgreen"],
category_orders={"market_creator": ["pearl", "quickstart", "all"]},
)
fig.update_traces(boxmean=True)
fig.update_layout(
xaxis_title="Week",
yaxis_title=yaxis_title,
legend=dict(yanchor="top", y=0.5),
)
fig.update_xaxes(tickformat="%b %d\n%Y")
return gr.Plot(
value=fig,
)
def plot_trader_daily_metrics_by_market_creator(
metric_name: str, traders_df: pd.DataFrame
) -> gr.Plot:
"""Plots the daily trader metrics."""
if metric_name == "mech calls":
metric_name = "mech_calls"
column_name = "nr_mech_calls"
yaxis_title = "Total nr of mech calls per trader"
elif metric_name == "ROI":
column_name = "roi"
yaxis_title = "Total ROI (net profit/cost)"
elif metric_name == "bet amount":
metric_name = "bet_amount"
column_name = metric_name
yaxis_title = "Total bet amount per trader (xDAI)"
elif metric_name == "net earnings":
metric_name = "net_earnings"
column_name = metric_name
yaxis_title = "Total net profit per trader (xDAI)"
elif metric_name == "nr_trades":
column_name = metric_name
yaxis_title = "Total nr of trades per trader"
else: # earnings
column_name = metric_name
yaxis_title = "Total gross profit per trader (xDAI)"
traders_filtered = traders_df[["creation_date", "market_creator", column_name]]
fig = px.box(
traders_filtered,
x="creation_date",
y=column_name,
color="market_creator",
color_discrete_sequence=["purple", "goldenrod", "darkgreen"],
category_orders={"market_creator": ["pearl", "quickstart", "all"]},
)
fig.update_traces(boxmean=True)
fig.update_layout(
xaxis_title="Day",
yaxis_title=yaxis_title,
legend=dict(yanchor="top", y=0.5),
)
fig.update_xaxes(tickformat="%b %d\n%Y")
return gr.Plot(
value=fig,
)
def plot_median_roi_by_creation_date(traders_df: pd.DataFrame) -> gr.Plot:
traders_df["creation_date"] = traders_df["creation_timestamp"].dt.date
traders_all = traders_df.copy(deep=True)
traders_all["market_creator"] = "all"
# merging both dataframes
final_traders = pd.concat([traders_all, traders_df], ignore_index=True)
final_traders = final_traders.sort_values(by="creation_date", ascending=True)
roi_daily_metrics = (
final_traders.groupby(
["creation_date", "market_creator", "trader_address"], sort=False
)
.agg(
median_roi=("roi", "median"),
mean_roi=("roi", "mean"),
total_trades=("roi", "count"),
)
.reset_index()
)
# Create the scatter plot with facets for each market_creator
fig = px.scatter(
roi_daily_metrics,
x="creation_date",
y="median_roi",
facet_col="market_creator",
color="market_creator",
color_discrete_map={
"pearl": "purple",
"quickstart": "goldenrod",
"all": "darkgreen",
},
title="Median ROI Over Time by Market Creator",
labels={
"creation_date": "Creation Date",
"median_roi": "Median ROI (%)",
"market_creator": "Market Creator",
},
hover_data={
"creation_date": "|%B %d, %Y", # Custom date format in hover
"median_roi": True,
"mean_roi": True,
"total_trades": True,
},
category_orders={"market_creator": ["pearl", "quickstart", "all"]},
# trendline=None, # Ensure no trendlines are added
)
# Customize the layout for better aesthetics
fig.update_layout(
template="plotly_white",
hovermode="closest",
showlegend=False, # Disable the legend as each facet has its own context
)
# Update each subplot's x-axis to share the same range
fig.update_xaxes(matches="x") # Link x-axes across facets
fig.update_yaxes(matches="y") # Link y-axes across facets
# Add a vertical dashed line in dark red at the specified date
vline_date = "2024-09-29"
vline_datetime = pd.to_datetime(vline_date, format="%Y-%m-%d")
fig.add_vline(
x=vline_datetime,
line_dash="dash",
line_color="darkred",
)
return gr.Plot(
value=fig,
)
import plotly.express as px
def create_median_roi_plot(roi_daily_metrics):
"""
Creates a Plotly scatter plot for median ROI over time, colored by market_creator.
Parameters:
- roi_daily_metrics (pd.DataFrame): Aggregated ROI metrics with columns:
['creation_date', 'market_creator', 'trader_address', 'median_roi', 'mean_roi', 'total_trades']
Returns:
- fig (plotly.graph_objs._figure.Figure): The Plotly figure object.
"""
# Ensure 'creation_date' is in datetime format
roi_daily_metrics["creation_date"] = pd.to_datetime(
roi_daily_metrics["creation_date"]
)
# Create the line plot with scatter markers
fig = px.line(
roi_daily_metrics,
x="creation_date",
y="median_roi",
color="market_creator",
markers=True, # Add markers to lines
title="Median ROI Over Time by Market Creator",
labels={
"creation_date": "Creation Date",
"median_roi": "Median ROI (%)",
"market_creator": "Market Creator",
},
hover_data={
"creation_date": "|%B %d, %Y", # Custom date format in hover
"median_roi": True,
"mean_roi": True,
"total_trades": True,
},
)
# Customize the layout for better aesthetics
fig.update_layout(
xaxis_title="Creation Date",
yaxis_title="Median ROI (%)",
legend_title="Market Creator",
template="plotly_white",
hovermode="x unified",
)
# Optional: Add vertical lines for specific events (e.g., "multibet release")
# Example:
# fig.add_vline(
# x=pd.to_datetime("2023-01-02"),
# line_dash="dash",
# line_color="red",
# annotation_text="Multibet Release",
# annotation_position="top left",
# annotation=dict(
# bgcolor="white",
# font_size=12,
# font_color="red"
# )
# )
return fig
def plot_trader_metrics_by_trader_type(metric_name: str, traders_df: pd.DataFrame):
"""Plots the weekly trader metrics."""
if metric_name == "mech calls":
metric_name = "mech_calls"
column_name = "nr_mech_calls"
yaxis_title = "Total nr of mech calls per trader"
elif metric_name == "ROI":
column_name = "roi"
yaxis_title = "Total ROI (net profit/cost)"
elif metric_name == "bet amount":
metric_name = "bet_amount"
column_name = metric_name
yaxis_title = "Total bet amount per trader (xDAI)"
elif metric_name == "net earnings":
metric_name = "net_earnings"
column_name = metric_name
yaxis_title = "Total net profit per trader (xDAI)"
else: # earnings
column_name = metric_name
yaxis_title = "Total gross profit per trader (xDAI)"
traders_filtered = traders_df[["month_year_week", "trader_type", column_name]]
fig = px.box(
traders_filtered,
x="month_year_week",
y=column_name,
color="trader_type",
color_discrete_sequence=["gray", "orange", "darkblue"],
category_orders={"trader_type": ["singlebet", "multibet", "all"]},
)
fig.update_traces(boxmean=True)
fig.update_layout(
xaxis_title="Week",
yaxis_title=yaxis_title,
legend=dict(yanchor="top", y=0.5),
)
fig.update_xaxes(tickformat="%b %d\n%Y")
return gr.Plot(
value=fig,
)
def plot_winning_metric_per_trader(traders_winning_df: pd.DataFrame) -> gr.Plot:
fig = px.box(
traders_winning_df,
x="month_year_week",
y="winning_perc",
color="market_creator",
color_discrete_sequence=["purple", "goldenrod", "darkgreen"],
category_orders={"market_creator": ["pearl", "quickstart", "all"]},
)
fig.update_traces(boxmean=True)
fig.update_layout(
xaxis_title="Week",
yaxis_title="Weekly winning percentage %",
legend=dict(yanchor="top", y=0.5),
width=1000, # Adjusted for better fit on laptop screens
height=600, # Adjusted for better fit on laptop screens
)
fig.update_xaxes(tickformat="%b %d\n%Y")
return gr.Plot(
value=fig,
)