Я не совсем уверен, что вы пытаетесь сделать и почему вы называете эту функцию xml-eval.
Но, похоже, вам нужна функция, которая берет кучу вложенных списков и заменяет те, которые начинаются с % , результатом кода, который они содержат. Поэтому вы можете использовать что-то вроде этого:
(defn xml-eval [x]
(if (coll? x)
(if (= (first x) '%)
(eval (rest x))
(map xml-eval x))
x))
Кажется, это делает то, что вы хотите.
user=> (xml-eval '(item (itemname "some item") (price (% * 19.95 1.08))))
(item (itemname "some item") (price 21.546))
Но вы также можете заглянуть в без кавычек
user=> `(item (itemname "some item") (price ~(* 19.95 1.08)))
(user/item (user/itemname "some item") (user/price 21.546))