This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2022-08-31
Channels
- # announcements (6)
- # babashka (32)
- # beginners (78)
- # biff (11)
- # calva (7)
- # clj-kondo (20)
- # clojure (35)
- # clojure-europe (10)
- # clojure-nl (4)
- # clojure-norway (8)
- # clojure-uk (2)
- # clojurescript (41)
- # conjure (14)
- # core-async (10)
- # cursive (7)
- # datomic (12)
- # deps-new (4)
- # emacs (15)
- # fulcro (48)
- # gratitude (11)
- # hugsql (1)
- # hyperfiddle (3)
- # introduce-yourself (3)
- # jobs (3)
- # klipse (2)
- # off-topic (7)
- # polylith (30)
- # reitit (1)
- # remote-jobs (1)
- # reveal (8)
- # scittle (4)
- # shadow-cljs (40)
- # squint (13)
- # tools-deps (7)
- # xtdb (7)
We are working on upgrading to FC3. Is it possible to have both FC2 EQL parser and pathom?
EQL is EQL. Fulcro doesn’t care. If you mean you’d like to use existing helpers from F2 on the server, then I don’t see a problem (off-hand)
The only danger of having F2 and F3 on the classpath at the same time is accidental usage of an old F2 ns in F3 code. I made sure there are no ns overlaps, but that doesn’t fix the “IDE Autocomplete” features that might do that.
I’m referring to the porting guide here:
> Fulcro 3 no longer supplies server-side macros for mutations and reads, as pathom
is a much better choice for EQL service.
I’m trying to determine if its best to try and swap all of the backend to pathom, prior to fully upgrading to fc3
True, using Pathom’s supplied defresolver and defmutation are better, but there’s no reason the existing things won’t work, other than you have to figure out how to do the dispatch
I’d probably just define two remotes and two URIs like /api and /api-new, then you can have the app select the remote. That would let you port over time.
If I do a query [:x :y :z]
that could involve 3 difference resolvers (in Pathom). In F2 you probably were just doing full query resolution per top-level keyword…so there was no need to dispatch to multiple code units to complete the query
As you port to Pathom, you’ll have resolvers that do smaller units of work, and Pathom will coordinate them (dispatch based on context and EQL)
Sounds like testing it out in a smaller chunk might help me figure out the best course of action
but if you issue a query where :x and :y need to come from new API and :z needs to come from old api, then you have a dispatch problem. One EQL query won’t hit “both”
That said, if you’re doing what I think you’re doing for F2, then porting may not be as bad as you think. Mutations are trivial (change which macro you use, and the notation slightly). Queries, if you’re mainly doing things where you’re not processing the EQL but just blindly responding to what you know you need, will be very simple as well.
I feel like I could do it on a component by component basis and pull over the APIs needed for each query. As I get closer to the end of them, I imagine I would have ported a majority of things
Most of our routes follow an initial load pattern which have a defmethod mutate
and look something like:
(df/load reconciler [:profile/by-id sso-id] ProfileForm etc...
In reading a bit about pathom it sounds like I could have a defresolver
that does something similar to the api-read
above
the api-read is dispatching on single keywords. That is the ::pc/output
setting on a resolver.
for ident loading, you’d use a ::pc/input
of #{:profile/by-id}
, which would then give you the id in the input params of the resolver.
@tony.kay re multiple remotes: Is there any of examples of this in the docs? I have diving into the source code a bit and found this:
`:networking` (optional). An instance of FulcroNetwork that will act as the default remote (named :remote). If
you want to support multiple remotes, then this should be a map whose keys are the keyword names of the remotes
and whose values are FulcroNetwork instances.
just look at the constructor function for new fulcro apps doc string, and implementation (source). It creates :remote
for you. Just do that again with an addl kw. On the server: the middleware lets you specify the URI.
(defn new-client-with-defaults []
(fc/new-fulcro-client :started-callback on-app-started
:network-error-callback
(fn [_ _ {:keys [type message]}]
(log/error type ":" message))
{:networking {:pathom-remote (fulcro-http-remote {:url "/pathom/api"})}}))
and then I would just make another instance of make-fulcro-server
? Where the app-name refers to this url above?
(fulcro.easy-server/make-fulcro-server :app-name "pathom" *...*)
I’m mostly referring to this https://book.fulcrologic.com/fulcro2/#_modifying_the_api_route but I’m not sure its the right path since I don’t have two apps, its more like one app with two api routes
on the client:
(app/fulcro-app …
:remotes {:remote (net/fulcro-http-remote
{:url "/api"
:response-middleware response-middleware
:request-middleware secured-request-middleware})
:newapi (net/fulcro-http-remote
{:url "/api-new"
:response-middleware response-middleware
:request-middleware secured-request-middleware})
refer to:
https://book.fulcrologic.com/#_creating_a_remote
https://book.fulcrologic.com/#_remote_mutationson the server, just install the middleware the new F3 middleware with /api-new
:
(wrap-api "/api-new")
and then in df/load
use :remote :newapi
when you want to load from the new one. In mutations use the (remote [_] true)
to mutate against old API and (newapi [_] true)
to mutate against the new one.where wrap-api is something like:
(defn wrap-api [handler uri]
(fn [request]
(if (= uri (:uri request))
(handle-api-request
(:transit-params request)
(fn [tx] (parser {:ring/request request} tx)))
(handler request))))
and `
[com.fulcrologic.fulcro.server.api-middleware :refer [handle-api-request]]
is where handle-api-request comes fromThe current app is in FC2, I’m concerned that our backend apis will break once I upgrade so I’m attempting to make a path to convert them over to pathom in the current FC2 setup prior to upgrading.
Yes of course. Like I said, both can be on the class path, and EQL hasn't changed, so the front end will have no idea what is implementing the back end.
Honestly, this looks a lot like what I’m trying to achieve: https://book.fulcrologic.com/fulcro2/#_interfacing_with_alternate_network_protocols
@tony.kay You posted about your connect-macros to create resolvers that don’t require restarting Pathom, which is posted here: https://gist.github.com/awkay/86a3d7b3be912f79961e7bffba91a6f2 Can you also post the source the [app.lib.pathom.registry :refer [register!]], which it requires? Many thanks! (I’d love to give this a try!)
(ns app.lib.pathom.registry
(:require
[com.wsscode.pathom.connect :as pc]
[taoensso.timbre :as log]))
(defonce pathom-registry (atom {}))
(defn register! [resolver]
(log/debug "Registering resolver" (::pc/sym resolver))
(swap! pathom-registry assoc (::pc/sym resolver) resolver))
Then when you make the parser somewhere you’ve got a list of all your resolvers, just include it there:
resolvers [form/resolvers
(blob/resolvers r.model/all-attributes)
(res/generate-resolvers r.model/all-attributes)
(rad-datomic/generate-resolvers attributes-with-security :main)
(vec (vals @pathom-registry))]
The registry uses a map so that if you re-eval something it doesn’t get duplicated (unless you renamed it, which is just like def and namespaces)