235 lines
6.7 KiB
Python
235 lines
6.7 KiB
Python
"""
|
|
Apointment Managment
|
|
=========================
|
|
|
|
This module manages appointments in the database. It provides comprehensive
|
|
functionality for creating, updating, retrieving appointments items.
|
|
|
|
Key Features:
|
|
- Creating and updating appointments
|
|
- Retrieving items by ID
|
|
- Managing time slots
|
|
- client retrival
|
|
|
|
Collection Structure:
|
|
- appointments:
|
|
- Required fields: user, start_date, end_date, daytime, slots, slot_time
|
|
- Optional fields: Images, Filter, Filter2, Filter3, Anschaffungsjahr, Anschaffungskosten, Code_4
|
|
- Status fields: slots_used_by
|
|
"""
|
|
import Web.modules.database.settings as cfg
|
|
from Web.modules.database.settings import MongoClient
|
|
from bson.objectid import ObjectId
|
|
import datetime
|
|
|
|
|
|
def _get_tenant_db(client):
|
|
try:
|
|
from tenant import get_tenant_db
|
|
return get_tenant_db(client)
|
|
except Exception:
|
|
return client[cfg.MONGODB_DB]
|
|
|
|
def _active_record_query(extra_query=None):
|
|
"""Build a query that excludes logically deleted records."""
|
|
base_query = {'Deleted': {'$ne': True}}
|
|
if extra_query:
|
|
base_query.update(extra_query)
|
|
return base_query
|
|
|
|
|
|
def add(date_start: str, date_end: str, time_span: list, slots: int, slot_lenght: int, user: str, mail: list=[], note:str="", calendar_enabled: bool=False, title: str=""):
|
|
try:
|
|
client = MongoClient(cfg.MONGODB_HOST, cfg.MONGODB_PORT)
|
|
db = _get_tenant_db(client)
|
|
items = db['appointments']
|
|
|
|
item = {
|
|
'date_start': date_start,
|
|
'date_end': date_end,
|
|
'time_span': time_span,
|
|
'slots': slots,
|
|
'slot_lenght': slot_lenght,
|
|
'user': user,
|
|
'mail': mail,
|
|
'note': note,
|
|
'title': title,
|
|
'calendar_enabled': bool(calendar_enabled),
|
|
'slots_booked': [], # -> [(start_time, name), ...]the list gets there indexes as the slot 1-defined so is can be counted without an extra variable
|
|
'Created': datetime.datetime.now(),
|
|
'LastUpdated': datetime.datetime.now()
|
|
}
|
|
result = items.insert_one(item)
|
|
return result.inserted_id
|
|
except Exception as e:
|
|
print(f"Exception accured: {e}")
|
|
|
|
|
|
def get_item(id):
|
|
"""
|
|
Retrieve a specific appointment by its ID.
|
|
|
|
Args:
|
|
id (str): ID of the appointsment to retrieve
|
|
|
|
Returns:
|
|
dict: The appointment document or None if not found
|
|
"""
|
|
try:
|
|
client = MongoClient(cfg.MONGODB_HOST, cfg.MONGODB_PORT)
|
|
db = _get_tenant_db(client)
|
|
items = db['appointments']
|
|
item = items.find_one(_active_record_query({'_id': ObjectId(id)}))
|
|
client.close()
|
|
return item
|
|
except Exception as e:
|
|
print(f"Error retrieving item: {e}")
|
|
return None
|
|
|
|
def update(id,slots_used: list):
|
|
"""
|
|
Update an existing appointment.
|
|
|
|
Args:
|
|
id (str): ID of the item to update
|
|
|
|
|
|
Returns:
|
|
bool: True if successful, False otherwise
|
|
"""
|
|
try:
|
|
client = MongoClient(cfg.MONGODB_HOST, cfg.MONGODB_PORT)
|
|
db = _get_tenant_db(client)
|
|
items = db['appointments']
|
|
|
|
update_data = {
|
|
'slots_booked': slots_used,
|
|
'LastUpdated': datetime.datetime.now()
|
|
}
|
|
|
|
result = items.update_one(
|
|
{'_id': ObjectId(id)},
|
|
{'$set': update_data}
|
|
)
|
|
|
|
client.close()
|
|
return result.modified_count > 0
|
|
except Exception as e:
|
|
print(f"Error updating item: {e}")
|
|
return False
|
|
|
|
|
|
def remove_slot(id, date_start_time, name):
|
|
"""
|
|
Remove a booked slot from an appointment's `slots_booked`.
|
|
|
|
Args:
|
|
id (str): Appointment ID
|
|
date_start_time: The start time value used when booking
|
|
name (str): Name associated with the booking
|
|
|
|
Returns:
|
|
bool: True if a slot was removed, False otherwise
|
|
"""
|
|
try:
|
|
client = MongoClient(cfg.MONGODB_HOST, cfg.MONGODB_PORT)
|
|
db = _get_tenant_db(client)
|
|
items = db['appointments']
|
|
|
|
# Attempt to pull the exact element (stored as an array/tuple)
|
|
result = items.update_one(
|
|
{'_id': ObjectId(id)},
|
|
{'$pull': {'slots_booked': [date_start_time, name]}}
|
|
)
|
|
|
|
client.close()
|
|
return result.modified_count > 0
|
|
except Exception as e:
|
|
print(f"Error removing slot: {e}")
|
|
return False
|
|
|
|
|
|
def remove(id):
|
|
"""
|
|
Soft-delete an appointment by setting its `Deleted` flag.
|
|
|
|
Args:
|
|
id (str): Appointment ID
|
|
|
|
Returns:
|
|
bool: True if the appointment was marked deleted, False otherwise
|
|
"""
|
|
try:
|
|
client = MongoClient(cfg.MONGODB_HOST, cfg.MONGODB_PORT)
|
|
db = _get_tenant_db(client)
|
|
items = db['appointments']
|
|
|
|
result = items.delete_one({'_id': ObjectId(id)})
|
|
|
|
client.close()
|
|
return result.deleted_count > 0
|
|
except Exception as e:
|
|
print(f"Error removing appointment: {e}")
|
|
return False
|
|
|
|
def remove_done():
|
|
"""removose already finisched appointments"""
|
|
try:
|
|
client = MongoClient(cfg.MONGODB_HOST, cfg.MONGODB_PORT)
|
|
db = _get_tenant_db(client)
|
|
items = db['appointments']
|
|
|
|
today = datetime.date.today().strftime('%Y-%m-%d')
|
|
removed_count = 0
|
|
|
|
cursor = items.find(
|
|
_active_record_query(
|
|
{
|
|
'date_end': {'$lt': today},
|
|
}
|
|
)
|
|
).sort('date_start', 1)
|
|
|
|
for item in cursor:
|
|
item['_id'] = str(item.get('_id'))
|
|
result = items.delete_one({'_id': ObjectId(item['_id'])})
|
|
removed_count += result.deleted_count
|
|
|
|
client.close()
|
|
return removed_count > 0
|
|
except Exception as e:
|
|
print(f"Error removing appointment: {e}")
|
|
return False
|
|
|
|
def get_upcoming_for_user(user: str, limit: int = 25):
|
|
"""Return upcoming appointment plans for a user ordered by start date."""
|
|
remove_done()
|
|
try:
|
|
client = MongoClient(cfg.MONGODB_HOST, cfg.MONGODB_PORT)
|
|
db = _get_tenant_db(client)
|
|
items = db['appointments']
|
|
|
|
today = datetime.date.today().strftime('%Y-%m-%d')
|
|
cursor = items.find(
|
|
_active_record_query(
|
|
{
|
|
'user': str(user or '').strip(),
|
|
'date_end': {'$gte': today},
|
|
}
|
|
)
|
|
).sort('date_start', 1)
|
|
|
|
results = []
|
|
for item in cursor:
|
|
item['_id'] = str(item.get('_id'))
|
|
results.append(item)
|
|
if len(results) >= max(1, int(limit)):
|
|
break
|
|
|
|
client.close()
|
|
return results
|
|
except Exception as e:
|
|
print(f"Error retrieving upcoming appointments: {e}")
|
|
return []
|
|
|
|
|