示例#1
0
文件: tickets.py 项目: bfirsh/Website
def new_ticket_type(copy_id):
    form = NewTicketTypeForm()

    if form.validate_on_submit():
        expires = form.expires.data if form.expires.data else None
        token = form.discount_token.data if form.discount_token.data else None
        description = form.description.data if form.description.data else None

        tt = TicketType(form.order.data, form.admits.data,
                        form.name.data, form.type_limit.data, expires=expires,
                        discount_token=token, description=description,
                        personal_limit=form.personal_limit.data,
                        has_badge=form.has_badge.data,
                        is_transferable=form.is_transferable.data)

        tt.prices = [TicketPrice('GBP', form.price_gbp.data),
                     TicketPrice('EUR', form.price_eur.data)]
        app.logger.info('%s adding new TicketType %s', current_user.name, tt)
        db.session.add(tt)
        db.session.commit()
        flash('Your new ticket type has been created')
        return redirect(url_for('.ticket_type_details', type_id=tt.id))

    if copy_id != -1:
        form.init_with_ticket_type(TicketType.query.get(copy_id))

    return render_template('admin/new-ticket-type.html', ticket_type_id=copy_id, form=form)
示例#2
0
    def test_ticket_creation(self):
        with self.app.app_context():
            self.db.session.add(self.user)
            tt = TicketType.query.filter_by(fixed_id=0).one()
            ticket = Ticket(type=tt, user_id=self.user.id)
            self.db.session.add(ticket)
            self.db.session.commit()

            # A ticket without a payment isn't sold...
            assert sum(TicketType.get_ticket_sales().values()) == 0
            assert ticket.id is not None

            ticket.paid = True
            self.db.session.flush()
            # ... but a paid one is
            assert sum(TicketType.get_ticket_sales().values()) == 1

            ticket.expires = datetime.utcnow() - timedelta(minutes=1)
            self.db.session.flush()
            # Expired tickets still count towards capacity
            assert sum(TicketType.get_ticket_sales().values()) == 1

            ticket.paid = False
            self.db.session.flush()
            assert sum(TicketType.get_ticket_sales().values()) == 0
示例#3
0
def new_ticket_type(copy_id):
    form = NewTicketTypeForm()

    if form.validate_on_submit():
        expires = form.expires.data if form.expires.data else None
        token = form.discount_token.data if form.discount_token.data else None
        description = form.description.data if form.description.data else None

        tt = TicketType(form.order.data,
                        form.admits.data,
                        form.name.data,
                        form.type_limit.data,
                        expires=expires,
                        discount_token=token,
                        description=description,
                        personal_limit=form.personal_limit.data,
                        has_badge=form.has_badge.data,
                        is_transferable=form.is_transferable.data)

        tt.prices = [
            TicketPrice('GBP', form.price_gbp.data),
            TicketPrice('EUR', form.price_eur.data)
        ]
        app.logger.info('%s adding new TicketType %s', current_user.name, tt)
        db.session.add(tt)
        db.session.commit()
        flash('Your new ticket type has been created')
        return redirect(url_for('.ticket_type_details', type_id=tt.id))

    if copy_id != -1:
        form.init_with_ticket_type(TicketType.query.get(copy_id))

    return render_template('admin/new-ticket-type.html',
                           ticket_type_id=copy_id,
                           form=form)
示例#4
0
def calc_sales_state(date):
    if TicketType.get_tickets_remaining() < 1:
        # We've hit capacity - no more tickets will be sold
        return "sold-out"
    elif date > datetime(2016, 8, 7):
        return "sales-ended"
    elif TicketType.get_price_cheapest_full() is None:
        # Tickets not currently available, probably just for this round, but we haven't hit site capacity
        return "unavailable"
    else:
        return "available"
示例#5
0
文件: admin.py 项目: Jonty/Website
def ticket_types():
    if current_user.admin:
        form = None
        if request.method == 'POST':
            form = NewTicketTypeForm()
            if form.validate():
                tt = TicketType(form.name.data, form.capacity.data, form.limit.data)
                tt.prices = [TicketPrice('GBP', form.price_gbp), TicketPrice('EUR', form.price_eur)]
                db.session.add(tt)
                db.session.commit()
                return redirect(url_for('ticket_types'))

        types = TicketType.query.all()
        if not form:
            form = NewTicketTypeForm(formdata=None)
        return render_template('admin/admin_ticket_types.html', types=types, form=form)
    else:
        return(('', 404))
示例#6
0
def main():
    full_price = TicketType.get_price_cheapest_full()
    if not (feature_enabled('BANK_TRANSFER')
            or feature_enabled('GOCARDLESS')) and full_price is not None:
        # Only card payment left
        full_price += StripePayment.premium('GBP', full_price)

    state = get_site_state()
    if app.config.get('DEBUG'):
        state = request.args.get("site_state", state)

    return render_template('home/%s.html' % state, full_price=full_price)
示例#7
0
def main():
    full_price = TicketType.get_price_cheapest_full()
    if not (feature_enabled('BANK_TRANSFER') or feature_enabled('GOCARDLESS')) and full_price is not None:
        # Only card payment left
        full_price += StripePayment.premium('GBP', full_price)

    state = get_site_state()
    if app.config.get('DEBUG'):
        state = request.args.get("site_state", state)

    return render_template('home/%s.html' % state,
                           full_price=full_price)
示例#8
0
def tickets_token(token=None):
    tts = TicketType.get_types_for_token(token)
    if tts:
        session['ticket_token'] = token
    else:
        if 'ticket_token' in session:
            del session['ticket_token']
        flash('Ticket token was invalid')

    if any(tt.admits in ['full', 'kid'] for tt in tts):
        return redirect(url_for('tickets.choose'))

    return redirect(url_for('tickets.choose', flow='other'))
示例#9
0
def tickets_token(token=None):
    tts = TicketType.get_types_for_token(token)
    if tts:
        session['ticket_token'] = token
    else:
        if 'ticket_token' in session:
            del session['ticket_token']
        flash('Ticket token was invalid')

    if any(tt.admits in ['full', 'kid'] for tt in tts):
        return redirect(url_for('tickets.choose'))

    return redirect(url_for('tickets.choose', flow='other'))
示例#10
0
def ticket_types():
    if current_user.admin:
        form = None
        if request.method == 'POST':
            form = NewTicketTypeForm()
            if form.validate():
                tt = TicketType(form.name.data, form.capacity.data,
                                form.limit.data)
                tt.prices = [
                    TicketPrice('GBP', form.price_gbp),
                    TicketPrice('EUR', form.price_eur)
                ]
                db.session.add(tt)
                db.session.commit()
                return redirect(url_for('ticket_types'))

        types = TicketType.query.all()
        if not form:
            form = NewTicketTypeForm(formdata=None)
        return render_template('admin/admin_ticket_types.html',
                               types=types,
                               form=form)
    else:
        return (('', 404))
示例#11
0
def choose(flow=None):
    token = session.get('ticket_token')
    sales_state = get_sales_state()

    if flow is None:
        admissions = True
    elif flow == 'other':
        admissions = False
    else:
        abort(404)

    if sales_state in ['unavailable', 'sold-out']:
        # For the main entry point, we assume people want admissions tickets,
        # but we still need to sell people e.g. parking tickets or tents until
        # the final cutoff (sales-ended).
        if not admissions:
            sales_state = 'available'

        # Allow people with valid discount tokens to buy tickets
        elif token is not None and TicketType.get_types_for_token(token):
            sales_state = 'available'

    if app.config.get('DEBUG'):
        sales_state = request.args.get("sales_state", sales_state)

    if sales_state == 'available':
        pass
    elif not current_user.is_anonymous() and current_user.has_permission(
            'admin'):
        pass
    else:
        return render_template("tickets-cutoff.html")

    form = TicketAmountsForm()

    # If this is the main page, exclude tents and other paraphernalia.
    # For the non-admissions page, only exclude actual admissions tickets.
    # This means both pages show parking and caravan tickets.
    if admissions:
        tts = TicketType.query.filter(~TicketType.admits.in_(['other']))
    else:
        tts = TicketType.query.filter(~TicketType.admits.in_(['full', 'kid']))

    tts = tts.order_by(TicketType.order).all()
    limits = dict((tt.id, tt.user_limit(current_user, token)) for tt in tts)

    if request.method != 'POST':
        # Empty form - populate ticket types
        for tt in tts:
            form.types.append_entry()
            form.types[-1].type_id.data = tt.id

    tts = {tt.id: tt for tt in tts}
    for f in form.types:
        t_id = f.type_id.data
        f._type = tts[t_id]

        values = range(limits[t_id] + 1)
        f.amount.values = values
        f._any = any(values)

    if form.validate_on_submit():
        if form.buy.data or form.buy_other.data:
            set_user_currency(form.currency_code.data)

            basket = []
            for f in form.types:
                if f.amount.data:
                    tt = f._type
                    app.logger.info('Adding %s %s tickets to basket',
                                    f.amount.data, tt.name)
                    basket += [tt.id] * f.amount.data

            if basket:
                session['basket'] = basket

                return redirect(url_for('tickets.pay', flow=flow))
            elif admissions:
                flash("Please select at least one ticket to buy.")
            else:
                flash("Please select at least one item to buy.")

    if request.method == 'POST' and form.set_currency.data:
        if form.set_currency.validate(form):
            app.logger.info("Updating currency to %s only",
                            form.set_currency.data)
            set_user_currency(form.set_currency.data)

            for field in form:
                field.errors = []

    form.currency_code.data = get_user_currency()

    return render_template("tickets-choose.html",
                           form=form,
                           admissions=admissions)
示例#12
0
文件: cfp.py 项目: emfcamp/Website
def main(cfp_type="talk"):
    if cfp_type not in ["talk", "workshop", "installation"]:
        abort(404)

    ignore_closed = "closed" in request.args

    if app.config.get("CFP_CLOSED") and not ignore_closed:
        return render_template("cfp/closed.html")

    forms = [
        TalkProposalForm(prefix="talk"),
        WorkshopProposalForm(prefix="workshop"),
        InstallationProposalForm(prefix="installation"),
    ]
    (form,) = [f for f in forms if f.type == cfp_type]
    form.active_cfp_type = cfp_type

    # If the user is already logged in set their name & email for the form
    if current_user.is_authenticated():
        form.name.data = current_user.name
        form.email.data = current_user.email

    if request.method == "POST":
        app.logger.info("Checking %s proposal for %s (%s)", cfp_type, form.name.data, form.email.data)

    if form.validate_on_submit():
        new_user = False
        if current_user.is_anonymous():
            try:
                create_current_user(form.email.data, form.name.data)
                new_user = True
            except IntegrityError as e:
                app.logger.warn("Adding user raised %r, possible double-click", e)
                flash("An error occurred while creating an account for you. Please try again.")
                return redirect(url_for(".main"))

        if cfp_type == "talk":
            cfp = TalkProposal()
            cfp.length = form.length.data

        elif cfp_type == "workshop":
            cfp = WorkshopProposal()
            cfp.length = form.length.data
            cfp.attendees = form.attendees.data
            cfp.cost = form.cost.data

        elif cfp_type == "installation":
            cfp = InstallationProposal()
            cfp.size = form.size.data
            cfp.funds = form.funds.data

        cfp.user_id = current_user.id

        cfp.title = form.title.data
        cfp.requirements = form.requirements.data
        cfp.description = form.description.data
        cfp.notice_required = form.notice_required.data
        cfp.needs_help = form.needs_help.data

        db.session.add(cfp)
        db.session.commit()

        # Send confirmation message
        msg = Message(
            "Electromagnetic Field CFP Submission", sender=app.config["CONTENT_EMAIL"], recipients=[current_user.email]
        )

        msg.body = render_template("emails/cfp-submission.txt", cfp=cfp, type=cfp_type, new_user=new_user)
        mail.send(msg)

        return redirect(url_for(".complete"))

    full_price = TicketType.get_price_cheapest_full()

    return render_template(
        "cfp/main.html",
        full_price=full_price,
        forms=forms,
        active_cfp_type=cfp_type,
        has_errors=bool(form.errors),
        ignore_closed=ignore_closed,
    )
示例#13
0
def choose(flow=None):
    token = session.get('ticket_token')
    sales_state = get_sales_state()

    if flow is None:
        admissions = True
    elif flow == 'other':
        admissions = False
    else:
        abort(404)

    if sales_state in ['unavailable', 'sold-out']:
        # For the main entry point, we assume people want admissions tickets,
        # but we still need to sell people e.g. parking tickets or tents until
        # the final cutoff (sales-ended).
        if not admissions:
            sales_state = 'available'

        # Allow people with valid discount tokens to buy tickets
        elif token is not None and TicketType.get_types_for_token(token):
            sales_state = 'available'


    if app.config.get('DEBUG'):
        sales_state = request.args.get("sales_state", sales_state)

    if sales_state == 'available':
        pass
    elif not current_user.is_anonymous() and current_user.has_permission('admin'):
        pass
    else:
        return render_template("tickets-cutoff.html")

    form = TicketAmountsForm()

    # If this is the main page, exclude tents and other paraphernalia.
    # For the non-admissions page, only exclude actual admissions tickets.
    # This means both pages show parking and caravan tickets.
    if admissions:
        tts = TicketType.query.filter(~TicketType.admits.in_(['other']))
    else:
        tts = TicketType.query.filter(~TicketType.admits.in_(['full', 'kid']))

    tts = tts.order_by(TicketType.order).all()
    limits = dict((tt.id, tt.user_limit(current_user, token)) for tt in tts)

    if request.method != 'POST':
        # Empty form - populate ticket types
        for tt in tts:
            form.types.append_entry()
            form.types[-1].type_id.data = tt.id


    tts = {tt.id: tt for tt in tts}
    for f in form.types:
        t_id = f.type_id.data
        f._type = tts[t_id]

        values = range(limits[t_id] + 1)
        f.amount.values = values
        f._any = any(values)

    if form.validate_on_submit():
        if form.buy.data or form.buy_other.data:
            set_user_currency(form.currency_code.data)

            basket = []
            for f in form.types:
                if f.amount.data:
                    tt = f._type
                    app.logger.info('Adding %s %s tickets to basket', f.amount.data, tt.name)
                    basket += [tt.id] * f.amount.data

            if basket:
                session['basket'] = basket

                return redirect(url_for('tickets.pay', flow=flow))
            elif admissions:
                flash("Please select at least one ticket to buy.")
            else:
                flash("Please select at least one item to buy.")

    if request.method == 'POST' and form.set_currency.data:
        if form.set_currency.validate(form):
            app.logger.info("Updating currency to %s only", form.set_currency.data)
            set_user_currency(form.set_currency.data)

            for field in form:
                field.errors = []

    form.currency_code.data = get_user_currency()

    return render_template("tickets-choose.html", form=form, admissions=admissions)
示例#14
0
文件: tickets.py 项目: mokele/Website
def tickets_choose():
    form = TicketAmountsForm(request.form)

    if not form.types:
        for tt in TicketType.query.order_by(TicketType.order).all():
            form.types.append_entry()
            form.types[-1].type_id.data = tt.id

    if current_user.is_authenticated():
        prepays = current_user.tickets.filter_by(type=TicketType.bycode("prepay"), paid=True).count()
        fulls = current_user.tickets.join(TicketType).filter(TicketType.code.like("full%")).count()
        if fulls >= prepays:
            prepays = 0
    else:
        prepays = 0
        fulls = 0

    token_tts = TicketToken.types(session.get("ticket_token"))
    token_only = ["full_ucl", "full_hs", "full_make", "full_adafruit", "full_hackaday", "full_boingboing", "full_dp"]

    for f in form.types:
        tt = TicketType.query.get(f.type_id.data)
        f._type = tt

        limit = tt.user_limit(current_user)

        values = range(limit + 1)
        if tt.code == "prepay":
            values = []
        elif tt.code == "full_prepay":
            assert prepays <= limit
            values = [prepays]
        elif tt.code in token_only and tt not in token_tts:
            values = []
        elif tt.code == "full":
            if token_tts:
                values = []

        f.amount.values = values
        f._any = any(values)

    if request.method == "POST" and form.validate():

        basket = []
        for f in form.types:
            if f.amount.data:
                tt = f._type

                if tt.code in token_only and tt not in token_tts:
                    if f.amount.data:
                        flash("Ticket type %s is not currently available")
                    return redirect(url_for("tickets_choose"))

                app.logger.info("Adding %s %s tickets to basket", f.amount.data, tt.name)
                basket += [tt.id] * f.amount.data

        if basket:
            session["basket"] = basket

            if current_user.is_authenticated():
                return redirect(url_for("tickets_info"))
            else:
                return redirect(url_for("signup", next=url_for("tickets_info")))

    return render_template("tickets-choose.html", form=form)
示例#15
0
def tickets_choose():
    if ticket_cutoff():
        return render_template("tickets-cutoff.html")
    form = TicketAmountsForm(request.form)

    if not form.types:
        for tt in TicketType.query.order_by(TicketType.order).all():
            form.types.append_entry()
            form.types[-1].type_id.data = tt.id

    if current_user.is_authenticated():
        prepays = current_user.tickets. \
            filter_by(type=TicketType.bycode('prepay'), paid=True). \
            count()
        fulls = current_user.tickets.join(TicketType). \
            filter(TicketType.code.like('full%')). \
            count()
        if fulls >= prepays:
            prepays = 0
    else:
        prepays = 0
        fulls = 0

    token_tts = TicketToken.types(session.get('ticket_token'))
    token_only = ['full_ucl', 'full_hs', 'full_make', 'full_adafruit',
                    'full_hackaday', 'full_boingboing', 'full_dp']

    for f in form.types:
        tt = TicketType.query.get(f.type_id.data)
        f._type = tt

        limit = tt.user_limit(current_user)

        values = range(limit + 1)
        if tt.code == 'prepay':
            values = []
        elif tt.code == 'full_prepay':
            assert prepays <= limit
            values = [prepays]
        elif tt.code in token_only and tt not in token_tts:
            values = []
        elif tt.code == 'full':
            if token_tts:
                values = []

        f.amount.values = values
        f._any = any(values)


    if request.method == 'POST' and form.validate():

        basket = []
        for f in form.types:
            if f.amount.data:
                tt = f._type

                if tt.code in token_only and tt not in token_tts:
                    if f.amount.data:
                        flash('Ticket type %s is not currently available')
                    return redirect(url_for('tickets_choose'))

                app.logger.info('Adding %s %s tickets to basket', f.amount.data, tt.name)
                basket += [tt.id] * f.amount.data

        if basket:
            session['basket'] = basket

            if current_user.is_authenticated():
                return redirect(url_for('tickets_info'))
            else:
                return redirect(url_for('signup', next=url_for('tickets_info')))

    return render_template("tickets-choose.html", form=form)
示例#16
0
def main(cfp_type='talk'):
    if cfp_type not in ['talk', 'workshop', 'installation']:
        abort(404)

    ignore_closed = 'closed' in request.args

    if app.config.get('CFP_CLOSED') and not ignore_closed:
        return render_template('cfp/closed.html')

    forms = [
        TalkProposalForm(prefix="talk"),
        WorkshopProposalForm(prefix="workshop"),
        InstallationProposalForm(prefix="installation")
    ]
    (form, ) = [f for f in forms if f.type == cfp_type]
    form.active_cfp_type = cfp_type

    # If the user is already logged in set their name & email for the form
    if current_user.is_authenticated():
        form.name.data = current_user.name
        form.email.data = current_user.email

    if request.method == 'POST':
        app.logger.info('Checking %s proposal for %s (%s)', cfp_type,
                        form.name.data, form.email.data)

    if form.validate_on_submit():
        new_user = False
        if current_user.is_anonymous():
            try:
                create_current_user(form.email.data, form.name.data)
                new_user = True
            except IntegrityError as e:
                app.logger.warn('Adding user raised %r, possible double-click',
                                e)
                flash(
                    'An error occurred while creating an account for you. Please try again.'
                )
                return redirect(url_for('.main'))

        if cfp_type == 'talk':
            cfp = TalkProposal()
            cfp.length = form.length.data

        elif cfp_type == 'workshop':
            cfp = WorkshopProposal()
            cfp.length = form.length.data
            cfp.attendees = form.attendees.data
            cfp.cost = form.cost.data

        elif cfp_type == 'installation':
            cfp = InstallationProposal()
            cfp.size = form.size.data
            cfp.funds = form.funds.data

        cfp.user_id = current_user.id

        cfp.title = form.title.data
        cfp.requirements = form.requirements.data
        cfp.description = form.description.data
        cfp.notice_required = form.notice_required.data
        cfp.needs_help = form.needs_help.data

        db.session.add(cfp)
        db.session.commit()

        # Send confirmation message
        msg = Message('Electromagnetic Field CFP Submission',
                      sender=app.config['CONTENT_EMAIL'],
                      recipients=[current_user.email])

        msg.body = render_template('emails/cfp-submission.txt',
                                   cfp=cfp,
                                   type=cfp_type,
                                   new_user=new_user)
        mail.send(msg)

        return redirect(url_for('.complete'))

    full_price = TicketType.get_price_cheapest_full()

    return render_template('cfp/main.html',
                           full_price=full_price,
                           forms=forms,
                           active_cfp_type=cfp_type,
                           has_errors=bool(form.errors),
                           ignore_closed=ignore_closed)