0

My app is organized like this:

#---Project
#   |---- core
#           |_____ views.py
#           |_____ __init__.py
#           |_____ helpers.py
#   |---- error_pages
#           |_____ handlers.py
#           |_____ templates
#                 |_____ 404.html
#   |---- templates
#           |_____ layout.html
#           |_____ index.html
#           |_____ temp.html
#           |_____ tempform.html
#           |_____ tempJS.html

#   |---- static
#           |_____ style.css

#   |----- application.py
#   |----- model.py
#   |----- __init__.py

I want to handle errors in a folder error_pages.In this folder I have a handles.py with:

from flask import Blueprint, render_template


error_pages = Blueprint('error_pages',__name__, template_folder='/templates')


@error_pages.app_errorhandler(404)
def error_404(error):
    return render_template('404.html'), 404
@error_pages.app_errorhandler(403)
def error_403(error):
    return render_template('403.html'), 403

my init.py is:

# errors templates
from Project.error_pages.handlers import error_pages
app.register_blueprint(error_pages)

But I want to check if error code is ok and filled and non existing html page: the error is:

jinja2.exceptions.TemplateNotFound: 404.html

I have over Blueprint which are working (for users,...)

Can someone can help ?

  • The page not found surround (`@error_pages.app_errorhandler(404)`) works only when a user requests an URL that is cannot be found. You could use a `try catch` combination that renders the template and stores it in a variable. If there is an exception due to the file (i.e. template) not being found, then render a default error page and store it in a variable. Finally, return that variable – lsabi Jul 05 '20 at 20:31

2 Answers2

2

By looking at the tree of your application, even without the template_folder attribute, the blueprint should know where to find the application templates folder.

Then why does the template_folder attribute exist, you might ask.

The purpose of the template_folder in the context of a blueprint is to add another template folder to the search path of templates, but with a lower priority than the actual application's template folder.

This can be quite tricky if your application structure is not well defined. You might get to the point where you accidentally override a blueprint template. That's why you need to make sure you provide different relative paths to each blueprint (otherwise the first blueprint registered takes precedence over the others).

What's the catch, why would you use "sub-templates"?

I m calling them "sub-templates" to differentiate them from the application template folder.

Do this when you want to refactor your application and for each blueprint provide a template.

Example

If you have a blueprint named auth and you want to render a template called auth/login.html having provided templates as a template_folder to this blueprint you will have to create a file like this: yourapplication/auth/templates/auth/login.html.

So the best idea is to lay out your templates like this:

yourpackage/
    blueprints/
        auth/
            templates/
                auth/
                    login.html
            __init__.py

The reason for the extra auth folder is to avoid getting our template overriden by a templated named login.html in the actual application template folder.

Then when you want to render the template in your view functions you can use auth/login.html as the name to look up the template by.

If you encounter problems loading the correct templates enable the EXPLAIN_TEMPLATE_LOADING config variable which will instruct Flask to print out the steps to locate templates on every render_template call.

To answer your issue modify first your templates path like this:

error_pages = Blueprint('error_pages',__name__, template_folder='/templates')

Then modify your project structure like this

#   |---- error_pages
#           |_____ handlers.py
#           |_____ templates
#              |_____ error_pages
#                 |_____ 404.html
netlemon
  • 964
  • 8
  • 22
0

There's a subtle, but significant difference between

error_pages = Blueprint('error_pages',__name__, template_folder='/templates')

and

error_pages = Blueprint('error_pages',__name__, template_folder='templates')

You're using the former. Try the latter.

Dave W. Smith
  • 24,318
  • 4
  • 40
  • 46