-
Notifications
You must be signed in to change notification settings - Fork 19
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
Fee Recipient API #24
Conversation
keymanager-oapi.yaml
Outdated
/eth/v1/feerecipient: | ||
$ref: './apis/fee_recipient.yaml' |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i think the question here will come down to what we actually want to do when consuming the api.
- if i had 2000 validators or more loaded, do i really want to list all of the fee recipients for all of the validators?
- when I'm updating a fee recipient, am i likely to want to update all, or a small number (like 1)
for this api, I would be very tempted to start off by offering the ability to get / post to 1 specific validator in the first instance, and see if a get all / list all is likely to be actually required.
for example, if we were to provide /eth/v1/feerecipient/{pubkey}
and and a get will fetch the recipient for that pubkey, a POST will update it, then that may be a very useful way to interact, especially for UI's I would expect...
Again - it depends on how it's going to be used. Not having a UI, this seems to make the most sense in the first instance.
If we do go down the route of a larger array of data, then we should at least be using feerecipients
plural, because it's not acting on a single. It would likely need to be able to accept a query parameter or a body to get a subset on the GET
. I'd be very interested to know why it's needed though.
Potentially we'd also want a DELETE
to remove an overridden fee recipient for one (or many). otherwise the POST would need to accept an empty string or something to indicate we're removing that and just want to use the default fee recipient, which seems hacky.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
the other thing a specific endpoint gives us is the ability to return 404...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
good points let me brew over it for the evening, going to see if others had any thoughts on this too.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
a specific get is a good idea and it could also be a post endpoint accepting array of pubkeys, also it should indicate that if the fee_recipient registered against it is a default or overridden.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would be very tempted to start off by offering the ability to get / post to 1 specific validator in the first instance and see if a get all / list all is likely to be actually required.
thinking back on this I feel like the reverse would be used more often with something like client migration 🤔
If we do go down the route of a larger array of data, then we should at least be using feerecipients plural, because it's not acting on a single. It would likely need to be able to accept a query parameter or a body to get a subset on the GET.
That's probably true. I think this will take longer to implement than the single use one haha so maybe you're right and we should just go with that....
Potentially we'd also want a DELETE to remove an overridden fee recipient for one (or many).
I guess most clients don't persist this 🤔 so it'll get reset on validator restart, they can update it again with whatever they need and also have a default, not sure if it's needed for mvp.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i think most of the time people will have a default fee recipient and be updating smaller numbers (probably 1), or they'll have large numbers and be basically wanting all/most to a default... they're the 2 main use-cases i can see... I think the latter is more likely to use a config based setup than keymanager management.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ok i updated based on the individual get/post. hope I'm doing this correctly 😓 . ready for re-review.
apis/fee_recipient.yaml
Outdated
Specific Public keys not mapped will continue to use the default address for fee recipient in accordance to the startup of the validator client and beacon node. | ||
Cannot specify default fee recipient address through API. | ||
|
||
WARNING: API only works POST MERGE(Bellatrix) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we'd be far better off allowing this to happen as long as the Bellatrix milestone is enabled in config.
People everywhere would otherwise have to script updating their config, or leave it for hours potentially not correct, which I can't see as a great outcome.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think prysm has a fork config flag 🤔 unless you meant something else.
the API doesn't set the default address ( which i think would complain loudly), but those ux problems are definitely a concern.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think what @rolfyone is saying is the config has bellatrix
epoch set to non infinity. But in my opinion there is no need to condition it to anything, a user will obviously use this api on setup which is merged or impending merge.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I guess the note maybe could be more for future devs doing integration testing? which I guess is a whole different UX problem lol. Do we keep the description as is then?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if its future devs, we don't care.
- what do we need now for UX to be ideal?
- are we doing more than we need, or are we doing 'enough'?
Ultimately we're trying to make it possible to provide a 'painless' UX for people, and that's why i think that restricting to after bellatrix epoch may be against that idea.
apis/fee_recipient.yaml
Outdated
pubkeys: | ||
type: array | ||
description: hexadecimal validator public keys. | ||
items: | ||
$ref: "../keymanager-oapi.yaml#/components/schemas/Pubkey" | ||
ethaddresses: | ||
type: array | ||
description: hexadecimal eth addresses that the validator public key should be associated to, the length should match . | ||
items: | ||
$ref: "../keymanager-oapi.yaml#/components/schemas/Ethaddress" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this really is just being unkind to ourselves. we should be creating an object so that we dont have 2 large disassociated arrays.
{
"pubkey": "0x...",
"fee_recipient": "0x..."
}
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
actually, i think this would mean we're just using the fee recipient map defined here as a ref
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
that's fair I was following the model on the other APIs that ended up getting approved. I do think it should be called fee recipient and then have ethaddress as the second property. other thoughts?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I agree, the array of this object is better, but then one will also need to qualify that last entry wins in case there are repeats for a pubkey. Also should there be a signature field for validating the the fee_recipient request is actually authorized. Might be crucial for multi party single validator setup if thats a thing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Another point: one special value of fee_recipient could be default
deleting any set entry against this validaor which is akin to delete as highlighted by @rolfyone later in the comments
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if we do batch, then yes the last one wins. I think an individual call might be cleaner...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I also think an individual call is cleaner though I am still wondering how important it is to implement right now.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
please take a look at the updated version
types/fee_recipient_map.yaml
Outdated
properties: | ||
pubkey: | ||
$ref: './public_key.yaml' | ||
ethaddress: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
call this by its function not its type - fee_recipient
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
manage_fee_recipient? 😅
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
im not sure why not fee_recipient?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think i called the api the same thing 😓 so i was thinking it should be different but I guess they are in different folders
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
updated
apis/fee_recipient.yaml
Outdated
description: | | ||
- set: new fee recipient mapping is set. | ||
- updated: existing fee recipient mapping is replaced. | ||
- error: Any other status different to the above: decrypting error, I/O errors, etc. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
or validator not registered
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What did you mean by this one? I think you can set the fee recipient mapping even if the validator doesn't exist in the validator/ it's not active.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
umm... returning error would be more prudent, or if not error then another enum value stating validator missing or something ? 🤔
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Still not sure on this. as long as it's valid format shouldn't it just be set? 🤔 even if you don't have the keys currently or if those aren't real keys, the validator itself will check when the keys become active.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
we really want to take advantage of HTTP return codes...
200 - updated, 202, updated (no content reuturned)
404 - not found
400 - error
404 is a particularly useful response on the POST to a specific address
so if the fee_recipient is set, and we don't have a body to return (don't think we should need one) then the 'most appropriate' response is really 202 with no body.
If the entity wasn't found to update, then 404, and if we tried to update it but there were errors, then a 400 with a mesage would be ideal, because you can provide feedback in the message about the nature of the failure.
apis/fee_recipient.yaml
Outdated
items: | ||
type: object | ||
required: [status] | ||
properties: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
can we also return what is now the current update value set against it (irrespective of the status)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I guess it would be stated in the message, but how would you like to see it? to be honest I was just following how the previous APIs were implemented haha.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
return property as fee_recipient
🤔
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
added 🤔
apis/fee_recipient.yaml
Outdated
description: | | ||
- set: new fee recipient mapping is set. | ||
- updated: existing fee recipient mapping is replaced. | ||
- error: Any other status different to the above: decrypting error, I/O errors, etc. | ||
enum: | ||
- set | ||
- updated | ||
- error |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i think if we're doing this kind of individual interface, then that changes the response too.
202 is literally 'ok'/'updated' and no content body returned
400 with an error message thats useful, something like {data:{"code": 400, "message": "oopsie"}}
we don't need to pass back fee recipient if it's a 202, because we literally passed it in.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
should it be 202 accepted or 200 ok? 🤔 i kept it as 200 right now since I wasn't sure but I just updated this
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
no body would be 202... typically a 200 would expect to have a HTTP BODY associated
apis/fee_recipient.yaml
Outdated
List the validator public key to eth address mapping for fee recipient feature on a specific public key. | ||
The validator public key will return with the default fee recipient address if a specific one was not found. | ||
|
||
WARNING: API only works POST MERGE(Bellatrix) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Potentially something like The fee_recipient is not used on Phase0 or Altair networks.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
updated
apis/fee_recipient.yaml
Outdated
"200": | ||
description: ok or updated | ||
content: | ||
application/json: | ||
schema: | ||
title: SetFeeRecipientResponse | ||
type: string | ||
example: "updated" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
so i think we go with 202, description "successfully updated", and no content.
The 200 then wont be used for the POST. I've said this in a couple of comments but highlighting the actual code for review here (sorry if it sounds like I'm nagging, but this is arguably the best actual place to comment for it)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
got it, appreciate the comments. I just updated it, how does it look now?
keymanager-oapi.yaml
Outdated
@@ -52,8 +56,12 @@ components: | |||
schemas: | |||
Pubkey: | |||
$ref: './types/public_key.yaml' | |||
Ethaddress: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
EthAddress
- missed capital ~A
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
updated
I was talking to the team and someone pointed out having it more rest like changes the path a bit but makes things more flexible, and more rest-like, so it sounds good... This may look like Overall I think we're close to a model here, but we may be kind to ourselves by going this route and maybe leveraging that model down the line... |
Cool I think this is fair and a good idea for down the road, maybe we can migrate to that one once we have some more APIs for the specific validator key ! |
keymanager-oapi.yaml
Outdated
@@ -41,6 +43,8 @@ paths: | |||
$ref: './apis/local_keystores.yaml' | |||
/eth/v1/remotekeys: | |||
$ref: './apis/remote_keystores.yaml' | |||
/eth/v1/feerecipient/{pubkey}: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this is the bit i think, if we just change this in the current PR to be /eth/v1/validator/{pubkey}/feerecipient
I think we leave the change i was talking about easy without making people move from the one we do here...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
oh i misunderstood then, ok i'll follow that then and change it to under validator
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM overall, I think changing the path before implementing is probably a good plan, it seems logical...
marking approved because i think we're in a good place overall.
Thanks for your patience James, looks good, happy for you to merge ;) |
Post Merge ( Bellatrix release) , stakers will be able to set an eth address to their corresponding validator key to receive gas fees when proposing a block. Fee recipient mapping could be standard across all validating public keys or specific per validating key.
Validator clients should provide a standard API to update and view the fee recipient settings so stakers who have a gui only setup ( dappnode/avado ) and stakers who want to update fee recipients at run time can do so.
This PR proposes one possible implementation of this standard API.
related to #23