Fork me on GitHub
#beginners
<
2021-07-23
>
Chandru03:07:18

I’m trying to use a deps.edn file to compile CLSJ as a bundle. My deps.edn looks like this:

{:deps {org.clojure/clojurescript {:mvn/version "1.10.758"}}
 :asset-path "src"
 :target :bundle
 :optimizations :advanced
 :output-to "main2.js"}
anyone know why the compiler shows this warning?

dpsutton03:07:05

Because deps isn’t a valid compiler option. You really shouldn’t merge those two files

dpsutton03:07:37

Those compiler options never go in the deps edn file in the examples.

dpsutton03:07:39

from - Create a deps.edn file the following contents: - In order for this to work we need to set a couple of compiler options. Create a build.edn file with the following: and then invoke with clj -M -m cljs.main -co build.edn -v -c -r note -co uses a bespoke file build.edn and doesn't try to repurpose the deps.edn file.

Chandru04:07:31

Oh okay! Thank you very much!

zackteo08:07:12

Not sure if this is a stupid qn but does lein uberjar take everything inclusive of what is being used in the /resources folder and package it into a jar? Meaning any .csv and even .py I might be calling with shell/sh

delaguardo08:07:21

yes, everything, unless you explicitly filter some files out using :uberjar-exclusions

zackteo08:07:54

Thank you!

zackteo08:07:52

On that same note, are there any guides you recommend to compile a leinigen backend and shadow-cljs frontend? And dockerise the solution?

delaguardo08:07:03

is your backend serving the assets compiled by shadow-cljs?

delaguardo08:07:29

asking because there is no silver bullet ) every situation is unique and requires some special care

zackteo08:07:12

Not to my knowledge. Currently am using a separate project.clj for the backend and separate shadow-cljs.edn for the frontend

delaguardo08:07:56

then I would recommend to read at this link - https://shadow-cljs.github.io/docs/UsersGuide.html#release understand what artifacts will be generated for production usage then general advise - split your docker image preparation into stages: • generate your client assets • build uberjar with those assets included • add uberjar to some thin image with jdk. An entrypoint could be something like java -jar /path/to/uber.jar

zackteo09:07:51

Would this only be for the frontend? Or is this if I use shadow-cljs for both frontend and backend? o: (Am only aware I can use project.clj for both)

delaguardo09:07:25

idk, nether used shadow-cljs for backend

tws15:07:19

a jar file is basically a zip file, you can inspect it and see yourself. on my BSD system, tar works. tar xvf foo.jar | grep *.py

noisesmith19:07:13

> Meaning any .csv and even .py I might be calling with shell/sh these will end up in the jar if they are on the calculated classpath (eg. inside the resources/ directory with a default setup), but for shell/sh to provide the document to an OS process it needs to be copied out of the jar into a location the process can use (eg. by spitting it to a file, or providing its contents to stdin etc.)

practicalli-john15:07:25

I am curious what logging libraries people recommend or prefer. For context, I'm creating a new Clojure CLI project that will be a rest api with reitit and dynamodb and deployed on AWS Fargate (so logs will end up in cloudwatch) The common options seem to be • clojure.tools.logging and logback • Timbre • BrunoBonacci/mulog I would prefer to send logs as data rather than strings and minimising dependencies is always preferable. Thank you.

practicalli-john11:07:09

I decided to go with mulog for the logging of the new application and very happy with it so far. Its been very simple to use in the repl and wire up to the application with Integrant and Integrant REPL

hiredman16:07:41

if you want minimal dependencies something like https://gist.github.com/hiredman/64bc7ee3e89dbdb3bb2d92c6bddf1ff6 might be a nice start. it uses the built in java logging stuff and has an api (macros for different log levels) vaguely similar to tools.logging

hiredman16:07:44

I've only played around with the above, not used it at work. At worked we use clojure.tools.logging and log4j2, after migrating off of timbre

hiredman16:07:11

(I believe these days logback is seen as deprecated in favor of log4j2)

indy16:07:35

Yup we use https://github.com/gja/clj-log4j2 and it has served us well for quite a long time. Just plain old log4j2 and some macros as done in the lib work quite well. Easy to roll one's own like hiredman's gist.

roelof17:07:52

how can I solve this one :

(ns rich4clojure.elementary.problem-4
  (:require [hyperfiddle.rcf :refer [tests]]))

;; = Intro to Lists =
;; By 4Clojure user: dbyrne
;; Difficulty: Elementary
;; 
;; Lists can be constructed with either a function or a
;; quoted form.

(def __  '(:a :b :c))

(comment
  
  )

(tests
 (list __) := (quote (:a :b :c)))

;; Share your solution, and/or check how others did it:
;; 

roelof17:07:30

the answer is :a :b: :c but def cannot hold that much data

seancorfield17:07:06

Perhaps it is a bug in the test? The rich4clojure project is brand new and some of the auto-translated examples might be buggy...

roelof17:07:34

I do not thinnk so. on 4 clojure the same code and there my solution :a :b :c works @seancorfield

seancorfield18:07:34

What I mean is that rich4clojure isn't working the same way as 4clojure used to. It looks like 4clojure used to just do string replacement on __ so you could enter a solution of :a :b :c and it would work. You can't def __ to that in Clojure (as you have observed) so this is a case where the rich4clojure translation is not working the same way.

seancorfield18:07:01

user-forms is a string built from the forms in the solution box -- so when you type :a :b :c into the solution box, it reads three forms (`:a`, :b, and :c) and then turns them back into strings, joins them with spaces so it has ":a :b :c", and then it just substitutes that for the string "__" in the test code (a string), and then reads the result and evaluates it...

pez21:07:10

Thanks! I’ll probably need to change some of the problems to adapt for how the tests now work.

seancorfield21:07:57

Problem 4 is definitely a bit weird. I don't know how many others assume multiple input forms...

roelof08:07:37

I think problem 6 has the same problem

pez09:07:31

It's probably in the low numbers we find this. Please file issues about it.

roelof09:07:44

@pez 4 issues I made already and I stop now because Im going on holidays for 2/ 3 weeks

pez09:07:45

As you deserve! Have a blast!

roelof09:07:21

we hope, as we look at the weather expectations we get 2 weeks rain. and that is not fun with camping with a tent

roelof10:07:24

@pez thanks for solving the first issues. I will test them after im back from the holidays

pez19:07:34

I think for the other issues it is more about that the user needs to read the README a bit careful. I have pushed an update to the readme where it is a bit more clearly stressed that all problems cannot be solved by redefining __,

roelof19:07:23

not all there is one possible namespace problem in it I think

roelof18:07:44

oke, thanks

Christopher Gsell20:07:11

Hello I am using shadow cljs and I’m importing an npm library. For some reason, the import works on the node-repl, but when I import in the namespace using (:require [“…” :as …]) and try to use it I get that it’s not a function

sova-soars-the-sora21:07:57

You did npm install ... and it works on the REPL but not in a file?

Christopher Gsell23:07:42

Correct. It works in shadows repl but not the file.

Christopher Gsell23:07:00

For the file, I get a JS object when importing but I can’t run the same functions on it- ie I get a “not a function” error

jaju02:07:47

This — (:require ["…" :as …]) will work only within the (ns …) block. Notice that :require is not a function that can import dependencies on its own, but a keyword - the ns form understands it. In standalone mode, you need to use require (notice - not a keyword). Again, I don’t do CLJS much so there may be quirks, but that is the idea.

jaju02:07:47

When I say standalone, I meant top-level form that stands on its own.

Christopher Gsell03:07:39

Right yeah so in the repl I did the function (require ‘[“…” :as x] ) and then in the file i did (:require [“…” :as x]). They should import the same thing but they did not

jaju03:07:46

Not sure I understand the “did not import the same thing” part. Did one of them work?

Christopher Gsell03:07:55

Yes the repl one worked and I can call the appropriate api functions, but the file one did not. While it imported a JS object, I cannot call the same functions on it.

jaju03:07:38

The file version - where are you calling (:require…)? Inside the top-level (ns… (:require ["…" :as …]) or by itself?

Christopher Gsell03:07:36

Yeah it’s inside the namespace declaration

jaju03:07:17

Got it. Is there any more context you can provide? More code in the context of evaluation, or relevant parts of the error you see in the logs?

Christopher Gsell04:07:19

Yeah sure. So in the shadow node-repl, I write (require '["@babajidemm/african-countries-api" :as x])

Christopher Gsell04:07:37

Then I write (.. x (byName "Algeria") -body toString) and get the proper body response

Christopher Gsell04:07:17

In the file namespace, I write: (ns african-countries.data (:require ["@babajidemm/african-countries-api" :as africanCountriesAPI])) (defn getCountryByName [] (let [info (.. africanCountriesAPI (byName "Algeria") -body toString)] (js/console.log info)))

Christopher Gsell04:07:16

I call this function, get this error twice: Uncaught TypeError: module$node_modules$$babajidemm$african_countries_api$index.byName is not a function at Object.african_countries$data$getCountryByName [as getCountryByName] (data.cljs:9) at eval (views.cljs:24)

Christopher Gsell04:07:10

Lastly, this is important: It works in the node-repl but not in the browser-repl. In the browser-repl I get an error that says: "Execution error:  "Module not provided: ./v1/lib/CountriesService"

jaju04:07:21

Ok - I tried something and I don’t think I have a good answer for you. But the library you mention did not work for me in the “browser” REPL, and worked fine in “node”. Node was fine both repl and file

jaju04:07:54

Ah - posted at the same time. It could be that the module format of the @babajidemm/african-countries-api isn’t supported in browsers and needs some special handling for browsers. You may find better support in the #clojurescript channel I think - a more focused group for cljs.

Christopher Gsell17:07:34

Thank you @U06KGH6LB, I think you're right. I think the difference is the module is build for a backend node process

👍 3
Christopher Gsell20:07:50

Is there a difference in importing in the repl vs the namespace besides the syntax?

noisesmith19:07:18

the namespace :import clause is just a syntax for what import does at the top level, both work in a file or a repl (though for obvious reasons you are more likely to have a carefully crafted ns clause in a file)

noisesmith19:07:09

in fact the list of things that are different between file and repl in clojure are extremely small (unless you count conventions / coding style differences, that's a much bigger list)

Rob Haisfield22:07:29

I find myself pretty frequently writing a predicate, receiving some trues, nils, and falses, and then wanting to get the values that returned one of those values. Is there an easy way to consistently do that? My hacky solution is to grab the indexes of those values and then the nth function on the results of the query but maybe there’s a better way

dpsutton22:07:36

(let [{matched true} (group-by even? (range 10))] matched)

4
Rob Haisfield22:07:38

Awesome, thank you so much!

Cora (she/her)22:07:54

could you (filter pred coll) ?

Cora (she/her)22:07:11

and just make the pred return a truthy value for what you're looking for

Cora (she/her)22:07:01

don't get me wrong, I love me some group-by, and it's possible I'm not understanding the question

ghosttoaster22:07:06

I'd like to use a namespace in the https://github.com/zk/clojuredocs/blob/master/src/clj/clojuredocs/data/import.clj source code, but its not exactly a library (there is no maven/artifactID or version number). Is it possible to use their repo as a dependency anyways? Or should I just borrow/extract the code I want and turn it into a library?

alpox22:07:57

@corasaurus-hex I had it before that I wanted them both at the same time - truthy and falsy - but in a different list. I was very happy about group-by then because I didn't have to do an extra iteration.

Cora (she/her)22:07:58

@cdimara I think that's all in a comment so you'd have to pull it out of there?

ghosttoaster22:07:53

oops yeah. didn't even notice that comment block. gonna have to pull it out...

ghosttoaster22:07:09

If it weren't in a comment expression would using a source file from a non-library be possible?

Cora (she/her)22:07:19

I'm honestly not sure, I think deps.edn has some git support but I think that's still library and project based and not individual files.

seancorfield22:07:31

@cdimara If you're using deps.edn and the Clojure CLI (rather than lein) then you could have a git dependency on the http://clojuredocs.org source code and then you could reference its namespaces in your code.

bubblebobble 2
seancorfield22:07:37

However, https://github.com/zk/clojuredocs is a Leiningen project so you'd have to override that in deps.edn (`:deps/manifest :deps`) and then you would also need to explicitly specify in your deps.edn file, the dependencies from clojuredocs' project.clj file.

seancorfield22:07:53

So it's possible but non-trivial for some older projects...

ghosttoaster22:07:50

what would be the artifactID/version number if there's no .pom?

seancorfield22:07:03

You use a git dependency instead.

seancorfield22:07:20

(! 658)-> cat deps.edn 
{:deps {io.github.zk/clojuredocs {:git/url "" :sha "28f5ee500f4349039ee81c70d7ac40acbb19e5d8" :deps/manifest :deps}}}

gotta_go_fast 4
seancorfield22:07:13

Although in this case the checked out repo doesn't have the right structure to be able to require clojuredocs.env -- b/c it doesn't match the default (and we had to override the manifest type).

seancorfield22:07:00

A big plus of the CLI and deps.edn is to be able to use repos from GitHub and GitLab directly without them needing to be deployed to Clojars or Maven.

💯 2
seancorfield23:07:26

For example: https://github.com/clojure/tools.build -- it has "releases" but they are only tags on GitHub -- it doesn't exist on Maven or Clojars -- but you can see in the README how to depend on a specific tagged release from GitHub directly.

2
ghosttoaster23:07:52

You said "the checked out repo doesn't have the right structure to be able to require clojuredocs.env " Whats wrong with the structure?

ghosttoaster23:07:30

If you make the :path ["src/clj"] the folders match the namespace.

seancorfield00:07:23

Yes, but you shouldn't edit the checked out repo -- you should pretend it is immutable -- otherwise it won't work on someone else's machine.

ghosttoaster00:07:39

Thank you Sensei Corfield!

Cora (she/her)22:07:21

@alpox that's the ideal situation for group-by 😄

Cora (she/her)22:07:01

but if you're just looking for all the values that return one of the results of the predicate, a filter would work out a little better

2
ghosttoaster22:07:37

@corasaurus-hex I could see a situation where you want to see all of your values but you don't want to produce the results.

Cora (she/her)22:07:15

I'm sorry, I don't think I understand what you mean by that

Cora (she/her)22:07:23

could you talk about it a little more?

ghosttoaster22:07:03

So, say you had a bunch of input say a vector of unknown numbers.

ghosttoaster22:07:19

And your predicate was even?

ghosttoaster22:07:20

if you do the group-by you get your results and they're labled by the result of your predicate.

ghosttoaster22:07:50

you can do destructuring and hold on to your results forever.

Cora (she/her)22:07:27

sure, definitely

Cora (she/her)22:07:53

but also if I don't need the other ones then I'm making a list of the other values, and a hashmap, for no reason, and obscuring what I'm doing by adding details I don't need

ghosttoaster22:07:46

yes. Thats if you don't need the other values.

Cora (she/her)22:07:50

(let [{matched true} (group-by even? (range 10))] matched) is a lot more complex than (let [matched (filter even? (range 10))] matched)

Cora (she/her)22:07:04

that's what it all hinges on, and how I read the original question

ghosttoaster22:07:08

But if you need them both AND you want to inspect a few, group-by allows you to do that work just once.

Cora (she/her)22:07:08

but I wasn't sure

Cora (she/her)22:07:22

I think we're on the same page ☺️

2
Cora (she/her)22:07:56

it's fine if you don't want to

Cora (she/her)22:07:06

it sounds like you're working on this whole import library situation