Add admin area
This commit is contained in:
7
slices/admin/action.rb
Normal file
7
slices/admin/action.rb
Normal file
@@ -0,0 +1,7 @@
|
||||
# auto_register: false
|
||||
# frozen_string_literal: true
|
||||
|
||||
module Admin
|
||||
class Action < Adamantium::Action
|
||||
end
|
||||
end
|
0
slices/admin/actions/.keep
Normal file
0
slices/admin/actions/.keep
Normal file
12
slices/admin/actions/index.rb
Normal file
12
slices/admin/actions/index.rb
Normal file
@@ -0,0 +1,12 @@
|
||||
module Admin
|
||||
module Actions
|
||||
class Index < Action
|
||||
|
||||
include Deps["views.index"]
|
||||
|
||||
def handle(req, res)
|
||||
res.render index
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
17
slices/admin/actions/tags/delete.rb
Normal file
17
slices/admin/actions/tags/delete.rb
Normal file
@@ -0,0 +1,17 @@
|
||||
module Admin
|
||||
module Actions
|
||||
module Tags
|
||||
class Delete < Action
|
||||
|
||||
include Deps["repos.post_tag_repo", "repos.tag_repo"]
|
||||
|
||||
def handle(req, res)
|
||||
tag_id = req.params[:id]
|
||||
|
||||
post_tag_repo.delete(tag_id: tag_id)
|
||||
tag_repo.delete(tag_id: tag_id)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
14
slices/admin/actions/tags/index.rb
Normal file
14
slices/admin/actions/tags/index.rb
Normal file
@@ -0,0 +1,14 @@
|
||||
module Admin
|
||||
module Actions
|
||||
module Tags
|
||||
class Index < Action
|
||||
|
||||
include Deps["views.tags.index"]
|
||||
|
||||
def handle(req, res)
|
||||
res.render index
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
11
slices/admin/repos/post_tag_repo.rb
Normal file
11
slices/admin/repos/post_tag_repo.rb
Normal file
@@ -0,0 +1,11 @@
|
||||
module Admin
|
||||
module Repos
|
||||
class PostTagRepo < Adamantium::Repo[:post_tags]
|
||||
|
||||
def delete(tag_id:)
|
||||
post_tags.where(tag_id: tag_id).delete
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
end
|
16
slices/admin/repos/tag_repo.rb
Normal file
16
slices/admin/repos/tag_repo.rb
Normal file
@@ -0,0 +1,16 @@
|
||||
module Admin
|
||||
module Repos
|
||||
class TagRepo < Adamantium::Repo[:tags]
|
||||
def list
|
||||
tags
|
||||
.combine(:posts)
|
||||
.order(Sequel.function(:lower, :label))
|
||||
.to_a
|
||||
end
|
||||
|
||||
def delete(tag_id:)
|
||||
tags.by_pk(tag_id).delete
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
12
slices/admin/templates/index.html.slim
Normal file
12
slices/admin/templates/index.html.slim
Normal file
@@ -0,0 +1,12 @@
|
||||
div class="mb-12 prose dark:prose-invert max-w-prose mx-auto text-gray-800 dark:text-gray-200"
|
||||
h1 Admin
|
||||
|
||||
div class="max-w-prose mx-auto"
|
||||
ul
|
||||
li
|
||||
a href="/admin/tags" Tags
|
||||
|
||||
div class="max-w-screen-md mx-auto border-t-4 border-solid border-gray-400 dark:border-gray-600"
|
||||
|
||||
|
||||
|
56
slices/admin/templates/layouts/app.html.slim
Normal file
56
slices/admin/templates/layouts/app.html.slim
Normal file
@@ -0,0 +1,56 @@
|
||||
html
|
||||
head
|
||||
meta charest="utf-8"
|
||||
|
||||
meta name="viewport" content="width=device-width, initial-scale=1.0"
|
||||
|
||||
meta name="theme-color" content="rgb(37, 99, 235)"
|
||||
|
||||
title Daniel Nitsikopoulos
|
||||
|
||||
link rel="authorization_endpoint" href=Hanami.app.settings.micropub_authorization_endpoint
|
||||
link rel="token_endpoint" href=Hanami.app.settings.micropub_token_endpoint
|
||||
link rel="micropub" href="#{URI.join(Hanami.app.settings.micropub_site_url, "micropub")}"
|
||||
|
||||
link rel="webmention" href=Hanami.app.settings.webmention_url
|
||||
link rel="pingback" href=Hanami.app.settings.pingback_url
|
||||
link rel="feed" type="text/html" href="/posts"
|
||||
link rel="feed alternate" type="application/rss+xml" href="/feeds/rss"
|
||||
link rel="feed alternate" type="application/rss+xml" href="/feeds/statuses_rss"
|
||||
|
||||
link rel="me" href=Hanami.app.settings.mastodon_url
|
||||
link rel="me" href=Hanami.app.settings.github_url
|
||||
|
||||
link rel="stylesheet" href="/assets/index.css"
|
||||
link rel="icon" type="image/x-icon" href="/assets/favicon.ico"
|
||||
|
||||
script data-domain="dnitza.com" src="https://stats.dnitza.com/js/script.js" defer="true"
|
||||
script src="/assets/index.js"
|
||||
|
||||
script src="https://unpkg.com/htmx.org@1.9.2" integrity="sha384-L6OqL9pRWyyFU3+/bjdSri+iIphTN/bvYyM37tICVyOJkWZLpP2vGn6VUEXgzg6h" crossorigin="anonymous"
|
||||
|
||||
- if Hanami.app.settings.micropub_pub_key
|
||||
link rel="pgpkey" href="/key"
|
||||
body class="bg-white dark:bg-black selection:bg-blue-100 selection:text-blue-900 dark:selection:bg-blue-600 dark:selection:text-blue-100"
|
||||
main class="pb-8 px-4 pt-4 md:pt-8"
|
||||
header class="mb-12 max-w-screen-md mx-auto"
|
||||
div class="flex items-center mb-8 md:mb-12 text-lg md:text-xl text-gray-400 dark:text-gray-600"
|
||||
div class="flex-none mx-auto md:flex-auto md:mx-0"
|
||||
div class="h-card flex items-center"
|
||||
img class="u-photo w-6 h6 md:w-10 md:h-10 rounded-full mr-1.5" src="/assets/memoji.png"
|
||||
a href="/" rel="me" class="u-url u-uid"
|
||||
h1 class="p-name uppercase text-sm md:text-sm text-gray-400 dark:text-gray-400" = Hanami.app.settings.site_name
|
||||
nav class="space-x-1 text-sm md:text-sm uppercase md:block"
|
||||
a class="p-1 rounded text-gray-400 hover:bg-red-100 hover:text-red-400 dark:hover:bg-red-200 #{link_active?('about') ? 'text-red-600 dark:text-red-400' : ''}" href="/admin" Admin
|
||||
span class="text-gray-400 dark:text-gray-600"
|
||||
= "/"
|
||||
a class="p-1 rounded text-gray-400 hover:bg-red-100 hover:text-red-400 dark:hover:bg-red-200 #{link_active?('about') ? 'text-red-600 dark:text-red-400' : ''}" href="/admin/tags" Tags
|
||||
span class="text-gray-400 dark:text-gray-600"
|
||||
= "/"
|
||||
== yield
|
||||
div class="px-4 max-w-screen-md mx-auto pb-10"
|
||||
p class="float-left text-gray-200 dark:text-gray-600" © 2023 Daniel Nitsikopoulos. All rights reserved.
|
||||
p class="float-right text-gray-200 dark:text-gray-600"
|
||||
a href="https://xn--sr8hvo.ws/%F0%9F%8D%93%E2%9E%97%F0%9F%8E%B0/previous" ←
|
||||
a href="https://xn--sr8hvo.ws" 🕸💍
|
||||
a href="https://xn--sr8hvo.ws/%F0%9F%8D%93%E2%9E%97%F0%9F%8E%B0/next" →
|
4
slices/admin/templates/shared/_tag.html.slim
Normal file
4
slices/admin/templates/shared/_tag.html.slim
Normal file
@@ -0,0 +1,4 @@
|
||||
li id="tag-#{tag.id}"
|
||||
= "#{tag.label} (#{tag.posts.count})"
|
||||
= " — "
|
||||
button hx-delete="/admin/tags/#{tag.id}" hx-target="#tag-#{tag.id}" delete
|
17
slices/admin/templates/tags/index.html.slim
Normal file
17
slices/admin/templates/tags/index.html.slim
Normal file
@@ -0,0 +1,17 @@
|
||||
div class="mb-12 prose dark:prose-invert max-w-prose mx-auto text-gray-800 dark:text-gray-200"
|
||||
h1 Admin // Tags
|
||||
|
||||
div class="max-w-prose mx-auto"
|
||||
ul
|
||||
- unused_tags.each do |tag|
|
||||
== render "shared/tag", tag: tag
|
||||
li class="py-2"
|
||||
hr
|
||||
- used_tags.each do |tag|
|
||||
== render "shared/tag", tag: tag
|
||||
|
||||
|
||||
div class="max-w-screen-md mx-auto border-t-4 border-solid border-gray-400 dark:border-gray-600"
|
||||
|
||||
|
||||
|
6
slices/admin/view.rb
Normal file
6
slices/admin/view.rb
Normal file
@@ -0,0 +1,6 @@
|
||||
module Admin
|
||||
class View < Adamantium::View
|
||||
config.layouts_dir = "layouts"
|
||||
config.paths = "slices/admin/templates"
|
||||
end
|
||||
end
|
7
slices/admin/views/index.rb
Normal file
7
slices/admin/views/index.rb
Normal file
@@ -0,0 +1,7 @@
|
||||
module Admin
|
||||
module Views
|
||||
class Index < Admin::View
|
||||
|
||||
end
|
||||
end
|
||||
end
|
22
slices/admin/views/tags/index.rb
Normal file
22
slices/admin/views/tags/index.rb
Normal file
@@ -0,0 +1,22 @@
|
||||
module Admin
|
||||
module Views
|
||||
module Tags
|
||||
class Index < Admin::View
|
||||
|
||||
include Deps["repos.tag_repo"]
|
||||
|
||||
expose :tags do
|
||||
tag_repo.list.to_a
|
||||
end
|
||||
|
||||
expose :unused_tags do |tags|
|
||||
tags.partition {|t| t.posts.count == 0}.first
|
||||
end
|
||||
|
||||
expose :used_tags do |tags|
|
||||
tags.partition {|t| t.posts.count == 0}.last
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
Reference in New Issue
Block a user