-
Notifications
You must be signed in to change notification settings - Fork 20
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
Support function invocation in Rib #442
Comments
You took the idea further than I imagined! However, I kind of like it, because it results in more uniformity and takes advantages of features already in "Rib". But I would say, force the user to return the response in the last line of the expression (or with the The one thing we have to worry about is durability guarantees for Rib: if a user can invoke many functions on many different workers, what sort of guarantees would they (a) expect, and (b) require? I think a user might assume Rib is durable too. I think we cannot guarantee that for now. Eventually Rib could be compiled to WASM and executed as a worker. But that's far in the future. |
Agreed with @jdegoes - I think the worker bridge should remain a 1-1 mapping between an arbitrary HTTP (or gRPC etc) request/response pair and a worker invocation. It should not have any side effects such as doing multiple invocations - it should just declare a pure mapping from input to invocation, and from invocation result to response. Otherwise it is not only having the durability issues John mention, but also becomes quite confusing where you should implement your application logic. And I think we need to have a single way for defining application logic, by writing a component and running it as a worker. |
Sure. I think we can constrain the Rib to 1-1 mapping to request/response, with the last expression in the program to be HttpResponse or GrpcResponse. The flexiblefunction invocation done within the program is still geared to the idea "that's the function you invoke as part of the http endpoint". This will make sure we have the use-case supported by Rib constrained, yet flexible enough to deal with the use case. |
And at the same time, it paves the path to future of being able to compile Rib to be able to run as a worker. For now the answer - "as far as it's a worker in Golem, it is durable, and Rib is not running as a worker". |
Also currently the Expression's result is the result of last line let x = { a : 1}
let y = { b: 2}
x.a > y.b So if the user needs to do a request-response mapping, they are already forced to return http response as the last line. I wish we had types, but as of now they need to return the wasm record Also, to mention, the idea of invoking function within the expression may not be done before 1.0. It needs a lot more changes |
Why would we want to compile Rib to be a worker? I think I'm missing the goal here. Is there any real-world example we are trying to solve with this level of flexibility? |
@vigoo @afsalthaj I think for now we could just restrict to a single worker invocation per Rib script. Note that's not really enough to entirely solve the problem because worker-bridge provides no guarantees that just because this invocation takes place, a value will be returned by the API. We need to solve the idempotency problem before we could even talk about a solution to this problem. But keep in mind there will be other functions we introduce over time, which do not perform RPC invocation, and which are nonetheless useful. An example is a function that parses a JSON string into a component model value. Or a function that generates a random number. Or a function that uppercases strings. Rib is designed to be the "glue" that allows you to put different APIs atop components. Every API Gateway has something like Rib (Lua for Kong, an unnamed expression language for Tailcall, user-defined language for Tyk, etc.). I don't think we can escape from having something like Rib but we should avoid it growing too big for us to handle. |
So, should we place this ticket as part of milestone 1.0? |
We can totally avoid calling multiple worker functions at once. I don't think the purpose of this ticket pointed to be able to invoke multiple functions. However, in a larger context, not everything that uses/works-wiith Golem has to be durable. Take Golem-Timeline, for instance. With that, I can whip up some Rib code that just meshes together results from different workers and shoots them back to the user. To have a more precise example: Write an endpoint that returns a Json of all subcomputation results of a complex computation done by golem-timeline in a durable way. Summary:
|
As I wrote, I think it gives too much power by introducing an alternate way of doing things (compared to writing your worker) instead of just mapping a worker's request/response to an alternative protocol defining a pure 1-1 mapping.
How is it prevented? |
We build expressions, and when building it, if we see more than 1 invocation we simply fail and return, without even going to evaluation of Rib. |
I think we should propagate idempotence keys from the API into any worker invocations. If we do that, I say it is not necessary to prevent multiple worker invocations. But neither is it necessary to support them now. What we need for now is:
That's enough to solve existing use cases, and room to grow in the future. I don't think we should entertain durable Rib or compilation. Though at some point, I think we will do performance work on Rib in order to lower infrastructure costs, and whether or not that could involve compilation is anyone's guess. Perhaps to return the final value, we should use |
Fixed in #532 |
Based on the discussion, instead of providing
functionName: <name of the function>
in the worker-binding, users should be able to directly invoke the function when writing Rib program.In this way, we simply write a program when it comes to worker-bridge/api-gateway instead of a overly granular way of setting up worker-binding information.
And a way to bind the
result
with the actualhttp
response. Good if Rib allows it by exposing typeThis way , we can ask users to provide
Rib<HttpResponse>
orRib<GrpcResponse>
etccc @jdegoes
Let me know if this is all making sense
The text was updated successfully, but these errors were encountered: