Skip to content

Instantly share code, notes, and snippets.

@loongest loongest/edit.html
Last active Dec 4, 2019

What would you like to do?
category model
{% extends "base.html" %}
{% import 'bootstrap/wtf.html' as wtf %}
{% block head %}
<link href="{{ url_for('static', filename='css/dashboard.css') }}" rel="stylesheet"/ >
{% endblock %}
{% block app_content %}
{{ super() }}
<main role="main" class="col-md-9 ml-sm-auto col-lg-10 pt-3 px-4">
<div class="d-flex justify-content-between flex-wrap flex-md-nowrap align-items-center pb-2 mb-3 border-bottom">
<h1 class="h2">Category</h1>
<div class="btn-toolbar mb-2 mb-md-0">
<div class="btn-group mr-2">
<button class="btn btn-sm btn-outline-secondary" id="btn-list">
<span data-feather="calendar"></span>
{% for field, errors in form.errors.items() %}
<div class="alert alert-error" style="color:red">
{{ form[field].label }}: {{ ', '.join(errors) }}
{% endfor %}
<div class="table-responsive">
{% if form %}
{{ wtf.quick_form(form) }}
{% endif %}
{% endblock %}
{% block scripts %}
$("#btn-new").on('click', function(e){
window.location.href = "{{ url_for('category.add') }}";
$("#btn-list").on('click', function(e){
window.location.href = "{{ url_for('category.index') }}";
{% endblock %}
from flask_wtf import FlaskForm
from wtforms import validators, StringField, SubmitField
from wtforms.validators import DataRequired, EqualTo, ValidationError
from wtforms.ext.sqlalchemy.fields import QuerySelectField
from app.category.models import Category
def categories(columns=None):
return Category.query
class CategoryForm(FlaskForm):
name_en = StringField('Category (en)',[
validators.Length(min=1, max=100)
name_cn = StringField('Category (cn)',[
validators.Length(min=0, max=100)
name_my = StringField('Category (my)',[
validators.Length(min=0, max=100)
parent = QuerySelectField('Parent', query_factory=categories, allow_blank=True,
get_label='name_en', get_pk=lambda a:,
blank_text=u'Select a categories...')
submit = SubmitField('Save')
from app import db
import time
from datetime import datetime
from geoalchemy2 import Geometry, func
from geoalchemy2.elements import WKTElement
from datetime import datetime, date
# Category relationship table
category_tree = db.Table(
db.Column('parent_id', db.Integer, db.ForeignKey('')),
db.Column('children_id', db.Integer, db.ForeignKey(''))
""" WorkType = Category """
class Category(db.Model):
__tablename__ = 'category'
id = db.Column(db.Integer, primary_key=True)
name_en = db.Column(db.String(100), nullable=False, unique=True)
name_my = db.Column(db.String(100), nullable=True)
name_cn = db.Column(db.String(100), nullable=True)
created_date = db.Column(db.DateTime, server_default=db.func.current_timestamp())
created_by = db.Column(db.String(100), default="Admin")
updated_date = db.Column(db.DateTime, server_default=db.func.current_timestamp())
updated_by = db.Column(db.String(100), default="Admin")
children = db.relationship(
backref=db.backref('parents', lazy='dynamic'),
def remove_children(self):
if self.children.all() and len(self.children.all()) > 0:
for c in self.children:
def audit_log(self, username):
self.updated_date =
self.updated_by = username
def __repr__(self):
return '<Category> {}'.format(
def serialize(self):
return {
'name_en': self.name_en,
'name_my': self.name_my,
'name_cn': self.name_cn,
'parent_id' : [ for i in self.children]
from flask import Flask, json, url_for, request, render_template, redirect, flash, make_response, session, jsonify
from app import db
from .models import *
def get_category_parent_reference(category):
childref = None
if category.children.all() and len(category.children.all()) > 0:
childref = category.children[0]
return childref
def get_self_refences_banlist(category):
banlist = []
categories = Category.query.all()
for cat in categories:
if cat.children.first():
if cat.children.first().id ==
return banlist
@bp.route('/edit/<id>', methods = ['GET','POST'])
def edit(id=None, error=None):
id is None or redirect(url_for('category.index'))
category = Category.query.get(id)
if category is None:
return render_template('404.html'), 404
childref = get_category_parent_reference(category)
form = CategoryForm(parent=childref,
if form.validate_on_submit():
banlist = get_self_refences_banlist(category)
""" validation for infinite loop """
if is not None and ==
flash(u'Error: Parent category cannot be the same', 'green')
return redirect( url_for('category.edit', id=id))
if banlist is not None and len(banlist) > 0:
for i in banlist:
if == i:
flash(u'Error: Infinite self reference, please choose other parent category', 'green')
return redirect( url_for('category.edit', id=id))
category.name_en =
category.name_cn =
category.name_my =
if is not None:
flash(u'Category has been update successfully!', 'green')
return render_template('category/edit.html', error=error, form=form)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.