Skip to content
Snippets Groups Projects
Commit 20fb1fb1 authored by David Hintermann's avatar David Hintermann
Browse files

wip: tested reablance reserves

parent 1025d528
No related branches found
No related tags found
1 merge request!10feat(rebalancer): rebalance automatically
...@@ -15,28 +15,14 @@ public class PotatoStorage(DbContextOptions<PotatoStorage> options) : DbContext( ...@@ -15,28 +15,14 @@ public class PotatoStorage(DbContextOptions<PotatoStorage> options) : DbContext(
public async Task<PotatoTransaction> RemovePotatoes(double weight) public async Task<PotatoTransaction> RemovePotatoes(double weight)
{ {
var transactions = Transactions var maxRemovableWeight = SupplyWeight();
.OrderBy(p => p.Id)
.AsQueryable(); var removingWeight = Math.Min(maxRemovableWeight, weight);
var newTransaction = new PotatoTransaction
var newTransaction = new PotatoTransaction();
foreach (var transaction in transactions)
{ {
var newTransactionWeight = newTransaction.Weight + transaction.Weight; Weight = -removingWeight,
if (newTransactionWeight <= weight) };
{ await Transactions.AddAsync(newTransaction);
newTransaction.Weight += transaction.Weight;
Transactions.Remove(transaction);
}
else
{
var overshoot = newTransactionWeight - weight;
transaction.Weight -= overshoot;
newTransaction.Weight += transaction.Weight;
Transactions.Update(transaction);
}
}
await SaveChangesAsync(); await SaveChangesAsync();
return newTransaction; return newTransaction;
} }
......
using System.Diagnostics.Metrics;
using Frontend.Configuration;
using Frontend.Metrics;
using Nethereum.Web3;
using Nethereum.Web3.Accounts;
namespace Frontend.BackgroundServices;
public class RebalanceService : BackgroundService
{
private readonly ILogger<RebalanceService> _logger;
private readonly TimeSpan _interval = TimeSpan.FromSeconds(10);
private int startUpDelayCycles = 6;
private readonly Rebalancer _rebalancer;
public RebalanceService(
Rebalancer rebalancer,
Logger<RebalanceService> logger
)
{
_logger = logger;
_rebalancer = rebalancer;
}
protected async override Task ExecuteAsync(CancellationToken stoppingToken)
{
while (!stoppingToken.IsCancellationRequested)
{
if (startUpDelayCycles > 0)
{
_logger.LogInformation("RebalanceService is waiting to start. remaining cycles: {startUpDelayCycles}", startUpDelayCycles);
startUpDelayCycles--;
}
else
{
_logger.LogInformation("Rebalancer: EnsureCoinSupplyMatchesRwaSupplyAsync is running at {time}", DateTime.Now);
await _rebalancer.EnsureCoinSupplyMatchesRwaSupplyAsync();
_logger.LogInformation("Rebalancer: MaintainLiquidReservesAsync is running at {time}", DateTime.Now);
await _rebalancer.MaintainLiquidReservesAsync();
_logger.LogInformation("Rebalancer: MaintainPoolAsync is running at {time}", DateTime.Now);
await _rebalancer.MaintainPoolAsync();
}
await Task.Delay(_interval, stoppingToken);
}
}
}
\ No newline at end of file
...@@ -14,7 +14,7 @@ public class PotatoMarketplaceMock( ...@@ -14,7 +14,7 @@ public class PotatoMarketplaceMock(
string wethAddress string wethAddress
) : IPotatoMarketPlace ) : IPotatoMarketPlace
{ {
private const double potatoKgChfPrice = 2.02; // source: https://www.blw.admin.ch/blw/de/home/markt/marktbeobachtung/kartoffeln.html private const double potatoKgChfPrice = 0.8; //2.02; // source: https://www.blw.admin.ch/blw/de/home/markt/marktbeobachtung/kartoffeln.html
private readonly Account account = marketplaceAccount; private readonly Account account = marketplaceAccount;
private readonly Web3 web3 = marketplaceWeb3Client; private readonly Web3 web3 = marketplaceWeb3Client;
...@@ -60,7 +60,7 @@ public class PotatoMarketplaceMock( ...@@ -60,7 +60,7 @@ public class PotatoMarketplaceMock(
public async Task<bool> Sell(PotatoTransaction transaction, string receiverAddress) public async Task<bool> Sell(PotatoTransaction transaction, string receiverAddress)
{ {
var amount = (double)await PotatoKgWeiPrice() * transaction.Weight; var amount = (double)await PotatoKgWeiPrice() * Math.Abs(transaction.Weight); // negative weight means selling
var transferHandler = web3.Eth.GetContractTransactionHandler<TransferFunction>(); var transferHandler = web3.Eth.GetContractTransactionHandler<TransferFunction>();
var transferFunction = new TransferFunction var transferFunction = new TransferFunction
......
using Frontend.Assets;
using Frontend.AssetStores;
using Frontend.Configuration; using Frontend.Configuration;
using Microsoft.AspNetCore.Mvc.RazorPages; using Microsoft.AspNetCore.Mvc.RazorPages;
using Nethereum.Web3; using Nethereum.Web3;
...@@ -12,14 +14,16 @@ public class IndexModel : PageModel ...@@ -12,14 +14,16 @@ public class IndexModel : PageModel
private readonly ChainSettings _chainSettings; private readonly ChainSettings _chainSettings;
private readonly Account _account; private readonly Account _account;
private readonly Rebalancer _rebalancer; private readonly Rebalancer _rebalancer;
private readonly PotatoStorage _potatoStorage;
public IndexModel(ILogger<IndexModel> logger, Web3 web3, ChainSettings chainSettings, Account account, Rebalancer rebalancer) public IndexModel(ILogger<IndexModel> logger, Web3 web3, ChainSettings chainSettings, Account account, Rebalancer rebalancer, PotatoStorage potatoStorage)
{ {
_logger = logger; _logger = logger;
_poolV3Client = new PoolV3Client(web3, chainSettings, account); _poolV3Client = new PoolV3Client(web3, chainSettings, account);
_chainSettings = chainSettings; _chainSettings = chainSettings;
_account = account; _account = account;
_rebalancer = rebalancer; _rebalancer = rebalancer;
_potatoStorage = potatoStorage;
} }
public void OnGet() public void OnGet()
...@@ -57,5 +61,14 @@ public class IndexModel : PageModel ...@@ -57,5 +61,14 @@ public class IndexModel : PageModel
if(Request.Query.ContainsKey("ensureRWA")){ if(Request.Query.ContainsKey("ensureRWA")){
_rebalancer.EnsureCoinSupplyMatchesRwaSupplyAsync().Wait(); _rebalancer.EnsureCoinSupplyMatchesRwaSupplyAsync().Wait();
} }
if(Request.Query.ContainsKey("buyRwa")){
amount = decimal.Parse(Request.Query["buyRwa"]);
if(amount>0){
_potatoStorage.AddPotatoes(new PotatoTransaction{Weight=(double)amount}).Wait();
}else if(amount<0){
_potatoStorage.RemovePotatoes((double)Math.Abs(amount)).Wait();
}
}
} }
} }
...@@ -232,7 +232,7 @@ public class PoolV3Client ...@@ -232,7 +232,7 @@ public class PoolV3Client
amount = (double)(liquidity * BigInteger.Pow(2, 96) * (sqrtPriceX96 - desiredSqrtPriceX96)) / (double)(desiredSqrtPriceX96 * sqrtPriceX96); amount = (double)(liquidity * BigInteger.Pow(2, 96) * (sqrtPriceX96 - desiredSqrtPriceX96)) / (double)(desiredSqrtPriceX96 * sqrtPriceX96);
balance = await Token0Client.BalanceOf(_account.Address); balance = await Token0Client.BalanceOf(_account.Address);
} }
amount *= 1.0 + (double)await QueryPoolFee() / 1000000.0; // add the pool fees (fee/1000)=% amount /= 1.0 - (double)await QueryPoolFee() / 1000000.0; // add the pool fees (fee/1000)=%
var bigIntAmount = new BigInteger(amount); var bigIntAmount = new BigInteger(amount);
if (balance < bigIntAmount) if (balance < bigIntAmount)
......
...@@ -40,6 +40,7 @@ chainConfiguration.Bind(chainSettings); ...@@ -40,6 +40,7 @@ chainConfiguration.Bind(chainSettings);
// Add services to the container. // Add services to the container.
builder.Services.AddHostedService<PrometheusService>(); builder.Services.AddHostedService<PrometheusService>();
builder.Services.AddHostedService<RebalanceService>();
builder.Services.AddSingleton<Erc20TokenMetrics>(); builder.Services.AddSingleton<Erc20TokenMetrics>();
builder.Services.AddSingleton<PotatoStorageMetrics>(); builder.Services.AddSingleton<PotatoStorageMetrics>();
builder.Services.AddSingleton<PotatoMarketplaceMetrics>(); builder.Services.AddSingleton<PotatoMarketplaceMetrics>();
......
...@@ -169,6 +169,7 @@ ...@@ -169,6 +169,7 @@
"mode": "off" "mode": "off"
} }
}, },
"decimals": 8,
"mappings": [], "mappings": [],
"thresholds": { "thresholds": {
"mode": "absolute", "mode": "absolute",
...@@ -567,13 +568,13 @@ ...@@ -567,13 +568,13 @@
}, },
"id": 11, "id": 11,
"options": { "options": {
"displayLabels": [
"percent"
],
"legend": { "legend": {
"displayMode": "list", "displayMode": "list",
"placement": "bottom", "placement": "bottom",
"showLegend": true "showLegend": true,
"values": [
"percent"
]
}, },
"pieType": "pie", "pieType": "pie",
"reduceOptions": { "reduceOptions": {
...@@ -687,7 +688,9 @@ ...@@ -687,7 +688,9 @@
"id": 10, "id": 10,
"options": { "options": {
"legend": { "legend": {
"calcs": [], "calcs": [
"last"
],
"displayMode": "list", "displayMode": "list",
"placement": "bottom", "placement": "bottom",
"showLegend": true "showLegend": true
...@@ -965,6 +968,6 @@ ...@@ -965,6 +968,6 @@
"timezone": "browser", "timezone": "browser",
"title": "Total Supply of ROC", "title": "Total Supply of ROC",
"uid": "ce3nybz6khudcd", "uid": "ce3nybz6khudcd",
"version": 1, "version": 15,
"weekStart": "" "weekStart": ""
} }
\ No newline at end of file
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment