class TestCase(unittest.TestCase): '''An helper mixin for common operations''' def setUp(self): '''Initialize an Flask application''' self.app = Flask(__name__) @contextmanager def context(self): with self.app.test_request_context('/'): yield def get_specs(self, prefix='/api', app=None): '''Get a Swagger specification for a RestPlus API''' with self.app.test_client() as client: response = client.get('{0}/specs.json'.format(prefix)) self.assertEquals(response.status_code, 200) self.assertEquals(response.content_type, 'application/json') return json.loads(response.data.decode('utf8')) def get_declaration(self, namespace='default', prefix='/api', status=200, app=None): '''Get an API declaration for a given namespace''' with self.app.test_client() as client: response = client.get('{0}/{1}.json'.format(prefix, namespace)) self.assertEquals(response.status_code, status) self.assertEquals(response.content_type, 'application/json') return json.loads(response.data.decode('utf8'))
def testGetTpls(self): app = Flask(__name__) with app.test_client() as c: testRequest = c.get('/tpls.json?which=asdfjdskfjs') self.assertEquals(statserv.server.send_error(request, 'template does'\ ' not exist'), statserv.server.get_tpls(), 'The get_tpls method really shouldn\'t try to send '\ 'back a template for \'asdfjdskfjs.\'') tplsempty = False with app.test_client() as c: testRequest = c.get('/tpls.json?which=') tplsempty = statserv.server.get_tpls() with app.test_client() as c: testRequest = c.get('/tpls.json?which=all') self.assertEquals(statserv.server.get_tpls(), tplsempty, 'The get_tpls method should send back all '\ 'templates on both which=all and which=.') with app.test_client() as c: testRequest = c.get('/tpls.json?callback=blah'\ '&which=header&which=home') header = open(statserv.server.determine_path()\ + '/tpls/header.tpl').read() home = open(statserv.server.determine_path()\ + '/tpls/home.tpl').read() response = statserv.server.make_response('blah', dict({'header': header, 'home': home})) self.assertEquals(statserv.server.get_tpls(), response, 'The single-template support does not seem to be '\ 'working properly.')
class DefaultsTestCase(FlaskCorsTestCase): def setUp(self): self.app = Flask(__name__) @self.app.route('/', methods=['GET','OPTIONS']) @cross_origin() def wildcard(): return 'Welcome!' def test_wildcard_defaults_no_origin(self): ''' If there is no Origin header in the request, the Access-Control-Allow-Origin header should not be included, according to the w3 spec. ''' with self.app.test_client() as c: for verb in self.iter_verbs(c): result = verb('/') self.assertEqual(result.headers.get(AccessControlAllowOrigin), '*') def test_wildcard_defaults_origin(self): ''' If there is no Origin header in the request, the Access-Control-Allow-Origin header should be included, if and only if the always_send parameter is `True`, which is the default value. ''' example_origin = 'http://example.com' with self.app.test_client() as c: for verb in self.iter_verbs(c): result = verb('/',headers = {'Origin': example_origin}) self.assertEqual(result.headers.get(AccessControlAllowOrigin),'*')
class W3TestCase(FlaskCorsTestCase): def setUp(self): self.app = Flask(__name__) @self.app.route('/', methods=['GET','OPTIONS']) @cross_origin(origins='*', send_wildcard=False, always_send=False) def allowOrigins(): ''' This sets up flask-cors to echo the request's `Origin` header, only if it is actually set. This behavior is most similar to the actual W3 specification, http://www.w3.org/TR/cors/ but is not the default because it is more common to use the wildcard approach. ''' return 'Welcome!' def test_wildcard_origin_header(self): ''' If there is an Origin header in the request, the Access-Control-Allow-Origin header should be echoed back. ''' example_origin = 'http://example.com' with self.app.test_client() as c: for verb in self.iter_verbs(c): result = verb('/', headers = {'Origin': example_origin}) self.assertEqual(result.headers.get(AccessControlAllowOrigin),example_origin) def test_wildcard_no_origin_header(self): ''' If there is no Origin header in the request, the Access-Control-Allow-Origin header should not be included. ''' with self.app.test_client() as c: for verb in self.iter_verbs(c): result = verb('/') self.assertTrue(AccessControlAllowOrigin not in result.headers)
class SupportsCredentialsCase(FlaskCorsTestCase): def setUp(self): self.app = Flask(__name__) @self.app.route('/test_credentials') @cross_origin(supports_credentials=True) def test_credentials(): return 'Credentials!' @self.app.route('/test_open') @cross_origin() def test_open(): return 'Open!' def test_credentialed_request(self): ''' The specified route should return the Access-Control-Allow-Credentials header. ''' with self.app.test_client() as c: result = c.get('/test_credentials') header = result.headers.get(ACL_CREDENTIALS) self.assertEquals(header, 'true') def test_open_request(self): ''' The default behavior should be to disallow credentials. ''' with self.app.test_client() as c: result = c.get('/test_open') self.assertTrue(ACL_CREDENTIALS not in result.headers)
class TestCase(unittest.TestCase): '''An helper mixin for common operations''' def setUp(self): '''Initialize an Flask application''' self.app = Flask(__name__) @contextmanager def context(self, **kwargs): with self.app.test_request_context('/', **kwargs): yield @contextmanager def settings(self, **settings): ''' A context manager to alter app settings during a test and restore it after.. ''' original = {} # backup for key, value in settings.items(): original[key] = self.app.config.get(key) self.app.config[key] = value yield # restore for key, value in original.items(): self.app.config[key] = value @contextmanager def assert_warning(self, category=Warning): with warnings.catch_warnings(record=True) as w: warnings.simplefilter('always') # Cause all warnings to always be triggered. yield self.assertGreaterEqual(len(w), 1, 'It should raise a warning') warning = w[0] self.assertEqual(warning.category, category, 'It should raise {0}'.format(category.__name__)) def get(self, url, **kwargs): with self.app.test_client() as client: return client.get(url, **kwargs) def post(self, url, **kwargs): with self.app.test_client() as client: return client.post(url, **kwargs) def get_json(self, url, status=200, **kwargs): response = self.get(url, **kwargs) self.assertEqual(response.status_code, status) self.assertEqual(response.content_type, 'application/json') return json.loads(response.data.decode('utf8')) def get_specs(self, prefix='', status=200, **kwargs): '''Get a Swagger specification for a RestPlus API''' return self.get_json('{0}/swagger.json'.format(prefix), status=status, **kwargs) def assertDataEqual(self, tested, expected): '''Compare data without caring about order and type (dict vs. OrderedDict)''' assert_data_equal(tested, expected)
class OriginsW3TestCase(FlaskCorsTestCase): def setUp(self): self.app = Flask(__name__) @self.app.route('/') @cross_origin(origins='*', send_wildcard=False, always_send=False) def allowOrigins(): ''' This sets up flask-cors to echo the request's `Origin` header, only if it is actually set. This behavior is most similar to the actual W3 specification, http://www.w3.org/TR/cors/ but is not the default because it is more common to use the wildcard configuration in order to support CDN caching. ''' return 'Welcome!' @self.app.route('/default-origins') @cross_origin(send_wildcard=False, always_send=False) def noWildcard(): ''' With the default origins configuration, send_wildcard should still be respected. ''' return 'Welcome!' def test_wildcard_origin_header(self): ''' If there is an Origin header in the request, the Access-Control-Allow-Origin header should be echoed back. ''' example_origin = 'http://example.com' with self.app.test_client() as c: for verb in self.iter_verbs(c): result = verb('/', headers={'Origin': example_origin}) self.assertEqual( result.headers.get(ACL_ORIGIN), example_origin ) def test_wildcard_no_origin_header(self): ''' If there is no Origin header in the request, the Access-Control-Allow-Origin header should not be included. ''' with self.app.test_client() as c: for verb in self.iter_verbs(c): result = verb('/') self.assertTrue(ACL_ORIGIN not in result.headers) def test_wildcard_default_origins(self): ''' If there is an Origin header in the request, the Access-Control-Allow-Origin header should be echoed back. ''' example_origin = 'http://example.com' with self.app.test_client() as c: for verb in self.iter_verbs(c): result = verb( '/default-origins', headers={'Origin': example_origin} ) self.assertEqual( result.headers.get(ACL_ORIGIN), example_origin )
def test_bugsnag_custom_data(self, deliver): meta_data = [{"hello": {"world": "once"}}, {"again": {"hello": "world"}}] app = Flask("bugsnag") @app.route("/hello") def hello(): bugsnag.configure_request(meta_data=meta_data.pop()) raise SentinelError("oops") handle_exceptions(app) app.test_client().get('/hello') app.test_client().get('/hello') self.assertEqual(deliver.call_count, 2) payload = deliver.call_args_list[0][0][0] event = payload['events'][0] self.assertEqual(event['metaData'].get('hello'), None) self.assertEqual(event['metaData']['again']['hello'], 'world') payload = deliver.call_args_list[1][0][0] event = payload['events'][0] self.assertEqual(event['metaData']['hello']['world'], 'once') self.assertEqual(event['metaData'].get('again'), None)
class KazooTestCase(unittest.TestCase): def setUp(self): self.app = Flask(__name__) self.app.config['TESTING'] = True self.kazoo = Kazoo(self.app) self.node_prefix = '/kazoo-test/' self.node_name = 'test-kazoo-node' self.node_value = uuid.uuid1().bytes self.app.extensions['kazoo']['client'].create('/kazoo-test/%s' % self.node_name, self.node_value, makepath=True) @self.app.route('/write/<path>') def write(path): return str(kazoo_client.set(self.node_prefix + path, b'OK')) @self.app.route('/read/<path>') def read(path): return kazoo_client.get(self.node_prefix + path)[0] def tearDown(self): try: self.app.extensions['kazoo']['client'].delete(self.node_prefix + self.node_name) except NoNodeError: print "Teardown got NoNodeError" def test_kazoo_set(self): with self.app.test_client() as c: results = c.get('/write/%s' % self.node_name) self.assertEqual(results.status_code, 200) def test_kazoo_read(self): with self.app.test_client() as c: results = c.get('/read/%s' % self.node_name) self.assertEqual(results.data, self.node_value)
class LogicalAPINamingTestCase(unittest.TestCase): def setUp(self): self.app = Flask(__name__) self.tasks = [{"id": 1, "task": "Do the laundry"}, {"id": 2, "task": "Do the dishes"}] def get_tasks(request): return self.tasks def post_task(request): data = request.json self.tasks.append({"task": data["task"]}) return {}, 201 self.get_tasks = get_tasks self.post_task = post_task def test_naming_a_single_api(self): api_1 = Api(version="v1", name="read-only-methods") api_1.register_endpoint(ApiEndpoint(http_method="GET", endpoint="/task/", handler=self.get_tasks)) self.app.register_blueprint(api_1) self.app.config["TESTING"] = True client = self.app.test_client() resp = client.get("/v1/task/", content_type="application/json") self.assertEqual(resp.status_code, 200) self.assertEqual(resp.headers["Content-Type"], "application/json") data = json.loads(resp.data.decode(resp.charset)) self.assertEqual(len(data), 2) def test_naming_multiple_logic_apis(self): api_1 = Api(version="v1", name="read-only-methods") api_1.register_endpoint(ApiEndpoint(http_method="GET", endpoint="/task/", handler=self.get_tasks)) self.app.register_blueprint(api_1) api_2 = Api(version="v1", name="write-methods") api_2.register_endpoint(ApiEndpoint(http_method="POST", endpoint="/task/", handler=self.post_task)) self.app.register_blueprint(api_2) self.app.config["TESTING"] = True client = self.app.test_client() # Testing GET resp = client.get("/v1/task/", content_type="application/json") self.assertEqual(resp.status_code, 200) self.assertEqual(resp.headers["Content-Type"], "application/json") data = json.loads(resp.data.decode(resp.charset)) self.assertEqual(len(data), 2) # Testing POST resp = client.post("/v1/task/", content_type="application/json", data=json.dumps({"task": "New Task!"})) self.assertEqual(resp.status_code, 201) self.assertEqual(resp.headers["Content-Type"], "application/json") self.assertEqual(len(self.tasks), 3)
def test_modal_edit(): # bootstrap 2 - test edit_modal app_bs2 = Flask(__name__) admin_bs2 = Admin(app_bs2, template_mode="bootstrap2") class EditModalOn(fileadmin.FileAdmin): edit_modal = True editable_extensions = ('txt',) class EditModalOff(fileadmin.FileAdmin): edit_modal = False editable_extensions = ('txt',) path = op.join(op.dirname(__file__), 'files') edit_modal_on = EditModalOn(path, '/files/', endpoint='edit_modal_on') edit_modal_off = EditModalOff(path, '/files/', endpoint='edit_modal_off') admin_bs2.add_view(edit_modal_on) admin_bs2.add_view(edit_modal_off) client_bs2 = app_bs2.test_client() # bootstrap 2 - ensure modal window is added when edit_modal is enabled rv = client_bs2.get('/admin/edit_modal_on/') eq_(rv.status_code, 200) data = rv.data.decode('utf-8') ok_('fa_modal_window' in data) # bootstrap 2 - test edit modal disabled rv = client_bs2.get('/admin/edit_modal_off/') eq_(rv.status_code, 200) data = rv.data.decode('utf-8') ok_('fa_modal_window' not in data) # bootstrap 3 app_bs3 = Flask(__name__) admin_bs3 = Admin(app_bs3, template_mode="bootstrap3") admin_bs3.add_view(edit_modal_on) admin_bs3.add_view(edit_modal_off) client_bs3 = app_bs3.test_client() # bootstrap 3 - ensure modal window is added when edit_modal is enabled rv = client_bs3.get('/admin/edit_modal_on/') eq_(rv.status_code, 200) data = rv.data.decode('utf-8') ok_('fa_modal_window' in data) # bootstrap 3 - test modal disabled rv = client_bs3.get('/admin/edit_modal_off/') eq_(rv.status_code, 200) data = rv.data.decode('utf-8') ok_('fa_modal_window' not in data)
class TestCase(unittest.TestCase): """An helper mixin for common operations""" def setUp(self): """Initialize an Flask application""" self.app = Flask(__name__) @contextmanager def context(self): with self.app.test_request_context("/"): yield @contextmanager def settings(self, **settings): """ A context manager to alter app settings during a test and restore it after.. """ original = {} # backup for key, value in settings.items(): original[key] = self.app.config.get(key) self.app.config[key] = value yield # restore for key, value in original.items(): self.app.config[key] = value def get_specs(self, prefix="/api", app=None, status=200): """Get a Swagger specification for a RestPlus API""" with self.app.test_client() as client: response = client.get("{0}/swagger.json".format(prefix)) self.assertEquals(response.status_code, status) self.assertEquals(response.content_type, "application/json") return json.loads(response.data.decode("utf8")) def get_declaration(self, namespace="default", prefix="/api", status=200, app=None): """Get an API declaration for a given namespace""" with self.app.test_client() as client: response = client.get("{0}/swagger.json".format(prefix, namespace)) self.assertEquals(response.status_code, status) self.assertEquals(response.content_type, "application/json") return json.loads(response.data.decode("utf8")) def get_json(self, url, status=200): with self.app.test_client() as client: response = client.get(url) self.assertEquals(response.status_code, status) self.assertEquals(response.content_type, "application/json") return json.loads(response.data.decode("utf8"))
class ExposeHeadersTestCase(FlaskCorsTestCase): def setUp(self): self.app = Flask(__name__) @self.app.route('/test_default') @cross_origin() def test_default(): return 'Welcome!' @self.app.route('/test_list') @cross_origin(expose_headers=["Foo", "Bar"]) def test_list(): return 'Welcome!' @self.app.route('/test_string') @cross_origin(expose_headers="Foo") def test_string(): return 'Welcome!' @self.app.route('/test_set') @cross_origin(expose_headers=set(["Foo", "Bar"])) def test_set(): return 'Welcome!' def test_default(self): with self.app.test_client() as c: resp = c.get('/test_default') self.assertTrue(resp.headers.get(ACL_EXPOSE_HEADERS) is None, "Default should have no allowed headers") def test_list_serialized(self): ''' If there is an Origin header in the request, the Access-Control-Allow-Origin header should be echoed back. ''' with self.app.test_client() as c: resp = c.get('/test_list') self.assertEqual(resp.headers.get(ACL_EXPOSE_HEADERS), 'Bar, Foo') def test_string_serialized(self): ''' If there is an Origin header in the request, the Access-Control-Allow-Origin header should be echoed back. ''' with self.app.test_client() as c: resp = c.get('/test_string') self.assertEqual(resp.headers.get(ACL_EXPOSE_HEADERS), 'Foo') def test_set_serialized(self): ''' If there is an Origin header in the request, the Access-Control-Allow-Origin header should be echoed back. ''' with self.app.test_client() as c: resp = c.get('/test_set') self.assertEqual(resp.headers.get(ACL_EXPOSE_HEADERS), 'Bar, Foo')
def test_multiple_apps(self): app1 = Flask(__name__) app2 = Flask(__name__) limiter = Limiter(global_limits = ["1/second"]) limiter.init_app(app1) limiter.init_app(app2) @app1.route("/ping") def ping(): return "PONG" @app1.route("/slowping") @limiter.limit("1/minute") def slow_ping(): return "PONG" @app2.route("/ping") @limiter.limit("2/second") def ping_2(): return "PONG" @app2.route("/slowping") @limiter.limit("2/minute") def slow_ping_2(): return "PONG" with hiro.Timeline().freeze() as timeline: with app1.test_client() as cli: self.assertEqual(cli.get("/ping").status_code, 200) self.assertEqual(cli.get("/ping").status_code, 429) timeline.forward(1) self.assertEqual(cli.get("/ping").status_code, 200) self.assertEqual(cli.get("/slowping").status_code, 200) timeline.forward(59) self.assertEqual(cli.get("/slowping").status_code, 429) timeline.forward(1) self.assertEqual(cli.get("/slowping").status_code, 200) with app2.test_client() as cli: self.assertEqual(cli.get("/ping").status_code, 200) self.assertEqual(cli.get("/ping").status_code, 200) self.assertEqual(cli.get("/ping").status_code, 429) timeline.forward(1) self.assertEqual(cli.get("/ping").status_code, 200) self.assertEqual(cli.get("/slowping").status_code, 200) timeline.forward(59) self.assertEqual(cli.get("/slowping").status_code, 200) self.assertEqual(cli.get("/slowping").status_code, 429) timeline.forward(1) self.assertEqual(cli.get("/slowping").status_code, 200)
def test_bugsnag_crash(deliver): app = Flask("bugsnag") @app.route("/hello") def hello(): raise SentinalError("oops") handle_exceptions(app) app.test_client().get("/hello") eq_(deliver.call_count, 1) payload = deliver.call_args[0][0] eq_(payload["events"][0]["exceptions"][0]["errorClass"], "test_flask.SentinalError") eq_(payload["events"][0]["metaData"]["request"]["url"], "http://localhost/hello")
def test_bugsnag_notify(deliver): app = Flask("bugsnag") @app.route("/hello") def hello(): bugsnag.notify(SentinalError("oops")) return "OK" handle_exceptions(app) app.test_client().get('/hello') eq_(deliver.call_count, 1) payload = deliver.call_args[0][0] eq_(payload['events'][0]['metaData']['request']['url'], 'http://localhost/hello')
def test_bugsnag_crash(deliver): app = Flask("bugsnag") @app.route("/hello") def hello(): raise SentinalError("oops") handle_exceptions(app) app.test_client().get('/hello') eq_(deliver.call_count, 1) payload = deliver.call_args[0][0] eq_(payload['events'][0]['exceptions'][0]['errorClass'], 'test_flask.SentinalError') eq_(payload['events'][0]['metaData']['request']['url'], 'http://localhost/hello')
def test_bugsnag_notify(self): app = Flask("bugsnag") @app.route("/hello") def hello(): bugsnag.notify(SentinelError("oops")) return "OK" handle_exceptions(app) app.test_client().get('/hello') self.assertEqual(1, len(self.server.received)) payload = self.server.received[0]['json_body'] self.assertEqual(payload['events'][0]['metaData']['request']['url'], 'http://localhost/hello')
def test_bugsnag_includes_unknown_content_type_posted_data(deliver): app = Flask("bugsnag") @app.route("/form", methods=["PUT"]) def hello(): raise SentinalError("oops") handle_exceptions(app) app.test_client().put("/form", data="_data", content_type="application/octet-stream") eq_(deliver.call_count, 1) payload = deliver.call_args[0][0] eq_(payload["events"][0]["exceptions"][0]["errorClass"], "test_flask.SentinalError") eq_(payload["events"][0]["metaData"]["request"]["url"], "http://localhost/form") ok_("_data" in payload["events"][0]["metaData"]["request"]["data"]["body"])
def test_bugsnag_includes_posted_json_data(deliver): app = Flask("bugsnag") @app.route("/ajax", methods=["POST"]) def hello(): raise SentinalError("oops") handle_exceptions(app) app.test_client().post("/ajax", data='{"key": "value"}', content_type="application/json") eq_(deliver.call_count, 1) payload = deliver.call_args[0][0] eq_(payload["events"][0]["exceptions"][0]["errorClass"], "test_flask.SentinalError") eq_(payload["events"][0]["metaData"]["request"]["url"], "http://localhost/ajax") eq_(payload["events"][0]["metaData"]["request"]["data"], dict(key="value"))
def test_menu_render(): menu = decorators.menu menu.clear() app = Flask(__name__) app.testing = True @menu("Hello World", group_name="admin") class Hello(object): @menu("Index") def index(self): pass @menu("Page 2") def index2(self): pass @menu("Monster") class Monster(object): @menu("Home") def maggi(self): pass with app.test_client() as c: c.get("/") assert len(menu.render()) == 2
def setUp(self): self.engine = Engine("op1", "op2") self.engine.op1.setup(in_name="in", out_name="middle", required=False) self.engine.op2.setup(in_name="middle", out_name="out") self.engine.op1.set(OptProductEx()) foisdouze = OptProductEx("foisdouze") foisdouze.force_option_value("factor", 12) self.engine.op2.set(foisdouze, OptProductEx()) egn_view = EngineView(self.engine, name="my_egn") egn_view.add_input("in", Numeric(vtype=int, min=-5, max=5)) egn_view.add_input("middle", Numeric(vtype=int)) print(self.engine.needed_inputs()) egn_view.add_output("in") egn_view.add_output("middle") egn_view.add_output("out") api = ReliureAPI() api.register_view(egn_view) app = Flask(__name__) app.config['TESTING'] = True app.register_blueprint(api, url_prefix="/api") self.app = app.test_client()
def main(): app = Flask(__name__) app.config.update( DB_CONNECTION_STRING=':memory:', CACHE_TYPE='simple', SQLALCHEMY_DATABASE_URI='sqlite://', ) app.debug = True injector = init_app(app=app, modules=[AppModule]) configure_views(app=app, cached=injector.get(Cache).cached) post_init_app(app, injector) client = app.test_client() response = client.get('/') print('%s\n%s%s' % (response.status, response.headers, response.data)) response = client.post('/', data={'key': 'foo', 'value': 'bar'}) print('%s\n%s%s' % (response.status, response.headers, response.data)) response = client.get('/') print('%s\n%s%s' % (response.status, response.headers, response.data)) response = client.get('/hello') print('%s\n%s%s' % (response.status, response.headers, response.data)) response = client.delete('/hello') print('%s\n%s%s' % (response.status, response.headers, response.data)) response = client.get('/') print('%s\n%s%s' % (response.status, response.headers, response.data)) response = client.get('/hello') print('%s\n%s%s' % (response.status, response.headers, response.data)) response = client.delete('/hello') print('%s\n%s%s' % (response.status, response.headers, response.data))
def setUp(self): app = Flask(__name__) Funnel(app) app.config['CSS_BUNDLES'] = { 'css-bundle': ( 'css/test.css', 'less/test.less', 'scss/test.scss', 'stylus/test.styl', ), } app.config['JS_BUNDLES'] = { 'js-bundle': ( 'js/test1.js', 'js/test2.js', 'coffee/test.coffee', ), } @app.route('/') def index(): return render_template_string( "{{ css('css-bundle') }} {{ js('js-bundle') }}") self.app = app self.client = app.test_client()
def test_flask(self): app = Flask(__name__) db = SQLAlchemy(app) app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///:memory:' class Cities(db.Model): __tablename__ = 'users' id = Column(Integer, primary_key=True) name = Column(String) population = Column(Integer) def __init__(self, name, population): self.name = name self.population = population app.config['TESTING'] = True app = app.test_client() db.create_all() city = Cities("Cordoba", 1000000) db.session.add(city) city = Cities("Rafaela", 99000) db.session.add(city) db.session.commit() query_string = '{ "sort": { "population" : "desc" } }' results = elastic_query(Cities, query_string) assert(results[0].name == 'Cordoba')
def test_whitelisting(self): app = Flask(__name__) limiter = Limiter(app, global_limits=["1/minute"], headers_enabled=True) @app.route("/") def t(): return "test" @limiter.request_filter def w(): if request.headers.get("internal", None) == "true": return True return False with hiro.Timeline().freeze() as timeline: with app.test_client() as cli: self.assertEqual(cli.get("/").status_code, 200) self.assertEqual(cli.get("/").status_code, 429) timeline.forward(60) self.assertEqual(cli.get("/").status_code, 200) for i in range(0,10): self.assertEqual( cli.get("/", headers = {"internal": "true"}).status_code, 200 )
def test_custom_headers_from_config(self): app = Flask(__name__) app.config.setdefault(C.HEADER_LIMIT, "X-Limit") app.config.setdefault(C.HEADER_REMAINING, "X-Remaining") app.config.setdefault(C.HEADER_RESET, "X-Reset") limiter = Limiter(app, global_limits=["10/minute"], headers_enabled=True) @app.route("/t1") @limiter.limit("2/second; 10 per minute; 20/hour") def t(): return "test" with hiro.Timeline().freeze() as timeline: with app.test_client() as cli: for i in range(11): resp = cli.get("/t1") timeline.forward(1) self.assertEqual( resp.headers.get('X-Limit'), '10' ) self.assertEqual( resp.headers.get('X-Remaining'), '0' ) self.assertEqual( resp.headers.get('X-Reset'), str(int(time.time() + 49)) )
def test_headers_breach(self): app = Flask(__name__) limiter = Limiter(app, global_limits=["10/minute"], headers_enabled=True) @app.route("/t1") @limiter.limit("2/second; 10 per minute; 20/hour") def t(): return "test" with hiro.Timeline().freeze() as timeline: with app.test_client() as cli: for i in range(11): resp = cli.get("/t1") timeline.forward(1) self.assertEqual( resp.headers.get('X-RateLimit-Limit'), '10' ) self.assertEqual( resp.headers.get('X-RateLimit-Remaining'), '0' ) self.assertEqual( resp.headers.get('X-RateLimit-Reset'), str(int(time.time() + 49)) )
def setUp(self): app = Flask(__name__) app.config['SECRET_KEY'] = 'my secret' digest_auth_my_realm = HTTPDigestAuth(realm='My Realm') @digest_auth_my_realm.get_password def get_digest_password_3(username): if username == 'susan': return 'hello' elif username == 'john': return 'bye' else: return None @app.route('/') def index(): return 'index' @app.route('/digest-with-realm') @digest_auth_my_realm.login_required def digest_auth_my_realm_route(): return 'digest_auth_my_realm:' + digest_auth_my_realm.username() self.app = app self.client = app.test_client()
class MethodViewLoginTestCase(unittest.TestCase): def setUp(self): self.app = Flask(__name__) self.login_manager = LoginManager() self.login_manager.init_app(self.app) self.login_manager._login_disabled = False class SecretEndpoint(MethodView): decorators = [ login_required, fresh_login_required, ] def options(self): return u'' def get(self): return u'' self.app.add_url_rule('/secret', view_func=SecretEndpoint.as_view('secret')) def test_options_call_exempt(self): with self.app.test_client() as c: result = c.open('/secret', method='OPTIONS') self.assertEqual(result.status_code, 200)