This establishes two routes (‘GET’ for reading and ‘POST’ for writing) on the
URI localhost:9003/lispdoc/<symbol>
.
(defpackage #:readme-demo (:use #:cl #:snooze)) (in-package #:readme-demo) (defun find-symbol-or-lose (name package) (or (find-symbol (string name) (find-package package)) (http-condition 404 "Sorry, no such symbol"))) (defroute lispdoc (:get :text/* name &key (package :cl) (doctype 'function)) (or (documentation (find-symbol-or-lose name package) doctype) (http-condition 404 "Sorry, ~a doesn't have any ~a doc" name doctype))) (defroute lispdoc (:post :text/plain name &key (package :cl) (doctype 'function)) (setf (documentation (find-symbol-or-lose name package) doctype) (payload-as-string))) ;; Let's use clack as a server backend (clack:clackup (snooze:make-clack-app) :port 9003)
Here’s an illustration of how they respond:
GET /lispdoc/defun => 200 OK GET /lispdoc/funny-syntax?package=snooze => 404 Not found GET /lispdoc/in/?valid=args => 400 Bad Request GET /lispdoc/defun => 406 Not Acceptable Accept: application/json POST /lispdoc/scan?package=cl-ppcre => 200 OK Content-type: text/plain POST /lispdoc/defun => 415 Unsupported Media Type Content-type: application/json
The error codes 400, 406 and 415 are error reporting that you get "for free": if the HTTP client strays off these routes, be it for improper syntax or unsupported content types, the correct HTTP condition is signalled.
There are already some Common Lisp systems for HTTP routing, like
Unfortunately, they tend to make you learn some extra route-defining syntax.
On the contrary Snooze maps REST/HTTP concepts to Common Lisp concepts:
HTTP-REST Concept | Snooze CL Concept |
---|---|
REST Resource | CLOS generic function |
Route | CLOS method |
Verbs (GET, POST, DELETE, etc) | CLOS specializer on first argument |
Accept: and Content-Type: | CLOS specializer on second argument |
URI path (/path1/path2/path3)) | Required and optional arguments |
URL queries (?param=value&p2=v2) | Keyword arguments |
Status codes (404, 500, etc) | CL conditions |
This has many advantages, for example: