mirror of
https://github.com/Drop-OSS/drop.git
synced 2025-11-10 04:22:09 +10:00
fix: more eslint issues
This commit is contained in:
@ -18,8 +18,8 @@ const carousel = inject(injectCarousel)!;
|
|||||||
|
|
||||||
const amount = carousel.maxSlide - carousel.minSlide + 1;
|
const amount = carousel.maxSlide - carousel.minSlide + 1;
|
||||||
|
|
||||||
function slideTo(index: number) {
|
// function slideTo(index: number) {
|
||||||
const offsetIndex = index + carousel.minSlide;
|
// const offsetIndex = index + carousel.minSlide;
|
||||||
carousel.nav.slideTo(offsetIndex);
|
// carousel.nav.slideTo(offsetIndex);
|
||||||
}
|
// }
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@ -58,7 +58,7 @@ const emit = defineEmits<{
|
|||||||
created: [collectionId: string];
|
created: [collectionId: string];
|
||||||
}>();
|
}>();
|
||||||
|
|
||||||
const open: Ref<boolean> = defineModel<boolean>();
|
const open = defineModel<boolean>({ required: true });
|
||||||
|
|
||||||
const collectionName = ref("");
|
const collectionName = ref("");
|
||||||
const createCollectionLoading = ref(false);
|
const createCollectionLoading = ref(false);
|
||||||
|
|||||||
@ -1,7 +1,7 @@
|
|||||||
<template>
|
<template>
|
||||||
<svg class="text-blue-400" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
<svg class="text-blue-400" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
<path
|
<path
|
||||||
d="M4 13.5C4 11.0008 5.38798 8.76189 7.00766 7C8.43926 5.44272 10.0519 4.25811 11.0471 3.5959C11.6287 3.20893 12.3713 3.20893 12.9529 3.5959C13.9481 4.25811 15.5607 5.44272 16.9923 7C18.612 8.76189 20 11.0008 20 13.5C20 17.9183 16.4183 21.5 12 21.5C7.58172 21.5 4 17.9183 4 13.5Z"
|
d="M4 13.5C4 11.0008 5.38798 8.76189 7.00766 7C8.43926 5.44272 10.0519 4.25811 11.0471 3.5959C11.6287 3.20893 12.3713 3.20893 12.9529 3.5959C13.9481 4.25811 15.5607 5.44272 16.9923 7C18.612 8.76189 20 11.0008 20 13.5C20 17.9183 16.4183 21.5 12 21.5C7.58172 21.5 4 17.9183 4 13.5Z"
|
||||||
stroke="currentColor" stroke-width="2" />
|
stroke="currentColor" stroke-width="2" />
|
||||||
</svg>
|
</svg>
|
||||||
</template>
|
</template>
|
||||||
@ -1,6 +1,6 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="flex flex-row items-center gap-x-2">
|
<div class="flex flex-row items-center gap-x-2">
|
||||||
<img :src="game.icon" class="w-12 h-12 rounded-sm object-cover" >
|
<img :src="game.icon" class="w-12 h-12 rounded-sm object-cover" />
|
||||||
<div class="flex flex-col items-left">
|
<div class="flex flex-col items-left">
|
||||||
<h1 class="font-semibold font-display text-lg text-zinc-100">
|
<h1 class="font-semibold font-display text-lg text-zinc-100">
|
||||||
{{ game.name }}
|
{{ game.name }}
|
||||||
@ -18,7 +18,7 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import type { GameMetadataSearchResult } from "~/server/internal/metadata/types";
|
import type { GameMetadataSearchResult } from "~/server/internal/metadata/types";
|
||||||
|
|
||||||
const props = defineProps<{
|
const { game } = defineProps<{
|
||||||
game: GameMetadataSearchResult & { sourceName?: string };
|
game: GameMetadataSearchResult & { sourceName?: string };
|
||||||
}>();
|
}>();
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@ -14,7 +14,7 @@
|
|||||||
autocomplete="off"
|
autocomplete="off"
|
||||||
class="block w-full rounded-md bg-zinc-900 py-2 pl-9 pr-2 text-sm text-zinc-100 outline outline-1 -outline-offset-1 outline-zinc-700 placeholder:text-gray-400 focus:outline focus:outline-2 focus:-outline-offset-2 focus:outline-blue-600"
|
class="block w-full rounded-md bg-zinc-900 py-2 pl-9 pr-2 text-sm text-zinc-100 outline outline-1 -outline-offset-1 outline-zinc-700 placeholder:text-gray-400 focus:outline focus:outline-2 focus:-outline-offset-2 focus:outline-blue-600"
|
||||||
placeholder="Search library..."
|
placeholder="Search library..."
|
||||||
>
|
/>
|
||||||
<MagnifyingGlassIcon
|
<MagnifyingGlassIcon
|
||||||
class="pointer-events-none absolute left-3 top-1/2 -translate-y-1/2 h-4 w-4 text-zinc-400"
|
class="pointer-events-none absolute left-3 top-1/2 -translate-y-1/2 h-4 w-4 text-zinc-400"
|
||||||
aria-hidden="true"
|
aria-hidden="true"
|
||||||
@ -37,9 +37,11 @@
|
|||||||
:src="useObject(game.mCoverId)"
|
:src="useObject(game.mCoverId)"
|
||||||
class="h-9 w-9 flex-shrink-0 rounded transition-all duration-300 group-hover:scale-105 hover:rotate-[-2deg] hover:shadow-lg"
|
class="h-9 w-9 flex-shrink-0 rounded transition-all duration-300 group-hover:scale-105 hover:rotate-[-2deg] hover:shadow-lg"
|
||||||
alt=""
|
alt=""
|
||||||
>
|
/>
|
||||||
<div class="min-w-0 flex-1 pl-2.5">
|
<div class="min-w-0 flex-1 pl-2.5">
|
||||||
<p class="text-sm font-semibold text-display text-zinc-200 truncate text-left">
|
<p
|
||||||
|
class="text-sm font-semibold text-display text-zinc-200 truncate text-left"
|
||||||
|
>
|
||||||
{{ game.mName }}
|
{{ game.mName }}
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
@ -57,7 +59,6 @@
|
|||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { HomeIcon } from "@heroicons/vue/24/outline";
|
|
||||||
import { Bars3Icon, MagnifyingGlassIcon } from "@heroicons/vue/24/solid";
|
import { Bars3Icon, MagnifyingGlassIcon } from "@heroicons/vue/24/solid";
|
||||||
|
|
||||||
const library = await useLibrary();
|
const library = await useLibrary();
|
||||||
@ -68,7 +69,7 @@ const filteredLibrary = computed(() =>
|
|||||||
library.value.entries
|
library.value.entries
|
||||||
.map((e) => e.game)
|
.map((e) => e.game)
|
||||||
.filter((e) =>
|
.filter((e) =>
|
||||||
e.mName.toLowerCase().includes(searchQuery.value.toLowerCase())
|
e.mName.toLowerCase().includes(searchQuery.value.toLowerCase()),
|
||||||
)
|
),
|
||||||
);
|
);
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@ -29,7 +29,7 @@
|
|||||||
autocomplete="off"
|
autocomplete="off"
|
||||||
class="mt-1 block w-full rounded-md bg-zinc-900 border-zinc-700 text-zinc-100 shadow-sm focus:border-primary-500 focus:ring-primary-500"
|
class="mt-1 block w-full rounded-md bg-zinc-900 border-zinc-700 text-zinc-100 shadow-sm focus:border-primary-500 focus:ring-primary-500"
|
||||||
required
|
required
|
||||||
>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div>
|
<div>
|
||||||
@ -42,7 +42,7 @@
|
|||||||
type="text"
|
type="text"
|
||||||
class="mt-1 block w-full rounded-md bg-zinc-900 border-zinc-700 text-zinc-100 shadow-sm focus:border-primary-500 focus:ring-primary-500"
|
class="mt-1 block w-full rounded-md bg-zinc-900 border-zinc-700 text-zinc-100 shadow-sm focus:border-primary-500 focus:ring-primary-500"
|
||||||
required
|
required
|
||||||
>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div>
|
<div>
|
||||||
@ -124,8 +124,8 @@
|
|||||||
accept="image/*"
|
accept="image/*"
|
||||||
class="hidden"
|
class="hidden"
|
||||||
type="file"
|
type="file"
|
||||||
@change="(e) => file = (e.target as any)?.files"
|
@change="(e) => (file = (e.target as any)?.files)"
|
||||||
>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div>
|
<div>
|
||||||
@ -155,7 +155,7 @@
|
|||||||
placeholder="Add a tag..."
|
placeholder="Add a tag..."
|
||||||
class="mt-1 block w-full rounded-md bg-zinc-900 border-zinc-700 text-zinc-100 shadow-sm focus:border-primary-500 focus:ring-primary-500"
|
class="mt-1 block w-full rounded-md bg-zinc-900 border-zinc-700 text-zinc-100 shadow-sm focus:border-primary-500 focus:ring-primary-500"
|
||||||
@keydown.enter.prevent="addTag"
|
@keydown.enter.prevent="addTag"
|
||||||
>
|
/>
|
||||||
<button
|
<button
|
||||||
type="button"
|
type="button"
|
||||||
class="mt-1 px-3 py-2 rounded-md bg-zinc-800 text-zinc-100 hover:bg-zinc-700"
|
class="mt-1 px-3 py-2 rounded-md bg-zinc-800 text-zinc-100 hover:bg-zinc-700"
|
||||||
@ -207,12 +207,10 @@ import {
|
|||||||
XCircleIcon,
|
XCircleIcon,
|
||||||
XMarkIcon,
|
XMarkIcon,
|
||||||
} from "@heroicons/vue/24/solid";
|
} from "@heroicons/vue/24/solid";
|
||||||
import type { Article } from "@prisma/client";
|
|
||||||
import { micromark } from "micromark";
|
import { micromark } from "micromark";
|
||||||
import type { SerializeObject } from "nitropack/types";
|
|
||||||
|
|
||||||
const news = useNews();
|
const news = useNews();
|
||||||
if(!news.value){
|
if (!news.value) {
|
||||||
news.value = await fetchNews();
|
news.value = await fetchNews();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -230,6 +228,8 @@ const newArticle = ref({
|
|||||||
});
|
});
|
||||||
|
|
||||||
const markdownPreview = computed(() => {
|
const markdownPreview = computed(() => {
|
||||||
|
// TODO: maybe?? add https://github.com/cure53/DOMPurify
|
||||||
|
// micromark says its safe, but this is straight html we are injecting
|
||||||
return micromark(newArticle.value.content);
|
return micromark(newArticle.value.content);
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -302,7 +302,7 @@ function addTag() {
|
|||||||
|
|
||||||
function removeTag(tagToRemove: string) {
|
function removeTag(tagToRemove: string) {
|
||||||
newArticle.value.tags = newArticle.value.tags.filter(
|
newArticle.value.tags = newArticle.value.tags.filter(
|
||||||
(tag) => tag !== tagToRemove
|
(tag) => tag !== tagToRemove,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -367,7 +367,8 @@ async function createArticle() {
|
|||||||
|
|
||||||
modalOpen.value = false;
|
modalOpen.value = false;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
error.value = (e as any)?.statusMessage ?? "An unknown error occured.";
|
// @ts-expect-error attempt to get statusMessage on error
|
||||||
|
error.value = e?.statusMessage ?? "An unknown error occured.";
|
||||||
} finally {
|
} finally {
|
||||||
loading.value = false;
|
loading.value = false;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -21,7 +21,7 @@
|
|||||||
type="text"
|
type="text"
|
||||||
class="block w-full rounded-md border-0 bg-zinc-800 py-2.5 pl-10 pr-3 text-zinc-100 placeholder:text-zinc-400 focus:ring-2 focus:ring-inset focus:ring-blue-500 sm:text-sm sm:leading-6"
|
class="block w-full rounded-md border-0 bg-zinc-800 py-2.5 pl-10 pr-3 text-zinc-100 placeholder:text-zinc-400 focus:ring-2 focus:ring-inset focus:ring-blue-500 sm:text-sm sm:leading-6"
|
||||||
placeholder="Search articles..."
|
placeholder="Search articles..."
|
||||||
>
|
/>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@ -85,7 +85,7 @@
|
|||||||
<img
|
<img
|
||||||
:src="useObject(article.image)"
|
:src="useObject(article.image)"
|
||||||
class="absolute blur-sm inset-0 w-full h-full object-cover transition-all duration-200 group-hover:scale-110"
|
class="absolute blur-sm inset-0 w-full h-full object-cover transition-all duration-200 group-hover:scale-110"
|
||||||
>
|
/>
|
||||||
<div
|
<div
|
||||||
class="absolute inset-0 bg-gradient-to-b from-transparent to-zinc-800 transition-all duration-200"
|
class="absolute inset-0 bg-gradient-to-b from-transparent to-zinc-800 transition-all duration-200"
|
||||||
/>
|
/>
|
||||||
@ -117,7 +117,7 @@ import { MagnifyingGlassIcon } from "@heroicons/vue/24/solid";
|
|||||||
import { micromark } from "micromark";
|
import { micromark } from "micromark";
|
||||||
|
|
||||||
const news = useNews();
|
const news = useNews();
|
||||||
if(!news.value){
|
if (!news.value) {
|
||||||
news.value = await fetchNews();
|
news.value = await fetchNews();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -154,6 +154,7 @@ const formatDate = (date: string) => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const formatExcerpt = (excerpt: string) => {
|
const formatExcerpt = (excerpt: string) => {
|
||||||
|
// TODO: same as one in NewsArticleCreateButton
|
||||||
// Convert markdown to HTML
|
// Convert markdown to HTML
|
||||||
const html = micromark(excerpt);
|
const html = micromark(excerpt);
|
||||||
// Strip HTML tags using regex
|
// Strip HTML tags using regex
|
||||||
@ -175,28 +176,32 @@ const filteredArticles = computed(() => {
|
|||||||
const now = new Date();
|
const now = new Date();
|
||||||
let matchesDate = true;
|
let matchesDate = true;
|
||||||
|
|
||||||
switch (dateFilter.value) {
|
switch (dateFilter.value.toLowerCase()) {
|
||||||
case "today":
|
case "today": {
|
||||||
matchesDate = articleDate.toDateString() === now.toDateString();
|
matchesDate = articleDate.toDateString() === now.toDateString();
|
||||||
break;
|
break;
|
||||||
case "week":
|
}
|
||||||
|
case "week": {
|
||||||
const weekAgo = new Date(now.setDate(now.getDate() - 7));
|
const weekAgo = new Date(now.setDate(now.getDate() - 7));
|
||||||
matchesDate = articleDate >= weekAgo;
|
matchesDate = articleDate >= weekAgo;
|
||||||
break;
|
break;
|
||||||
case "month":
|
}
|
||||||
|
case "month": {
|
||||||
matchesDate =
|
matchesDate =
|
||||||
articleDate.getMonth() === now.getMonth() &&
|
articleDate.getMonth() === now.getMonth() &&
|
||||||
articleDate.getFullYear() === now.getFullYear();
|
articleDate.getFullYear() === now.getFullYear();
|
||||||
break;
|
break;
|
||||||
case "year":
|
}
|
||||||
|
case "year": {
|
||||||
matchesDate = articleDate.getFullYear() === now.getFullYear();
|
matchesDate = articleDate.getFullYear() === now.getFullYear();
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const matchesTags =
|
const matchesTags =
|
||||||
selectedTags.value.length === 0 ||
|
selectedTags.value.length === 0 ||
|
||||||
selectedTags.value.every((tag) =>
|
selectedTags.value.every((tag) =>
|
||||||
article.tags.find((e) => e.name == tag)
|
article.tags.find((e) => e.name == tag),
|
||||||
);
|
);
|
||||||
|
|
||||||
return matchesSearch && matchesDate && matchesTags;
|
return matchesSearch && matchesDate && matchesTags;
|
||||||
|
|||||||
@ -60,8 +60,8 @@
|
|||||||
:accept="props.accept"
|
:accept="props.accept"
|
||||||
class="hidden"
|
class="hidden"
|
||||||
type="file"
|
type="file"
|
||||||
@change="(e) => file = (e.target as any)?.files"
|
@change="(e) => (file = (e.target as any)?.files)"
|
||||||
>
|
/>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -112,14 +112,15 @@ import { ref } from "vue";
|
|||||||
import {
|
import {
|
||||||
Dialog,
|
Dialog,
|
||||||
DialogPanel,
|
DialogPanel,
|
||||||
DialogTitle,
|
|
||||||
TransitionChild,
|
TransitionChild,
|
||||||
TransitionRoot,
|
TransitionRoot,
|
||||||
} from "@headlessui/vue";
|
} from "@headlessui/vue";
|
||||||
import { ArrowUpTrayIcon } from "@heroicons/vue/20/solid";
|
import { ArrowUpTrayIcon } from "@heroicons/vue/20/solid";
|
||||||
import { XCircleIcon } from "@heroicons/vue/24/solid";
|
import { XCircleIcon } from "@heroicons/vue/24/solid";
|
||||||
|
|
||||||
const open: Ref<boolean> = defineModel<boolean>() as any;
|
const open = defineModel<boolean>({
|
||||||
|
required: true,
|
||||||
|
});
|
||||||
|
|
||||||
const file = ref<FileList | undefined>();
|
const file = ref<FileList | undefined>();
|
||||||
const currentFile = computed(() => file.value?.item(0));
|
const currentFile = computed(() => file.value?.item(0));
|
||||||
|
|||||||
@ -6,7 +6,7 @@
|
|||||||
<img
|
<img
|
||||||
:src="useObject(user.profilePicture)"
|
:src="useObject(user.profilePicture)"
|
||||||
class="w-5 h-5 rounded-sm"
|
class="w-5 h-5 rounded-sm"
|
||||||
>
|
/>
|
||||||
<span class="ml-2 text-sm font-bold">{{ user.displayName }}</span>
|
<span class="ml-2 text-sm font-bold">{{ user.displayName }}</span>
|
||||||
<ChevronDownIcon class="ml-3 h-4" />
|
<ChevronDownIcon class="ml-3 h-4" />
|
||||||
</div>
|
</div>
|
||||||
@ -33,7 +33,7 @@
|
|||||||
<img
|
<img
|
||||||
:src="useObject(user.profilePicture)"
|
:src="useObject(user.profilePicture)"
|
||||||
class="w-5 h-5 rounded-sm"
|
class="w-5 h-5 rounded-sm"
|
||||||
>
|
/>
|
||||||
<span class="ml-2 text-sm font-bold">{{ user.displayName }}</span>
|
<span class="ml-2 text-sm font-bold">{{ user.displayName }}</span>
|
||||||
</div>
|
</div>
|
||||||
</NuxtLink>
|
</NuxtLink>
|
||||||
@ -45,6 +45,7 @@
|
|||||||
v-slot="{ active, close }"
|
v-slot="{ active, close }"
|
||||||
hydrate-on-visible
|
hydrate-on-visible
|
||||||
>
|
>
|
||||||
|
<!-- TODO: think this would work better as a NuxtLink instead of a button -->
|
||||||
<button
|
<button
|
||||||
:href="nav.route"
|
:href="nav.route"
|
||||||
:class="[
|
:class="[
|
||||||
@ -92,9 +93,4 @@ const navigation: NavigationItem[] = [
|
|||||||
].filter((e) => e !== undefined);
|
].filter((e) => e !== undefined);
|
||||||
|
|
||||||
const router = useRouter();
|
const router = useRouter();
|
||||||
|
|
||||||
function navigateLink(href: string, closeFn: () => any) {
|
|
||||||
closeFn();
|
|
||||||
router.push(href);
|
|
||||||
}
|
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@ -6,7 +6,7 @@ type FullCollection = Collection & {
|
|||||||
};
|
};
|
||||||
|
|
||||||
export const useCollections = async () => {
|
export const useCollections = async () => {
|
||||||
// @ts-expect-error
|
// @ts-expect-error undefined is used to tell if value has been fetched or not
|
||||||
const state = useState<FullCollection[]>("collections", () => undefined);
|
const state = useState<FullCollection[]>("collections", () => undefined);
|
||||||
if (state.value === undefined) {
|
if (state.value === undefined) {
|
||||||
state.value = await $dropFetch<FullCollection[]>("/api/v1/collection");
|
state.value = await $dropFetch<FullCollection[]>("/api/v1/collection");
|
||||||
@ -17,7 +17,9 @@ export const useCollections = async () => {
|
|||||||
|
|
||||||
export async function refreshCollection(id: string) {
|
export async function refreshCollection(id: string) {
|
||||||
const state = useState<FullCollection[]>("collections");
|
const state = useState<FullCollection[]>("collections");
|
||||||
const collection = await $dropFetch<FullCollection>(`/api/v1/collection/${id}`);
|
const collection = await $dropFetch<FullCollection>(
|
||||||
|
`/api/v1/collection/${id}`,
|
||||||
|
);
|
||||||
const index = state.value.findIndex((e) => e.id == id);
|
const index = state.value.findIndex((e) => e.id == id);
|
||||||
if (index == -1) {
|
if (index == -1) {
|
||||||
state.value.push(collection);
|
state.value.push(collection);
|
||||||
@ -27,7 +29,7 @@ export async function refreshCollection(id: string) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export const useLibrary = async () => {
|
export const useLibrary = async () => {
|
||||||
// @ts-expect-error
|
// @ts-expect-error undefined is used to tell if value has been fetched or not
|
||||||
const state = useState<FullCollection>("library", () => undefined);
|
const state = useState<FullCollection>("library", () => undefined);
|
||||||
if (state.value === undefined) {
|
if (state.value === undefined) {
|
||||||
await refreshLibrary();
|
await refreshLibrary();
|
||||||
|
|||||||
@ -31,7 +31,7 @@ export const fetchNews = async (options?: {
|
|||||||
|
|
||||||
const news = useNews();
|
const news = useNews();
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore forget why this ignor exists
|
||||||
const newValue = await $dropFetch(`/api/v1/news?${query.toString()}`);
|
const newValue = await $dropFetch(`/api/v1/news?${query.toString()}`);
|
||||||
|
|
||||||
news.value = newValue;
|
news.value = newValue;
|
||||||
|
|||||||
@ -1,5 +1,4 @@
|
|||||||
import type {
|
import type {
|
||||||
$Fetch,
|
|
||||||
ExtractedRouteMethod,
|
ExtractedRouteMethod,
|
||||||
NitroFetchOptions,
|
NitroFetchOptions,
|
||||||
NitroFetchRequest,
|
NitroFetchRequest,
|
||||||
@ -8,15 +7,15 @@ import type {
|
|||||||
|
|
||||||
interface DropFetch<
|
interface DropFetch<
|
||||||
DefaultT = unknown,
|
DefaultT = unknown,
|
||||||
DefaultR extends NitroFetchRequest = NitroFetchRequest
|
DefaultR extends NitroFetchRequest = NitroFetchRequest,
|
||||||
> {
|
> {
|
||||||
<
|
<
|
||||||
T = DefaultT,
|
T = DefaultT,
|
||||||
R extends NitroFetchRequest = DefaultR,
|
R extends NitroFetchRequest = DefaultR,
|
||||||
O extends NitroFetchOptions<R> = NitroFetchOptions<R>
|
O extends NitroFetchOptions<R> = NitroFetchOptions<R>,
|
||||||
>(
|
>(
|
||||||
request: R,
|
request: R,
|
||||||
opts?: O
|
opts?: O,
|
||||||
): Promise<
|
): Promise<
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
TypedInternalResponse<
|
TypedInternalResponse<
|
||||||
|
|||||||
@ -34,7 +34,7 @@
|
|||||||
autocomplete="username"
|
autocomplete="username"
|
||||||
required
|
required
|
||||||
class="block w-full rounded-md border-0 py-1.5 px-3 shadow-sm bg-zinc-950/20 text-zinc-300 ring-1 ring-inset ring-zinc-800 placeholder:text-zinc-400 focus:ring-2 focus:ring-inset focus:ring-blue-600 sm:text-sm sm:leading-6"
|
class="block w-full rounded-md border-0 py-1.5 px-3 shadow-sm bg-zinc-950/20 text-zinc-300 ring-1 ring-inset ring-zinc-800 placeholder:text-zinc-400 focus:ring-2 focus:ring-inset focus:ring-blue-600 sm:text-sm sm:leading-6"
|
||||||
>
|
/>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@ -53,7 +53,7 @@
|
|||||||
autocomplete="current-password"
|
autocomplete="current-password"
|
||||||
required
|
required
|
||||||
class="block w-full rounded-md border-0 py-1.5 px-3 shadow-sm bg-zinc-950/20 text-zinc-300 ring-1 ring-inset ring-zinc-800 placeholder:text-zinc-400 focus:ring-2 focus:ring-inset focus:ring-blue-600 sm:text-sm sm:leading-6"
|
class="block w-full rounded-md border-0 py-1.5 px-3 shadow-sm bg-zinc-950/20 text-zinc-300 ring-1 ring-inset ring-zinc-800 placeholder:text-zinc-400 focus:ring-2 focus:ring-inset focus:ring-blue-600 sm:text-sm sm:leading-6"
|
||||||
>
|
/>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@ -65,7 +65,7 @@
|
|||||||
name="remember-me"
|
name="remember-me"
|
||||||
type="checkbox"
|
type="checkbox"
|
||||||
class="h-4 w-4 rounded bg-zinc-800 border-zinc-700 text-blue-600 focus:ring-blue-600"
|
class="h-4 w-4 rounded bg-zinc-800 border-zinc-700 text-blue-600 focus:ring-blue-600"
|
||||||
>
|
/>
|
||||||
<label
|
<label
|
||||||
for="remember-me"
|
for="remember-me"
|
||||||
class="ml-3 block text-sm leading-6 text-zinc-400"
|
class="ml-3 block text-sm leading-6 text-zinc-400"
|
||||||
@ -113,7 +113,7 @@
|
|||||||
src="/wallpapers/signin.jpg"
|
src="/wallpapers/signin.jpg"
|
||||||
class="absolute inset-0 h-full w-full object-cover"
|
class="absolute inset-0 h-full w-full object-cover"
|
||||||
alt=""
|
alt=""
|
||||||
>
|
/>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
@ -121,7 +121,7 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { XCircleIcon } from "@heroicons/vue/20/solid";
|
import { XCircleIcon } from "@heroicons/vue/20/solid";
|
||||||
import type { User } from "@prisma/client";
|
import type { User } from "@prisma/client";
|
||||||
import Logo from "~/components/Logo.vue";
|
import Logo from "~/components/DropLogo.vue";
|
||||||
|
|
||||||
const username = ref("");
|
const username = ref("");
|
||||||
const password = ref("");
|
const password = ref("");
|
||||||
|
|||||||
@ -22,13 +22,13 @@
|
|||||||
src="/wallpapers/signin.jpg"
|
src="/wallpapers/signin.jpg"
|
||||||
class="absolute inset-0 h-full w-full object-cover"
|
class="absolute inset-0 h-full w-full object-cover"
|
||||||
alt=""
|
alt=""
|
||||||
>
|
/>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import Logo from "~/components/Logo.vue";
|
import Logo from "~/components/DropLogo.vue";
|
||||||
const router = useRouter();
|
const router = useRouter();
|
||||||
|
|
||||||
// Clear the user state
|
// Clear the user state
|
||||||
|
|||||||
@ -70,9 +70,9 @@
|
|||||||
class="whitespace-nowrap inline-flex gap-x-4 px-3 py-4 text-sm text-zinc-400"
|
class="whitespace-nowrap inline-flex gap-x-4 px-3 py-4 text-sm text-zinc-400"
|
||||||
>
|
>
|
||||||
<component
|
<component
|
||||||
|
:is="PLATFORM_ICONS[platform]"
|
||||||
v-for="platform in platforms"
|
v-for="platform in platforms"
|
||||||
:key="platform"
|
:key="platform"
|
||||||
:is="PLATFORM_ICONS[platform]"
|
|
||||||
class="text-blue-600 w-6 h-6"
|
class="text-blue-600 w-6 h-6"
|
||||||
/>
|
/>
|
||||||
<span
|
<span
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
import { APITokenMode } from "@prisma/client";
|
import { APITokenMode } from "@prisma/client";
|
||||||
import { DateTime } from "luxon";
|
import { DateTime } from "luxon";
|
||||||
import { UserACL } from "~/server/internal/acls";
|
import type { UserACL } from "~/server/internal/acls";
|
||||||
import { defineClientEventHandler } from "~/server/internal/clients/event-handler";
|
import { defineClientEventHandler } from "~/server/internal/clients/event-handler";
|
||||||
import prisma from "~/server/internal/db/database";
|
import prisma from "~/server/internal/db/database";
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user