Merge branch 'master' of github.com:ZeusWPI/Haldis
This commit is contained in:
commit
48e314335f
10 changed files with 66 additions and 9 deletions
|
@ -3,6 +3,7 @@ from logging.handlers import TimedRotatingFileHandler
|
||||||
from flask import Flask
|
from flask import Flask
|
||||||
from flask.ext.bootstrap import Bootstrap, StaticCDN
|
from flask.ext.bootstrap import Bootstrap, StaticCDN
|
||||||
from flask.ext.sqlalchemy import SQLAlchemy
|
from flask.ext.sqlalchemy import SQLAlchemy
|
||||||
|
from flask_debugtoolbar import DebugToolbarExtension
|
||||||
|
|
||||||
from airbrake import Airbrake, AirbrakeHandler
|
from airbrake import Airbrake, AirbrakeHandler
|
||||||
|
|
||||||
|
@ -16,6 +17,8 @@ app.extensions['bootstrap']['cdns']['bootstrap'] = StaticCDN()
|
||||||
|
|
||||||
db = SQLAlchemy(app)
|
db = SQLAlchemy(app)
|
||||||
|
|
||||||
|
toolbar = DebugToolbarExtension(app)
|
||||||
|
|
||||||
class PrefixFix(object):
|
class PrefixFix(object):
|
||||||
|
|
||||||
def __init__(self, app, script_name):
|
def __init__(self, app, script_name):
|
||||||
|
|
|
@ -30,6 +30,7 @@ class OrderForm(Form):
|
||||||
|
|
||||||
class OrderItemForm(Form):
|
class OrderItemForm(Form):
|
||||||
product_id = SelectField('Item', coerce=int)
|
product_id = SelectField('Item', coerce=int)
|
||||||
|
extra = StringField('Extra')
|
||||||
submit_button = SubmitField('Submit')
|
submit_button = SubmitField('Submit')
|
||||||
|
|
||||||
def populate(self, location):
|
def populate(self, location):
|
||||||
|
|
26
app/migrations/versions/4e94c0b08ed_.py
Normal file
26
app/migrations/versions/4e94c0b08ed_.py
Normal file
|
@ -0,0 +1,26 @@
|
||||||
|
"""Add extra message
|
||||||
|
|
||||||
|
Revision ID: 4e94c0b08ed
|
||||||
|
Revises: 42709384216
|
||||||
|
Create Date: 2015-06-24 21:42:41.466973
|
||||||
|
|
||||||
|
"""
|
||||||
|
|
||||||
|
# revision identifiers, used by Alembic.
|
||||||
|
revision = '4e94c0b08ed'
|
||||||
|
down_revision = '42709384216'
|
||||||
|
|
||||||
|
from alembic import op
|
||||||
|
import sqlalchemy as sa
|
||||||
|
from sqlalchemy.dialects import mysql
|
||||||
|
|
||||||
|
def upgrade():
|
||||||
|
### commands auto generated by Alembic - please adjust! ###
|
||||||
|
op.add_column('order_item', sa.Column('extra', sa.String(length=254), nullable=True))
|
||||||
|
### end Alembic commands ###
|
||||||
|
|
||||||
|
|
||||||
|
def downgrade():
|
||||||
|
### commands auto generated by Alembic - please adjust! ###
|
||||||
|
op.drop_column('order_item', 'extra')
|
||||||
|
### end Alembic commands ###
|
|
@ -102,12 +102,18 @@ class Order(db.Model):
|
||||||
user["paid"] = user.get("paid", True) and item.paid
|
user["paid"] = user.get("paid", True) and item.paid
|
||||||
user["products"] = user.get("products", []) + [item.product]
|
user["products"] = user.get("products", []) + [item.product]
|
||||||
group[item.get_name()] = user
|
group[item.get_name()] = user
|
||||||
|
|
||||||
return group
|
return group
|
||||||
|
|
||||||
def group_by_product(self):
|
def group_by_product(self):
|
||||||
group = defaultdict(int)
|
group = dict()
|
||||||
for item in self.items:
|
for item in self.items:
|
||||||
group[item.product.name] += 1
|
product = group.get(item.product.name, dict())
|
||||||
|
product['count'] = product.get("count", 0) + 1
|
||||||
|
if item.extra:
|
||||||
|
product["extras"] = product.get("extras", []) + [item.extra]
|
||||||
|
group[item.product.name] = product
|
||||||
|
|
||||||
return group
|
return group
|
||||||
|
|
||||||
def can_close(self, user_id):
|
def can_close(self, user_id):
|
||||||
|
@ -126,8 +132,10 @@ class OrderItem(db.Model):
|
||||||
id = db.Column(db.Integer, primary_key=True)
|
id = db.Column(db.Integer, primary_key=True)
|
||||||
user_id = db.Column(db.Integer, db.ForeignKey('user.id'))
|
user_id = db.Column(db.Integer, db.ForeignKey('user.id'))
|
||||||
order_id = db.Column(db.Integer, db.ForeignKey('order.id'), nullable=False)
|
order_id = db.Column(db.Integer, db.ForeignKey('order.id'), nullable=False)
|
||||||
product_id = db.Column(db.Integer, db.ForeignKey('product.id'))
|
product_id = db.Column(db.Integer, db.ForeignKey('product.id'),
|
||||||
paid = db.Column(db.Boolean, default=False)
|
nullable=False)
|
||||||
|
paid = db.Column(db.Boolean, default=False, nullable=False)
|
||||||
|
extra = db.Column(db.String(254), nullable=True)
|
||||||
name = db.Column(db.String(120))
|
name = db.Column(db.String(120))
|
||||||
|
|
||||||
def configure(self, user, order, product):
|
def configure(self, user, order, product):
|
||||||
|
|
|
@ -18,3 +18,7 @@ body {
|
||||||
.full-width {
|
.full-width {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.product .extras {
|
||||||
|
padding-left: 20px;
|
||||||
|
}
|
|
@ -27,7 +27,7 @@
|
||||||
{%- endif %}
|
{%- endif %}
|
||||||
</div>
|
</div>
|
||||||
<div class="col-sm-5 col-sm-push-2">
|
<div class="col-sm-5 col-sm-push-2">
|
||||||
{% if orders|count > 0 -%}
|
{% if recently_closed|count > 0 -%}
|
||||||
<h3>Recently closed orders:</h3>
|
<h3>Recently closed orders:</h3>
|
||||||
{% for order in recently_closed %}
|
{% for order in recently_closed %}
|
||||||
{{ util.render_order(order) }}
|
{{ util.render_order(order) }}
|
||||||
|
|
|
@ -38,6 +38,11 @@
|
||||||
{{ form.product_id(class='form-control select') }}
|
{{ form.product_id(class='form-control select') }}
|
||||||
{{ util.render_form_field_errors(form.product_id) }}
|
{{ util.render_form_field_errors(form.product_id) }}
|
||||||
</div>
|
</div>
|
||||||
|
<div class="form-group {{ 'has-errors' if form.product_id.errors }}">
|
||||||
|
{{ form.extra.label(class='control-label') }}<br>
|
||||||
|
{{ form.extra(class='form-control', placeholder='Fill in extras, when applicable') }}
|
||||||
|
{{ util.render_form_field_errors(form.extra) }}
|
||||||
|
</div>
|
||||||
{% if current_user.is_anonymous() %}
|
{% if current_user.is_anonymous() %}
|
||||||
<div class="form-group{{ ' has-error' if form.name.errors }}{{ ' required' if form.name.flags.required }}">
|
<div class="form-group{{ ' has-error' if form.name.errors }}{{ ' required' if form.name.flags.required }}">
|
||||||
{{ form.name.label(class='control-label') }}
|
{{ form.name.label(class='control-label') }}
|
||||||
|
@ -63,7 +68,7 @@
|
||||||
{% for item in order.items -%}
|
{% for item in order.items -%}
|
||||||
<tr>
|
<tr>
|
||||||
<td>{{ item.get_name() }}</td>
|
<td>{{ item.get_name() }}</td>
|
||||||
<td>{{ item.product.name }}</td>
|
<td><span title="{{ item.extra if item.extra }}">{{ item.product.name }}{{ "*" if item.extra }}</span></td>
|
||||||
<td>{{ item.product.price|euro }}</td>
|
<td>{{ item.product.price|euro }}</td>
|
||||||
{% if courier_or_admin %}<td>{% if not item.paid %} <a class="btn btn-xs btn-primary" href="{{ url_for('.item_paid', order_id=order.id, item_id=item.id) }}">Pay</a> {% else %} <span class="glyphicon glyphicon-chevron-down"></span> {% endif %}</td>{% endif %}
|
{% if courier_or_admin %}<td>{% if not item.paid %} <a class="btn btn-xs btn-primary" href="{{ url_for('.item_paid', order_id=order.id, item_id=item.id) }}">Pay</a> {% else %} <span class="glyphicon glyphicon-chevron-down"></span> {% endif %}</td>{% endif %}
|
||||||
<td>{% if item.can_delete(order.id, current_user.id, session.get('anon_name', '')) -%}<a href="{{ url_for('.delete_item', order_id=order.id, item_id=item.id) }}"><span class="glyphicon glyphicon-remove"></span></a>{%- endif %}<br/></td>
|
<td>{% if item.can_delete(order.id, current_user.id, session.get('anon_name', '')) -%}<a href="{{ url_for('.delete_item', order_id=order.id, item_id=item.id) }}"><span class="glyphicon glyphicon-remove"></span></a>{%- endif %}<br/></td>
|
||||||
|
@ -75,7 +80,16 @@
|
||||||
<div class="col-md-push-2 col-md-4 darker" id="items-ordered">
|
<div class="col-md-push-2 col-md-4 darker" id="items-ordered">
|
||||||
<h3>Ordered products:</h3>
|
<h3>Ordered products:</h3>
|
||||||
{% for key, value in order.group_by_product().items() -%}
|
{% for key, value in order.group_by_product().items() -%}
|
||||||
{{ key }} - {{ value }}<br/>
|
<div class="product">
|
||||||
|
{{ key }}: {{ value["count"] }}
|
||||||
|
{% if value["extras"] -%}
|
||||||
|
<div class="extras">
|
||||||
|
{% for extra in value["extras"] -%}
|
||||||
|
<div>{{ extra }}</div>
|
||||||
|
{% endfor %}
|
||||||
|
</div>
|
||||||
|
{%- endif %}
|
||||||
|
</div>
|
||||||
{%- endfor %}
|
{%- endfor %}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -35,7 +35,7 @@
|
||||||
{{ util.render_form_field_errors(form.starttime) }}
|
{{ util.render_form_field_errors(form.starttime) }}
|
||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
<div class="form-group{{ ' has-error' if form.stoptime.errors }}{{ ' required' if form.stoptime.flags.required }}{{ ' hidden' if not current_user.is_admin() }}">
|
<div class="form-group{{ ' has-error' if form.stoptime.errors }}{{ ' required' if form.stoptime.flags.required }}">
|
||||||
{{ form.stoptime.label(class='control-label') }}
|
{{ form.stoptime.label(class='control-label') }}
|
||||||
<div class='input-group date' class='datetimepicker'>
|
<div class='input-group date' class='datetimepicker'>
|
||||||
{{ form.stoptime(class='form-control datetimepicker') }}
|
{{ form.stoptime(class='form-control datetimepicker') }}
|
||||||
|
|
|
@ -50,7 +50,7 @@
|
||||||
{{ util.render_form_field_errors(form.starttime) }}
|
{{ util.render_form_field_errors(form.starttime) }}
|
||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
<div class="form-group{{ ' has-error' if form.stoptime.errors }}{{ ' required' if form.stoptime.flags.required }}{{ ' hidden' if not current_user.is_admin() }}">
|
<div class="form-group{{ ' has-error' if form.stoptime.errors }}{{ ' required' if form.stoptime.flags.required }}">
|
||||||
{{ form.stoptime.label(class='control-label') }}
|
{{ form.stoptime.label(class='control-label') }}
|
||||||
<div class='input-group date' class='datetimepicker'>
|
<div class='input-group date' class='datetimepicker'>
|
||||||
{{ form.stoptime(class='form-control datetimepicker') }}
|
{{ form.stoptime(class='form-control datetimepicker') }}
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
Flask==0.10.1
|
Flask==0.10.1
|
||||||
Flask-Admin==1.1.0
|
Flask-Admin==1.1.0
|
||||||
Flask-Bootstrap==3.3.4.1
|
Flask-Bootstrap==3.3.4.1
|
||||||
|
Flask-DebugToolbar==0.10.0
|
||||||
Flask-Login==0.2.11
|
Flask-Login==0.2.11
|
||||||
Flask-Migrate==1.4.0
|
Flask-Migrate==1.4.0
|
||||||
Flask-OAuthlib==0.9.1
|
Flask-OAuthlib==0.9.1
|
||||||
|
|
Loading…
Reference in a new issue