Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

PriceImprovement fee policy #2277

Closed
wants to merge 28 commits into from
Closed

PriceImprovement fee policy #2277

wants to merge 28 commits into from

Conversation

squadgazzz
Copy link
Contributor

@squadgazzz squadgazzz commented Jan 12, 2024

Description

Partly closes #2287

How to test

TBD

max_volume_factor: _,
quote: _,
}) => {
todo!()
Copy link
Contributor Author

@squadgazzz squadgazzz Jan 12, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How the quote should be used here?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think the cleanest solution would probably to adjust fee_from_surplus() such that it computes the surplus compared to a given reference price. Then you could pass in the user signed limit prices for FeePolicy::Surplus or the quoted amounts for FeePolicy::PriceImprovement.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let me know if I got it wrong 4a0e5ff

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, this is exactly what I had in mind. I would just call the new arguments sth like reference_(buy|sell)_amount and add a doc comment explaining the meaning of the reference amounts.

@squadgazzz squadgazzz marked this pull request as ready for review January 12, 2024 18:21
@squadgazzz squadgazzz requested a review from a team as a code owner January 12, 2024 18:21
@squadgazzz squadgazzz changed the title Price improvement policy PriceImprovement fee policy Jan 12, 2024
crates/autopilot/src/arguments.rs Outdated Show resolved Hide resolved
crates/autopilot/src/domain/fee/mod.rs Outdated Show resolved Hide resolved
crates/autopilot/src/domain/fee/mod.rs Outdated Show resolved Hide resolved
crates/driver/openapi.yml Outdated Show resolved Hide resolved
max_volume_factor: _,
quote: _,
}) => {
todo!()
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think the cleanest solution would probably to adjust fee_from_surplus() such that it computes the surplus compared to a given reference price. Then you could pass in the user signed limit prices for FeePolicy::Surplus or the quoted amounts for FeePolicy::PriceImprovement.

Copy link
Contributor

@fleupold fleupold left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good first step!

Note, that there is an ongoing discussion whether it should be called PriceImprovement or QuoteDeviation (https://cowservices.slack.com/archives/C05N1FNP3MX/p1704971316558629)

crates/autopilot/src/arguments.rs Outdated Show resolved Hide resolved
PriceImprovement {
factor: f64,
max_volume_factor: f64,
quote: Quote,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I really like that the quote becomes part of the fee policy enum. This makes it very clear how to use it.

crates/autopilot/src/domain/fee/mod.rs Outdated Show resolved Hide resolved
crates/driver/openapi.yml Outdated Show resolved Hide resolved
}
}) => self.calculate_fee(
self.order().sell.amount.0,
self.order().buy.amount.0,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I am not sure this works for scaling partially fillable sell orders. Will need to go over it once more tomorrow, with a fresh mind.

Copy link
Contributor

@fleupold fleupold left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it would actually be great if we could get driver based integration tests running before adding more fee policies.

@@ -90,3 +95,48 @@ pub enum Policy {
factor: f64,
},
}

#[derive(Debug)]
pub enum PolicyRaw {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm a bit surprised by this type. I don't find the word "raw" very descriptive nor appealing and it's missing documentation for why it exists (on top of FeePolicy). It looks like the only difference is the quote (which in only part of the other struct).

Is there any way we can get around defining two almost identical domain types or can we differentiate better between the two?

Maybe PolicyRaw is more like an incomplete Policy (maybe a PolicyBuilder), that can be converted into a full policy .with(quote)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, totally makes sense. Renamed both the struct and the function.

}

impl PolicyRaw {
pub fn to_domain(&self, quote: &domain::Quote) -> Policy {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

isn't PolicyRaw already a domain object?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Comment on lines 240 to 241
let protocol_fees = self.protocol_fee.get(&order, quote);
Some(boundary::order::to_domain(order, protocol_fees))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it would read slightly nicer if ProtocolFee would return the domain order type.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed

Comment on lines 93 to 94
quote.sell_amount,
quote.buy_amount,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think here we need to use whatever is better (quote or limit price)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Comment on lines 264 to 265
sell_amount | numeric | | quote's sell amount
buy_amount | numeric | | quote's buy amount
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Don't we already store this information in order_quotes? Do we want to duplicate it?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think these will be different values defining user price exchange rate, compared to order_quotes where the amm price exchange rate is saved.
The user price exchange rate takes fee into account.

Here I wrote about an example.

@sunce86
Copy link
Contributor

sunce86 commented Jan 25, 2024

I think we are somewhat close to finishing this PR (at least roughly we know what needs to be done). However, it's hard to review it with high confidence that it's correct and that it doesn't break the existing functionality (since it tackles most of the tasks from #2287).

Do you think it makes sense to split this PR into multiple PRs and try to write tests for each of them?

Comment on lines +93 to +94
let sell_amount = quote.sell_amount.max(self.order().sell.amount.0);
let buy_amount = quote.buy_amount.min(self.order().buy.amount.0);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Isn't this turned around? We want to take what's better for the trader between quote and limit (where I have to sell less and where I get to buy more)? I really think we should do a test case to cover this.

fee_policy_skip_market_orders: bool,
}

impl ProtocolFee {
pub fn new(policy: Policy, fee_policy_skip_market_orders: bool) -> Self {
pub fn new(policy: PolicyBuilder, fee_policy_skip_market_orders: bool) -> Self {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sorry for being flip floppy here, but now that I look at it isn't this more like a config object (without any need for logic on it)? This way we could leave all logic inside the ProtocolFee component?

Copy link
Contributor

@sunce86 sunce86 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we merge the changes from main branch, so we can make sure the quote_fee_amount is included in the Quote we send to the driver (it should be added to the quote_sell_amount)?

ilia and others added 2 commits January 29, 2024 19:11
# Conflicts:
#	crates/autopilot/src/domain/fee/mod.rs
#	crates/autopilot/src/solvable_orders.rs
Copy link

CLA Assistant Lite bot:
Thank you for your submission, we really appreciate it. Like many open-source projects, we ask that you all sign our Contributor License Agreement before we can accept your contribution. You can sign the CLA by just posting a Pull Request Comment same as the below format.


I have read the CLA Document and I hereby sign the CLA


1 out of 2 committers have signed the CLA.
@squadgazzz
@Ilia
ilia seems not to be a GitHub user. You need a GitHub account to be able to sign the CLA. If you have already a GitHub account, please add the email address used for this commit to your account.
You can retrigger this bot by commenting recheck in this Pull Request

Copy link

github-actions bot commented Feb 6, 2024

This pull request has been marked as stale because it has been inactive a while. Please update this pull request or it will be automatically closed.

@github-actions github-actions bot added the stale label Feb 6, 2024
@sunce86 sunce86 removed the stale label Feb 6, 2024
# Conflicts:
#	crates/autopilot/src/domain/fee/mod.rs
Copy link

github-actions bot commented Feb 6, 2024

Reminder: Please update the DB Readme.


Caused by:

@squadgazzz
Copy link
Contributor Author

Splitting the PR into parts to properly follow #2287

@squadgazzz squadgazzz closed this Feb 6, 2024
@github-actions github-actions bot locked and limited conversation to collaborators Feb 6, 2024
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

feat: Protocol Fees Tracker 2: PriceImprovement over Quotes
4 participants