src/view/rss.lisp

DOWNLOAD
(in-package :murja.view.rss)

(deftab rss-single-item (:url "/feeds/:feed-id/item/:item-id"
			 :subtab rss
			 :require-login t
			 :captured-url-params (feed-id item-id))
  (let* ((post-row (postmodern:query "UPDATE blog.feed_item
SET read_at = now()
WHERE id = $1 AND feed = $2
RETURNING id, title, description, link, author, pubdate" item-id feed-id :list)))
    (destructuring-bind (id title description link author pubdate) post-row
      (let ((p (make-instance 'murja.model.post:RSS-Post
			      :created-at pubdate
			      :id id
			      :tags nil
			      :creator (make-instance 'murja.model.user:user
						      :nickname author)
			      :content description
			      :title title
			      :rss-link link)))
	(murja.view.components.blogpost:blogpost p)))))

(deftab rss-single-feed (:url "/feeds/:feed-id"
			 :subtab rss
			 :params (&get archived)
			 :require-login t
			 :captured-url-params (feed-id archived))
  (let ((items (postmodern:query
		"SELECT id, fetched, title, link, author, pubdate
FROM blog.feed_item
WHERE feed = $1 AND (read_at is null OR $2) AND pubdate <= now()
ORDER BY pubdate DESC" feed-id (not (not archived))))
	(feed-name (caar (postmodern:query "SELECT name FROM blog.feed_subscription WHERE id = $1" feed-id)))
	(lisp-fixup:*rfc822* t))
    (:h* ("~a (~d)" feed-name (length items)))

    (:div
     (:a :href (str:replace-all "?archived=NIL" ""
				(genurl:route->url 'rss-single-feed :feed-id feed-id :archived (not archived)))
	 (if archived
	     "Show only unread"
	     "Show all")))
    
    (:ul
     (dolist (item items)
       (destructuring-bind (id fetched title link author pubdate) item
	 (declare (ignore fetched link author))
	 (:li (:a :href (genurl:route->url 'rss-single-item :feed-id feed-id :item-id id) title)
	      (:section ("Published ~a" (lisp-fixup:fix-timestamp pubdate)))))))))


(defroute delete-feed-route ("/feed/:id"
			     :decorators (@db
					  @ssr-authenticated)
			     :method :delete ) ()
  (murja.rss.reader-db:delete-feed id (murja.model.user:user-id *user*))
  (setf (hunchentoot:return-code*) 204)
  "")

(defun delete-script ()
  (ps
    (defun-async delete-feed (feed-id)
      (let ((result (await (fetch (lisp (genurl:route->url-ps 'delete-feed-route :id 'feed-id))
				  (create method "DELETE")))))
	(if (equal 204 (await (@ result status)))
	    (chain location (reload))
	    (alert (+ "FAIL " (await (chain result (text))))))))
    
    (chain document
	   (add-event-listener "DOMContentLoaded"
			       (lambda (e)
				 (let ((buttons (chain
						 document
						 (query-selector-all "button.remove-feed"))))
				   (dolist (b buttons)
				     (chain b
					    (add-event-listener "click"
								(lambda (e)
								  (when (confirm (+ "Are you sure you wish to DELETE " (@ e target dataset feedname) "?"))
								    (delete-feed (@ e target dataset feedid)))))))))))))

(defroute new-feed ("/feed"
		    :decorators (@db
				 @ssr-authenticated)
		    :method :post)
    (&post feed_name feed_url)
  (murja.rss.reader-db:subscribe-to-feed2 feed_name feed_url *user*)
  (let ((referer (hunchentoot:header-in* "referer")))
    (hunchentoot:redirect referer)))

(deftab rss (:url "/feeds/"
	     :title "RSS Feeds"
	     :require-login t)
  (let ((feeds (get-user-feeds2 (user-id *user*) nil))
	(lisp-fixup:*rfc822* t))
    (:script (:raw (delete-script)))
    (:ul.flowy-list
     (dolist (feed feeds)
       (destructuring-bind (id name url count last-modified) feed
	 (:li.flowy-list-item
	  (:h*
	    (:a :href (genurl:route->url 'rss-single-feed :feed-id id)
		(format nil "~a (~d)" name count)))
	  (:div "Feed is located in " (:a :href url url))
	  (:div ("Last updated ~a" (unless (equalp last-modified :NULL)
				     (lisp-fixup:fix-timestamp last-modified))))

	  (:button.remove-feed :data-feedid id :data-feedname name "DELETE THIS FEED")))))

    (:form :method "POST" :action (genurl:route->url 'new-feed)
	   (:h* "Subscribe into a new feed?")
	   (:label "Feed name: " (:input :type :text :name "feed_name"))
	   (:label "Feed url: " (:input :type :text :name "feed_url"))
	   (:input :type :submit))))