140 lines
3.5 KiB
Vue
140 lines
3.5 KiB
Vue
<script setup>
|
|
definePageMeta({
|
|
layout: "custom"
|
|
});
|
|
|
|
const { makes } = useCars();
|
|
const user = useSupabaseUser();
|
|
const supabase = useSupabaseClient();
|
|
|
|
const info = useState('adInfo', () => {
|
|
return {
|
|
make: '',
|
|
model: "",
|
|
year: "",
|
|
miles: "",
|
|
price: "",
|
|
city: "",
|
|
seats: "",
|
|
features: "",
|
|
description: "",
|
|
image: null
|
|
}
|
|
});
|
|
|
|
const errorMessage = ref("");
|
|
|
|
const onChangeInput = (data, name) => {
|
|
info.value[name] = data;
|
|
};
|
|
|
|
const inputs = [
|
|
{
|
|
id: 1,
|
|
title: "Model *",
|
|
name: "model",
|
|
placeholder: "Civic"
|
|
},
|
|
{
|
|
id: 2,
|
|
title: "Year *",
|
|
name: "year",
|
|
placeholder: "2020"
|
|
},
|
|
{
|
|
id: 3,
|
|
title: "Price *",
|
|
name: "price",
|
|
placeholder: "10000"
|
|
},
|
|
{
|
|
id: 4,
|
|
title: "Miles *",
|
|
name: "miles",
|
|
placeholder: "10000"
|
|
},
|
|
{
|
|
id: 5,
|
|
title: "City *",
|
|
name: "city",
|
|
placeholder: "Austin"
|
|
},
|
|
{
|
|
id: 6,
|
|
title: "Number of Seats *",
|
|
name: "seats",
|
|
placeholder: "5"
|
|
},
|
|
{
|
|
id: 7,
|
|
title: "Features *",
|
|
name: "features",
|
|
placeholder: "Leather Interior, No Accidents"
|
|
},
|
|
];
|
|
|
|
const isButtonDisabled = computed(() => {
|
|
console.log(info.value);
|
|
for (let key in info.value) {
|
|
console.log(`key ${key} - ${info.value[key]}`);
|
|
if (!info.value[key]) return true;
|
|
}
|
|
return false;
|
|
});
|
|
|
|
const handleSubmit = async () => {
|
|
const fileName = Math.floor(Math.random() * 100000000000000);
|
|
const { data, error } = await supabase.storage.from("images").upload("public/" + fileName, info.value.image);
|
|
|
|
if (error) {
|
|
return errorMessage.value = "cannot upload image";
|
|
}
|
|
const body = {
|
|
...info.value,
|
|
features: info.value.features.split(', '),
|
|
numberOfSeats: parseInt(info.value.seats),
|
|
year: parseInt(info.value.year),
|
|
miles: parseInt(info.value.miles),
|
|
price: parseInt(info.value.price),
|
|
name: `${info.value.make} ${info.value.model}`,
|
|
image: data.path,
|
|
listerId: user.value.id
|
|
}
|
|
|
|
delete body.seats;
|
|
|
|
console.log(body);
|
|
try {
|
|
const response = await $fetch("/api/car/listings", {
|
|
method: "post",
|
|
body
|
|
});
|
|
navigateTo('/profile/listings')
|
|
} catch (error) {
|
|
errorMessage.value = error.statusMessage;
|
|
|
|
await supabase.storage.from("images").remove(data.path);
|
|
}
|
|
|
|
};
|
|
</script>
|
|
|
|
<template>
|
|
<div>
|
|
<div class="mt-24">
|
|
<h1 class="text-6xl mt-24">Create a new Listing</h1>
|
|
</div>
|
|
<div class="shadow rounded p-3 mt-5 flex flex-wrap justify-between">
|
|
<CarAdSelect title="Make *" :options="makes" name="make" @change-input="onChangeInput" />
|
|
<CarAdInput v-for="input in inputs" :key="input.id" :title="input.title" :name="input.name"
|
|
:placeholder="input.placeholder" @changeInput="onChangeInput" />
|
|
<CarAdTextarea title="Description *" name="description" @change-input="onChangeInput" />
|
|
<CarAdImage title="Image *" @change-input="onChangeInput" />
|
|
<div>
|
|
<button class="bg-blue-400 text-white rounded py-2 px-7 mt-3" :disabled="isButtonDisabled"
|
|
@click="handleSubmit">Submit</button>
|
|
</div>
|
|
<p v-if="errorMessage" class="mt-3 text-red-400">{{ errorMessage }}</p>
|
|
</div>
|
|
</div>
|
|
</template> |