-
Notifications
You must be signed in to change notification settings - Fork 186
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
Remove generics of Client
, enabling dynamic dispatch
#125
base: main
Are you sure you want to change the base?
Conversation
'static means that a type implementing `Config` cannot have references other than 'static ones
Use Rc not Box for clonability
Hey this initiative is awesome, thanks for this. A couple questions:
Keep in mind I haven't thoroughly reviewed the code, so I may have made some mistakes in this comment. |
I think you are moving generics from a place to another. Ideally, a client should be agnostic to configs in terms of functionalities and type signatures. And honestly, I don't think dynamic dispatch and generics don't make much difference in terms of performance. We've already spent trillion of cycles to run transformers after all. Programming ergonomics matters more in my opinion. But it's not the case in |
# Conflicts: # async-openai/src/chat.rs # async-openai/src/client.rs # async-openai/src/completion.rs # async-openai/src/file.rs # async-openai/src/image.rs # async-openai/src/moderation.rs
@64bit hey I saw new releases getting published and new PR getting merged while this PR got no feedback. Do you have any comments? |
This does look like moving in right direction long term, and similar to how it looked before Azure support. I recalled why Generics were used in first place - so that differences in Azure and OpenAI can be handled in type safe manner. But now Azure OpenAI service not available to everyone, and with growing drift between Azure and OpenAI spec just means that long term async-openai should just drop support for Azure OpenAI service. And so this PR is in right direction. Now breaking change in this is really breaking, and so moving in this direction means this is one way and not going back (type safe API for two platforms) So we target this to be released in next version bump? v0.18.0, if yes do you mind updating this PR? Thats all I have on the topic. |
I see. I rely on both Azure and OpenAI. I recently took a closer look at the differences between Azure and OpenAI's APIs. Except headers and API versioning, they work almost the same. Recently because OpenAI dramatically changed their APIs, Azure and OpenAI APIs diverges a lot, but I think Azure's APIs of a newer version will converge again with OpenAI's. The premise to remove generics of Client is that APIs of the two are not so different, but for now the premise does not hold unfortunately. If Azure is still supported, then we should wait and see Azure's APIs of a newer version that converge again. If Azure support is drop in v0.18.0, then I think we can just go ahead. Off topic a bit: |
Good points!
assuming sometime in near future, that would be best time to get this PR in (and most justified reason for anyone to deal with breaking changes) and Azure support doesnt need to be dropped. For now we wait for Azure OpenAI Service. |
Hello @ifsheldon Would you like to get this into next version bump, perhaps v0.19.0 or v0.20.0? It seems not worth holding too long for uncertainties surrounding Azure. Not having access to it is tough to maintain changes related to it. So I'd be completely relying on you for testing. This PR would also be beneficial to dynamic dispatch to other LLMs / AI providers fully compatible with OpenAI. |
# Conflicts: # async-openai/src/chat.rs
due to tokio::spawn in tests that requires `Send`
Yeah. Noteworthy is that after merging updates from main, a few tests failed to compile due to |
I think Azure support is still fine, incomplete though, because only latest version of Azure APIs is and will be compatible with OpenAI's. For example, I think this crate, as of now, can only support |
Ah nice, anything on Azure that works with latest of OpenAI is good. Please feel free to repurpose/augment the note about Azure in README for documentation. |
Enabling extra configs that can be opted in, which may be needed for LLM services other than OpenAI
I think I've got a better idea. In 639eaa4 , I added With this, any differences in difference LLM services/deployments can be handled in a type safe manner. API users just need to impl We could make pub struct Client<ExtraConfigs = ()> {
http_client: reqwest::Client,
config: Arc<dyn Config<ExtraConfigs>>,
backoff: backoff::ExponentialBackoff,
} but I think it's over generic for now. Tell me what you think @64bit |
That's a clever approach. I see that blanket Moreover So, there's no rationale to make |
OK, make sense. When I rethink about making Then we will/can have But this would be a radical change. For now, I will revert 639eaa4 |
This reverts commit 639eaa4.
Thats a good idea too. However, we want to keep things simple without falling into overengineering trap, above all, just working with openai should be prioritized even if that means library doesn't work with any other providers. The assumption with other providers is that they provider compatible API, if APIs differ significantly then it would become a nightmare to maintain and so async-openai should limit scope to work well with just one provider that is OpenAI. Other perspective that I often think about is that if we were to use ideas (and code) from this crate to implement OpenAPI spec for some other unrelated API provider - good ideas should spill over - meaning we have a good abstraction for generating Rust code from OpenAPI spec - this perspective help me keep things simple too. |
yeah, that would be async-litellm in Rust.
If you feel like ready, you can merge this before next release. I think now I don't have anything major to add. And tests seem fine. |
Thank you @ifsheldon, I'll give it one last review. Hey @deipkumar, this was your feature request - do you wanna take it for test drive and provide us any feedback (you're also welome to review the PR) before this makes it into a release? |
This is an attempt to solve #106. This removes generics of
Client
and useRcArc trait objects to do dynamic dispatch.Breaking changes:
Client
is different, so users need to change their code to use this newer version. Fortunately, the change is easy, just remove anything like<C: Config>
.Config
trait is different, sinceDebug + 'static
Debug + 'static + Send + Sync
is added as a trait bound. As long as users do notimpl Config
for their own type, this is perfectly fine. Otherwise, they need toimpl Debug
for their structs and make sure their structs don't contain non-static references.Client::configs
now returns&Rc<dyn Config>
&Arc<dyn Config>
, not&C: Config
.I think this breaking change is worthwhile, since users don't need to color all their functions that use client with
C: Config
and this makes switching between services at runtime painless.