<commit_before>Adding your own views
===========

Standalone views
------------
Now, lets add an administrative view. The next example will result in two items appearing in the navbar menu: *Home*
and *Hello*. To do this, you need to derive from the :class:`~flask_admin.base.BaseView` class::

    from flask import Flask
    from flask_admin import Admin, BaseView, expose

    class MyView(BaseView):
        @expose('/')
        def index(self):
            return self.render('index.html')

    app = Flask(__name__)

    admin = Admin(app)
    admin.add_view(MyView(name='Hello'))

    app.run()

One important restriction on admin views is that each view class should have a default page-view method with a root
url, '/'. The following example is correct::

    class MyView(BaseView):
        @expose('/')
        def index(self):
            return self.render('index.html')

but, this wouldn't work::

    class MyView(BaseView):
        @expose('/index/')
        def index(self):
            return self.render('index.html')

Now, create a new *index.html* file with following content::

    {% extends 'admin/master.html' %}
    {% block body %}
        Hello World from MyView!
    {% endblock %}

and place it in a *templates* directory. To maintain a consistent look and feel, all administrative pages should extend
the *admin/master.html* template.

You should now see your new admin page in action on the *Hello* page

    .. image:: images/quickstart/quickstart_2.png
        :width: 640
        :target: ../_images/quickstart_2.png

To add another level of menu items, you can specify a value for the *category* parameter when passing admin views to
the Admin instance. The category specifies the name of the top-level menu item, and all of the views that are associated
with it, will be accessible from a drop-down menu. For example::

    from flask import Flask
    from flask_admin import Admin, BaseView, expose

    class MyView(BaseView):
        @expose('/')
        def index(self):
            return self.render('index.html')

    app = Flask(__name__)

    admin = Admin(app)
    admin.add_view(MyView(name='Hello 1', endpoint='test1', category='Test'))
    admin.add_view(MyView(name='Hello 2', endpoint='test2', category='Test'))
    admin.add_view(MyView(name='Hello 3', endpoint='test3', category='Test'))
    app.run()

will look like

    .. image:: images/quickstart/quickstart_3.png
        :width: 640
        :target: ../_images/quickstart_3.png


Overriding specific model views
------------------<commit_msg>Adding your own views: Overriding the builtin views.<commit_after>Adding your own views
===========

Standalone views
------------
Now, lets add an administrative view. The next example will result in two items appearing in the navbar menu: *Home*
and *Hello*. To do this, you need to derive from the :class:`~flask_admin.base.BaseView` class::

    from flask import Flask
    from flask_admin import Admin, BaseView, expose

    class MyView(BaseView):
        @expose('/')
        def index(self):
            return self.render('index.html')

    app = Flask(__name__)

    admin = Admin(app)
    admin.add_view(MyView(name='Hello'))

    app.run()

One important restriction on admin views is that each view class should have a default page-view method with a root
url, '/'. The following example is correct::

    class MyView(BaseView):
        @expose('/')
        def index(self):
            return self.render('index.html')

but, this wouldn't work::

    class MyView(BaseView):
        @expose('/index/')
        def index(self):
            return self.render('index.html')

Now, create a new *index.html* file with following content::

    {% extends 'admin/master.html' %}
    {% block body %}
        Hello World from MyView!
    {% endblock %}

and place it in a *templates* directory. To maintain a consistent look and feel, all administrative pages should extend
the *admin/master.html* template.

You should now see your new admin page in action on the *Hello* page

    .. image:: images/quickstart/quickstart_2.png
        :width: 640
        :target: ../_images/quickstart_2.png

To add another level of menu items, you can specify a value for the *category* parameter when passing admin views to
the Admin instance. The category specifies the name of the top-level menu item, and all of the views that are associated
with it, will be accessible from a drop-down menu. For example::

    from flask import Flask
    from flask_admin import Admin, BaseView, expose

    class MyView(BaseView):
        @expose('/')
        def index(self):
            return self.render('index.html')

    app = Flask(__name__)

    admin = Admin(app)
    admin.add_view(MyView(name='Hello 1', endpoint='test1', category='Test'))
    admin.add_view(MyView(name='Hello 2', endpoint='test2', category='Test'))
    admin.add_view(MyView(name='Hello 3', endpoint='test3', category='Test'))
    app.run()

will look like

    .. image:: images/quickstart/quickstart_3.png
        :width: 640
        :target: ../_images/quickstart_3.png


Overriding the builtin views
------------------------------------

If you want most of the builtin ModelView functionality, but you want to have your own view
in place of the default `create`, `edit`, or `list` view.

Then you can override the view in question as follows::

    from flask_admin.contrib.sqla import ModelView

    # Flask and Flask-SQLAlchemy initialization here

    class UserView(ModelView):
    @expose('/new/', methods=('GET', 'POST'))
        def create_view(self):
        """
            Custom create view.
        """

        return self.render('create_user.html')

{'fraction_non_alphanumeric': 0.11871262750615547, 'fraction_numerical': 0.005627857896588111, 'mean_word_length': 2.9603064066852367, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3490515', 'n_tokens_mistral': 1638, 'n_tokens_neox': 1552, 'n_words': 597}