Fork me on GitHub
Daniel Tobias03:01:51

hello all, I am trying to make an app in cljs (with reagent) and it needs to interact with an API that's being hosted by a django backend. Is there a way to do the neat little development environment but somehow proxy all my requests to the django backend?


In this video, there's a quote from Rich Hickey and the presenter says that if there's one thing to be taken away from the talk, it should be that:

When you combine two pieces of data you get data. When you combine two machines you get trouble.
I understand what this means (I think). But can someone explain why this has to be stated explicitly? Or what's the context in which this was quipped by Rich Hickey?


@dan.yb.tobias IIUC your django backend will be the only web server, right? then just tell your build tool to put the generated javascript somewhere that your django backend will know to serve


in principle it's not very different to working with a Clojure backend

Daniel Tobias03:01:08

doesnt figwheel or whatever spin up a little development server?

Daniel Tobias03:01:14

i dont want to have to compile every time i make a change etc


that's independent of the server that actually serves your main web page


if you serve a html doc like the one described in that page from your web server, and if your web server serves the right file when asked for "/cljs-out/dev-main.js", you should be good

Daniel Tobias04:01:48

im a bit confused here, the doc linked doesnt say anything about it

Daniel Tobias04:01:35

do i need to change the port of the ring server to match as well?

Daniel Tobias04:01:51

I am so confused, am i running fig:build or what?


your django server would replace the ring server. it doesn't matter what port it listens on, as long as you visit localhost:<that-port> in your browser


you can run any regular figwheel command

Daniel Tobias04:01:08

there is no html file produced though?

Daniel Tobias04:01:01

oof this is not working at all, i made an html and loaded the js there but

Daniel Tobias05:01:04

@U65FN6WL9 it looks like how the js is trying to load files is's using escape charatcers in strings?


Hi everyone, I'm not sure where I should ask this but am trying to get the automated testing for clojurewerkz/money working again. Seems like at least for openjdk8 all tests pass but am encountering Tried to use insecure HTTP repository without TLS as shown here Understand that this is the result of the snapshot deployment link for Nexus, but does anyone know what link i should update it to in the project.clj here -


@zackteo Change http:// to https://?


Wow it did work. Guess i should have just tried that

Titan Roark04:01:15

Hey guys and girls. New to Clojure, I'm learning by writing clojure to solve problems at I just solved #3 using Clojure and I'd like to get some advice and tips about how I could've written my code better. Here's a gist, lmk if the link works: Also, there's an error I could use help debugging with the getFactor function, if passed 6857 (`getFactor 6857`) there's a stack overflow that I'm not sure how to go about solving.


I did some Project Euler problems some time ago. You can find here: Just check for problem 3

Rowan Barnard09:01:46

You might also want to look at which has problems designed to help you learn the language.


@seancorfield thought about that. Guess I could give that a try. Was thinking if the link was meant to be inaccessible


@titanroark a quick thing to try would be to replace recursive calls to getFactor with recur:

Titan Roark16:01:44

Thank you, this is the kind of advice I was looking for


also, to find factors you only need to check up to the square root... but now we're talking math. if your current primary focus is learning Clojure, problems may have the focus too much on the math side?


factorial is a different math concept. stick to the name "factor"

Daniel Tobias04:01:06

euccastro i think what you suggested before isnt quite right

👀 1

sorry, I had missed your reply; I've just replied in that thread


lines 8-11 are the same as line 14, just specialized for the number 2. you could just call (getFactor x 2) at that point


Not sure if this falls under beginners but has anyone encountered a situation where a new github pull request (that just changes the readme breaks the existing clojure tests? CI on github actions) It is very strange. Because when I try rerunning the tests on the previous commit there is no issue. But once I make a new pull request, even in the minimal example just amending the readme, breaks the CI


It's possible the tests are non-deterministic or something in the tests is not compatible with the GitHub Actions environment...


hmmm, my issue is that it would make sense that the github actions doing the test would have failed for the previous commits then or failed when I reran the actions but no issues


It is just generally quite an odd situation


Computers are deterministic by definition 🙂


My own theory is that the github secrets might be having issues when I am the one pushing the commit


Tho I am not sure if that theory checks out with the github actions history :thinking_face:


In which it should be intermittent and kicking off the process again should succeed...


Oh I mean the owner of the repo might be the only one able to access the secrets - I can't tell if that makes sense


guess all I can do is sleep on it


Do not know what is the right channel for pedestral questions so I ask here I have this :

`(ns hello
  (:require [io.pedestral.http :as http]
            [io.pedestral.http.route :as route]))

(defn respond-hello [request]
  {:status 200 :body "Hello, world!"})

(respond-hello {})


You have a typo, it's called pedestal, not pedestral. (Remove the r ) FYI there's #pedestal


See that I have to learn a lot more about clojure to make my own sites and really understand how things really work


interceptors are I think the hard part


You don't need interceptors to make a site


Pedestal bundles a few things together


If you find it hard to grok you could go a step back. I think the absolute minimum for a beginner is something like compojure and figwheel but it's best to ask around


maybe I will or go back to duct or take a few steps more back. Before pedestal I did a few tutorials about duct and before that about ring.



 {io.pedestal/pedestal.service {:mvn/version "0.5.7"}
  io.pedestal/pedestal.route   {:mvn/version "0.5.7"}
  io.pedestal/pedestal.jetty   {:mvn/version "0.5.7"}
  org.slf4j/slf4j-simple       {:mvn/version "1.7.28"}}
 :paths ["src"]}


but still I see this error :

; Execution error (FileNotFoundException) at hello/eval13893$loading (REPL:1).
; Could not locate io/pedestral/http__init.class, io/pedestral/http.clj or io/pedestral/http.cljc on classpath.


Your deps.edn looks fine. But you have a misspelling in your require. "pedestral"


What am I not getting?

(defn vec-of-14 [& seqs]
  (count seqs) ;=> 3
  (->> seqs
       (take 14)
       (vec)) ;=> Eval timed out!

  (vec-of-14 (repeat 14 true)
             (repeat 1 false)
             (repeat true)) ;=> Eval timed out!
  (->> (concat (repeat 14 true)
               (repeat 1 false)
               (repeat true))
       (take 14)
       (vec)) ;=> [true true true true true true true true true true true true true true]
So, the second form in the comment there works as I expect. Trying to make a function from it blows up. The seqs are realized is my guess, but when and how and why?

Matheus Moreira10:01:47

You probably need to replace (concat) by (apply concat) in your method.


Oh, of course… Thanks!


what would be the pattern if I basically want to block until a certain condition is true? I'm waiting on a file and the last-modification time keeps changing and I want to wait until it doesn't change any longer for 100ms or something


So what exactly are the differences between `(filter #(<= 5 %) coll)` and `(filter (partial <= 5) coll)` ? Is that second example using a "transducer?"


From reading the home page docs I don't think so. I should be creating an "xform." I get the feel that transducers are the current trend in performant, idiomatic clojure but I'm mostly confused about it all.


Any resources you recommend to start thinking in the transducer way of doing things? I feel like that could (should?) be the next step in upping my fp game.


What initially inspired this is this reddit thread: I want to start thinking like how SimonGray and joinr handled the problem


neither of those are using transducers


I knew the first one wasn't, just wasn't sure if that second one was. I guess I don't really know what I'm asking besides how to start thinking in the higher abstraction, transducer sense of solving problems. Probably the only answer is experience.


read that guide and internalize what transducers are. i think its really important to remember they are functions that take reducing functions and return reducing functions


Will do. The embarrassing part is the first paragraph reiterates: Note: this reduced arity is not currying or partial application. And here I am asking if that partial produced a transducer. lol


no worries. they can be a bit difficult to grok them. follow that guide and build up your intuition and also keep that definition in mind: a function from a reducing function to a reducing function


And are they more performant to use in most cases? I know that's probably to general to ask though. But is it something you usually try and reach for when writing idiomatic clojure?


at the top is a link for "good use cases for transducers" which has a section about performance. nothing more authoritative or thoughtful than that section


Fair enough! Thanks


These are the same


The only difference is that #(<= 5 %) creates the predicate function at read time, and (partial <= 5) creates the predicate function at run-time


The docstring you're reading is referring to the arity (number of arguments) of filter


Both your example call filter with 2 arguments though, so in your case you are using the 2-ary version of filter in both case


The doc says return a transducer when no collection is provided, and in both cases you provide [pred coll]


again stuck how I have to deal with this :

; Implement update-in.

(def my-update-in [m k f]
I think at some way I have to find the part with the key and then apply the function at the value and put the whole m again together. Do I thinking the right way ?


Sounds like a good plan, yes. If by "put the whole m again together" you are thinking "create a new map in N steps if the original map m has N key/value pairs", then there are faster ways, e.g. "create a new map from m by replacing only the value of key k with the new value"


hmmm, then I have to think again


that could work but on some way I have to check where I want to check things


You could get a correct solution by creating a new map in N steps.


It probably just would not be among the fastest solutions.


Your original statement said "and put the whole m again together".


There are multiple things you might have meant when you said that, and I don't know what you were thinking.


that is not the most important I think. This is a challenge from the brave book and I think the purpose is to understand how things work


One thing you might have meant was "for each of the N keys in the original input map, add that key to a new map to be returned"


not find the fastest one


Lets say we have this map : (def users [{:name "James" :age 26}  {:name "John" :age 43}])


That is a vector containing two maps.


another one then : {:name "James" ;age 26}


That is one map 🙂


now I want to change the age to 36 because I made a typo


then my idea was to use for example `get to get the age out of it


make a new age with 36


and then I have to make a new map with the name part and the new age part


or if I want to change the name a new map with the new name and the old age part


but I think I do not see how the pieces comes together


My only point was that there is more than one way to do that last step, and I was making a comment about efficiency of a couple of different ways. If you aren't worried about efficiency at all, then by all means ignore that comment.


I think I have to store the new part somewhere with a let ?


I wouldn't say "have to", but if it helps you write a solution, then let is perfectly reasonable.


(def my-update-in [m k f] (let [new_value (f (get m k)]      )


If you want to use let, then taking your breaking the function up in to steps, you can first get the current value in the map for key k, and bind that result to some new name in the let, e.g. cur-val or whatever you would like to call it.


Sure, what you do there is doing your first two steps in one line, which is also good.


oke , if I go to fast , say it please


I will. Don't worry, I'm following so far 🙂


then I have to make a new map. I think I need to use assoc


but how do I now from the old map what is then the old part ?


and what is the new part?


So assoc always returns a new map, leaving the original one unchanged. The new map is almost the same as the input map, except for the value associated with the key you give to assoc, which in the returned map will be the value you give to assoc


yep, so there im stuck


user=> (assoc {:a 1 :b 2 :c 3} :b -2)
{:a 1, :b -2, :c 3}


oke, so I do not have to know


I didn't tell assoc to do anything with keys :a or :c, and the returned map still has them, associated with their original values.


That is what assoc is intended to do.


oke, did not realize that


Has the book you are following described assoc before this exercise, I hope?


so I can do just this :

(def my-update-in [m k f]
   (let [new_value (f (get m k)]
   (assoc m new_value) 


yep, I did


but I think I misunderstood it as just for adding things


Your call to assoc doesn't have the correct number of parameters.


(def my-update-in [m k f]
   (let [new_value (f (get m k)]
   (assoc m k new_value) 


that looks better


Looks like a good time to try out your new function with some sample input parameters in a REPL and test if it works as you hope.


there is still a error somehow


What editor are you using?


calva is yelling me that the closing ] is on the wrong place


I use vs code with calva


Most editors have the option to show you when parens, square brackets, or curly braces are matching or not. You definitely want to get familiar with how to understand what it is telling you there.


e.g. many editors will show you the matching paren, bracket, or brace when your cursor is on or just after one of them, highlighting it visually so you can see which one matches the one where the cursor is.


yep, I was missing a )


Trying to write a Lisp-like language without such editor support is going to slow you down tremendously.


There is a lot of fancy 'structural editing' stuff you may have heard about that some people love, but I've never used that myself. But I do really, really miss it if I ever use an editor that doesn't show me matching parens and brackets.


still somewhere a error :

; Execution error (ClassCastException) at chapter5/my-update-in (form-init95645667318631163.clj:51).
; class java.lang.Long cannot be cast to class clojure.lang.IFn (java.lang.Long is in module java.base of loader 'bootstrap'; clojure.lang.IFn is in unnamed module of loader 'app')
code :
(defn my-update-in [m k f]
  (let [new_value (f (get m k))]
    (assoc m k new_value)))

(my-update-in p :age 35)


Is there anything else in the same file with that function? Looking at the function definition, nothing obviously wrong jumps out at me.


What is the 3rd parameter of my-update-in supposed to be?


Im my first idea it was a function but later it changed to the new value


What does my-update-in do with the 3rd parameter?


it uses it to make the new map with a updated key


so it is not a function


The only place the 3rd parameter is used in my-update-in is this expression (f (get m k))


So it is trying to call f as a function.


yep, I see it , thinking how tto solve it


That is what the exercise asked you to write, I think, yes?


Then when you are trying to use my-update-in, you gave it the number 35 as the 3rd parameter, and my-update-in tried calling the number 35 as if it were a function.


So it appears to me that your my-update-in is doing what the exercise says it should, but your attempt to call the function is passing a 3rd parameter that it was never intended to handle.


i.e. you are calling my-update-in incorrectly. You should try calling it where the 3rd parameter is some function.


If you want a quick try, replace 35 with inc, which is a function.


yep, that works


Does it make sense why you got the error when you passed in 35?


it makes sense


Do you know how to write a Clojure function that takes a number and adds 10 to it?



defn add-ten [number] (+ number 10))```


Good. If you define that function, you could pass add-ten as the 3rd parameter to my-update-in


oke, so there is no way I could make it work without a function ?


only given the right value


You could write a different function than my-update-in


that takes a new value for the 3rd parameter instead of a function.


If you did, I would call it my-assoc 🙂


I was thinking to change my_update_in


If you change my-update-in to take a value instead of a function as the third parameter, you can certainly do that. Note that it would not be one that solves the exercise you were working on.


?? the only that the challenge said it to implement update-in


Yes, I understand that.


YOu asked if you could change my-update-in to behave differently. You can do that if you want.


I am only saying that such a changed my-update-in does not solve the challenge.


oke, I see it, update-in takes always a function


as the 3rd parameter, yes.


so I wanted to make another function


And I encourage you to experiment to your heart's content 🙂


thanks for thinking with me and teaching me some things


clojure is a totally other beast then when I was learning ruby or haskell


but I love the way repl helps me to see the results when I try something


You could write my-update-in in Haskell in about the same number of characters, I suspect. Clojure and Haskell share that they deal mostly with immutable values, but Haskell has far fewer "escape hatches" than Clojure does for mutating state.


And Clojure doesn't restrict you to writing code that passes Haskell's type checker.


and clojure is much faster then a haskell programm is my feeling


and I played with some web stuff and clojure has much more choices then haskell


in haskell you have only yesod and servant as big players


I don't know a lot about Haskell performance to compare it to Clojure -- they both are not necessarily the language you want to use to get the best performance for heavy numerical computation, for example.


clojure has for back-end duct, pedestral en some more


but both are perfectly fine for calling out to libraries written in other languages for doing that kind of thing.


but much more to do for your own


dinner time


and tomorrow or later time to study the next chapter macro's 🙂


Anyone using cider with Doom emacs? Trying to figure out the most appropriate way to evaluate the form under the cursor

👀 1
Max Deineko17:01:14

I'm using it with lispy[ville] and lispy-eval keybinding (iianm I had to add com.cemerick/pomegranate and com.billpiel/sayid to my clojure deps for it to work)

Max Deineko17:01:48

Apart from that and cider-eval-… bindings as well as cider-pprint-eval-last-sexp-to-comment I so far have found cider debugger with enlighten-mode quite useful. Seeing how flexible this all is I'd be also interested in seeing what others are using for quick & easy inspection of forms & values 🙂


I moved away from lispy because of le-clojure.clj. I use cider-eval-defun-at-point and cider-eval-last-sexp ... If I ever need to be more granular, I use er/expand-region and then cider-eval-region ... all these are bound to things like , e d , e e etc

Max Deineko18:01:25

@U014JFA9EP5 Are you're referring to the part of lispy provided by le-clojure.el ? Does it have some flaws one should be aware of?

Daniel Tobias18:01:20

it really doesnt look like cljs works well with a django backend 😛

Daniel Tobias18:01:25

i am really struggling to get it working


The backend and front end are orthogonal. If you return Json the backend technology is irrelevant for cljs. Do you have a more specific problem you can share?

Daniel Tobias18:01:12

i think it's more about the project.clj file, im doing a figwheel-main reagent template and I guess i need to hook it up so that the project itself isnt necessarily in the django folders but the produced html/js/css ends up in the correct places

Daniel Tobias18:01:20

there's just like 2 million directories specified in this thing

Daniel Tobias18:01:31

looks like the configuration doesnt like relative paths either


can you share your project.clj?

Daniel Tobias19:01:14

(defproject livematch "0.1.0-SNAPSHOT"
  :description "FIXME: write this!"
  :url ""
  :license {:name "Eclipse Public License"
            :url ""}

  :min-lein-version "2.7.1"

  :dependencies [[org.clojure/clojure "1.10.0"]
                 [org.clojure/clojurescript "1.10.773"]
                 [reagent "0.10.0" ]]

  :source-paths ["src"]

  :aliases {"fig"       ["run" "-m" "figwheel.main"]
            "fig:build" ["run" "-m" "figwheel.main" "-b" "dev" "-r"]
            "fig:min"   ["run" "-m" "figwheel.main" "-O" "advanced" "-bo" "dev"]
            "fig:test"  ["run" "-m" "figwheel.main" "-co" "test.cljs.edn" "-m" "livematch.test-runner"]}

  :profiles {:dev {:dependencies [[com.bhauman/figwheel-main "0.2.12"]]
                   :resource-paths ["target"]
                   ;; need to add the compiled assets to the :clean-targets
                   :clean-targets ^{:protect false} ["target"]}})

Daniel Tobias19:01:46

the main issue im having i think is the dev-main.js can't find any of the deps it needs for some reason

Daniel Tobias19:01:07

if i look at dev-main.js i have lines like this:

Daniel Tobias19:01:10

document.write('<script src="..\..\paladeenz\website\static\livematch\public\cljs-out\dev/cljs_deps.js"></script>');

Daniel Tobias19:01:15

notice the escape characters..

Daniel Tobias19:01:40

it's just copy and pasting the target directory..but remember the src is in a different folder than my django when the js gets put into the django app it needs to look in the correct place for the deps but isnt


what’s dev-main.js?


where is this file? and what’s suppose to do?

Daniel Tobias19:01:51

this is the output js from building...i fixed it by editing all of the urls the issue is that if recompiled it will overwrite and i have to change it over and over

Daniel Tobias19:01:50

the target-dir i set is so that it can create dev-main.js in the correct spot, but dev-main itself seems to be using the target-dir also to find the dependencies which completely breaks it

Daniel Tobias19:01:26

so i have a figwheel-main.edn file which says

:target-dir "../../paladeenz/website/static/livematch"

Daniel Tobias19:01:52

which puts dev-main.js where it needs to's just now dev-main.js is trying to load files from target-dir + other stuff, which is wrong


it’s long time since i use fighweel.main but let me see if i can find something

Daniel Tobias19:01:27

im going to try adding in output-to and output-dir

Daniel Tobias19:01:31

NVM it didnt like those keywords haha

Daniel Tobias19:01:40

it's like this stuff is designed to be as cryptic as possible


did you try maybe asking in the #figwheel-main channel, i think somebody with more experience than me will be able to help you (and wife is screaming at me now 8:30 pm now :D)

Daniel Tobias19:01:52

ok ill ask there, ty


What is here wrong ?

(defn my-update-in [m ks f args]
  (assoc m ks (apply f (get m ks) args)))

(my-update-in p [:1] :age inc)
error :
; Execution error (IllegalArgumentException) at chapter5/my-update-in (form-init95645667318631163.clj:51).
; Don't know how to create ISeq from: clojure.core$inc


you specify f before args, then :age before inc


also (get m ks) is weird - it's as if you expect the whole seq of keys to be one key


neither :age nor inc are collections, so neither works as a last arg to apply


that last call needs to be outside the [] binding block


the syntax of let is (let [binding value ... ...] body) - it's usually a logic error not to provide a body, and it's a compilation error to have a binding without a value (or visa versa)


you mean like this :

(defn my-update-in [m ks f & args]
  (let [[k & ks] ks]
  (assoc m k (apply f (get m ks) args))))

(my-update-in p [:1] assoc :name "James" :age 35)


that does this :

{:name "James", :age 26, :1 {:name "James", :age 35}}


and not updating the value


Im not getting what you want to achieve there. Update-in work with nested maps. And ks is supposed to be a list a key of your map. What do you want to specify with :1 ?