|
@@ -0,0 +1,82 @@
|
|
|
+#|-*- mode:lisp -*-|#
|
|
|
+#|
|
|
|
+exec ros -Q -- $0 "$@"
|
|
|
+|#
|
|
|
+
|
|
|
+;; Woo is a fast non-blocking HTTP server built on top of
|
|
|
+;; libev. Although Woo is written in Common Lisp, it aims
|
|
|
+;; to be the fastest web server written in any programming
|
|
|
+;; language.
|
|
|
+
|
|
|
+;; https://github.com/fukamachi/woo
|
|
|
+
|
|
|
+;; Quicklisp is a library manager for Common Lisp. Use
|
|
|
+;; QuickLisp's quickload function to retrieve external
|
|
|
+;; packages. These packages are automatically curl'd when
|
|
|
+;; the program runs.
|
|
|
+
|
|
|
+;; Woo - https://github.com/fukamachi/woo
|
|
|
+;; Clack - https://github.com/fukamachi/clack
|
|
|
+;; Alexandria - https://github.com/keithj/alexandria
|
|
|
+;; Optima - https://github.com/m2ym/optima
|
|
|
+;; Jonathan - https://github.com/fukamachi/jonathan
|
|
|
+
|
|
|
+(ql:quickload '(:uiop :woo :alexandria :optima :jonathan) :silent t)
|
|
|
+(use-package :optima)
|
|
|
+
|
|
|
+;; This is just boilerplate
|
|
|
+(defun starts-with (x starts)
|
|
|
+ (and (<= (length starts) (length x))
|
|
|
+ (string= x starts :end1 (length starts))))
|
|
|
+
|
|
|
+(defun parse-argv (args)
|
|
|
+ (flet ((parse-int-value (option value)
|
|
|
+ (handler-case (parse-integer value)
|
|
|
+ (error (e)
|
|
|
+ (error "Invalid value for ~S: ~S~% ~A" option value e)))))
|
|
|
+ (loop for option = (pop args)
|
|
|
+ for value = (pop args)
|
|
|
+ while option
|
|
|
+ if (not (starts-with option "--"))
|
|
|
+ do (error "Invalid option: ~S" option)
|
|
|
+ else
|
|
|
+ if (equal option "--worker")
|
|
|
+ append (list :worker-num (parse-int-value option value))
|
|
|
+ else
|
|
|
+ if (equal option "--port")
|
|
|
+ append (list :port (parse-int-value option value))
|
|
|
+ else
|
|
|
+ do (error "Unknown option: ~S" option))))
|
|
|
+;; END BOILERPLATE
|
|
|
+
|
|
|
+
|
|
|
+;; Plaintext handler
|
|
|
+(defun plaintext (env)
|
|
|
+ (declare (ignore env))
|
|
|
+ '(200 (:content-type "text/plain" :server "Woo") ("Hello, World!"))
|
|
|
+)
|
|
|
+
|
|
|
+
|
|
|
+;; Route handler
|
|
|
+(defun handler (env)
|
|
|
+ (optima:match env
|
|
|
+ (
|
|
|
+ (guard (property :path-info path) (alexandria:starts-with-subseq "/plaintext" path))
|
|
|
+ (funcall 'plaintext env)
|
|
|
+ )
|
|
|
+ )
|
|
|
+)
|
|
|
+
|
|
|
+
|
|
|
+;; Create and start the server
|
|
|
+(defun main (&rest argv)
|
|
|
+ (let ((args (parse-argv argv)))
|
|
|
+ (apply #'woo:run
|
|
|
+ (lambda (env)
|
|
|
+ (funcall 'handler env)
|
|
|
+ )
|
|
|
+ :debug nil
|
|
|
+ args
|
|
|
+ )
|
|
|
+ )
|
|
|
+)
|