PronounsPage/app/components/admin/AdminStorageItem.vue
Valentyne Stigloher 10180aa6a3 (refactor) use #shared alias instead of ~~/shared
the #shared alias used by Nuxt cannot be easily disabled and to prevent breackage with jiti, we make use of it
2025-08-17 18:56:02 +02:00

86 lines
2.3 KiB
Vue

<script setup lang="ts">
import { formatSize } from '#shared/helpers.ts';
import { adminStorageRefreshInjectionKey } from '#shared/injectionKeys.ts';
const props = defineProps<{
itemKey: string;
size: number;
}>();
const chunk = computed(() => props.itemKey.replace(/^.+:/, ''));
const isOpen = ref(false);
const contentUrl = computed(() => `/api/admin/storage/items/${props.itemKey}`);
const contentAsyncData = useFetch(contentUrl.value, {
immediate: false,
});
watch(isOpen, async () => {
if (isOpen.value) {
await contentAsyncData.execute();
}
});
const adminStorageRefresh = inject(adminStorageRefreshInjectionKey);
const dialogue = useDialogue();
const remove = async () => {
try {
await dialogue.confirm(`Are you sure you want to remove ${props.itemKey}?`, 'danger');
} catch (error) {
if (error === undefined) {
return;
}
throw error;
}
await $fetch(contentUrl.value, { method: 'DELETE' });
if (adminStorageRefresh) {
await adminStorageRefresh();
}
};
</script>
<template>
<details @toggle="isOpen = $event.newState === 'open'">
<summary>
<span class="py-1 d-inline-flex justify-content-between align-items-start">
<code>{{ chunk }}</code>
<span>
<span class="badge text-bg-info">{{ formatSize(size) }}</span>
<button type="button" class="btn btn-sm btn-outline-danger" @click="remove()">
<Icon v="trash" />
</button>
</span>
</span>
</summary>
<div v-if="isOpen" class="ps-3">
<template v-if="contentAsyncData.status.value === 'success'">
<img
v-if="itemKey.endsWith('.png')"
:src="contentUrl"
:alt="`Image content for storage key ${itemKey}`"
>
<pre v-else class="mb-0">{{ contentAsyncData.data }}</pre>
</template>
<Spinner v-else />
</div>
</details>
</template>
<style scoped lang="scss">
@import 'assets/variables';
summary > span {
width: calc(100% - #{$spacer});
}
img {
max-width: 100%;
}
pre {
max-height: 80vh;
}
</style>