@ -35,192 +35,174 @@ def has_encoding(name):
class TestJSON ( object ) :
class TestJSON ( object ) :
def test_ignore_cached_json ( self , app ) :
def test_ignore_cached_json ( self ) :
app = flask . Flask ( __name__ )
with app . test_request_context ( ' / ' , method = ' POST ' , data = ' malformed ' ,
with app . test_request_context ( ' / ' , method = ' POST ' , data = ' malformed ' ,
content_type = ' application/json ' ) :
content_type = ' application/json ' ) :
assert flask . request . get_json ( silent = True , cache = True ) is None
assert flask . request . get_json ( silent = True , cache = True ) is None
with pytest . raises ( BadRequest ) :
with pytest . raises ( BadRequest ) :
flask . request . get_json ( silent = False , cache = False )
flask . request . get_json ( silent = False , cache = False )
def test_post_empty_json_adds_exception_to_response_content_in_debug ( self ) :
def test_post_empty_json_adds_exception_to_response_content_in_debug ( self , app , client ) :
app = flask . Flask ( __name__ )
app . config [ ' DEBUG ' ] = True
app . config [ ' DEBUG ' ] = True
@app . route ( ' /json ' , methods = [ ' POST ' ] )
@app . route ( ' /json ' , methods = [ ' POST ' ] )
def post_json ( ) :
def post_json ( ) :
flask . request . get_json ( )
flask . request . get_json ( )
return None
return None
c = app . test_client ( )
rv = c . post ( ' /json ' , data = None , content_type = ' application/json ' )
rv = client . post ( ' /json ' , data = None , content_type = ' application/json ' )
assert rv . status_code == 400
assert rv . status_code == 400
assert b ' Failed to decode JSON object ' in rv . data
assert b ' Failed to decode JSON object ' in rv . data
def test_post_empty_json_wont_add_exception_to_response_if_no_debug ( self ) :
def test_post_empty_json_wont_add_exception_to_response_if_no_debug ( self , app , client ) :
app = flask . Flask ( __name__ )
app . config [ ' DEBUG ' ] = False
app . config [ ' DEBUG ' ] = False
@app . route ( ' /json ' , methods = [ ' POST ' ] )
@app . route ( ' /json ' , methods = [ ' POST ' ] )
def post_json ( ) :
def post_json ( ) :
flask . request . get_json ( )
flask . request . get_json ( )
return None
return None
c = app . test_client ( )
rv = c . post ( ' /json ' , data = None , content_type = ' application/json ' )
rv = client . post ( ' /json ' , data = None , content_type = ' application/json ' )
assert rv . status_code == 400
assert rv . status_code == 400
assert b ' Failed to decode JSON object ' not in rv . data
assert b ' Failed to decode JSON object ' not in rv . data
def test_json_bad_requests ( self ) :
def test_json_bad_requests ( self , app , client ) :
app = flask . Flask ( __name__ )
@app . route ( ' /json ' , methods = [ ' POST ' ] )
@app . route ( ' /json ' , methods = [ ' POST ' ] )
def return_json ( ) :
def return_json ( ) :
return flask . jsonify ( foo = text_type ( flask . request . get_json ( ) ) )
return flask . jsonify ( foo = text_type ( flask . request . get_json ( ) ) )
c = app . test_client ( )
rv = c . post ( ' /json ' , data = ' malformed ' , content_type = ' application/json ' )
rv = client . post ( ' /json ' , data = ' malformed ' , content_type = ' application/json ' )
assert rv . status_code == 400
assert rv . status_code == 400
def test_json_custom_mimetypes ( self ) :
def test_json_custom_mimetypes ( self , app , client ) :
app = flask . Flask ( __name__ )
@app . route ( ' /json ' , methods = [ ' POST ' ] )
@app . route ( ' /json ' , methods = [ ' POST ' ] )
def return_json ( ) :
def return_json ( ) :
return flask . request . get_json ( )
return flask . request . get_json ( )
c = app . test_client ( )
rv = c . post ( ' /json ' , data = ' " foo " ' , content_type = ' application/x+json ' )
rv = client . post ( ' /json ' , data = ' " foo " ' , content_type = ' application/x+json ' )
assert rv . data == b ' foo '
assert rv . data == b ' foo '
def test_json_body_encoding ( self ) :
def test_json_body_encoding ( self , app , client ) :
app = flask . Flask ( __name__ )
app . testing = True
app . testing = True
@app . route ( ' / ' )
@app . route ( ' / ' )
def index ( ) :
def index ( ) :
return flask . request . get_json ( )
return flask . request . get_json ( )
c = app . test_client ( )
resp = client . get ( ' / ' , data = u ' " Hällo Wörld " ' . encode ( ' iso-8859-15 ' ) ,
resp = c . get ( ' / ' , data = u ' " Hällo Wörld " ' . encode ( ' iso-8859-15 ' ) ,
content_type = ' application/json; charset=iso-8859-15 ' )
content_type = ' application/json; charset=iso-8859-15 ' )
assert resp . data == u ' Hällo Wörld ' . encode ( ' utf-8 ' )
assert resp . data == u ' Hällo Wörld ' . encode ( ' utf-8 ' )
def test_json_as_unicode ( self ) :
@pytest . mark . parametrize ( ' test_value,expected ' , [ ( True , ' " \\ u2603 " ' ) , ( False , u ' " \u2603 " ' ) ] )
app = flask . Flask ( __name__ )
def test_json_as_unicode ( self , test_value , expected , app , app_ctx ) :
app . config [ ' JSON_AS_ASCII ' ] = True
app . config [ ' JSON_AS_ASCII ' ] = test_value
with app . app_context ( ) :
rv = flask . json . dumps ( u ' \N{SNOWMAN} ' )
rv = flask . json . dumps ( u ' \N{SNOWMAN} ' )
assert rv == ' " \\ u2603 " '
assert rv == expected
app . config [ ' JSON_AS_ASCII ' ] = False
def test_json_dump_to_file ( self , app , app_ctx ) :
with app . app_context ( ) :
rv = flask . json . dumps ( u ' \N{SNOWMAN} ' )
assert rv == u ' " \u2603 " '
def test_json_dump_to_file ( self ) :
app = flask . Flask ( __name__ )
test_data = { ' name ' : ' Flask ' }
test_data = { ' name ' : ' Flask ' }
out = StringIO ( )
out = StringIO ( )
with app . app_context ( ) :
flask . json . dump ( test_data , out )
flask . json . dump ( test_data , out )
out . seek ( 0 )
out . seek ( 0 )
rv = flask . json . load ( out )
rv = flask . json . load ( out )
assert rv == test_data
assert rv == test_data
@pytest . mark . parametrize ( ' test_value ' , [ 0 , - 1 , 1 , 23 , 3.14 , ' s ' , " longer string " , True , False , None ] )
@pytest . mark . parametrize ( ' test_value ' , [ 0 , - 1 , 1 , 23 , 3.14 , ' s ' , " longer string " , True , False , None ] )
def test_jsonify_basic_types ( self , test_value ) :
def test_jsonify_basic_types ( self , test_value , app , client ) :
""" Test jsonify with basic types. """
""" Test jsonify with basic types. """
app = flask . Flask ( __name__ )
c = app . test_client ( )
url = ' /jsonify_basic_types '
url = ' /jsonify_basic_types '
app . add_url_rule ( url , url , lambda x = test_value : flask . jsonify ( x ) )
app . add_url_rule ( url , url , lambda x = test_value : flask . jsonify ( x ) )
rv = c . get ( url )
rv = client . get ( url )
assert rv . mimetype == ' application/json '
assert rv . mimetype == ' application/json '
assert flask . json . loads ( rv . data ) == test_value
assert flask . json . loads ( rv . data ) == test_value
def test_jsonify_dicts ( self ) :
def test_jsonify_dicts ( self , app , client ) :
""" Test jsonify with dicts and kwargs unpacking. """
""" Test jsonify with dicts and kwargs unpacking. """
d = dict (
d = { ' a ' : 0 , ' b ' : 23 , ' c ' : 3.14 , ' d ' : ' t ' ,
a = 0 , b = 23 , c = 3.14 , d = ' t ' , e = ' Hi ' , f = True , g = False ,
' e ' : ' Hi ' , ' f ' : True , ' g ' : False ,
h = [ ' test list ' , 10 , False ] ,
' h ' : [ ' test list ' , 10 , False ] ,
i = { ' test ' : ' dict ' }
' i ' : { ' test ' : ' dict ' } }
)
app = flask . Flask ( __name__ )
@app . route ( ' /kw ' )
@app . route ( ' /kw ' )
def return_kwargs ( ) :
def return_kwargs ( ) :
return flask . jsonify ( * * d )
return flask . jsonify ( * * d )
@app . route ( ' /dict ' )
@app . route ( ' /dict ' )
def return_dict ( ) :
def return_dict ( ) :
return flask . jsonify ( d )
return flask . jsonify ( d )
c = app . test_client ( )
for url in ' /kw ' , ' /dict ' :
for url in ' /kw ' , ' /dict ' :
rv = c . get ( url )
rv = client . get ( url )
assert rv . mimetype == ' application/json '
assert rv . mimetype == ' application/json '
assert flask . json . loads ( rv . data ) == d
assert flask . json . loads ( rv . data ) == d
def test_jsonify_arrays ( self ) :
def test_jsonify_arrays ( self , app , client ) :
""" Test jsonify of lists and args unpacking. """
""" Test jsonify of lists and args unpacking. """
l = [
l = [
0 , 42 , 3.14 , ' t ' , ' hello ' , True , False ,
0 , 42 , 3.14 , ' t ' , ' hello ' , True , False ,
[ ' test list ' , 2 , False ] ,
[ ' test list ' , 2 , False ] ,
{ ' test ' : ' dict ' }
{ ' test ' : ' dict ' }
]
]
app = flask . Flask ( __name__ )
@app . route ( ' /args_unpack ' )
@app . route ( ' /args_unpack ' )
def return_args_unpack ( ) :
def return_args_unpack ( ) :
return flask . jsonify ( * l )
return flask . jsonify ( * l )
@app . route ( ' /array ' )
@app . route ( ' /array ' )
def return_array ( ) :
def return_array ( ) :
return flask . jsonify ( l )
return flask . jsonify ( l )
c = app . test_client ( )
for url in ' /args_unpack ' , ' /array ' :
for url in ' /args_unpack ' , ' /array ' :
rv = c . get ( url )
rv = client . get ( url )
assert rv . mimetype == ' application/json '
assert rv . mimetype == ' application/json '
assert flask . json . loads ( rv . data ) == l
assert flask . json . loads ( rv . data ) == l
def test_jsonify_date_types ( self ) :
def test_jsonify_date_types ( self , app , client ) :
""" Test jsonify with datetime.date and datetime.datetime types. """
""" Test jsonify with datetime.date and datetime.datetime types. """
test_dates = (
test_dates = (
datetime . datetime ( 1973 , 3 , 11 , 6 , 30 , 45 ) ,
datetime . datetime ( 1973 , 3 , 11 , 6 , 30 , 45 ) ,
datetime . date ( 1975 , 1 , 5 )
datetime . date ( 1975 , 1 , 5 )
)
)
app = flask . Flask ( __name__ )
c = app . test_client ( )
for i , d in enumerate ( test_dates ) :
for i , d in enumerate ( test_dates ) :
url = ' /datetest {0} ' . format ( i )
url = ' /datetest {0} ' . format ( i )
app . add_url_rule ( url , str ( i ) , lambda val = d : flask . jsonify ( x = val ) )
app . add_url_rule ( url , str ( i ) , lambda val = d : flask . jsonify ( x = val ) )
rv = c . get ( url )
rv = client . get ( url )
assert rv . mimetype == ' application/json '
assert rv . mimetype == ' application/json '
assert flask . json . loads ( rv . data ) [ ' x ' ] == http_date ( d . timetuple ( ) )
assert flask . json . loads ( rv . data ) [ ' x ' ] == http_date ( d . timetuple ( ) )
def test_jsonify_uuid_types ( self ) :
def test_jsonify_uuid_types ( self , app , client ) :
""" Test jsonify with uuid.UUID types """
""" Test jsonify with uuid.UUID types """
test_uuid = uuid . UUID ( bytes = b ' \xDE \xAD \xBE \xEF ' * 4 )
test_uuid = uuid . UUID ( bytes = b ' \xDE \xAD \xBE \xEF ' * 4 )
app = flask . Flask ( __name__ )
url = ' /uuid_test '
url = ' /uuid_test '
app . add_url_rule ( url , url , lambda : flask . jsonify ( x = test_uuid ) )
app . add_url_rule ( url , url , lambda : flask . jsonify ( x = test_uuid ) )
c = app . test_client ( )
rv = client . get ( url )
rv = c . get ( url )
rv_x = flask . json . loads ( rv . data ) [ ' x ' ]
rv_x = flask . json . loads ( rv . data ) [ ' x ' ]
assert rv_x == str ( test_uuid )
assert rv_x == str ( test_uuid )
rv_uuid = uuid . UUID ( rv_x )
rv_uuid = uuid . UUID ( rv_x )
assert rv_uuid == test_uuid
assert rv_uuid == test_uuid
def test_json_attr ( self ) :
def test_json_attr ( self , app , client ) :
app = flask . Flask ( __name__ )
@app . route ( ' /add ' , methods = [ ' POST ' ] )
@app . route ( ' /add ' , methods = [ ' POST ' ] )
def add ( ) :
def add ( ) :
json = flask . request . get_json ( )
json = flask . request . get_json ( )
return text_type ( json [ ' a ' ] + json [ ' b ' ] )
return text_type ( json [ ' a ' ] + json [ ' b ' ] )
c = app . test_client ( )
rv = c . post ( ' /add ' , data = flask . json . dumps ( { ' a ' : 1 , ' b ' : 2 } ) ,
rv = client . post ( ' /add ' , data = flask . json . dumps ( { ' a ' : 1 , ' b ' : 2 } ) ,
content_type = ' application/json ' )
content_type = ' application/json ' )
assert rv . data == b ' 3 '
assert rv . data == b ' 3 '
def test_template_escaping ( self ) :
def test_template_escaping ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
render = flask . render_template_string
render = flask . render_template_string
with app . test_request_context ( ) :
rv = flask . json . htmlsafe_dumps ( ' </script> ' )
rv = flask . json . htmlsafe_dumps ( ' </script> ' )
assert rv == u ' " \\ u003c/script \\ u003e " '
assert rv == u ' " \\ u003c/script \\ u003e " '
assert type ( rv ) == text_type
assert type ( rv ) == text_type
@ -238,37 +220,41 @@ class TestJSON(object):
data = { ' x ' : [ " foo " , " bar " , " baz ' " ] } )
data = { ' x ' : [ " foo " , " bar " , " baz ' " ] } )
assert rv == ' <a ng-data= \' { " x " : [ " foo " , " bar " , " baz \\ u0027 " ]} \' ></a> '
assert rv == ' <a ng-data= \' { " x " : [ " foo " , " bar " , " baz \\ u0027 " ]} \' ></a> '
def test_json_customization ( self ) :
def test_json_customization ( self , app , client ) :
class X ( object ) :
class X ( object ) :
def __init__ ( self , val ) :
def __init__ ( self , val ) :
self . val = val
self . val = val
class MyEncoder ( flask . json . JSONEncoder ) :
class MyEncoder ( flask . json . JSONEncoder ) :
def default ( self , o ) :
def default ( self , o ) :
if isinstance ( o , X ) :
if isinstance ( o , X ) :
return ' < %d > ' % o . val
return ' < %d > ' % o . val
return flask . json . JSONEncoder . default ( self , o )
return flask . json . JSONEncoder . default ( self , o )
class MyDecoder ( flask . json . JSONDecoder ) :
class MyDecoder ( flask . json . JSONDecoder ) :
def __init__ ( self , * args , * * kwargs ) :
def __init__ ( self , * args , * * kwargs ) :
kwargs . setdefault ( ' object_hook ' , self . object_hook )
kwargs . setdefault ( ' object_hook ' , self . object_hook )
flask . json . JSONDecoder . __init__ ( self , * args , * * kwargs )
flask . json . JSONDecoder . __init__ ( self , * args , * * kwargs )
def object_hook ( self , obj ) :
def object_hook ( self , obj ) :
if len ( obj ) == 1 and ' _foo ' in obj :
if len ( obj ) == 1 and ' _foo ' in obj :
return X ( obj [ ' _foo ' ] )
return X ( obj [ ' _foo ' ] )
return obj
return obj
app = flask . Flask ( __name__ )
app . testing = True
app . testing = True
app . json_encoder = MyEncoder
app . json_encoder = MyEncoder
app . json_decoder = MyDecoder
app . json_decoder = MyDecoder
@app . route ( ' / ' , methods = [ ' POST ' ] )
@app . route ( ' / ' , methods = [ ' POST ' ] )
def index ( ) :
def index ( ) :
return flask . json . dumps ( flask . request . get_json ( ) [ ' x ' ] )
return flask . json . dumps ( flask . request . get_json ( ) [ ' x ' ] )
c = app . test_client ( )
rv = c . post ( ' / ' , data = flask . json . dumps ( {
rv = client . post ( ' / ' , data = flask . json . dumps ( {
' x ' : { ' _foo ' : 42 }
' x ' : { ' _foo ' : 42 }
} ) , content_type = ' application/json ' )
} ) , content_type = ' application/json ' )
assert rv . data == b ' " <42> " '
assert rv . data == b ' " <42> " '
def test_blueprint_json_customization ( self ) :
def test_blueprint_json_customization ( self , app , client ) :
class X ( object ) :
class X ( object ) :
def __init__ ( self , val ) :
def __init__ ( self , val ) :
self . val = val
self . val = val
@ -299,20 +285,18 @@ class TestJSON(object):
def index ( ) :
def index ( ) :
return flask . json . dumps ( flask . request . get_json ( ) [ ' x ' ] )
return flask . json . dumps ( flask . request . get_json ( ) [ ' x ' ] )
app = flask . Flask ( __name__ )
app . testing = True
app . testing = True
app . register_blueprint ( bp )
app . register_blueprint ( bp )
c = app . test_client ( )
rv = client . post ( ' /bp ' , data = flask . json . dumps ( {
rv = c . post ( ' /bp ' , data = flask . json . dumps ( {
' x ' : { ' _foo ' : 42 }
' x ' : { ' _foo ' : 42 }
} ) , content_type = ' application/json ' )
} ) , content_type = ' application/json ' )
assert rv . data == b ' " <42> " '
assert rv . data == b ' " <42> " '
def test_modified_url_encoding ( self ) :
def test_modified_url_encoding ( self , app ) :
class ModifiedRequest ( flask . Request ) :
class ModifiedRequest ( flask . Request ) :
url_charset = ' euc-kr '
url_charset = ' euc-kr '
app = flask . Flask ( __name__ )
app . testing = True
app . testing = True
app . request_class = ModifiedRequest
app . request_class = ModifiedRequest
app . url_map . charset = ' euc-kr '
app . url_map . charset = ' euc-kr '
@ -328,8 +312,7 @@ class TestJSON(object):
if not has_encoding ( ' euc-kr ' ) :
if not has_encoding ( ' euc-kr ' ) :
test_modified_url_encoding = None
test_modified_url_encoding = None
def test_json_key_sorting ( self ) :
def test_json_key_sorting ( self , app , client ) :
app = flask . Flask ( __name__ )
app . testing = True
app . testing = True
app . debug = True
app . debug = True
@ -340,8 +323,7 @@ class TestJSON(object):
def index ( ) :
def index ( ) :
return flask . jsonify ( values = d )
return flask . jsonify ( values = d )
c = app . test_client ( )
rv = client . get ( ' / ' )
rv = c . get ( ' / ' )
lines = [ x . strip ( ) for x in rv . data . strip ( ) . decode ( ' utf-8 ' ) . splitlines ( ) ]
lines = [ x . strip ( ) for x in rv . data . strip ( ) . decode ( ' utf-8 ' ) . splitlines ( ) ]
sorted_by_str = [
sorted_by_str = [
' { ' ,
' { ' ,
@ -401,11 +383,9 @@ class TestJSON(object):
except AssertionError :
except AssertionError :
assert lines == sorted_by_str
assert lines == sorted_by_str
class TestSendfile ( object ) :
def test_send_file_regular ( self ) :
class TestSendfile ( object ) :
app = flask . Flask ( __name__ )
def test_send_file_regular ( self , app , req_ctx ) :
with app . test_request_context ( ) :
rv = flask . send_file ( ' static/index.html ' )
rv = flask . send_file ( ' static/index.html ' )
assert rv . direct_passthrough
assert rv . direct_passthrough
assert rv . mimetype == ' text/html '
assert rv . mimetype == ' text/html '
@ -414,10 +394,8 @@ class TestSendfile(object):
assert rv . data == f . read ( )
assert rv . data == f . read ( )
rv . close ( )
rv . close ( )
def test_send_file_xsendfile ( self , catch_deprecation_warnings ) :
def test_send_file_xsendfile ( self , app , req_ctx , catch_deprecation_warnings ) :
app = flask . Flask ( __name__ )
app . use_x_sendfile = True
app . use_x_sendfile = True
with app . test_request_context ( ) :
rv = flask . send_file ( ' static/index.html ' )
rv = flask . send_file ( ' static/index.html ' )
assert rv . direct_passthrough
assert rv . direct_passthrough
assert ' x-sendfile ' in rv . headers
assert ' x-sendfile ' in rv . headers
@ -426,8 +404,7 @@ class TestSendfile(object):
assert rv . mimetype == ' text/html '
assert rv . mimetype == ' text/html '
rv . close ( )
rv . close ( )
def test_send_file_last_modified ( self ) :
def test_send_file_last_modified ( self , app , client ) :
app = flask . Flask ( __name__ )
last_modified = datetime . datetime ( 1999 , 1 , 1 )
last_modified = datetime . datetime ( 1999 , 1 , 1 )
@app . route ( ' / ' )
@app . route ( ' / ' )
@ -436,26 +413,18 @@ class TestSendfile(object):
last_modified = last_modified ,
last_modified = last_modified ,
mimetype = ' text/plain ' )
mimetype = ' text/plain ' )
c = app . test_client ( )
rv = client . get ( ' / ' )
rv = c . get ( ' / ' )
assert rv . last_modified == last_modified
assert rv . last_modified == last_modified
def test_send_file_object_without_mimetype ( self ) :
def test_send_file_object_without_mimetype ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
with app . test_request_context ( ) :
with pytest . raises ( ValueError ) as excinfo :
with pytest . raises ( ValueError ) as excinfo :
flask . send_file ( StringIO ( " LOL " ) )
flask . send_file ( StringIO ( " LOL " ) )
assert ' Unable to infer MIME-type ' in str ( excinfo )
assert ' Unable to infer MIME-type ' in str ( excinfo )
assert ' no filename is available ' in str ( excinfo )
assert ' no filename is available ' in str ( excinfo )
with app . test_request_context ( ) :
flask . send_file ( StringIO ( " LOL " ) , attachment_filename = ' filename ' )
flask . send_file ( StringIO ( " LOL " ) , attachment_filename = ' filename ' )
def test_send_file_object ( self ) :
def test_send_file_object ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
with app . test_request_context ( ) :
with open ( os . path . join ( app . root_path , ' static/index.html ' ) , mode = ' rb ' ) as f :
with open ( os . path . join ( app . root_path , ' static/index.html ' ) , mode = ' rb ' ) as f :
rv = flask . send_file ( f , mimetype = ' text/html ' )
rv = flask . send_file ( f , mimetype = ' text/html ' )
rv . direct_passthrough = False
rv . direct_passthrough = False
@ -466,7 +435,6 @@ class TestSendfile(object):
app . use_x_sendfile = True
app . use_x_sendfile = True
with app . test_request_context ( ) :
with open ( os . path . join ( app . root_path , ' static/index.html ' ) ) as f :
with open ( os . path . join ( app . root_path , ' static/index.html ' ) ) as f :
rv = flask . send_file ( f , mimetype = ' text/html ' )
rv = flask . send_file ( f , mimetype = ' text/html ' )
assert rv . mimetype == ' text/html '
assert rv . mimetype == ' text/html '
@ -474,7 +442,6 @@ class TestSendfile(object):
rv . close ( )
rv . close ( )
app . use_x_sendfile = False
app . use_x_sendfile = False
with app . test_request_context ( ) :
f = StringIO ( ' Test ' )
f = StringIO ( ' Test ' )
rv = flask . send_file ( f , mimetype = ' application/octet-stream ' )
rv = flask . send_file ( f , mimetype = ' application/octet-stream ' )
rv . direct_passthrough = False
rv . direct_passthrough = False
@ -485,8 +452,10 @@ class TestSendfile(object):
class PyStringIO ( object ) :
class PyStringIO ( object ) :
def __init__ ( self , * args , * * kwargs ) :
def __init__ ( self , * args , * * kwargs ) :
self . _io = StringIO ( * args , * * kwargs )
self . _io = StringIO ( * args , * * kwargs )
def __getattr__ ( self , name ) :
def __getattr__ ( self , name ) :
return getattr ( self . _io , name )
return getattr ( self . _io , name )
f = PyStringIO ( ' Test ' )
f = PyStringIO ( ' Test ' )
f . name = ' test.txt '
f . name = ' test.txt '
rv = flask . send_file ( f , attachment_filename = f . name )
rv = flask . send_file ( f , attachment_filename = f . name )
@ -504,7 +473,6 @@ class TestSendfile(object):
app . use_x_sendfile = True
app . use_x_sendfile = True
with app . test_request_context ( ) :
f = StringIO ( ' Test ' )
f = StringIO ( ' Test ' )
rv = flask . send_file ( f , mimetype = ' text/html ' )
rv = flask . send_file ( f , mimetype = ' text/html ' )
assert ' x-sendfile ' not in rv . headers
assert ' x-sendfile ' not in rv . headers
@ -514,48 +482,44 @@ class TestSendfile(object):
not callable ( getattr ( Range , ' to_content_range_header ' , None ) ) ,
not callable ( getattr ( Range , ' to_content_range_header ' , None ) ) ,
reason = " not implement within werkzeug "
reason = " not implement within werkzeug "
)
)
def test_send_file_range_request ( self ) :
def test_send_file_range_request ( self , app , client ) :
app = flask . Flask ( __name__ )
@app . route ( ' / ' )
@app . route ( ' / ' )
def index ( ) :
def index ( ) :
return flask . send_file ( ' static/index.html ' , conditional = True )
return flask . send_file ( ' static/index.html ' , conditional = True )
c = app . test_client ( )
rv = client . get ( ' / ' , headers = { ' Range ' : ' bytes=4-15 ' } )
rv = c . get ( ' / ' , headers = { ' Range ' : ' bytes=4-15 ' } )
assert rv . status_code == 206
assert rv . status_code == 206
with app . open_resource ( ' static/index.html ' ) as f :
with app . open_resource ( ' static/index.html ' ) as f :
assert rv . data == f . read ( ) [ 4 : 16 ]
assert rv . data == f . read ( ) [ 4 : 16 ]
rv . close ( )
rv . close ( )
rv = c . get ( ' / ' , headers = { ' Range ' : ' bytes=4- ' } )
rv = client . get ( ' / ' , headers = { ' Range ' : ' bytes=4- ' } )
assert rv . status_code == 206
assert rv . status_code == 206
with app . open_resource ( ' static/index.html ' ) as f :
with app . open_resource ( ' static/index.html ' ) as f :
assert rv . data == f . read ( ) [ 4 : ]
assert rv . data == f . read ( ) [ 4 : ]
rv . close ( )
rv . close ( )
rv = c . get ( ' / ' , headers = { ' Range ' : ' bytes=4-1000 ' } )
rv = client . get ( ' / ' , headers = { ' Range ' : ' bytes=4-1000 ' } )
assert rv . status_code == 206
assert rv . status_code == 206
with app . open_resource ( ' static/index.html ' ) as f :
with app . open_resource ( ' static/index.html ' ) as f :
assert rv . data == f . read ( ) [ 4 : ]
assert rv . data == f . read ( ) [ 4 : ]
rv . close ( )
rv . close ( )
rv = c . get ( ' / ' , headers = { ' Range ' : ' bytes=-10 ' } )
rv = client . get ( ' / ' , headers = { ' Range ' : ' bytes=-10 ' } )
assert rv . status_code == 206
assert rv . status_code == 206
with app . open_resource ( ' static/index.html ' ) as f :
with app . open_resource ( ' static/index.html ' ) as f :
assert rv . data == f . read ( ) [ - 10 : ]
assert rv . data == f . read ( ) [ - 10 : ]
rv . close ( )
rv . close ( )
rv = c . get ( ' / ' , headers = { ' Range ' : ' bytes=1000- ' } )
rv = client . get ( ' / ' , headers = { ' Range ' : ' bytes=1000- ' } )
assert rv . status_code == 416
assert rv . status_code == 416
rv . close ( )
rv . close ( )
rv = c . get ( ' / ' , headers = { ' Range ' : ' bytes=- ' } )
rv = client . get ( ' / ' , headers = { ' Range ' : ' bytes=- ' } )
assert rv . status_code == 416
assert rv . status_code == 416
rv . close ( )
rv . close ( )
rv = c . get ( ' / ' , headers = { ' Range ' : ' somethingsomething ' } )
rv = client . get ( ' / ' , headers = { ' Range ' : ' somethingsomething ' } )
assert rv . status_code == 416
assert rv . status_code == 416
rv . close ( )
rv . close ( )
@ -563,19 +527,19 @@ class TestSendfile(object):
os . path . join ( app . root_path , ' static/index.html ' ) ) ) . replace (
os . path . join ( app . root_path , ' static/index.html ' ) ) ) . replace (
microsecond = 0 )
microsecond = 0 )
rv = c . get ( ' / ' , headers = { ' Range ' : ' bytes=4-15 ' ,
rv = client . get ( ' / ' , headers = { ' Range ' : ' bytes=4-15 ' ,
' If-Range ' : http_date ( last_modified ) } )
' If-Range ' : http_date ( last_modified ) } )
assert rv . status_code == 206
assert rv . status_code == 206
rv . close ( )
rv . close ( )
rv = c . get ( ' / ' , headers = { ' Range ' : ' bytes=4-15 ' , ' If-Range ' : http_date (
rv = client . get ( ' / ' , headers = { ' Range ' : ' bytes=4-15 ' , ' If-Range ' : http_date (
datetime . datetime ( 1999 , 1 , 1 ) ) } )
datetime . datetime ( 1999 , 1 , 1 ) ) } )
assert rv . status_code == 200
assert rv . status_code == 200
rv . close ( )
rv . close ( )
def test_attachment ( self ) :
def test_attachment ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
app = flask . Flask ( __name__ )
with app . test_request_context ( ) :
with open ( os . path . join ( app . root_path , ' static/index.html ' ) ) as f :
with open ( os . path . join ( app . root_path , ' static/index.html ' ) ) as f :
rv = flask . send_file ( f , as_attachment = True ,
rv = flask . send_file ( f , as_attachment = True ,
attachment_filename = ' index.html ' )
attachment_filename = ' index.html ' )
@ -586,14 +550,12 @@ class TestSendfile(object):
assert ' filename* ' not in rv . headers [ ' Content-Disposition ' ]
assert ' filename* ' not in rv . headers [ ' Content-Disposition ' ]
rv . close ( )
rv . close ( )
with app . test_request_context ( ) :
rv = flask . send_file ( ' static/index.html ' , as_attachment = True )
rv = flask . send_file ( ' static/index.html ' , as_attachment = True )
value , options = parse_options_header ( rv . headers [ ' Content-Disposition ' ] )
value , options = parse_options_header ( rv . headers [ ' Content-Disposition ' ] )
assert value == ' attachment '
assert value == ' attachment '
assert options [ ' filename ' ] == ' index.html '
assert options [ ' filename ' ] == ' index.html '
rv . close ( )
rv . close ( )
with app . test_request_context ( ) :
rv = flask . send_file ( StringIO ( ' Test ' ) , as_attachment = True ,
rv = flask . send_file ( StringIO ( ' Test ' ) , as_attachment = True ,
attachment_filename = ' index.txt ' ,
attachment_filename = ' index.txt ' ,
add_etags = False )
add_etags = False )
@ -603,10 +565,7 @@ class TestSendfile(object):
assert options [ ' filename ' ] == ' index.txt '
assert options [ ' filename ' ] == ' index.txt '
rv . close ( )
rv . close ( )
def test_attachment_with_utf8_filename ( self ) :
def test_attachment_with_utf8_filename ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
with app . test_request_context ( ) :
rv = flask . send_file ( ' static/index.html ' , as_attachment = True , attachment_filename = u ' Ñandú/pingüino.txt ' )
rv = flask . send_file ( ' static/index.html ' , as_attachment = True , attachment_filename = u ' Ñandú/pingüino.txt ' )
content_disposition = set ( rv . headers [ ' Content-Disposition ' ] . split ( ' ; ' ) )
content_disposition = set ( rv . headers [ ' Content-Disposition ' ] . split ( ' ; ' ) )
assert content_disposition == set ( (
assert content_disposition == set ( (
@ -616,10 +575,9 @@ class TestSendfile(object):
) )
) )
rv . close ( )
rv . close ( )
def test_static_file ( self ) :
def test_static_file ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
# default cache timeout is 12 hours
# default cache timeout is 12 hours
with app . test_request_context ( ) :
# Test with static file handler.
# Test with static file handler.
rv = app . send_static_file ( ' index.html ' )
rv = app . send_static_file ( ' index.html ' )
cc = parse_cache_control_header ( rv . headers [ ' Cache-Control ' ] )
cc = parse_cache_control_header ( rv . headers [ ' Cache-Control ' ] )
@ -631,7 +589,7 @@ class TestSendfile(object):
assert cc . max_age == 12 * 60 * 60
assert cc . max_age == 12 * 60 * 60
rv . close ( )
rv . close ( )
app . config [ ' SEND_FILE_MAX_AGE_DEFAULT ' ] = 3600
app . config [ ' SEND_FILE_MAX_AGE_DEFAULT ' ] = 3600
with app . test_request_context ( ) :
# Test with static file handler.
# Test with static file handler.
rv = app . send_static_file ( ' index.html ' )
rv = app . send_static_file ( ' index.html ' )
cc = parse_cache_control_header ( rv . headers [ ' Cache-Control ' ] )
cc = parse_cache_control_header ( rv . headers [ ' Cache-Control ' ] )
@ -642,9 +600,11 @@ class TestSendfile(object):
cc = parse_cache_control_header ( rv . headers [ ' Cache-Control ' ] )
cc = parse_cache_control_header ( rv . headers [ ' Cache-Control ' ] )
assert cc . max_age == 3600
assert cc . max_age == 3600
rv . close ( )
rv . close ( )
class StaticFileApp ( flask . Flask ) :
class StaticFileApp ( flask . Flask ) :
def get_send_file_max_age ( self , filename ) :
def get_send_file_max_age ( self , filename ) :
return 10
return 10
app = StaticFileApp ( __name__ )
app = StaticFileApp ( __name__ )
with app . test_request_context ( ) :
with app . test_request_context ( ) :
# Test with static file handler.
# Test with static file handler.
@ -658,28 +618,25 @@ class TestSendfile(object):
assert cc . max_age == 10
assert cc . max_age == 10
rv . close ( )
rv . close ( )
def test_send_from_directory ( self ) :
def test_send_from_directory ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
app . testing = True
app . testing = True
app . root_path = os . path . join ( os . path . dirname ( __file__ ) ,
app . root_path = os . path . join ( os . path . dirname ( __file__ ) ,
' test_apps ' , ' subdomaintestmodule ' )
' test_apps ' , ' subdomaintestmodule ' )
with app . test_request_context ( ) :
rv = flask . send_from_directory ( ' static ' , ' hello.txt ' )
rv = flask . send_from_directory ( ' static ' , ' hello.txt ' )
rv . direct_passthrough = False
rv . direct_passthrough = False
assert rv . data . strip ( ) == b ' Hello Subdomain '
assert rv . data . strip ( ) == b ' Hello Subdomain '
rv . close ( )
rv . close ( )
def test_send_from_directory_bad_request ( self ) :
def test_send_from_directory_bad_request ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
app . testing = True
app . testing = True
app . root_path = os . path . join ( os . path . dirname ( __file__ ) ,
app . root_path = os . path . join ( os . path . dirname ( __file__ ) ,
' test_apps ' , ' subdomaintestmodule ' )
' test_apps ' , ' subdomaintestmodule ' )
with app . test_request_context ( ) :
with pytest . raises ( BadRequest ) :
with pytest . raises ( BadRequest ) :
flask . send_from_directory ( ' static ' , ' bad \x00 ' )
flask . send_from_directory ( ' static ' , ' bad \x00 ' )
class TestLogging ( object ) :
class TestLogging ( object ) :
def test_logger_cache ( self ) :
def test_logger_cache ( self ) :
app = flask . Flask ( __name__ )
app = flask . Flask ( __name__ )
logger1 = app . logger
logger1 = app . logger
@ -713,19 +670,18 @@ class TestLogging(object):
with pytest . raises ( ZeroDivisionError ) :
with pytest . raises ( ZeroDivisionError ) :
c . get ( ' /exc ' )
c . get ( ' /exc ' )
def test_debug_log_override ( self ) :
def test_debug_log_override ( self , app ) :
app = flask . Flask ( __name__ )
app . debug = True
app . debug = True
app . logger_name = ' flask_tests/test_debug_log_override '
app . logger_name = ' flask_tests/test_debug_log_override '
app . logger . level = 10
app . logger . level = 10
assert app . logger . level == 10
assert app . logger . level == 10
def test_exception_logging ( self ) :
def test_exception_logging ( self , app ) :
out = StringIO ( )
out = StringIO ( )
app = flask . Flask ( __name__ )
app . config [ ' LOGGER_HANDLER_POLICY ' ] = ' never '
app . config [ ' LOGGER_HANDLER_POLICY ' ] = ' never '
app . logger_name = ' flask_tests/test_exception_logging '
app . logger_name = ' flask_tests/test_exception_logging '
app . logger . addHandler ( StreamHandler ( out ) )
app . logger . addHandler ( StreamHandler ( out ) )
app . testing = False
@app . route ( ' / ' )
@app . route ( ' / ' )
def index ( ) :
def index ( ) :
@ -741,76 +697,83 @@ class TestLogging(object):
assert ' 1 // 0 ' in err
assert ' 1 // 0 ' in err
assert ' ZeroDivisionError: ' in err
assert ' ZeroDivisionError: ' in err
def test_processor_exceptions ( self ) :
def test_processor_exceptions ( self , app , client ) :
app = flask . Flask ( __name__ )
app . config [ ' LOGGER_HANDLER_POLICY ' ] = ' never '
app . config [ ' LOGGER_HANDLER_POLICY ' ] = ' never '
app . testing = False
@app . before_request
@app . before_request
def before_request ( ) :
def before_request ( ) :
if trigger == ' before ' :
if trigger == ' before ' :
1 / / 0
1 / / 0
@app . after_request
@app . after_request
def after_request ( response ) :
def after_request ( response ) :
if trigger == ' after ' :
if trigger == ' after ' :
1 / / 0
1 / / 0
return response
return response
@app . route ( ' / ' )
@app . route ( ' / ' )
def index ( ) :
def index ( ) :
return ' Foo '
return ' Foo '
@app . errorhandler ( 500 )
@app . errorhandler ( 500 )
def internal_server_error ( e ) :
def internal_server_error ( e ) :
return ' Hello Server Error ' , 500
return ' Hello Server Error ' , 500
for trigger in ' before ' , ' after ' :
for trigger in ' before ' , ' after ' :
rv = app . test_ client( ) . get ( ' / ' )
rv = client . get ( ' / ' )
assert rv . status_code == 500
assert rv . status_code == 500
assert rv . data == b ' Hello Server Error '
assert rv . data == b ' Hello Server Error '
def test_url_for_with_anchor ( self ) :
def test_url_for_with_anchor ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
@app . route ( ' / ' )
@app . route ( ' / ' )
def index ( ) :
def index ( ) :
return ' 42 '
return ' 42 '
with app . test_request_context ( ) :
assert flask . url_for ( ' index ' , _anchor = ' x y ' ) == ' /#x % 20y '
assert flask . url_for ( ' index ' , _anchor = ' x y ' ) == ' /#x % 20y '
def test_url_for_with_scheme ( self ) :
def test_url_for_with_scheme ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
@app . route ( ' / ' )
@app . route ( ' / ' )
def index ( ) :
def index ( ) :
return ' 42 '
return ' 42 '
with app . test_request_context ( ) :
assert flask . url_for ( ' index ' , _external = True , _scheme = ' https ' ) == ' https://localhost/ '
assert flask . url_for ( ' index ' , _external = True , _scheme = ' https ' ) == ' https://localhost/ '
def test_url_for_with_scheme_not_external ( self ) :
def test_url_for_with_scheme_not_external ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
@app . route ( ' / ' )
@app . route ( ' / ' )
def index ( ) :
def index ( ) :
return ' 42 '
return ' 42 '
with app . test_request_context ( ) :
pytest . raises ( ValueError ,
pytest . raises ( ValueError ,
flask . url_for ,
flask . url_for ,
' index ' ,
' index ' ,
_scheme = ' https ' )
_scheme = ' https ' )
def test_url_for_with_alternating_schemes ( self ) :
def test_url_for_with_alternating_schemes ( self , app , req_ctx ) :
app = flask . Flask ( __name__ )
@app . route ( ' / ' )
@app . route ( ' / ' )
def index ( ) :
def index ( ) :
return ' 42 '
return ' 42 '
with app . test_request_context ( ) :
assert flask . url_for ( ' index ' , _external = True ) == ' http://localhost/ '
assert flask . url_for ( ' index ' , _external = True ) == ' http://localhost/ '
assert flask . url_for ( ' index ' , _external = True , _scheme = ' https ' ) == ' https://localhost/ '
assert flask . url_for ( ' index ' , _external = True , _scheme = ' https ' ) == ' https://localhost/ '
assert flask . url_for ( ' index ' , _external = True ) == ' http://localhost/ '
assert flask . url_for ( ' index ' , _external = True ) == ' http://localhost/ '
def test_url_with_method ( self ) :
def test_url_with_method ( self , app , req_ctx ) :
from flask . views import MethodView
from flask . views import MethodView
app = flask . Flask ( __name__ )
class MyView ( MethodView ) :
class MyView ( MethodView ) :
def get ( self , id = None ) :
def get ( self , id = None ) :
if id is None :
if id is None :
return ' List '
return ' List '
return ' Get %d ' % id
return ' Get %d ' % id
def post ( self ) :
def post ( self ) :
return ' Create '
return ' Create '
myview = MyView . as_view ( ' myview ' )
myview = MyView . as_view ( ' myview ' )
app . add_url_rule ( ' /myview/ ' , methods = [ ' GET ' ] ,
app . add_url_rule ( ' /myview/ ' , methods = [ ' GET ' ] ,
view_func = myview )
view_func = myview )
@ -819,7 +782,6 @@ class TestLogging(object):
app . add_url_rule ( ' /myview/create ' , methods = [ ' POST ' ] ,
app . add_url_rule ( ' /myview/create ' , methods = [ ' POST ' ] ,
view_func = myview )
view_func = myview )
with app . test_request_context ( ) :
assert flask . url_for ( ' myview ' , _method = ' GET ' ) == ' /myview/ '
assert flask . url_for ( ' myview ' , _method = ' GET ' ) == ' /myview/ '
assert flask . url_for ( ' myview ' , id = 42 , _method = ' GET ' ) == ' /myview/42 '
assert flask . url_for ( ' myview ' , id = 42 , _method = ' GET ' ) == ' /myview/42 '
assert flask . url_for ( ' myview ' , _method = ' POST ' ) == ' /myview/create '
assert flask . url_for ( ' myview ' , _method = ' POST ' ) == ' /myview/create '
@ -845,24 +807,24 @@ class TestNoImports(object):
class TestStreaming ( object ) :
class TestStreaming ( object ) :
def test_streaming_with_context ( self , app , client ) :
def test_streaming_with_context ( self ) :
app = flask . Flask ( __name__ )
app . testing = True
app . testing = True
@app . route ( ' / ' )
@app . route ( ' / ' )
def index ( ) :
def index ( ) :
def generate ( ) :
def generate ( ) :
yield ' Hello '
yield ' Hello '
yield flask . request . args [ ' name ' ]
yield flask . request . args [ ' name ' ]
yield ' ! '
yield ' ! '
return flask . Response ( flask . stream_with_context ( generate ( ) ) )
return flask . Response ( flask . stream_with_context ( generate ( ) ) )
c = app . test_client ( )
rv = c . get ( ' /?name=World ' )
rv = client . get ( ' /?name=World ' )
assert rv . data == b ' Hello World! '
assert rv . data == b ' Hello World! '
def test_streaming_with_context_as_decorator ( self ) :
def test_streaming_with_context_as_decorator ( self , app , client ) :
app = flask . Flask ( __name__ )
app . testing = True
app . testing = True
@app . route ( ' / ' )
@app . route ( ' / ' )
def index ( ) :
def index ( ) :
@flask . stream_with_context
@flask . stream_with_context
@ -870,35 +832,42 @@ class TestStreaming(object):
yield hello
yield hello
yield flask . request . args [ ' name ' ]
yield flask . request . args [ ' name ' ]
yield ' ! '
yield ' ! '
return flask . Response ( generate ( ' Hello ' ) )
return flask . Response ( generate ( ' Hello ' ) )
c = app . test_client ( )
rv = c . get ( ' /?name=World ' )
rv = client . get ( ' /?name=World ' )
assert rv . data == b ' Hello World! '
assert rv . data == b ' Hello World! '
def test_streaming_with_context_and_custom_close ( self ) :
def test_streaming_with_context_and_custom_close ( self , app , client ) :
app = flask . Flask ( __name__ )
app . testing = True
app . testing = True
called = [ ]
called = [ ]
class Wrapper ( object ) :
class Wrapper ( object ) :
def __init__ ( self , gen ) :
def __init__ ( self , gen ) :
self . _gen = gen
self . _gen = gen
def __iter__ ( self ) :
def __iter__ ( self ) :
return self
return self
def close ( self ) :
def close ( self ) :
called . append ( 42 )
called . append ( 42 )
def __next__ ( self ) :
def __next__ ( self ) :
return next ( self . _gen )
return next ( self . _gen )
next = __next__
next = __next__
@app . route ( ' / ' )
@app . route ( ' / ' )
def index ( ) :
def index ( ) :
def generate ( ) :
def generate ( ) :
yield ' Hello '
yield ' Hello '
yield flask . request . args [ ' name ' ]
yield flask . request . args [ ' name ' ]
yield ' ! '
yield ' ! '
return flask . Response ( flask . stream_with_context (
return flask . Response ( flask . stream_with_context (
Wrapper ( generate ( ) ) ) )
Wrapper ( generate ( ) ) ) )
c = app . test_client ( )
rv = c . get ( ' /?name=World ' )
rv = client . get ( ' /?name=World ' )
assert rv . data == b ' Hello World! '
assert rv . data == b ' Hello World! '
assert called == [ 42 ]
assert called == [ 42 ]
@ -920,7 +889,7 @@ class TestSafeJoin(object):
( ( ' a/b/c ' , ' X/.. ' ) , ' a/b/c/. ' ) ,
( ( ' a/b/c ' , ' X/.. ' ) , ' a/b/c/. ' ) ,
# Base directory is always considered safe
# Base directory is always considered safe
( ( ' ../ ' , ' a/b/c ' ) , ' ../a/b/c ' ) ,
( ( ' ../ ' , ' a/b/c ' ) , ' ../a/b/c ' ) ,
( ( ' /.. ' , ) , ' /.. ' ) ,
( ( ' /.. ' , ) , ' /.. ' ) ,
)
)
for args , expected in passing :
for args , expected in passing :