hey squinters anyone used playwright with squint? my current issue is that playwright is giving me errors if i try this
(require '["@playwright/test" :refer [test expect]])
(test "has title"
(^:async fn [{:keys [page]}]
(js-await (page.goto ""))
(js-await (-> (expect page)
(.toHaveTitle #"/MyTest/")))))
Playwright complains that the first argument of the generated function has to be destructured. So squint generates this
test("has title", (async function (p__3) {....
but playwright wants that
test("has title", (async function ({ page }) {
Any way to get this working with squint or do i have to fiddle that somehow :Dyou can use ^:js to use js destructuring
Aaaah
is there a way to create a macro for this piece of code something like (deftest name body)
i'm currently trying to get that somehow but i'm to dumb for macros i'm not that advanced yet 😄
can anyone explain what i'm doing wrong 😞
(defmacro deftest [name bound & body]
`(test ~name
(^:async fn [^:js {:keys [page]}]
(let [~bound page]
~@body))))
test is a function that is defined in a node libraryman now i get it why you should use macroexpand-1 😄 ok wrote my second real use macro thanx again @borkdude and i promise to not over use this stuff
what's the error?
SyntaxError: /home/metti/code/staryou/node/e2e-tests/tests/ex.spec.mjs: Unexpected reserved word 'await'. (11:1)
9 | clojure.core.test(squint_core.str("2. has title"), (function ({macros_SLASH_page}) {
10 | const _STAR_page_STAR_1 = macros.page;
> 11 | (await _STAR_page_STAR_1.goto(""));
| ^
12 | return (await expect(_STAR_page_STAR_1).toHaveTitle(/StarYou/));
13 | ;;;
14 | }));
at ex.spec.mjs:11
9 | clojure.core.test(squint_core.str("2. has title"), (function ({macros_SLASH_page}) {
10 | const _STAR_page_STAR_1 = macros.page;
> 11 | (await _STAR_page_STAR_1.goto(""));
| ^
12 | return (await expect(_STAR_page_STAR_1).toHaveTitle(/StarYou/));
13 | ;;;
14 | }));
Error: No tests found and the funny part is why is it using clojure.core.test 😄
test is a clojure.core function
you probably want to do something like this:
(defmacro deftest [name bound & body]
`(~'test ~name
((with-meta 'fn {:async true}) [~(with-meta '{:keys [page]} {:js true})]
(let [~bound ~'page]
~@body))))
I think I might just switch to non-syntax-quote since you're basically fighting against auto-resolving hereWhats the wit-meta doing?
I guess i have to learn more about macros :/
when you want to generate a symbol that has metadata from a macro you have to do it that way
I just found the doc in the reader section interesting didn't know that. And non-syntax-quote means somthing like that (list test ~name ...) ?
Usually you want to use list* so the varargs flattened into the list
(list* 'test .... body)Ah ok so i dont have to use ~@body right
yes
Ok this was great thank you so much @borkdude
yay i did it but still not really a clue 😄 but it works that way
(defmacro deftest [name binding & body]
(list 'test name
(list 'fn [(with-meta '{:keys [page]} {:js true})]
(let [binding 'page]
(list 'Promise.all (into [] body))))))
nice, perhaps you forgot the async metadata on fn though?
the let expression also needs to be quoted
it would probably help if you just wrote this as a function and inspected the output yourself in a REPL
you can also print the metadata like this:
(binding [*print-meta* true] (pr-str expression))combined with:
(def expression (macroexpand-1 '(deftest ....)))
you may get what's failinghere is a newer version
(defmacro deftest [name binding & body]
(list 'test name
(list (with-meta 'fn {:async true}) [(with-meta '{:keys [page]} {:js true})]
(let [binding 'page]
body
nil))))
is there a more elegant way to skip the return?you mean nrepl with squint and do a macroexpand-1 right
skip the return? what I mean is that you're not generating a let expression
you can do this in a normal Clojure REPL, squint's REPL doesn't support this probably
babashka / nbb do
do you use clj-kondo?
here you can see that the binding argument of the macro isn't used:
which may already give you a clue
so something like that right
(defmacro deftest [name binding & body]
(list 'test name
(list (with-meta 'fn {:async true}) [(with-meta '{:keys [page]} {:js true})]
(list 'let (vector binding 'page)
(list* 'do body)))))
no 😄indeed
heleluja
now you compare this version with the syntax-quote and decide which one is worse :)
so thats how a playwright test would look now
(deftest "2. has title" page
(js-await (.goto page ""))
(js-await (-> page
expect
(.toHaveTitle #"Hello World")))) vs
(test "3. has title"
(^:async fn [^:js {:keys [page]}]
(js-await (.goto page ""))
(js-await (-> page
expect
(.toHaveTitle #"StarYou")))))