Merge branch 'master' into 'fix-what-i-broke'

# Conflicts:
#   templates/base.html
This commit is contained in:
ynerant 2020-03-11 17:03:44 +01:00
commit 46e472ed6d
8 changed files with 141 additions and 103 deletions

3
.gitmodules vendored Normal file
View File

@ -0,0 +1,3 @@
[submodule "apps/scripts"]
path = apps/scripts
url = git@gitlab.crans.org:bde/nk20-scripts.git

View File

@ -46,6 +46,7 @@ class Profile(models.Model):
class Meta: class Meta:
verbose_name = _('user profile') verbose_name = _('user profile')
verbose_name_plural = _('user profile') verbose_name_plural = _('user profile')
indexes = [ models.Index(fields=['user']) ]
def get_absolute_url(self): def get_absolute_url(self):
return reverse('user_detail', args=(self.pk,)) return reverse('user_detail', args=(self.pk,))
@ -152,6 +153,7 @@ class Membership(models.Model):
class Meta: class Meta:
verbose_name = _('membership') verbose_name = _('membership')
verbose_name_plural = _('memberships') verbose_name_plural = _('memberships')
indexes = [ models.Index(fields=['user']) ]
# @receiver(post_save, sender=settings.AUTH_USER_MODEL) # @receiver(post_save, sender=settings.AUTH_USER_MODEL)
# def save_user_profile(instance, created, **_kwargs): # def save_user_profile(instance, created, **_kwargs):

View File

@ -6,7 +6,7 @@ from django import forms
from django.utils.translation import gettext_lazy as _ from django.utils.translation import gettext_lazy as _
from .models import Alias from .models import Alias
from .models import Transaction, TransactionTemplate, TemplateTransaction from .models import Transaction, TransactionTemplate
class AliasForm(forms.ModelForm): class AliasForm(forms.ModelForm):
@ -99,33 +99,3 @@ class TransactionForm(forms.ModelForm):
}, },
), ),
} }
class ConsoForm(forms.ModelForm):
def save(self, commit=True):
button: TransactionTemplate = TransactionTemplate.objects.filter(
name=self.data['button']).get()
self.instance.destination = button.destination
self.instance.amount = button.amount
self.instance.reason = '{} ({})'.format(button.name, button.category)
self.instance.template = button
self.instance.category = button.category
super().save(commit)
class Meta:
model = TemplateTransaction
fields = ('source',)
# Le champ d'utilisateur est remplacé par un champ d'auto-complétion.
# Quand des lettres sont tapées, une requête est envoyée sur l'API d'auto-complétion
# et récupère les aliases de note valides
widgets = {
'source':
autocomplete.ModelSelect2(
url='note:note_autocomplete',
attrs={
'data-placeholder': 'Note ...',
'data-minimum-input-length': 1,
},
),
}

View File

@ -209,6 +209,10 @@ class Alias(models.Model):
class Meta: class Meta:
verbose_name = _("alias") verbose_name = _("alias")
verbose_name_plural = _("aliases") verbose_name_plural = _("aliases")
indexes = [
models.Index(fields=['name']),
models.Index(fields=['normalized_name']),
]
def __str__(self): def __str__(self):
return self.name return self.name

View File

@ -119,6 +119,11 @@ class Transaction(PolymorphicModel):
class Meta: class Meta:
verbose_name = _("transaction") verbose_name = _("transaction")
verbose_name_plural = _("transactions") verbose_name_plural = _("transactions")
indexes = [
models.Index(fields=['created_at']),
models.Index(fields=['source']),
models.Index(fields=['destination']),
]
def save(self, *args, **kwargs): def save(self, *args, **kwargs):
""" """

View File

@ -7,9 +7,11 @@ from django.db.models import Q
from django.urls import reverse from django.urls import reverse
from django.utils.translation import gettext_lazy as _ from django.utils.translation import gettext_lazy as _
from django.views.generic import CreateView, ListView, UpdateView from django.views.generic import CreateView, ListView, UpdateView
from django_tables2 import SingleTableView
from .forms import TransactionForm, TransactionTemplateForm, ConsoForm from .forms import TransactionForm, TransactionTemplateForm
from .models import Transaction, TransactionTemplate, Alias, TemplateTransaction from .models import Transaction, TransactionTemplate, Alias
from .tables import HistoryTable
class TransactionCreate(LoginRequiredMixin, CreateView): class TransactionCreate(LoginRequiredMixin, CreateView):
@ -121,13 +123,16 @@ class TransactionTemplateUpdateView(LoginRequiredMixin, UpdateView):
form_class = TransactionTemplateForm form_class = TransactionTemplateForm
class ConsoView(LoginRequiredMixin, CreateView): class ConsoView(LoginRequiredMixin, SingleTableView):
""" """
Consume Consume
""" """
model = TemplateTransaction model = Transaction
template_name = "note/conso_form.html" template_name = "note/conso_form.html"
form_class = ConsoForm
# Transaction history table
table_class = HistoryTable
table_pagination = {"per_page": 10}
def get_context_data(self, **kwargs): def get_context_data(self, **kwargs):
""" """
@ -142,9 +147,3 @@ class ConsoView(LoginRequiredMixin, CreateView):
context['no_cache'] = True context['no_cache'] = True
return context return context
def get_success_url(self):
"""
When clicking a button, reload the same page
"""
return reverse('note:consos')

1
apps/scripts Submodule

@ -0,0 +1 @@
Subproject commit 123466cfa914422422cd372197e64adf65ef05f7

View File

@ -1,80 +1,134 @@
{% extends "base.html" %} {% extends "base.html" %}
{% load i18n static pretty_money %} {% load i18n static pretty_money django_tables2 %}
{# Remove page title #} {# Remove page title #}
{% block contenttitle %}{% endblock %} {% block contenttitle %}{% endblock %}
{% block content %} {% block content %}
{# Regroup buttons under categories #} <div class="row mt-4">
{% regroup transaction_templates by category as categories %} <div class="col-sm-5 col-md-4">
<div class="row">
<form method="post" onsubmit="window.onbeforeunload=null"> {# User details column #}
{% csrf_token %} <div class="col-xl-5">
<div class="card border-success shadow mb-4">
<div class="row"> <img src="https://perso.crans.org/erdnaxe/site-crans/img/logo.svg"
<div class="col-sm-5 mb-4"> alt="" class="img-fluid rounded mx-auto d-block">
{% if form.non_field_errors %} <div class="card-body text-center">
<p class="errornote"> Paquito (aka. PAC) : -230 €
{% for error in form.non_field_errors %}
{{ error }}
{% endfor %}
</p>
{% endif %}
{% for field in form %}
<div class="form-row{% if field.errors %} errors{% endif %}">
{{ field.errors }}
<div>
{{ field.label_tag }}
{% if field.is_readonly %}
<div class="readonly">{{ field.contents }}</div>
{% else %}
{{ field }}
{% endif %}
{% if field.field.help_text %}
<div class="help">{{ field.field.help_text|safe }}</div>
{% endif %}
</div> </div>
</div> </div>
{% endfor %} </div>
</div>
<div class="col-sm-7"> {# User selection column #}
<div class="card text-center shadow"> <div class="col-xl-7">
{# Tabs for button categories #} <div class="card border-success shadow mb-4">
<div class="card-header"> <div class="card-header">
<ul class="nav nav-tabs nav-fill card-header-tabs"> <p class="card-text font-weight-bold">
{% for category in categories %} Sélection des émitteurs
<li class="nav-item"> </p>
<a class="nav-link" data-toggle="tab" href="#{{ category.grouper|slugify }}"> </div>
{{ category.grouper }} <ul class="list-group list-group-flush">
</a> <li class="list-group-item py-1 d-flex justify-content-between align-items-center">
</li> Cras justo odio
{% endfor %} <span class="badge badge-dark badge-pill">14</span>
</li>
<li class="list-group-item py-1 d-flex justify-content-between align-items-center">
Dapibus ac facilisis in
<span class="badge badge-dark badge-pill">1</span>
</li>
</ul> </ul>
</div> <div class="card-body">
TODO: reimplement select2 here in JS
{# Tabs content #}
<div class="card-body">
<div class="tab-content">
{% for category in categories %}
<div class="tab-pane" id="{{ category.grouper|slugify }}">
<div class="d-inline-flex flex-wrap justify-content-center">
{% for button in category.list %}
<button class="btn btn-outline-dark rounded-0 flex-fill"
name="button" value="{{ button.name }}">
{{ button.name }} ({{ button.amount | pretty_money }})
</button>
{% endfor %}
</div>
</div>
{% endfor %}
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</form>
{# Buttons column #}
<div class="col-sm-7 col-md-8">
{# Show last used buttons #}
<div class="card shadow mb-4">
<div class="card-body text-nowrap" style="overflow:auto hidden">
<p class="card-text text-muted font-weight-light font-italic">
Les boutons les plus utilisés s'afficheront ici.
</p>
</div>
</div>
{# Regroup buttons under categories #}
{% regroup transaction_templates by template_type as template_types %}
<div class="card border-primary text-center shadow mb-4">
{# Tabs for button categories #}
<div class="card-header">
<ul class="nav nav-tabs nav-fill card-header-tabs">
{% for template_type in template_types %}
<li class="nav-item">
<a class="nav-link font-weight-bold" data-toggle="tab" href="#{{ template_type.grouper|slugify }}">
{{ template_type.grouper }}
</a>
</li>
{% endfor %}
</ul>
</div>
{# Tabs content #}
<div class="card-body">
<div class="tab-content">
{% for template_type in template_types %}
<div class="tab-pane" id="{{ template_type.grouper|slugify }}">
<div class="d-inline-flex flex-wrap justify-content-center">
{% for button in template_type.list %}
<button class="btn btn-outline-dark rounded-0 flex-fill"
name="button" value="{{ button.name }}">
{{ button.name }} ({{ button.amount | pretty_money }})
</button>
{% endfor %}
</div>
</div>
{% endfor %}
</div>
</div>
{# Mode switch #}
<div class="card-footer border-primary">
<a class="btn btn-sm btn-secondary float-left" href="{% url 'note:template_list' %}">
<i class="fa fa-edit"></i> Éditer
</a>
<div class="btn-group btn-group-toggle float-right" data-toggle="buttons">
<label class="btn btn-sm btn-outline-primary active">
<input type="radio" name="options" id="option1" checked>
Consomations simples
</label>
<label class="btn btn-sm btn-outline-primary">
<input type="radio" name="options" id="option2">
Consomations doubles
</label>
</div>
</div>
</div>
</div>
</div>
<div class="card shadow mb-4">
<div class="card-header">
<p class="card-text font-weight-bold">
Historique des transactions récentes
</p>
</div>
{% render_table table %}
</div>
{% endblock %}
{% block extracss %}
<style>
.select2-container{
max-width: 100%;
min-width: 100%;
}
</style>
{% endblock %} {% endblock %}
{% block extrajavascript %} {% block extrajavascript %}