How to manually invoke server functions?
Hey all, have a bit of a weird problem trying to combine SolidStart with Cloudflare Durable Objects and Server Functions.
The following works great, unless the server function is used during server side rendering, in which case the "request" context that we forward to the durable object is for the page being rendered, not for the invocation of the server function. So the durable object responds with the fully rendered page, instead of the server function result. As you can imagine, this causes issues. It's easy enough to detect when this happens, but I can't figure out how to construct a new request to send to the Durable Object to invoke just the server function?
Or perhaps it would be best to skip any rendering on the worker entirely, and just send the whole request to the durable object to begin with. However this would require me to fork the
cloudflare-durable
preset.
1 Reply
Is the RPC interface of server functions considered "private"?
If so, is there some directive to generate a copy of the "client" version of the server function on the server, so I can use that to construct the request to send to the durable object?
I'm probably going to need to fork the
cloudflare-durable
preset anyway because it hard codes in the durable object name for websockets which doesn't work for me use case, so perhaps I've answered my own question and the worker should just always forward to the durable object for rendering. Although I have some routes that aren't paramaterised by the GameID, so they'll have to remain in the worker 🤔
In addition to that, is there any way to hook into the kind of conditional compilation that is used to drive the magic behind server functions? i.e. generate this code on the client and this code on the server?
I’m porting over an app from using Leptos / Rust which has a similar server function thing, but it’s much easier to make your own variation on that tech using Rusts compiler config / conditional compilation
Actually turns out the root of the problem is a kind of "double encoding" problem, the response from the durable object is already the encoded server function response, e.g.
so returning that response from inside the worker's server function results in it being "double encoded" in a way. I'd need to find a way to bypass the encoding from the worker's server function and return the response directly 🤔
Alright I was able to solve the double encoding problem with X-Content-Raw
but still have the "rendering the whole page during ssr" problem since I need to figure out how to manually invoke the server function
I was able to reverse engineer most of the server side function protocol, but it seemed rather fragile to rely upon. In particular I found it difficult to abstract out routing calls to the Durable Object with higher order functions and "use server" interacting weirdly.
I've gone back to just using regular API endpoints which means I unfortunately loose the nice DX of server functions, and then have a middleware intercept those calls and forward them to the DO which is injected into the request context via the entrypoint
I then also need a SSR compatible fetch becuase you can't use relative URLs during SSR
Alright, I was able to get server functions working with durable objects using a kind of janking middleware, unfortunately the middleware has to exists inside the server function definition so it can get access to the server function ID which is set by a proxy
I think I'm just going to go with a regular API route though because I don't like that there's no real spec to the server functions and I don't want it breaking between deployments / unable to handle proper versioning