This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2016-02-07
Channels
- # beginners (4)
- # boot (186)
- # cider (68)
- # cljsjs (2)
- # cljsrn (6)
- # clojure (103)
- # clojure-dev (1)
- # clojure-russia (117)
- # clojurescript (40)
- # community-development (31)
- # cursive (2)
- # data-science (7)
- # datomic (6)
- # devcards (2)
- # editors-rus (2)
- # emacs (2)
- # jobs (2)
- # ldnclj (2)
- # lein-figwheel (41)
- # off-topic (5)
- # om (50)
- # overtone (2)
- # re-frame (36)
- # reagent (1)
- # spacemacs (3)
- # yada (2)
hey guys, quick question. I’m creating uberjar and resulting file gets created somewhere in ~/.boot/cache. is there any way (other then setting BOOT_EMIT_TARGET) to provide destination dir ?
@jethroksy: great! that’s what I needed. thanks!
Hi. Is it possible to spit
huge EDN object (i.e. huge piece of data) in one task and read it from another?
https://github.com/boot-clj/boot/wiki/Filesets @andrewboltachev does this help at all?
@dominicm: I'm using them already. I just wonder should I use them or not if my file is, say, 50 megabytes of Clojure data? EDN parser would reject probably
i.e. what files (in a fileset, or filesystem or whereever) contain is strings, not data objects
so, what I wanted Boot to do for me is to watch
for changes
Hi folks. I'm thinking about extending boot to support first-class task dependencies, so e.g. a compile task will only run if sources have changed. I can't see how to do this with handler composition, at least not without embedding the logic in the tasks themselves, which would be bad. Any plans for this sort of things?
@juhoteperi: I did, and yes, the update after separation of boot/boot-bin are later than 15.09 so you need to be on unstable
@juhoteperi: or just override stuff in your .nixpkgs/config.nix
@mobileink: you mean like a cljs task that only compiles if cljs files have changed? why would you want to split the "see if something has changed" bit from the actual task?
@jellea: I think it's a good idea to avoid confusion over the version of boot to use/have installed
@martinklepsch: Well, there's the general principle that a task should do one thing only; checking for file changes and compiling are distinct tasks. But more practically, nested handler composition forces you to invoke every task in the chain. If we have a task chain A -> B -> C, the actual work of A might not be needed, but it has to call B since it cannot determine if B is needed, and so on. To be able to skip unnecessary tasks, the task controller must be separate from the tasks, and the tasks must be annotated with input/output info so the controller can determine which tasks can be skipped. This is roughly what Gradle does, but working with Gradle is a nightmare once you've seen Clojure. In principle is should be possible to have a defjob macro, with first arg {:inputs [..filesets..] :outputs [..filesets..]}, together with a composition op such that the composition mechanism decides whether or not to run tasks. Only data/files would be passed from task to task, not handlers. The task pipeline would be a flat one-way sequence rather than a nest of embedded fns. In other words, first order composition v. the second order composition used by boot, ring, etc. So far this is just an idea, but it seems feasible. I would really like to have the power and flexibility of Gradle in Clojure and boot seems like a good candidate. Make sense? BTW I'm not complaining about handler composition, it works great when that's what you need.
@mobileink: there is benefit to running all tasks in the pipeline though
so a task may find that the files it's interested in have not changed since the last time it was called, so it will not build anything. instead it will add cached files from the last build to the fileset
this is an extremely efficient process because no copying of files or I/O actually takes place
i think in most cases it's much harder to specify a correct dependency DAG than it is to just put the tasks in a pipeline in a certain order
because to the developer it's usually completely obvious which tasks need to happen before which other tasks
kind of related - we've talked with Alan briefly on the merits of https://github.com/ndmitchell/shake here and he brought up the possibility to kind-of JIT-optimize the boot build by noting what files are touched in the tasks
these are usually superior to other solutions because they are self-contained, they don't need to negotiate with some supervisor
imagine if every time you wrote a task you would need to express the relationship it will have to any other task that might be used
@micha: right, handler composition definitely has its place and you guys have done a great job. i have to think about this some more, but basically i think there are two approaches. one is to make each task responsible for caching, diffing, etc.; this is the approach boot takes. the other is to give that responsibility to a supervisor/controller. there are pros and cons to each approach.
the reason we went with the pipeline model was because we were stuck by how obvious the pipeline is in any specific build scenario, versus the complexity of trying to solve the problem in a general way for all build scenarios
like building a system that could divine the user's intent from declarative specifications is way more complicated than the user just telling you their intent by putting tasks in a linear pipeline
actually I think removing the caching/diffing decision-making from tasks makes it much easier to build (flat) pipelines. no need to express relations to other tasks, or to negotiate anything - just specify your inputs and outputs, and then construct a pipeline - the controller decides what needs to be done, based on the inputs and outputs. (Note that I'm making a distinction between handler pipelines (which are not really pipelines, they're nestings) and flat pipelines. And I'm not suggesting handler pipelines should be replaced - they're just a mechanism and they work well.)
In any case, it sounds like what I've described is not being worked on so if I can find the time to do some proof-of-concept work I won't be overlapping.
I should probably write a blog post with some more detailed examples of what I have in mind. Ultimately I think this is the sort of thing for which we need some running code so we can see what would happen with it in actual use. I think it would work but there are undoubtedly hidden landmines. Plus you would want it to work seamlessly with boot as it is now - it's not really a major change of paradigm, just a different mechanism for dealing with task/data dependencies.
@mobileink: totally
@pandeiro: the boot program looks in two places for a file named boot.properties when it starts, it doesn't look on the classpath or anything like that
@micha thanks much for the feedback. I'll make some time to write up a blog post with more detailed examples and maybe some implementation ideas and then run it past you.
@pandeiro: also I think JVM options can't be set via boot.properties
(because it's Java reading the properties file)
@mobileink: if you need any info on lower-level fileset stuff don't hesitate to ask
if a lib specifies a BOOT_VERSION in boot.properties, is there any reason to include boot/core in :dependencies
as well?
the boot.properties of the lib are not packaged in the jar, and they don't appear in the pom
i think having an explicit dependency on clojure in a library is good, because it provides information to consumers of the library about which version of clojure it is supposed to work with
depending on boot itself is currently somewhat broken, so you would need to use :scope "provided"
, which isn't ideal
i think having an explicit clojure dependency in your library that will be in the pom is what you want
the user will need to declare their own clojure dependency in their build.boot anyway or things will get weird
i mean you'll pull in some random version of clojure from one of your dependencies no matter what
so i should remove the boot/core dependeny from build.boot and just specify that in boot.properties, and remove scope provided from clojure in build.boot?
but this means that an app using e.g. clojure 1.8.0 will have to possibly use :exclusions [org.clojure/clojure] with my lib to prevent it using 1.7.0 (lib version) instead, right?
but you need to do that anyway, because if you have any dependencies at all you will have some random clojure transitive dep
but the value here is that someone can do boot show -p
and see which version of clojure your library was intended to work with
if you had :scope "provided"
or no clojure dependency at all in your library then boot show -p
wouldn't show anything
i think a good rule of thumb is that task libraries should have only one dependency: clojure
all other dependencies are loaded by the library into a pod, so they are not declared as transitive deps in the pom.xml
I could make boot-test a dev-dependency that only gets loaded in the test task, but how would I do with bootlaces?
so when a consumer of your library adds your lib to their deps, maven downloads your pom
if the pom has scope test for a given dependency, then maven won't load that dependency into the consumer's classpath
so if i understand you correctly you want to use boot-test while you're developing your library, but you don't want consumers of your library to have boot-test pulled into their project transitively, right?
that will cause maven to only load that dependency when you're working on your library, that is to say it will only load that dependency in your own build.boot
i don't think there is any real need to have "dev dependencies" that are loaded from tasks
you can have all your dev dependencies in the :dependencies
at the top level, at least for boot-tasks, since they don't have any transitive deps that could cause any problems
but back to your guideline, maybe it could be libs should depend on clojure + stuff in test scope?
so you don't need to load different deps when you're testing and developing from when you are deploying
if everything but clojure is scope test then when a consumer depends on your library and does show -d they will only see clojure as a dependency of your library
so like the cljs compiler pod, for example, would be named adzerk.boot-cljs
, since that's the namespace that makes the pod
btw would this set the stage for being able to walk all a namespaces of a project and its deps and build a complete dependency graph?
i should mention that pods can be garbage collected and fall out of scope, so you may need to do something to have access to a given pod
so when you call (require ...)
on a namespace that's already compiled it doesn't compile it again
seems like you could make a ns-tracker type thing without doing any analysis of source files at all
@micha I hit one problem with removing boot/core from dependencies: if I try to execute a task within my test NS, it complains that it can't find boot/core boot/core_init etc
Otherwise I would just do it the way boot-cljs does, with a task invocation outside the tests
@pandeiro: if you feel adventurous enough there is a branch with that kind of workflow (`clojure.test` embedded in boot tasks) in https://github.com/boot-clj/boot/pull/401
hopefully it will soon be merged to 2.6.0-SNAPSHOT
but boot.built-in/runtests
allows you to run (in parallel) tasks with is
inside
and collect results and display as usual
neat @richiardiandrea thanks
(if I understood correctly your problem of course)
it was fun