SoFunction
Updated on 2024-11-19

Python Flask implementation of the image verification code and e-mail verification code process explained in detail

1. Image CAPTCHA

1.1 Tools -

Put all the methods related to image verification codes in class ImageCode.

import random
import string
from io import BytesIO
from PIL import Image, ImageFont, ImageDraw
class ImageCode:
    def rand_color(self):
        """Generate random colors for drawing strings(You can specify as much as you want.0-255number between)"""
        red = (32, 200)
        green = (22, 255)
        blue = (0, 200)
        return red, green, blue
    def gen_text(self):
        """Generate a 4-digit random string."""
        # sample is used to construct a sub-list of N random characters from a large list or string.
        list = (string.ascii_letters, 5)
        return ''.join(list)
    def draw_verify_code(self):
        """Drawing CAPTCHA images."""
        code = self.gen_text()
        width, height = 120, 50  # Set the image size, which can be adjusted according to actual needs
        im = ('RGB', (width, height), 'white')  # Create a picture object and set the background color to white
        font = (font='', size=40)  # Choose which font and font size to use
        draw = (im)  # New ImageDraw object
        # Draw strings
        for i in range(4):
            ((5 + (-3, 3) + 23 * i, 5 + (-3, 3)),
                      text=code[i], fill=self.rand_color(), font=font)
        ()

At this point you can add the following code to the above class and run it alone to see if the CAPTCHA will be generated

ImageCode().draw_verify_code()

If it's running properly, it will open your own computer's image viewer by default, and then display an image verification code

It's also possible to add distracting lines to image captchas

In class ImageCode, add the draw_verify_code() method on top of the code generation method, and call it when drawing the code.

Method of drawing interference lines

def draw_lines(self, draw, num, width, height):
    """
    Drawing interference lines
    :param draw: picture object
    :param num: number of interference lines
    :param width: width of the picture
    :param height: height of the image
    :return.
    """
    for num in range(num):
        x1 = (0, width / 2)
        y1 = (0, height / 2)
        x2 = (0, width)
        y2 = (height / 2, height)
        (((x1, y1), (x2, y2)), fill='black', width=2)

When drawing an image CAPTCHA, call the above method for drawing interference lines before ()

The methodology is as follows:

def draw_verify_code(self):
    """Drawing CAPTCHA images."""
    code = self.gen_text()
    width, height = 120, 50  # Set the image size, which can be adjusted according to actual needs
    im = ('RGB', (width, height), 'white')  # Create a picture object and set the background color to white
    font = (font='', size=40)  # Choose which font and font size to use
    draw = (im)  # New ImageDraw object
    # Draw strings
    for i in range(4):
        ((5 + (-3, 3) + 23 * i, 5 + (-3, 3)),text=code[i], fill=self.rand_color(), font=font)
    self.draw_lines(draw, 4, width, height)  # Drawing interference lines
    ()

Then run it again with the following results:

The above image is stored in memory, and the program will terminate automatically after closing the image

Because the final image is to be returned to the front-end, the above method of generating CAPTCHA needs to be modified again as follows:

def draw_verify_code(self):
    """Drawing CAPTCHA images."""
    code = self.gen_text()
    width, height = 120, 50  # Set the image size, which can be adjusted according to actual needs
    im = ('RGB', (width, height), 'white')  # Create a picture object and set the background color to white
    font = (font='', size=40)  # Choose which font and font size to use
    draw = (im)  # New ImageDraw object
    # Draw strings
    for i in range(4):
        ((5 + (-3, 3) + 23 * i, 5 +(-3, 3)), text=code[i], fill=self.rand_color(), font=font)
        self.draw_lines(draw, 4, width, height)  # Drawing interference lines
    # () # For temporary debugging, you can display the generated image directly
    return im, code

1.2 Control layer -

Returning images to the front-end

from flask import Blueprint, make_response, session
from  import ImageCode
from  import Users
user = Blueprint('user', __name__)
@('/vcode')
def vcode():
    code, bstring = ImageCode().get_code()
    response = make_response(bstring)
    ['Content-Type'] = 'image/jpeg'
    session['vcode'] = ()
    return response

Register the above controllers into the main entry of the program

if __name__ == '__main__':
    from  import *
    app.register_blueprint(user)
    (debug=True)  # have sth. in placedebugmode of operation

By this point, the backend of the image captcha has been fully implemented

As for the front-end, you can just add an img tag where you want to place the image captcha, and then the value in the src attribute will be the interface of the above controller, as follows:

<img src="/vcode" style="cursor:pointer;"/>

To match the ones on the web that regenerate a new CAPTCHA after clicking on the image, add an onclick event

<img src="/vcode"  class="col-3" style="cursor:pointer;" onclick="='/vcode?'+()"/>

The reason why you add a random number to the end is because if you don't, the front-end browser won't re-send the request when it recognizes that it's the same request, unless you force a page refresh. But with a random number, the browser realizes that each request is different and sends it to the backend normally

2. E-mail authentication code

2.1 Preparation

This example uses QQ mailbox, using other mailboxes can also be, the operation is generally the same

Login to your QQ mailbox, open POP3/SMTP service, and then find the button of "Generate Authorization Code" under the respective interface, and generate the authorization code according to the respective process.

2.2 Tools -

New method in the above tool class

Note that it is better not to put the method in the class ImageCode, just put it outside, or you can add a new mailbox class and put it in there.

I'll just leave it outside.

from smtplib import SMTP_SSL
from  import MIMEText
from  import Header
def send_email(self, receiver, ecode):
    """Send mail."""
    sender = 'XXX <xxxxxxxxx@>'  # E-mail account number and sender's signature
    # Define the content of the email to be sent, with support for HTML and CSS styles
    content = f"Your email verification code is:<span style='color: red; font-size: 20px;'>{ecode}</span>" 
    message = MIMEText(content, 'html', 'utf-8')  # Instantiate the mail object and specify the key message of the message
    # Specify the subject of the message, again using utf-8 encoding
    message['Subject'] = Header('CAPTCHA', 'utf-8')
    message['From'] = sender
    message['To'] = receiver
    smtpObj = SMTP_SSL('')  # Links to QQ mail servers
    (user='xxxxxxxxx@', password='Authorization Code')  # Login to QQ mailbox through your own mailbox account and the obtained authorization code
    # Specify the sender, recipient and content of the message
    (sender, receiver, str(message))
    ()
def gen_email_code(self):
    str = (string.ascii_letters + , 6)
    return ''.join(str)

2.3 Control layer -

@('/ecode', methods=['POST'])
def ecode():
    email = ('email')
	# Formatting mailboxes
    if not ('^.+\\@(\\[?)[a-zA-Z0-9\\-\\.]+\\.([a-zA-Z]{2,3}|[0-9]{1,3})(\\]?)$', email):
        return 'email-invalid'
    code = gen_email_code()
    try:
        send_email(email, code)
        session['ecode'] = code  # Save email verification code in session
        return 'send-pass'
    except:
        return 'send-fail'

By this point, the backend of the mailbox captcha has been fully implemented

To this point this article on Python Flask to achieve picture CAPTCHA and email CAPTCHA process explained in detail on the article is introduced to this, more related Python CAPTCHA content, please search for my previous articles or continue to browse the following related articles I hope that you will support me in the future more!