This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
@narkisr it's working to me (vim+slamhound). But better with this hack applied: https://github.com/technomancy/slamhound/pull/87 :)
Hi,
I'm trying to figure out (with a standard lein new compojure-app foo
application) why I'm unable to refer into my foo.core
namespace specific public vars from another namespace (i.e. foo.bar
).
My foo.core
namespace looks like:
(ns foo.core
(:require [foo.bar :as fbr :refer [qux beep]])
(:gen-class))
And my foo.bar
namespace looks like:
(ns foo.bar)
(def baz 1)
(def qux 2)
(defn beep [] "bop")
But it seems when running lein repl
from the project directory and being dropped automatically into foo.core
that I can still execute fbr/baz
and access that value although I was hoping to "refer" into the namespace only qux
and beep
?
Any ideas? Thanks.
ah… that’s not how it works is the short answer If you want private vars you can mark them as private. if you don’t want to expose fbr, just don’t :as fbr
`(:require [foo.bar :refer [qux beep]]) <— no such thing as fbr, but qux and beep are in scope
(def ^:private baz 1)
fbr/baz will still be a thing but complain about being private...
does that help? or are you trying to do something else entirely?
requiring a namespace fully loads it, so from there it is just a matter of how you access the things
even private things aren’t strictly private.
@michaelr I use sente and would not expect the order to be preserved, the function handling seems to be decoupled from the message queue
@timothypratley: no that's fine thanks I guess it was just a case of me understanding the real practical differences between
:use
and :require
.
gotcha, it would be better if use didn’t exist 😉 so just ignore it
@timothypratley: cool. oh I just tried the following and it still exposed the baz
variable - so I've probably not quite understood your comment about refer yet
(ns foo.core
(:require [foo.bar :refer [qux beep]])
(:gen-class))
Were you saying that in this case as I'm not using :as
that :refer
should only allow allow access to qux
and beep
. I know you said before that require
basically loads everything, but then it seems the :refer
is sort of pointless?
With the above form, you should only be able to access baz
with it’s fully qualified name foo.bar/baz
(ns foo.core
(:require [foo.bar :refer [qux beep]])
(inc baz)
is an error.
:refer is just a shortcut to avoid using any namespacing and :as is just a shortcut for a shorter form of namespacing…
Sounds like you are typing baz
at the REPL however and expecting it to not be defined but it is?in which case it might just be that it is defined in your REPL session in your current namespace, or used or referred
require loads an entire namespace (if it is not loaded already) so the vars are defined after a require, the refer is just about how you want to refer to them in the current namespace (your options are, 1.nothing:fully qualified 2.aliased with :as 3.referred(avoid conflicts though!) 4. :refer :all (don’t do this, it is just like use, and will cause conflicts and hard to follow dependencies)
@timothyandrew: oh I see! sorry it has clicked now
I was accessing everything with a namespace (e.g. foo.bar/qux
√ and then doing foo.bar/baz
and wondering why it was still accessible), doh. Silly me
but yes, if I do qux
it's accessible, but baz
is not (unless I namespace it directly).
gotcha
that's great. got it now, thank you
@timothypratley: strange..
@timothypratley: i tried to follow the source and it seems that sente does try to send messages in the same order they are put on the buffer, but it appears as if the web server itself changes the order of messages sometimes. I use immutant here
@integralist: I've been having the same conceptual issues with :require and :refer and I think part of the reason is that I'm coming from Python where the import mechanics are different. @timothypratley You've simplified the issue for me as well, thanks.
:thumbsup:
tired of writing the same clj-http/cljs-https boilerplate? want an easy way to express the notion of talking to an endpoint or a service? check out remote: https://github.com/outpace/remote
@noprompt: one thing I’m getting tired of, with writing Om apps, is adding API fns that are just data getters for datomic, with authentication
I’ve been thinking about how to create a DSL/policy thing that says “this client w/ this auth can grab any of this data"
@arohner: remote's pretty boring. it's just a classic example of use a map, make a function, put a macro on top of it.
more than likely you could apply the same technique too. it's a matter of figuring out which parts can be expressed as data then going from there.
the main win with remote while i was at outpace is that it gave everyone the same tools for solving the same problem. after writing the boilerplate a few times, and debugging it a few more times, or reading and debugging someone else's boilerplate i just got fed up.
some people are fine with writing the same helpers and boilerplate, which is cool for certain projects, but if you have a large team or have several applications a DSL that can solve 99% the problem every time will almost always be better.
if you're able, it's worth the time to stop and clean it up. alex taggart and i probably spent half a day talking about the problem and then another day or so implementing the first version. it took longer to replace old code than it did to solve the problem.
In lein is there a way I can say "this project provides some other project". Say I forked a date time library and want to make my patched but differently named version appear to provide the dependency it is intended to replace so that transitive deps don't pull in the unpatched version. Or is this just where you have to use exclusions?
an explicit dep it will override transitive ones, but it seems like a bad idea to have projects force that on their dependants
The idea is that since my copy claims to provide the other you only pull mine if you would otherwise reach both..
I guess it's not generally possible (or sustainable in the long term) two have two artifacts/projects with identical APIs and behavior
so it's sane to say "you must choose one and depend hard on that" rather than pretending you can have interchangable components...
in order to bump your project's version, you must first define a schema migration up and down for any objects that can escape from its functions
then you can have multiple versions of code living in the same process, using the same objects
I was reading earlier that ocaml has functions on modules that return new modules, i wonder what's the state of art.
in V1 I move it to com.foo.bar.impl/qux since it doesn't need to be public or whatever
This is where Phil and Chas appear in pillars of smoke with the any change is breaking mantra
I write code that relies on certains vars not being in namespaces that I don't control.