I have a User
model class and password
is one attribute among many. I am using Flask web framework and Flask-Admin extension to create the admin view of my model classes. I want to make certain fields in the admin view like password
non editable or not show them at all. How do I do it?
I can make the fields not show up in the normal view but when I click on the edit button of any record in the table, all fields show up and are editable.
You should extend your view from ModelView and overwrite the necessary fields.
In my class it looks like this:
class UserView(ModelView):
column_list = ('first_name', 'last_name', 'username', 'email')
searchable_columns = ('username', 'email')
# this is to exclude the password field from list_view:
excluded_list_columns = ['password']
can_create = True
can_delete = False
# If you want to make them not editable in form view: use this piece:
form_widget_args = {
'name': {
'readonly': True
},
}
Hope this helps!
For more information check out the documentation:
- Flask-Admin Documentation
- Model View Documentation
Here is a solution that expands upon Remo's answer and this so answer. It allows for different field_args for edit and create forms.
Custom Field Rule Class
from flask_admin.form.rules import Field
class CustomizableField(Field):
def __init__(self, field_name, render_field='lib.render_field', field_args={}):
super(CustomizableField, self).__init__(field_name, render_field)
self.extra_field_args = field_args
def __call__(self, form, form_opts=None, field_args={}):
field_args.update(self.extra_field_args)
return super(CustomizableField, self).__call__(form, form_opts, field_args)
UserView Class
class UserView(ModelView):
column_list = ('first_name', 'last_name', 'username', 'email')
searchable_columns = ('username', 'email')
# this is to exclude the password field from list_view:
excluded_list_columns = ['password']
can_create = True
can_delete = False
# If you want to make them not editable in form view: use this piece:
form_edit_rules = [
CustomizableField('name', field_args={
'readonly': True
}),
# ... place other rules here
]
Yet another way to work the problem around is to use Flask-Admin ModelView method called on_form_prefill
to set readonly property argument. According to Flask-Admin Docs:
on_form_prefill(form, id)
Perform additional actions to pre-fill the edit form.
Called from edit_view, if the current action is rendering the form rather than receiving client side input, after default pre-filling has been performed.
In other words, this is a trigger, which is run when opening only Edit form, not the Create one.
So, the solution for the example used above would be:
class UserView(ModelView):
...
def on_form_prefill(self, form, id):
form.name.render_kw = {'readonly': True}
The method is run after all other rules applied, so none of them are broken, including set of columns.