I already have an application using my SQLAlchemy model, and I'm now trying to add a flask admin website on top to manage some of the data in the DB. This model is already setup and working throughout the existing application so I know the relationships are configured correctly. In my DB the data_package table has a FK to the supplier table, and this has been added as a relationship. However, when I create a flask model view to allow editing of the data_package I'm receiving the error:
Exception: Cannot find reverse relation for model
I've added a subset of the code below, there are a lot more columns and logic but this is the bare minimum I have to try and test a fix to the issue.The issue is happening because I am adding inline_models = (Supplier,) which I need as I want to have a select to allow the supplier to be changed for a data package.
The line of code throwing the exception is https://github.com/flask-admin/flask-admin/blob/master/flask_admin/contrib/sqla/form.py#L558. The reason for this is the relationship direction is defined as ONETOMANY, and there is a check to ensure the direction is MANYTOONE or MANYTOMANY
Base = declarative_base()
class Supplier(Base):
__tablename__ = 'supplier'
id = Column(Integer, primary_key=True)
name = Column(String(100), nullable=False)
class DataPackage(Base):
__tablename__ = 'data_package'
id = Column(Integer, primary_key=True)
name = Column(String(100), nullable=False)
supplier_id = Column(Integer, ForeignKey('supplier.id'), index=True, nullable=False)
supplier = relationship("Supplier", backref='packages')
class DataPackageAdminView(ModelViewOnly):
form_columns = ['name', 'supplier']
inline_models = (Supplier,)
def create_app():
settings.configure_orm()
app = Flask(__name__)
app.config.from_pyfile('config.py')
@app.route('/')
def index():
return '<a href="/admin/">Click me to get to Admin!</a>'
admin = Admin(app, name='Test Editor', template_mode='bootstrap3')
admin.add_view(DataPackageAdminView(DataPackage, settings.Session, category='Data Sources'))
return app
if __name__ == '__main__':
app = create_app()
app.run(debug=True)