def orders(request): items_count = DBSession.query(func.count(Order.id)) \ .filter_by(uid=request.user.id) \ .filter(Order.close_date != None) \ .scalar() page_items = 100 pages = int((items_count / page_items) + 0.5) try: page = int(request.GET['page']) except (KeyError, ValueError): page = 0 offset = page * page_items orders = DBSession.query(Order).filter_by(uid=request.user.id) \ now = datetime.datetime.now() orders = orders.filter( (Order.paid == True) | # Order is paid ((Order.paid == False) & (Order.close_date > now)) | # Or not expired ((Order.paid == False) & (Order.paid_amount > 0)) # Or not fully paid ) orders = orders.order_by(Order.start_date.desc()) orders = orders.limit(page_items).offset(offset).all() return {'orders': orders, 'page': page, 'pages': pages}
def api_gateway_auth(request): try: fullname = request.POST['username'] password = request.POST['password'] except KeyError: return HTTPBadRequest('Require username/password') if '/' in fullname: username, profilename = fullname.split('/', 1) else: username = fullname profilename = None user = DBSession.query(User).filter_by(username=username).first() if not user or not user.check_password(password) or not user.is_active: return HTTPForbidden('Invalid username or password.') if not user.is_paid: return HTTPForbidden('Free account') if profilename: profile = DBSession.query(Profile) \ .filter_by(name=profilename, uid=user.id).first() if not profile: return HTTPForbidden('Unknown profile') return HTTPOk(empty_body=True)
def setup_database(): """ Create an empty database and structure """ DBSession.remove() engine = create_engine('sqlite://') Base.metadata.create_all(engine) DBSession.configure(bind=engine) return DBSession
def order_post(request): _ = request.translate code = request.POST.get('code') if code: return order_post_gc(request, code) times = (1, 3, 6, 12) try: method_name = request.POST.get('method') time_months = int(request.POST.get('time')) except (ValueError, TypeError): return HTTPSeeOther(location=request.route_url('account')) if method_name == 'admin' and request.user.is_admin: time = datetime.timedelta(days=30 * time_months) request.user.add_paid_time(time) return HTTPSeeOther(location=request.route_url('account')) method = request.payment_methods.get(method_name) if not method or time_months not in times: return HTTPBadRequest('Invalid method/time') time = datetime.timedelta(days=30 * time_months) o = method.init(request.user, time) DBSession.add(o) DBSession.flush() return method.start(request, o)
def status(request): settings = request.registry.settings domain = settings.get('net_domain', '') gateways = DBSession.query(Gateway) \ .filter_by(enabled=True) \ .order_by(Gateway.country, Gateway.name) \ .all() l = list(gateways) get_uptime = get_uptime_factory(settings) for host in l: host.host_name = '%s-%s.%s'%(host.country, host.name, domain) host.uptime = get_uptime(host.host_name) host.bps_formatted = format_bps(host.bps) bw_graph_url = settings.get('munin.bw_graph_url', None) bw_graph_img = settings.get('munin.bw_graph_img', None) bw_graph = (bw_graph_url, bw_graph_img) return { 'gateways': l, 'bw_graph': bw_graph if all(bw_graph) else None, 'n_users': DBSession.query(func.count(User.id)) .filter_by(is_paid=True).scalar(), 'n_countries': len(set(i.country for i in l)), 'total_bw': format_bps(sum(i.bps for i in l)), }
def api_gateway_connect(request): try: fullname = request.POST['username'] client_addr = request.POST['remote_addr'] except KeyError: return HTTPBadRequest('Require username/remote_addr') if '/' in fullname: username, profilename = fullname.split('/', 1) else: username = fullname profilename = None user = DBSession.query(User).filter_by(username=username).first() if not user or not user.is_active or not user.is_paid: return HTTPForbidden('Invalid account') sess = VPNSession() sess.gateway_id = request.gw.id sess.gateway_version = request.gw_version sess.user_id = user.id sess.remote_addr = client_addr if profilename: profile = DBSession.query(Profile) \ .filter_by(name=profilename, uid=user.id).first() if not profile: return HTTPForbidden('Unknown profile') sess.profile_id = profile.id DBSession.add(sess) params = {} return HTTPOk(body=json.dumps(params))
def orders(request): items_count = DBSession.query(func.count(Order.id)) \ .filter_by(uid=request.user.id) \ .filter(Order.close_date != None) \ .scalar() page_items = 100 pages = int((items_count / page_items) + 0.5) try: page = int(request.GET['page']) except (KeyError, ValueError): page = 0 offset = page * page_items orders = DBSession.query(Order).filter_by(uid=request.user.id) \ now = datetime.datetime.now() orders = orders.filter((Order.paid == True) | # Order is paid ((Order.paid == False) & (Order.close_date > now)) | # Or not expired ((Order.paid == False) & (Order.paid_amount > 0)) # Or not fully paid ) orders = orders.order_by(Order.start_date.desc()) orders = orders.limit(page_items).offset(offset).all() return {'orders': orders, 'page': page, 'pages': pages}
def status(request): settings = request.registry.settings domain = settings.get('net_domain', '') gateways = DBSession.query(Gateway) \ .filter_by(enabled=True) \ .order_by(Gateway.country, Gateway.name) \ .all() l = list(gateways) get_uptime = get_uptime_factory(settings) for host in l: host.host_name = '%s-%s.%s' % (host.country, host.name, domain) host.uptime = get_uptime(host.host_name) host.bps_formatted = format_bps(host.bps) bw_graph_url = settings.get('munin.bw_graph_url', None) bw_graph_img = settings.get('munin.bw_graph_img', None) bw_graph = (bw_graph_url, bw_graph_img) return { 'gateways': l, 'bw_graph': bw_graph if all(bw_graph) else None, 'n_users': DBSession.query(func.count(User.id)).filter_by(is_paid=True).scalar(), 'n_countries': len(set(i.country for i in l)), 'total_bw': format_bps(sum(i.bps for i in l)), }
def forgot(request): _ = request.translate if request.method != 'POST' or 'username' not in request.POST: return {} u = DBSession.query(User) \ .filter_by(username=request.POST['username']) \ .first() if not u: request.messages.error(_('Unknown username.')) request.response.status_code = HTTPBadRequest.code return {} if not u.email: request.messages.error( _('No e-mail address associated with username.')) request.response.status_code = HTTPBadRequest.code return {} token = PasswordResetToken(u) DBSession.add(token) DBSession.flush() mailer = get_mailer(request) body = render('mail/password_reset.mako', { 'user': u, 'requested_by': request.remote_addr, 'url': request.route_url('account_reset', token=token.token) }, request=request) message = Message(subject=_('CCVPN: Password reset request'), recipients=[u.email], body=body) mailer.send(message) request.messages.info(_('We sent a reset link. Check your emails.')) return {}
def forgot(request): if request.method != 'POST' or 'username' not in request.POST: return {} u = DBSession.query(User) \ .filter_by(username=request.POST['username']) \ .first() if not u: request.messages.error('Unknown username.') request.response.status_code = HTTPBadRequest.code return {} if not u.email: request.messages.error('No e-mail address associated with username.') request.response.status_code = HTTPBadRequest.code return {} token = PasswordResetToken(u) with transaction.manager: DBSession.add(token) mailer = get_mailer(request) body = render('mail/password_reset.mako', { 'user': u, 'requested_by': request.remote_addr, 'url': request.route_url('account_reset', token=token.token) }) message = Message(subject='CCVPN: Password reset request', recipients=[u.email], body=body) mailer.send(message) request.messages.info('We sent a reset link. Check your emails.') return {}
def initialize_db(): Base.metadata.create_all(DBSession.bind.engine) if not DBSession.query(User).filter_by(username='******').count(): with transaction.manager: admin = User(username='******', is_admin=True) admin.set_password('admin') DBSession.add(admin)
def main(argv=sys.argv): parser = ArgumentParser(description=__doc__, formatter_class=RawTextHelpFormatter) parser.add_argument('-v', '--verbose', action='count') parser.add_argument('-S', '--send', action='store_true', default=False) parser.add_argument('--active', action='store_true', default=True) parser.add_argument('-s', '--subject', action='store') parser.add_argument('config') parser.add_argument('textfile') args = parser.parse_args() log_level = logging.WARNING if args.verbose is not None: verbose = int(args.verbose) if verbose == 1: log_level = logging.INFO elif verbose >= 2: log_level = logging.DEBUG logging.basicConfig(level=log_level) config_uri = args.config setup_logging(config_uri) settings = get_appsettings(config_uri) engine = engine_from_config(settings, 'sqlalchemy.') DBSession.configure(bind=engine) mailer = mailer_factory_from_settings(settings) if not args.subject: print('Require a subject.') exit(1) message_in = open(args.textfile, 'r').read() if not message_in: print('Require a message.') exit(1) q = DBSession.query(User) q = q.filter(User.email != '') q = q.filter(User.email is not None) if args.active: q = q.filter_by(is_paid=True) users = list(q.all()) print('Sending to: %d users.' % (len(users))) if args.verbose: for u in users: print('- %s [%s]' % (u.email, u.username)) for u in users: if not args.send: print('Not sending message to %s.' % u.email) continue message = Message(subject=args.subject, recipients=[u.email], body=message_in) mailer.send_immediately(message)
def main(argv=sys.argv): if len(argv) != 2: usage(argv) config_uri = argv[1] setup_logging(config_uri) settings = get_appsettings(config_uri) engine = engine_from_config(settings, 'sqlalchemy.') DBSession.configure(bind=engine) initialize_db()
def order_callback(request): id = int(request.matchdict['hexid'], 16) o = DBSession.query(Order).filter_by(id=id).first() if not o: return HTTPNotFound() method = methods.METHOD_IDS[o.method] ret = method().callback(request, o) DBSession.flush() return ret
def main(argv=sys.argv): if len(argv) != 2: usage(argv) config_uri = argv[1] setup_logging(config_uri) settings = get_appsettings(config_uri) engine = engine_from_config(settings, 'sqlalchemy.') DBSession.configure(bind=engine) checkbtcorders(settings)
def profiles_edit_post(request): _ = request.translate try: profile_id = int(request.matchdict['id']) profile = DBSession.query(Profile).filter_by(id=profile_id) \ .filter_by(uid=request.user.id).one() except (KeyError, ValueError, NoResultFound): return HTTPSeeOther(location=request.route_url('account')) redirect = HTTPSeeOther( location=request.route_url('account_profiles_edit', id=profile.id)) try: name = request.POST.get('name', '') client_os = request.POST['client_os'] gateway = request.POST['gateway'] protocol = request.POST['protocol'] disable_ipv6 = 'enable_ipv6' not in request.POST http_proxy = request.POST.get('use_http_proxy', '') except (KeyError, ValueError): return redirect if protocol not in Profile.PROTOCOLS: return redirect if profile.name and name and name != profile.name: if not profile.validate_name(name): request.messages.error(_('Invalid name.')) return redirect # Check if the name is already used used = DBSession.query(Profile).filter_by(uid=request.user.id) \ .filter_by(name=name).first() if used: request.messages.error(_('Name already used.')) return redirect profile.name = name profile.client_os = client_os profile.protocol = protocol profile.disable_ipv6 = disable_ipv6 profile.use_http_proxy = http_proxy if gateway.startswith('rr_') and len(gateway) == 5: # rr_<cc> # random in country cc = gateway[3:] profile.gateway_country = cc profile.gateway_id = None else: # random profile.gateway_country = None profile.gateway_id = None request.messages.info(_('Saved!')) return HTTPSeeOther(location=request.route_url('account'))
def profiles_edit_post(request): _ = request.translate try: profile_id = int(request.matchdict['id']) profile = DBSession.query(Profile).filter_by(id=profile_id) \ .filter_by(uid=request.user.id).one() except (KeyError, ValueError, NoResultFound): return HTTPSeeOther(location=request.route_url('account')) redirect = HTTPSeeOther(location=request.route_url('account_profiles_edit', id=profile.id)) try: name = request.POST.get('name', '') client_os = request.POST['client_os'] gateway = request.POST['gateway'] protocol = request.POST['protocol'] disable_ipv6 = 'enable_ipv6' not in request.POST http_proxy = request.POST.get('use_http_proxy', '') except (KeyError, ValueError): return redirect if protocol not in Profile.PROTOCOLS: return redirect if profile.name and name and name != profile.name: if not profile.validate_name(name): request.messages.error(_('Invalid name.')) return redirect # Check if the name is already used used = DBSession.query(Profile).filter_by(uid=request.user.id) \ .filter_by(name=name).first() if used: request.messages.error(_('Name already used.')) return redirect profile.name = name profile.client_os = client_os profile.protocol = protocol profile.disable_ipv6 = disable_ipv6 profile.use_http_proxy = http_proxy if gateway.startswith('rr_') and len(gateway) == 5: # rr_<cc> # random in country cc = gateway[3:] profile.gateway_country = cc profile.gateway_id = None else: # random profile.gateway_country = None profile.gateway_id = None request.messages.info(_('Saved!')) return HTTPSeeOther(location=request.route_url('account'))
def setUp(self): self.config = testing.setUp() self.session = setup_database() with transaction.manager: self.u = User(username='******', password='******') DBSession.add(self.u) self.pu = User(username='******', password='******') self.pu.add_paid_time(datetime.timedelta(days=30)) DBSession.add(self.pu)
def main(argv=sys.argv): if len(argv) != 2: usage(argv) config_uri = argv[1] setup_logging(config_uri) settings = get_appsettings(config_uri) engine = engine_from_config(settings, 'sqlalchemy.') DBSession.configure(bind=engine) with transaction.manager: checkbtcorders(settings)
def setUp(self): super().setUp() self.u = User(username='******', password='******') DBSession.add(self.u) self.session.flush() self.pu = User(username='******', password='******') self.pu.add_paid_time(datetime.timedelta(days=30)) DBSession.add(self.pu) self.session.flush()
def order_callback(request): _ = request.translate id = int(request.matchdict['hexid'], 16) o = DBSession.query(Order).filter_by(id=id).first() if not o: return HTTPNotFound() method = request.payment_methods.get(o.method) r = method.callback(request, o) DBSession.flush() return r
def setUp(self): self.config = testing.setUp() self.session = setup_database() self.u = User(username='******', password='******') DBSession.add(self.u) self.session.flush() self.pu = User(username='******', password='******') self.pu.add_paid_time(datetime.timedelta(days=30)) DBSession.add(self.pu) self.session.flush()
def add(args): t = Gateway() t.label = args.label if args.token == '-': args.token = input('Token (empty=random): ') if args.token: t.token = args.token if args.remote_addr: t.remote_addr = args.remote_addr DBSession.add(t) DBSession.commit() print('Inserted. token=%s' % t.token)
def add(args): t = APIAccessToken() t.label = args.label if args.token == '-': args.token = input('Token (empty=random): ') if args.token: t.token = args.token if args.remote_addr: t.remote_addr = args.remote_addr DBSession.add(t) DBSession.commit() print('Inserted. token=%s' % t.token)
def main(argv=sys.argv): parser = ArgumentParser(description=__doc__, formatter_class=RawTextHelpFormatter) parser.add_argument('-v', '--verbose', action='count') parser.add_argument('-s', '--send', action='store_true', default=False) parser.add_argument('config') args = parser.parse_args() log_level = logging.WARNING if args.verbose is not None: verbose = int(args.verbose) if verbose == 1: log_level = logging.INFO elif verbose >= 2: log_level = logging.DEBUG logging.basicConfig(level=log_level) config_uri = args.config setup_logging(config_uri) settings = get_appsettings(config_uri) engine = engine_from_config(settings, 'sqlalchemy.') DBSession.configure(bind=engine) if 'mako.directories' not in settings: settings['mako.directories'] = 'ccvpn:templates/' if 'mako.imports' not in settings: settings['mako.imports'] = 'from ccvpn.filters import check' config = Configurator(settings=settings) config.include('pyramid_mako') config.commit() config.begin() mailer = mailer_factory_from_settings(settings) try: days = int(settings.get('expire_mail_days', 3)) except ValueError: log.warning('Invalid integer value for expire_mail_days. Using default') days = 3 users = get_future_expire(days) + get_expired() if args.send: for u in users: print('sending notice to %s (%s)' % (u.username, u.email)) send_notice(u, mailer) transaction.commit() else: for u in users: print('not sending notice to %s (%s)' % (u.username, u.email)) print('Use -s to send messages')
def order_post_gc(request, code): try: gc = GiftCode.one(code=code) gc.use(request.user) time = gc.time.days request.messages.info('OK! Added %d days to your account.' % time) DBSession.flush() except (NoResultFound, MultipleResultsFound): request.messages.error('Unknown code.') except AlreadyUsedGiftCode: request.messages.error('Already used code') return HTTPSeeOther(location=request.route_url('account'))
def profiles_edit(request): _ = request.translate try: profile_id = int(request.matchdict['id']) profile = DBSession.query(Profile).filter_by(id=profile_id) \ .filter_by(uid=request.user.id).one() except (KeyError, ValueError, NoResultFound): return HTTPSeeOther(location=request.route_url('account')) return { 'profile': profile, 'edit_post_url': request.route_url('account_profiles_edit', id=profile.id), 'gw_countries': set(i[0] for i in DBSession.query(Gateway.country).all()), }
def account_post(request): _ = request.translate redirect = HTTPSeeOther(location=request.route_url('account')) profiles_limit = 10 profile_name = request.POST.get('profilename') profile_delete = request.POST.get('delete') if profile_name: p = Profile() if not p.validate_name(profile_name): request.messages.error(_('Invalid name.')) return redirect # Check if the name is already used used = DBSession.query(Profile).filter_by(uid=request.user.id) \ .filter_by(name=profile_name).first() if used: request.messages.error(_('Name already used.')) return redirect # Check if this user's under the profile number limit profiles_count = DBSession.query(func.count(Profile.id)) \ .filter_by(uid=request.user.id).scalar() if profiles_count > profiles_limit: request.messages.error(_('You have too many profiles.')) return redirect p.name = profile_name p.uid = request.user.id DBSession.add(p) DBSession.flush() return HTTPSeeOther( location=request.route_url('account_profiles_edit', id=p.id)) if profile_delete: try: profile_delete = int(profile_delete) except ValueError: return redirect p = DBSession.query(Profile) \ .filter_by(id=int(profile_delete)) \ .filter(Profile.name != '') \ .filter_by(uid=request.user.id) \ .first() if not p: request.messages.error(_('Unknown profile.')) return redirect DBSession.delete(p) return redirect
def order_post_gc(request, code): _ = request.translate try: gc = GiftCode.one(code=code) gc.use(request.user) time = gc.time.days request.messages.info(_('OK! Added ${time} days to your account.', mapping={'time': time})) DBSession.flush() except (NoResultFound, MultipleResultsFound): request.messages.error(_('Unknown gift code.')) except AlreadyUsedGiftCode: request.messages.error(_('Gift code already used.')) return HTTPSeeOther(location=request.route_url('account'))
def logs(request): items_count = DBSession.query(func.count(VPNSession.id)) \ .filter_by(user_id=request.user.id) \ .scalar() page_items = 100 pages = int((items_count / page_items) + 0.5) try: page = int(request.GET['page']) except (KeyError, ValueError): page = 0 offset = page * page_items logs = DBSession.query(VPNSession).filter_by(user_id=request.user.id) \ .order_by(VPNSession.connect_date.desc()) \ .limit(page_items).offset(offset) return {'logs': logs, 'page': page, 'pages': pages}
def account_post(request): _ = request.translate redirect = HTTPSeeOther(location=request.route_url('account')) profiles_limit = 10 profile_name = request.POST.get('profilename') profile_delete = request.POST.get('delete') if profile_name: p = Profile() if not p.validate_name(profile_name): request.messages.error(_('Invalid name.')) return redirect # Check if the name is already used used = DBSession.query(Profile).filter_by(uid=request.user.id) \ .filter_by(name=profile_name).first() if used: request.messages.error(_('Name already used.')) return redirect # Check if this user's under the profile number limit profiles_count = DBSession.query(func.count(Profile.id)) \ .filter_by(uid=request.user.id).scalar() if profiles_count > profiles_limit: request.messages.error(_('You have too many profiles.')) return redirect p.name = profile_name p.uid = request.user.id DBSession.add(p) DBSession.flush() return HTTPSeeOther(location=request.route_url('account_profiles_edit', id=p.id)) if profile_delete: try: profile_delete = int(profile_delete) except ValueError: return redirect p = DBSession.query(Profile) \ .filter_by(id=int(profile_delete)) \ .filter(Profile.name != '') \ .filter_by(uid=request.user.id) \ .first() if not p: request.messages.error(_('Unknown profile.')) return redirect DBSession.delete(p) return redirect
def get_future_expire(days=3): """This function get user accounts that will expire in a few days. """ limit_date = datetime.now() + timedelta(days=days) q = DBSession.query(User) \ .filter(User.email != '') \ .filter(User.email != None) # Expire now < expiration < N days q = q.filter(User.paid_until > datetime.now()) q = q.filter(User.paid_until < limit_date) # Only send notice if the last one was before the first time we could have # sent a notice # [last notice] < [expiration - 3days] < [this notice] < [expiration] if DBSession.bind.dialect.name == 'sqlite': a1 = func.julianday(User.paid_until) a2 = func.julianday(User.last_expiry_notice) cond = a1 - a2 > days else: cond = User.paid_until - User.last_expiry_notice > timedelta(days=days) q = q.filter(or_(User.last_expiry_notice == None, cond)) users = list(q.all()) log.debug('found %d accounts that expire in less than %d days', len(users), days) return users
def get_item(self, id): item_id = self.request.GET['id'] item = DBSession.query(self.model).filter_by(id=item_id).first() template = 'admin/item.mako' if item is None: raise HTTPNotFound() return render_to_response(self.item_template or template, self.tvars(dict(item=item)))
def _get_uid(self, input): if input.startswith('#'): return input[1:] user = DBSession.query(User).filter_by(username=input).first() if not user: # TODO: handle that correctly raise HTTPBadRequest() return user.id
def config(request): _ = request.translate settings = request.registry.settings domain = settings.get('net_domain', '') if not domain.startswith('.'): domain = '.' + domain gw_countries = [i[0] for i in DBSession.query(Gateway.country).all()] try: username = request.matchdict['username'] pname = request.matchdict.get('pname', '') if request.user.username != username: # Only allow corrently logged user for now raise ValueError() user = request.user profile = DBSession.query(Profile) \ .filter_by(uid=user.id) \ .filter_by(name=pname) \ .one() except (ValueError, KeyError, NoResultFound): return HTTPNotFound() # Use 'Other / GNU/Linux' as the default OS if no other is set client_os = profile.client_os or 'other' params = { 'profile': profile, 'remote': profile.get_vpn_remote(domain), 'use_fragment': (profile.protocol == 'udpl'), 'use_ipv6': (profile.client_os != 'freebox') and not profile.disable_ipv6, 'use_http_proxy': (profile.protocol == 'tcp'), 'use_resolvconf': (profile.client_os == 'ubuntu'), 'openvpn_ca': openvpn_ca, } r = render_to_response('config.ovpn.mako', params, request=request) if 'plain' in request.GET: r.content_type = 'text/plain' else: r.content_type = 'application/x-openvpn-profile' return r
def order_view(request): id = int(request.matchdict['hexid'], 16) o = DBSession.query(Order).filter_by(id=id).first() if not o: return HTTPNotFound() if not request.user.is_admin and request.user.id != o.uid: return HTTPUnauthorized() return {'o': o}
def signup(request): _ = request.translate if request.method != 'POST': return {} errors = [] try: username = request.POST.get('username') password = request.POST.get('password') password2 = request.POST.get('password2') email = request.POST.get('email') if not User.validate_username(username): errors.append(_('Invalid username.')) if not User.validate_password(password): errors.append(_('Invalid password.')) if email and not User.validate_email(email): errors.append(_('Invalid email address.')) if password != password2: errors.append(_('Both passwords do not match.')) assert not errors used = User.is_used(username, email) if used[0] > 0: errors.append(_('Username already registered.')) if used[1] > 0 and email: errors.append(_('E-mail address already registered.')) assert not errors with transaction.manager: u = User(username=username, email=email, password=password) if request.referrer: u.referrer_id = request.referrer.id DBSession.add(u) DBSession.flush() request.session['uid'] = u.id return HTTPSeeOther(location=request.route_url('account')) except AssertionError: for error in errors: request.messages.error(error) fields = ('username', 'password', 'password2', 'email') request.response.status_code = HTTPBadRequest.code return {k: request.POST[k] for k in fields}
def checkbtcorders(settings): method = BitcoinMethod() orders = DBSession.query(Order) \ .filter_by(paid=False, method=Order.METHOD.BITCOIN) for order in orders: method.check_paid(settings, order) log.debug('Order#%d: amount=%f, paid=%f', order.id, order.amount, order.paid_amount)
def checkbtcorders(settings): method = BitcoinMethod(settings) orders = DBSession.query(Order) \ .filter_by(paid=False, method=Order.METHOD.BITCOIN) for order in orders: method.check_paid(order) log.debug('Order#%d: amount=%f, paid=%f', order.id, order.amount, order.paid_amount)
def config(request): _ = request.translate settings = request.registry.settings domain = settings.get('net_domain', '') gw_countries = [i[0] for i in DBSession.query(Gateway.country).all()] pname = request.GET.get('profile') if pname: profile = DBSession.query(Profile) \ .filter_by(uid=request.user.id, name=pname) \ .first() if not profile: return HTTPNotFound() else: profile = None gw = request.GET.get('gw') if gw and gw[0:3] == 'rr_' and gw[3:] in gw_countries: gateway = 'gw.' + gw[3:] + '.' + domain else: gateway = 'gw.random.' + domain os = request.GET.get('os') # These clients do not fully support OpenVPN config not_real_ovpn = os == 'android' or os == 'ios' params = { 'force_udp': os == 'freebox', 'force_tcp': not_real_ovpn or 'forcetcp' in request.GET, 'windows_dns': os == 'windows', 'resolvconf': os == 'ubuntu', 'ipv6': os != 'freebox' and 'enable_ipv6' in request.GET, 'dhcp': os != 'freebox', 'username': request.user.username, 'profile': profile, 'gateway': gateway, 'openvpn_ca': openvpn_ca, } r = render_to_response('config.ovpn.mako', params, request=request) r.content_type = 'application/x-openvpn-profile' return r
def main(argv=sys.argv): parser = ArgumentParser(description=__doc__, formatter_class=RawTextHelpFormatter) parser.add_argument('-v', '--verbose', action='count', help='Increase verbosity') parser.add_argument('config') subparsers = parser.add_subparsers(title='subcommands') parser_add = subparsers.add_parser('add', help='add API access token') parser_add.set_defaults(func=add) parser_add.add_argument('label') parser_add.add_argument('-t', '--token', default='') parser_add.add_argument('-r', '--remote-addr', default='') parser_rev = subparsers.add_parser('rev', help='revoke API access token') parser_rev.set_defaults(func=revoke) parser_rev.add_argument('-n', '--label', default='') parser_rev.add_argument('-t', '--token', default='') parser_rev.add_argument('-r', '--remote-addr', default='') parser_rev.add_argument('-y', '--yes', default=False, action='store_true', help='Dont ask for confirmation') parser_rev.add_argument('-f', '--force', default=False, action='store_true', help='Revoke even if multiple found') args = parser.parse_args() log_level = logging.WARNING if args.verbose is not None: verbose = int(args.verbose) if verbose == 1: log_level = logging.INFO elif verbose >= 2: log_level = logging.DEBUG logging.basicConfig(level=log_level) config_uri = args.config setup_logging(config_uri) settings = get_appsettings(config_uri) engine = engine_from_config(settings, 'sqlalchemy.') DBSession.configure(bind=engine) args.func(args)
def reset(request): _ = request.translate token = DBSession.query(PasswordResetToken) \ .filter_by(token=request.matchdict['token']) \ .first() if not token or not token.user: request.messages.error(_('Unknown password reset token.')) url = request.route_url('account_forgot') return HTTPMovedPermanently(location=url) password = request.POST.get('password') password2 = request.POST.get('password2') if request.method != 'POST' or not password or not password2: return {'token': token} if not User.validate_password(password) or password != password2: request.messages.error(_('Invalid password.')) request.response.status_code = HTTPBadRequest.code return {'token': token} token.user.set_password(password) mailer = get_mailer(request) body = render('mail/password_reset_done.mako', { 'user': token.user, 'changed_by': request.remote_addr, }, request=request) message = Message(subject=_('CCVPN: Password changed'), recipients=[token.user.email], body=body) mailer.send(message) msg = _('You have changed the password for ${user}.', mapping={'user': token.user.username}) msg += ' ' + _('You can now log in.') request.messages.info(msg) DBSession.delete(token) url = request.route_url('account_login') return HTTPMovedPermanently(location=url)
def get_list(self, page): query = DBSession.query(self.model).order_by(self.model.id) for f in self.get_list_filters: query = f(query) # Pagination count_q = DBSession.query(func.count(self.model.id)) for f in self.get_list_filters: count_q = f(count_q) count = count_q.scalar() pages = ceil(count / self.list_page_items) query = query.limit(self.list_page_items) query = query.offset(self.list_page_items * page) items = query.all() self.main_template = 'list.mako' if self.can_add: self.templates.append('add.mako') return {'list_items': items, 'page': page, 'pages': pages}
def setUp(self): if not 'mako.directories' in self.settings: self.settings['mako.directories'] = 'ccvpn:templates/' if not 'mako.imports' in self.settings: self.settings['mako.imports'] = 'from ccvpn.filters import check' self.config = testing.setUp(settings=self.settings) self.config.include('pyramid_mailer.testing') self.config.include('pyramid_mako') self.config.include('pyramid_beaker') self.config.include('pyramid_mailer.testing') setup_routes(self.config) DBSession.remove() #self.engine = engine_from_config(settings, 'sqlalchemy.') self.conn = self.engine.connect() self.trans = self.conn.begin() DBSession.configure(bind=self.conn) Base.metadata.create_all(self.engine) self.session = DBSession
def api_gateway_connect(request): try: fullname = request.POST['username'] client_addr = request.POST['remote_addr'] internal_ip4 = request.POST['internal_ip4'] internal_ip6 = request.POST['internal_ip6'] except KeyError: return HTTPBadRequest('Require username/remote_addr') if '/' in fullname: username, profilename = fullname.split('/', 1) else: username = fullname profilename = None user = DBSession.query(User).filter_by(username=username).first() if not user or not user.is_active or not user.is_paid: return HTTPForbidden('Invalid account') sess = VPNSession() sess.gateway_id = request.gw.id sess.gateway_version = request.gw_version sess.user_id = user.id sess.remote_addr = client_addr sess.internal_ip4 = internal_ip4 sess.internal_ip6 = internal_ip6 if profilename: profile = DBSession.query(Profile) \ .filter_by(name=profilename, uid=user.id).first() if not profile: return HTTPForbidden('Unknown profile') sess.profile_id = profile.id DBSession.add(sess) params = {} return HTTPOk(body=json.dumps(params))