Commit c9a0dbcd authored by Serge S. Koval's avatar Serge S. Koval

Allow overriding base form class

parent f3eb5cf1
......@@ -14,7 +14,6 @@ from mongoengine.connection import get_db
from bson.objectid import ObjectId
from flask.ext.admin.actions import action
from flask.ext.admin.form import BaseForm
from .filters import FilterConverter, BaseMongoEngineFilter
from .form import get_form, CustomModelConverter
from .typefmt import DEFAULT_FORMATTERS
......@@ -251,7 +250,7 @@ class ModelView(BaseModelView):
"""
form_class = get_form(self.model,
self.model_form_converter(self),
base_class=BaseForm,
base_class=self.form_base_class,
only=self.form_columns,
exclude=self.form_excluded_columns,
field_args=self.form_args,
......
......@@ -218,7 +218,7 @@ class ModelView(BaseModelView):
def scaffold_form(self):
form_class = get_form(self.model, self.model_form_converter(),
base_class=form.BaseForm,
base_class=self.form_base_class,
only=self.form_columns,
exclude=self.form_excluded_columns,
field_args=self.form_args,
......
......@@ -513,6 +513,7 @@ class ModelView(BaseModelView):
"""
converter = self.model_form_converter(self.session, self)
form_class = form.get_form(self.model, converter,
base_class=self.form_base_class,
only=self.form_columns,
exclude=self.form_excluded_columns,
field_args=self.form_args,
......
......@@ -144,9 +144,6 @@ class FileUploadField(fields.TextField):
:param allowed_extensions:
List of allowed extensions. If not provided, will allow any file.
"""
if not base_path:
raise ValueError('FileUploadField field requires target path.')
self.base_path = base_path
self.relative_path = relative_path
......@@ -210,6 +207,9 @@ class FileUploadField(fields.TextField):
return urljoin(self.relative_path, filename)
def _get_path(self, filename):
if not self.base_path:
raise ValueError('FileUploadField field requires base_path to be set.')
return op.join(self.base_path, filename)
def _delete_file(self, filename):
......
......@@ -7,6 +7,7 @@ from jinja2 import contextfunction
from flask.ext.admin.babel import gettext
from flask.ext.admin.base import BaseView, expose
from flask.ext.admin.form import BaseForm
from flask.ext.admin.model import filters, typefmt
from flask.ext.admin.actions import ActionsMixin
from flask.ext.admin.helpers import get_form_data, validate_form_on_submit
......@@ -247,16 +248,34 @@ class BaseModelView(BaseView, ActionsMixin):
form = None
"""
Form class. Override if you want to use custom form for your model.
Will completely disable form scaffolding functionality.
For example::
class MyForm(Form):
pass
name = TextField('Name')
class MyModelView(BaseModelView):
form = MyForm
"""
form_base_class = BaseForm
"""
Base form class. Will be used by form scaffolding function when creating model form.
Useful if you want to have custom contructor or override some fields.
Example::
class MyBaseForm(Form):
def do_something(self):
pass
class MyModelView(BaseModelView):
form_base_class = MyBaseForm
"""
form_args = None
"""
Dictionary of form field arguments. Refer to WTForms documentation for
......
......@@ -8,6 +8,7 @@ if not PY2:
from wtforms import fields
from flask.ext.admin import form
from flask.ext.admin.contrib.mongoengine import ModelView
from . import setup
......@@ -191,3 +192,23 @@ def test_extra_field_order():
pos1 = data.find('Extra Field')
pos2 = data.find('Test1')
ok_(pos2 > pos1)
def test_custom_form_base():
app, db, admin = setup()
class TestForm(form.BaseForm):
pass
Model1, _ = create_models(db)
view = CustomModelView(
Model1,
form_base_class=TestForm
)
admin.add_view(view)
ok_(hasattr(view._create_form_class, 'test1'))
create_form = view.create_form()
ok_(isinstance(create_form, TestForm))
......@@ -10,6 +10,7 @@ import peewee
from wtforms import fields
from flask.ext.admin import form
from flask.ext.admin._compat import iteritems
from flask.ext.admin.contrib.peewee import ModelView
......@@ -173,3 +174,23 @@ def test_extra_fields():
pos1 = data.find('Extra Field')
pos2 = data.find('Test1')
ok_(pos2 < pos1)
def test_custom_form_base():
app, db, admin = setup()
class TestForm(form.BaseForm):
pass
Model1, _ = create_models(db)
view = CustomModelView(
Model1,
form_base_class=TestForm
)
admin.add_view(view)
ok_(hasattr(view._create_form_class, 'test1'))
create_form = view.create_form()
ok_(isinstance(create_form, TestForm))
......@@ -2,6 +2,7 @@ from nose.tools import eq_, ok_, raises
from wtforms import fields
from flask.ext.admin import form
from flask.ext.admin._compat import iteritems
from flask.ext.admin.contrib.sqla import ModelView
......@@ -618,4 +619,23 @@ def test_extra_field_order():
pos2 = data.find('Test1')
ok_(pos2 > pos1)
# TODO: Babel tests
def test_custom_form_base():
app, db, admin = setup()
class TestForm(form.BaseForm):
pass
Model1, _ = create_models(db)
view = CustomModelView(
Model1, db.session,
form_base_class=TestForm
)
admin.add_view(view)
ok_(hasattr(view._create_form_class, 'test1'))
create_form = view.create_form()
ok_(isinstance(create_form, TestForm))
......@@ -309,3 +309,5 @@ def test_custom_form():
eq_(view._create_form_class, TestForm)
eq_(view._edit_form_class, TestForm)
ok_(not hasattr(view._create_form_class, 'col1'))
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment