We find ourselves at the heart of the AI revolution, a transformative era where jobs are increasingly being taken over by AI applications and robotics. The challenge is that AI isn't working for everyday people, but rather for big corporations and wealthy investors who can afford to invest in and create AI systems for their own benefit.
A crucial question emerges: How can everyday people harness the value of the AI revolution to ensure AI works for them, rather than leaving them behind? This challenge is what KiraAI's mission aims to solve.
We need to build a mechanism without barriers that allows everyone to participate in harnessing AI's power, working for their benefit while automatically distributing profits.
Let us introduce Zoe our AI Agent hedge fund manager with a proven. zoe excels at selecting optimal delta-neutral strategies to capture trading opportunities in the crypto market. These opportunities include:
ZoeAI: AI Agent Hedge Fund for All
In the near term, the primary source of income comes from our AI-trained trading agent Zoe, who captures delta-neutral and arbitrage opportunities. Our major strategies currently include Coin-Futures Funding Rate Farming, Spread Arbitrage, and MEV (Miner Extractable Value). In the long term, income will be derived from our community-owned robotic and AI Agent services. These services will extend beyond financial markets (where zoe operates) to include opportunities like autonomous driving taxis and household service robots. Learn more.
How is the income generated by Zoe distributed?
By owning zoe tokens, holders automatically own profits generated by Zoe. As Zoe generates more profits, the value of zoe tokens increases. These profits are used to participate in zoe trading on the secondary market. Holders can buy and sell their zoe tokens on publicly available markets. Through this mechanism, profits are automatically redistributed back to zoe holders. Learn more.
USDi is an interest-bearing, delta-neutral synthetic dollar. It forms the backbone for distributing the wealth created by Zoe. Income generated by the community-owned ZoeAI will be automatically distributed to USDi holders, based on the amount they hold and the length of time they hold it. Learn more.
General individuals or DAOs can obtain USDi through multiple methods:
xxxxxxxxxx- Bank transfer- Cash
Additionally, community members can earn USDi by becoming node operators and committing their time to running a node. Learn more.
Your personal AI hedge fund manager
![[Pasted image 20250320204546.png]]
There are four core functionalities that enable Zoe to perform reliably and generate stable yields: strategy picking, modeling, heuristics and simulation.
Zoe analyses the crypto market to identify optimal delta-neutral trading strategies, prioritizing those with superior Sharpe ratios for maximum risk-adjusted returns.
Zoe leverages historical market trading data to train and optimize our models, fine-tuning parameters for optimal yield capture.
Zoe adopts heuristic techniques to help her funds achieve consistent risk-adjusted returns by removing emotional bias, enabling quick decision-making in fast markets, and providing a systematic framework for portfolio management that can be scaled across multiple delta neutral strategies.
Zoe Implements automated stress-testing protocols and market simulations for comprehensive risk management across diverse market scenarios.
The Zoekuro Token (zoe)
zoe is the meme token for Zoekuro, our first AI Agent Hedge Fund Manager. By owning zoe, holders own a portion of Zoekuro. All future profits, value, and other benefits created by Zoe belong to zoe token holders.
zoe is built by the community and fair-launched exclusively for the community. There are no pre-sales, private sales, or pre-mining events for the zoe token.
zoe holders can vote to decide Zoe's growth path and help make critical decisions about her training and evolution. Additionally, zoe holders have exclusive advantages such as access to special boosting events. Zoekuro needs your help to decide key configurations for her portfolio through zoe holders' voting. Here is a list of key configurations:
| Configurations | Discription | Value |
|---|---|---|
| Reserve % | the percentage that distributed to reserve pool | 100% |
| Risks Tolerance | the risks exposure level | 20% |
| Rewards Frequency | the frequency to distribute profits | Monthly |
| Yield Booster | the booster rewards for zoe token holders | 10% |
| Target APY | A target APY | 20% |
An interest-bearing synthetic dollar
USDi is an interest-bearing synthetic dollar with a stable 1:1 value ratio to USD, featuring automatic interest distribution with no gas fees required for claims. Holders can transfer USDi to anyone at any time without disqualifying their yield gains. An index tracks the amount and holding period of each USDi holder, with longer holding periods and larger amounts earning proportionally higher yields.
USDi is backed by its underlying fully hedged assets, and the intrinsic market cap value of USDi should always equal the total value of these hedged assets. Yield generated from the portfolio steadily increases the total asset value. When it surpasses a certain threshold and the total asset value significantly exceeds USDi in circulation, new USDi is minted and distributed to all USDi holders as profit gains. If the USDi in circulation ever exceeds the total asset value, the difference will be covered by burning USDi from the Zoe's reserve pool by sending it to the locked account, thereby reducing circulation.
We will publish more detailed USDi pegging mechanisms when we are ready to launch the USDi token.
Where to Get USDi Token
After the launch of USDi, users can acquire it through three methods:
The beauty of AI Algorithms
With Zoe's self-evolving decision trees, we no longer rely on human judgment but on trading data and mathematics. This helps eliminate human errors and bias throughout the entire process: optimized strategy selection, simulation and model training, stress testing, and execution. The system is fully autonomous, run entirely by Zoe.
the purpose of the simulator is to give the most optimized configurations for 0max1 monitor. This recommended configurations is based on historic backtest simulation results.
Steps:
xxxxxxxxxx1. Start2. Read DataRaw history funding rates data ('df'): fatched by Monitor.Simulation Configurations Data ('simulations_df'): contains multiple simulations with varying configurations in each simulation.1. Define Functions'token_score_func(symbol, simulations_id, model_num)':It is used to calculate the scores for every token within each simulation.'simulation_apr_func(Tokens_names, simulations_id, model_num)':It is used to calculate the APR for each simulation based on the top tokens that are selected by their scores.1. Model Generation Process- The model initially selects a 'simulations_id' from 'simulations_df'- Generates the simulation 10 times over 30 days, utilizing 90 data points at a frequency of every 3 days (yielding 9 data points each)- Calculates scores for every 40 tokens within each generation by using the function 'token_score_func(symbol, simulations_id, model_num)'- Selectes the top tokens ('Token_names') based on their scores ('top3_score')- Calculates the realized APR of the simulation ('cal_apr') by using the function 'simulation_apr_func(Token_names, simulations_id, model_num)'- Stores all 10 generations realized APRs for this single simulation in 'simulation_total_apr'- Computes the average APR and stores in 'simulation_avg_apr'- Repeat the process for every simulation and the results are stored in 'sorted_simulation_avg_apr'- The whole model generation process will repeat every 30 days (90 data points)2. Collect and Prepare Final DataCompile all processed and optimized realized APR into a final DataFrame 'max_realized_apr'Format and sort each simulation's realized APR score and merge it with Simulation Configurations Data 'simulations_df'1. Output ResultsDisplay the final DataFrame 'final_output'
Historical Funding Rates Data (df): this DataFrame reads the CSV file containing original historical funding rate data collected by Monitor. To verify the simulation, you can use the monitor by restricting the time range and resetting the weight and allocation.
Simulation Configurations Input (simulations_df): this dataframe reads the CSV file containing inputs for different period funding rate weights and allocation weights for each simulation. These are the configurations that will be used to calculate tokens' scores and the simulation's realized APRs. (Simulations_df is created by Weight_Generator)
funding rate weights inputs: are established for a token's average funding rates over different periods—3 days, 7 days, 30 days, previous funding rate, and next funding rate within a simulation. These funding rate weights are defined in the code as
Copy
xxxxxxxxxxWEIGHTS = [W3, W7, W30, W_prev, W_next]
allocation weights inputs: are determined for the top-ranked tokens selected based on their scores within a simulation. These allocation weights are defined in the code as
Copy
xxxxxxxxxxALLOCATIONS = [A1, A2, A3]
symbol: token's name
symbol∈unique(df[′symbol′])symbol∈unique(df[′symbol′])
simulations_id: index id of the specific simulation in 'simulations_df'
simulation_id∈Simulation ID[0,1,2,3,4,5,....,n], where Simulation ID∈simulations_dfsimulation_id∈SimulationID[0,1,2,3,4,5,....,n],whereSimulationID∈simulations_df
model_num: is the number represents the ithith generation for a simulation that generates in the model
model_num∈[1,2,3,4,5,6,7,8,9,10]model_num∈[1,2,3,4,5,6,7,8,9,10]
group: is the subset of 'df' where the token symbol matches symbolsymbol, specifically the funding rate data.
ii: calculates index based on the length of 'group', the model number, and other factors. This will identify the rates that will be collected, beginning with index ii.
i=(len(group) mod 90)+(model_num−1)×9i=(len(group)mod90)+(model_num−1)×9
WW: List of weight arrays, where each weight array corresponds to a particular simulation
weights=[Wj[simulations_id] for Wj in WEIGHTS]weights=[Wj[simulations_id]forWjinWEIGHTS]
AA: List of allocation weight arrays, where each allocation weight array corresponds to a particular rank for a token that selected in a simulation
allocations=[Aj[simulations_id] for Aj in ALLOCATIONS]allocations=[Aj[simulations_id]forAjinALLOCATIONS]
Token Scores Function 'token_score_func(symbol, simulations_id, model_num)': is a function to calculate all tokens' scores of a simulation in a single generation.
Average Periodic APR Calculations: Calculate average funding rates over different periods and scale them to get APRs. For the APR calculations for different periods
APR3=Mean(group[i:i+9])×3×360×100APR7=Mean(group[i:i+21])×3×360×100APR30=Mean(group[i:i+90])×3×360×100APRprev=Mean(group[i+1])×3×360×100APRnext=Mean(group[i])×3×360×100APR3=Mean(group[i:i+9])×3×360×100APR7=Mean(group[i:i+21])×3×360×100APR30=Mean(group[i:i+90])×3×360×100APRprev=Mean(group[i+1])×3×360×100APRnext=Mean(group[i])×3×360×100
token_score_func=∑km(APRk(symbol,i)×Wk[simulation_id]),for k∈m=[3, 7, 30, prev, next]token_score_func=k∑m(APRk(symbol,i)×Wk[simulation_id]),fork∈m=[3,7,30,prev,next]
Simulation Realized APR Function 'simulation_apr_func(Tokens_names, simulations_id, model_num)': is a function to calculate a simulation's APR in a single generation, using the top 3 tokens chosen by Token Scores Function.
Average 3 days funding rate: Calculate average funding rate over 3 days for the token identified by 'symbol' that selected by its score in a simulation.
avg_3Days_rate=Mean(groupsymbol[i−9:i])avg_3Days_rate=Mean(groupsymbol[i−9:i])
simulation_apr_func=∑jr(avg_3Days_rate(symbolj)×Aj[simulation_id]),for j∈r=[1, 2, 3, ...], ′r′ represents top token′s rank in a simulation.simulation_apr_func=j∑r(avg_3Days_rate(symbolj)×Aj[simulation_id]),forj∈r=[1,2,3,...], ′r′representstoptoken′srankinasimulation.
simulation_avg_apr=∑h=1Tsimulation_apr_funch ÷ Tfor h∈model_num,where T=∑model_num,simulation_avg_apr=h=1∑Tsimulation_apr_funch÷Tforh∈model_num,whereT=∑model_num,
Final Output ('final_output'): final output is a merged table that includes 'funding_rate_weight_df' with an additional column called 'Realized APR' and 'Tokens'. 'Realized APR' contains the average APRs from each of the 9 simulations across a total of 10 generations."
The Most Optimized Configurations: is the recommend configuration selected from a simulation with the highest 'Realized APR' in the final output, which will be fed into the monitor.
Weight Generator
xxxxxxxxxx
import pandas as pd
import numpy as np
import itertools
def generate_weights_with_constraints_25(num_weights, num_simulation=70):
possible_values = [0, 0.25, 0.5, 0.75, 1]
simulations = []
# Generate all possible combinations
all_combinations = list(itertools.product(possible_values, repeat=num_weights))
valid_combinations = [combo for combo in all_combinations if np.isclose(sum(combo), 1)]
simulations = np.random.choice(len(valid_combinations), num_simulation, replace=False)
simulations = [valid_combinations[i] for i in simulations]
return simulations
# For 0.25 interval, total number of simulation are 70
num_weights = 5
num_simulation = 70
simulations = generate_weights_with_constraints_25(num_weights, num_simulation)
simulations = pd.DataFrame(simulations
xxxxxxxxxx
def generate_allcations_with_constraints_10(num_allocations, num_simulation=70):
possible_values = [0, 0.1,0.2,0.3,0.4,0.5,0.6,0.7,0.8,0.9,1.0]
simulations = []
# Generate all possible combinations
all_combinations = list(itertools.product(possible_values, repeat=num_allocations))
valid_combinations = [combo for combo in all_combinations if np.isclose(sum(combo), 1)]
simulations = np.random.choice(len(valid_combinations), num_simulation, replace=False)
simulations = [valid_combinations[i] for i in simulations]
return simulations
# For 0.1 interval, total number of allocations are 66
num_allocations = 3
num_simulation = 66
allocations_simulation = generate_allcations_with_constraints_10(num_allocations, num_simulation)
allocations_simulation = pd.DataFrame(allocations_simulation)
xxxxxxxxxx
simulations['Re-Balance Frequence Day'] = 3
allocations_simulation['Re-Balance Frequence Day'] = 3
simulations_df = pd.merge(simulations, allocations_simulation, on='Re-Balance Frequence Day')
simulations_df = simulations_df.reset_index()
simulations_df = simulations_df.rename(columns={'index': 'Simulation ID',
'0_y':'% Allocation for Priority 1',
'1_y':'% Allocation for Priority 2',
'2_y': '% Allocation for Priority 3',
'0_x': 'Previous Funding Rate APR Weight',
'1_x': 'Next Funding Rate APR Weight',
'2_x': '3 Day Cum Funding APR Weight',
3: '7 Day Cum Funding APR Weight',
4: '30 Day Cum Funding APR Weight'
})
simulations_df.to_csv('new_funding_rate_weight_df_2.csv', index=False)
Simulation Configurations Input:
Historical Funding Rates Data:
xxxxxxxxxx
simulations_df = pd.read_csv('/~path/funding_rate_weight_df.csv')
# Define the weights by properly calling tolist() with parentheses
W3 = simulations_df['3 Day Cum Funding APR Weight'].tolist()
W7 = simulations_df['7 Day Cum Funding APR Weight'].tolist()
W30 = simulations_df['30 Day Cum Funding APR Weight'].tolist()
W_next = simulations_df['Next Funding Rate APR Weight'].tolist()
W_prev = simulations_df['Previous Funding Rate APR Weight'].tolist()
A1 = simulations_df['% Allocation for Priority 1'].tolist()
A2 = simulations_df['% Allocation for Priority 2'].tolist()
A3 = simulations_df['% Allocation for Priority 3'].tolist()
F = simulations_df['Re-Balance Frequence Day'].tolist()
# Global weights for APR calculation
WEIGHTS = [W3, W7, W30, W_prev, W_next]
ALLOCATIONS = [A1, A2, A3]
Creating feasible DataFrame
xxxxxxxxxx
# Load the data
with open('historical_funding_rates_0707.json', 'r') as file:
data = json.load(file)
frames = []
for symbol, records in data.items():
df = pd.json_normalize(records)
df['symbol'] = symbol
# Check if 'fundingRate' exists in the dataframe and convert to numeric
if 'fundingRate' in df.columns:
df['fundingRate'] = pd.to_numeric(df['fundingRate'], errors='coerce')
else:
df['fundingRate'] = pd.NA # Assign a missing value indicator if 'fundingRate' is not present
frames.append(df)
# Concatenate all frames into a single DataFrame
df = pd.concat(frames, ignore_index=True)
# Convert 'fundingTime' from milliseconds to a datetime object
df['fundingTime'] = pd.to_datetime(df['fundingTime'], unit='ms')
# Split 'fundingTime' into separate date and time components
df['date'] = df['fundingTime'].dt.date
df['time'] = df['fundingTime'].dt.time
# Drop rows where any column has NaN values
df = df.dropna()
# Sort by 'date' in descending order
df = df.sort_values(by='date', ascending=False)
# Display the first few rows to verify
df = df[['symbol', 'date', 'time', 'fundingRate', 'markPrice']]
xxxxxxxxxx
def token_score_func(symbol, simulations_id, model_num):
group = df.loc[df['symbol'] == symbol, 'fundingRate']
i = len(group) % 90 + (model_num - 1) * 9
aprs = [
group.iloc[i : i + 9].mean() * 3 * 360 * 100,
group.iloc[i : 21 + i].mean() * 3 * 360 * 100,
group.iloc[i : 90 + i].mean() * 3 * 360 * 100,
group.iloc[1 + i] * 3 * 360 * 100,
group.iloc[i] * 3 * 360 * 100
]
#simulations_id = simulations_id - 1
weights = [W[simulations_id] for W in WEIGHTS] # Gather weights for each APR based on simulation ID
# Calculate the weighted APR score
apr_score = sum(apr * weight for apr, weight in zip(aprs, weights))
return apr_score
xxxxxxxxxx
def simulation_apr_func(Tokens_names, simulations_id, model_num):
top3_rates = []
for symbol in Tokens_names:
group = df.loc[df['symbol'] == symbol, 'fundingRate']
i = len(group) % 90 + (model_num - 1) * 9
rates = group.iloc[i - 9 : i ].mean()
top3_rates.append(rates)
allocations = [A[simulations_id] for A in ALLOCATIONS]
sim_apr = sum(rate * allocation for rate, allocation in zip(top3_rates, allocations)) * 360 * 3
return sim_apr
xxxxxxxxxx
token_score = {}
simulaiton_id = simulations_df.index.tolist()
model_nums = range(1,11)
token_score_rank = []
simulation_avg_apr = {}
for id in simulaiton_id:
simulation_total_apr = 0
for i in model_nums:
token_score = {}
simulation_apr = {}
for symbol in symbols:
score = token_score_func(symbol, id, i)
token_score[(symbol, id, i)] = score
top3_score = dict(sorted(token_score.items(), key=lambda item: item[1],reverse=True)[:3])
Token_names = [key[0] for key in top3_score.keys()]
cal_apr = simulation_apr_func(Token_names, id, i)
simulation_apr[(f'Model Num {i}', f'Simulation {id}')] = cal_apr
simulation_total_apr += cal_apr
simulation_avg_apr[id] = simulation_total_apr / len(model_nums)
sorted_simulation_avg_apr = dict(sorted(simulation_avg_apr.items(), key=lambda item: item[1], reverse=True))
sorted_simulation_avg_apr
xxxxxxxxxx
max_realized_apr = [
{'Simulation ID': key, 'Realized APR': value}
for key, value in sorted_simulation_avg_apr.items()
]
max_realized_apr_token = [
{'Simulation ID': key, 'Tokens': value}
for key, value in simulation_top3_token.items()
]
max_realized_apr = pd.DataFrame(max_realized_apr)
max_realized_apr.reset_index(drop=True, inplace=True)
max_realized_apr_token = pd.DataFrame(max_realized_apr_token)
max_realized_apr = pd.merge(max_realized_apr, max_realized_apr_token, on='Simulation ID')
max_realized_apr.to_csv('max_realized_apr_may.csv', index=False)
max_realized_apr
The goal of the monitor is to give live suggestions of portfolio target allocation %, based on pre-decided configurations from 0max1 simulator. It takes input from the exchange public API and calculate Apr score for each asset then give suggestions.
Process:
xxxxxxxxxx1. Start•2. Set API KeyRetrieve the Binance API key from environment variables.•1. Fetch All Futures SymbolsUse get_futures_symbols() to get a list of all futures symbols available on Binance.•1. For Each Symbol, Fetch Funding Rate HistoryLoop through each symbol.Use get_funding_rate_history(symbol, 60) to fetch the last 60 days' worth of funding rate data for each symbol.•1. Data Processing and APR CalculationFor each dataset fetched:Calculate 3-day, 7-day, and 30-day average funding rates.Annualize these averages to get APRs by multiplying the average rates by 365 and converting to percentage.Store these calculations in the DataFrame.•1. Optimize APR ScoreFor the funding rate data of each symbol, use optimize_apr_score(group) to compute the optimized APR score based on weighted averages of the 3-day, 7-day, 30-day, and the most recent funding rates.•1. Collect and Prepare Final DataCompile all processed and optimized data into a final DataFrame.Format and sort data based on optimized APR scores.•1. Output ResultsDisplay the final DataFrame.
xxxxxxxxxx1. Environment Setup:api_key: This variable retrieves the API key from the environment variables to securely access the Binance API without hardcoding sensitive information.1. Global Constants:Weights (WEIGHTS): These are coefficients used to calculate the Annual Percentage Rate (APR) score based on the funding rates over various periods. They reflect the importance of each period's funding rate in determining the overall APR score. The weights are defined as follows:W3: Weight for the 3-day funding rate.W7: Weight for the 7-day funding rate.W30: Weight for the 30-day funding rate.W_next: Weight for the next funding rate.W_prev: Weight for the previous funding rate.1. Function Definitions:get_futures_symbols(): Calls the Binance API to retrieve a list of all available futures symbols.get_funding_rate_history(symbol, display_days=30): Fetches the funding rate history for a specified futures symbol over a set number of days from the Binance API.calculate_apr_score(group): Computes the APR score for a given dataset of funding rates using predefined weights. This score helps in assessing the profitability of each contract.1. Data Retrieval and Processing:Initially, all futures symbols are fetched and stored.For each symbol, its funding rate history is retrieved for the last 60 days.This data is then processed to compute the APR score using the function calculate_apr_score.1. Data Aggregation and Output:All the processed data is aggregated into a DataFrame.The DataFrame is sorted by APR score, and the top 5 entries are assigned allocation percentages based on their rankings.The final DataFrame is formatted for readability and saved as a CSV file named APR.csv.1. Post-Processing:Certain columns in the DataFrame are formatted as percentages for clarity.The DataFrame includes columns like symbol, time, funding rates, APR score, and allocation percentage, making it informative and easy to understand.
xxxxxxxxxx
import requests
import pandas as pd
import os
import websocket
import json
import ssl
import threading
import datetime
# Set Binance API Key as an environment variable
api_key = os.getenv('BINANCE_API_KEY')
latest_funding_rates = {}
def on_message(ws, message):
global latest_funding_rates
data = json.loads(message)
if 'stream' in data:
symbol = data['stream'].split('@')[0].upper() # Extract symbol from stream name in uppercase
latest_funding_rates[symbol] = float(data['data']['r']) # Store the rate
def on_error(ws, error):
print("Error:", error)
def on_close(ws, code, reason):
print(f"WebSocket closed with code {code}, reason {reason}")
def on_open(ws):
global streams
symbols = get_futures_symbols()
streams = [f"{symbol.lower()}@markPrice" for symbol in symbols]
subscribe_message = json.dumps({
"method": "SUBSCRIBE",
"params": streams,
"id": 1
})
ws.send(subscribe_message)
def connect_websocket():
websocket.enableTrace(False)
ws = websocket.WebSocketApp("wss://dstream.binance.com/stream",
on_open=on_open,
on_message=on_message,
on_error=on_error,
on_close=on_close)
def run_ws():
ws.run_forever(sslopt={"cert_reqs": ssl.CERT_NONE})
thread = threading.Thread(target=run_ws)
thread.start()
return ws, thread
def get_futures_symbols():
url = 'https://dapi.binance.com/dapi/v1/exchangeInfo'
headers = {'X-MBX-APIKEY': api_key}
response = requests.get(url, headers=headers)
if response.status_code == 200:
data = response.json()
symbols = [item['symbol'] for item in data['symbols'] if item['contractType'] == 'PERPETUAL']
return symbols
return []
# Global weights for APR calculation
WEIGHTS = [W3, W7, W30, W_prev, W_next]
def calculate_apr_score(group, symbol):
symbol = symbol.upper() # Ensure the symbol is in uppercase
aprs = [
group.head(9)['fundingRate'].mean() * 3 * 360 * 100,
group.head(21)['fundingRate'].mean() * 3 * 360 * 100,
group.head(90)['fundingRate'].mean() * 3 * 360 * 100,
group.iloc[1]['fundingRate'] * 3 * 360 * 100,
latest_funding_rates.get(symbol, group.iloc[0]['fundingRate']) * 3 * 360 * 100 # Use real-time rate if available
]
apr_score = sum(apr * weight for apr, weight in zip(aprs, WEIGHTS))
return apr_score
def get_funding_rate_history(symbol, display_days=30):
url = 'https://dapi.binance.com/dapi/v1/fundingRate'
params = {'symbol': symbol, 'limit': display_days * 3}
headers = {'X-MBX-APIKEY': api_key}
response = requests.get(url, params=params, headers=headers)
if response.status_code == 200:
data = response.json()
df = pd.DataFrame(data)
df['fundingRate'] = pd.to_numeric(df['fundingRate'], errors='coerce')
df['Time'] = pd.to_datetime(df['fundingTime'], unit='ms', utc=True).dt.tz_convert(None)
return df.sort_values('Time', ascending=False).head(display_days)
return pd.DataFrame()
def process_data():
ws, thread = connect_websocket()
thread.join(timeout=30) # Wait for the WebSocket to collect data
symbols = get_futures_symbols()
all_data_frames = []
for symbol in symbols:
df = get_funding_rate_history(symbol, 60)
if not df.empty:
df['symbol'] = symbol
all_data_frames.append(df)
final_data_list = []
for data in all_data_frames:
symbol = data['symbol'].iloc[0]
apr_score = calculate_apr_score(data, symbol)
latest_data = data.sort_values('Time', ascending=False).iloc[0].to_dict()
latest_data['Previous Funding Rate'] = data.iloc[1]['fundingRate'] * 360 * 3 * 100
latest_data['Next Funding Rate'] = latest_funding_rates.get(symbol, data.iloc[0]['fundingRate']) * 360 * 3 * 100
latest_data['3 Day Cum Funding APR'] = data.head(9)['fundingRate'].mean() * 360 * 3 * 100
latest_data['7 Day Cum Funding APR'] = data.head(21)['fundingRate'].mean() * 360 * 3 * 100
latest_data['30 Day Cum Funding APR'] = data.head(90)['fundingRate'].mean() * 360 * 3 * 100
latest_data['APR Score'] = f"{apr_score:.3f}%"
# Select only the desired columns
final_data_list.append({
'symbol': latest_data['symbol'],
'Time': latest_data['Time'],
'Previous Funding Rate': f"{latest_data['Previous Funding Rate']:.3f}%",
'Next Funding Rate': f"{latest_data['Next Funding Rate']:.3f}%",
'3 Day Cum Funding APR': f"{latest_data['3 Day Cum Funding APR']:.3f}%",
'7 Day Cum Funding APR': f"{latest_data['7 Day Cum Funding APR']:.3f}%",
'30 Day Cum Funding APR': f"{latest_data['30 Day Cum Funding APR']:.3f}%",
'APR Score': latest_data['APR Score']
})
final_data = pd.DataFrame(final_data_list)
final_data.sort_values('APR Score', ascending=False, inplace=True)
# Add timestamp to file name
timestamp = datetime.datetime.utcnow().strftime('%Y-%m-%d_%H-%M-%S_UTC')
file_name = f'APR_results_{timestamp}.csv'
final_data.to_csv(file_name, index=False)
print(f"Data saved to '{file_name}'")
if ws.sock and ws.sock.connected:
ws.close()
if __name__ == "__main__":
process_data()
xxxxxxxxxx1. Average Funding Rate Calculation:Average Funding Rate_n = (Sum of Funding Rates over the last n periods) / nHere, n represents the number of periods, such as 3, 7, or 30 days.1. Annualization of the Funding Rate:Annualized Funding APR_n = Average Funding Rate_n x 360 x 3 x 100This converts the average funding rate for n days into an annual percentage rate by multiplying by the number of days in a year (365) and then converting it to a percentage by multiplying by 100.1. APR Score Calculation with Weights:APR Score = (Annualized Funding APR_3 x W_3) + (Annualized Funding APR_7 x W_7) + (Annualized Funding APR_30 x W_30) + (Annualized Funding APR_next x W_next) + (Annualized Funding APR_prev x W_prev)The APR Score is calculated by taking the weighted average of several Annualized Funding APRs for different periods. This is done by multiplying each Annualized Funding APR by its respective weight and then summing up these products.
xxxxxxxxxx
import requests
import pandas as pd
import os
import websocket
import json
import ssl
import threading
import datetime
# Set Binance API Key as an environment variable
api_key = os.getenv('BINANCE_API_KEY')
latest_funding_rates = {}
def on_message(ws, message):
global latest_funding_rates
data = json.loads(message)
if 'stream' in data:
symbol = data['stream'].split('@')[0].upper() # Extract symbol from stream name in uppercase
latest_funding_rates[symbol] = float(data['data']['r']) # Store the rate
def on_error(ws, error):
print("Error:", error)
def on_close(ws, code, reason):
print(f"WebSocket closed with code {code}, reason {reason}")
def on_open(ws):
global streams
symbols = get_futures_symbols()
streams = [f"{symbol.lower()}@markPrice" for symbol in symbols]
subscribe_message = json.dumps({
"method": "SUBSCRIBE",
"params": streams,
"id": 1
})
ws.send(subscribe_message)
def connect_websocket():
websocket.enableTrace(False)
ws = websocket.WebSocketApp("wss://dstream.binance.com/stream",
on_open=on_open,
on_message=on_message,
on_error=on_error,
on_close=on_close)
def run_ws():
ws.run_forever(sslopt={"cert_reqs": ssl.CERT_NONE})
thread = threading.Thread(target=run_ws)
thread.start()
return ws, thread
def get_futures_symbols():
url = 'https://dapi.binance.com/dapi/v1/exchangeInfo'
headers = {'X-MBX-APIKEY': api_key}
response = requests.get(url, headers=headers)
if response.status_code == 200:
data = response.json()
symbols = [item['symbol'] for item in data['symbols'] if item['contractType'] == 'PERPETUAL']
return symbols
return []
# Global weights for APR calculation
WEIGHTS = [W3, W7, W30, W_prev, W_next]
def calculate_apr_score(group, symbol):
symbol = symbol.upper() # Ensure the symbol is in uppercase
aprs = [
group.head(9)['fundingRate'].mean() * 3 * 360 * 100,
group.head(21)['fundingRate'].mean() * 3 * 360 * 100,
group.head(90)['fundingRate'].mean() * 3 * 360 * 100,
group.iloc[1]['fundingRate'] * 3 * 360 * 100,
latest_funding_rates.get(symbol, group.iloc[0]['fundingRate']) * 3 * 360 * 100 # Use real-time rate if available
]
apr_score = sum(apr * weight for apr, weight in zip(aprs, WEIGHTS))
return apr_score
def get_funding_rate_history(symbol, display_days=30):
url = 'https://dapi.binance.com/dapi/v1/fundingRate'
params = {'symbol': symbol, 'limit': display_days * 3}
headers = {'X-MBX-APIKEY': api_key}
response = requests.get(url, params=params, headers=headers)
if response.status_code == 200:
data = response.json()
df = pd.DataFrame(data)
df['fundingRate'] = pd.to_numeric(df['fundingRate'], errors='coerce')
df['Time'] = pd.to_datetime(df['fundingTime'], unit='ms', utc=True).dt.tz_convert(None)
return df.sort_values('Time', ascending=False).head(display_days)
return pd.DataFrame()
def process_data():
ws, thread = connect_websocket()
thread.join(timeout=30) # Wait for the WebSocket to collect data
symbols = get_futures_symbols()
all_data_frames = []
for symbol in symbols:
df = get_funding_rate_history(symbol, 60)
if not df.empty:
df['symbol'] = symbol
all_data_frames.append(df)
final_data_list = []
for data in all_data_frames:
symbol = data['symbol'].iloc[0]
apr_score = calculate_apr_score(data, symbol)
latest_data = data.sort_values('Time', ascending=False).iloc[0].to_dict()
latest_data['Previous Funding Rate'] = data.iloc[1]['fundingRate'] * 360 * 3 * 100
latest_data['Next Funding Rate'] = latest_funding_rates.get(symbol, data.iloc[0]['fundingRate']) * 360 * 3 * 100
latest_data['3 Day Cum Funding APR'] = data.head(9)['fundingRate'].mean() * 360 * 3 * 100
latest_data['7 Day Cum Funding APR'] = data.head(21)['fundingRate'].mean() * 360 * 3 * 100
latest_data['30 Day Cum Funding APR'] = data.head(90)['fundingRate'].mean() * 360 * 3 * 100
latest_data['APR Score'] = f"{apr_score:.3f}%"
# Select only the desired columns
final_data_list.append({
'symbol': latest_data['symbol'],
'Time': latest_data['Time'],
'Previous Funding Rate': f"{latest_data['Previous Funding Rate']:.3f}%",
'Next Funding Rate': f"{latest_data['Next Funding Rate']:.3f}%",
'3 Day Cum Funding APR': f"{latest_data['3 Day Cum Funding APR']:.3f}%",
'7 Day Cum Funding APR': f"{latest_data['7 Day Cum Funding APR']:.3f}%",
'30 Day Cum Funding APR': f"{latest_data['30 Day Cum Funding APR']:.3f}%",
'APR Score': latest_data['APR Score']
})
final_data = pd.DataFrame(final_data_list)
final_data.sort_values('APR Score', ascending=False, inplace=True)
# Add timestamp to file name
timestamp = datetime.datetime.utcnow().strftime('%Y-%m-%d_%H-%M-%S_UTC')
file_name = f'APR_results_{timestamp}.csv'
final_data.to_csv(file_name, index=False)
print(f"Data saved to '{file_name}'")
if ws.sock and ws.sock.connected:
ws.close()
if __name__ == "__main__":
process_data()
xxxxxxxxxx1. Average Funding Rate Calculation:Average Funding Rate_n = (Sum of Funding Rates over the last n periods) / nHere, n represents the number of periods, such as 3, 7, or 30 days.2. Annualization of the Funding Rate:Annualized Funding APR_n = Average Funding Rate_n x 360 x 3 x 100This converts the average funding rate for n days into an annual percentage rate by multiplying by the number of days in a year (365) and then converting it to a percentage by multiplying by 100.3. APR Score Calculation with Weights:APR Score = (Annualized Funding APR_3 x W_3) + (Annualized Funding APR_7 x W_7) + (Annualized Funding APR_30 x W_30) + (Annualized Funding APR_next x W_next) + (Annualized Funding APR_prev x W_prev)The APR Score is calculated by taking the weighted average of several Annualized Funding APRs for different periods. This is done by multiplying each Annualized Funding APR by its respective weight and then summing up these products.
Zoe only picks delta-neutral and arbitrage trading opportunities. This approach avoids underlying asset price fluctuation risks and can generate predictable future cash flows. Since this is the very beginning of our fully Autonomous AI Agent hedge fund, building a successful track record is key to gaining everyone's trust.
Delta-Neutral - Price fluctuation is completely excluded
Arbitrage - Risk-free execution, especially when automated by AI
Farming the coin future market funding fees
All arbitrage trades by 0max1 are risk-free, offering stable and secure returns.
Stable yield ranged between 8% ~ 25% APY passive income.
Delivery Futures contracts always converge with Spot prices at expiration dates.
Onchain arbitrage bundles, completed within the same block to generate passive income.
The revenue is the price spread between different swap pools and the cost is on chain gas fees.
| Terminology | Definition |
|---|---|
| total return | The net realized absolute return for the period of time selected |
| NAV per USDi | The current value of one USDi unit based on total assets |
| Cumulative Interest | The total interest earned and paid out to date |
| 30-Day Interest | The estimated interest you will earn over the next 30 days |
| 30 Day APY | The annual percentage yield calculated based on the past 30 days' performance |
| 90 Day APY | The annual percentage yield calculated based on the past 90 days' performance |
| Implied APY | The estimated annual percentage yield based on current rates |
| Implied 30 Days Earnings | The estimated total earnings for the protocol over the next 30 days |
| Net Exposure Value | The total value of unhedged assets |
| TVL | Current total value of all assets under management. |
| 30 Day Net Earnings | The total actual earnings achieved over the past 30 days |
| Portfolio | Buy and Sell trading pair for funding rate arbitrage |
| Latest funding rate | The annual percentage yield calculated based on the next funding fees |
| previous funding APY | The annual percentage yield calculated based on the latest funding fees |
| 3 Day Cum Funding APY | The annual percentage yield calculated based on the past 3 days funding fees |
| 7 Day Cum Fudding APY | The annual percentage yield calculated based on the past 7 days funding fees |
| 30 Day Cum Funding APY | The annual percentage yield calculated based on the past 30 days funding fees |
| Total Assets Value | Current total value of all managed assets |
a. Request
Headers: Content-Type: application/json
Query Parameters: None
Body:
b. Responce
xxxxxxxxxx
{ "access_token": "<access_token>", "refresh_token": "<refresh_token>" }
c. Example
xxxxxxxxxx
fetch('https://max1-funding-arb.uc.r.appspot.com/login', {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
username: 'admin',
password: 'admin'
})
})
.then(response => response.json())
.then(data => console.log(data))
.catch(error => console.error('Error:', error));
a. Request
b. Response
c. Example
xxxxxxxxxx
fetch('https://max1-funding-arb.uc.r.appspot.com/raw_data_table', {
method: 'GET',
headers: {
'Authorization': 'Bearer YOUR_JWT_TOKEN_HERE'
}
})
.then(response => {
if (!response.ok) {
throw new Error('Network response was not ok');
}
return response.json();
})
.then(data => console.log(data))
.catch(error => console.error('Error:', error));
d. Response Example
xxxxxxxxxx
[
{"funding_id":1,"fundingrate":"-0.00021167","fundingtime":1713456000000,"markprice":"63515.40000000","symbol":"BTCUSD_PERP","time":"Thu, 27 Jun 2024 08:03:24 GMT"},
{"funding_id":2,"fundingrate":"-0.00029339","fundingtime":1713484800000,"markprice":"63477.88531564","symbol":"BTCUSD_PERP","time":"Thu, 27 Jun 2024 08:03:24 GMT"},
…
]
a. Request
Headers: None
Query Parameters:
Body: None
b. Response
c. Example
xxxxxxxxxx
fetch('https://max1-funding-arb.uc.r.appspot.com/portfolio_track_records?page=1&limit=60, {
method: 'GET',
headers: {
'Authorization': 'Bearer YOUR_JWT_TOKEN_HERE'
}
})
.then(response => {
if (!response.ok) {
throw new Error('Network response was not ok');
}
return response.json();
})
.then(data => console.log(data))
.catch(error => console.error('Error:', error));
d. Response Example
xxxxxxxxxx
{[
{"id":1,"money_at_risk_percent":"-0.7635539234855009","net_exposure_value":"-0.7577440087800085","portfolio_implied_30days_earnings":"0.8605773848134116","portfolio_implied_apr":"0.10406109150689863","timestamp":"Fri, 28 Jun 2024 04:20:33 GMT","total_assets_value":"99.23909569098001"},
{"id":2,"money_at_risk_percent":"-0.7301864268488106","net_exposure_value":"-0.7248933446900026","portfolio_implied_30days_earnings":"0.8606027411036695","portfolio_implied_apr":"0.10402641079258573","timestamp":"Fri, 28 Jun 2024 07:05:01 GMT","total_assets_value":"99.27510537526001"},
…..
],
"total_records": 120,
"page": 1,
"limit": 60
}
a. Request
Headers: None
Query Parameters:
Body: None
b. Response
c. Example
xxxxxxxxxx
fetch('https://max1-funding-arb.uc.r.appspot.com/track_records_daily_latest?start_date=2024-08-03&end_date=2024-09-02', {
method: 'GET',
headers: {
'Authorization': 'Bearer YOUR_JWT_TOKEN_HERE'
}
})
.then(response => {
if (!response.ok) {
throw new Error('Network response was not ok');
}
return response.json();
})
.then(data => console.log(data))
.catch(error => console.error('Error:', error));
// Some code
a. Request
b. Response
c. Example
xxxxxxxxxx
fetch('https://max1-funding-arb.uc.r.appspot.com/portfolio_latest', {
method: 'GET',
headers: {
'Authorization': 'Bearer YOUR_JWT_TOKEN_HERE'
}
})
.then(response => {
if (!response.ok) {
throw new Error('Network response was not ok');
}
return response.json();
})
.then(data => console.log(data))
.catch(error => console.error('Error:', error));
d. Response Example
xxxxxxxxxx
[
{"amount":"6.8792","assets_types":"Crypto","assets_value":"62.2633","implied_apr":"0.0","mark_price":"9.051","order_value_required":"0.0","portfolio_allocation":"0.6271","product_category":"Coin-M Futures","symbol":"UNI","target_allocation_percent":"0.0","utc_timestamp":"Tue, 02 Jul 2024 08:20:19 GMT"},
{"amount":"0.2512","assets_types":"Crypto","assets_value":"37.0242","implied_apr":"0.0","mark_price":"147.389","order_value_required":"0.0","portfolio_allocation":"0.3729","product_category":"Coin-M Futures","symbol":"SOL","target_allocation_percent":"0.0","utc_timestamp":"Tue, 02 Jul 2024 08:20:19 GMT"},
…
]
a. Request
b. Response
c. Example
xxxxxxxxxx
fetch('https://max1-funding-arb.uc.r.appspot.com/monitor_apr_attribute', {
method: 'GET',
headers: {
'Authorization': 'Bearer YOUR_JWT_TOKEN_HERE'
}
})
.then(response => {
if (!response.ok) {
throw new Error('Network response was not ok');
}
return response.json();
})
.then(data => console.log(data))
.catch(error => console.error('Error:', error));
d. Response Example
xxxxxxxxxx
[
{"30_day_cum_funding":"0.09370907999999999","3_day_cum_funding":"0.1376676","7_day_cum_funding":"0.07607777142857143","allocation_percentage":"0.4","apr_id":1,"apr_score":"0.1449632622857143","next_funding_rate":"0.2306664","previous_funding_rate":"0.14273280000000002","simulator_id":null,"symbol":"BNBUSD_PERP","time":"Thu, 27 Jun 2024 08:00:00 GMT"},
{"30_day_cum_funding":"0.12468504000000001","3_day_cum_funding":"0.13084440000000003","7_day_cum_funding":"0.09699222857142857","allocation_percentage":"0.35","apr_id":2,"apr_score":"0.11432026971428573","next_funding_rate":"0.10800000000000001","previous_funding_rate":"0.10800000000000001","simulator_id":null,"symbol":"RUNEUSD_PERP","time":"Thu, 27 Jun 2024 08:00:00 GMT"},
…..
]
a. Request
Headers
Body: None
b. Response
a. Request
b. Response
a. Request
b. Response
a. Request
b. Response
The Crypto to Cash (C2C) Network is a global protocol that connects cryptocurrency holders with cash holders. The protocol facilitates seamless exchanges between crypto and traditional cash, providing users with a secure and efficient way to conduct transactions worldwide.
Members can mint or redeem their USDi through the C2C Network option. Our globally available node operators will fulfill requests within 2 days. Learn more about the detailed process.
Node operators are verified individuals who have staked a specific amount of zoe tokens. If any service issues occur, their tokens will be slashed by the network. Individual transactions cannot exceed 60% of their staked zoe value. Learn more about the detailed process.
Zoe, our AI Agent, facilitates transactions and communications between network participants. This ensures smooth, secure, and efficient coordination of exchanges across the network.
As a C2C Node Operator, you'll enjoy:
Becoming a node operator is straightforward:
Here's a step-by-step guide to redeeming USDi through the C2C network.
To initiate a redemption:
Your USDi will be held in the collateral account until you confirm receipt of funds.
Once your request is submitted:
After confirming cash receipt:
Our backend system submits the redemption request to the provided wallet address
Transaction status changes to Redeem Requested
The operator must verify:
Here are the available payment methods for the C2C network with corresponding fees and amount limits.
| Payment methods | Processing time | Amount limit | Fees |
|---|---|---|---|
| Bank Wire | 2 days | larger than $10,000 | 1 % |
| Zelle | 24 hrs | $100 ~ $10,000 | 0.5 % |
| Venmo | 24 hrs | $100 ~$3,000 | 0.5 % |
| Alipay | 24 hrs | $5,000 ~ $50,000 | 1 % |
| Cash - Paper | 2 days | larger than $10,000 | 1 % |
Cash (Paper Delivery) Available in select cities:
Exchange Rate: The best market rate on the delivery date applies for non-USD transactions.