hanze/muizenval

server/routes.py in layout
Repositories | Summary | Log | Files

routes.py (7485B) download


  1import json
  2import os
  3import secrets
  4from datetime import datetime, timedelta
  5
  6from flask import flash, redirect, render_template, request, url_for, jsonify
  7from flask_login import current_user, login_required, login_user, logout_user
  8from PIL import Image
  9
 10from .app import app, bcrypt, db, socket
 11from .forms import ConnectTrapForm, LoginForm, RegistrationForm, UpdateAccountForm, UpdateTrapForm
 12from .models import Trap, User, UserType
 13
 14def clean_traps():
 15    query = Trap.query.filter((Trap.connect_expired < datetime.utcnow()) & (Trap.owner == None))
 16    i = len(query.all())
 17    query.delete()
 18    db.session.commit()
 19    print(f'[*] {i} traps cleaned')
 20
 21@app.route("/api/update_status", methods=['POST', 'GET'])
 22def update_status():
 23    if not request.json:
 24        return jsonify({ "error": "invalid-json" })
 25    trap = Trap.query.filter_by(mac=request.json['mac']).first() 
 26    if not trap:
 27        return jsonify({ "error": "not-found" })
 28
 29    trap.caught = request.json['status']
 30    db.session.commit()
 31
 32    if trap.owner:
 33        socket.emit('trap-change', { 'user': trap.owner })
 34
 35    return jsonify({ "error": "ok" })
 36
 37@app.route("/api/search_connect", methods=['POST', 'GET'])
 38def search_connect():
 39    if not request.json:
 40        return jsonify({ "error": "invalid-json" })
 41    
 42    trap = Trap.query.filter_by(mac=request.json['mac']).first()
 43    if not trap:
 44        trap = Trap(mac=request.json['mac'])
 45        db.session.add(trap)
 46
 47    trap.owner = None
 48    trap.connect_expired = datetime.utcnow() + timedelta(minutes=5)
 49
 50    db.session.commit()
 51
 52    return jsonify({ "error": "ok" })
 53
 54
 55""" index.html (home-page) route """
 56@app.route("/")
 57def index():
 58    form = LoginForm()
 59    return render_template('index.html', form=form)
 60
 61""" about.html route """
 62@app.route("/about")
 63def about():
 64    return render_template('about.html', title='Over ons')
 65
 66""" register.html route """
 67@app.route("/register", methods=['GET', 'POST'])
 68def register():
 69    if current_user.is_authenticated:
 70        flash('U bent al ingelogd', 'warning')
 71        return redirect('/')
 72
 73    form = RegistrationForm()
 74    if form.validate_on_submit():
 75        hashed_password = bcrypt.generate_password_hash(form.password.data).decode('utf-8')
 76        address = f"{form.street} {form.housenumber}\n{form.zipcode} {form.place}"
 77        user = User(
 78            name=form.name.data, 
 79            email=form.email.data, 
 80            password=hashed_password,
 81            phone=form.phone.data,
 82            address = address
 83        )
 84        db.session.add(user)
 85        db.session.commit()
 86        flash('Uw profiel werd toegevoegd! U kan nu inloggen.', 'success')
 87        return redirect(url_for('login'))
 88    return render_template('register.html', title='Registeren', form=form)
 89
 90
 91@app.route("/producten")
 92def producten():
 93    return render_template('producten.html')
 94
 95""" login.html route """
 96@app.route("/login", methods=['GET', 'POST'])
 97def login():
 98    if current_user.is_authenticated:
 99        flash('U bent al ingelogd', 'warning')
100        return redirect('/')
101    form = LoginForm()
102    if form.validate_on_submit():
103        user = User.query.filter_by(email=form.email.data).first()
104        if user and bcrypt.check_password_hash(user.password, form.password.data):
105            login_user(user, remember=form.remember.data)
106            if bcrypt.check_password_hash(user.password, form.email.data):
107                flash('Wij zullen aanbevelen uw wachtwoord weer te veranderen', 'warning')
108            next_page = request.args.get('next')
109            return redirect(next_page if next_page else '/')
110        else:
111            flash('Kon niet inloggen, is uw e-mail en wachtwoord juist?', 'danger')
112    return render_template('login.html', title='Inloggen', form=form)
113
114""" logout route """
115@app.route("/logout")
116def logout():
117    logout_user()
118    return redirect('/')
119
120""" save-picture function for account.html """
121def save_picture(form_picture):
122    random_hex = secrets.token_hex(8)
123    _, f_ext = os.path.splitext(form_picture.filename)
124    picture_fn = random_hex + f_ext
125    picturepath = os.path.join(app.root_path, 'static/profile_pics', picture_fn)
126
127    output_size = (125, 125)
128    i = Image.open(form_picture)
129    i.thumbnail(output_size)
130    i.save(picturepath)
131
132    return picture_fn
133
134""" account.html route """
135@app.route("/user/self", methods=[ 'GET', 'POST' ])
136@login_required
137def account():
138    form = UpdateAccountForm()
139    if form.validate_on_submit():
140        current_user.name = form.name.data
141        current_user.email = form.email.data
142        if form.picture.data:
143            picture_file = save_picture(form.picture.data)
144            current_user.image_file = picture_file
145        if form.password.data:
146            current_user.password = bcrypt.generate_password_hash(form.password.data).decode('utf-8')
147        db.session.commit()
148        flash('Uw profiel is bewerkt!', 'success')
149        return redirect(url_for('account'))
150
151    elif request.method == 'GET':
152        form.name.data = current_user.name
153        form.email.data = current_user.email
154    image_file = url_for('static', filename='profile_pics/' + current_user.image_file)
155    return render_template('account.html',  title='Profiel', image_file=image_file, form=form)
156
157
158@app.route('/traps')
159@login_required
160def traps():
161    if current_user.type == UserType.ADMIN:
162        clean_traps()
163        query = Trap.query.all()
164    else:
165        query = Trap.query.filter_by(owner=current_user.id)
166
167    trap_json = [ { c.name: str(getattr(trap, c.name)) for c in trap.__table__.columns } for trap in query ]
168
169    return render_template('trap.html', traps=query, trap_json=trap_json)
170
171@app.route('/traps/connect', methods=['POST', 'GET'])
172@login_required
173def trap_connect():
174    form = ConnectTrapForm()
175    if form.validate_on_submit() and form.mac.data:
176        trap = Trap.query.filter_by(mac=form.mac.data.replace(':', '').replace(' ', '')).filter(Trap.connect_expired > datetime.utcnow()).first()
177        if not trap:
178            flash('Muizenval niet gevonden', 'danger')
179            return redirect(url_for('trap_connect'))
180
181        trap.owner = current_user.id
182        db.session.commit()
183        flash('Muizenval toegevoegd!', 'success')
184        return redirect(url_for('traps'))
185
186    return render_template('connect.html', form=form)
187
188
189@app.route('/trap/<trap_id>/update', methods=['POST', 'GET'])
190@login_required
191def trap_update(trap_id):
192    form = UpdateTrapForm()
193    trap = Trap.query.filter_by(mac=trap_id).first()
194    if form.validate_on_submit():
195        trap.name = form.name.data
196        if form.email.data:
197            user = User.query.filter_by(email=form.email.data).first()
198            trap.owner = user.id
199        db.session.commit()
200        return redirect(url_for('traps'))
201    elif not trap:
202        flash('Muizeval niet gevonden', 'danger')
203        return redirect(url_for('traps'))
204    elif request.method == 'GET':
205        form.mac.data = trap.mac
206        form.name.data = trap.name
207    return render_template('updatetrap.html', form=form, trap=trap)
208
209@app.route('/trap/<trap_id>/delete')
210@login_required
211def trap_delete(trap_id):
212    trap = Trap.query.filter_by(mac=trap_id).first()
213    db.session.delete(trap)
214    db.session.commit()
215    
216    return redirect(url_for('traps'))
217
218""" 404 not found handler """
219@app.errorhandler(404)
220def not_found(error):
221    flash(f"Deze pagina werd niet gevonden", 'danger')
222    return index() # geen redirect om de '/bla' te houden