def start_subscription(user): if not user.payment: raise APIError( "Cannot start subscription for user without a credit card: %s" % user.id) user.payment.start() Session.commit()
def delete(user_id): # TODO: user_id -> user u = model.User.get(user_id) if not u: raise APIError('Invalid user: %s' % user_id) delete_payments(u) u.delete() Session.commit()
def delete_payments(user): user.time_next_payment = None if not user.num_remaining: user.num_remaining = 0 is_free_plan = user.plan and not user.plan.price and not user.plan.features.get( 'num_emails') if is_free_plan: user.num_remaining = None if user.payment: user.payment.delete() Session.commit()
def get_user(request, required=False, joinedload=None): """ Get the current logged in User object, else None. Overrides request.features from loaded user. """ user_id = get_user_id(request, required=required) if not user_id: return q = Session.query(model.User) for p in iterate(joinedload or []): q = q.options(orm.joinedload(p)) u = q.get(user_id) if not u: request.session.pop('user_id', None) request.session.save() return get_user(request, required=required) # Try again. if u: # Override features request.features.update(u.config or {}) return u
def index(self): api.account.get_admin(self.request) q = Session.query(model.User) q = q.options(orm.joinedload_all('accounts.reports'), orm.joinedload_all('subscriptions')) q = q.order_by(model.User.id.asc()) users = q.all() self.c.active_users, self.c.inactive_users, self.c.active_trials = [], [], [] for u in users: account_reports = [a.reports for a in u.accounts] if u.is_active and (u.subscriptions or account_reports or u.payment): self.c.active_users.append(u) if u.plan_id == 'trial': self.c.active_trials.append(u) else: self.c.inactive_users.append(u) payment_info = [u for u in users if u.payment] active_customers = [ u for u in payment_info if u.payment.is_charging and u.num_remaining is None ] self.c.num_users = len(users) self.c.num_payment_info = len(payment_info) self.c.num_active_customers = len(active_customers) self.c.num_mrr = sum( (u.plan.price_monthly or 0) for u in active_customers) self.c.by_plan = groupby_count(active_customers, key=lambda u: u.plan_id) self.c.by_payment = groupby_count(payment_info, key=lambda u: u.payment.id) self.c.expiring_trials = [] for u in self.c.active_trials: num_reports = len([a.reports for a in u.accounts]) if num_reports * 2 < u.num_remaining: continue self.c.expiring_trials.append(u) q = Session.query(model.ReportLog).order_by( model.ReportLog.id.desc()).limit(10) self.c.recent_reports = q.all() return self._render('admin/index.mako')
def set_plan(user, plan_id, update_subscription=None): plan = pricing.PLANS_LOOKUP.get(plan_id) if not plan: raise APIError('Invalid plan: %s' % plan_id) user.plan_id = plan_id num_remaining = plan.features.get('num_emails') if num_remaining or not user.num_remaining: user.num_remaining = num_remaining Session.commit() if update_subscription is None: # Default behaviour update_subscription = user.num_remaining is None or user.num_remaining <= 0 if update_subscription and user.payment: user.payment.start()
def get_or_create(user_id=None, email=None, service='google', token=None, display_name=None, plan_id=None, remote_id=None, remote_data=None, **create_kw): u = None q = Session.query(model.User).options(orm.joinedload(model.User.accounts)) if user_id: u = q.get(user_id) if not u: raise APIError('Invalid user: %s' % user_id) elif email: u = q.filter(model.User.email == email).first() if not u: u = model.User.create(email=email, display_name=display_name, **create_kw) set_plan(u, plan_id or 'trial') if service: # Create account account = u.get_account(service=service) if not account: account = model.Account.create(display_name=display_name, user=u, service=service, remote_id=remote_id, remote_data=remote_data) u.accounts.append(account) if token and token.get('refresh_token'): # Update token if it's a better one (with refresh). account.oauth_token = token Session.commit() return u
def set_payments(user, plan_id=None, card_token=None, metadata=None, payment_type='stripe'): if plan_id: try: set_plan(user, plan_id) except KeyError: raise APIError('Invalid plan: %s' % plan_id) p = user.payment if p and p.id != payment_type: raise APIError('Incompatible payment type user: %s' % user) if not p: p = payment.registry[payment_type](user) if p.id == 'stripe' and not card_token: # For testing log.warning('Skipping interfacing set_payments for user: %s' % user) Session.commit() return user p.set(card_token, metadata=metadata) Session.commit() if plan_id and not user.num_remaining: user.payment.start() Session.commit() return user
def user(self): u = api.account.get_admin(self.request) user_id = self.request.matchdict['id'] q = Session.query(model.User) q = q.options( orm.joinedload_all('accounts.reports.subscriptions.user')) self.c.user = q.get(user_id) q = Session.query(model.User).filter_by(invited_by_user_id=user_id) q = q.options(orm.joinedload_all('subscriptions')) self.c.invited = q.all() self.c.invited_by = None if self.c.user.invited_by_user_id: self.c.invited_by = model.User.get(self.c.user.invited_by_user_id) q = Session.query(model.ReportLog).join( model.Account).filter_by(user_id=self.c.user.id) q = q.order_by(model.ReportLog.id.desc()).limit(10) self.c.recent_reports = q.all() return self._render('admin/user.mako')
def get(id=None, email=None, token=None): if not any([id, email, token]): raise APIError('Must specify user query criteria.') q = Session.query(model.User) if id: q = q.filter_by(id=id) if email: q = q.filter_by(email=email) if token: email_token, id = token.split('-', 2) q = q.filter_by(id=int(id), email_token=email_token) return q.first()
def close_session(*args, **kwargs): from briefmetrics.model.meta import Session Session.remove()
def connect_oauth(request, oauth, user_required=False): user, account = get_account(request, service=oauth.id, user_required=user_required) code = request.params.get('code') if not code: raise httpexceptions.HTTPBadRequest('Missing code.') error = request.params.get('error') if error: raise APIError('Failed to connect: %s' % error) url = request.current_route_url().replace( 'http://', 'https://') # We lie, because honeybadger. try: token = oauth.auth_token(url) except InvalidGrantError: # Try again. raise httpexceptions.HTTPSeeOther( request.route_path('account_login', service=oauth.id)) except OAuth2Error as e: raise APIError( "Unexpected authentication error, please try again: %s" % e.description) except ValueError as e: raise APIError("Unexpected response error, please try again: %s" % e) remote_id, email, display_name, remote_data = oauth.query_user() if not user: # New user user = get_or_create( email=email, service=oauth.id, token=token, display_name=display_name, remote_id=remote_id, remote_data=remote_data, ) account = user.accounts[0] elif not account: # New account account = model.Account.create( display_name=display_name or user.display_name, user=user, oauth_token=token, service=oauth.id, remote_id=remote_id, remote_data=remote_data, ) else: # Update account account.oauth_token = token account.remote_id = remote_id account.remote_data = remote_data force_skip = oauth.is_autocreate and Session.query( model.Report).filter_by(account_id=account.id).limit(1).count() if force_skip: # Already exists, skip autocreate. oauth.is_autocreate = False Session.commit() return account