Créations des fichiers pour le déploiement de l'application sur le Web avec Flask :

- Page de sélection du département
- Page des salles libres
Corrections diverses.
This commit is contained in:
Antoine Waehren 2022-05-10 20:55:19 +02:00
parent f66c516773
commit 1c9b10a54e
6 changed files with 352 additions and 62 deletions

91
app.py Normal file
View File

@ -0,0 +1,91 @@
################
### UniSquat ###
################
"""
Indique toutes les salles disponibles dans les différents départements de
l'Université de Strasbourg.
"""
from flask import Flask
from flask import render_template
from flask import url_for
from flask import request
import rooms_get as ro
import datetime as dti
app = Flask(__name__)
# Modules :
import datetime
import time
# Fichiers locaux :
import date_tools
import rooms_get as ro
# import definitions as lib # TODO : À quoi ça sert ?
@app.route("/")
def select_dept() :
"""
Permet de sélectionner un ou plusieurs départements dans lesquels
chercher des salles libres.
Parameters
----------
None.
Returns
-------
flask.render_template
"""
dept_filen = "data/dept_list.txt"
dept_list = ro.get_depts(dept_filen)
content = {"dept_list":dept_list}
url_for("static", filename="style.css")
return render_template("dept-select.html", **content)
@app.route("/free-rooms", methods=["POST", "GET"])
def free_rooms() :
"""
Affiche les salles libres dans les départements sélectionnés
dans la page précédente.
Parameters
----------
None.
Returns
-------
flask.render_template
"""
depts = request.form["dept"]
print(depts)
#hdelay = 1 #TODO : décalage horaire (pb de fuseau ?)
#if time.localtime().tm_isdst != 0 :
#hdelay = 2
#ignore_list = ["salle non définie", "salle en Distanciel"]
##dept = dept_list[0] #TODO : proposer d'autres départements
#date = dti.datetime(2022, 5, 5, 10, 30)
#available_rooms = ro.getrooms(date, depts, ignore_list)
#context = {"available_rooms":available_rooms, "hdelay":hdelay}
context = {}
url_for("static", filename="style.css")
return render_template("free-rooms.html", **context)

View File

@ -18,13 +18,15 @@ Created on Thu Feb 24 17:14:05 2022
# Modules :
import datetime
import time
# Fichiers locaux :
import date_tools
import rooms_get as ro
# import definitions as lib # TODO : À quoi ça sert ?
# Globales
favorites = ["C" + str(i) + " MATH" for i in range(1,12)] + ["C42-CMI"] # TODO : Ne sera pas conservé
#favorites = ["C" + str(i) + " MATH" for i in range(1,12)] + ["C42-CMI"] # TODO : Ne sera pas conservé
favorites = []
links = [] # Liens vers les calendriers des salles des différents bâtiments de l'université
@ -43,6 +45,11 @@ def main() :
print("~~~ UniSquat ~~~\n")
hdelay = 1 #TODO : décalage horaire (pb de fuseau ?)
if time.localtime().tm_isdst != 0 :
hdelay = 2
ignore_list = ["salle non définie", "salle en Distanciel"]
dept_filen = "data/dept_list.txt"
@ -97,7 +104,7 @@ def main() :
if room.end.hour == 23 and room.end.minute == 59 and room.end.second == 59 :
print(" - " + room.name)
else :
print(" - " + room.name + " | Occupée à : " + str(room.end.hour + 1) + ":" + str(room.end.minute) + " (dans " + remain_time_str + ")") # TODO : Obligé d'ajouter 1h (problème de fuseau horaire ?)
print(" - " + room.name + " | Occupée à : " + str(room.end.hour + hdelay) + ":" + str(room.end.minute) + " (dans " + remain_time_str + ")") # TODO : Obligé d'ajouter 1h (problème de fuseau horaire ?)
# Salles libres prochainement :
print("\nLes salles suivantes seront disponibles prochainement : \n")
@ -114,9 +121,9 @@ def main() :
# print(" - " + room["name"]+" | libre dans : "+str(int(deltasec/60+0.5))+" minutes")
if room.end.hour == 23 and room.end.minute == 59 and room.end.second == 59 :
print(" - " + room.name + " | Libre à " + str(room.start.hour + 1) + ":" + str(room.start.minute) + " (dans " + remain_time_str + ")") # TODO : Obligé d'ajouter 1h (problème de fuseau horaire ?)
print(" - " + room.name + " | Libre à " + str(room.start.hour + hdelay) + ":" + str(room.start.minute) + " (dans " + remain_time_str + ")") # TODO : Obligé d'ajouter 1h (problème de fuseau horaire ?)
else :
print(" - " + room.name + " | Libre de " + str(room.start.hour + 1) + ":" + str(room.start.minute) + " à " + str(room.end.hour + 1) + ":" + str(room.end.minute) + " (dans " + remain_time_str + ")") # TODO : Obligé d'ajouter 1h (problème de fuseau horaire ?)
print(" - " + room.name + " | Libre de " + str(room.start.hour + hdelay) + ":" + str(room.start.minute) + " à " + str(room.end.hour + hdelay) + ":" + str(room.end.minute) + " (dans " + remain_time_str + ")") # TODO : Obligé d'ajouter 1h (problème de fuseau horaire ?)
if __name__=="__main__":
main()

View File

@ -165,17 +165,17 @@ def get_depts(filename) :
return dept_list
def get_tot_rooms(datet, dept, ignore_list) :
def get_tot_rooms(datet, depts, ignore_list) :
"""
Crée une liste de toutes les salles du département choisi.
Crée une liste de toutes les salles des départements choisis.
Parameters
----------
datet : datetime.datetime()
Date pour la recherche de salles.
dept : Dept
Bâtiment dans lequel chercher des salles.
dept : list
Liste des départements dans lesquel chercher des salles.
ignore_list : list
Liste des noms de salles à ignorer.
@ -198,28 +198,31 @@ def get_tot_rooms(datet, dept, ignore_list) :
else :
cal_start.replace(month = cal_start.month - margintime)
# Récupération des calendriers correspondants au lien du département, sur une période de 'margintime' mois :
result = sched_get(datet, dept.link, datet.replace(month = datet.month + margintime))
cal = icalendar.Calendar.from_ical(result)
# Récupération des calendriers correspondants aux liens des départements, sur une période de 'margintime' mois :
cals = list() # Liste des emplois du temps des départements choisis
for d in depts :
result = sched_get(datet, d.link, datet.replace(month = datet.month + margintime))
cals.append(icalendar.Calendar.from_ical(result))
rnamelist = [] # Contient le nom de toutes les salles indiquées dans la section "LOCATION"
# Parcours de ces calendriers, pour faire la liste de toutes les salles :
for comp in cal.walk() : # Événements
if comp.name == "VEVENT" :
# Ajout de la salle dans le dictionnaire, si elle n'y est pas :
roomname = str(comp.get("location"))
if roomname not in rnamelist :
rnamelist.append(roomname)
start = datet.replace(hour = 0, minute = 0, second=0) # Par défaut, l'heure de début de disponibilité est aujourd'hui à 00:00
end = datet.replace(hour = 23, minute = 59, second = 59) # Par défaut, l'heure de fin de la prochaine période disponibilité est aujourd'hui à 23:59
is_free = True # Par défaut, la salle est libre
total_rooms.append(Room(roomname, start, end, is_free))
for cal in cals :
for comp in cal.walk() : # Événements
if comp.name == "VEVENT" :
# Ajout de la salle dans le dictionnaire, si elle n'y est pas :
roomname = str(comp.get("location"))
if roomname not in rnamelist :
rnamelist.append(roomname)
start = datet.replace(hour = 0, minute = 0, second=0) # Par défaut, l'heure de début de disponibilité est aujourd'hui à 00:00
end = datet.replace(hour = 23, minute = 59, second = 59) # Par défaut, l'heure de fin de la prochaine période disponibilité est aujourd'hui à 23:59
is_free = True # Par défaut, la salle est libre
total_rooms.append(Room(roomname, start, end, is_free))
return total_rooms
def getrooms(datet, dept, ignore_list) :
def getrooms(datet, depts, ignore_list) :
"""
Ajout des informations supplémentaires à la liste des salles
(heures de début-fin de dispo, indicateur de dispo).
@ -229,8 +232,8 @@ def getrooms(datet, dept, ignore_list) :
datet : datetime.datetime()
Date pour la recherche de salles.
dept : Dept
Bâtiment dans lequel chercher des salles.
dept : list
Liste des départements dans lesquel chercher des salles.
ignore_list : list
Liste des noms de salles à ignorer.
@ -242,50 +245,55 @@ def getrooms(datet, dept, ignore_list) :
"""
# Création de la liste de toutes les salles :
total_rooms = get_tot_rooms(datet, dept, ignore_list)
total_rooms = get_tot_rooms(datet, depts, ignore_list)
# Récupération des calendriers correspondants au lien du département :
result = sched_get(datet, dept.link)
cal = icalendar.Calendar.from_ical(result)
cals = list() # Liste des emplois du temps des départements choisis
for d in depts :
result = sched_get(datet, d.link, datet.replace(month = datet.month + margintime))
cals.append(icalendar.Calendar.from_ical(result))
# Ajout des infos supplémentaires sur les salles (heures de début-fin de dispo, indicateur de dispo), s'il y en a :
# Première boucle, pour déterminer les salles occupées :
for comp in cal.walk() : # Événements
if comp.name == "VEVENT" :
# Récupération des infos :
datestart = comp.decoded("dtstart")
dateend = comp.decoded("dtend")
roomname = str(comp.get("location"))
for cal in cals :
# Première boucle, pour déterminer les salles occupées :
for comp in cal.walk() : # Événements
if comp.name == "VEVENT" :
# Récupération des infos :
datestart = comp.decoded("dtstart")
dateend = comp.decoded("dtend")
roomname = str(comp.get("location"))
# L'événement se passe maintenant (salle occupée maintenant) :
if datestart.timestamp() <= datet.timestamp() and dateend.timestamp() > datet.timestamp() :
start = dateend # L'heure de début de la prochaine période de disponibilité est la fin de l'événement
end = datet.replace(hour = 23, minute = 59, second = 59) # Par défaut, l'heure de fin de la prochaine période disponibilité est aujourd'hui à 23:59
is_free = False
for r in total_rooms :
if r.name == roomname :
r = Room(roomname, start, end, is_free)
# L'événement se passe maintenant (salle occupée maintenant) :
if datestart.timestamp() <= datet.timestamp() and dateend.timestamp() > datet.timestamp() :
start = dateend # L'heure de début de la prochaine période de disponibilité est la fin de l'événement
end = datet.replace(hour = 23, minute = 59, second = 59) # Par défaut, l'heure de fin de la prochaine période disponibilité est aujourd'hui à 23:59
is_free = False
for r in total_rooms :
if r.name == roomname :
r.start = start
r.end = end
r.is_free = is_free
# Deuxième boucle, pour ajouter les heures de dispos des salles :
for comp in cal.walk() : # Événements
if comp.name == "VEVENT" :
# Récupération des infos :
datestart = comp.decoded("dtstart")
dateend = comp.decoded("dtend")
roomname = str(comp.get("location"))
# Deuxième boucle, pour ajouter les heures de dispos des salles :
for comp in cal.walk() : # Événements
if comp.name == "VEVENT" :
# Récupération des infos :
datestart = comp.decoded("dtstart")
dateend = comp.decoded("dtend")
roomname = str(comp.get("location"))
# L'événement se passe prochainement (salle occupée à l'occasion de cet événement) :
if datestart.timestamp() > datet.timestamp() :
for r in total_rooms :
if r.name == roomname :
if datestart.timestamp() < r.end.timestamp() :
if datestart.timestamp() == r.start.timestamp() :
start = dateend
end = r.end
else :
start = r.end
end = datestart
is_free = r.is_free
r = Room(roomname, start, end, is_free)
# L'événement se passe prochainement (salle occupée à l'occasion de cet événement) :
if datestart.timestamp() > datet.timestamp() :
for r in total_rooms :
if r.name == roomname :
if datestart.timestamp() < r.end.timestamp() :
if datestart.timestamp() == r.start.timestamp() :
start = dateend
end = r.end
else :
start = r.end
end = datestart
r.start = start
r.end = end
return total_rooms

117
static/style.css Normal file
View File

@ -0,0 +1,117 @@
:root {
--bg: #191919;
--bg-dark: #252525;
--bg-light: #4b4b4b;
--fg: #ffffff;
--hl: #8080ff;
}
* {
background: var(--bg);
padding-left: 5px;
padding-right: 5px;
font-family: "ubuntu", "sans";
color: var(--fg);
}
header {
background: var(--hl);
font-size: 250%;
font-weight: lighter;
text-align: center;
margin: 10px;
margin-left: calc(-50vw + 50%);
margin-right: calc(-50vw + 50%);
margin-top: calc(-50vw + 50%);
padding-top: 20px;
padding-bottom: 5px;
}
main {
/*display: flex;
flex-direction: row;*/
line-height: 1.7;
}
nav {
vertical-align: top;
margin: 10px;
width: 50%;
}
#body {
margin: 10px;
}
p {
text-align: justify;
text-indent: 50px;
}
.flex-container {
width: 100%;
display: flex;
flex-direction: column;
}
h1, h2, h3, h4 {
font-weight: lighter;
border-left: solid;
border-width: 5px;
border-color: var(--hl);
}
a {
color: var(--hl);
}
img {
margin: 10px;
align-self: flex-start;
max-width: 200px;
border-radius: 10px;
}
iframe {
max-width: 200px;
max-height: 500px;
}
ul {
margin-bottom: 5px;
}
dt {
font-weight: bold;
font-size: 90%;
border-bottom-style: solid;
border-bottom-width: 2px;
border-bottom-color: var(--bg-light);
padding: 10px;
}
dt .details {
font-weight: normal;
font-size: 80%;
}
button, input {
background: var(--bg-light);
border-style: solid;
border-width: 1px;
border-color: var(--bg);
padding: 10px;
border-radius: 10px;
}
.done {
background: var(--bg-dark);
text-decoration: line-through;
}
input {
background: var(--bg-dark);
}
@media screen and (max-width: 769px) {
}

View File

@ -0,0 +1,22 @@
<!DOCTYPE html>
<html lang="">
<head>
<meta charset="utf-8">
<title>UniSquat</title>
<link rel="stylesheet" type="text/css" href="../static/style.css">
</head>
<body>
<header>UniSquat</header>
<main>
Sélectionnez des départements dans la liste :
<form action="/free-rooms" method="post">
<input type="submit" value="Valider">
<br>
{% for d in dept_list : %}
<input type="radio" id="{{ d }}" name="dept" value="{{ d }}"><br>
{% endfor %}
</form>
</main>
<footer></footer>
</body>
</html>

45
templates/free-rooms.html Normal file
View File

@ -0,0 +1,45 @@
<!DOCTYPE html>
<html lang="">
<head>
<meta charset="utf-8">
<title>UniSquat</title>
<link rel="stylesheet" type="text/css" href="../static/style.css">
</head>
<body>
<header>UniSquat</header>
<main>
Les salles suivantes sont disponibles actuellement :
<div class="flex-container">
<ul>
{% for room in available_rooms : %}
{% if room.is_free : %}
<dt>{{ room.name }}
{% if not(room.end.hour == 23 and room.end.minute == 59 and room.end.second == 59) : %}
<br><span class=details>Occupée à : {{ room.end.hour + hdelay }}:{{ room.end.minute }}</span>
{% endif %}
</dt>
{% endif %}
{% endfor %}
</ul>
</div>
<br>
Les salles suivantes seront disponibles prochainement :
<div class="flex-container">
<ul>
{% for room in available_rooms : %}
{% if not room.is_free : %}
<dt>{{ room.name }}
{% if room.end.hour == 23 and room.end.minute == 59 and room.end.second == 59 : %}
<br><span class=details>Libre à : {{ room.start.hour + hdelay }}:{{ room.start.minute + hdelay }}</span>
{% else %}
<br><span class=details>Libre de {{ room.start.hour + hdelay }}:{{ room.start.minute + hdelay }} à {{ room.end.hour + hdelay }}:{{ room.end.minute + hdelay }}</span>
{% endif %}
</dt>
{% endif %}
{% endfor %}
</ul>
</div>
</main>
<footer></footer>
</body>
</html>