modiimedia / arri

Arri RPC is a code-first RPC framework for end-to-end type safety in any language
MIT License
41 stars 3 forks source link

nxCloudAccess token #85

Closed leccles1 closed 1 month ago

leccles1 commented 1 month ago

Hey,

Been playing around with Arri the last couple days, love the DX so far. TS -> Dart is a stack I've been trying to find a comfortable set of tooling for quite some time now. And I'm especially interested in exposing Arripc in a serverless environment.

Anywho, in playing around with the repo, I came across - https://github.com/modiimedia/arri/blob/master/nx.json#L60.

I've not used nx much at all so I'm not sure of the implications but rather I'm seeing an access token and am just concerned it should not be there 😊

Keep up the great work Many Thanks!

joshmossas commented 1 month ago

Hey @leccles1 so when I first setup this project NX said that it was fine for the token to be public facing as it's just a way to tag the project for their distributed cache. In fact their CLI initialized the project with the token there directly in the nx.json config file which surprised me as well!

However because of your comment I looked into again and it looks like they might be changing their tune. Although it's not exactly clear (https://github.com/nrwl/nx/issues/3649#issuecomment-1474483462). I'm going to revoke the token just to be safe and remove it from the nx.json. It just means outside collaborators won't benefit from distributed cached-builds (local cache would still work), but that's prolly fine since it's mostly a concern in CI anyway.

If someone becomes a regular contributor I could always generate a token for them as well.

joshmossas commented 1 month ago

@leccles1 Thanks for the report. The issue has been fixed

Also I'm glad you enjoy the project. I've been using a similar stack to you (TS backend and Dart frontend) and it's a huge time saver (no waiting for the build runner to compile freezed and json_serializable classes LOL)

Concerning serverless, I've been deploying to cloud run with pretty good success. You basically just give it a Dockerfile and it takes care of everything else. If you want to target other runtimes, the Arri TS server supports all of the runtimes that H3 supports since ArriApp uses H3 under the hood. Although do note that it's not automatic (yet)

Basically there's a (not documented) way to override the way the server gets initialized when running arri build so it's possible to make adapters for other environments like deno deploy or whatever.

Let's say you wanted to deploy to Deno deploy

The following is a bare-bones example. First you need to update your arri.config.ts and specify a custom server entry.

// arri.config.ts
export default defineConfig(
  server: servers.tsServer({
    // this tells the CLI to use `./src/custom-server.ts` as a template when running `arri build`
    serverEntry: 'custom-server.ts'
  }),
  generators: []
)

Then inside of ./src/custom-server.ts you would write something like this:

// all of the H3 utilities are re-exported by `@arrirpc/server`
import { toWebHandler } from "@arrirpc/server";
// this is a virtual module that will be during the build process with your actual app
import app from "virtual:arri/app"

// the raw h3App is available via app.h3App
Deno.serve(toWebHandler(app.h3App));

Do note that this only works during arri build. arri dev will still use node.

Eventually I'd like for arri build to detect what environment it's running in and take care of all this automatically. We could accomplish this by creating templates for each popular runtime and then pick the correct one at build time.

leccles1 commented 1 month ago

Thanks for the snippet thats quite useful and lets me know I was at least slightly on the right track.

I'd managed to get "some" loosely working example deployed to a lambda via SST ; utilising the toWebHandler that is conveniently re-exported.

I feel my current implementation is a bit frankenstein-ish, but I was attempting to implement it in a similar way to how Hono is configured to run on Lambdas, which is basically by taking the incoming Lambda event and reconstructing it as an h3 compatible web request that is passed onto the wrapped h3 app.

The import app from "virtual:arri/app" line is very interesting! And something I definitely need to read up on some more, I'm currently facing an issue with;

Failed to build function "src/custom-server.handler": Could not resolve "virtual:arri/app"

However this is purely my fault - Because I haven't quite worked out the required configuration within SST to get esbuild to play nicely with and or be able to run the proper arri build command.

Going the standard route arri build and running node .output/server.mjs works exactly like you shared above 👍

joshmossas commented 1 month ago

The import app from "virtual:arri/app" line is very interesting! And something I definitely need to read up on some more, I'm currently facing an issue with;

When arri builds it's just using esbuild-plugin-replace to replace virtual:arri/app with the actual location of the bundled app. You can see here: https://github.com/modiimedia/arri/blob/c8f7914ac5fa7b32c3ab24c2075a287c5fe2ffdb/tooling/cli/src/serverConfigs/tsServer.ts#L277

However this is purely my fault - Because I haven't quite worked out the required configuration within SST to get esbuild to play nicely with and or be able to run the proper arri build command.

Yeah SST has been on my radar, but I haven't actually used it myself yet. It seems that SST wants to run esbuild but arri build does some additional stuff to register all of the file based routes before bundling with esbuild.

You could try running arri build before SST and then pointing SST to the .output/server.mjs file. Basically things would get double processed by esbuild but :shrug:

OR if you are willing to forego file based routing you can skip using the virtual:arri/app import entirely and just import the actual app. Then just need to remove serverEntry from your arri config. With that arri dev will still work and then SST will be able to bundle your app using esbuild.

joshmossas commented 1 month ago

Yeah so briefly looking through the SST codebase it seems like setting the handler to point to .output/server.mjs should work. Which means running arri build && sst deploy. Not ideal. I can prolly look into making a native SST integration in the future.