В рамках изучения Lisp я решил один небольшой проект веб-приложения сделать на нём (ибо заказчику всё равно какой язык я буду использовать, ему лишь бы работало, да и время у меня есть).
В качестве веб-сервера использую модуль Hunchentoot. Поскольку мне не нужно ничего супер-сложного, использую его фреймворк easy-handlers для задания маршрутов.
Хочу сделать так, чтобы обработчик вызывался для любого запроса, начинающегося с «/foo/». То есть сюда подходят всякие варианты «/foo/bar», «/foo/baz» и т. д.
У функции define-easy-handler параметр :url может быть не только строкой, но и функцией.
Таким образом можно написать что-то вроде:
(defun starts-with (substr str)
(if (>= (length str) (length substr))
(equal substr (subseq str 0 (length substr)))))
(define-easy-handler (foo-page :uri #'(lambda (request) (starts-with "/foo/" (request-uri request)))) ()
...)
Но это же не красиво! Хочу вынести создание лябмды в отдельную функцию. Чтобы писать как-то так:
(defun prefix-uri (prefix)
`(function (lambda (request) (starts-with ,prefix (request-uri request)))))
(define-easy-handler (foo-page :url (prefix-uri "/foo/"))
...)
Однако как бы я не расставлял квотирование, либо получаю ошибку компиляции, либо сервер выдаёт 404, либо при обращении к странице вылетает ошибка 500, а в логах пишется, мол мне требуется function symbol, а ты подсунул мне какую-то фигню вместо него.
Как правильно такое реализовать?