tools-build

practicalli-johnny 2023-01-26T16:32:58.413759Z

Do I have to create a build.clj file for every project I want to use tools.build with to create a jar or uberjar package? Is there a common default I can use to or a package that provides such a thing? Or is tools.build only for creating a custom build each time? Given the tools.build project describes itself as a programmatic approach and I would prefer a declarative approach, I am not sure if tools.build is something relevant. Ideally I just want to run something like clojure -T:project/uberjar or clojure -T: project/build uberjar and I get a defacto .jar file I dont have any requirements to tailor the build and would prefer something consistent across all projects (until I find an exceptional case where I need to do something different)

seancorfield 2023-01-26T16:44:15.518459Z

That was the original concept behind my build-clj wrapper but in reality, every project seems to be just slightly different enough that I added knobs & dials to it to try to accommodate that -- instead of pushing back and using tools.build in the first place. That said, when I've updated deps-new's templates to use raw tools.build and dropped the build-clj wrapper from those, the generated projects will be as close to "stock" uses of tools.build as possible as a starting point.

seancorfield 2023-01-26T16:51:01.160009Z

An example, for uberjars, is whether you have transitive dependencies on log4j2 and whether those deps include formatting plugin caches -- if so, you need a log4j2 conflict handler for the uber tasks.

Alex Miller (Clojure team) 2023-01-26T16:52:24.573529Z

the examples in https://clojure.org/guides/tools_build are meant to be "typical" starting points. in reality, most projects start the same (but rarely end the same). a "declarative" approach (like maven/lein) leads to 1000 knobs to cover all the deviations

seancorfield 2023-01-26T16:55:02.589879Z

Yup, this point_up::skin-tone-2 build-clj was meant to be "so simple it could be used from the CLI" but the reality is that just doesn't work for "most" projects.

borkdude 2023-01-26T16:56:11.370879Z

@jr0cket You can run neil add build in your project to get a reasonable default. See https://blog.michielborkent.nl/new-clojure-project-quickstart.html It adds a build.clj and add tools.build to the :build alias. This can be done in any existing deps.edn project. I just figured that I can update the build.clj file to add an uber function too.

seancorfield 2023-01-26T16:57:17.316329Z

build.clj for a library JAR and for an application JAR are pretty different and you generally only want one or the other.

borkdude 2023-01-26T16:58:42.588879Z

(oh never mind, neil add build already gets you to clojure -T:build uber by default)

Alex Miller (Clojure team) 2023-01-26T17:04:33.469549Z

yeah, I think neil is a good approach to bridge here

practicalli-johnny 2023-01-26T17:06:03.300139Z

Ah, I did find notes about seancorfield/build-clj and that would be useful, but sounds like its being decommissioned like depstar. So I have something to think about. Sounds like my preferred approach isnt going to be realistic, so will have some hammoc time about it some more and how (if at all) this can be added to the practicalli config. For now I'll remove the old packaging aliases from practicalli/clojure-deps-edn and leave it up to people to figure this stuff out in a project deps.edn or another tool approach.

seancorfield 2023-01-26T17:07:41.979149Z

Both depstar and build-clj evolved beyond their initial "simple wrapper" starting points to include far too many knobs & dials -- because no two projects are alike, as soon as they move from their initial starting point.

seancorfield 2023-01-26T17:09:13.156829Z

It would be nice if some basic "create new project" and "add build file" features were included in the CLI -- but even then you have library projects and application projects being quite different from the get-go and they quickly diverge from there... so I'm not sure what the best answer is...

borkdude 2023-01-26T17:09:45.187409Z

I've also noticed this project: https://github.com/liquidz/build.edn but I've never used it. The idea, I think, is to make build.clj declarative again, but it might suffer from the same "wrapper" limitation

seancorfield 2023-01-26T17:09:53.713709Z

Even hearing that neil add build adds a build.clj that caters for both library jar and application uber seems unnecessary complexity for someone just trying to get started.

seancorfield 2023-01-26T17:10:16.605819Z

It's a really hard problem to solve correctly...

borkdude 2023-01-26T17:10:19.116529Z

@seancorfield Well, you don't have to use the uberjar function, you can just let it sit there or remove it :)

seancorfield 2023-01-26T17:11:03.542859Z

Sure, but someone new to all this will tend to look at the build file and want to understand all of it -- and wonder why "half" of it isn't relevant to their project 🙂

seancorfield 2023-01-26T17:12:18.274699Z

Historically, I've found that running tests in "real" projects tends to get beyond just clojure -X:test pretty quickly so I've ended up always adding testing to build.clj -- multi-version testing, doc example testing, Clojure & ClojureScript cross-platform testing, etc.

practicalli-johnny 2023-01-26T17:13:00.104949Z

I'll write up some options about tools.build in Practicalli Clojure book instead of trying to shoe-horn in some user aliases that have external requirements I was looking at liquidz/build-edn and think its a nice alternative for project configuration (not so easy for a user alias though as it still needs a build.edn flle) I guess I have just relied on depstar for way too long... 🙂

seancorfield 2023-01-26T17:13:38.623369Z

(some people have "opinions" on running tests from build.clj but I prefer not to have a mix of shell scripts and Clojure scripts if possible)

borkdude 2023-01-26T17:13:47.289729Z

@seancorfield What you are describing sounds like a task runner to me and the tools.build can be used as such, but there are other solutions for this too (like bb tasks, Makefile, Justfile)

seancorfield 2023-01-26T17:14:11.171419Z

But then your dev/CI/CD platform needs additional tooling installed.

borkdude 2023-01-26T17:15:01.562819Z

For some people that is worth the trade-off ;)

seancorfield 2023-01-26T17:18:40.570729Z

I haven't used Makefiles for decades -- and I'm very happy about that 🙂

borkdude 2023-01-26T17:19:26.433519Z

I also don't like Makefiles, which is why bb tasks exists ;)

seancorfield 2023-01-26T17:19:36.756829Z

I did cave in and add bb to next.jdbc for running tests that require more setup... but it was a marginal tradeoff TBH...

seancorfield 2023-01-26T17:20:32.743139Z

At work, we vendor in the Clojure CLI so our entire toolchain only needs git and java and nothing else. That's why I don't want to add extra tooling requirements there.

practicalli-johnny 2023-01-26T17:20:41.597759Z

Most commercial work I've done recently had to be done within Docker, so there were already tooling requirements. Once place even enforced a Makefile had to be used (I had forgotten how much I like them, so use them a lot now). I (now) have a pretty standard Dockerfile / docker-compose.yaml / Makefile combination for CI that I am happy with (and some .k8s/ configs too... when necessary) Sometimes it feels there is more config than application code laughcry I I think creating my own project template / template repository will be the smoothest approach to creating a basis for new Practicalli projects

seancorfield 2023-01-26T17:21:37.152839Z

@jr0cket LMK if you need help creating a deps-new template -- they are mostly declarative (EDN) 🙂

👍 1
borkdude 2023-01-26T17:22:20.152859Z

@seancorfield If you need to add more tools, check out asdf, it's a pretty nice way to control which CLIs and versions you get per directory/project. They are using it heavily at Pitch.

practicalli-johnny 2023-01-26T17:23:27.414219Z

Yes, @seancorfield I think the plan is to create a git repo of what I want the project to look like and then create a deps-new template to generate it, replacing project names in namespaces/filenames and any other useful substitutions. Thanks

👍🏻 1
seancorfield 2023-01-26T17:32:39.290409Z

@borkdude So then we'd need to install another tool -- asdf -- in order to install more tools? That seems like it is compounding the problem 🤣 By vendoring the CLI into our repo, we can automate a lot of setup/deployment that doesn't require additional downloads and installs across containers and servers.