コード例 #1
0
ファイル: schedule_xml.py プロジェクト: emfcamp/Website
def make_root():
    root = etree.Element('schedule')

    _add_sub_with_text(root, 'version', '1.0-public')

    conference = etree.SubElement(root, 'conference')

    _add_sub_with_text(conference, 'title', 'Electromagnetic Field {}'.format(event_start().year))
    _add_sub_with_text(conference, 'acronym', 'emf{}'.format(event_start().year))
    _add_sub_with_text(conference, 'start', event_start().strftime('%Y-%m-%d'))
    _add_sub_with_text(conference, 'end', event_end().strftime('%Y-%m-%d'))
    _add_sub_with_text(conference, 'days', '3')
    _add_sub_with_text(conference, 'timeslot_duration', '00:10')

    return root
コード例 #2
0
def add_event(room, event):
    url = external_url('schedule.line_up_proposal',
                       proposal_id=event['id'],
                       slug=event['slug'])

    event_node = etree.SubElement(room,
                                  'event',
                                  id=str(event['id']),
                                  guid=str(uuid5(NAMESPACE_URL, url)))

    _add_sub_with_text(event_node, 'room', room.attrib['name'])
    _add_sub_with_text(event_node, 'title', event['title'])
    _add_sub_with_text(event_node, 'type', event.get('type', 'talk'))
    _add_sub_with_text(event_node, 'date', event['start_date'].isoformat())

    # Start time
    _add_sub_with_text(event_node, 'start',
                       event['start_date'].strftime('%H:%M'))

    duration = get_duration(event['start_date'], event['end_date'])
    _add_sub_with_text(event_node, 'duration', duration)

    _add_sub_with_text(event_node, 'abstract', event['description'])
    _add_sub_with_text(event_node, 'description', event['description'])

    _add_sub_with_text(
        event_node, 'slug',
        'emf%s-%s-%s' % (event_start().year, event['id'], event['slug']))

    _add_sub_with_text(event_node, 'subtitle', '')
    _add_sub_with_text(event_node, 'track', '')

    add_persons(event_node, event)
    add_recording(event_node, event)
コード例 #3
0
def get_auth_tag():
    tag = "emf-{}-".format(event_start().year)
    msg = b"bar-training-" + tag.encode("utf-8")
    tag += hmac.new(app.config["SECRET_KEY"].encode("utf-8"),
                    msg,
                    digestmod=sha256).hexdigest()
    return tag
コード例 #4
0
ファイル: schedule.py プロジェクト: praxeology/Website
def favourites_ical():
    code = request.args.get('token', None)
    user = None
    if code:
        user = User.get_by_api_token(app.config.get('SECRET_KEY'), str(code))
    if not current_user.is_anonymous:
        user = current_user
    if not user:
        abort(404)

    schedule = _get_scheduled_proposals(request.args, override_user=user)
    title = 'EMF {} Favourites for {}'.format(event_start().year, user.name)

    cal = Calendar()
    cal.add('summary', title)
    cal.add('X-WR-CALNAME', title)
    cal.add('X-WR-CALDESC', title)
    cal.add('version', '2.0')

    for event in schedule:
        if not event['is_fave']:
            continue
        cal_event = Event()
        cal_event.add('uid', event['id'])
        cal_event.add('summary', event['title'])
        cal_event.add('description', event['description'])
        cal_event.add('location', event['venue'])
        cal_event.add('dtstart', event['start_date'])
        cal_event.add('dtend', event['end_date'])
        cal.add_component(cal_event)

    return Response(cal.to_ical(), mimetype='text/calendar')
コード例 #5
0
ファイル: schedule_xml.py プロジェクト: emfcamp/Website
def add_event(room, event):
    url = external_url('schedule.line_up_proposal', proposal_id=event['id'], slug=event['slug'])

    event_node = etree.SubElement(room, 'event', id=str(event['id']),
                                                 guid=str(uuid5(NAMESPACE_URL, url)))

    _add_sub_with_text(event_node, 'room', room.attrib['name'])
    _add_sub_with_text(event_node, 'title', event['title'])
    _add_sub_with_text(event_node, 'type', event.get('type', 'talk'))
    _add_sub_with_text(event_node, 'date', event['start_date'].isoformat())

    # Start time
    _add_sub_with_text(event_node, 'start', event['start_date'].strftime('%H:%M'))

    duration = get_duration(event['start_date'], event['end_date'])
    _add_sub_with_text(event_node, 'duration', duration)

    _add_sub_with_text(event_node, 'abstract', event['description'])
    _add_sub_with_text(event_node, 'description', '')

    _add_sub_with_text(event_node, 'slug', 'emf%s-%s-%s' % (event_start().year, event['id'], event['slug']))

    _add_sub_with_text(event_node, 'subtitle', '')
    _add_sub_with_text(event_node, 'track', '')

    add_persons(event_node, event)
    add_recording(event_node, event)
コード例 #6
0
ファイル: schedule.py プロジェクト: dominicgs/Website
def favourites_ical():
    code = request.args.get('token', None)
    user = None
    if code:
        user = User.get_by_checkin_code(app.config.get('FEED_SECRET_KEY'), str(code))
    if not current_user.is_anonymous:
        user = current_user
    if not user:
        abort(404)

    schedule = _get_scheduled_proposals(request.args, override_user=user)
    title = 'EMF {} Favourites for {}'.format(event_start().year, user.name)

    cal = Calendar()
    cal.add('summary', title)
    cal.add('X-WR-CALNAME', title)
    cal.add('X-WR-CALDESC', title)
    cal.add('version', '2.0')

    for event in schedule:
        if not event['is_fave']:
            continue
        cal_event = Event()
        cal_event.add('uid', event['id'])
        cal_event.add('summary', event['title'])
        cal_event.add('description', event['description'])
        cal_event.add('location', event['venue'])
        cal_event.add('dtstart', event['start_date'])
        cal_event.add('dtend', event['end_date'])
        cal.add_component(cal_event)

    return Response(cal.to_ical(), mimetype='text/calendar')
コード例 #7
0
ファイル: feeds.py プロジェクト: geeksareforlife/Website
def favourites_ical():
    code = request.args.get("token", None)
    user = None
    if code:
        user = User.get_by_api_token(app.config.get("SECRET_KEY"), str(code))
    if not current_user.is_anonymous:
        user = current_user
    if not user:
        abort(404)

    schedule = _get_scheduled_proposals(request.args, override_user=user)
    title = "EMF {} Favourites for {}".format(event_start().year, user.name)

    cal = Calendar()
    cal.add("summary", title)
    cal.add("X-WR-CALNAME", title)
    cal.add("X-WR-CALDESC", title)
    cal.add("version", "2.0")

    for event in schedule:
        if not event["is_fave"]:
            continue
        cal_event = Event()
        cal_event.add("uid", event["id"])
        cal_event.add("summary", event["title"])
        cal_event.add("description", _format_event_description(event))
        cal_event.add("location", event["venue"])
        cal_event.add("dtstart", event["start_date"])
        cal_event.add("dtend", event["end_date"])
        cal.add_component(cal_event)

    return Response(cal.to_ical(), mimetype="text/calendar")
コード例 #8
0
    def event_date_processor():
        def suffix(d):
            return ("th" if 11 <= d <= 13 else {
                1: "st",
                2: "nd",
                3: "rd"
            }.get(d % 10, "th"))

        s = event_start()
        e = event_end()
        assert s.year == e.year
        if s.month == e.month:
            fancy_dates = f"""{s.strftime('%B')}<span style="white-space: nowrap">
                {s.day}<sup>{suffix(s.day)}</sup>&ndash;{e.day}<sup>{suffix(e.day)}</sup>
                {s.year}
                </span>"""

            simple_dates = f"{s.day}&ndash;{e.day} {s.strftime('%B')}"

        else:
            fancy_dates = f"""{s.strftime("%B")}
                {s.day}<sup>{suffix(s.day)}</sup>&ndash;{e.strftime("%B")}
                {e.day}<sup>{suffix(e.day)}</sup>"""

            simple_dates = (
                f"""{s.day} {s.strftime("%B")}&ndash;{e.day} {e.strftime("%B")}"""
            )

        return {
            "fancy_dates": Markup(fancy_dates),
            "simple_dates": Markup(simple_dates),
            "event_start": s,
            "event_end": e,
            "event_year": s.year,
        }
コード例 #9
0
ファイル: receipt.py プロジェクト: emfcamp/Website
def attach_tickets(msg, user):
    # Attach tickets to a mail Message
    page = render_receipt(user, pdf=True)
    url = external_url('tickets.receipt', user_id=user.id)
    pdf = render_pdf(url, page)

    msg.attach('EMF{}.pdf'.format(event_start().year), 'application/pdf', pdf.read())
コード例 #10
0
def get_auth_tag():
    tag = 'emf-{}-'.format(event_start().year)
    msg = b'bar-training-' + tag.encode('utf-8')
    tag += hmac.new(app.config['SECRET_KEY'].encode('utf-8'),
                    msg,
                    digestmod=sha256).hexdigest()
    return tag
コード例 #11
0
def attach_tickets(msg, user):
    # Attach tickets to a mail Message
    page = render_receipt(user, pdf=True)
    url = external_url('tickets.receipt', user_id=user.id)
    pdf = render_pdf(url, page)

    msg.attach('EMF{}.pdf'.format(event_start().year), 'application/pdf',
               pdf.read())
コード例 #12
0
def make_root():
    root = etree.Element("schedule")

    _add_sub_with_text(root, "version", "1.0-public")

    conference = etree.SubElement(root, "conference")

    _add_sub_with_text(conference, "title",
                       "Electromagnetic Field {}".format(event_start().year))
    _add_sub_with_text(conference, "acronym",
                       "emf{}".format(event_start().year))
    _add_sub_with_text(conference, "start", event_start().strftime("%Y-%m-%d"))
    _add_sub_with_text(conference, "end", event_end().strftime("%Y-%m-%d"))
    _add_sub_with_text(conference, "days", "3")
    _add_sub_with_text(conference, "timeslot_duration", "00:10")

    return root
コード例 #13
0
def make_root():
    root = etree.Element('schedule')

    _add_sub_with_text(root, 'version', '1.0-public')

    conference = etree.SubElement(root, 'conference')

    _add_sub_with_text(conference, 'title',
                       'Electromagnetic Field {}'.format(event_start().year))
    _add_sub_with_text(conference, 'acronym',
                       'emf{}'.format(event_start().year))
    _add_sub_with_text(conference, 'start', event_start().strftime('%Y-%m-%d'))
    _add_sub_with_text(conference, 'end', event_end().strftime('%Y-%m-%d'))
    _add_sub_with_text(conference, 'days', '3')
    _add_sub_with_text(conference, 'timeslot_duration', '00:10')

    return root
コード例 #14
0
ファイル: __init__.py プロジェクト: roseregina/Website
    def event_date_processor():
        def suffix(d):
            return 'th' if 11 <= d <= 13 else {1: 'st', 2: 'nd', 3: 'rd'}.get(d % 10, 'th')

        s = event_start()
        e = event_end()
        assert s.year == e.year
        if s.month == e.month:
            fancy_dates = '{s_month} ' \
                '<span style="white-space: nowrap">' \
                '{s.day}<sup>{s_suff}</sup>&mdash;' \
                '{e.day}<sup>{e_suff}</sup>' \
                '</span>' \
                .format(s=s, s_suff=suffix(s.day),
                        s_month=s.strftime('%B'),
                        e=e, e_suff=suffix(e.day))

            simple_dates = '{s.day}&mdash;' \
                '{e.day} ' \
                '{s_month}' \
                .format(s=s, s_month=s.strftime('%B'),
                        e=e)

        else:
            fancy_dates = '{s_month} ' \
                '{s.day}<sup>{s_suff}</sup>&ndash;' \
                '{e_month} ' \
                '{e.day}<sup>{e_suff}</sup>' \
                .format(s=s, s_suff=suffix(s.day),
                        s_month=s.strftime('%B'),
                        e=e, e_suff=suffix(e.day),
                        e_month=e.strftime('%B'))

            simple_dates = '{s.day} ' \
                '{s_month}&ndash;' \
                '{e.day} ' \
                '{e_month}' \
                .format(s=s, s_month=s.strftime('%B'),
                        e=e, e_month=e.strftime('%B'))


        return {
            'fancy_dates': Markup(fancy_dates),
            'simple_dates': Markup(simple_dates),
            'event_start': s,
            'event_end': e,
            'event_year': s.year,
        }
コード例 #15
0
ファイル: receipt.py プロジェクト: unknowndomain/emf-website
def attach_tickets(msg, user):
    # Attach tickets to a mail Message
    page = render_receipt(user, pdf=True)
    url = external_url('tickets.receipt', user_id=user.id)
    pdf = render_pdf(url, page)

    msg.attach('EMF{}.pdf'.format(event_start().year), 'application/pdf',
               pdf.read())

    purchases = user.owned_purchases.filter_by(is_paid_for=True, state='paid') \
                                    .join(PriceTier, Product, ProductGroup) \
                                    .filter(ProductGroup.type.in_(RECEIPT_TYPES)) \
                                    .with_entities(Purchase) \
                                    .group_by(Purchase) \
                                    .order_by(Purchase.id)

    for p in purchases:
        p.set_state('receipt-emailed')
コード例 #16
0
ファイル: schedule.py プロジェクト: dominicgs/Website
def schedule_ical():
    schedule = _get_scheduled_proposals(request.args)
    title = 'EMF {}'.format(event_start().year)

    cal = Calendar()
    cal.add('summary', title)
    cal.add('X-WR-CALNAME', title)
    cal.add('X-WR-CALDESC', title)
    cal.add('version', '2.0')

    for event in schedule:
        cal_event = Event()
        cal_event.add('uid', event['id'])
        cal_event.add('summary', event['title'])
        cal_event.add('description', event['description'])
        cal_event.add('location', event['venue'])
        cal_event.add('dtstart', event['start_date'])
        cal_event.add('dtend', event['end_date'])
        cal.add_component(cal_event)

    return Response(cal.to_ical(), mimetype='text/calendar')
コード例 #17
0
ファイル: schedule.py プロジェクト: praxeology/Website
def schedule_ical():
    schedule = _get_scheduled_proposals(request.args)
    title = 'EMF {}'.format(event_start().year)

    cal = Calendar()
    cal.add('summary', title)
    cal.add('X-WR-CALNAME', title)
    cal.add('X-WR-CALDESC', title)
    cal.add('version', '2.0')

    for event in schedule:
        cal_event = Event()
        cal_event.add('uid', event['id'])
        cal_event.add('summary', event['title'])
        cal_event.add('description', event['description'])
        cal_event.add('location', event['venue'])
        cal_event.add('dtstart', event['start_date'])
        cal_event.add('dtend', event['end_date'])
        cal.add_component(cal_event)

    return Response(cal.to_ical(), mimetype='text/calendar')
コード例 #18
0
def add_event(room, event):
    url = external_url("schedule.item",
                       year=event_year(),
                       proposal_id=event["id"],
                       slug=event["slug"])

    event_node = etree.SubElement(room,
                                  "event",
                                  id=str(event["id"]),
                                  guid=str(uuid5(NAMESPACE_URL, url)))

    _add_sub_with_text(event_node, "room", room.attrib["name"])
    _add_sub_with_text(event_node, "title", event["title"])
    _add_sub_with_text(event_node, "type", event.get("type", "talk"))
    _add_sub_with_text(event_node, "date", event["start_date"].isoformat())

    # Start time
    _add_sub_with_text(event_node, "start",
                       event["start_date"].strftime("%H:%M"))

    duration = get_duration(event["start_date"], event["end_date"])
    _add_sub_with_text(event_node, "duration", duration)

    _add_sub_with_text(event_node, "abstract", event["description"])
    _add_sub_with_text(event_node, "description", "")

    _add_sub_with_text(
        event_node,
        "slug",
        "emf%s-%s-%s" % (event_start().year, event["id"], event["slug"]),
    )

    _add_sub_with_text(event_node, "subtitle", "")
    _add_sub_with_text(event_node, "track", "")

    add_persons(event_node, event)
    add_recording(event_node, event)
コード例 #19
0
ファイル: feeds.py プロジェクト: geeksareforlife/Website
def schedule_ical(year):
    if year != event_year():
        return feed_historic(year, "ics")

    schedule = _get_scheduled_proposals(request.args)
    title = "EMF {}".format(event_start().year)

    cal = Calendar()
    cal.add("summary", title)
    cal.add("X-WR-CALNAME", title)
    cal.add("X-WR-CALDESC", title)
    cal.add("version", "2.0")

    for event in schedule:
        cal_event = Event()
        cal_event.add("uid", event["id"])
        cal_event.add("summary", event["title"])
        cal_event.add("description", _format_event_description(event))
        cal_event.add("location", event["venue"])
        cal_event.add("dtstart", event["start_date"])
        cal_event.add("dtend", event["end_date"])
        cal.add_component(cal_event)

    return Response(cal.to_ical(), mimetype="text/calendar")
コード例 #20
0
ファイル: stripe.py プロジェクト: emfcamp/Website
def charge_stripe(payment):
    logger.info("Charging Stripe payment %s, token %s", payment.id, payment.token)
    # If we fail to go from charging to charged, we won't have the charge ID,
    # so can't process the webhook. The payment will need to be manually resolved.
    # Test this with 4000000000000341.

    payment.state = 'charging'
    db.session.commit()
    payment = get_user_payment_or_abort(
        payment.id, 'stripe',
        valid_states=['charging'],
    )

    # Stripe say it's max 15 chars, appended to company name,
    # but it looks like only 10 chars is reliable.
    description = 'EMF {}'.format(event_start().year)
    try:
        try:
            charge = stripe.Charge.create(
                amount=payment.amount_int,
                currency=payment.currency.lower(),
                card=payment.token,
                description=payment.description,
                statement_description=description,
            )
        except stripe.CardError as e:
            error = e.json_body['error']
            logger.warn('Card payment failed with exception "%s"', e)
            flash('Unfortunately your card payment failed with the error: %s' % (error['message']))
            raise

        except Exception as e:
            logger.warn("Exception %r confirming payment", e)
            flash('An error occurred with your payment, please try again')
            raise

    except Exception:
        # Allow trying again
        payment.state = 'captured'
        db.session.commit()
        return redirect(url_for('.stripe_tryagain', payment_id=payment.id))

    payment.chargeid = charge.id
    if charge.paid:
        payment.paid()
    else:
        payment.state = 'charged'
        payment.expires = datetime.utcnow() + timedelta(days=app.config['EXPIRY_DAYS_STRIPE'])

    db.session.commit()

    logger.info('Payment %s completed OK (state %s)', payment.id, payment.state)

    # FIXME: determine whether these are tickets or generic products
    msg = Message("Your EMF ticket purchase",
                  sender=app.config.get('TICKETS_EMAIL'),
                  recipients=[payment.user.email])

    already_emailed = set_tickets_emailed(payment.user)
    msg.body = render_template("emails/tickets-purchased-email-stripe.txt",
                               user=payment.user, payment=payment,
                               already_emailed=already_emailed)

    if feature_enabled('ISSUE_TICKETS') and charge.paid:
        attach_tickets(msg, payment.user)

    mail.send(msg)
    db.session.commit()

    return redirect(url_for('.stripe_waiting', payment_id=payment.id))
コード例 #21
0
def charge_stripe(payment):
    logger.info("Charging Stripe payment %s, token %s", payment.id,
                payment.token)
    # If we fail to go from charging to charged, we won't have the charge ID,
    # so can't process the webhook. The payment will need to be manually resolved.
    # Test this with 4000000000000341.

    payment.state = 'charging'
    db.session.commit()
    payment = get_user_payment_or_abort(
        payment.id,
        'stripe',
        valid_states=['charging'],
    )

    # max 15 chars, appended to company name
    description = 'Tickets {}'.format(event_start().year)
    try:
        try:
            charge = stripe.Charge.create(
                amount=payment.amount_int,
                currency=payment.currency.lower(),
                card=payment.token,
                description=payment.description,
                statement_description=description,
            )
        except stripe.CardError as e:
            error = e.json_body['error']
            logger.warn('Card payment failed with exception "%s"', e)
            flash('Unfortunately your card payment failed with the error: %s' %
                  (error['message']))
            raise

        except Exception as e:
            logger.warn("Exception %r confirming payment", e)
            flash('An error occurred with your payment, please try again')
            raise

    except Exception:
        # Allow trying again
        payment.state = 'captured'
        db.session.commit()
        return redirect(url_for('.stripe_tryagain', payment_id=payment.id))

    payment.chargeid = charge.id
    if charge.paid:
        payment.paid()
    else:
        payment.state = 'charged'
        payment.expires = datetime.utcnow() + timedelta(
            days=app.config['EXPIRY_DAYS_STRIPE'])

    db.session.commit()

    logger.info('Payment %s completed OK (state %s)', payment.id,
                payment.state)

    # FIXME: determine whether these are tickets or generic products
    msg = Message("Your EMF ticket purchase",
                  sender=app.config.get('TICKETS_EMAIL'),
                  recipients=[payment.user.email])
    msg.body = render_template("emails/tickets-purchased-email-stripe.txt",
                               user=payment.user,
                               payment=payment)

    if feature_enabled('ISSUE_TICKETS') and charge.paid:
        attach_tickets(msg, payment.user)

    mail.send(msg)
    db.session.commit()

    return redirect(url_for('.stripe_waiting', payment_id=payment.id))
コード例 #22
0
ファイル: ical.py プロジェクト: geeksareforlife/Website
    def refresh(self):
        request = requests.get(self.url)

        cal = Calendar.from_ical(request.text)
        if self.name is None:
            self.name = cal.get("X-WR-CALNAME")

        for event in self.events:
            event.displayed = False

        local_tz = pendulum.timezone("Europe/London")
        alerts = []
        uids_seen = set()
        out_of_range_event = False
        for component in cal.walk():
            if component.name == "VEVENT":
                summary = component.get("Summary")

                # postgres converts to UTC if given an aware datetime, so strip it up front
                start_dt = pendulum.instance(component.get("dtstart").dt)
                start_dt = local_tz.convert(start_dt).naive()

                end_dt = pendulum.instance(component.get("dtend").dt)
                end_dt = local_tz.convert(end_dt).naive()

                name = summary
                if summary and start_dt:
                    name = "'{}' at {}".format(summary, start_dt)
                elif summary:
                    name = "'{}'".format(summary)
                elif start_dt:
                    name = "Event at {}".format(start_dt)
                else:
                    name = len(self.events) + 1

                if not component.get("uid"):
                    alerts.append(("danger", "{} has no UID".format(name)))
                    continue

                uid = str(component["uid"])
                if uid in uids_seen:
                    alerts.append(
                        ("danger", "{} has duplicate UID {}".format(name,
                                                                    uid)))
                    continue
                uids_seen.add(uid)

                if "rrule" in component:
                    alerts.append(
                        ("warning",
                         "{} has rrule, which is not processed".format(uid)))

                # Allow a bit of slop for build-up events
                if (start_dt < event_start() - pendulum.duration(days=2)
                        and not out_of_range_event):
                    alerts.append((
                        "warning",
                        "At least one event ({}) is before the start of the event"
                        .format(uid),
                    ))
                    out_of_range_event = True

                if (end_dt > event_end() + pendulum.duration(days=1)
                        and not out_of_range_event):
                    alerts.append((
                        "warning",
                        "At least one event ({}) is after the end of the event"
                        .format(uid),
                    ))
                    out_of_range_event = True

                if start_dt > end_dt:
                    alerts.append((
                        "danger",
                        "Start time for {} is after its end time".format(uid),
                    ))
                    out_of_range_event = True

                try:
                    event = CalendarEvent.query.filter_by(source_id=self.id,
                                                          uid=uid).one()

                except NoResultFound:
                    event = CalendarEvent(uid=uid)
                    self.events.append(event)
                    if len(self.events) > 1000:
                        raise Exception("Too many events in feed")

                event.start_dt = start_dt
                event.end_dt = end_dt
                event.summary = component.get("summary")
                event.description = component.get("description")
                event.location = component.get("location")
                event.displayed = True

        self.refreshed_at = pendulum.now()

        return alerts
コード例 #23
0
ファイル: payment.py プロジェクト: emfcamp/Website
 def description(self):
     return 'EMF {} purchase'.format(event_start().year)
コード例 #24
0
ファイル: bar_training.py プロジェクト: emfcamp/Website
def get_auth_tag():
    tag = 'emf-{}-'.format(event_start().year)
    msg = b'bar-training-' + tag.encode('utf-8')
    tag += hmac.new(app.config['SECRET_KEY'].encode('utf-8'), msg, digestmod=sha256).hexdigest()
    return tag
コード例 #25
0
ファイル: ical.py プロジェクト: emfcamp/Website
    def refresh(self):
        request = requests.get(self.url)

        cal = Calendar.from_ical(request.text)
        if self.name is None:
            self.name = cal.get('X-WR-CALNAME')

        for event in self.events:
            event.displayed = False

        local_tz = pendulum.timezone('Europe/London')
        alerts = []
        uids_seen = set()
        out_of_range_event = False
        for component in cal.walk():
            if component.name == 'VEVENT':
                summary = component.get('Summary')

                # postgres converts to UTC if given an aware datetime, so strip it up front
                start_dt = pendulum.instance(component.get('dtstart').dt)
                start_dt = local_tz.convert(start_dt).naive()

                end_dt = pendulum.instance(component.get('dtend').dt)
                end_dt = local_tz.convert(end_dt).naive()

                name = summary
                if summary and start_dt:
                    name = "'{}' at {}".format(summary, start_dt)
                elif summary:
                    name = "'{}'".format(summary)
                elif start_dt:
                    name = 'Event at {}'.format(start_dt)
                else:
                    name = len(self.events) + 1

                if not component.get('uid'):
                    alerts.append(('danger', "{} has no UID".format(name)))
                    continue

                uid = str(component['uid'])
                if uid in uids_seen:
                    alerts.append(('danger', "{} has duplicate UID {}".format(name, uid)))
                    continue
                uids_seen.add(uid)

                if 'rrule' in component:
                    alerts.append(('warning', "{} has rrule, which is not processed".format(uid)))

                # Allow a bit of slop for build-up events
                if start_dt < event_start() - pendulum.duration(days=2) and not out_of_range_event:
                    alerts.append(('warning', "At least one event ({}) is before the start of the event".format(uid)))
                    out_of_range_event = True

                if end_dt > event_end() + pendulum.duration(days=1) and not out_of_range_event:
                    alerts.append(('warning', "At least one event ({}) is after the end of the event".format(uid)))
                    out_of_range_event = True

                if start_dt > end_dt:
                    alerts.append(('danger', "Start time for {} is after its end time".format(uid)))
                    out_of_range_event = True


                try:
                    event = CalendarEvent.query.filter_by(source_id=self.id, uid=uid).one()

                except NoResultFound:
                    event = CalendarEvent(uid=uid)
                    self.events.append(event)
                    if len(self.events) > 1000:
                        raise Exception("Too many events in feed")

                event.start_dt = start_dt
                event.end_dt = end_dt
                event.summary = component.get('summary')
                event.description = component.get('description')
                event.location = component.get('location')
                event.displayed = True

        self.refreshed_at = pendulum.now()

        return alerts
コード例 #26
0
ファイル: payment.py プロジェクト: praxeology/Website
 def description(self):
     return 'EMF {} purchase'.format(event_start().year)