src/view/components/root.lisp

DOWNLOAD
(defpackage murja.view.components.root
  (:use :cl :spinneret :binding-arrows
   :murja.settings
   :murja.middleware.auth
	:murja.model.user)

  (:export :*inject-to-head* :root-component)
  (:import-from :murja.posts.post-db :get-titles-by-year))

(in-package :murja.view.components.root)

(defun sidebar-tree ()
  (let* ((sidebar-titles (->>
			   (get-titles-by-year)
			   (lisp-fixup:group-by "Year"))))
    (with-html 
      (:ul :id "grouper"
	   (loop for year being the hash-keys of sidebar-titles
		 collecting (:li
			     (:details
			      (:summary (format nil "~a (~d)" year (length (gethash year sidebar-titles))))
			      (:ul 
			       (let ((by-month (lisp-fixup:group-by "Month" (gethash year sidebar-titles))))
				 (loop for month being the hash-keys of by-month
				       collecting (:li
						   (:details
						    (:summary (format nil "~a (~d)" month (length (gethash month by-month))))
						    (:ul 
						     (map 'list
							  (lambda (title)
							    (cl-hash-util:with-keys ("Id" "Title") title
							      (:li (:a :href (format nil "/blog/post/~d" Id)
								       Title))))
							  (gethash month by-month)))))))))))))))

(defun loginform/user-widget ()
  (with-html 
    (if *user*
	(:p :data-testid "welcome-user-label"
	    "Welcome, " (:a :href "/blog/usersettings" (user-nickname *user*)))
	(:form :method "post" :action "/api/login"
	       (:label "Username "
		       (:input :id "username" :name "username" :data-testid "username-input-field"))
	       (:label "Password "
		       (:input :id "password" :name "password" :type "password" :data-testid "password-input-field"))
	       (:input :type :submit :value "Log in")))))
  


(defvar *inject-to-head* nil)
(defmacro root-component (inner-component)
  (assert inner-component)
  "Returns the root html element of murja with `inner-component` embedded inside it"
  `(format nil "<!DOCTYPE html>~%~a"
	   (with-html-string 
	     (:html
	      (:head
	       (:link :href "/resources/murja.css" :rel "stylesheet" :type "text/css")
	       (:script :src "/resources/newui.js")
	       (:meta :charset "UTF-8")
	       (dolist (head-element *inject-to-head*)
		 (funcall head-element)))
	      
	      (:body
	       (:header
		(:a :href "/" (gethash "blog-title" *settings* )))

	       (:div :class "sidebar-flex"
		     ,inner-component
		     (:div :id "sidebar"
			   (loginform/user-widget)
			   (sidebar-tree))))))))