Commit 4b6cfadb authored by Nicolas Joyard's avatar Nicolas Joyard

Ajout gestion des abonnements aux alertes

parent 7972dc1d
......@@ -3,6 +3,14 @@
from .database import db
abonnements = db.Table(
'abonnements',
db.Column('user_id', db.Integer, db.ForeignKey('users.id')),
db.Column('parlementaire_id', db.Integer,
db.ForeignKey('parlementaires.id'))
)
class User(db.Model):
__tablename__ = 'users'
......@@ -18,3 +26,7 @@ class User(db.Model):
actions = db.relationship('Action', back_populates='user',
order_by='Action.date')
abonnements = db.relationship('Parlementaire',
secondary=abonnements,
backref='abonnes')
......@@ -69,8 +69,26 @@ def setup_routes(app):
if not parl:
return not_found()
abonne = False
abonne_dept = False
if session.get('user'):
user = User.query.filter(User.id == session['user']['id']) \
.options(joinedload(User.abonnements)) \
.first()
abonne = parl in user.abonnements
dept = Parlementaire.query.join(Parlementaire.etape) \
.filter(Parlementaire.num_deptmt ==
parl.num_deptmt) \
.filter(Etape.ordre > 0) \
.all()
abonne_dept = all([p in user.abonnements for p in dept])
data = {
'parlementaire': parl,
'abonne': abonne,
'abonne_dept': abonne_dept,
'pris_en_charge': bool(pris_en_charge(parl))
}
......
......@@ -2,10 +2,12 @@
from flask import flash, render_template, request, session
from ..models import Action, Etape, User, db
from sqlalchemy.orm import joinedload
from ..models import Action, Etape, Parlementaire, User, db
from ..models.constants import ETAPE_ENVOYE
from ..tools.routing import not_found, redirect_back, require_user
from ..tools.routing import not_found, redirect_back, require_user, url_for
from ..tools.text import check_email, check_password, sanitize_hard
......@@ -92,7 +94,9 @@ def setup_routes(app):
@app.route('/profil', endpoint='profil', methods=['GET', 'POST'])
@require_user
def profil():
user = User.query.filter(User.id == session['user']['id']).first()
user = User.query.filter(User.id == session['user']['id']) \
.options(joinedload(User.abonnements)) \
.first()
if not user:
return not_found()
......@@ -117,3 +121,53 @@ def setup_routes(app):
return redirect_back()
return render_template('profil.html.j2', user=user, envois=envois)
@app.route('/abonnement/parlementaire/<id>/<action>',
endpoint='abo_parlementaire')
@require_user
def abo_parlementaire(id, action):
user = User.query.filter(User.id == session['user']['id']).first()
parl = Parlementaire.query.filter(Parlementaire.id == id).first()
if not user or not parl:
return not_found()
if action == 'on':
user.abonnements.append(parl)
else:
user.abonnements.remove(parl)
db.session.commit()
return redirect_back(fallback=url_for('parlementaire', id=id))
@app.route('/abonnement/departement/<deptmt>/<action>',
endpoint='abo_departement')
@require_user
def abo_departement(deptmt, action):
user = User.query.filter(User.id == session['user']['id']).first()
parl = Parlementaire.query.join(Parlementaire.etape) \
.filter(Parlementaire.num_deptmt == deptmt) \
.filter(Etape.ordre > 0) \
.all()
if not user:
return not_found()
if action == 'on':
[user.abonnements.append(p) for p in parl]
else:
[user.abonnements.remove(p) for p in parl]
db.session.commit()
return redirect_back(fallback=url_for('parlementaire', id=id))
@app.route('/abonnement/clear', endpoint='abo_clear')
@require_user
def abo_clear():
user = User.query.filter(User.id == session['user']['id']).first()
user.abonnements.clear()
db.session.commit()
return redirect_back()
......@@ -61,8 +61,8 @@
<li>
<form class="form-horizontal login-form" method="POST" action="{{ url_for('login') }}">
<input name="nick" type="text" class="form-control" placeholder="Pseudo">
<input name="email" type="text" class="form-control" placeholder="Adresse e-mail (facultatif)">
<br>
<input name="email" type="text" class="form-control" placeholder="Adresse e-mail">
<small>Votre adresse e-mail ne sera pas publiée.</small><br><br>
<input type="submit" class="btn btn-primary" value="Valider">
</form>
</li>
......
......@@ -34,6 +34,61 @@
</article>
</section>
<!-- Abonnements -->
<section class="panel panel-default">
<header class="panel-heading">
<b>Alertes</b>
</header>
<article class="panel-body">
Vous pouvez recevoir une alerte par e-mail lorsque la situation change pour ce parlementaire ou pour tout parlementaire de ce département.
{% if not session.user %}
<br><br>
Pour cela, vous devez d'abord <a href="#" class="identify-link">vous identifier</a>.
{% endif %}
</article>
{% if session.user %}
<table class="table table-responsive">
<tr>
<td class="col-right">{{ parlementaire.nom_complet }}</td>
<td class="col-center">
{% if abonne %}
<a class="btn btn-sm btn-danger" href="{{ url_for('abo_parlementaire', id=parlementaire.id, action='off') }}">
<i class="fa fa-bell"></i>
Ne plus m'alerter
</a>
{% else %}
<a class="btn btn-sm btn-primary" href="{{ url_for('abo_parlementaire', id=parlementaire.id, action='on') }}">
<i class="fa fa-bell"></i>
M'alerter
</a>
{% endif %}
</td>
</tr>
<tr>
<td class="col-right">{{ parlementaire.nom_circo }}</td>
<td class="col-center">
{% if abonne_dept %}
<a class="btn btn-sm btn-danger" href="{{ url_for('abo_departement', deptmt=parlementaire.num_deptmt, action='off') }}">
<i class="fa fa-bell"></i>
Ne plus m'alerter
</a>
{% else %}
<a class="btn btn-sm btn-primary" href="{{ url_for('abo_departement', deptmt=parlementaire.num_deptmt, action='on') }}">
<i class="fa fa-bell"></i>
M'alerter
</a>
{% endif %}
</td>
</tr>
</table>
{% endif %}
</section>
</div>
<div class="col-md-9">
......@@ -146,7 +201,7 @@
{% else %}
<div class="alert alert-warning">
Pour nous permettre d'assurer le suivi de l'envoi des courriers aux parlementaires, vous devez <a href="#" id="identify-link">vous identifier</a> pour pouvoir le prendre en charge.
Pour nous permettre d'assurer le suivi de l'envoi des courriers aux parlementaires, vous devez <a href="#" class="identify-link">vous identifier</a> pour pouvoir le prendre en charge.
</div>
{% endif %}
......@@ -383,7 +438,7 @@
{% block scripts %}
<script src="{{ url_for('static', filename='bootstrap.file-input.js') }}"></script>
<script>
$('#identify-link').click(function(e) {
$('.identify-link').click(function(e) {
$('.login .dropdown-toggle').dropdown('toggle');
$('.login [name="nick"]').focus();
return false;
......
......@@ -38,5 +38,54 @@
</form>
</article>
</section>
{% if user.abonnements %}
<section class="panel panel-default">
<header class="panel-heading">
<b>Mes alertes</b>
</header>
<table class="table table-condensed table-striped">
<tr>
<th colspan="2" data-defaultsort="asc" data-mainsort="1">Parlementaire</th>
<th class="col-center">Groupe</th>
<th>Circonscription</th>
<th class="col-center">Etape</th>
<th class="col-right">
<a class="btn btn-sm btn-danger" href="{{ url_for('abo_clear') }}">
<i class="fa fa-trash"></i>
Tout supprimer
</a>
</th>
</tr>
{% for parl in user.abonnements %}
<tr>
<td class="col-center">
<a data-toggle="tooltip" title="Accéder à la page du parlementaire ({{ chambres[parl.chambre] }})" target="_blank" href="{{ parl.url_off }}">
<img class="chamber-icon" src="{{ url_for('static', filename=parl.chambre|lower+'.png') }}">
</a>
</td>
<td>
<a href="{{ url_for('parlementaire', id=parl.id) }}">{{ parl.nom_complet }}</a>
{% if not parl.adresse %}
<span class="label label-danger">Adresse manquante !</span>
{% endif %}
</td>
<td class="col-center">{{ parl.groupe|label_groupe }}</td>
<td>{{ parl.nom_circo }} n°{{ parl.num_circo }}</td>
<td class="col-center">
{{ parl.etape|label_etape }}
</td>
<td class="col-right">
<a class="btn btn-sm btn-danger" href="{{ url_for('abo_parlementaire', id=parl.id, action='off') }}">
<i class="fa fa-bell"></i>
Ne plus m'alerter
</a>
</td>
</tr>
{% endfor %}
</table>
</section>
{% endif %}
</div>
{% endblock %}
......@@ -50,15 +50,11 @@ def upgrade():
WHERE a.nick != '';
""")
# op.drop_column('actions', 'email')
# op.drop_column('actions', 'nick')
# ### end Alembic commands ###
def downgrade():
# ### commands auto generated by Alembic - please adjust! ###
op.add_column('actions', sa.Column('nick', sa.VARCHAR(), autoincrement=False, nullable=True))
op.add_column('actions', sa.Column('email', sa.VARCHAR(), autoincrement=False, nullable=True))
op.drop_constraint(None, 'actions', type_='foreignkey')
op.drop_column('actions', 'user_id')
op.drop_table('users')
......
"""Ajout abonnements
Revision ID: 56431e581030
Revises: 0f6485160e01
Create Date: 2017-05-20 19:37:03.948322
"""
from alembic import op
import sqlalchemy as sa
# revision identifiers, used by Alembic.
revision = '56431e581030'
down_revision = '0f6485160e01'
branch_labels = None
depends_on = None
def upgrade():
# ### commands auto generated by Alembic - please adjust! ###
op.create_table('abonnements',
sa.Column('user_id', sa.Integer(), nullable=True),
sa.Column('parlementaire_id', sa.Integer(), nullable=True),
sa.ForeignKeyConstraint(['parlementaire_id'], ['parlementaires.id'], ),
sa.ForeignKeyConstraint(['user_id'], ['users.id'], )
)
op.drop_column('actions', 'email')
op.drop_column('actions', 'nick')
# ### end Alembic commands ###
def downgrade():
# ### commands auto generated by Alembic - please adjust! ###
op.add_column('actions', sa.Column('nick', sa.VARCHAR(), autoincrement=False, nullable=True))
op.add_column('actions', sa.Column('email', sa.VARCHAR(), autoincrement=False, nullable=True))
op.drop_table('abonnements')
# ### end Alembic commands ###
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment