jQuery AJAX based Registration System using Python Flask MySQL

Introduction

This guide will walk you through how to build jQuery AJAX based registration system using Python Flask MySQL. In this example I am going to build REST API that will be called from front-end technologies – jQuery, HTML including AJAX technique. I will determine registration process based on various http status codes such as 200 – success, 400 – bad request, 409 – conflict.

I will also use template from Flask API to render the sign up page where input fields will be displayed for entering user details. I will use MySQL database to store user information. I will encrypt the password instead of saving it as plain text which exposes security threats.

Related Posts:

Prerequisites

Python 3.8.0 – 3.9.1, Flask 1.1.1 – 1.1.2, MySQL 8.0.17 – 8.0.22

MySQL Table

You need to store user information into the database table, so you will create a MySQL table with the below structure.

I have also kept a field admin to indicate whether a user is admin or normal user. Value of admin field with 1 indicates admin user and 0 indicates normal user. 0 is the default value.

CREATE TABLE `user` (
  `id` int unsigned COLLATE utf8mb4_unicode_ci NOT NULL AUTO_INCREMENT,
  `name` varchar(50) COLLATE utf8mb4_unicode_ci NULL,
  `email` varchar(50) COLLATE utf8mb4_unicode_ci NULL,
  `pwd` varchar(255) COLLATE utf8mb4_unicode_ci NULL,
  `admin` tinyint COLLATE utf8mb4_unicode_ci DEFAULT 0,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;

Project Directory

Create a project root directory called python-flask-ajax-mysql-registration as per your chosen location.

I may not mention the project’s root directory name in the subsequent sections but I will assume that I am creating files with respect to the project’s root directory.

Configure Flask

I here configure application through flask framework. Create a file called app.py with the below code.

from flask import Flask

app = Flask(__name__)

Database Configuration

I create the below db_config.py Python script to setup the MySQL database configurations for connecting to database and storing user information into user table under roytuts database.

I need to configure database connection with flask module and that’s why I have imported app module and setup the MySQL configuration with flask module.

Make sure to change the database configuration values according to your database setup.

from app import app
from flaskext.mysql import MySQL

mysql = MySQL()
 
# MySQL configurations
app.config['MYSQL_DATABASE_USER'] = 'root'
app.config['MYSQL_DATABASE_PASSWORD'] = 'root'
app.config['MYSQL_DATABASE_DB'] = 'roytuts'
app.config['MYSQL_DATABASE_HOST'] = 'localhost'
mysql.init_app(app)

Store User Information

I will store user information once a user register himself/herself in the system successfully.

Create a Python script dao.py with the below source code.

In the below script I have two functions – user_exist() and register().

The function user_exist() simply checks whether a user who wants to register into the system with the email already exists or not. If the user’s email already exists in the system then I don’t allow him/her to register again.

The function register() stores user details into the table user in MySQL database.

I encrypt the password instead of storing plain text to avoid any security threats.

import pymysql
from db_config import mysql
#from werkzeug import generate_password_hash, check_password_hash
from werkzeug.security import generate_password_hash, check_password_hash

def user_exist(email):
	conn = None;
	cursor = None;
	
	try:
		conn = mysql.connect()
		cursor = conn.cursor()
		
		sql = "SELECT email FROM user WHERE email=%s"
		sql_where = (email,)
		
		cursor.execute(sql, sql_where)
		row = cursor.fetchone()
		
		if row:
			return True
		return False

	except Exception as e:
		print(e)

	finally:
		if cursor and conn:
			cursor.close()
			conn.close()

def register(email, name, pwd):
	conn = None;
	cursor = None;
	
	try:
		conn = mysql.connect()
		cursor = conn.cursor()
		
		sql = "INSERT INTO user(name, email, pwd) VALUES(%s, %s, %s)"
		data = (name, email, generate_password_hash(pwd),)
		
		cursor.execute(sql, data)
		
		conn.commit()

	except Exception as e:
		print(e)

	finally:
		if cursor and conn:
			cursor.close()
			conn.close()

REST Endpoint

As I said at the beginning that I will build REST API to register our users into the system.

Create a Python script rest.py with the following source code.

In the below REST endpoint I get the input values and if they are empty then I send http status 400 – bad request parameters.

If email address already exists in the database then I send 409 – conflict.

If there is any internal error – http status 500, then that will be sent automatically. Otherwise on success http response code 201, resource created, is returned.

import dao
import json
from app import app
from flask import jsonify, request

@app.route('/signup', methods=['POST'])
def signup():
	_json = request.json
	_name = _json['name']
	_email = _json['email']
	_pwd = _json['password']
	
	if _email and _name and _pwd:
	
		user_exist = dao.user_exist(_email)
		
		if user_exist == True:
			resp = jsonify({'message' : 'User already registered'})
			resp.status_code = 409
			return resp
		else:		
			dao.register(_email, _name, _pwd)
			
			resp = jsonify({'message' : 'User registered successfully'})
			resp.status_code = 201
			return resp
	else:
		resp = jsonify({'message' : 'Bad Request - invalid parameters'})
		resp.status_code = 400
		return resp

AJAX using jQuery

I mentioned in the beginning that I am going to use AJAX technique with jQuery to call the REST API.

So here is the code that will register a user provided that user inputs all the required fields with proper format.

In the below code I get the input values from sign up page once user click on submit button.

I validate the email address, I also check whether password and confirm password are same or not.

I check different http status code and display message to the end users.

On successful registration I hide the registration form and show success message.

The below code is written in a file register.js under static/js folder. This is a convention that you put your static resources under static folder.

$(document).ready(function() {
	$('#signupSubmit').on('click', function(e) {
		e.preventDefault();
		
		var name = $('#fullname').val();
		var email = $('#email').val();
		var pwd = $('#password').val();
		var cnfpwd = $('#cnfpassword').val();
		
		var regex = /^([a-zA-Z0-9_.+-])+\@(([a-zA-Z0-9-])+\.)+([a-zA-Z0-9]{2,4})+$/i;
		
		if(email != "" && pwd != "" && cnfpwd != "") {
			if(pwd != cnfpwd) {
				$('#msg').html('<span style="color: red;">Password and confirm password must match</span>');
			} else if(!regex.test(email)) {
				$('#msg').html('<span style="color: red;">Invalid email address</span>');
			} else {
				$.ajax({
					method: "POST",
					url: '/signup',
					contentType: 'application/json;charset=UTF-8',
					data: JSON.stringify({'name': name, 'email': email, 'password': pwd}),
					dataType: "json",
					success: function(data) {
						$('#signupform').hide();
						$('#msg').html('<span style="color: green;">You are registered successfully</span>');
					},statusCode: {
						400: function() {
							$('#msg').html('<span style="color: red;">Bad request parameters</span>');
						},
						409 : function() {
							$('#msg').html('<span style="color: red;">You are already registered user</span>');
						}
					},
					error: function(err) {
						console.log(err);
					}
				});
			}
		} else {
			$('#msg').html('<span style="color: red;">All fields are required</span>');
		}
	});
});

Template File

As I need to display registration page with input fields, so I need to have a template page. The template page is written with simple HTML tags.

By convention, the template page is put under templates directory.

Create a template file called signup.html and put the below source code into it.

<!DOCTYPE html>
<html>
	<head>
		<meta name="viewport" content="width=device-width, initial-scale=1.0">
		<title>jQuery AJAX based Registration System using Python Flask MySQL</title>
		<script src="https://code.jquery.com/jquery-3.4.1.min.js"></script>
		<script type="text/javascript" src="{{ url_for('static', filename='js/register.js') }}"/>
		<script type="text/javascript">
			$SCRIPT_ROOT = {{ request.script_root|tojson|safe }};
		</script>
	</head>
<body>
	<div style="width: 500px; margin: auto;">
		<div id="msg"></div>
		<div style="clear: both;"></div>
		<div id="signupform" style="width: 500px; margin: auto;">
			<h2>Sign Up</h2>
			<dl>
				<p>
					<input id="fullname" value="" type="text" placeholder="Full Name" required>
				</p>
				<p>
					<input id="email" value="" type="text" placeholder="Email" required>
				</p>
				<p>
					<input id="password" value="" type="password" placeholder="Password" autocomplete="off" required>
				</p>
				<p>
					<input id="cnfpassword" value="" type="password" placeholder="Confirm Password" autocomplete="off" required>
				</p>
			</dl>
			<p>
				<input type="button" id="signupSubmit" value="Submit">
			</p>
		</div>
	</div>
</body>
</html>

Render Sign up Page

The below code will render the sign up page on application startup.

Create a Python script main.py with the following source code.

import rest
from app import app
from flask import render_template

@app.route('/')
def home():
	return render_template('signup.html')
		
if __name__ == "__main__":
    app.run()

Testing the Application

Now navigate to the project directory and execute the command python main.py or simply main.py, your server will be started on default port 5000.

If you want to change the port then you can change the line app.run() to app.run(port=5001), where 5001 is the new port.

Now you can hit the URL http://localhost:5000 on your browser and you will see sign up page is displayed on the browser.

jquery ajax based registration system using python flask mysql

If you try to click on submit button without any input or partial input then you will see the following error:

jquery ajax based registration system using python flask mysql

On invalid email entry you will below error:

jquery ajax based registration system using python flask mysql

On successful registration you will see below message:

jquery ajax based registration system using python flask mysql

In the database you will find one entry added:

jquery ajax based registration system using python flask mysql

That’s all. Hope you got idea how to use AJAX in Flask framework.

Source Code

Download

Leave a Reply

Your email address will not be published. Required fields are marked *