add sweetAlert2 for all Alerts in pages

This commit is contained in:
Diyar Akhgar 2025-06-29 02:36:05 +03:30
parent e8a4d5b597
commit dfcc5cb94c
21 changed files with 1041 additions and 389 deletions

View File

@ -102,7 +102,7 @@
</template> </template>
<script> <script>
export default { export default {
name: 'AddUserModal', name: 'AddUserModal',
props: { props: {
isVisible: { isVisible: {
@ -125,17 +125,14 @@ export default {
watch: { watch: {
isVisible(newVal) { isVisible(newVal) {
if (newVal) { if (newVal) {
// غیرفعال کردن اسکرول هنگام باز شدن پاپآپ
document.body.style.overflow = 'hidden'; document.body.style.overflow = 'hidden';
} else { } else {
// فعال کردن اسکرول هنگام بسته شدن پاپآپ
document.body.style.overflow = ''; document.body.style.overflow = '';
} }
}, },
}, },
methods: { methods: {
beforeDestroy() { beforeDestroy() {
// اطمینان از فعال شدن اسکرول هنگام حذف کامپوننت
document.body.style.overflow = ''; document.body.style.overflow = '';
}, },
close() { close() {
@ -150,15 +147,34 @@ export default {
this.$emit('close'); this.$emit('close');
}, },
handleSubmit() { handleSubmit() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
if (!this.newUser.first_name || !this.newUser.last_name || !this.newUser.mobile_number || !this.newUser.password || !this.newUser.semat) { if (!this.newUser.first_name || !this.newUser.last_name || !this.newUser.mobile_number || !this.newUser.password || !this.newUser.semat) {
alert('لطفاً تمام فیلدها را پر کنید.'); // Show error Toast for incomplete fields
Toast.fire({
icon: 'error',
title: 'لطفاً تمام فیلدها را پر کنید.',
});
return; return;
} }
this.$emit('add-user', { ...this.newUser }); this.$emit('add-user', { ...this.newUser });
this.close(); this.close();
}, },
}, },
}; };
</script> </script>
<style scoped> <style scoped>

View File

@ -51,7 +51,7 @@
<span>مبلغ قابل پرداخت:</span> <span>مبلغ قابل پرداخت:</span>
<span>{{ selectedPlan.total.toLocaleString() }} تومان</span> <span>{{ selectedPlan.total.toLocaleString() }} تومان</span>
</div> </div>
<button class="primary-button" style="width: 100%;" @click="pay">پرداخت</button> <button class="primary-button" style="width: 100%;max-width: 100%;" @click="pay">پرداخت</button>
</div> </div>
</div> </div>
</template> </template>
@ -66,7 +66,7 @@ export default {
availableMemberOptions: { type: Array, default: () => [5, 10, 20, 100] }, availableMemberOptions: { type: Array, default: () => [5, 10, 20, 100] },
baseUrl: { type: String, required: true }, baseUrl: { type: String, required: true },
hasActiveSubscription: { type: Boolean, default: false }, hasActiveSubscription: { type: Boolean, default: false },
hasExpiredSubscription: { type: Boolean, default: false }, // جدید hasExpiredSubscription: { type: Boolean, default: false },
}, },
data() { data() {
return { return {
@ -92,18 +92,43 @@ export default {
this.selectedPlan = { ...plan, basePrice: base, tax, total: base + tax }; this.selectedPlan = { ...plan, basePrice: base, tax, total: base + tax };
}, },
async pay() { async pay() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimeritarian
toast.onmouseleave = this.$swal.resumeTimer;
},
});
if (this.hasActiveSubscription) { if (this.hasActiveSubscription) {
alert('شما اشتراک فعالی دارید و نمی‌توانید اشتراک دیگری خریداری کنید.'); Toast.fire({
icon: 'warning',
title: 'شما اشتراک فعالی دارید و نمی‌توانید اشتراک دیگری خریداری کنید.',
});
return; return;
} }
if (this.hasExpiredSubscription) { if (this.hasExpiredSubscription) {
alert('شما یکبار اشتراک تهیه کردید و نمی‌توانید دوباره اشتراک تهیه کنید.'); Toast.fire({
icon: 'warning',
title: 'شما یکبار اشتراک تهیه کردید و نمی‌توانید دوباره اشتراک تهیه کنید.',
});
return; return;
} }
if (!this.selectedPlan) { if (!this.selectedPlan) {
alert('لطفاً یک طرح اشتراک انتخاب کنید.'); Toast.fire({
icon: 'error',
title: 'لطفاً یک طرح اشتراک انتخاب کنید.',
});
return; return;
} }
try { try {
const startTime = new Date().toISOString(); const startTime = new Date().toISOString();
const endTime = this.calculateEndTime(this.selectedPlan.name); const endTime = this.calculateEndTime(this.selectedPlan.name);
@ -114,16 +139,50 @@ export default {
endTime, endTime,
price: this.selectedPlan.total, price: this.selectedPlan.total,
}; };
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
if (!token) throw new Error('توکن احراز هویت یافت نشد.'); if (!token) {
Toast.fire({
icon: 'error',
title: 'توکن احراز هویت یافت نشد.',
});
throw new Error('Authentication token not found.');
}
const response = await axios.post(`${this.baseUrl}/add_subscription/`, subscriptionData, { const response = await axios.post(`${this.baseUrl}/add_subscription/`, subscriptionData, {
headers: { Authorization: `Token ${token}`, 'Content-Type': 'application/json' }, headers: { Authorization: `Token ${token}`, 'Content-Type': 'application/json' },
}); });
this.$emit('payment-success', { subscriptionId: response.data.subscription_id }); this.$emit('payment-success', { subscriptionId: response.data.subscription_id });
// Show success Toast
Toast.fire({
icon: 'success',
title: 'اشFinally با موفقیت ثبت شد.',
});
this.selectedPlan = null; this.selectedPlan = null;
} catch (error) { } catch (error) {
let errorMessage = 'خطا در ثبت اشتراک. لطفاً دوباره تلاش کنید.';
if (error.response) {
if (error.response.status === 401) {
errorMessage = 'توکن احراز هویت نامعتبر است.';
} else if (error.response.status === 400) {
errorMessage = 'اطلاعات ورودی نامعتبر است.';
} else {
errorMessage = error.response.data.message || errorMessage;
}
} else if (error.request) {
errorMessage = 'مشکل در ارتباط با سرور. لطفاً دوباره تلاش کنید.';
}
// Show error Toast
Toast.fire({
icon: 'error',
title: errorMessage,
});
console.error('Error registering subscription:', error); console.error('Error registering subscription:', error);
alert('خطا در ثبت اشتراک. لطفاً دوباره تلاش کنید.');
} }
}, },
calculateEndTime(planName) { calculateEndTime(planName) {
@ -140,6 +199,7 @@ export default {
}; };
</script> </script>
<style scoped> <style scoped>
.buy-subscription-container { .buy-subscription-container {
direction: rtl; direction: rtl;

View File

@ -433,9 +433,12 @@ export default {
customer() { customer() {
return JSON.parse(localStorage.getItem('customer') || '{}'); return JSON.parse(localStorage.getItem('customer') || '{}');
}, },
userInfo() {
return JSON.parse(localStorage.getItem('user') || '{}');
},
fullName() { fullName() {
return this.customer.first_name && this.customer.last_name return this.userInfo.first_name && this.userInfo.last_name
? `${this.customer.first_name} ${this.customer.last_name}` ? `${this.userInfo.first_name} ${this.userInfo.last_name}`
: 'کاربر مهمان'; : 'کاربر مهمان';
}, },
userPhone() { userPhone() {
@ -448,7 +451,7 @@ export default {
return this.customer.profile_img || this.defaultProfileIcon; return this.customer.profile_img || this.defaultProfileIcon;
}, },
userId() { userId() {
return this.customer.id || null; return this.customer.user_id || null;
}, },
}, },
watch: { watch: {
@ -482,19 +485,47 @@ export default {
}, },
methods: { methods: {
async fetchTeamMembers() { async fetchTeamMembers() {
// Define Toast configuration for SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
if (!token) throw new Error('توکن احراز هویت پیدا نشد'); if (!token) {
throw new Error('توکن احراز هویت پیدا نشد');
}
const response = await axios.get(`${API_BASE_URL}/get_all_team_members`, { const response = await axios.get(`${API_BASE_URL}/get_all_team_members`, {
headers: { Authorization: `Token ${token.trim()}` }, headers: { Authorization: `Token ${token.trim()}` },
}); });
this.teamMembers = response.data.members.filter( this.teamMembers = response.data.members.filter(
(member) => member.user?.id && member.user.first_name && member.user.last_name (member) => member.user?.id && member.user.first_name && member.user.last_name
); );
} catch (error) { } catch (error) {
if (error.response?.status === 403) { if (error.response?.status === 403) {
alert('لطفاً دوباره وارد شوید'); // Show unauthorized error Toast and redirect to login
Toast.fire({
icon: 'error',
title: 'لطفاً دوباره وارد شوید',
});
window.location.href = '/login'; window.location.href = '/login';
} else {
// Show general error Toast for team members fetch
Toast.fire({
icon: 'error',
title: 'خطا در بارگذاری لیست اعضای تیم',
});
} }
this.error = 'خطا در بارگذاری لیست اعضای تیم'; this.error = 'خطا در بارگذاری لیست اعضای تیم';
} }
@ -528,23 +559,60 @@ export default {
return member ? `${member.user.first_name} ${member.user.last_name}` : ''; return member ? `${member.user.first_name} ${member.user.last_name}` : '';
}, },
addParticipant() { addParticipant() {
// Define Toast configuration for SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
if (!this.selectedParticipantId) { if (!this.selectedParticipantId) {
// Show error Toast for no participant selected
Toast.fire({
icon: 'error',
title: 'لطفاً یک عضو تیم انتخاب کنید.',
});
this.error = 'لطفاً یک عضو تیم انتخاب کنید.'; this.error = 'لطفاً یک عضو تیم انتخاب کنید.';
return; return;
} }
const selectedMember = this.teamMembers.find((member) => member.user.id === this.selectedParticipantId); const selectedMember = this.teamMembers.find((member) => member.user.id === this.selectedParticipantId);
if (!selectedMember) { if (!selectedMember) {
// Show error Toast for invalid participant
Toast.fire({
icon: 'error',
title: 'کاربر انتخاب‌شده یافت نشد.',
});
this.error = 'کاربر انتخاب‌شده یافت نشد.'; this.error = 'کاربر انتخاب‌شده یافت نشد.';
return; return;
} }
if (this.participants.some((p) => p.id === this.selectedParticipantId)) { if (this.participants.some((p) => p.id === this.selectedParticipantId)) {
// Show error Toast for duplicate participant
Toast.fire({
icon: 'error',
title: 'این کاربر قبلاً اضافه شده است.',
});
this.error = 'این کاربر قبلاً اضافه شده است.'; this.error = 'این کاربر قبلاً اضافه شده است.';
return; return;
} }
if (this.selectedParticipantId === this.userId) { if (this.selectedParticipantId === this.userId) {
// Show error Toast for adding self
Toast.fire({
icon: 'error',
title: 'نمی‌توانید خودتان را به‌عنوان شرکت‌کننده اضافه کنید.',
});
this.error = 'نمی‌توانید خودتان را به‌عنوان شرکت‌کننده اضافه کنید.'; this.error = 'نمی‌توانید خودتان را به‌عنوان شرکت‌کننده اضافه کنید.';
return; return;
} }
this.participants.push({ this.participants.push({
id: selectedMember.user.id, id: selectedMember.user.id,
phone: selectedMember.mobile_number, phone: selectedMember.mobile_number,
@ -552,9 +620,11 @@ export default {
role: selectedMember.semat || 'بدون سمت', role: selectedMember.semat || 'بدون سمت',
profile_img: selectedMember.profile_img || this.defaultProfileIcon, profile_img: selectedMember.profile_img || this.defaultProfileIcon,
}); });
this.selectedParticipantId = ''; this.selectedParticipantId = '';
this.isDropdownOpen = false; this.isDropdownOpen = false;
this.error = null; this.error = null;
}, },
removeParticipant(id) { removeParticipant(id) {
this.participants = this.participants.filter((p) => p.id !== id); this.participants = this.participants.filter((p) => p.id !== id);
@ -569,7 +639,6 @@ export default {
this.$emit('close'); this.$emit('close');
this.resetForm(); this.resetForm();
}, },
resetForm() { resetForm() {
this.form = { this.form = {
title: '', title: '',
@ -598,25 +667,62 @@ export default {
if (this.form[field] > 0) this.form[field]--; if (this.form[field] > 0) this.form[field]--;
}, },
async handleSubmit() { async handleSubmit() {
// Define Toast configuration for SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
if (!this.form.title || !this.form.date) { if (!this.form.title || !this.form.date) {
// Show error Toast for missing title or date
Toast.fire({
icon: 'error',
title: 'لطفاً نام جلسه و تاریخ را وارد کنید.',
});
this.error = 'لطفاً نام جلسه و تاریخ را وارد کنید.'; this.error = 'لطفاً نام جلسه و تاریخ را وارد کنید.';
return; return;
} }
if (!this.form.selectedRoom || this.form.space === null || this.form.asset_bundle === null) { if (!this.form.selectedRoom || this.form.space === null || this.form.asset_bundle === null) {
// Show error Toast for missing room selection
Toast.fire({
icon: 'error',
title: 'لطفاً یک اتاق برای جلسه انتخاب کنید.',
});
this.error = 'لطفاً یک اتاق برای جلسه انتخاب کنید.'; this.error = 'لطفاً یک اتاق برای جلسه انتخاب کنید.';
return; return;
} }
const momentDate = moment(this.form.date, 'jYYYY/jMM/jDD'); const momentDate = moment(this.form.date, 'jYYYY/jMM/jDD');
if (!momentDate.isValid()) { if (!momentDate.isValid()) {
// Show error Toast for invalid date
Toast.fire({
icon: 'error',
title: 'تاریخ وارد شده معتبر نیست.',
});
this.error = 'تاریخ وارد شده معتبر نیست.'; this.error = 'تاریخ وارد شده معتبر نیست.';
return; return;
} }
const startTimeInMinutes = this.form.startHour * 60 + this.form.startMinute; const startTimeInMinutes = this.form.startHour * 60 + this.form.startMinute;
const endTimeInMinutes = this.form.endHour * 60 + this.form.endMinute; const endTimeInMinutes = this.form.endHour * 60 + this.form.endMinute;
if (endTimeInMinutes <= startTimeInMinutes) { if (endTimeInMinutes <= startTimeInMinutes) {
// Show error Toast for invalid time range
Toast.fire({
icon: 'error',
title: 'زمان پایان باید بعد از زمان شروع باشد.',
});
this.error = 'زمان پایان باید بعد از زمان شروع باشد.'; this.error = 'زمان پایان باید بعد از زمان شروع باشد.';
return; return;
} }
const startDateTime = momentDate const startDateTime = momentDate
.clone() .clone()
.set({ hour: this.form.startHour, minute: this.form.startMinute, second: 0 }) .set({ hour: this.form.startHour, minute: this.form.startMinute, second: 0 })
@ -635,7 +741,13 @@ export default {
try { try {
this.$emit('create-meeting', meetingData); this.$emit('create-meeting', meetingData);
this.closeModalByButton(); this.closeModalByButton();
} catch (error) { } catch (error) {
// Show error Toast for data preparation failure
Toast.fire({
icon: 'error',
title: `خطا در آماده‌سازی داده‌ها: ${error.message}`,
});
this.error = `خطا در آماده‌سازی داده‌ها: ${error.message}`; this.error = `خطا در آماده‌سازی داده‌ها: ${error.message}`;
} }
}, },

View File

@ -49,7 +49,10 @@
</div> </div>
</div> </div>
<div v-else class="loading-message"> <div v-if="spaces.length === 0 && !isLoading" class="loading-message">
<p>امکان ساختن فضا برای شما وجود ندارد</p>
</div>
<div v-else-if="spaces.length === 0 && isLoading" class="loading-message">
<p>در حال بارگذاری فضاها...</p> <p>در حال بارگذاری فضاها...</p>
</div> </div>
</div> </div>
@ -106,34 +109,52 @@ export default {
capacity: '', capacity: '',
description: '', description: '',
}, },
isLoading: false,
}; };
}, },
methods: { methods: {
beforeDestroy() { beforeDestroy() {
// اطمینان از فعال شدن اسکرول هنگام حذف کامپوننت
document.body.style.overflow = ''; document.body.style.overflow = '';
}, },
closeModal() { closeModal() {
this.$emit('close'); this.$emit('close');
this.resetForm() this.resetForm();
}, },
resetForm() { resetForm() {
this.spaces = [], this.spaces = [];
this.selectedSpace = null, this.selectedSpace = null;
this.form = { this.form = {
name : '', name: '',
capacity : '', capacity: '',
description : '', description: '',
} };
}, },
selectSpace(space) { selectSpace(space) {
this.selectedSpace = space; this.selectedSpace = space;
}, },
async fetchSpaces() { async fetchSpaces() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
this.isLoading = true;
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
if (!token) { if (!token) {
console.error('No token found!'); // Show error Toast if no token is found
Toast.fire({
icon: 'error',
title: 'توکن یافت نشد. لطفا دوباره وارد شوید.',
});
return; return;
} }
@ -147,8 +168,6 @@ export default {
} }
); );
console.log(response.data);
this.spaces = response.data.assetbundle_rooms.map(room => ({ this.spaces = response.data.assetbundle_rooms.map(room => ({
name: room.name, name: room.name,
img: room.img, img: room.img,
@ -158,10 +177,30 @@ export default {
id: room.id, id: room.id,
})); }));
} catch (error) { } catch (error) {
// Show error Toast
Toast.fire({
icon: 'error',
title: 'خطا در بارگذاری فضاها. لطفا دوباره تلاش کنید.',
});
console.error('Error fetching spaces:', error); console.error('Error fetching spaces:', error);
} finally {
this.isLoading = false;
} }
}, },
async submitForm() { async submitForm() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
const spaceData = { const spaceData = {
assetBundleRoomId: this.selectedSpace.id, assetBundleRoomId: this.selectedSpace.id,
name: this.form.name, name: this.form.name,
@ -172,7 +211,11 @@ export default {
try { try {
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
if (!token) { if (!token) {
console.error('No token found!'); // Show error Toast if no token is found
Toast.fire({
icon: 'error',
title: 'توکن یافت نشد. لطفا دوباره وارد شوید.',
});
return; return;
} }
@ -187,24 +230,45 @@ export default {
} }
); );
console.log(response.data); // Show success Toast
Toast.fire({
icon: 'success',
title: 'فضا با موفقیت اضافه شد',
});
this.$emit('submit', response.data); this.$emit('submit', response.data);
this.closeModal(); // Close the modal this.closeModal();
window.location.reload(); // Refresh the page window.location.reload();
} catch (error) { } catch (error) {
let errorMessage = 'خطا در ارسال اطلاعات. لطفا دوباره تلاش کنید.';
if (error.response) {
if (error.response.status === 401) {
errorMessage = 'عدم دسترسی. لطفا دوباره وارد شوید.';
} else if (error.response.status === 400) {
errorMessage = 'اطلاعات ورودی نامعتبر است.';
} else {
errorMessage = error.response.data.message || errorMessage;
}
} else if (error.request) {
errorMessage = 'مشکل در ارتباط با سرور. لطفا دوباره تلاش کنید.';
}
// Show error Toast
Toast.fire({
icon: 'error',
title: errorMessage,
});
console.error('Error submitting form:', error); console.error('Error submitting form:', error);
alert('خطا در ارسال اطلاعات، لطفا دوباره تلاش کنید');
} }
}, },
}, },
watch: { watch: {
isVisible(newVal) { isVisible(newVal) {
if (newVal) { if (newVal) {
// غیرفعال کردن اسکرول هنگام باز شدن پاپآپ
document.body.style.overflow = 'hidden'; document.body.style.overflow = 'hidden';
this.fetchSpaces(); this.fetchSpaces();
} else { } else {
// فعال کردن اسکرول هنگام بسته شدن پاپآپ
document.body.style.overflow = ''; document.body.style.overflow = '';
} }
}, },

View File

@ -137,6 +137,19 @@ export default {
this.$emit('close'); this.$emit('close');
}, },
async downloadFile() { async downloadFile() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
const response = await fetch(this.previewUrl); const response = await fetch(this.previewUrl);
const blob = await response.blob(); const blob = await response.blob();
@ -148,14 +161,38 @@ export default {
a.click(); a.click();
window.URL.revokeObjectURL(downloadUrl); window.URL.revokeObjectURL(downloadUrl);
document.body.removeChild(a); document.body.removeChild(a);
// Show success Toast
Toast.fire({
icon: 'success',
title: 'فایل با موفقیت دانلود شد',
});
} catch (error) { } catch (error) {
console.error('Error downloading file:', error); console.error('Error downloading file:', error);
alert('خطا در دانلود فایل');
// Show error Toast
Toast.fire({
icon: 'error',
title: 'خطا در دانلود فایل',
});
} }
}, },
async deleteFile() { async deleteFile() {
if (this.previewIndex === null || !this.previewType) return; if (this.previewIndex === null || !this.previewType) return;
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
const deleteUrl = `${this.baseUrl}/delete${this.previewType.charAt(0).toUpperCase() + this.previewType.slice(1)}/${this.previewIndex}/`; const deleteUrl = `${this.baseUrl}/delete${this.previewType.charAt(0).toUpperCase() + this.previewType.slice(1)}/${this.previewIndex}/`;
@ -168,10 +205,33 @@ export default {
this.$emit('delete-success'); this.$emit('delete-success');
this.closePreviewDialog(); this.closePreviewDialog();
alert('فایل با موفقیت حذف شد');
// Show success Toast
Toast.fire({
icon: 'success',
title: 'فایل با موفقیت حذف شد',
});
} catch (error) { } catch (error) {
console.error('Error deleting file:', error); console.error('Error deleting file:', error);
alert('خطا در حذف فایل');
let errorMessage = 'خطا در حذف فایل';
if (error.response) {
if (error.response.status === 401) {
errorMessage = 'عدم دسترسی: لطفا دوباره وارد شوید.';
} else if (error.response.status === 400) {
errorMessage = 'درخواست نامعتبر است.';
} else {
errorMessage = error.response.data.message || errorMessage;
}
} else if (error.request) {
errorMessage = 'مشکل در ارتباط با سرور. لطفا دوباره تلاش کنید.';
}
// Show error Toast
Toast.fire({
icon: 'error',
title: errorMessage,
});
} }
}, },
}, },

View File

@ -502,7 +502,7 @@ export default {
return this.customer.profile_img || this.defaultProfileIcon; return this.customer.profile_img || this.defaultProfileIcon;
}, },
userId() { userId() {
return this.customer.id || null; return this.customer.user_id || null;
}, },
}, },
watch: { watch: {
@ -524,6 +524,19 @@ export default {
}, },
methods: { methods: {
async fetchTeamMembers() { async fetchTeamMembers() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
if (!token) throw new Error('توکن احراز هویت پیدا نشد'); if (!token) throw new Error('توکن احراز هویت پیدا نشد');
@ -535,7 +548,11 @@ export default {
); );
} catch (error) { } catch (error) {
if (error.response?.status === 403) { if (error.response?.status === 403) {
alert('لطفاً دوباره وارد شوید'); // Show error Toast for unauthorized access
Toast.fire({
icon: 'error',
title: 'لطفاً دوباره وارد شوید',
});
window.location.href = '/login'; window.location.href = '/login';
} }
this.error = 'خطا در بارگذاری لیست اعضای تیم'; this.error = 'خطا در بارگذاری لیست اعضای تیم';
@ -638,20 +655,53 @@ export default {
return member ? `${member.user.first_name} ${member.user.last_name}` : ''; return member ? `${member.user.first_name} ${member.user.last_name}` : '';
}, },
addParticipant() { addParticipant() {
// Define Toast configuration for participant errors
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
if (!this.selectedParticipantId) { if (!this.selectedParticipantId) {
// Show error Toast for no participant selected
Toast.fire({
icon: 'error',
title: 'لطفاً یک عضو تیم انتخاب کنید.',
});
this.error = 'لطفاً یک عضو تیم انتخاب کنید.'; this.error = 'لطفاً یک عضو تیم انتخاب کنید.';
return; return;
} }
const selectedMember = this.teamMembers.find((member) => member.user.id === this.selectedParticipantId); const selectedMember = this.teamMembers.find((member) => member.user.id === this.selectedParticipantId);
if (!selectedMember) { if (!selectedMember) {
// Show error Toast for invalid participant
Toast.fire({
icon: 'error',
title: 'کاربر انتخاب‌شده یافت نشد.',
});
this.error = 'کاربر انتخاب‌شده یافت نشد.'; this.error = 'کاربر انتخاب‌شده یافت نشد.';
return; return;
} }
if (this.participants.some((p) => p.id === this.selectedParticipantId)) { if (this.participants.some((p) => p.id === this.selectedParticipantId)) {
// Show error Toast for duplicate participant
Toast.fire({
icon: 'error',
title: 'این کاربر قبلاً اضافه شده است.',
});
this.error = 'این کاربر قبلاً اضافه شده است.'; this.error = 'این کاربر قبلاً اضافه شده است.';
return; return;
} }
if (this.selectedParticipantId === this.userId) { if (this.selectedParticipantId === this.userId) {
// Show error Toast for self-addition
Toast.fire({
icon: 'error',
title: 'نمی‌توانید خودتان را به‌عنوان شرکت‌کننده اضافه کنید.',
});
this.error = 'نمی‌توانید خودتان را به‌عنوان شرکت‌کننده اضافه کنید.'; this.error = 'نمی‌توانید خودتان را به‌عنوان شرکت‌کننده اضافه کنید.';
return; return;
} }
@ -709,22 +759,55 @@ export default {
if (this.form[field] > 0) this.form[field]--; if (this.form[field] > 0) this.form[field]--;
}, },
async handleSubmit() { async handleSubmit() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
if (!this.form.title || !this.form.date) { if (!this.form.title || !this.form.date) {
// Show error Toast for missing title or date
Toast.fire({
icon: 'error',
title: 'لطفاً نام جلسه و تاریخ را وارد کنید.',
});
this.error = 'لطفاً نام جلسه و تاریخ را وارد کنید.'; this.error = 'لطفاً نام جلسه و تاریخ را وارد کنید.';
return; return;
} }
if (!this.form.selectedRoom || this.form.space === null || this.form.asset_bundle === null) { if (!this.form.selectedRoom || this.form.space === null || this.form.asset_bundle === null) {
// Show error Toast for missing room selection
Toast.fire({
icon: 'error',
title: 'لطفاً یک اتاق برای جلسه انتخاب کنید.',
});
this.error = 'لطفاً یک اتاق برای جلسه انتخاب کنید.'; this.error = 'لطفاً یک اتاق برای جلسه انتخاب کنید.';
return; return;
} }
const momentDate = moment(this.form.date, 'jYYYY/jMM/jDD'); const momentDate = moment(this.form.date, 'jYYYY/jMM/jDD');
if (!momentDate.isValid()) { if (!momentDate.isValid()) {
// Show error Toast for invalid date
Toast.fire({
icon: 'error',
title: 'تاریخ وارد شده معتبر نیست.',
});
this.error = 'تاریخ وارد شده معتبر نیست.'; this.error = 'تاریخ وارد شده معتبر نیست.';
return; return;
} }
const startTimeInMinutes = this.form.startHour * 60 + this.form.startMinute; const startTimeInMinutes = this.form.startHour * 60 + this.form.startMinute;
const endTimeInMinutes = this.form.endHour * 60 + this.form.endMinute; const endTimeInMinutes = this.form.endHour * 60 + this.form.endMinute;
if (endTimeInMinutes <= startTimeInMinutes) { if (endTimeInMinutes <= startTimeInMinutes) {
// Show error Toast for invalid time range
Toast.fire({
icon: 'error',
title: 'زمان پایان باید بعد از زمان شروع باشد.',
});
this.error = 'زمان پایان باید بعد از زمان شروع باشد.'; this.error = 'زمان پایان باید بعد از زمان شروع باشد.';
return; return;
} }
@ -761,15 +844,26 @@ export default {
maxCapacity: this.form.selectedRoom.capacity || 10, maxCapacity: this.form.selectedRoom.capacity || 10,
invited_users: this.participants, invited_users: this.participants,
}); });
// Show success Toast
Toast.fire({
icon: 'success',
title: 'جلسه با موفقیت ویرایش شد!',
});
this.closeModalByButton(); this.closeModalByButton();
alert('جلسه با موفقیت ویرایش شد!');
} catch (error) { } catch (error) {
// Show error Toast for submission failure
Toast.fire({
icon: 'error',
title: `خطا در ویرایش جلسه: ${error.response?.data?.message || error.message}`,
});
this.error = `خطا در ویرایش جلسه: ${error.response?.data?.message || error.message}`; this.error = `خطا در ویرایش جلسه: ${error.response?.data?.message || error.message}`;
} }
}, },
}, },
}; };
</script> </script>
<style scoped> <style scoped>
.participant-input { .participant-input {
position: relative; position: relative;

View File

@ -146,7 +146,7 @@ export default {
} else if (/\.(mp4|mov|mkv|wmv|m4v|mpg|webm|ogg)$/i.test(fileName)) { } else if (/\.(mp4|mov|mkv|wmv|m4v|mpg|webm|ogg)$/i.test(fileName)) {
this.currentUploadType = 'video'; this.currentUploadType = 'video';
this.dialogTitle = 'آپلود ویدیو'; this.dialogTitle = 'آپلود ویدیو';
} else if (/\.(glb|obj|fbx|stl|ply|gltf)|$/i.test(fileName)) { } else if (/\.(glb|obj|fbx|stl|ply|gltf)$/i.test(fileName)) {
this.currentUploadType = 'glb'; this.currentUploadType = 'glb';
this.dialogTitle = 'آپلود مدل 3D'; this.dialogTitle = 'آپلود مدل 3D';
} else { } else {
@ -156,8 +156,25 @@ export default {
} }
}, },
async uploadFile() { async uploadFile() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
if (!this.selectedFile) { if (!this.selectedFile) {
alert('لطفاً یک فایل انتخاب کنید.'); // Check if a file is selected
Toast.fire({
icon: 'error',
title: 'لطفاً یک فایل انتخاب کنید.',
});
return; return;
} }
@ -171,9 +188,12 @@ export default {
let uploadUrl = `${this.baseUrl}/upload${this.currentUploadType.charAt(0).toUpperCase() + this.currentUploadType.slice(1)}/`; let uploadUrl = `${this.baseUrl}/upload${this.currentUploadType.charAt(0).toUpperCase() + this.currentUploadType.slice(1)}/`;
if (this.currentUploadType === 'other') { if (this.currentUploadType === 'other') {
console.log('File sent to "other" category:', this.selectedFile.name);
console.log('فایل به دسته "سایر" ارسال می‌شود:', this.selectedFile.name); // Log and show Toast for 'other' file type (test mode)
alert('فایل به دسته "سایر" ارسال شد (تستی).'); Toast.fire({
icon: 'success',
title: 'فایل به دسته "سایر" ارسال شد.',
});
this.resetForm(); this.resetForm();
this.$emit('upload-success'); this.$emit('upload-success');
this.$emit('close'); this.$emit('close');
@ -187,17 +207,40 @@ export default {
}, },
}); });
// Show success Toast
Toast.fire({
icon: 'success',
title: 'فایل با موفقیت آپلود شد',
});
this.resetForm(); this.resetForm();
this.$emit('upload-success'); this.$emit('upload-success');
this.$emit('close'); this.$emit('close');
alert('فایل با موفقیت آپلود شد');
if (this.$route.path !== '/dashboard/files') { if (this.$route.path !== '/dashboard/files') {
this.$router.push('/dashboard/files'); this.$router.push('/dashboard/files');
} }
} catch (error) { } catch (error) {
let errorMessage = 'خطا در آپلود فایل. لطفا دوباره تلاش کنید.';
if (error.response) {
if (error.response.status === 401) {
errorMessage = 'عدم دسترسی. لطفاً وارد حساب کاربری شوید.';
} else if (error.response.status === 400) {
errorMessage = 'اطلاعات ورودی نامعتبر است.';
} else {
errorMessage = error.response.data.message || errorMessage;
}
} else if (error.request) {
errorMessage = 'مشکل در ارتباط با سرور. لطفا دوباره تلاش کنید.';
}
// Show error Toast
Toast.fire({
icon: 'error',
title: errorMessage,
});
console.error('Error uploading file:', error); console.error('Error uploading file:', error);
alert('خطا در آپلود فایل');
} finally { } finally {
this.uploading = false; this.uploading = false;
} }

View File

@ -430,7 +430,7 @@ export default {
if (selectedRoomDetails.isTemporary) { if (selectedRoomDetails.isTemporary) {
roomData = { roomData = {
...selectedRoomDetails, ...selectedRoomDetails,
space: 18, space: 29,
asset_bundle: selectedRoomDetails.id, asset_bundle: selectedRoomDetails.id,
use_space: false, use_space: false,
image: selectedRoomDetails.image || 'https://via.placeholder.com/150', image: selectedRoomDetails.image || 'https://via.placeholder.com/150',
@ -455,6 +455,8 @@ export default {
}, },
}; };
</script> </script>
<style scoped> <style scoped>
.modal-overlay { .modal-overlay {
position: fixed; position: fixed;

View File

@ -122,9 +122,30 @@ export default {
}, },
methods: { methods: {
async fetchTeamData() { async fetchTeamData() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
if (!token) throw new Error('توکن احراز هویت یافت نشد.'); if (!token) {
// Show error Toast for missing token
Toast.fire({
icon: 'error',
title: 'توکن احراز هویت یافت نشد.',
});
throw new Error('No authentication token found.');
}
const response = await axios.get(`${this.baseUrl}/get_team`, { const response = await axios.get(`${this.baseUrl}/get_team`, {
headers: { Authorization: `Token ${token}`, 'Content-Type': 'application/json' }, headers: { Authorization: `Token ${token}`, 'Content-Type': 'application/json' },
}); });
@ -135,10 +156,19 @@ export default {
this.form.teamId = team.id; this.form.teamId = team.id;
this.teamLogo = team.logo ? `${this.baseUrl}${team.logo}` : null; this.teamLogo = team.logo ? `${this.baseUrl}${team.logo}` : null;
} else { } else {
alert('هیچ اطلاعاتی برای تیم یافت نشد.'); // Show error Toast for no team data
Toast.fire({
icon: 'error',
title: 'هیچ اطلاعاتی برای تیم یافت نشد.',
});
} }
} catch { } catch (error) {
alert('خطا در بارگذاری اطلاعات تیم.'); // Show error Toast for fetch failure
Toast.fire({
icon: 'error',
title: 'خطا در بارگذاری اطلاعات تیم.',
});
console.error('Fetch team error:', error);
} }
}, },
handleLogoUpload(event) { handleLogoUpload(event) {
@ -148,30 +178,69 @@ export default {
} }
}, },
async submitForm() { async submitForm() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
if (!this.form.teamName && !this.form.activityType && !this.uploadedLogoFile) { if (!this.form.teamName && !this.form.activityType && !this.uploadedLogoFile) {
alert('لطفاً حداقل یک فیلد یا لوگو وارد کنید.'); // Show error Toast for empty form
Toast.fire({
icon: 'error',
title: 'لطفاً حداقل یک فیلد یا لوگو وارد کنید.',
});
return; return;
} }
try { try {
const formData = new FormData(); const formData = new FormData();
if (this.form.teamName) formData.append('name', this.form.teamName); if (this.form.teamName) formData.append('name', this.form.teamName);
if (this.form.activityType) formData.append('description', this.form.activityType); if (this.form.activityType) formData.append('description', this.form.activityType);
if (this.uploadedLogoFile) formData.append('logo', this.uploadedLogoFile); if (this.uploadedLogoFile) formData.append('logo', this.uploadedLogoFile);
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
if (!token) throw new Error('توکن احراز هویت یافت نشد.'); if (!token) {
// Show error Toast for missing token
Toast.fire({
icon: 'error',
title: 'توکن احراز هویت یافت نشد.',
});
throw new Error('No authentication token found.');
}
await axios.patch(`${this.baseUrl}/update_team/${this.form.teamId}/`, formData, { await axios.patch(`${this.baseUrl}/update_team/${this.form.teamId}/`, formData, {
headers: { Authorization: `Token ${token}`, 'Content-Type': 'multipart/form-data' }, headers: { Authorization: `Token ${token}`, 'Content-Type': 'multipart/form-data' },
}); });
this.$emit('update:team-data', { this.$emit('update:team-data', {
teamName: this.form.teamName, teamName: this.form.teamName,
activityType: this.form.activityType, activityType: this.form.activityType,
teamLogo: this.uploadedLogoFile, teamLogo: this.uploadedLogoFile,
}); });
alert('اطلاعات تیم با موفقیت به‌روزرسانی شد.');
// Show success Toast
Toast.fire({
icon: 'success',
title: 'اطلاعات تیم با موفقیت به‌روزرسانی شد.',
});
this.resetForm(); this.resetForm();
await this.fetchTeamData(); await this.fetchTeamData();
} catch { } catch (error) {
alert('خطا در به‌روزرسانی اطلاعات تیم.'); // Show error Toast for update failure
Toast.fire({
icon: 'error',
title: 'خطا در به‌روزرسانی اطلاعات تیم.',
});
console.error('Update team error:', error);
} }
}, },
resetForm() { resetForm() {

View File

@ -321,9 +321,26 @@ export default {
}, },
methods: { methods: {
openAddUserModal() { openAddUserModal() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
if (this.remainingCapacity <= 0) { if (this.remainingCapacity <= 0) {
this.$emit('change-tab', 'buy-subscription'); this.$emit('change-tab', 'buy-subscription');
alert('اشتراک فعالی ندارید , لطفا اشتراک تهیه نمایید.'); // Show error Toast for no active subscription
Toast.fire({
icon: 'error',
title: 'اشتراک فعالی ندارید، لطفا اشتراک تهیه نمایید.',
});
return; return;
} }
this.isAddUserModalVisible = true; this.isAddUserModalVisible = true;
@ -348,7 +365,6 @@ export default {
beforeUnmount() { beforeUnmount() {
window.removeEventListener('resize', this.handleResize); window.removeEventListener('resize', this.handleResize);
}, },
}; };
</script> </script>
@ -846,7 +862,7 @@ export default {
.add-card { .add-card {
width: 48%; width: 48%;
height: auto; height: 11.38rem;
} }
} }

View File

@ -67,18 +67,15 @@ export default {
}, },
}); });
// Prepare login data
const loginData = { const loginData = {
mobile_number: this.form.mobileNumber, mobile_number: this.form.mobileNumber,
password: this.form.password, password: this.form.password,
}; };
try { try {
// Send login request
const response = await apiClient.post('/login', loginData); const response = await apiClient.post('/login', loginData);
if (response.data.status === 200) { if (response.data.status === 200) {
// Store token and user data in localStorage
const token = response.data.data.token; const token = response.data.data.token;
const user = response.data.data.user; const user = response.data.data.user;
@ -91,7 +88,6 @@ export default {
title: 'ورود با موفقیت انجام شد', title: 'ورود با موفقیت انجام شد',
}); });
// Redirect to dashboard
this.$router.push('/dashboard'); this.$router.push('/dashboard');
} else { } else {
// Show error Toast with server message // Show error Toast with server message
@ -101,10 +97,8 @@ export default {
}); });
} }
} catch (error) { } catch (error) {
// Handle specific error cases
let errorMessage = 'خطا در ورود, لطفا دوباره تلاش کنید'; let errorMessage = 'خطا در ورود, لطفا دوباره تلاش کنید';
if (error.response) { if (error.response) {
// Handle server errors (e.g., 400, 401, 500)
if (error.response.status === 401) { if (error.response.status === 401) {
errorMessage = '.شماره تماس یا رمز عبور اشتباه است'; errorMessage = '.شماره تماس یا رمز عبور اشتباه است';
} else if (error.response.status === 400) { } else if (error.response.status === 400) {
@ -113,7 +107,6 @@ export default {
errorMessage = error.response.data.message || errorMessage; errorMessage = error.response.data.message || errorMessage;
} }
} else if (error.request) { } else if (error.request) {
// Handle network errors (no response from server)
errorMessage = 'مشکل در ارتباط با سرور, لطفا دوباره تلاش کنید'; errorMessage = 'مشکل در ارتباط با سرور, لطفا دوباره تلاش کنید';
} }
@ -123,7 +116,6 @@ export default {
title: errorMessage, title: errorMessage,
}); });
// Log error for debugging
console.error('Login error:', error); console.error('Login error:', error);
} }
}, },

View File

@ -64,7 +64,7 @@
</template> </template>
<script> <script>
import apiClient from '@/api/axios'; // Adjust the path based on your project structure import apiClient from '@/api/axios';
export default { export default {
data() { data() {
@ -74,7 +74,7 @@ export default {
code: '', code: '',
password: '', password: '',
}, },
codeSent: false, // Tracks if the code has been sent codeSent: false,
}; };
}, },
methods: { methods: {
@ -93,13 +93,11 @@ export default {
}); });
try { try {
// Send request to get reset code
const response = await apiClient.post('/requestResetCode', { const response = await apiClient.post('/requestResetCode', {
mobile_number: this.form.mobileNumber, mobile_number: this.form.mobileNumber,
}); });
if (response.data.success) { if (response.data.success) {
// Update state to show code and password input form
this.codeSent = true; this.codeSent = true;
// Show success Toast // Show success Toast
@ -115,10 +113,8 @@ export default {
}); });
} }
} catch (error) { } catch (error) {
// Handle specific error cases
let errorMessage = 'خطا در ارسال کد تأیید, لطفاً دوباره تلاش کنید'; let errorMessage = 'خطا در ارسال کد تأیید, لطفاً دوباره تلاش کنید';
if (error.response) { if (error.response) {
// Handle server errors (e.g., 400, 401, 500)
if (error.response.status === 400) { if (error.response.status === 400) {
errorMessage = '.شماره تماس نامعتبر است'; errorMessage = '.شماره تماس نامعتبر است';
} else if (error.response.status === 404) { } else if (error.response.status === 404) {
@ -127,7 +123,6 @@ export default {
errorMessage = error.response.data.message || errorMessage; errorMessage = error.response.data.message || errorMessage;
} }
} else if (error.request) { } else if (error.request) {
// Handle network errors (no response from server)
errorMessage = 'مشکل در ارتباط با سرور, لطفاً دوباره تلاش کنید'; errorMessage = 'مشکل در ارتباط با سرور, لطفاً دوباره تلاش کنید';
} }
@ -137,7 +132,6 @@ export default {
title: errorMessage, title: errorMessage,
}); });
// Log error for debugging
console.error('Error requesting reset code:', error); console.error('Error requesting reset code:', error);
} }
}, },
@ -156,7 +150,6 @@ export default {
}); });
try { try {
// Send request to verify code and reset password
const response = await apiClient.post('/verifyResetCode', { const response = await apiClient.post('/verifyResetCode', {
mobile_number: this.form.mobileNumber, mobile_number: this.form.mobileNumber,
code: this.form.code, code: this.form.code,
@ -170,7 +163,6 @@ export default {
title: '.رمز عبور با موفقیت بازنشانی شد', title: '.رمز عبور با موفقیت بازنشانی شد',
}); });
// Redirect to login page
this.$router.push('/'); this.$router.push('/');
} else { } else {
// Show error Toast with server message // Show error Toast with server message
@ -180,10 +172,8 @@ export default {
}); });
} }
} catch (error) { } catch (error) {
// Handle specific error cases
let errorMessage = '.خطا در بازنشانی رمز عبور , لطفاً کد یا رمز عبور را بررسی کنید'; let errorMessage = '.خطا در بازنشانی رمز عبور , لطفاً کد یا رمز عبور را بررسی کنید';
if (error.response) { if (error.response) {
// Handle server errors (e.g., 400, 401, 500)
if (error.response.status === 400) { if (error.response.status === 400) {
errorMessage = '.کد تأیید یا رمز عبور نامعتبر است'; errorMessage = '.کد تأیید یا رمز عبور نامعتبر است';
} else if (error.response.status === 401) { } else if (error.response.status === 401) {
@ -192,7 +182,6 @@ export default {
errorMessage = error.response.data.message || errorMessage; errorMessage = error.response.data.message || errorMessage;
} }
} else if (error.request) { } else if (error.request) {
// Handle network errors (no response from server)
errorMessage = '.مشکل در ارتباط با سرور , لطفاً دوباره تلاش کنید'; errorMessage = '.مشکل در ارتباط با سرور , لطفاً دوباره تلاش کنید';
} }
@ -202,7 +191,6 @@ export default {
title: errorMessage, title: errorMessage,
}); });
// Log error for debugging
console.error('Error resetting password:', error); console.error('Error resetting password:', error);
} }
}, },

View File

@ -88,7 +88,6 @@ export default {
}, },
}); });
// Validate form inputs
if (!this.form.firstName || !this.form.lastName || !this.form.semat || !this.form.mobileNumber || !this.form.password) { if (!this.form.firstName || !this.form.lastName || !this.form.semat || !this.form.mobileNumber || !this.form.password) {
Toast.fire({ Toast.fire({
icon: 'error', icon: 'error',
@ -97,7 +96,6 @@ export default {
return; return;
} }
// Prepare the data to match API format
const signupData = { const signupData = {
first_name: this.form.firstName, first_name: this.form.firstName,
last_name: this.form.lastName, last_name: this.form.lastName,
@ -107,12 +105,9 @@ export default {
}; };
try { try {
// Send signup request
const response = await axios.post('http://194.62.43.230:8000/signup', signupData); const response = await axios.post('http://194.62.43.230:8000/signup', signupData);
// Check if signup was successful
if (response.data.token) { if (response.data.token) {
// Store token in localStorage
localStorage.setItem('token', response.data.token); localStorage.setItem('token', response.data.token);
// Show success Toast // Show success Toast
@ -121,7 +116,6 @@ export default {
title: '.حساب کاربری با موفقیت ساخته شد', title: '.حساب کاربری با موفقیت ساخته شد',
}); });
// Redirect to login page
this.$router.push('/'); this.$router.push('/');
} else { } else {
// Show error Toast with server message // Show error Toast with server message
@ -131,17 +125,14 @@ export default {
}); });
} }
} catch (error) { } catch (error) {
// Handle specific error cases
let errorMessage = 'خطا در ثبت‌نام, لطفاً دوباره تلاش کنید'; let errorMessage = 'خطا در ثبت‌نام, لطفاً دوباره تلاش کنید';
if (error.response) { if (error.response) {
// Handle server errors (e.g., 400)
if (error.response.status === 400) { if (error.response.status === 400) {
errorMessage = '.شماره تلفن قبلاً ثبت شده است'; errorMessage = '.شماره تلفن قبلاً ثبت شده است';
} else { } else {
errorMessage = error.response.data.message || errorMessage; errorMessage = error.response.data.message || errorMessage;
} }
} else if (error.request) { } else if (error.request) {
// Handle network errors (no response from server)
errorMessage = 'مشکل در ارتباط با سرور, لطفاً دوباره تلاش کنید'; errorMessage = 'مشکل در ارتباط با سرور, لطفاً دوباره تلاش کنید';
} }
@ -151,7 +142,6 @@ export default {
title: errorMessage, title: errorMessage,
}); });
// Log error for debugging
console.error('Signup error:', error); console.error('Signup error:', error);
} }
}, },

View File

@ -52,7 +52,7 @@
</template> </template>
<script> <script>
import axios from '@/axios'; // Adjust the path based on your project structure import axios from '@/axios';
export default { export default {
data() { data() {
@ -62,19 +62,18 @@ export default {
code: '', code: '',
password: '', password: '',
}, },
codeSent: false, // Tracks if the code has been sent codeSent: false,
isButtonDisabled: false, // Tracks if resend button is disabled isButtonDisabled: false,
countdown: 120, // Countdown timer in seconds (2 minutes) countdown: 120,
countdownInterval: null, // Interval for countdown countdownInterval: null,
}; };
}, },
mounted() { mounted() {
// Check for token and trigger SMS sending on mount
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
if (!token) { if (!token) {
window.location.reload(); window.location.reload();
} else { } else {
this.sendSms(); // Automatically call sendSms on mount this.sendSms();
} }
}, },
methods: { methods: {
@ -93,10 +92,7 @@ export default {
}); });
try { try {
// Get token from localStorage
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
// Send request to get verification SMS
const response = await axios.get('/sendSmsVerification', { const response = await axios.get('/sendSmsVerification', {
headers: { headers: {
Authorization: `Token ${token}`, Authorization: `Token ${token}`,
@ -105,29 +101,21 @@ export default {
}); });
if (response.status === 200) { if (response.status === 200) {
// Update state to indicate code was sent
this.codeSent = true; this.codeSent = true;
// Show success Toast
Toast.fire({ Toast.fire({
icon: 'success', icon: 'success',
title: '.کد تأیید به شماره موبایل شما ارسال شد', title: '.کد تأیید به شماره موبایل شما ارسال شد',
}); });
// Start countdown for resend button
this.startCountdown(); this.startCountdown();
} else { } else {
// Show error Toast with server message
Toast.fire({ Toast.fire({
icon: 'error', icon: 'error',
title: response.data.message || 'خطا در ارسال کد تأیید, لطفاً دوباره تلاش کنید', title: response.data.message || 'خطا در ارسال کد تأیید, لطفاً دوباره تلاش کنید',
}); });
} }
} catch (error) { } catch (error) {
// Handle specific error cases
let errorMessage = 'خطا در ارسال کد تأیید, لطفاً دوباره تلاش کنید'; let errorMessage = 'خطا در ارسال کد تأیید, لطفاً دوباره تلاش کنید';
if (error.response) { if (error.response) {
// Handle server errors (e.g., 400, 401)
if (error.response.status === 400) { if (error.response.status === 400) {
errorMessage = '.درخواست نامعتبر است'; errorMessage = '.درخواست نامعتبر است';
} else if (error.response.status === 401) { } else if (error.response.status === 401) {
@ -136,30 +124,23 @@ export default {
errorMessage = error.response.data.message || errorMessage; errorMessage = error.response.data.message || errorMessage;
} }
} else if (error.request) { } else if (error.request) {
// Handle network errors (no response from server)
errorMessage = 'مشکل در ارتباط با سرور, لطفاً دوباره تلاش کنید'; errorMessage = 'مشکل در ارتباط با سرور, لطفاً دوباره تلاش کنید';
} }
// Show error Toast
Toast.fire({ Toast.fire({
icon: 'error', icon: 'error',
title: errorMessage, title: errorMessage,
}); });
// Log error for debugging
console.error('Error requesting SMS code:', error); console.error('Error requesting SMS code:', error);
} }
}, },
startCountdown() { startCountdown() {
// Disable resend button and start countdown
this.isButtonDisabled = true; this.isButtonDisabled = true;
this.countdown = 120; // Reset to 2 minutes this.countdown = 120;
if (this.countdownInterval) { if (this.countdownInterval) {
clearInterval(this.countdownInterval); clearInterval(this.countdownInterval);
} }
// Update countdown every second
this.countdownInterval = setInterval(() => { this.countdownInterval = setInterval(() => {
if (this.countdown > 0) { if (this.countdown > 0) {
this.countdown--; this.countdown--;
@ -184,10 +165,7 @@ export default {
}); });
try { try {
// Get token from localStorage
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
// Send request to verify SMS code
const response = await axios.post( const response = await axios.post(
'/submitSmsVerification', '/submitSmsVerification',
{ {
@ -202,26 +180,20 @@ export default {
); );
if (response.status === 200) { if (response.status === 200) {
// Show success Toast
Toast.fire({ Toast.fire({
icon: 'success', icon: 'success',
title: '.کد تأیید صحیح است', title: '.کد تأیید صحیح است',
}); });
// Redirect to dashboard
this.$router.push('/dashboard'); this.$router.push('/dashboard');
} else { } else {
// Show error Toast with server message
Toast.fire({ Toast.fire({
icon: 'error', icon: 'error',
title: response.data.message || '.کد تأیید نامعتبر است', title: response.data.message || '.کد تأیید نامعتبر است',
}); });
} }
} catch (error) { } catch (error) {
// Handle specific error cases
let errorMessage = '.کد تأیید نامعتبر است'; let errorMessage = '.کد تأیید نامعتبر است';
if (error.response) { if (error.response) {
// Handle server errors (e.g., 400, 401)
if (error.response.status === 400) { if (error.response.status === 400) {
errorMessage = '.کد تأیید نامعتبر است'; errorMessage = '.کد تأیید نامعتبر است';
} else if (error.response.status === 401) { } else if (error.response.status === 401) {
@ -230,17 +202,12 @@ export default {
errorMessage = error.response.data.message || errorMessage; errorMessage = error.response.data.message || errorMessage;
} }
} else if (error.request) { } else if (error.request) {
// Handle network errors (no response from server)
errorMessage = 'مشکل در ارتباط با سرور, لطفاً دوباره تلاش کنید'; errorMessage = 'مشکل در ارتباط با سرور, لطفاً دوباره تلاش کنید';
} }
// Show error Toast
Toast.fire({ Toast.fire({
icon: 'error', icon: 'error',
title: errorMessage, title: errorMessage,
}); });
// Log error for debugging
console.error('Error verifying SMS code:', error); console.error('Error verifying SMS code:', error);
} }
}, },

View File

@ -73,7 +73,6 @@ export default {
}; };
}, },
setup() { setup() {
// Define male avatars
const maleAvatars = ref([ const maleAvatars = ref([
{ id: 1, name: 'مرد ۱', src: 'http://my.xroomapp.com:8000/media/user_glbs/men1.glb', profile_img: 'http://my.xroomapp.com:8000/media/user_images/men1.png' }, { id: 1, name: 'مرد ۱', src: 'http://my.xroomapp.com:8000/media/user_glbs/men1.glb', profile_img: 'http://my.xroomapp.com:8000/media/user_images/men1.png' },
{ id: 2, name: 'مرد ۲', src: 'http://my.xroomapp.com:8000/media/user_glbs/men2.glb', profile_img: 'http://my.xroomapp.com:8000/media/user_images/men2.png' }, { id: 2, name: 'مرد ۲', src: 'http://my.xroomapp.com:8000/media/user_glbs/men2.glb', profile_img: 'http://my.xroomapp.com:8000/media/user_images/men2.png' },
@ -81,7 +80,6 @@ export default {
{ id: 17, name: 'مرد ۴', src: 'http://my.xroomapp.com:8000/media/user_glbs/men4.glb', profile_img: 'http://my.xroomapp.com:8000/media/user_images/men4.png' }, { id: 17, name: 'مرد ۴', src: 'http://my.xroomapp.com:8000/media/user_glbs/men4.glb', profile_img: 'http://my.xroomapp.com:8000/media/user_images/men4.png' },
]); ]);
// Define female avatars
const femaleAvatars = ref([ const femaleAvatars = ref([
{ id: 4, name: 'زن ۱', src: 'http://my.xroomapp.com:8000/media/user_glbs/women1.glb', profile_img: 'http://my.xroomapp.com:8000/media/user_images/women1.png' }, { id: 4, name: 'زن ۱', src: 'http://my.xroomapp.com:8000/media/user_glbs/women1.glb', profile_img: 'http://my.xroomapp.com:8000/media/user_images/women1.png' },
{ id: 10, name: 'زن ۲', src: 'http://my.xroomapp.com:8000/media/user_glbs/women2.glb', profile_img: 'http://my.xroomapp.com:8000/media/user_images/women2.png' }, { id: 10, name: 'زن ۲', src: 'http://my.xroomapp.com:8000/media/user_glbs/women2.glb', profile_img: 'http://my.xroomapp.com:8000/media/user_images/women2.png' },
@ -100,12 +98,10 @@ export default {
}; };
}, },
created() { created() {
// Fetch user data on component creation
this.fetchUserData(); this.fetchUserData();
}, },
computed: { computed: {
userProfilePicUrl() { userProfilePicUrl() {
// Get customer data from localStorage
const customer = JSON.parse(localStorage.getItem('customer') || {}); const customer = JSON.parse(localStorage.getItem('customer') || {});
if (!customer.profile_img) return this.defaultProfileImage; if (!customer.profile_img) return this.defaultProfileImage;
return `http://194.62.43.230:8000/media/${customer.profile_img}`; return `http://194.62.43.230:8000/media/${customer.profile_img}`;
@ -126,12 +122,10 @@ export default {
}, },
}); });
// Set saving state and selected avatar
this.saving = true; this.saving = true;
this.selectedAvatar = avatar.id; this.selectedAvatar = avatar.id;
try { try {
// Send request to update profile with selected avatar
await axios.post(`${this.baseUrl}/editProfile/`, { await axios.post(`${this.baseUrl}/editProfile/`, {
profile_glb_url: avatar.src, profile_glb_url: avatar.src,
profile_img: avatar.profile_img profile_img: avatar.profile_img
@ -147,16 +141,13 @@ export default {
title: '.آواتار با موفقیت انتخاب شد', title: '.آواتار با موفقیت انتخاب شد',
}); });
// Delay redirect to allow Toast to be visible
setTimeout(() => { setTimeout(() => {
window.location.assign('/dashboard'); window.location.assign('/dashboard');
}, 2000); // 3-second delay to match Toast duration }, 2000);
} catch (error) { } catch (error) {
// Handle specific error cases
let errorMessage = 'خطا در انتخاب آواتار. لطفاً دوباره تلاش کنید'; let errorMessage = 'خطا در انتخاب آواتار. لطفاً دوباره تلاش کنید';
if (error.response) { if (error.response) {
// Handle server errors (e.g., 400, 401)
if (error.response.status === 400) { if (error.response.status === 400) {
errorMessage = 'درخواست نامعتبر است.'; errorMessage = 'درخواست نامعتبر است.';
} else if (error.response.status === 401) { } else if (error.response.status === 401) {
@ -165,7 +156,6 @@ export default {
errorMessage = error.response.data.detail || error.response.data.message || errorMessage; errorMessage = error.response.data.detail || error.response.data.message || errorMessage;
} }
} else if (error.request) { } else if (error.request) {
// Handle network errors (no response from server)
errorMessage = 'مشکل در ارتباط با سرور. لطفاً دوباره تلاش کنید'; errorMessage = 'مشکل در ارتباط با سرور. لطفاً دوباره تلاش کنید';
} }
@ -175,10 +165,8 @@ export default {
title: errorMessage, title: errorMessage,
}); });
// Log error for debugging
console.error('Error selecting avatar:', error); console.error('Error selecting avatar:', error);
} finally { } finally {
// Reset saving state and selected avatar
this.saving = false; this.saving = false;
this.selectedAvatar = null; this.selectedAvatar = null;
} }
@ -198,21 +186,17 @@ export default {
}); });
try { try {
// Fetch user data
const response = await axios.get('/getInfo'); const response = await axios.get('/getInfo');
this.userData = response.data; this.userData = response.data;
} catch (error) { } catch (error) {
// Handle specific error cases
let errorMessage = 'خطا در دریافت اطلاعات کاربر'; let errorMessage = 'خطا در دریافت اطلاعات کاربر';
if (error.response) { if (error.response) {
// Handle server errors (e.g., 400, 401)
if (error.response.status === 401) { if (error.response.status === 401) {
errorMessage = 'توکن نامعتبر است. لطفاً دوباره وارد شوید'; errorMessage = 'توکن نامعتبر است. لطفاً دوباره وارد شوید';
} else { } else {
errorMessage = error.response.data.detail || error.response.data.message || errorMessage; errorMessage = error.response.data.detail || error.response.data.message || errorMessage;
} }
} else if (error.request) { } else if (error.request) {
// Handle network errors (no response from server)
errorMessage = 'مشکل در ارتباط با سرور. لطفاً دوباره تلاش کنید'; errorMessage = 'مشکل در ارتباط با سرور. لطفاً دوباره تلاش کنید';
} }
@ -222,7 +206,6 @@ export default {
title: errorMessage, title: errorMessage,
}); });
// Log error for debugging
console.error('Error fetching user data:', error); console.error('Error fetching user data:', error);
} }
}, },
@ -240,10 +223,8 @@ export default {
}, },
}); });
// Set saving state
this.saving = true; this.saving = true;
try { try {
// Prepare form data for profile update
const formData = new FormData(); const formData = new FormData();
formData.append('first_name', this.editForm.first_name); formData.append('first_name', this.editForm.first_name);
formData.append('last_name', this.editForm.last_name); formData.append('last_name', this.editForm.last_name);
@ -252,14 +233,12 @@ export default {
formData.append('profile_img', this.selectedProfileImage); formData.append('profile_img', this.selectedProfileImage);
} }
// Send request to update profile
await axios.post(`${this.baseUrl}/editProfile/`, formData, { await axios.post(`${this.baseUrl}/editProfile/`, formData, {
headers: { headers: {
'Content-Type': 'multipart/form-data' 'Content-Type': 'multipart/form-data'
} }
}); });
// Handle password change if filled
if (this.passwordForm.new_password && this.passwordForm.current_password) { if (this.passwordForm.new_password && this.passwordForm.current_password) {
if (this.passwordForm.new_password !== this.passwordForm.confirm_password) { if (this.passwordForm.new_password !== this.passwordForm.confirm_password) {
// Show error Toast for password mismatch // Show error Toast for password mismatch
@ -270,14 +249,12 @@ export default {
throw new Error('رمز عبور جدید و تکرار آن مطابقت ندارند'); throw new Error('رمز عبور جدید و تکرار آن مطابقت ندارند');
} }
// Send request to reset password
await axios.post(`${this.baseUrl}/resetPassword/`, { await axios.post(`${this.baseUrl}/resetPassword/`, {
old_password: this.passwordForm.current_password, old_password: this.passwordForm.current_password,
new_password: this.passwordForm.new_password new_password: this.passwordForm.new_password
}); });
} }
// Fetch updated user data
await this.fetchUserData(); await this.fetchUserData();
// Show success Toast // Show success Toast
@ -286,10 +263,8 @@ export default {
title: 'تغییرات با موفقیت ذخیره شد', title: 'تغییرات با موفقیت ذخیره شد',
}); });
} catch (error) { } catch (error) {
// Handle specific error cases
let errorMessage = 'خطا در ذخیره تغییرات. لطفاً دوباره تلاش کنید'; let errorMessage = 'خطا در ذخیره تغییرات. لطفاً دوباره تلاش کنید';
if (error.response) { if (error.response) {
// Handle server errors (e.g., 400, 401)
if (error.response.status === 400) { if (error.response.status === 400) {
errorMessage = '.درخواست نامعتبر است'; errorMessage = '.درخواست نامعتبر است';
} else if (error.response.status === 401) { } else if (error.response.status === 401) {
@ -298,7 +273,6 @@ export default {
errorMessage = error.response.data.detail || error.response.data.message || errorMessage; errorMessage = error.response.data.detail || error.response.data.message || errorMessage;
} }
} else if (error.request) { } else if (error.request) {
// Handle network errors (no response from server)
errorMessage = 'مشکل در ارتباط با سرور. لطفاً دوباره تلاش کنید'; errorMessage = 'مشکل در ارتباط با سرور. لطفاً دوباره تلاش کنید';
} }
@ -308,10 +282,8 @@ export default {
title: errorMessage, title: errorMessage,
}); });
// Log error for debugging
console.error('Error saving profile:', error); console.error('Error saving profile:', error);
} finally { } finally {
// Reset saving state
this.saving = false; this.saving = false;
} }
}, },
@ -356,7 +328,6 @@ export default {
}); });
}, },
uploadProfileImage(event) { uploadProfileImage(event) {
// Handle profile image upload
const file = event.target.files[0]; const file = event.target.files[0];
if (file) { if (file) {
this.selectedProfileImage = file; this.selectedProfileImage = file;

View File

@ -151,11 +151,9 @@ export default {
}, },
computed: { computed: {
userProfilePicUrl() { userProfilePicUrl() {
// Prioritize userData from API if available
if (this.userData.customer && this.userData.customer.profile_img) { if (this.userData.customer && this.userData.customer.profile_img) {
return this.userData.customer.profile_img; return this.userData.customer.profile_img;
} }
// Fallback to localStorage
const customer = JSON.parse(localStorage.getItem('customer') || '{}'); const customer = JSON.parse(localStorage.getItem('customer') || '{}');
return customer.profile_img || this.userAvatarUrl; return customer.profile_img || this.userAvatarUrl;
}, },
@ -176,13 +174,11 @@ export default {
try { try {
const response = await axios.get('/getInfo'); const response = await axios.get('/getInfo');
// Check if response.data and required fields exist
if (!response.data || !response.data.data) { if (!response.data || !response.data.data) {
throw new Error('داده‌های پاسخ از سرور معتبر نیست'); throw new Error('داده‌های پاسخ از سرور معتبر نیست');
} }
const userData = response.data.data; // Adjust to match the nested 'data' structure const userData = response.data.data;
if (!userData.user || !userData.customer) { if (!userData.user || !userData.customer) {
throw new Error('داده‌های کاربر یا مشتری در پاسخ سرور وجود ندارد'); throw new Error('داده‌های کاربر یا مشتری در پاسخ سرور وجود ندارد');
} }
@ -200,7 +196,6 @@ export default {
semat: this.editForm.semat, semat: this.editForm.semat,
}; };
// Update localStorage to keep it in sync with the API response
localStorage.setItem('customer', JSON.stringify(userData.customer)); localStorage.setItem('customer', JSON.stringify(userData.customer));
} catch (error) { } catch (error) {
Toast.fire({ Toast.fire({
@ -208,7 +203,6 @@ export default {
title: 'خطا در بارگذاری اطلاعات کاربر. لطفاً دوباره تلاش کنید', title: 'خطا در بارگذاری اطلاعات کاربر. لطفاً دوباره تلاش کنید',
}); });
console.error('Error fetching user data:', error); console.error('Error fetching user data:', error);
// Initialize with default values to prevent breaking the UI
this.editForm = { this.editForm = {
first_name: '', first_name: '',
last_name: '', last_name: '',

View File

@ -260,6 +260,19 @@ export default {
}, },
methods: { methods: {
async updateMeeting(updatedMeeting) { async updateMeeting(updatedMeeting) {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
this.meetings = this.meetings.map((meeting) => this.meetings = this.meetings.map((meeting) =>
meeting.id === updatedMeeting.id meeting.id === updatedMeeting.id
@ -278,8 +291,17 @@ export default {
this.$nextTick(() => { this.$nextTick(() => {
this.refreshSwiper(); this.refreshSwiper();
}); });
// Show success Toast
Toast.fire({
icon: 'success',
title: 'جلسه با موفقیت به‌روزرسانی شد',
});
} catch (error) { } catch (error) {
alert(`خطا در به‌روزرسانی جلسات: ${error.message}`); // Show error Toast
Toast.fire({
icon: 'error',
title: `خطا در به‌روزرسانی جلسات: ${error.message}`,
});
} }
}, },
openMeetingInfo(meeting) { openMeetingInfo(meeting) {
@ -293,6 +315,19 @@ export default {
} }
}, },
async fetchMeetings() { async fetchMeetings() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
let token = localStorage.getItem('token'); let token = localStorage.getItem('token');
if (!token) throw new Error('توکن احراز هویت پیدا نشد'); if (!token) throw new Error('توکن احراز هویت پیدا نشد');
@ -341,7 +376,11 @@ export default {
this.filterMeetings(); this.filterMeetings();
this.refreshSwiper(); this.refreshSwiper();
} catch (error) { } catch (error) {
alert(`خطایی در دریافت جلسات رخ داد: ${error.response?.data?.message || error.message}`); // Show error Toast
Toast.fire({
icon: 'error',
title: `خطایی در دریافت جلسات رخ داد: ${error.response?.data?.message || error.message}`,
});
} }
}, },
filterMeetings() { filterMeetings() {
@ -366,6 +405,19 @@ export default {
this.filterMeetings(); this.filterMeetings();
}, },
async refreshToken() { async refreshToken() {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
const response = await axios.post(`${API_BASE_URL}/refresh_token`, { const response = await axios.post(`${API_BASE_URL}/refresh_token`, {
refresh_token: localStorage.getItem('refresh_token'), refresh_token: localStorage.getItem('refresh_token'),
@ -374,12 +426,29 @@ export default {
localStorage.setItem('token', newToken); localStorage.setItem('token', newToken);
return newToken; return newToken;
} catch (error) { } catch (error) {
alert('لطفاً دوباره وارد شوید'); // Show error Toast and redirect to login
Toast.fire({
icon: 'error',
title: 'لطفاً دوباره وارد شوید',
});
window.location.href = '/login'; window.location.href = '/login';
throw error; throw error;
} }
}, },
async createNewMeeting(meetingData) { async createNewMeeting(meetingData) {
// Define Toast configuration with SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
let token = localStorage.getItem('token'); let token = localStorage.getItem('token');
if (!token) throw new Error('توکن احراز هویت پیدا نشد'); if (!token) throw new Error('توکن احراز هویت پیدا نشد');
@ -404,9 +473,17 @@ export default {
await new Promise((resolve) => setTimeout(resolve, 500)); await new Promise((resolve) => setTimeout(resolve, 500));
await this.fetchMeetings(); await this.fetchMeetings();
this.showModal = false; this.showModal = false;
alert('جلسه با موفقیت ایجاد شد!'); // Show success Toast
Toast.fire({
icon: 'success',
title: 'جلسه با موفقیت ایجاد شد',
});
} catch (error) { } catch (error) {
alert(`خطایی در ایجاد جلسه رخ داد: ${error.response?.data?.message || error.message}`); // Show error Toast
Toast.fire({
icon: 'error',
title: `خطایی در ایجاد جلسه رخ داد: ${error.response?.data?.message || error.message}`,
});
} }
}, },
}, },

View File

@ -96,8 +96,8 @@ export default {
], ],
activeSharingFilter: 'all', activeSharingFilter: 'all',
activeSpaceTypeFilter: 'spaces', activeSpaceTypeFilter: 'spaces',
spaces: [], // Initialize the spaces array spaces: [],
selectedSpace: null, // Store the selected space selectedSpace: null,
}; };
}, },
computed: { computed: {
@ -126,14 +126,14 @@ export default {
}, },
async fetchSpaces() { async fetchSpaces() {
try { try {
const token = localStorage.getItem('token'); // Retrieve the token from localStorage const token = localStorage.getItem('token');
if (!token) { if (!token) {
console.error('No token found!'); console.error('No token found!');
return; return;
} }
const response = await axios.get( const response = await axios.get(
'http://my.xroomapp.com:8000/get_spaces', // API endpoint 'http://my.xroomapp.com:8000/get_spaces',
{ {
headers: { headers: {
Authorization: `Token ${token}`, Authorization: `Token ${token}`,
@ -142,28 +142,26 @@ export default {
} }
); );
// Store the spaces data in the spaces array
this.spaces = response.data.spaces.map(space => ({ this.spaces = response.data.spaces.map(space => ({
name: space.name, name: space.name,
img: space.assetBundleRoomId.img, // Assuming 'img' exists in the API response img: space.assetBundleRoomId.img,
capacity: space.capacity, capacity: space.capacity,
type: space.Private ? 'Private' : 'Public', // Adjust if you have a different field type: space.Private ? 'Private' : 'Public',
sharing: space.Private ? 'private' : 'team', sharing: space.Private ? 'private' : 'team',
spaceType: 'spaces', spaceType: 'spaces',
description: space.description, // Store description from response description: space.description,
})); }));
} catch (error) { } catch (error) {
console.error('Error fetching spaces:', error); console.error('Error fetching spaces:', error);
} }
}, },
handleCreateSpaceSubmit(space) { handleCreateSpaceSubmit(space) {
// Handle form submission here, space will contain the selected space and the additional fields
console.log('Form submitted with:', space); console.log('Form submitted with:', space);
this.closeCreateSpaceModal(); // Close the modal after submission this.closeCreateSpaceModal();
}, },
}, },
mounted() { mounted() {
this.fetchSpaces(); // Fetch spaces when the component is mounted this.fetchSpaces();
}, },
}; };
</script> </script>

View File

@ -585,7 +585,7 @@ export default {
} }
.file-card, .swiper-file-card { .file-card, .swiper-file-card {
width: calc(33.333% - .67rem); width: 23.7%;
border: 1px solid #b8c0cb; border: 1px solid #b8c0cb;
border-radius: 16px; border-radius: 16px;
background: #fff; background: #fff;
@ -740,16 +740,16 @@ export default {
.file-card { .file-card {
border-radius: 16px; border-radius: 16px;
padding: .5rem .5rem 1rem; padding: 6px;
} }
.file-image { .file-image {
height: 190px; height: 190px;
border-radius: 15px; border-radius: 12px;
} }
.file-pdf, .file-video, .file-glb, .file-other { .file-pdf, .file-video, .file-glb, .file-other {
width: 100%; width: 70%;
} }
.file-card-info { .file-card-info {
@ -757,8 +757,8 @@ export default {
} }
.file-title { .file-title {
color: #444d5a; color: #101010;
font-size: 1.25rem; font-size: 19px;
} }
.file-meta svg { .file-meta svg {

View File

@ -16,12 +16,11 @@
</template> </template>
<script> <script>
import axios from '@/axios'; import axios from '@/axios';
export default { export default {
name: 'ChangeAvatar', name: 'ChangeAvatar',
components: { components: {},
},
data() { data() {
return { return {
subdomain: 'xroom', subdomain: 'xroom',
@ -29,7 +28,7 @@
frame: null, frame: null,
saving: false, saving: false,
userData: { userData: {
user: { first_name: '', last_name: '' } user: { first_name: '', last_name: '' },
}, },
maleAvatars: [ maleAvatars: [
{ id: 1, name: 'مرد ۱', src: 'http://194.62.43.230:8000/media/2025/5/5/men1.glb' }, { id: 1, name: 'مرد ۱', src: 'http://194.62.43.230:8000/media/2025/5/5/men1.glb' },
@ -40,20 +39,19 @@
{ id: 4, name: 'زن ۱', src: 'http://194.62.43.230:8000/media/2025/5/5/men1.glb' }, { id: 4, name: 'زن ۱', src: 'http://194.62.43.230:8000/media/2025/5/5/men1.glb' },
{ id: 10, name: 'زن ۳', src: 'http://194.62.43.230:8000/media/2025/5/5/men1.glb' }, { id: 10, name: 'زن ۳', src: 'http://194.62.43.230:8000/media/2025/5/5/men1.glb' },
], ],
baseUrl: 'http://194.62.43.230:8000' baseUrl: 'http://194.62.43.230:8000',
}; };
}, },
computed: { computed: {
iframeSrc() { iframeSrc() {
return `https://${this.subdomain}.readyplayer.me/avatar?frameApi`; return `https://${this.subdomain}.readyplayer.me/avatar?frameApi`;
} },
}, },
mounted() { mounted() {
this.frame = document.getElementById('frame'); this.frame = document.getElementById('frame');
window.addEventListener('message', this.subscribe); window.addEventListener('message', this.subscribe);
document.addEventListener('message', this.subscribe); document.addEventListener('message', this.subscribe);
// Load existing avatar if available
this.loadUserData(); this.loadUserData();
}, },
beforeUnmount() { beforeUnmount() {
@ -65,21 +63,19 @@
try { try {
const customer = JSON.parse(localStorage.getItem('customer') || '{}'); const customer = JSON.parse(localStorage.getItem('customer') || '{}');
const payload = { const payload = {
profile_glb_url: glbUrl profile_glb_url: glbUrl,
}; };
// If profile_img is null, set it to the thumbnail of the GLB
if (!customer.profile_img) { if (!customer.profile_img) {
payload.profile_img = this.getAvatarThumbnail(glbUrl); payload.profile_img = this.getAvatarThumbnail(glbUrl);
} }
const response = await axios.post(`${this.baseUrl}/editProfile/`, payload, { const response = await axios.post(`${this.baseUrl}/editProfile/`, payload, {
headers: { headers: {
'Content-Type': 'application/json' 'Content-Type': 'application/json',
} },
}); });
// Update local storage
if (!customer.profile_img) { if (!customer.profile_img) {
customer.profile_img = payload.profile_img; customer.profile_img = payload.profile_img;
} }
@ -92,12 +88,8 @@
throw error; throw error;
} }
}, },
getAvatarThumbnail(glbUrl) { getAvatarThumbnail(glbUrl) {
// Replace .glb with .png for thumbnail
// Adjust this based on your actual thumbnail URLs
if (glbUrl.includes('readyplayer.me')) { if (glbUrl.includes('readyplayer.me')) {
// For Ready Player Me avatars, use their thumbnail service
return glbUrl.replace('.glb', '.png'); return glbUrl.replace('.glb', '.png');
} }
return glbUrl.replace('.glb', '.png') || 'https://i.imgur.com/QbXfV6C.png'; return glbUrl.replace('.glb', '.png') || 'https://i.imgur.com/QbXfV6C.png';
@ -120,28 +112,49 @@
JSON.stringify({ JSON.stringify({
target: 'readyplayerme', target: 'readyplayerme',
type: 'subscribe', type: 'subscribe',
eventName: 'v1.**' eventName: 'v1.**',
}), }),
'*' '*'
); );
} }
if (json.eventName === 'v1.avatar.exported') { if (json.eventName === 'v1.avatar.exported') {
// Define Toast configuration
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
this.saving = true; this.saving = true;
try { try {
console.log(`Avatar URL: ${json.data.url}`); console.log(`Avatar URL: ${json.data.url}`);
this.avatarUrl = json.data.url; this.avatarUrl = json.data.url;
this.frame.hidden = true; this.frame.hidden = true;
// Save the avatar URL to your backend
await this.saveAvatarUrl(json.data.url); await this.saveAvatarUrl(json.data.url);
alert('آواتار با موفقیت ذخیره شد'); // Show success Toast
this.$router.push('/dashboard'); Toast.fire({
icon: 'success',
title: 'آواتار با موفقیت ذخیره شد',
});
this.$router.push('/dashboard');
} catch (error) { } catch (error) {
// Show error Toast
Toast.fire({
icon: 'error',
title: error.response?.data?.detail || 'خطا در ذخیره آواتار',
});
console.error('Error saving avatar:', error); console.error('Error saving avatar:', error);
alert('خطا در ذخیره آواتار');
} finally { } finally {
this.saving = false; this.saving = false;
} }
@ -157,19 +170,40 @@
openAvatarEditor() { openAvatarEditor() {
this.frame.hidden = false; this.frame.hidden = false;
}, },
async selectAvatar(avatar) { async selectAvatar(avatar) {
// Define Toast configuration
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
this.saving = true; this.saving = true;
try { try {
await this.saveAvatarUrl(avatar.src); await this.saveAvatarUrl(avatar.src);
this.avatarUrl = avatar.src; this.avatarUrl = avatar.src;
alert('آواتار با موفقیت انتخاب شد');
this.$router.push('/dashboard');
// Show success Toast
Toast.fire({
icon: 'success',
title: 'آواتار با موفقیت انتخاب شد',
});
this.$router.push('/dashboard');
} catch (error) { } catch (error) {
// Show error Toast with specific message
Toast.fire({
icon: 'error',
title: error.response?.data?.detail || 'خطا در انتخاب آواتار',
});
console.error('Error selecting avatar:', error); console.error('Error selecting avatar:', error);
alert(error.response?.data?.detail || error.message || 'خطا در انتخاب آواتار');
} finally { } finally {
this.saving = false; this.saving = false;
} }
@ -181,10 +215,10 @@
} catch (error) { } catch (error) {
console.error('Error fetching user data:', error); console.error('Error fetching user data:', error);
} }
} },
} },
}; };
</script> </script>
<style scoped> <style scoped>
/* Previous styles remain the same, add these new styles */ /* Previous styles remain the same, add these new styles */

View File

@ -63,6 +63,7 @@
</div> </div>
</template> </template>
<script> <script>
import TeamUser from '@/components/TeamUser.vue'; import TeamUser from '@/components/TeamUser.vue';
import BuySubscription from '@/components/BuySubscription.vue'; import BuySubscription from '@/components/BuySubscription.vue';
@ -82,8 +83,8 @@ export default {
teamMemberCapacity: 0, teamMemberCapacity: 0,
subscriptionCount: 0, subscriptionCount: 0,
hasActiveSubscription: false, hasActiveSubscription: false,
hasExpiredSubscription: false, // جدید: بررسی اشتراک منقضیشده hasExpiredSubscription: false,
subscriptionEndTime: null, // جدید: ذخیره تاریخ انقضای اشتراک subscriptionEndTime: null,
teamId: null, teamId: null,
subscriptionId: null, subscriptionId: null,
isBillingModalVisible: false, isBillingModalVisible: false,
@ -107,16 +108,46 @@ export default {
this.activeTab = tabName; this.activeTab = tabName;
}, },
async fetchTeamData() { async fetchTeamData() {
// Define Toast configuration for SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
const response = await this.axiosGet('/get_team'); const response = await this.axiosGet('/get_team');
const team = response.data.teams[0]; const team = response.data.teams[0];
this.teamId = team?.id || null; this.teamId = team?.id || null;
} catch (error) { } catch (error) {
// Log and show error Toast
console.error('Error fetching team data:', error); console.error('Error fetching team data:', error);
alert('خطا در بارگذاری اطلاعات تیم.'); Toast.fire({
icon: 'error',
title: 'خطا در بارگذاری اطلاعات تیم.',
});
} }
}, },
async fetchTeamMemberInfo() { async fetchTeamMemberInfo() {
// Define Toast configuration for SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
const response = await this.axiosGet('/get_all_team_members'); const response = await this.axiosGet('/get_all_team_members');
this.userList = response.data.members.map(member => ({ this.userList = response.data.members.map(member => ({
@ -128,28 +159,62 @@ export default {
})); }));
this.teamMemberCapacity = response.data.members.length; this.teamMemberCapacity = response.data.members.length;
} catch (error) { } catch (error) {
// Log and show error Toast
console.error('Error fetching team members:', error); console.error('Error fetching team members:', error);
alert('خطا در بارگذاری اطلاعات اعضای تیم.'); Toast.fire({
icon: 'error',
title: 'خطا در بارگذاری اطلاعات اعضای تیم.',
});
} }
}, },
async fetchUserData() { async fetchUserData() {
// Define Toast configuration for SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
const response = await this.axiosGet('/get_user_subscriptions'); const response = await this.axiosGet('/get_user_subscriptions');
const subscriptions = response.data.subscriptions || []; const subscriptions = response.data.subscriptions || [];
this.subscriptionCount = subscriptions.reduce((total, sub) => total + sub.user_count, 0); this.subscriptionCount = subscriptions.reduce((total, sub) => total + sub.user_count, 0);
this.subscriptionId = subscriptions[0]?.id || null; this.subscriptionId = subscriptions[0]?.id || null;
this.subscriptionEndTime = subscriptions[0]?.endTime || null; // جدید: تاریخ انقضا this.subscriptionEndTime = subscriptions[0]?.endTime || null;
const now = new Date(); const now = new Date();
const isExpiredByTime = this.subscriptionEndTime && new Date(this.subscriptionEndTime) < now; const isExpiredByTime = this.subscriptionEndTime && new Date(this.subscriptionEndTime) < now;
const isExpiredByCapacity = this.subscriptionCount <= this.teamMemberCapacity; const isExpiredByCapacity = this.subscriptionCount <= this.teamMemberCapacity;
this.hasActiveSubscription = subscriptions.length > 0 && !isExpiredByTime && !isExpiredByCapacity; this.hasActiveSubscription = subscriptions.length > 0 && !isExpiredByTime && !isExpiredByCapacity;
this.hasExpiredSubscription = subscriptions.length > 0 && (isExpiredByTime || isExpiredByCapacity); this.hasExpiredSubscription = subscriptions.length > 0 && (isExpiredByTime || isExpiredByCapacity);
} catch (error) { } catch (error) {
// Log and show error Toast
console.error('Error fetching user data:', error); console.error('Error fetching user data:', error);
alert('خطا در بارگذاری اطلاعات اشتراک.'); Toast.fire({
icon: 'error',
title: 'خطا در بارگذاری اطلاعات اشتراک.',
});
} }
}, },
async handlePaymentSuccess({ subscriptionId }) { async handlePaymentSuccess({ subscriptionId }) {
// Define Toast configuration for SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
try { try {
this.subscriptionId = subscriptionId; this.subscriptionId = subscriptionId;
await Promise.all([ await Promise.all([
@ -160,14 +225,26 @@ export default {
if (!this.teamId && this.subscriptionId) { if (!this.teamId && this.subscriptionId) {
await this.createTeam(); await this.createTeam();
alert('اشتراک و تیم به درستی ساخته شد.'); // Show success Toast
Toast.fire({
icon: 'success',
title: 'اشتراک و تیم با موفقیت ساخته شد.',
});
} else if (this.teamId) { } else if (this.teamId) {
alert('تیم از قبل وجود دارد.'); // Show message if team already exists
Toast.fire({
icon: 'info',
title: 'تیم از قبل وجود دارد.',
});
} }
this.activeTab = 'membership'; this.activeTab = 'membership';
} catch (error) { } catch (error) {
// Log and show error Toast
console.error('Error handling payment success:', error); console.error('Error handling payment success:', error);
alert('خطا در پردازش پرداخت یا ساخت تیم.'); Toast.fire({
icon: 'error',
title: 'خطا در پردازش پرداخت یا ساخت تیم.',
});
} }
}, },
async createTeam() { async createTeam() {
@ -181,13 +258,34 @@ export default {
await this.fetchTeamData(); await this.fetchTeamData();
}, },
async submitNewUser(newUser) { async submitNewUser(newUser) {
// Define Toast configuration for SweetAlert2
const Toast = this.$swal.mixin({
toast: true,
position: 'top-end',
showConfirmButton: false,
timer: 3000,
timerProgressBar: true,
didOpen: (toast) => {
toast.onmouseenter = this.$swal.stopTimer;
toast.onmouseleave = this.$swal.resumeTimer;
},
});
if (this.subscriptionCount - this.teamMemberCapacity <= 0) { if (this.subscriptionCount - this.teamMemberCapacity <= 0) {
alert('اشتراک فعالی ندارید , اشتراک تهیه نمایید.'); // Show error if no active subscription
Toast.fire({
icon: 'warning',
title: 'اشتراک فعالی ندارید، لطفاً اشتراک تهیه کنید.',
});
this.activeTab = 'buy-subscription'; this.activeTab = 'buy-subscription';
return; return;
} }
if (!this.teamId) { if (!this.teamId) {
alert('خطا: اطلاعات تیم یافت نشد.'); // Show error if team ID is missing
Toast.fire({
icon: 'error',
title: 'خطا: اطلاعات تیم یافت نشد.',
});
return; return;
} }
try { try {
@ -200,10 +298,18 @@ export default {
}); });
this.teamMemberCapacity++; this.teamMemberCapacity++;
await this.fetchTeamMemberInfo(); await this.fetchTeamMemberInfo();
alert('کاربر با موفقیت اضافه شد.'); // Show success Toast
Toast.fire({
icon: 'success',
title: 'کاربر با موفقیت اضافه شد.',
});
} catch (error) { } catch (error) {
// Log and show error Toast
console.error('Error adding user:', error); console.error('Error adding user:', error);
alert('خطا در اضافه کردن کاربر.'); Toast.fire({
icon: 'error',
title: 'خطا در اضافه کردن کاربر.',
});
} }
}, },
handleTeamData(data) { handleTeamData(data) {
@ -211,14 +317,14 @@ export default {
}, },
async axiosGet(endpoint) { async axiosGet(endpoint) {
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
if (!token) throw new Error('توکن احراز هویت یافت نشد.'); if (!token) throw new Error('Authentication token not found.');
return await axios.get(`${this.baseUrl}${endpoint}`, { return await axios.get(`${this.baseUrl}${endpoint}`, {
headers: { Authorization: `Token ${token}`, 'Content-Type': 'application/json' }, headers: { Authorization: `Token ${token}`, 'Content-Type': 'application/json' },
}); });
}, },
async axiosPost(endpoint, data) { async axiosPost(endpoint, data) {
const token = localStorage.getItem('token'); const token = localStorage.getItem('token');
if (!token) throw new Error('توکن احراز هویت یافت نشد.'); if (!token) throw new Error('Authentication token not found.');
return await axios.post(`${this.baseUrl}${endpoint}`, data, { return await axios.post(`${this.baseUrl}${endpoint}`, data, {
headers: { Authorization: `Token ${token}`, 'Content-Type': 'application/json' }, headers: { Authorization: `Token ${token}`, 'Content-Type': 'application/json' },
}); });
@ -232,7 +338,6 @@ export default {
}; };
</script> </script>
<style scoped> <style scoped>
.section-title { .section-title {