added admin area to delete feeds

This commit is contained in:
2026-06-09 21:55:07 +02:00
parent 6ae6490dec
commit 400648c3d1
5 changed files with 401 additions and 0 deletions
+133
View File
@@ -0,0 +1,133 @@
<script setup>
import { ref, onMounted } from 'vue'
import axios from 'axios'
const feeds = ref([])
const error = ref('')
function authHeaders() {
return {
headers: {
'Content-Type': 'application/json',
'user-token': localStorage.getItem('user-token'),
},
}
}
async function loadFeeds() {
const userId = localStorage.getItem('user-id')
try {
const response = await axios.get(`/api/v1/article/feeds/${userId}`, authHeaders())
feeds.value = response.data.feeds
} catch (e) {
error.value = 'Failed to load feeds.'
}
}
async function deleteFeed(feedId) {
if (!window.confirm('Delete this feed and all its articles?')) return
try {
await axios.delete(`/api/v1/article/feed/${feedId}`, authHeaders())
feeds.value = feeds.value.filter(f => f.id !== feedId)
} catch (e) {
error.value = 'Failed to delete feed.'
}
}
onMounted(loadFeeds)
</script>
<template>
<div class="admin">
<h1 class="admin__heading">Admin</h1>
<p v-if="error" class="admin__error">{{ error }}</p>
<p v-else-if="feeds.length === 0" class="admin__empty">No feeds added yet.</p>
<ul v-else class="admin__list">
<li v-for="feed in feeds" :key="feed.id" class="admin__item">
<div class="admin__item-info">
<span class="admin__item-title">{{ feed.title }}</span>
<a :href="feed.url" class="admin__item-url" target="_blank" rel="noopener">{{ feed.url }}</a>
</div>
<button class="admin__delete" type="button" @click="deleteFeed(feed.id)">Delete</button>
</li>
</ul>
</div>
</template>
<style scoped>
.admin {
padding: 1.5rem 1rem;
max-width: 720px;
margin: 0 auto;
}
.admin__heading {
font-size: 1.25rem;
font-weight: bold;
margin-bottom: 1.25rem;
}
.admin__error,
.admin__empty {
opacity: 0.6;
}
.admin__list {
list-style: none;
padding: 0;
margin: 0;
display: flex;
flex-direction: column;
gap: 0.75rem;
}
.admin__item {
display: flex;
align-items: center;
justify-content: space-between;
gap: 1rem;
padding: 0.75rem 1rem;
border: 1px solid var(--color-border);
border-radius: 6px;
background: var(--color-background-soft);
}
.admin__item-info {
display: flex;
flex-direction: column;
gap: 0.2rem;
min-width: 0;
}
.admin__item-title {
font-weight: 600;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.admin__item-url {
font-size: 0.8rem;
opacity: 0.6;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
color: inherit;
}
.admin__delete {
flex-shrink: 0;
min-height: 36px;
padding: 0.3rem 0.9rem;
border: 1px solid var(--color-border);
border-radius: 4px;
background: transparent;
color: var(--color-text);
font: inherit;
cursor: pointer;
}
.admin__delete:hover {
border-color: var(--color-border-hover);
}
</style>
+9
View File
@@ -0,0 +1,9 @@
<script setup>
import AdminFeeds from '../components/AdminFeeds.vue'
</script>
<template>
<main>
<AdminFeeds />
</main>
</template>