Fork me on GitHub
#babashka
<
2023-06-29
>
Colin (fosskers)00:06:30

TIL: require paths for local modules in the same project don't "just work" unless you have a bb.edn that actually knows to look in src/!

borkdude06:06:26

@U058DHAN3UP You can also add a bb.edn with {:paths ["."]} to add the local directory to the classpath

👍 2
Colin (fosskers)08:06:27

@U043RSZ25HQ Thanks, that's a handy pattern

Casey07:06:39

I see markdown-clj seems to be supported based on the code in the babashka repo..but it seems it can't be loaded?

----- Context ------------------------------------------------------------------
1: (require '[markdown.core :as md])
   ^--- Could not find namespace: markdown.core.

lispyclouds07:06:20

how did you add the library as a dep? its not built into bb if thats what you were expecting?

borkdude08:06:48

The lib must be added to bb.edn deps

Casey08:06:11

Oh. my mistake. thanks.

Casey08:06:43

I assumed all libs at https://babashka.org/toolbox/ were builtin.. but now that i take a closer look I see the tags

mmer10:06:45

Sorry to ask yet another question: I have a project that works with a java setup but I want to move to bb so I can share it more easily. The clj files are in a directory src/ogsetup. There is a core.clj and some other files such as bulk.clj My bb.edn

{:paths ["src", "src/og-setup"]
 :deps {com.rpl/specter {:mvn/version "1.1.4"}
        org.clj-commons/clj-http-lite {:mvn/version "1.0.13"}}
 :tasks {:init (do
                 (add-tap println))
         :requires ([ogsetup.core]
                    [ogsetup.bulk]
                    [ogsetup.single]
                    [ogsetup.delete])
         delete-tests (do
                               (println "Running delete tests")
                               (add-tap println)
                               (delete-users "test-data/")
                               (delete-usergroups "test-data/")
                               (delete-objectgroups "test-data/")
                               (delete-roles "test-data/"))
         test (println "Test Task Ran")
         } }
The functions delete-users in src/ogsetp/core.clj but I get the following error:
(do (println "Running delete tests") (add-tap println) (delete-users "test-data/") (delete-usergroups "test-data/") (delete-objectgroups "test-data/") (delete-roles "test-data/")))) delete-tests
                                                           ^--- Could not resolve symbol: delete-users
Do I need to include my files in the :deps?

borkdude10:06:57

You need to either use an alias or refer with the requires or use the full namespace name in a fully qualified symbol

borkdude10:06:25

I’m not at the kbd right now but hopefully someone else can elaborate if necessary

mmer10:06:07

Thanks I think I have it working using :as on all those files in the :requires Thanks

👍 2
mmer12:06:06

The fix was to reference the files in the required section:

:tasks {:requires ([ogsetup.core :as  core]
                    [ogsetup.single :as  single]
                    [cheshire.core :as json]
                    [clojure.tools.cli :as cli])
Then calling functions with the qualifier.
(core/delete-user "test-data/")
Thanks

leifericf10:06:00

I'm working on https://github.com/leifericf/leifs-utils/tree/main/src/leifs_utils, which I have split into separate namespaces. Previously, everything was in a single namespace, so I could simply evaluate the whole file each time I started the REPL. But now that there are several namespaces, I must evaluate each in the REPL, which is probably not the correct way. How can I automatically evaluate all the namespaces and everything therein when I start a new REPL? Do I need to add something to bb.edn or calva.autoEvaluateCode.onConnect.clj? :thinking_face:

pez11:06:33

You should be able to evaluate just the top namespace as long as the classpath is correctly set up. One way to do this is to add the directory where the top namespace lives as part of the command starting the REPL. Can be done via the shebang:

#!/usr/bin/env -S bb -cp ./

Crispin11:06:48

if using emacs C-c C-k evaluates the entire buffer, and if it has requires at the top, it will include them

leifericf11:06:10

In this case, what would be "the top namespace?" Would that be clj꞉user? :thinking_face:

pez11:06:13

Then if you use a custom repl start command when jacking that just points to the script, it should work. Or you can use a global connect sequence like this one: https://calva.io/connect-sequences/#start-a-babashka-repl-via-wsl

"calva.replConnectSequences": [
    {
        "name": "Bashbabka (WSL)",
        "projectType": "custom",
        "customJackInCommandLine": "bash -c 'bb -cp ./ --nrepl-server JACK-IN-NREPL-PORT'",
    },
  ],

pez11:06:58

The top namespace would be the namespace that requires the other namespaces (that in turn require and so on). Your main script.

leifericf11:06:28

Aha, I see! I guess that's part of the problem: I don't have a single "top namespace" that requires all the others.

pez11:06:05

You can create one. 😃

leifericf11:06:34

Indeed! I guess I need to create a main.clj or something like that then.

leifericf11:06:02

Or rethink how I have chosen to structure the project.

pez11:06:07

repl.clj ?

💡 2
leifericf11:06:26

Yeah, that's better!

pez11:06:27

Or dev.clj.

leifericf11:06:39

If I have a repl.clj or dev.clj then I suppose I can also have functions in there to reload everything, etc.

metal 2
pez11:06:57

Make sure that all your scripts guard the call to their "main" function with something like so:

(when (= *file* (System/getProperty "babashka.file"))
  (main ...))
Or you will fire off a lot of work when loading your dev file. 😃

💡 2
leifericf11:06:01

Oh, I did read that! But sort of glossed over/missed that part. Thanks again!

pez11:06:30

You are most welcome, Sir!

leifericf11:06:50

My namespaces only define functions now, which may be used elsewhere, for example, by Babashka Tasks or at the command line. They don't do anything on their own, basically. In this case, I suppose I don't need to "guard calls to their main function?"

leifericf11:06:56

The idea I'm working towards is to define a bunch of Babashka Tasks to "do the stuff" by combining the functions defined within the namespaces under the src directory.

pez11:06:15

Yes, you only need to guard things that you want to happen when the scripts are called, but not when loading them in the REPL.

👍 2
leifericf09:07:44

For the record, I had made a few dumb mistakes: 1. Clobbered two functions from clojure.core 2. Introduced a circular dependency As a result, my REPL did not load dependencies correctly, which I had overlooked. After fixing those issues, I'm able to open any file and execute the expressions therein via a clean REPL.

mmer12:06:41

Is there a best practice to bundle a solution made up of multiple namespaces files and a bb.edn with tasks in it? I want to be able to give it to others to be able to run.

borkdude18:06:58

bb tasks are intended to be used locally in a project

borkdude18:06:30

if you want to distribute code, I'd just write some top level scripts that users can install using #C0400TZENE7 or so

borkdude06:06:25

another way is to let them download your project and then execute those tasks with:

bb --config ~/downloads/your-project/bb.edn <task>

👍 2
borkdude06:06:31

you could wrap this in a helper bash script

jmv16:06:35

is it possible to use ansi escape codes in bb task docstrings? the reason i ask is that i was to highlight key parts of docstrings for some potentially dangerous tasks

Bob B18:06:45

did you try it?

Bob B18:06:04

it appears to work, but this will also depend on the thing to which the docstring is being printed handling the escape codes

jmv16:06:58

ha, i did but i had a bad ansi escape sequence. i fixed that and it worked like a charm. thanks for reassurance!