This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2016-08-08
Channels
- # admin-announcements (2)
- # beginners (35)
- # boot (353)
- # capetown (1)
- # cider (1)
- # cljs-dev (41)
- # cljsjs (3)
- # cljsrn (3)
- # clojure (118)
- # clojure-austin (12)
- # clojure-russia (17)
- # clojure-spec (21)
- # clojure-taiwan (1)
- # clojure-uk (91)
- # clojurescript (80)
- # clojurex (1)
- # cloverage (3)
- # datomic (66)
- # devcards (2)
- # events (2)
- # garden (6)
- # hoplon (54)
- # jobs-rus (1)
- # keechma (1)
- # lein-figwheel (4)
- # leiningen (3)
- # luminus (3)
- # off-topic (7)
- # om (4)
- # onyx (53)
- # other-languages (17)
- # proton (7)
- # protorepl (4)
- # re-frame (123)
- # reagent (1)
- # ring (6)
- # rum (2)
- # spacemacs (1)
- # specter (21)
- # testing (1)
- # untangled (1)
- # yada (42)
system 0.3.1 is out and here is the official announcement. https://groups.google.com/forum/#!topic/clojure/Td4-b8gDL58
Oh man I have to take the time for trying mount, sorry about the delay
@richiardiandrea: Not a problem at all. Only if you have time and motivation to push this forward. The success of the mount branch depends on the people who want to see this happen. We'll get there, eventually. 🙂
@danielsz: Thank you for this great work. I'm using boot more and more and this only makes it better.
I have a boot task in my build.boot where I simply want to output the project version (i need it propagated to my namespaces, and just want to check if it is accessible in a task)
cli: expected short option, got echo
cli: expected long option, got nil
cli: option nil: expected optarg, got "version is: "
clojure.lang.ExceptionInfo: Wrong number of args (1) passed to: cli/argspec->cli-argspec
data: {:file "/tmp/boot.user4393831086517409494.clj", :line 27}
you need []
after the task name
@avabinary: because the error messages suck
good news: the error message has been fixed in master
now it works, thanks @pesterhazy
questions about util/verbosity
• why is it both dynamic and an atom?
• what is the idiomatic way to change it from the REPL?
I want (boot (turn-up-verbosity) (thing-I-am-testing))
Boot -vvv
Uh, ignore that, doesnt work like that from repl
(deftask turn-up-verbosity []
(fn [next-task]
(fn [fileset]
(binding [boot.util/*verbosity* (atom 3)] (next-task fileset)))))
don't know why micha made it a dynamic atom, but i do that so i can inc/dec a value without rebinding
cc @micha ⬆️
ah i don't remember, it was probably not an ideal way to solve whatever the problem was
am I “doing it wrong” trying to debug tasks at the REPL this way?
feels like anybody debugging a task would immediately hit this, so I wonder if my workflow is odd
i usually start with boot -vvv repl
and then (boot ...)
and (load-file "build.boot")
prodigiously.. so i think what you're doing is par
@stuarthalloway: do you still need to be able to use a non-maven version of clojure for boot itself, such as by specifying BOOT_CLOJURE_VERSION=
?
@micha I am using boot-cp everywhere, and writing my own code for managing classpath
non-mavening not just Clojure but other things
the only thing that doesn't cover is the version of clojure in the boot core pod, which will be loaded from local maven
that is fine
awesome
I have a lil problem in that I receive a Could not find artifact boot:core:jar:2.7.0-rc1 in clojars
here even if my boot.properties
says 2.6.0
...
shell I delete some cache
folder in .boot
?
found the culprit, never mind 😉
What was the culprit?
I had the 2.7.0-rc1
version hardcoded in deps for a pod
in general I use (boot.App/config "BOOT_VERSION")
but that was a leftover
ah, glad you figured it out 😄
me too 😄
I want to use the Spring S3 wagon, how do I say that in boot?
(aether/register-wagon-factory! "s3" #(org.springframework.build.aws.maven.SimpleStorageServiceWagon.))
@stuarthalloway: the "worker" pod is where the maven machinery is loaded, so you can add the implementation class to the classpath of the worker pod by using boot.pod/with-eval-worker
to call boot.pod/add-classpath
or boot.pod/add-dependencies
etc., then evaluate your code above in the worker pod too
that's for the https://github.com/technomancy/s3-wagon-private one
that will work "automatically" because it contains a file that describes the class bindings
this thing: https://github.com/technomancy/s3-wagon-private/blob/master/src/main/resources/leiningen/wagons.clj
so to clarify, if you don't have the wagons.clj
file in the jar already and the jar in maven, you want to do this:
(boot.pod/with-eval-worker
(boot.pod/add-classpath "path/to/wagon.jar")
(require '[cemerick.pomegranate.aether :as aether])
(aether/register-wagon-factory! "s3" #{...}))
thanks @micha. I have (set-env! :wagons #(conj % '[s3-wagon-private "1.2.0"]))
but don’t see the factory being registered, will post more when I narrow it down
@stuarthalloway: it should be registered in the worker pod
I see it if I eval in the worker pod directly:
(boot.pod/with-eval-worker
(require '[cemerick.pomegranate.aether :as aether]
'[clojure.pprint :as pp])
(util/warn "%s" (with-out-str (pp/pprint @#'cemerick.pomegranate.aether/wagon-factories))))
But not if I look while inside a task
(deftask demo
[]
(with-pass-thru [_]
(util/warn "%s" (with-out-str (pp/pprint @#'cemerick.pomegranate.aether/wagon-factories)))))
(boot (demo))
because the core pod (the one your task body is evaluated in) doesn't have any aether stuff in it
i don’t understand that last sentence and I want to 🙂
ah sorry, what i mean is that there are a couple of pods that boot starts when it boots up
it starts a worker pod that has various dependencies loaded in it, dependencies that boot needs to do its jobs, like the maven aether machinery, things like that
I am writing my own task that wants to run in that worker pod
when I write my own tasks, what pod do they run in?
when you call boot.pod/add-dependencies
etc it's really calling into the worker pod to resolve the maven coordinates into jar locations
got it
the boot.pod
namespace has many wrappers for functionality that is actually provided by the worker pod
the wrappers allow all other pods to use the functions in the worker pod via those proxies
@stuarthalloway: ah you can also add a :schemes
key to the :wagons
vector, like this
(set-env!
:wagons #(conj % '[some-maven-id "1.2.3" :schemes {"s3" '#(org.springframework.build.aws.maven.SimpleStorageServiceWagon.)}]))
you'd need to quote the factory fn like above, because it will be passed as data and eval
ed in the worker
now I am further down the rabbit hole...
I have an entire source file that I want to require from inside the worker pod
but I think that my dev source directory is not in the worker pod classpath
and this code is itself a library, so I need an approach that covers my dev use, and later downstream use
so naive use of boot.pod/add-classpath
won’t be enough — right now it is “src”, later it will be “this-lib.jar"
no, it is a bunch of code that uses pomegranate and aether
I will take a look
for example: https://github.com/boot-clj/boot/blob/master/boot/pod/src/boot/pod.clj#L539-L545
hm. I have existing libs that make use of aether. and I want to write a boot task shim for them
that certainly seems most flexible
yeah, it seems maybe worker pod should be treated mostly as private to boot itself — use it where it does something you need, but don’t add a lot to it
for myself — not to inflict on others 🙂
there are these multimethods, btw https://github.com/boot-clj/boot/blob/master/boot/core/src/boot/core.clj#L812
is it cool to add user-space things to pre-env!
? Should probably be namespaced keys...
but this is an interesting use case, seems like it will shed light on what the real API should be
Somewhat related to pre/post-env
, I was wondering if there's a good reason not to expose this on-change
handler for watching user-dirs: https://github.com/boot-clj/boot/blob/master/boot/core/src/boot/core.clj#L192-L194. I'm currently monkey patching boot.core (inconveniently) to piggieback on my own callbacks whenever there's a file change. I'm doing this so as to not spawn a whole bunch of watcher threads (which for our repo would be a lot given the number of directories we have). It seems like it could generally useful to expose file changes as something that could be observed while in the repl, for example.
@sbrady: have you seen this: http://ec2-54-162-17-9.compute-1.amazonaws.com
the watch task currently does some things to work around limitations of the fs event APIs
the fs events are good to use because you don't need to poll, which uses a significant amount of cpu
but i think it would be tricky to move that into boot core because you probably don't want to do that change tracking all the time
So here's the patch that I have for boot.core: https://gist.github.com/stephenbrady/400989c9cf1f2283f61ed08049c9bd2a
And then add callbacks to FileChangeCallbacks
at will while in the repl (or in build.boot)
I just basically lifted out the anonymous function and extended it will calling the callbacks
For the javac callback, I see if the file was added or removed and either compile it and add it to Clojure's class cache or remove it
seems like we'd be better off getting the background pipeline working efficiently than by exposing these internals
because then you have like a partial pipeline thing that isn't composable with anything else and goes outside the locking and synchronization of the pipeline
there are some semaphores and things in the pipeline because of all those filesystem event watches
I obviously don't have the perspective you have on the boot pipeline, but it does feel like the pipeline API doesn't quite fit the event orientation of the repl. While the repl's running, there are events that are happening. It does seem like I should be able to observe and react to those.
We've got things like pre-env and post-env, which look the start of being able to bind to events
I wouldn't use these things in the more command-line-oriented boot tasks that I have, but the repl does have its own orientation that's different
Having the repl sit at the end of the pipeline and block it, that seems to be the cause
so what we really want is that when you change a file in your project source dirs for instance
When I first hunted around, I actually did think that it was happening somewhere (with the user dirs sync), and I actually was surprised that the changes delivered by the watch-dirs provided it in a format that was not the fileset format
we can maybe refactor that part, the part that conveys fs event updates to the boot env
@micha: Not sure if you saw this as I posted it quite late but here is the first cut of the task we talked about last week: https://gist.github.com/kennyjwilli/97f83cc49934bc08af4d3905487a9b49 Any feedback?
(update-file :match-files #{#"ui\.cljs\.edn"}
:expr (fn [cljs-edn]
(update cljs-edn
:compiler-options #(-> %
(dissoc :preloads :external-config)
(assoc :closure-defines
{'myns.core "prod"
'myns.core/server-url ""})))))
There is one issue though.. As you probably know, in Clojure 1.9.0 namespaced map reader macros were introduced (http://dev.clojure.org/jira/browse/CLJ-1910). So, if you are using Clojure 1.9.0 in your project, the task will spit
the updated map using reader macros. This causes a problem in boot-cljs because it doesn't know how to read .cljs.edn
s with the new reader macros.
especially since there is no guarantee that there is not more than one reader macro representation for a given piece of data, is there?
Looking at boot-cljs, Clojure is a provided dep so I should be able to set the Clojure version in the project using boot-cljs
also how do you feel about adding your update-files task to the boot built-in sift
task?
at the comand line you'd do boot sift -u '*\.clj$:#(concat % (quote (println "hello")))'
I say we just make the default be the edn reader and if someone wants to use a different parsing function they can use the :update-string
option which is passed the contents of the file as a string.
but we could use a simpler thing with streams in the task and have functions that handle what you describe that are alraedy available
if you get stuck with it (the sift task is weird) you can make an issue on github to track it
you can do a lot of things you'd normally make a separate task for with this approach i think
http://dev.clojure.org/jira/browse/CLJ-1993 may solve the problem with the namespaced maps