This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2021-04-23
Channels
- # announcements (5)
- # aws (4)
- # babashka (141)
- # beginners (139)
- # calva (35)
- # cider (5)
- # clj-kondo (27)
- # cljsrn (20)
- # clojure (37)
- # clojure-czech (5)
- # clojure-dev (26)
- # clojure-europe (11)
- # clojure-germany (1)
- # clojure-italy (1)
- # clojure-nl (3)
- # clojure-spec (17)
- # clojure-uk (16)
- # clojurescript (2)
- # conjure (1)
- # cursive (6)
- # datomic (20)
- # defnpodcast (1)
- # emacs (15)
- # fulcro (26)
- # honeysql (2)
- # instaparse (3)
- # jackdaw (4)
- # jobs (2)
- # lsp (70)
- # luminus (2)
- # meander (16)
- # missionary (2)
- # other-languages (151)
- # pathom (6)
- # portkey (13)
- # re-frame (13)
- # reagent (2)
- # reitit (43)
- # releases (1)
- # remote-jobs (1)
- # reveal (5)
- # rum (2)
- # sci (15)
- # shadow-cljs (37)
- # spacemacs (4)
- # tools-deps (8)
- # vim (20)
I’m messing around with clojure.java.classpath
. If I require it in a lein repl
and call the clojure.java.classpath/classpath
fn, I get an empty list. I would expect to see something at least…
make sure you have a version that actually supports JDK9+, older versions only work up to JDK8
the documentation says:
"Returns a sequence of File objects of the elements on the
classpath. Defaults to searching for instances of
java.net.URLClassLoader in the classloader hierarchy above
clojure.lang.RT/baseLoader or the given classloader. If no
URLClassloader can be found, as on Java 9, falls back to the
'java.class'path' system property."
In Joy of Clojure, 2nd ed p. 450 they say: > Using dynamic binding is the preferred way to handle recoverable errors in a context-sensitive manner. They also say on p. 447 that > In its purest form, dynamic binding is a structured form of a side effect. The example they show is something like this: https://github.com/jumarko/clojure-experiments/blob/master/src/clojure_experiments/books/joy_of_clojure/ch17_clojure_way_of_thinking.clj#L474-L517
(defn ^:dynamic handle-weird-animal
[{[name] :content}]
(throw (Exception. (str name " must be 'dealt with'"))))
...
(defmethod visit :animal [{[name] :content :as animal}]
(case name
;; Note: could be `cond` and use `#{"Spot" "Lopshire"}
"Spot" (handle-weird-animal animal)
"Lopshire" (handle-weird-animal animal)
(println name)))
;; the default error handling
(traverse DB visit)
;; 1. Unhandled java.lang.Exception
;; Spot must be 'dealt with'
;; custom error handling
(binding [handle-weird-animal (fn [{[name] :content}] (println name "is harmless"))]
(traverse DB visit))
Is this something that people actually use as a standard practice?
I tend to frown at dynamic binding because it's implicit rather than explicit and can lead to unpleasant surprises.Yeah a defn that throws exeptions unconditionally by default sounds like a defprotocol/defmulti in disguise
That is an idiom you can use to emulate Common Lisp -style conditions and restarts but I haven't seen it actually used
And I avoid dynamic binding in general because it is bound to the low-level thread abstraction so it breaks in the presence of fancy thread pooling like core.async
and even just lazy seqs
If you're looking for an actual implementation of Common Lisp's condition system, check out https://github.com/IGJoshua/farolero, which uses dynamic bindings
@nilern point is just right! I’m working with dynamic binding (async context) in conjuction with core async on daily basis and it’s one big hack which I wish to get rid of someday.
Stupid question: is Pedestal still the go-to choice for web applications? I had a good experience with it so far but wondering if people are using something different nowadays
I wouldn't say that there even is the go-to choice for web applications. There are many choices.
@U015VUATAVC Are you asking about full stack apps or just backend web apps?
At Metosin the go-to stack was Ring + Reitit and it is in the new Web Development with Clojure book too
I think most folks just go for compojure-api for backend API apps?
At work we don’t even use compojure-api — just plain ol’ Ring + Compojure, although we also have a GraphQL app. And one app uses Bidi instead of Compojure.
@nilern Yeah, that’s def. the impression I’ve been getting too. I think I would try Reitit for any new web apps I wrote at this point. But compojure-api is def. “popular” still 🙂
I like pedestal - its docs could use some love and probably some parts of it could use a decoupling, but the interceptor thing is overhead i like the moment i want to do websockets
I still like yada but it's not very actively maintained. Still, it has what I need, including swagger and async
What I do not like about Pedestal so far (I know that’s stupid) is the fact they ask for a :route-name
that really feels useless
Other than that, I do not have any particular complains — I was mostly interested in alternatives
On frontend reverse routing is more often useful but also on the backend good to have for redirections at least
Of course if you don't make a SPA then all that link generation moves to the backend as well
Reitit, ring-jetty
The main lib combo I use for webapps these days is integrant (system composition) + http-kit (server) +ring (server abstraction) +reitit (routing). I’m very happy with it.
Same as @U0JUR9FPH except with Mount instead of Integrant.