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

docs(coding-guidelines): Add request response correlation #3290

Merged
merged 6 commits into from
Feb 27, 2023

Conversation

mxinden
Copy link
Member

@mxinden mxinden commented Dec 30, 2022

Description

Allow correlating asynchronous responses to their requests.

Notes

Links to any relevant issues

Came up in discussions around #2824.

Open Questions

Change checklist

  • I have performed a self-review of my own code
  • I have made corresponding changes to the documentation
  • I have added tests that prove my fix is effective or that my feature works
  • A changelog entry has been made in the appropriate crates

Allow correlating asynchronous responses to their requests.
Copy link
Contributor

@thomaseizinger thomaseizinger left a comment

Choose a reason for hiding this comment

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

Thanks for writing this up!

I think we should settle on one approach on how we do this in the codebase, otherwise it is not really a guideline.

My preference would be client-side generated IDs for commands:

They are a special case of "user data" just not being configurable, thus they can carry the same usecases but without the downsides of type parameters which make the code complex.

I am not sure about methods. For #3292, we would need client-side generated IDs but we can't do that if we have a more low-level component that hands out IDs.

@thomaseizinger
Copy link
Contributor

We might also want to add that this only applies to certain things. Streams for example should not have an identity but be interchangable in my opinion.

See #3268.

@mxinden
Copy link
Member Author

mxinden commented Jan 4, 2023

I think we should settle on one approach on how we do this in the codebase, otherwise it is not really a guideline.

I am assuming that you want to decide on either userdata or user-provided-ids, correct?

I don't feel strongly that we should be doing either or. In other words, I am fine using both in the rust-libp2p codebase, depending on the use-case.

I am not sure about methods. For #3292, we would need client-side generated IDs but we can't do that if we have a more low-level component that hands out IDs.

Thanks for bringing this up. for ListenOn we could later on return an event with both the listener ID and the user-provided-id. For RemoveListener the listener ID might suffice.

@thomaseizinger
Copy link
Contributor

I think we should settle on one approach on how we do this in the codebase, otherwise it is not really a guideline.

I am assuming that you want to decide on either userdata or user-provided-ids, correct?

Yes, I'd very much appreciate consistency here. I think it will make it easier to understand the codebase and allow us to better settle on reusable components.

I am not sure about methods. For #3292, we would need client-side generated IDs but we can't do that if we have a more low-level component that hands out IDs.

Thanks for bringing this up. for ListenOn we could later on return an event with both the listener ID and the user-provided-id. For RemoveListener the listener ID might suffice.

Ugh, not sure about two IDs 🫤

I think I'd prefer if we require the user to pass a ListenerId into the Transport. Those APIs shouldn't really be used directly anyway so the impact would be minimal.

Copy link
Contributor

@elenaf9 elenaf9 left a comment

Choose a reason for hiding this comment

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

Thanks for writing this up @mxinden.
Right now, this describes different approaches to solve more or less the same thing. I think it would be useful if there would be some additional notes on when it makes sense to use what.

docs/coding-guidelines.md Show resolved Hide resolved
docs/coding-guidelines.md Outdated Show resolved Hide resolved
docs/coding-guidelines.md Outdated Show resolved Hide resolved
Comment on lines 315 to 319
``` rust
fn my_method() -> Id {
// ...
}
```
Copy link
Contributor

Choose a reason for hiding this comment

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

Compared to the Command below the ID here is not user generated but instead handed out to the user. When would it be recommended to use user-generated IDs and when should they be handed out?

Copy link
Member Author

Choose a reason for hiding this comment

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

I don't have a good rule here, nor an opinion. Thus far I was simply deciding case-by-case.

Note that this is only really valid once we have libp2p#3327 and
the corresponding patch in `libp2p-swarm` `DialOpts`.
@mxinden
Copy link
Member Author

mxinden commented Jan 23, 2023

a951fbd and 694a09c remove the user-data option. Thanks for pushing for it @thomaseizinger and @elenaf9.

Comment on lines 311 to 319
When providing a **method** where the response to that method is delivered asynchronously through an
event, either synchronously return a request ID which is later on contained in the asynchronous
response event, or synchronously return a `Future` that eventually resolves into the response.

``` rust
fn my_method() -> Id {
// ...
}
```
Copy link
Contributor

Choose a reason for hiding this comment

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

Would it make sense to remove this and be consistent with commands where the caller always specifies the ID? Only Transport::dial currently behaves like stated here and we already said we wanted to fix this! :)

I'd be in favor of removing this from the guidelines (or rather, say that we want to accept the ID) and opening an issue to fix Transport::dial.

Copy link
Member Author

Choose a reason for hiding this comment

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

with commands where the caller always specifies the ID?

I have to give this more thought. In other words, I am not sure this is the way to go in all situations.

Do you feel strongly about removing this @thomaseizinger? I would prefer proceeding here. I see this pull request as a net-positive at this point.

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 makes sense for anything that is public API in our library. Internally, where we control all usages of an ID, it doesn't matter as much.

The reason for that is that the majority of our public API is command-based. Anything command-based needs to create the ID ahead of time. Any component underneath that creates its own IDs causes friction here because it doesn't compose well with commands.

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 a bit torn. There is certainly value in documenting this but if we document something, I'd prefer if we can back the written words 100%, e.g. have strong convictions that this is the way to go. Everything else is just confusing to the reader.

Copy link
Contributor

Choose a reason for hiding this comment

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

Would removing this section be a middle ground? i.e. only document that commands should come with a user-generated ID and not talk about functions at all?

Copy link
Member Author

Choose a reason for hiding this comment

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

Done with 12e61b6.

@mxinden
Copy link
Member Author

mxinden commented Feb 24, 2023

Addressed latest comment. @thomaseizinger please add the send-it label if you like the pull request as is.

@mergify mergify bot merged commit ad2954c into libp2p:master Feb 27, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants