Fork me on GitHub
#clojure
<
2022-11-25
>
dabrazhe10:11:23

On teaching Clojure to kids. What do you recommend as a low-entry drawing/animation library for young teens? We have already tried maria.cloud, but there are a bunch of issues that prevent us from going forward. Ideally, I would like to have smth with minimal installation, like babashka, but I did not find a good drawing lib. Most kids are using Windows. Installing Java and lein on Windows is a chore for them : )

borkdude10:11:06

Can you expand on why Maria isn't working for you? It was kind of designed for this setting I think. cc @U07SQTAEM @U050RLRRQ

3
dumrat10:11:53

@U96LS78UV Does quill work with babashka?

dumrat10:11:30

If you can get past the setup stuff, quill is straightforward I think

borkdude10:11:27

quill runs in the browser right? I think one could make a quill playground with SCI like it's done here for reagent / re-frame https://babashka.org/scittle/codemirror.html

dumrat10:11:49

@U04V15CAJ yeah forgot that quil had this. I only used from Clojure.

mhuebert11:11:42

as we are midway through a new implementation of Maria.cloud, definitely interested in what issues we could resolve

craftybones11:11:42

scittle with quill will be genuinely amazing and something I’d be interested in.

borkdude11:11:47

@U8VE0UBBR you could fork scittle, add quill as a plugin and publish @U8VE0UBBR/scittle-quilll on npm if you want

🤯 1
borkdude11:11:54

then people can also use it on http://codepen.io :)

dabrazhe11:11:04

@U04V15CAJ Maria.cloud has a rathe awkward interface they struggle with. But mostly saving, having a real repl, I can elaborate if some wants

borkdude11:11:09

Perhaps setting up Calva + the dependency for them would be easiest. calva works without any further installation of clj tools, since it uses deps.clj as a fallback

dabrazhe11:11:30

I looked into quill, it seems to be the the Plan B. Still looking for smth simpler.

dabrazhe11:11:45

Please mind that installing Java is already a bridge too far for some )

dabrazhe11:11:38

I thought you need to install java + lein on Calva as well?

borkdude11:11:47

If those things are too hard, maybe clojure will also be too hard. I'm not an expert in these children playgrounds. Perhaps Dr. Racket has something?

borkdude11:11:05

you don't need to install lein if you use deps.edn - then it uses deps.clj as an automatic fallback

dabrazhe11:11:36

I keep wondering if CLJ is indeed to complex for them. But most of them have a grasp of it after 4 lessons. Would be a shame to drop it now.

craftybones12:11:14

One simple hack is to use p5.js with scittle. Invoke the drawing parts as js/rect and js/fill….

robertfw19:11:17

Everything I've heard is that people with no pre-conceptions about programming tend to take to Clojure fairly easily, if you can get past the initial setup bumps

✔️ 1
💯 1
1
Adam Kalisz13:11:28

Is it possible to avoid writing what amounts to ~1 KB string to a file and instead give the Writer that expects a file handle something that is completely in memory such as a stream backed by a var or something? I currently have this ugly thing taking Prometheus metrics from HikariCP:

(let [f (File/createTempFile "hikari-metrics" ".txt")
      _ (with-open [w (io/writer f)]
          (TextFormat/write004 w (.metricFamilySamples (CollectorRegistry/defaultRegistry))))
      out (slurp f)]
  (.delete f)
  out)
It works, but it really is quite ugly and likely has edge cases I cannot forsee.

Mark Wardle14:11:44

Can you use a StringWriter?

Adam Kalisz14:11:59

I am not sure, how do I find out? I have this solution that kind of does what I want, but I am ready to learn an even better approach.

(with-open [baos (ByteArrayOutputStream.)
            w (io/writer baos)]
  (TextFormat/write004 w (.metricFamilySamples (CollectorRegistry/defaultRegistry)))
  (.close w)
  (.toString baos StandardCharsets/UTF_8))
This really wasn't obvious to me.

Mark Wardle14:11:55

Well from memory.... (let [writer (StringWriter.)] (TextFormat/write004 w xxxxx) (.toString writer). You don't need to bother closing a StringWriter and just get the contents after the write.

Mark Wardle14:11:29

clojure's io/writer is fine for many purposes, but not sure it can write to a string, so just use java interop and create a stringwriter yourself and pass it whereever you want a Writer?

Mark Wardle14:11:16

e,g. (defn write-004-to-string [mfs] (let [w (.StringWriter.)] (TextFormat/write004 w mfs) (.toString w)))

Mark Wardle14:11:53

or (-> (http://java.io.StringWriter.) (TextFormat/write004 mfs) (.toString)) as a one-liner 😉

Adam Kalisz14:11:00

Unfortunatelly, that doesn't seem to work. The TextFormat/write004 returns nil when used like that. The writer wrapped ByteArrayOutputStream works. 🙂

Mark Wardle15:11:27

Write004 looks as if it will always return nil. You have to return .toString on your writer?

Mark Wardle15:11:02

Otherwise I’m not sure sorry!

Mark Wardle15:11:39

This works for me.... (let [writer (.StringWriter.)] (.write writer "Hi there") (.toString writer))

Adam Kalisz15:11:02

Ah, yes. Sure.

(let [sw (StringWriter.)
      _ (TextFormat/write004 sw (.metricFamilySamples (CollectorRegistry/defaultRegistry)))]
  (.toString sw))
works

👍 1
Adam Kalisz15:11:51

It is also very slightly faster. Thank you for the help and patience!

sheluchin19:11:39

https://clojure.org/reference/deps_and_cli#find-versions can take a :lib value. What are the possible paths for obtaining this value?

Alex Miller (Clojure team)19:11:32

there is no magical source - it's either a Maven groupId/artifactId or a git id per https://clojure.org/reference/deps_and_cli#_coord_attributes

Alex Miller (Clojure team)19:11:46

so org.clojure/data.json or io.github.clojure/tools.build for example

Alex Miller (Clojure team)19:11:32

I have built some experimental "search" type functionality for this but it is pretty magical and gross

sheluchin19:11:28

Would parsing the classpath for these values be a reliable means of getting them?

sheluchin19:11:19

I suppose that strategy doesn't work because git libs get translated to some ~/.gitlibs/libs/* path, which doesn't communicate anything about inferred repo URL, so there's no way of knowing the which of the lib formats to use.

Alex Miller (Clojure team)19:11:42

Well if you have the libs in an existing deps.edn that would be an existing non magical source

Alex Miller (Clojure team)19:11:19

clj -X:deps list will show you those

sheluchin20:11:09

Thanks very much, @U064X3EF3. That's about all the info I need about this at the moment.

Alex Miller (Clojure team)00:11:17

if you clj -X:deps list :format :edn you get a lot more info in the lib map that is returned (map of lib to coord). if you filter just the coords that have empty :dependents, everything left is a top level dep, ala (reduce-kv (fn [ls lib coord] (if (seq (:dependents coord)) ls (conj ls lib))) [] libs)

sheluchin22:11:32

Thanks, @U064X3EF3. That is very helpful. It still requires downloading the deps, but I'll create a request for that.

Dan Boitnott20:11:06

I've defined this utility function but I can't help thinking there's a more idomatic way to do this:

(defn and-then>>
  "Returns (true-fn v) if v is truth-y otherwise returns v."
  [true-fn v]
  (if v (true-fn v) v))
My use case looks like this:
(->> pairs
       (remove (fn [[_ v]] (#{"NONE" "NO"} v)))
       (map (fn [[k v]] (str (-> k name (str/replace "_" " ") capitalize-words) ": " v)))
       (map li)
       seq
       (and-then>> ul))
The idea being that if the seq after that last map is empty we'll get nil but if it has items they'll be wrapped by the ul function. AND..... just answered my own question. I was looking for the some->> macro:
(some->> pairs
       (remove (fn [[_ v]] (#{"NONE" "NO"} v)))
       (map (fn [[k v]] (str (-> k name (str/replace "_" " ") capitalize-words) ": " v)))
       (map li)
       seq
       ul)

enn20:11:44

some->>?

Dan Boitnott20:11:58

LOL. JUST saw that and updated my message. Thanks!

peterh21:11:23

Nice, I’ve never seen this function before, but I am sure I will get some good use out of it as well.

sheluchin22:11:50

Is there any way to compute a classpath without downloading all the deps?

Alex Miller (Clojure team)22:11:06

logically, yes (you should be able to do it only by downloading pom files which provide the dep info), but that is not an option provided by tools.deps

Alex Miller (Clojure team)22:11:59

if you'd be interested in such a thing, a request at https://ask.clojure.org would be the place to put it (but would help to understand the use case more)

sheluchin23:11:20

@U064X3EF3 I'm asking this as a bit of an xy problem. Please give me a moment to clarify. What I'm really after is for a way to identify what deps a project is using without creating the project's runtime or downloading all of its dependencies. I want this information to make it easier to link projects together for my Clojure code explorer project. At the moment, I depend on grepping deps.edn for specific dependencies, and then matching ns+fn usages in the dependent project to ns+fn definitions in the dependency. It works, but not great. I think that if the list of :libs could easily be exported for a given project without downloading deps or creating a runtime, we could get this information included in clojure-lsp's output -- maybe even in clj-kondo, and it would provide for better linkability between projects in the Clojure ecosystem. Do you think this is worth submitting a request, or should I explore other angles?

Alex Miller (Clojure team)23:11:54

Only the top level dep info is actually in the project. To get full transitive deps, you need to interrogate other sources.

Alex Miller (Clojure team)23:11:59

If you’re just looking to do something like -X:deps list but download only metadata, not jars. I think that could be added pretty easily

sheluchin23:11:50

Great. Thanks for your input!