tools-deps

Discuss tools.deps.alpha, tools.build, and the clj/clojure command-line scripts! See also #depstar #clj-new
2021-03-26T10:10:26.208800Z

I just ran into a small issue with org.clojure/tools.namespace, where when used in a deps.edn project would over-zealously by default load namespaces found in ~/.gitlibs. Presumably because prior to tools.deps it was assumed deps found on the filesystem were most likely to be source code in your project and suitable for loading. Would it make sense for tns to now by default ignore any paths found in ~/.gitlibs?

2021-03-26T10:11:45.210100Z

Incidentally this is easily fixed by explicitly setting tnsrepl/set-refresh-dirs, but it did cause a colleague to get a very misleading stacktrace about a missing class from a namespace that his project wasn’t explicitly requiring.

2021-03-26T10:13:24.211200Z

I should add that they likely weren’t even fully aware they were using tns, because they were using integrant.repl/reset (which uses it)

alexmiller 2021-03-26T10:25:00.212500Z

I don’t understand - can you explain a repro in an ask.clojure question?

seancorfield 2021-03-26T16:46:59.217100Z

Cognitect’s test-runner seems to be accumulating issues and PRs without getting any feedback from Cognitect. Is it just considered “done” or just very low priority right now I wonder? I was thinking it would be really nice to have a -X entry point so that folks could leverage :exec-args and, in particular, their ability to merge across aliases so you could specify generic options via your :test alias (or :runner alias, in my case) and then specific options in other aliases. This would clean up a bit of boilerplate in our monorepo scenario where subprojects all have aliases but we still need to specify --dir via the command-line (since :main-opts don’t merge — just last-one-wins).

seancorfield 2021-03-26T16:48:18.218100Z

Luckily the test function in cognitect.test-runner is public so writing a tiny :exec-fn wrapper outside the runner is easy to do for now.

alexmiller 2021-03-26T17:01:30.218500Z

Just waiting for a cycle of attention

seancorfield 2021-03-26T17:02:23.219200Z

I’ll write the wrapper in our codebase for now and maybe submit a PR if/when test-runner gets an attention cycle.

alexmiller 2021-03-26T17:43:03.219500Z

Go for it!

borkdude 2021-03-26T18:30:20.220200Z

The test runner is working well for me

borkdude 2021-03-26T18:32:24.220700Z

@seancorfield I'd love to see an example invocation that is "better" with -X than with the -main function

seancorfield 2021-03-26T18:34:55.222500Z

We have a test alias for each subproject that brings in the test code and dependencies for that subproject. Via -X we can specify :exec-args {:dir #{"subproject/test"}} which will merge with our :runner alias which already has :exec-fn and the default :exec-args.

seancorfield 2021-03-26T18:35:43.223400Z

With -M, :main-opts do not merge so we either have to repeat the whole :main-opts for every subproject -test alias with just -d changed, or we have to specify -d on the command-line.

borkdude 2021-03-26T18:36:22.224500Z

so now you have to write another alias for every -d change?

seancorfield 2021-03-26T18:36:31.224900Z

Before:

$ clojure -M:defaults:subproj:subproj-test:test:runner -d subproj/test
After:
$ clojure -X:defaults:subproj:subproj-test:test:runner

borkdude 2021-03-26T18:37:55.225700Z

@seancorfield Do you store these long invocations in some separate bash script or Makefile? Or do you remember them from the top of your head?

borkdude 2021-03-26T18:38:24.226500Z

I'm currently considering a task runner which is supposed to solve this problem (of not having to remember these things)

borkdude 2021-03-26T18:38:48.227300Z

This is why I am curious about these use cases

seancorfield 2021-03-26T18:38:59.227600Z

We have a build shell script that turns build test subproj into the above command. But now that we have a primary deps.edn file at the top of our monorepo, it’s easy enough to run most things with the CLI directly (for single command invocation).

seancorfield 2021-03-26T18:39:39.228500Z

The build script supports multiple commands so we could say build tests subproj1 subproj2 and it runs two clojure commands.

borkdude 2021-03-26T18:40:05.229200Z

The example after -X is still pretty long, too long for me to remember without a bash history probably

borkdude 2021-03-27T20:44:26.242600Z

Just as an example: https://github.com/borkdude/antq/blob/bb.edn/bb.edn (ported from this Makefile: https://github.com/borkdude/antq/blob/bb.edn/Makefile)

2021-03-27T23:27:19.243800Z

This makefile is bad

2021-03-27T23:28:46.244Z

Like, the whole deal about makefiles is it tracks dependencies between files and has tasks that generate files

2021-03-27T23:29:51.244200Z

This make file has a target named 'pom' that is used to generate the file pom.xml

2021-03-27T23:30:21.244400Z

Which has no dependencies (like maybe on deps.edn?)

2021-03-27T23:30:31.244600Z

Gross

2021-03-27T23:35:28.244800Z

This task dsl is gross too. To impose a restrictive dsl without getting anything out of it (like dependency tracking) is silly. If you aren't doing extra stuff (dependency tracking, staleness tracking, rebuilding, etc) the just use normal clojure functions

2021-03-27T23:36:19.245Z

You want give some bit of functionality a name, and call it, we have defn for that

borkdude 2021-03-27T23:40:44.245200Z

This isn't my makefile btw, I just scouted some makefiles in the wild, and what I mostly see is that people just use it as a way to quickly invoke it from the command line. It's clear that you don't see the value of this, that was already clear in our earlier conversation. Thanks for the feedback.

borkdude 2021-03-27T23:41:20.245500Z

I do want to consider tracking, etc, like make does, it's done done yet

borkdude 2021-03-28T10:27:21.248200Z

Now ported the tasks to normal functions: https://github.com/borkdude/antq/blob/bb.edn/script/tasks.clj The code longer, but more flexible, so that may the way to go indeed. Tasks can be discovered using (maybe warrants a bb dir CLI option) :

$ bb -e "(require 'tasks) (clojure.repl/dir tasks)"
clean
coverage
deploy
docker
docker-test
install
jar
jar-file
lint
outdated
pom
repl
standalone-jar-file
tests
uberjar
Tasks can be invoked using:
bb -m runner/coverage
Docs:
$ bb doc tasks/coverage
-------------------------
tasks/coverage
([])
  Run test coverage.

seancorfield 2021-03-26T18:40:24.229700Z

We’re not going to invest more work in pipelining this stuff until we’ve seen tools.build released.

seancorfield 2021-03-26T18:41:29.230600Z

I’m anticipating being able to replace our build shell script with a tools.build invocation 🤞:skin-tone-2: 😸

borkdude 2021-03-26T18:42:28.231Z

I don't know what tools.build is, nor spec2 ;)

borkdude 2021-03-26T18:43:01.231200Z

But I hope they come out soon ;) 🔮

seancorfield 2021-03-26T18:47:17.232700Z

Based on what Alex has said publicly about tools.build, I would expect it to include “task runner” functionality (and some “standard” tasks). ISTR he’s already mentioned that it will add Java compilation as a task?

2021-03-26T19:46:04.234300Z

Why would you ever not have a history?

borkdude 2021-03-26T19:47:17.234500Z

That can happen when I switch systems yes, I have multiple laptops. But even then, fetching from history comes up with similar invocations and not always the one I'm looking for right away, unless I remember it more or less correctly. Hence, something like a task runner (something like make) could be nice

borkdude 2021-03-26T19:49:11.234800Z

But also for making these invocations known to colleagues, contributors, etc, you don't want to depend on history

2021-03-26T20:03:19.235Z

maybe; I am skeptical of lot of this additional tooling stuff. shells already support most of these things

2021-03-26T20:03:39.235200Z

everything goes in the history

2021-03-26T20:03:57.235400Z

support running all kinds of things, background jobs, etc

borkdude 2021-03-26T20:04:27.235600Z

you don't write any docs for your colleagues how to invoke the tests like Sean showed? I would have a hard time figuring that out by only looking at deps.edn

2021-03-26T20:04:30.235800Z

it is already the case that I almost never type a command in full into my shell, I pull it out of history and maybe edit it

2021-03-26T20:04:55.236Z

if you write docs then you already may as well just share the long command

2021-03-26T20:05:17.236200Z

"paste this into your shell, and it will run the tests"

borkdude 2021-03-26T20:05:20.236400Z

if you do document this, you might as well make those docs executable somehow

borkdude 2021-03-26T20:05:38.236600Z

yeah, that's usually how I've done it so far

2021-03-26T20:05:40.236800Z

I mean, I work with sean

borkdude 2021-03-26T20:07:08.237Z

Lucky you ;)

2021-03-26T20:08:09.237200Z

yeah, I mean, he does a lot of work on the tooling, so documentation wise it is way more likely to be written for me then by me :)