diff options
Diffstat (limited to 'backend/src/models')
-rw-r--r-- | backend/src/models/Category.js | 34 | ||||
-rw-r--r-- | backend/src/models/Feedback.js | 61 | ||||
-rw-r--r-- | backend/src/models/MenuItem.js | 73 | ||||
-rw-r--r-- | backend/src/models/Order.js | 60 | ||||
-rw-r--r-- | backend/src/models/OrderItem.js | 32 | ||||
-rw-r--r-- | backend/src/models/Reservation.js | 54 | ||||
-rw-r--r-- | backend/src/models/Table.js | 36 | ||||
-rw-r--r-- | backend/src/models/User.js | 70 |
8 files changed, 420 insertions, 0 deletions
diff --git a/backend/src/models/Category.js b/backend/src/models/Category.js new file mode 100644 index 0000000..bb28ba3 --- /dev/null +++ b/backend/src/models/Category.js @@ -0,0 +1,34 @@ +const mongoose = require('mongoose'); + +const categorySchema = new mongoose.Schema( + { + name: { + type: String, + required: [true, 'Category name is required'], + trim: true, + unique: true + }, + description: { + type: String, + trim: true + }, + image: { + type: String + }, + active: { + type: Boolean, + default: true + }, + displayOrder: { + type: Number, + default: 0 + } + }, + { + timestamps: true + } +); + +const Category = mongoose.model('Category', categorySchema); + +module.exports = Category;
\ No newline at end of file diff --git a/backend/src/models/Feedback.js b/backend/src/models/Feedback.js new file mode 100644 index 0000000..b433fed --- /dev/null +++ b/backend/src/models/Feedback.js @@ -0,0 +1,61 @@ +const mongoose = require('mongoose'); + +const feedbackSchema = new mongoose.Schema( + { + user: { + type: mongoose.Schema.Types.ObjectId, + ref: 'User', + required: [true, 'User is required'] + }, + order: { + type: mongoose.Schema.Types.ObjectId, + ref: 'Order' + }, + rating: { + type: Number, + required: [true, 'Rating is required'], + min: 1, + max: 5 + }, + comment: { + type: String, + trim: true + }, + foodRating: { + type: Number, + min: 1, + max: 5 + }, + serviceRating: { + type: Number, + min: 1, + max: 5 + }, + ambience: { + type: Number, + min: 1, + max: 5 + }, + photos: [ + { + type: String + } + ], + status: { + type: String, + enum: ['pending', 'approved', 'rejected'], + default: 'pending' + }, + adminResponse: { + type: String, + trim: true + } + }, + { + timestamps: true + } +); + +const Feedback = mongoose.model('Feedback', feedbackSchema); + +module.exports = Feedback;
\ No newline at end of file diff --git a/backend/src/models/MenuItem.js b/backend/src/models/MenuItem.js new file mode 100644 index 0000000..47701c8 --- /dev/null +++ b/backend/src/models/MenuItem.js @@ -0,0 +1,73 @@ +const mongoose = require('mongoose'); + +const menuItemSchema = new mongoose.Schema( + { + name: { + type: String, + required: [true, 'Menu item name is required'], + trim: true + }, + description: { + type: String, + trim: true + }, + price: { + type: Number, + required: [true, 'Price is required'], + min: 0 + }, + category: { + type: mongoose.Schema.Types.ObjectId, + ref: 'Category', + required: [true, 'Category is required'] + }, + image: { + type: String + }, + ingredients: { + type: [String], + default: [] + }, + available: { + type: Boolean, + default: true + }, + vegetarian: { + type: Boolean, + default: false + }, + vegan: { + type: Boolean, + default: false + }, + glutenFree: { + type: Boolean, + default: false + }, + spiceLevel: { + type: Number, + min: 0, + max: 5, + default: 0 + }, + preparationTime: { + type: Number, + min: 0, + default: 15 + }, + featuredItem: { + type: Boolean, + default: false + } + }, + { + timestamps: true + } +); + +// Create text index for search functionality +menuItemSchema.index({ name: 'text', description: 'text', ingredients: 'text' }); + +const MenuItem = mongoose.model('MenuItem', menuItemSchema); + +module.exports = MenuItem;
\ No newline at end of file diff --git a/backend/src/models/Order.js b/backend/src/models/Order.js new file mode 100644 index 0000000..c60f986 --- /dev/null +++ b/backend/src/models/Order.js @@ -0,0 +1,60 @@ +const mongoose = require('mongoose'); + +const orderSchema = new mongoose.Schema( + { + user: { + type: mongoose.Schema.Types.ObjectId, + ref: 'User', + required: [true, 'User is required'] + }, + items: [ + { + type: mongoose.Schema.Types.ObjectId, + ref: 'OrderItem' + } + ], + table: { + type: mongoose.Schema.Types.ObjectId, + ref: 'Table' + }, + status: { + type: String, + enum: ['pending', 'preparing', 'ready', 'served', 'completed', 'cancelled'], + default: 'pending' + }, + totalAmount: { + type: Number, + required: [true, 'Total amount is required'], + min: 0 + }, + paymentStatus: { + type: String, + enum: ['pending', 'completed', 'failed', 'refunded'], + default: 'pending' + }, + paymentMethod: { + type: String, + enum: ['cash', 'card', 'mobile'], + default: 'cash' + }, + specialInstructions: { + type: String, + trim: true + }, + isDelivery: { + type: Boolean, + default: false + }, + deliveryAddress: { + type: String, + trim: true + } + }, + { + timestamps: true + } +); + +const Order = mongoose.model('Order', orderSchema); + +module.exports = Order;
\ No newline at end of file diff --git a/backend/src/models/OrderItem.js b/backend/src/models/OrderItem.js new file mode 100644 index 0000000..0625c96 --- /dev/null +++ b/backend/src/models/OrderItem.js @@ -0,0 +1,32 @@ +const mongoose = require('mongoose'); + +const orderItemSchema = new mongoose.Schema( + { + menuItem: { + type: mongoose.Schema.Types.ObjectId, + ref: 'MenuItem', + required: [true, 'Menu item is required'] + }, + quantity: { + type: Number, + required: [true, 'Quantity is required'], + min: 1 + }, + price: { + type: Number, + required: [true, 'Price is required'], + min: 0 + }, + specialInstructions: { + type: String, + trim: true + } + }, + { + timestamps: true + } +); + +const OrderItem = mongoose.model('OrderItem', orderItemSchema); + +module.exports = OrderItem;
\ No newline at end of file diff --git a/backend/src/models/Reservation.js b/backend/src/models/Reservation.js new file mode 100644 index 0000000..8ddba54 --- /dev/null +++ b/backend/src/models/Reservation.js @@ -0,0 +1,54 @@ +const mongoose = require('mongoose'); + +const reservationSchema = new mongoose.Schema( + { + user: { + type: mongoose.Schema.Types.ObjectId, + ref: 'User', + required: [true, 'User is required'] + }, + table: { + type: mongoose.Schema.Types.ObjectId, + ref: 'Table', + required: [true, 'Table is required'] + }, + date: { + type: Date, + required: [true, 'Reservation date is required'] + }, + startTime: { + type: String, + required: [true, 'Start time is required'] + }, + endTime: { + type: String, + required: [true, 'End time is required'] + }, + numberOfGuests: { + type: Number, + required: [true, 'Number of guests is required'], + min: 1 + }, + status: { + type: String, + enum: ['pending', 'confirmed', 'cancelled', 'completed'], + default: 'pending' + }, + specialRequests: { + type: String, + trim: true + }, + occasion: { + type: String, + enum: ['regular', 'birthday', 'anniversary', 'business', 'other'], + default: 'regular' + } + }, + { + timestamps: true + } +); + +const Reservation = mongoose.model('Reservation', reservationSchema); + +module.exports = Reservation;
\ No newline at end of file diff --git a/backend/src/models/Table.js b/backend/src/models/Table.js new file mode 100644 index 0000000..7653b3e --- /dev/null +++ b/backend/src/models/Table.js @@ -0,0 +1,36 @@ +const mongoose = require('mongoose'); + +const tableSchema = new mongoose.Schema( + { + tableNumber: { + type: Number, + required: [true, 'Table number is required'], + unique: true + }, + capacity: { + type: Number, + required: [true, 'Capacity is required'], + min: 1 + }, + location: { + type: String, + enum: ['indoor', 'outdoor', 'balcony', 'private'], + default: 'indoor' + }, + available: { + type: Boolean, + default: true + }, + isReserved: { + type: Boolean, + default: false + } + }, + { + timestamps: true + } +); + +const Table = mongoose.model('Table', tableSchema); + +module.exports = Table;
\ No newline at end of file diff --git a/backend/src/models/User.js b/backend/src/models/User.js new file mode 100644 index 0000000..dda71d0 --- /dev/null +++ b/backend/src/models/User.js @@ -0,0 +1,70 @@ +const mongoose = require('mongoose'); +const bcrypt = require('bcryptjs'); + +const userSchema = new mongoose.Schema( + { + name: { + type: String, + required: [true, 'Name is required'], + trim: true + }, + email: { + type: String, + required: [true, 'Email is required'], + unique: true, + trim: true, + lowercase: true, + match: [/^\w+([.-]?\w+)*@\w+([.-]?\w+)*(\.\w{2,3})+$/, 'Please enter a valid email'] + }, + password: { + type: String, + required: [true, 'Password is required'], + minlength: [6, 'Password must be at least 6 characters long'], + select: false + }, + role: { + type: String, + enum: ['customer', 'staff', 'admin'], + default: 'customer' + }, + phone: { + type: String, + trim: true + }, + address: { + type: String, + trim: true + }, + active: { + type: Boolean, + default: true + } + }, + { + timestamps: true + } +); + +// Password hashing middleware +userSchema.pre('save', async function (next) { + if (!this.isModified('password')) { + return next(); + } + + try { + const salt = await bcrypt.genSalt(10); + this.password = await bcrypt.hash(this.password, salt); + next(); + } catch (error) { + next(error); + } +}); + +// Compare password method +userSchema.methods.comparePassword = async function (candidatePassword) { + return await bcrypt.compare(candidatePassword, this.password); +}; + +const User = mongoose.model('User', userSchema); + +module.exports = User;
\ No newline at end of file |