Creating admin pages, new brand API endpoint

This commit is contained in:
2024-09-25 15:42:05 +02:00
parent 6dd49f630d
commit 0856540441
28 changed files with 417 additions and 76 deletions

View File

@@ -12,7 +12,7 @@ const accountStore = useAccountStore()
<template>
<card-view
icon="mdi-home"
:title="$t('account.addresses')"
:title="$t('account.address')"
>
<v-expansion-panels v-if="accountStore.userAccount.addresses.length > 0">
<v-expansion-panel

View File

@@ -12,7 +12,7 @@ const accountStore = useAccountStore()
<template>
<card-view
icon="mdi-currency-usd"
:title="$t('account.payments')"
:title="$t('account.payment')"
>
<v-expansion-panels
v-if="accountStore.userAccount.payments.length > 0"

View File

@@ -0,0 +1,6 @@
<script setup lang="ts">
</script>
<template>
Accounts Page
</template>

View File

@@ -0,0 +1,6 @@
<script setup lang="ts">
</script>
<template>
Categories Page
</template>

View File

@@ -0,0 +1,6 @@
<script setup lang="ts">
</script>
<template>
Admin Dashboard Page
</template>

View File

@@ -0,0 +1,98 @@
<script setup lang="ts">
import cardView from '@/components/cardView.vue';
import { ProductModel } from '@/data/models/productModel';
import { useProductStore } from '@/data/stores/productStore';
import productEditDialog from './productEditDialog.vue';
import { ref } from 'vue';
const productStore = useProductStore()
const editProduct = ref(new ProductModel())
const showEditProductDialog = ref(false)
const headers = [
{ title: "Category", value: "category.name" },
{ title: "Brand", value: "brand.name" },
{ title: "Name", value: "name" },
{ title: "Price", value: "price" },
{ title: "Discount", value: "discount" },
{ title: "Rating", value: "rating" },
{ title: "In stock", value: "inStock" },
{ title: "Edit", value: "edit" },
]
function openEditProductDialog(product: ProductModel) {
editProduct.value = product
showEditProductDialog.value = true
}
</script>
<template>
<v-container>
<v-row>
<v-col>
<card-view
:title="$t('product.product', 2)"
:subtitle="productStore.products.length + ' ' + $t('product.product', productStore.products.length)"
icon="mdi-store"
>
<v-data-table
:headers="headers"
:items="productStore.products"
>
<template v-slot:item.price="{ item }">
{{ item.price }}
</template>
<template v-slot:item.discount="{ item }">
<div v-if="item.discount > 0">
{{ item.discount }} %
</div>
</template>
<template v-slot:item.inStock="{ item }">
<div v-if="item.inStock > 5" class="text-green-lighten-1">
<v-icon icon="mdi-check" />
{{ $t("product.storedItemsAvailable", [item.inStock]) }}
</div>
<div v-else-if="item.inStock > 0" class="text-orange-lighten-1">
<v-icon icon="mdi-alert" />
{{ $t("product.storedItemsAvailable", [item.inStock]) }}
</div>
<div v-else class="text-red">
<v-icon icon="mdi-alert-circle" />
{{ $t("product.soldOut") }}
</div>
</template>
<template v-slot:item.edit="{ item }">
<v-btn
icon="mdi-pencil"
color="orange"
variant="text"
@click="openEditProductDialog(item)"
/>
<v-btn
icon="mdi-store-off"
color="red"
variant="text"
v-if="item.offered"
/>
<v-btn
icon="mdi-store"
color="green"
variant="text"
v-if="!item.offered"
/>
</template>
</v-data-table>
</card-view>
</v-col>
</v-row>
</v-container>
<product-edit-dialog
v-model="showEditProductDialog"
:edit-product="editProduct" />
</template>

View File

@@ -0,0 +1,116 @@
<script setup lang="ts">
import actionDialog from '@/components/actionDialog.vue';
import { ProductModel } from '@/data/models/productModel';
import outlinedButton from '@/components/outlinedButton.vue';
import { useProductStore } from '@/data/stores/productStore';
import { ModelRef } from 'vue';
const showDialog: ModelRef<boolean> = defineModel()
const editProduct = defineModel("editProduct", { type: ProductModel, required: true})
const productStore = useProductStore()
function saveProduct() {
// todo
showDialog.value = false
}
</script>
<template>
<action-dialog
:title="$t('editProduct')"
icon="mdi-store-edit"
v-model="showDialog"
>
<v-row>
<v-col>
<v-select
:items="productStore.categories"
v-model="editProduct.category"
:label="$t('category')"
>
<template v-slot:item="{ props, item }">
<v-list-item v-bind="props" :prepend-icon="item.raw.icon" :title="item.raw.name" />
</template>
<template v-slot:selection="{ item }">
<v-list-item :prepend-icon="item.raw.icon" :title="item.raw.name" />
</template>
</v-select>
</v-col>
<v-col>
<v-select
:items="productStore.brands"
v-model="editProduct.brand"
:label="$t('brand')"
>
<template v-slot:item="{ props, item }">
<v-list-item v-bind="props" :title="item.raw.name" />
</template>
<template v-slot:selection="{ item }">
<v-list-item :title="item.raw.name" />
</template>
</v-select>
</v-col>
</v-row>
<v-row>
<v-col>
<v-text-field
v-model="editProduct.name"
:label="$t('product.productName')"
/>
</v-col>
</v-row>
<v-row>
<v-col>
<v-textarea
v-model="editProduct.description"
:label="$t('product.description')"
/>
</v-col>
</v-row>
<v-row>
<v-col>
<v-text-field
v-model="editProduct.price"
:label="$t('product.productPrice')"
suffix="€"
/>
</v-col>
<v-col>
<v-text-field
v-model="editProduct.discount"
:label="$t('product.discount')"
/>
</v-col>
</v-row>
<v-row>
<v-col>
<v-text-field
v-model="editProduct.inStock"
:label="$t('product.inStock')"
/>
</v-col>
</v-row>
<!-- todo -->
{{ editProduct.images }}
{{ editProduct.specs }}
<template #actions>
<outlined-button
color="green"
prepend-icon="mdi-content-save"
@click="saveProduct"
>
{{ $t('save') }}
</outlined-button>
</template>
</action-dialog>
</template>

View File

@@ -91,6 +91,7 @@ async function doOrder() {
@click="showDialog = false"
prepend-icon="mdi-close"
color="orange"
:disabled="orderingInProgress"
>
{{ $t('dialog.cancel') }}
</outlined-button>

View File

@@ -1,10 +1,8 @@
<script setup lang="ts">
import { SortOrder } from '@/data/enums/sortOrderEnum';
import { useCategoryStore } from '@/data/stores/categoryStore';
import { useProductStore } from '@/data/stores/productStore';
const productStore = useProductStore()
const categoryStore = useCategoryStore()
const sortOrderItems = Object.values(SortOrder)
</script>
@@ -19,8 +17,8 @@ const sortOrderItems = Object.values(SortOrder)
<v-list-item>
<v-select
:items="categoryStore.categories"
:label="$t('categories')"
:items="productStore.categories"
:label="$t('category', 2)"
v-model="productStore.filteredCategory"
>
<template v-slot:item="{ props, item }">