< Express

Express - Dátumvizsgálat

Szerző: Sallai András

Copyright © 2025, Sallai András

Licenc: CC Attribution-Share Alike 4.0 International

Web: https://szit.hu

Átfedésvizsgálat

Legyen 3 foglalás. Adott két meglévő foglalás:

3-tól 5-ig

7-től 9-ig

Szeretnénk 5-től 7-ig foglalni.

A másik lehetőség, hogy a meglévő foglalások:

3-tól 5-ig

9-től 11-ig

Amit szeretnénk foglalni: 6-tól 8-ig.

Lássuk a következő ábrán.

Az alábbiakban szállodai foglalásra látunk példát. Ha április 5-én elmegy egy vendég, akkor 5-től már lehet foglalni.

A Sequelize ORM lekérdezési és operátorhasználati lehetőségeit használjuk, amelyről többet olvashatsz itt:

https://sequelize.org/docs/v6/core-concepts/model-querying-basics/ (2025)

A következő részlet egy kontrollerben helyezhető el, például egy Create művelet esetén.

Implicit ÉS kapcsolattal:

const { startDate, endDate } = req.body const overlappingRental = await Rental.findAll({ where: { startDate: { [Op.lt]: endDate }, endDate: { [Op.gt]: startDate } } }) if(overlappingRental.length > 0) { throw new Error('Hiba! Átfedés a foglalásban!') }

Explicit, egyértelműen megadva az és kapcsolat:

const { startDate, endDate } = req.body const overlappingRental = await Rental.findAll({ where: { [Op.and]: [ { startDate: { [Op.lt]: endDate } }, { endDate: { [Op.gt]: startDate } } ] } }) if(overlappingRental.length > 0) { throw new Error('Hiba! Átfedés a foglalásban!') }

Csak adott felhasználónál vizsgáljuk:

const { userId, startDate, endDate } = req.body const overlappingRental = await Rental.findAll({ where: { userId: userId, [Op.and]: [ { startDate: { [Op.lt]: endDate } }, { endDate: { [Op.gt]: startDate } } ] } }) if(overlappingRental.length > 0) { throw new Error('Hiba! Átfedés a foglalásban!') }

Szigorú kizárás

Szigorú kizárásról beszélünk, amikor április 5-ig van foglalva valami, és csak másnaptól lehet újra foglalni.

where: { [Op.and]: [ { startDate: { [Op.lte]: endDate } }, { endDate: { [Op.gte]: startDate } } ] }

Minimum és maximum napok száma

Legyen egy foglalás, ahol minimum 3 napot, maximum 21 napot foglalhatunk.

Mivel nem szükséges lekérdezést végezni az adatbázisból, ezért az ilyen érvényességet vizsgálhatjuk a modellben is.

import { DataTypes } from 'sequelize' import sequelize from '../database/database.js' const Rental = sequelize.define('rental', { id: { type: DataTypes.INTEGER, autoIncrement: true, primaryKey: true }, userId: { type: DataTypes.STRING, allowNull: false, validate: { len: [1,] } }, startDate: { type: DataTypes.DATE, allowNull: true, validate: { isDate: true } }, endDate: { type: DataTypes.DATE, allowNull: true, validate: { isDate: true, checkDateRange(value) { if(this.startDate && value) { const startDate = new Date(this.startDate) const endDate = new Date(value) startDate.setHours(0, 0, 0, 0) endDate.setHours(0, 0, 0, 0) const diffInDays = Math.round((endDate - startDate) / (1000 * 60 * 60 * 24)) if(diffInDays < 2) { throw new Error('Hiba! A bérlés időtartalma legalább 3 nap') } if(diffInDays > 20) { throw new Error('Hiba! A bérlés maximum 21 nap') } } } } }, duration: { type: DataTypes.VIRTUAL, get() { if (this.endDate && this.startDate) { const millisecondsPerDay = 1000 * 60 * 60 * 24; return Math.floor((this.endDate - this.startDate) / millisecondsPerDay); } return null; } }, totalCost: { type: DataTypes.VIRTUAL, get() { let total = 0 if (this.rentalItems) { for(let i = 0; i < this.rentalItems.length; i++) { total += this.rentalItems[i].dailyPrice * this.duration } } return total } } }) sequelize.sync({ force: false }) export default Rental

A duration és a totalCost mezők számított mezők, amelyeket virtuális mezőként hoztunk létre. Ezekről többet olvashatsz A Sequelize dokumentációjában:

https://sequelize.org/docs/v6/core-concepts/getters-setters-virtuals/ (2025)