def history_all(): query = request.json Source = User.alias() Target = User.alias() history = Event.select( Event.id, Event.source, Event.target, Event.type, Event.amount, Event.created_at, Source.name.alias('source_name'), Target.name.alias('target_name')).join( Source, on=(Event.source == Source.id)).switch(Event).join( Target, on=(Event.target == Target.id)).switch(Event) # Process Query Parameters history = process_history_query(history, query) # Order By order_by = Event.created_at.desc() if 'sort' in query and query['sort'] is not None: field = query['sort']['field'] if 'field' in query[ 'sort'] else 'created_at' if field == 'source': field = 'source_name' elif field == 'target': field = 'target_name' order_by = SQL('%s %s' % (field, query['sort']['direction'])) history = history.order_by(order_by) # Get Result Count count = history.count() # Paginate page = 1 limit = 10 if 'page' in query and query['page'] is not None: page = query['page'] if 'limit' in query and query['limit'] is not None: limit = query['limit'] history = history.paginate(page, limit) # Query and return as dictionary history = history.dicts() # Process results events = [] for event in history: event['type'] = event['type'] if event['type'] != '' else 'other' events.append(event) result = {'history': events, 'count': count} return Response(json.dumps(result, cls=Encoder, use_decimal=True), mimetype='application/json')
def userNameAction(id): if request.method == 'GET': try: user = User.get_user(id, include_points=True) except DoesNotExist: abort(404) return Response(json.dumps(user, cls=Encoder), mimetype='application/json') elif request.method == 'PUT': if not current_user.elder: abort(403) data = request.json data['settings'] = json.dumps( data['settings']) if 'settings' in data else '{}' user = User(**data) user.save() return jsonify(success=1) elif request.method == 'DELETE': if not current_user.elder: abort(403) try: user = User.get(User.id == id) user.delete_instance() except DoesNotExist: abort(404) return jsonify(success=1)
def history_by_source(): query = request.json Source = User.alias() Target = User.alias() history = Event.select( Event.id, Event.source, Source.name.alias('source_name'), fn.Sum(Event.amount).alias('amount') ).join( Source, on=(Event.source == Source.id) ).switch(Event) # Group by Giver history = history.group_by(Event.source) # Process Query Parameters history = process_history_query(history, query) # Order By history = history.order_by(SQL('amount DESC')) # Get Result Count count = history.count() # Paginate page = 1 limit = 5 if 'page' in query and query['page'] is not None: page = query['page'] if 'limit' in query and query['limit'] is not None: limit = query['limit'] history = history.paginate(page, limit) # Query and return as dictionary history = history.dicts() # Process results events = [] for event in history: events.append(event) result = { 'history': events, 'count': count } return Response(json.dumps(result, cls=Encoder, use_decimal=True), mimetype='application/json')
def get_points(week=False): points = {} users = User.get_users() for source in users: sourceUser = users[source] if not sourceUser: continue if sourceUser['disabled']: continue events = Event.get_events(source, False, week) for event in events: target = event['user'] targetUser = User.get_user(target) if not targetUser: continue if targetUser['disabled']: continue if source not in points: points[source] = { 'givenTotal': 0, 'receivedTotal': 0, 'given': {}, 'received': {}, } amount = int(event['amount']) if event['type'] == 'give': points[source]['givenTotal'] += amount if target not in points[source]['given']: points[source]['given'][target] = 0 points[source]['given'][target] += amount else: points[source]['receivedTotal'] += amount if target not in points[source]['received']: points[source]['received'][target] = 0 points[source]['received'][target] += amount return points
def history_by_source(): query = request.json Source = User.alias() Target = User.alias() history = Event.select(Event.id, Event.source, Source.name.alias('source_name'), fn.Sum(Event.amount).alias('amount')).join( Source, on=(Event.source == Source.id)).switch(Event) # Group by Giver history = history.group_by(Event.source) # Process Query Parameters history = process_history_query(history, query) # Order By history = history.order_by(SQL('amount DESC')) # Get Result Count count = history.count() # Paginate page = 1 limit = 5 if 'page' in query and query['page'] is not None: page = query['page'] if 'limit' in query and query['limit'] is not None: limit = query['limit'] history = history.paginate(page, limit) # Query and return as dictionary history = history.dicts() # Process results events = [] for event in history: events.append(event) result = {'history': events, 'count': count} return Response(json.dumps(result, cls=Encoder, use_decimal=True), mimetype='application/json')
def eventIdAction(id): if request.method == 'DELETE': try: event = Event.get(Event.id == id) event.delete_instance() except DoesNotExist: abort(404) return jsonify(success=1) elif request.method == 'PUT': data = request.json data['source'] = data['source']['id'] data['target'] = data['target']['id'] data.pop('type', None) if data['source'] != current_user.id and current_user.elder == 0: abort(403) target = None try: target = User.get(User.id == data['target']) except DoesNotExist: abort(403) if target.disabled and current_user.elder == 0: abort(403) data['amount'] = max(min(current_user.max_points, data['amount']), 1) event = Event(**data) event.save() return jsonify(success=1) abort(404)
def load_user(id): from chalicepoints.models.user import User try: return User.get(User.id == id) except: return None
def matrixModeAction(mode): points = Point.get_points() users = User.get_users() names = users.keys() names.sort() if mode == 'received': matrix = [] for user in names: entry = [] for otherUser in names: value = 0 if user in points and otherUser in points[user]['received']: value = points[user]['received'][otherUser] entry.append(value) matrix.append(entry) else: matrix = [] for user in names: entry = [] for otherUser in names: value = 0 if user in points and otherUser in points[user]['given']: value = points[user]['given'][otherUser] entry.append(value) matrix.append(entry) return Response(json.dumps(matrix), mimetype='application/json')
def digest_weekly(): history = Event.select() now = datetime.now().date() dow = now.weekday() start_delta = timedelta(days=dow) start_date = now - start_delta start_text = start_date.strftime('%b %-d, %Y') end_delta = timedelta(days=6 - dow) end_date = now + end_delta end_text = end_date.strftime('%b %-d, %Y') history = history.where(Event.created_at >= start_date) history = history.where(Event.created_at <= end_date) history = history.order_by(Event.created_at.desc()) events = [] for event in history: event.type = Event.types[event.type] events.append(event) recipients = User.get_digest_weekly() text_body = render_template('digest_weekly.txt', events=events, start_date=start_text, end_date=end_text, base_url=app.config['SITE_URL']) html_body = render_template('digest_weekly.html', events=events, start_date=start_text, end_date=end_text, base_url=app.config['SITE_URL']) send_email('[CHALICEPOINTS] Weekly Digest', ('Chalice Points', app.config['SENDER_EMAIL']), recipients, text_body, html_body, ('Chalice Points', app.config['REPLY_EMAIL']))
def digest_monthly(): history = Event.select() now = datetime.now().date() start_date = now.replace(day = 1) start_text = start_date.strftime('%b %-d, %Y') end_date = now.replace(day = monthrange(now.year, now.month)[1]) end_text = end_date.strftime('%b %-d, %Y') history = history.where(Event.created_at >= start_date) history = history.where(Event.created_at <= end_date) history = history.order_by(Event.created_at.desc()) events = [] for event in history: event.type = Event.types[event.type] events.append(event) recipients = User.get_digest_monthly() text_body = render_template('digest_monthly.txt', events=events, start_date=start_text, end_date=end_text, base_url=app.config['SITE_URL']) html_body = render_template('digest_monthly.html', events=events, start_date=start_text, end_date=end_text, base_url=app.config['SITE_URL']) send_email('[CHALICEPOINTS] Monthly Digest', ('Chalice Points', app.config['SENDER_EMAIL']), recipients, text_body, html_body, ('Chalice Points', app.config['REPLY_EMAIL']))
def do_get_events(): events = {} users = User.get_users() for name in users: events[name] = Event.get_events(name) return jsonify(success=1, events=events)
def userNameAction(id): if request.method == 'GET': try: user = User.get_user(id, include_points=True) except DoesNotExist: abort(404) return Response(json.dumps(user, cls=Encoder), mimetype='application/json') elif request.method == 'PUT': if not current_user.elder: abort(403) data = request.json data['settings'] = json.dumps(data['settings']) if 'settings' in data else '{}' user = User(**data) user.save() return jsonify(success=1) elif request.method == 'DELETE': if not current_user.elder: abort(403) try: user = User.get(User.id == id) user.delete_instance() except DoesNotExist: abort(404) return jsonify(success=1)
def userTimelineAction(id): try: user = User.get(User.id == id) except DoesNotExist: abort(404) events = user.get_timeline() return Response(json.dumps(events, cls=Encoder), mimetype='application/json')
def mergeUser(id, target): Event.update(source=target).where(Event.source == id).execute() Event.update(target=target).where(Event.target == id).execute() try: user = User.get(User.id == id) user.delete_instance() except DoesNotExist: abort(404) return jsonify(success=1)
def eventAction(): data = request.json data.pop('id', None) if data['target'] == current_user.id: abort(403) target = User() try: target = User.get(User.id == data['target']) except DoesNotExist: abort(403) if target.disabled: abort(403) data['amount'] = max(min(current_user.max_points, int(data['amount'])), 1) event = Event(**data) event.source = current_user.id event.add() return jsonify(success=1)
def userAction(include_self=True): user_dict = User.get_users() user_names = user_dict.keys() user_names.sort() users = [] for name in user_names: if name == current_user.name and not include_self: continue entry = user_dict[name] users.append(entry) return Response(json.dumps(users), mimetype='application/json')
def load_user(id): from chalicepoints.models.user import User user_json = r.hget('openid', id) if user_json: u = json.loads(user_json) user = User.get_instance(u['email']) if not user: return None user.set_id(id) return user else: return None
def after_login(response): from chalicepoints.models.user import User email = string.lower(response.email) user = User.get_instance(email) if not user: abort(401) user.set_id(response.identity_url) user_json = user.to_json() r.hset('openid', response.identity_url, user_json) login_user(user) return redirect(url_for('site.index'))
def get_timeline(): events = {} users = User.get_users() for name in users: user_events = Event.get_events(name) for event in user_events: if event['type'] != 'give': continue timestamp = float(datetime.strptime(event['date'], '%Y-%m-%dT%H:%M:%SZ').strftime('%s')) while timestamp in events: timestamp += 0.001 event['source'] = name events[timestamp] = event timeline = OrderedDict(sorted(events.items(), key=lambda t: -t[0])) return timeline
def userNameAction(name): name = name.encode('ascii') if name == 'list': return userAction(False) users = User.get_users() if name not in users: abort(404) user = users[name] user['events'] = Event.get_events(name) user['given'] = 0 user['received'] = 0 points = Point.get_points() if name in points: user['given'] = points[name]['givenTotal'] user['received'] = points[name]['receivedTotal'] return Response(json.dumps(user), mimetype='application/json')
def add_event(source, target, eventDate, amount, message): if source == target: return False user = User.get_user(source) if not user: return False if user['disabled']: return False if amount > user['max_points']: amount = user['max_points'] sourceKey = Event.to_key(source) givenKey = 'cpEvents' + sourceKey given = { 'type': 'give', 'user': target, 'amount': amount, 'date': eventDate, 'message': message, } chalicepoints.r.lpush(givenKey, json.dumps(given)) targetKey = Event.to_key(target) receivedKey = 'cpEvents' + targetKey received = { 'type': 'receive', 'user': source, 'amount': amount, 'date': eventDate, 'message': message, } chalicepoints.r.lpush(receivedKey, json.dumps(received)) Event.update_hipchat(source, target, amount, message)
def do_post_events(data): source = current_user.name target = data['target'].encode('ascii') amount = max(min(5, data['amount']), 1) if target == current_user.name: abort(403) users = User.get_user_names() if target not in users: abort(403) # Hellban Alex from Giving more than 1 Point (for now) if source == 'Alex Lopes': amount = 1 message = 'None' if 'message' in data and data['message']: message = data['message'].encode('ascii') eventDate = datetime.utcnow().strftime('%Y-%m-%dT%H:%M:%SZ') Event.add_event(source, target, eventDate, amount, message) return jsonify(success=1)
def userAction(): users = User.get_users() return Response(json.dumps(users, cls=Encoder), mimetype='application/json')
def history_all(): query = request.json Source = User.alias() Target = User.alias() history = Event.select( Event.id, Event.source, Event.target, Event.type, Event.amount, Event.created_at, Source.name.alias('source_name'), Target.name.alias('target_name') ).join( Source, on=(Event.source == Source.id) ).switch(Event).join( Target, on=(Event.target == Target.id) ).switch(Event) # Process Query Parameters history = process_history_query(history, query) # Order By order_by = Event.created_at.desc() if 'sort' in query and query['sort'] is not None: field = query['sort']['field'] if 'field' in query['sort'] else 'created_at' if field == 'source': field = 'source_name' elif field == 'target': field = 'target_name' order_by = SQL('%s %s' % (field, query['sort']['direction'])) history = history.order_by(order_by) # Get Result Count count = history.count() # Paginate page = 1 limit = 10 if 'page' in query and query['page'] is not None: page = query['page'] if 'limit' in query and query['limit'] is not None: limit = query['limit'] history = history.paginate(page, limit) # Query and return as dictionary history = history.dicts() # Process results events = [] for event in history: event['type'] = event['type'] if event['type'] != '' else 'other' events.append(event) result = { 'history': events, 'count': count } return Response(json.dumps(result, cls=Encoder, use_decimal=True), mimetype='application/json')
def auth(): session_csrf_token = session.pop('csrf_token', None) csrf_token = request.args.get('state', None) code = request.args.get('code') if not session_csrf_token or not csrf_token: raise WebException('Missing CSRF token') if not code: raise WebException('Missing authorization code') if csrf_token != session_csrf_token: raise WebException('CSRF Token Mismatch') flow = OAuth2WebServerFlow( client_id=current_app.config['GOOGLE_API_CLIENT_ID'], client_secret=current_app.config['GOOGLE_API_CLIENT_SECRET'], scope=current_app.config['GOOGLE_API_SCOPE'], redirect_uri=current_app.config['SITE_URL'] + '/auth') credentials = flow.step2_exchange(code) http = credentials.authorize(httplib2.Http()) id_token = credentials.id_token if not validate_id_token(id_token): raise WebException('Invalid ID Token') (headers, content) = http.request('https://www.googleapis.com/oauth2/v3/userinfo', 'GET') if headers['status'] != '200': raise WebException('Unable to retrieve user info', 500) try: userinfo = json.loads(content) except ValueError: raise WebException('Unable to parse user info', 500) email = string.lower(userinfo['email']) try: user = User.get(User.email == email) user.name = userinfo['name'] user.save() except DoesNotExist: user = User() user.name = userinfo['name'] user.email = email user.api_key = str(uuid4()) user.gravatar = hashlib.md5(email.strip().lower()).hexdigest() user.url = id_token['sub'] user.save() if not user: raise WebException('Unable to upsert user', 500) login_user(user) return redirect(url_for('site.index'))
def winners(): totals = {} leaders = {} highest = {} current_week = datetime.now().strftime('%U %y 0') current_date = datetime.strptime(current_week, '%U %y %w').strftime('%Y-%m-%dT%H:%M:%S') users = User.get_users() for source in users: events = Event.get_events(source) for event in events: target = event['user'] amount = int(event['amount']) week = datetime.strptime(event['date'], '%Y-%m-%dT%H:%M:%SZ').strftime('%U %y 0') date = datetime.strptime(week, '%U %y %w').strftime('%Y-%m-%dT%H:%M:%S') if not date in totals: totals[date] = {} if not source in totals[date]: totals[date][source] = { 'given': 0, 'received': 0, } if not target in totals[date]: totals[date][target] = { 'given': 0, 'received': 0, } if event['type'] == 'give': totals[date][source]['given'] += amount totals[date][target]['received'] += amount for date in totals: leaders[date] = { 'date': date, 'current': 0, 'given': [], 'received': [], } if current_date == date: leaders[date]['current'] = 1 highest[date] = { 'given': 0, 'received': 0, } for person in totals[date]: if totals[date][person]['given'] > highest[date]['given']: leaders[date]['given'] = [{ 'name': person, 'amount': totals[date][person]['given'], }] highest[date]['given'] = totals[date][person]['given'] elif totals[date][person]['given'] == highest[date]['given']: leaders[date]['given'].append({ 'name': person, 'amount': totals[date][person]['given'], }) if totals[date][person]['received'] > highest[date]['received']: leaders[date]['received'] = [{ 'name': person, 'amount': totals[date][person]['received'], }] highest[date]['received'] = totals[date][person]['received'] elif totals[date][person]['received'] == highest[date]['received']: leaders[date]['received'].append({ 'name': person, 'amount': totals[date][person]['received'], }) return Response(json.dumps(leaders.values()), mimetype='application/json')
def userTargetsAction(): users = User.get_users(include_self=False, exclude_disabled=True) return Response(json.dumps(users, cls=Encoder), mimetype='application/json')