Data not saved to SQLite DB with multiple tables in Flask using WTForms
I am trying to Save Data to SQLite DB in Flask using WTForms.
I have one main table and three reference tables these reference tables have 1 field each which is called into my main table using foreignkey relationship.
When I save data using form on webpage. No error appears but data is also not saved to the database tables.
My Models
################################################################ ##### MODELS CONFIG ################### ################################################################ class dev_inventory(db.Model): __tablename__ = 'inventory' id = db.Column(db.Integer, primary_key=True) name = db.Column(db.String(120), unique=True, nullable=False) host = db.Column(db.String(120), unique=True, nullable=False) username = db.Column(db.String(120), nullable=False) password = db.Column(db.String(120), nullable=False) secret = db.Column(db.String(120), nullable=False) type = db.relationship('dev_type', backref='dev_inventory', lazy='dynamic') group_name = db.relationship('dev_group', backref='dev_inventory', lazy='dynamic') role = db.relationship('dev_role', backref='dev_inventory', lazy='dynamic') def __init__(self,name,host,username,password,secret): self.name = name self.host = host self.username = username self.password = password self.secret = secret def __repr__(self): return '<Host %r>' % self.host class dev_group(db.Model): __tablename__ = 'groups' id = db.Column(db.Integer, primary_key=True) group = db.Column(db.String(120), unique=True, nullable=False) host_id = db.Column(db.Integer, db.ForeignKey('inventory.id')) def __init__(self,group): self.group = group def __repr__(self): return '<Group %r>' % self.group class dev_role(db.Model): __tablename__ = 'roles' id = db.Column(db.Integer, primary_key=True) role = db.Column(db.String(120), unique=True, nullable=False) host_id = db.Column(db.Integer, db.ForeignKey('inventory.id')) def __init__(self,role): self.role = role def __repr__(self): return '<Role %r>' % self.role class dev_type(db.Model): __tablename__ = 'types' id = db.Column(db.Integer, primary_key=True) type = db.Column(db.String(120), unique=True, nullable=False) host_id = db.Column(db.Integer, db.ForeignKey('inventory.id')) def __init__(self,type): self.type = type class manage_users(db.Model): __tablename__ = 'users' id = db.Column(db.Integer, primary_key=True) username = db.Column(db.String(120), unique=True, nullable=False) password = db.Column(db.String(120), unique=True, nullable=False) def __init__(self,username,password): self.username = username self.password = password def __repr__(self): return '<User %r>' % self.user
Saving data to all other tables working fine except ‘dev_inventory’
I am using following form code –
class AddDeviceForm(FlaskForm): types_choices = [(type.type) for type in dev_type.query.order_by('type') ] group_choices = [(group.group) for group in dev_group.query.order_by('group') ] role_choices = [(role.role) for role in dev_role.query.order_by('role') ] name = StringField('Devive Name') host = StringField('Hostname/IP Address') username = StringField('Device Username') password = StringField('Device Password') secret = StringField('Device Secret') type = SelectField('Device Type', choices= types_choices) group = SelectField('Device Group', choices=group_choices) role = SelectField('Device Role', choices=role_choices) submit = SubmitField('Add Device')
When I fill and save form on web page, it throws no error or print anything on console. though it send a POST request and gives 200 OK but when I check DB, no data is saved in that table.
Here is my code for particular view –
@app.route('/add_device', methods=['GET','POST']) def add_device(): form = AddDeviceForm() if form.validate_on_submit(): name = form.name.data host = form.host.data username = form.username.data password = form.password.data secret = form.secret.data type = form.type.data group = form.group.data role = form.role.data device = dev_inventory(name, host, username, password, secret) print(device) db.session.add(device) db.session.add(type) db.session.add(group) db.session.add(role) db.session.commit() return "Device Added Successfully" return render_template('add_device.html', form=form)
I have also tried to save all variables using a single ‘db.session.add()’ command and then I broke this down further assuming since these are linked to different tables but none of the solution works.
Any help on this would be greatly appreciated.
There is no necessary to declare an __init__
method since you are already inheriting from db.Model and db.Model takes care to initialize the properties. I think that is the problem you are struggling on. So, remove the __init__
methods.
Additionally, you cannot send as argument the form data (i.e form.name.data) to the db.session.add().
role = form.role.data db.session.add(role) # bad device = dev_inventory(name, host, username, password, secret) db.session.add(device) # good
By another hand, remember the classes declaration have to be as CamelCase and not snake_case.