import { ref } from 'vue' import { defineStore } from 'pinia' export type AppBannerType = 'success' | 'info' | 'warning' | 'error' export interface AppBannerMessage { id: string type: AppBannerType title?: string message: string createdAt: number } interface PushBannerInput { type?: AppBannerType title?: string message: string } const MAX_BANNERS = 8 function createBannerId() { if (typeof crypto !== 'undefined' && typeof crypto.randomUUID === 'function') { return crypto.randomUUID() } return `banner-${Date.now()}-${Math.random().toString(36).slice(2, 9)}` } export const useAppBannersStore = defineStore('app-banners', () => { const banners = ref([]) function push(input: PushBannerInput) { const now = Date.now() const type = input.type ?? 'info' const normalizedMessage = input.message.trim() if (normalizedMessage.length === 0) { return '' } const lastBanner = banners.value[banners.value.length - 1] if ( lastBanner && lastBanner.type === type && lastBanner.message === normalizedMessage && now - lastBanner.createdAt < 1200 ) { return lastBanner.id } const banner: AppBannerMessage = { id: createBannerId(), type, title: input.title, message: normalizedMessage, createdAt: now, } banners.value = [...banners.value, banner].slice(-MAX_BANNERS) return banner.id } function pushError(message: string, title = 'Fehler') { return push({ type: 'error', title, message }) } function dismiss(id: string) { banners.value = banners.value.filter((banner) => banner.id !== id) } function clear() { banners.value = [] } return { banners, push, pushError, dismiss, clear, } })