Skip to content

Unable to test a Flask app with default (rewritting) assertions #317

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
pytestbot opened this issue Jun 7, 2013 · 5 comments
Closed

Unable to test a Flask app with default (rewritting) assertions #317

pytestbot opened this issue Jun 7, 2013 · 5 comments
Labels
type: bug problem that needs to be addressed

Comments

@pytestbot
Copy link
Contributor

Originally reported by: Sean Lynch (BitBucket: techniq, GitHub: techniq)


Due to how Flask determines it's instance_path (http://flask.pocoo.org/docs/config/#instance-folders), py.test will throw the following error on a simple test

Test

#!python

from flask import Flask

def test_example():
    app = Flask(__name__)
    assert True

Results / error

#!python

    def test_example():
>       app = Flask(__name__)

test_flask.py:5: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ 

self = <flask.app.Flask object at 0x10fd1e810>, import_name = 'test_flask', static_path = None, static_url_path = None
static_folder = 'static', template_folder = 'templates', instance_path = None, instance_relative_config = False

    def __init__(self, import_name, static_path=None, static_url_path=None,
                 static_folder='static', template_folder='templates',
                 instance_path=None, instance_relative_config=False):
        _PackageBoundObject.__init__(self, import_name,
                                     template_folder=template_folder)
        if static_path is not None:
            from warnings import warn
            warn(DeprecationWarning('static_path is now called '
                                    'static_url_path'), stacklevel=2)
            static_url_path = static_path

        if static_url_path is not None:
            self.static_url_path = static_url_path
        if static_folder is not None:
            self.static_folder = static_folder
        if instance_path is None:
>           instance_path = self.auto_find_instance_path()

../../../.virtualenvs/pytest-flask/lib/python2.7/site-packages/flask/app.py:303: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ 

self = <flask.app.Flask object at 0x10fd1e810>

    def auto_find_instance_path(self):
        """Tries to locate the instance path if it was not provided to the
            constructor of the application class.  It will basically calculate
            the path to a folder named ``instance`` next to your main file or
            the package.

            .. versionadded:: 0.8
            """
>       prefix, package_path = find_package(self.import_name)

../../../.virtualenvs/pytest-flask/lib/python2.7/site-packages/flask/app.py:608: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ 

import_name = 'test_flask'

    def find_package(import_name):
        """Finds a package and returns the prefix (or None if the package is
        not installed) as well as the folder that contains the package or
        module as a tuple.  The package path returned is the module that would
        have to be added to the pythonpath in order to make it possible to
        import the module.  The prefix is the path below which a UNIX like
        folder structure exists (lib, share etc.).
        """
        root_mod_name = import_name.split('.')[0]
        loader = pkgutil.get_loader(root_mod_name)
        if loader is None or import_name == '__main__':
            # import name is not found, or interactive/main module
            package_path = os.getcwd()
        else:
            # For .egg, zipimporter does not have get_filename until Python 2.7.
            if hasattr(loader, 'get_filename'):
                filename = loader.get_filename(root_mod_name)
            elif hasattr(loader, 'archive'):
                # zipimporter's loader.archive points to the .egg or .zip
                # archive filename is dropped in call to dirname below.
                filename = loader.archive
            else:
                # At least one loader is missing both get_filename and archive:
                # Google App Engine's HardenedModulesHook
                #
                # Fall back to imports.
                __import__(import_name)
                filename = sys.modules[import_name].__file__
            package_path = os.path.abspath(os.path.dirname(filename))
            # package_path ends with __init__.py for a package
>           if loader.is_package(root_mod_name):
E           AttributeError: 'AssertionRewritingHook' object has no attribute 'is_package'

The solution is simple (as outlined in the docs: http://pytest.org/latest/assert.html#advanced-assertion-introspection), pass assert=reinterp or assert=plain when running the test.

While not a major issue, it would be great if py.test could test a Flask app without needing to know this knowledge, either by gracefully degrading assertions from module rewriting to reinterp by default, or somehow fixing the root issue of module rewriting with what Flask expects.

Thoughts?


@pytestbot
Copy link
Contributor Author

Original comment by Ronny Pfannschmidt (BitBucket: RonnyPfannschmidt, GitHub: RonnyPfannschmidt):


got a unfinished patch that i need to reiterate

@pytestbot
Copy link
Contributor Author

Original comment by holger krekel (BitBucket: hpk42, GitHub: hpk42):


Not sure i understand how this error comes along. The Loader is not something that Flask influences, or does it? Will wait for @RonnyPfannschmidt -- it's defintely high priority to make flask interactions work out of the box.

UPDATED: now i understand, this is all Flask's code - didn't notice because the traceback was truncated. So this is an issue of pytest's Loader not supporting the right interface?

@pytestbot
Copy link
Contributor Author

Original comment by Ronny Pfannschmidt (BitBucket: RonnyPfannschmidt, GitHub: RonnyPfannschmidt):


correct, we are missing is_package, i need to reiterate my patch on that

@pytestbot
Copy link
Contributor Author

Original comment by holger krekel (BitBucket: hpk42, GitHub: hpk42):


any chance for a fix soonish?

@pytestbot
Copy link
Contributor Author

Original comment by Ronny Pfannschmidt (BitBucket: RonnyPfannschmidt, GitHub: RonnyPfannschmidt):


fix issue317: assertion rewriter support for the is_package method

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
type: bug problem that needs to be addressed
Projects
None yet
Development

No branches or pull requests

1 participant