Пример #1
0
def get_attr(obj, spec):
    # extract data for attr spec from populated database object
    # e.g. get_attr(member, 'address.line_1')
    # or get_attr(member, 'address.country_for_mail()') - invoke a method
    if not spec:
        return ''
    if '=' == first_or_default(spec, ' '):
        return eval(spec[1:])
    attr, tail = pop_next(spec, '.')
    if '()' in attr:  # function call
        res = getattr(obj, attr.replace('()', ''))()
    elif tail and '()' in tail:  # function call
        res = getattr(obj, attr)
    elif '[]' in attr:  # list - get first
        res = first_or_default(getattr(obj, attr.replace('[]', '')), None)
    elif 'actions[' in attr:  # list - get specific
        (name, type) = attr.split('[')
        res = first_or_default([a for a in getattr(obj, name) if a.action.name == type[:-1]], None)
    elif 'payments[' in attr:  # list - get specific
        (name, type) = attr.split('[')
        res = first_or_default([a for a in getattr(obj, name) if a.type.name == type[:-1]], None)
    elif '{' in attr:  # literal - return as value
        res = attr.replace('{', '').replace('}', '')
    else:  # property
        res = getattr(obj, attr)
    if res and tail:
        res = get_attr(res, tail)
    if res and 'date' in spec and isinstance(res, datetime.date):
        res = fmt_date(res)
    return res if res is not None else ''
Пример #2
0
def update_member_payments(member, details):
    payments = []
    for payment in details['payments']:
        if payment['amount'] is None:
            continue
        item = first_or_default([p for p in member.payments if p.date == payment['date']], None)
        if item:
            item.date = payment['date']
            item.type = PaymentType(payment['pay_type'])
            item.amount = payment['amount']
            item.method = PaymentMethod(payment['method']) if payment['method'] > 0 else None
            item.comment = payment['comment']
        else:
            item = Payment(
                member_id=member.id,
                date=payment['date'],
                type=PaymentType(payment['pay_type']),
                amount=payment['amount'],
                method=PaymentMethod(payment['method']) if payment['method'] > 0 else None,
                comment=payment['comment']
            )
        payments.append(item)
    if not member.last_payment_method:
        last = first_or_default(sorted(payments, key=lambda x: x.date, reverse=True), None)
        if last:
            member.last_payment_method = last.method
    else:
        last = PaymentMethod.from_value(details['payment_method'])
        if member.last_payment_method != last:
            member.last_payment_method = last
    member.payments = payments
Пример #3
0
def get_next_event(date=datetime.date.today()):
    start = date + datetime.timedelta(days=1)
    end = datetime.date(date.year, 12, 31)
    next = first_or_default(get_events_in((start, end)), None)
    if not next:
        end = datetime.date(date.year + 1, 12, 31)
        next = first_or_default(get_events_in((start, end)), None)
    return next
Пример #4
0
def save_event_details(event_id, details):
    event_type = details['event_type']
    if event_id > 0:
        event = get_event(event_id)
    else:
        event = Event(type=event_type)
        db_session.add(event)

    event.venue_id = details['venue_id']
    event.date = details['date']
    event.trophy_id = details['trophy_id']
    event.course_id = details['course_id']
    event.organiser_id = details['organiser_id']
    event.member_price = details['member_price']
    event.guest_price = details['guest_price']
    event.booking_start = details['start_booking']
    event.booking_end = details['end_booking']
    event.max = details['max']
    event.note = details['note']

    if event_type == EventType.wags_vl_event:
        schedule = []
        for row in details['schedule']:
            if row['time'] is None:
                continue
            item = first_or_default([s for s in event.schedule if s.time == row['time']], None)
            if item:
                item.time = row['time']
                item.text = row['text']
            else:
                item = Schedule(event_id=event_id, time=row['time'], text=row['text'])
            schedule.append(item)
        event.schedule = sorted(schedule)

    if event_type in [EventType.wags_tour, EventType.minotaur]:
        tour_events = []
        all_courses = get_all_courses()
        for row in details['tour_schedule']:
            date = row['date']
            course_id = row['course']
            if course_id > 0:
                venue_id = all_courses[course_id].venue_id
            else:
                venue_id = event.venue_id
            item = first_or_default([s for s in event.tour_events if s.date == date], None)
            if item:
                item.course_id = course_id
                item.venue_id = venue_id
            #
            else:
                item = get_event_for_course_and_date(date, course_id)
                item.type = EventType.wags_vl_event
                item.tour_event_id = event_id
                item.venue_id = venue_id
            tour_events.append(item)
        event.tour_events = tour_events
    db_session.commit()
    return event.id
Пример #5
0
def save_event_result(event_id, result):
    event = get_event(event_id)
    scores = []
    delete = {s.id: True for s in event.scores}
    for row in result.rows():
        score = first_or_default([s for s in event.scores if s.player_id == int(row['player_id'])], None)
        if score:
            score.position = row['position']
            score.shots = row['shots']
            score.points = row['points']
            if 'card' in row:
                score.card = row['card']
            if score.id in delete:
                delete[score.id] = False
        else:
            score = Score(event_id=event_id,
                          player_id=row['player_id'],
                          position=row['position'],
                          shots=row['shots'],
                          points=row['points'],
                          card=row.get('card', None)
                          )
        scores.append(score)
    for score in event.scores:
        if delete.get(score.id, False):
            db_session.delete(score)
    if len(result.data) > 0:
        update_event_winner(event, result)
    else:
        event.winner_id = event.average_score = None
    event.scores = scores
    if event.tour_event:
        if event.tour_event.trophy and event in event.tour_event.tour_events:
            update_tour_winner(event.tour_event)
    db_session.commit()
    def book_event(self, event_id, member_id):
        errors = self.errors
        if len(errors) > 0:
            return False
        booking = get_booking(event_id, member_id)
        with suspend_flush():
            booking.date = datetime.date.today()
            booking.playing = self.attend.data
            booking.comment = self.comment.data if len(
                self.comment.data) > 0 else None
            guests = []
            if booking.playing:
                for guest in self.guests:
                    name = string.capwords(guest.guest_name.data)
                    if len(name) > 0:
                        obj = first_or_default(
                            [g for g in booking.guests if g.name == name],
                            Guest(name=name, booking=booking))
                        hcap = parse_float(guest.handicap.data, 28.0)
                        known_player = get_player_by_name(name)
                        if known_player:
                            state = known_player.state_as_of(booking.date)
                            if state.status == PlayerStatus.member:
                                hcap = state.handicap
                        obj.handicap = hcap
                        guests.append(obj)
            booking.guests = guests
            app.logger.info(booking.debug_info())
        save_booking(booking)

        return self.confirm_booking(event_id, member_id)
Пример #7
0
def select_fields_to_update(select_fields, default_table):
    updates = {}
    for field in select_fields:
        if field.data:
            field_name = field.db_map
            if field.type == 'MySelectField':
                if field.data in [
                        c[0].value for c in field.choices
                        if not isinstance(c[0], int)
                ]:
                    value = field.data
                else:
                    value = [
                        c[1] for c in field.choices if c[0] == field.data
                    ][0]
                    if '(' in value:
                        value = value[:value.find('(') - 1]
                    value = first_or_default(
                        [v[0] for v in field.choices if v[1] == value], None)
            else:
                value = field.data
            func = None
            # if isinstance(value, (int, float)) or len(value) > 0:
            #     if '.' in field_name:
            #         a = field_name.split('.')
            #         if len(a) == 2:
            #             table, column = a
            #         if len(a) == 3:
            #             table, column, func = a
            #     else:
            #         table, column = default_table, field_name
            updates[field_name] = value
    return updates
Пример #8
0
def select_fields_to_query(select_fields, default_table):
    query_clauses = []
    for field in select_fields:
        if field.data:
            if field.type == 'MySelectField':
                if field.data in [
                        c[0].value for c in field.choices
                        if not isinstance(c[0], int)
                ]:
                    condition, value = '=', field.data
                else:
                    v = [c[1] for c in field.choices if c[0] == field.data][0]
                    condition, value = split_condition_and_value(v)
                    value = first_or_default(
                        [v[0] for v in field.choices if v[1] == value], None)
            else:
                condition, value = split_condition_and_value(field.data)
            func = None
            if isinstance(value, (int, float)) or len(value) > 0:
                field_name = field.db_map
                if '.' in field_name:
                    a = field_name.split('.')
                    if len(a) == 2:
                        table, column = a
                    if len(a) == 3:
                        table, column, func = a
                        if '()' not in func:
                            table, column, func = column, func, None
                else:
                    table, column = default_table, field_name
                query_clauses.append(
                    (table, column, value, condition, func, field.name))
    query_clauses = limit_status_and_lapsed_date_by_access(query_clauses)
    return query_clauses
Пример #9
0
 def _test_etl_bookings(self):
     year = '2018'
     event = 'event14.csv'
     event_id = 381
     booking_file = os.path.join(TestData.data_location, year, event)
     old = Table(*get_all_records(booking_file))
     for old_booking in old.rows():
         member_name = old_booking['name']
         member = get_member_by_name(member_name)
         booking = get_booking(event_id, member.id)
         booking.date = parse_date(old_booking['date'], reverse=True)
         booking.playing = old_booking['playing'] == '1'
         booking.comment = old_booking['comment']
         number = int(old_booking['number'])
         guests = []
         for count in range(1, number):
             name = old_booking['guest{}'.format(count)]
             hcap = parse_float(old_booking['guest{}_hcap'.format(count)])
             guest = first_or_default([g for g in booking.guests if g.name == name], Guest(name=name, booking=booking))
             known_player = get_player_by_name(name)
             if known_player:
                 state = known_player.state_as_of(booking.date)
                 if state.status == PlayerStatus.member:
                     hcap = state.handicap
             guest.handicap = hcap
             guests.append(guest)
         booking.guests = guests
         save_booking(booking, True)
     self.assertEqual(1, 1)
Пример #10
0
def renew_recent_resumers():
    resume_date = fmt_date(datetime.date(current_year_end().year, 4, 1))
    end_date = fmt_date(datetime.date(current_year_end().year, 8, 1))
    query_clauses = [
        ('Payment', 'date', resume_date, '>=', None),
        ('Payment', 'type', PaymentType.dues, '=', None),
        ('Member', 'end_date', end_date, '=', None),
    ]
    members = get_members_for_query(query_clauses)
    count = 0
    message = []
    for member in members:
        if member.is_recent_resume():
            member.end_date = new_end_date
            item = first_or_default([
                a for a in member.actions if a.action == MemberAction.card
                and a.status == ActionStatus.open
            ], None)
            if not item:
                item = Action(member_id=member.id,
                              date=datetime.date.today(),
                              action=MemberAction.card,
                              comment='auto renew recent resumer',
                              status=ActionStatus.open)
                member.actions.append(item)
            message += [member.dt_number()]
            save_member(member)
            count += 1
    return '\n'.join(['{} members updated'.format(count)] + message)
Пример #11
0
 def populate_trophy(self, trophy_id):
     trophy = get_trophy(trophy_id)
     self.trophy_name.data = trophy.name
     self.image_url.data = url_for_html('pictures', 'trophies',
                                        trophy.name.lower() + '.jpg')
     extra_file = 'user/extra/' + trophy.name.lower() + '.htm'
     if template_exists(extra_file):
         self.extra.data = extra_file
     hist = trophy.events
     for event in hist:
         tour = first_or_default([
             e for e in hist if e.date.year == event.date.year
             and e.type == EventType.wags_tour
         ], None)
         if event.date < datetime.date.today() \
                 and ((event.type == EventType.wags_vl_event and not tour) \
                      or (event.type == EventType.wags_tour and tour)):
             item_form = TrophyItemForm()
             item_form.venue = event.venue.name
             item_form.date = fmt_date(event.date)
             if event.winner:
                 item_form.winner = event.winner.full_name()
                 if event.type == EventType.wags_vl_event:
                     item_form.score = event.winner.score_for(
                         event.id).points
                     item_form.average = event.average_score
                 else:
                     item_form.score = item_form.average = ''
             else:
                 item_form.winner = item_form.score = item_form.average = ''
             self.winners.append_entry(item_form)
Пример #12
0
def get_answer(member, question, single=True, other=False):
    if other:
        ret = [q.other for q in member.qandas if q.question_id == question]
    else:
        ret = [q.answer for q in member.qandas if q.question_id == question]
    if single:
        return first_or_default(ret, None)
    else:
        return ret
Пример #13
0
 def member_status_at_renewal(self):
     status = self.status
     if status not in [MemberStatus.life, MemberStatus.plus]:
         upgrade = first_or_default([
             a for a in self.actions
             if a.action == MemberAction.upgrade and a.status ==
             ActionStatus.open and a.comment == 'Upgrade to DT plus'
         ], None)
         if upgrade:
             status = MemberStatus.plus
     return status
Пример #14
0
def competition_scratch_score(event):
    position = 2
    while position != 0:
        candidates = [s for s in event.scores if s.position == position]
        if any([
                c for c in candidates if c.player.state_as_of(
                    event.date).status == PlayerStatus.member
        ]):
            scratch = first_or_default([c.points for c in candidates], 0) - 1
            position = 0
        else:
            position += 1
    return scratch
Пример #15
0
def update_member_comments(member, details):
    comments = []
    for comment in details['comments']:
        if comment['comment'] in [None, '']:
            continue
        item = first_or_default([c for c in member.comments if c.date == comment['date']], None)
        if item:
            item.comment = comment['comment']
        else:
            item = Comment(
                member_id=member.id,
                date=comment['date'],
                comment=comment['comment']
            )
        comments.append(item)
    member.comments = comments
Пример #16
0
def save_event_score(event_id, player_id, position, card, shots, points):
    event = get_event(event_id)
    score = first_or_default([s for s in event.scores if s.player_id == player_id], None)
    if score:
        score.position = position
        score.card = card
        score.shots = shots
        score.points = points
    else:
        score = Score(event_id=event_id,
                      player_id=player_id,
                      position=position,
                      shots=shots,
                      points=points,
                      card=card)
        event.scores.append(score)
    db_session.commit()
Пример #17
0
def save_handicaps(new_table):
    if len(new_table.data) == 0:
        return
    players = set(new_table.get_columns('player_id'))
    dates = set(new_table.get_columns('date'))
    current = db_session.query(Handicap).filter(Handicap.date.in_(dates), Handicap.player_id.in_(players)).all()
    for new in new_table.rows():
        hcap = first_or_default([h for h in current if h.player_id == new['player_id'] and h.date == new['date']], None)
        if hcap:
            if (hcap.handicap == new['handicap'] and hcap.status == new['status']):
                continue
            hcap.handicap = new['handicap']
            hcap.status = new['status']
        else:
            hcap = Handicap(player_id=new['player_id'],
                            date=new['date'],
                            handicap=new['handicap'],
                            status=new['status'])
        db_session.add(hcap)
    db_session.commit()
Пример #18
0
def update_member_actions(member, details):
    actions = []
    for action in details['actions']:
        if action['action'] == 0:
            continue
        item = first_or_default([a for a in member.actions if a.date == action['date']], None)
        if item:
            item.date = action['date']
            item.action = MemberAction(action['action'])
            item.comment = action['comment']
            item.status = ActionStatus(action['status'])
        else:
            item = Action(
                member_id=member.id,
                date=action['date'],
                action=MemberAction(action['action']),
                comment=action['comment'],
                status=ActionStatus(action['status'])
            )
        actions.append(item)
    member.actions = actions
Пример #19
0
def query_fields_action(query_clauses):
    action = first_or_default([q for q in query_clauses if q[1] == 'action'],
                              None)
    if action:
        action = MemberAction.from_value(action[2]).name
    return action
Пример #20
0
 def is_upgrade(self):
     return self.is_adult() and \
            first_or_default(self.actions, MemberAction.other) == MemberAction
Пример #21
0
def update_member_renewal(member, details):
    #handle action
    item = first_or_default(
        [a for a in member.actions if a.action == MemberAction.upgrade and a.status == ActionStatus.open], None)
    if details['upgrade']:
        date = datetime.date.today()
        comment = 'Upgrade to DT plus'
        if item:
            item.date = date
            item.action = MemberAction.upgrade
            item.comment = comment
            item.status = ActionStatus.open
        else:
            item = Action(
                member_id=member.id,
                date=date,
                action=MemberAction.upgrade,
                comment=comment,
                status=ActionStatus.open
            )
            member.actions.append(item)
    elif item:
        member.actions.remove(item)
    #handle payment
    if member.status == MemberStatus.plus:
        dues = member.plus_dues()
    else:
        dues = member.base_dues() + (member.upgrade_dues() if details['upgrade'] else 0)
    date = datetime.date.today()
    item = first_or_default([p for p in member.payments if p.type == PaymentType.pending], None)
    if member.status != MemberStatus.life:
        payment_method = PaymentMethod.from_value(details['payment_method']) if details['payment_method'] else None
        if details['upgrade'] and (member.is_recent_new() or member.is_recent_resume()):
            item = None
            dues = member.upgrade_dues()
            payment_comment = 'upgrade only'
        else:
            payment_comment = 'renewal payment due'
        if item:
            item.date = date
            item.type = PaymentType.pending
            item.amount = dues
            item.method = payment_method
            item.comment = payment_comment
        elif dues > 0:
            item = Payment(
                member_id=member.id,
                date=date,
                type=PaymentType.pending,
                amount=dues,
                method=payment_method,
                comment=payment_comment
            )
            member.payments.append(item)

    if not details['comment'] in [None, '']:
        date = datetime.date.today()
        item = first_or_default([c for c in member.comments if c.date == date], None)
        if item:
            item.comment = details['comment']
        else:
            item = Comment(
                member_id=member.id,
                date=date,
                comment=details['comment']
            )
            member.comments.append(item)
Пример #22
0
def update_member_payment(rec, payment_method, save=True):
    # rec is line of payments file with keys id, date, amount and note
    message = []
    number = int(rec['id'][4:])
    date = parse_date(rec['date'], sep='/', reverse=True)
    amount = float(rec['amount'])
    member = get_member(number)
    pending = first_or_default([
        p for p in member.payments
        if p.type == PaymentType.pending and p.method == payment_method
    ], None)
    payment_comment = 'from payments file'
    if pending:
        comment = ['']
        if pending.amount != amount:
            comment = [
                "Expected amount {}, got {}".format(pending.amount, amount)
            ]
            message += comment
        pending.type = PaymentType.dues
        pending.date = date
        pending.amount = amount
        pending.comment = payment_comment + ' ' + comment[0]
    else:
        dues = first_or_default([
            p for p in member.payments
            if p.type == PaymentType.dues and p.method == payment_method
        ], None)
        if dues and dues.amount == amount and dues.date == date and dues.comment.startswith(
                payment_comment):
            message += ['Payment already processed']
            return message
        else:
            message += ["no pending payment: adding one"]
            pending = Payment(member_id=member.id,
                              date=date,
                              amount=amount,
                              type=PaymentType.dues,
                              method=payment_method,
                              comment=payment_comment)
            member.payments.append(pending)
    action = first_or_default([
        a for a in member.actions
        if a.action == MemberAction.card and a.status == ActionStatus.open
    ], None)
    if not action:
        action = Action(member_id=member.id,
                        date=datetime.date.today(),
                        action=MemberAction.card,
                        status=ActionStatus.open,
                        comment=payment_comment)
        member.actions.append(action)
    upgrade = amount in [20.0, 30.0, 45.0
                         ] and member.status != MemberStatus.plus
    action = first_or_default([
        a for a in member.actions
        if a.action == MemberAction.upgrade and a.status == ActionStatus.open
    ], None)
    if action:
        if upgrade:
            member.status = MemberStatus.plus
            action.status = ActionStatus.closed
        # else:
        #     message += ['expected an upgrade payment, upgrade action removed']
        #     member.actions.remove(action)
    else:
        if upgrade:
            action = Action(member_id=member.id,
                            date=date,
                            action=MemberAction.upgrade,
                            status=ActionStatus.closed,
                            comment=payment_comment)
            member.actions.append(action)
    member.end_date = new_end_date
    member.last_payment_method = payment_method
    if save:
        save_member(member)
    return message
Пример #23
0
def save_member(member_id, data):
    new_member = member_id == 0
    name = data['first_name'] + ' ' + data['last_name']
    orig_name = data['orig_name']
    handicap = data['handicap']
    status = data['status']
    player_id = get_player_id(name if new_member else orig_name)
    date = data['as_of'] or data['accepted']
    access = data['access']

    # set player status and handicap
    if status in [MemberStatus.full_member, MemberStatus.overseas_member]:
        player_status = PlayerStatus.member
    else:
        player_status = PlayerStatus.ex_member
    if player_id == 0:
        player = add_player(name, handicap, player_status, date, commit=False)
    else:
        player = get_player(player_id)
        if name != orig_name:
            player.first_name = data['first_name']
            player.last_name = data['last_name']

        if handicap != data['orig_handicap'] or status.value != data['orig_status']:
            state = first_or_default([s for s in player.handicaps if s.date == date], None)
            if state:
                state.handicap = handicap
                state.status = player_status
            else:
                state = Handicap(date=date, status=player_status, handicap=handicap)
                player.handicaps.append(state)
    # create/update member
    if new_member:
        contact = Contact(
            email=data['email'],
            address=data['address'],
            post_code=data['post_code'],
            phone=data['phone']
        )
        member = Member(
            player=player,
            contact=contact,
            status=status,
            proposer_id=data['proposer_id'],
            accepted=data['accepted']
        )
    else:
        member = get_member(member_id)
        member.contact.email = data['email']
        member.contact.address = data['address']
        member.contact.post_code = data['post_code']
        member.contact.phone = data['phone']
        member.player = player
        member.status = status
        member.proposer_id = data['proposer_id']
    if status.value != data['orig_status']:
        if status == MemberStatus.full_member:
            member.accepted = date
        elif status in (MemberStatus.ex_member, MemberStatus.rip):
            member.resigned = date
    else:
        member.accepted = data['accepted']
    if member.user:
        if not access in [r.role for r in member.user.roles]:
            member.user.roles.append(Role(user_id=member.user.id, role=access))
    db_session.commit()
Пример #24
0
def choice_name(choices, find_number):
    return first_or_default([name for (number, name) in choices if number == find_number], None)
Пример #25
0
def choice_number(choices, find_name):
    l = len(find_name)
    find_name = find_name.lower()
    return first_or_default([number for (number, name) in choices if name.lower()[:l] == find_name], None)