Tutorial on web forms in the Python Flask framework

Source: Internet
Author: User

Tutorial on web forms in the Python Flask framework

The following is a tutorial on web forms in the Python Flask framework. forms are the basic knowledge of various web frameworks. For more information, see

Summary

In the previous section, we defined a simple template for the Home Page. Some unimplemented modules, such as users or posts, use simulated objects as temporary placeholder.

This chapter shows how to fill these gaps with web forms.

Web forms are the most basic building elements of web applications. We use forms to Implement User posting and application login functions.

To complete this chapter, you must complete the Weibo application code based on the previous chapter. Make sure that the code has been installed and runs properly.

Configuration

Flask-WTF is the Flask framework extension of the WTForms project. We will use it to help us process web forms.

Most Flask extensions need to define related configuration items, so we should first create a configuration file under the application root directory for use. Create (fileconfig. py) as follows ):

?

1

2

CSRF_ENABLED = True

SECRET_KEY = 'you-will-never-guess'

It's easy. This is the two configuration items that Flask-WTF needs to use. The CSRF_ENABLED configuration enables cross-site request attack protection. In most cases, you need to enable this feature to make your application safer.

SECRET_KEY setting is valid when CSRF is enabled. This will generate an encrypted token for form verification. Make sure that this KEY is complex enough and won't be simply guessed.

Now this configuration file is basically available. After the project is created, you can create and edit the following file (fileapp/_ init _. py ):

?

1

2

3

4

5

6

From flask import Flask

 

App = Flask (_ name __)

App. config. from_object ('config ')

 

From app import views

User Logon form

A Form created using Flask-WTF is like an object and must inherit the subclass from the Form class. Then define the attribute variables of some classes in this subclass as form fields.

Create a logon form for user identification. However, unlike the usual login method that requires user name and password verification, we will use OpenId to process the login process. The advantage of using OpenId is that we don't have to worry about the authentication process of those usernames and passwords, and it is handed over to OpenId. It will return the data verified by the user. This makes it safer for users who use our website.

To log on with OpenId, you only need one string and then send it to the OpenId server. In addition, we also need to add an option box "remember me" in the form to those who don't want to authenticate every time they come to our website. After this option is selected, the First Login will use cookies to remember their login information in their browsers. The next time you log on to the website, you do not need to log on.

Let's start with our first form (fileapp/forms. py ):

?

1

2

3

4

5

6

From flask. ext. wtf import Form, TextField, BooleanField

From flask. ext. wtf import Required

 

Class LoginForm (Form ):

Openid = TextField ('openid', validators = [Required ()])

Remember_me = BooleanField ('Remember _ me', default = False)

Let's take a look at how simple and clear this class is. It is so simple, but it is very meaningful. We introduced a Form class and inherited this class. TextField and BooleanField are added as needed.

In addition, a form verification function Required is introduced, which can be attached to a field and used to check the data filled in by the user when the user submits the form. This Required function is used to prevent empty data from being submitted. Flask-WTF also has many form verification functions, which will be used later.

Form template

Now we need a template to display the logon form. The good news is that the login form class we just created knows how to convert fields into HTML, so we only need to focus on the page layout. Below is the template of our login form (fileapp/templates/login.html ):

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

<! -- Extend from base layout -->

{% Extends "base.html" %}

 

{% Block content %}

<H1> Sign In

<Form action = "" method = "post" name = "login">

{Form. hidden_tag ()}}

<P>

Please enter your OpenID: <br>

{Form. openid (size = 80) }}< br>

</P>

<P >{{ form. remember_me }} Remember Me </p>

<P> <input type = "submit" value = "Sign In"> </p>

</Form>

{% Endblock %}

In this template, we again use the method of template inheritance. Use the extends statement to inherit the template content from base.html. We will continue to use this method in the template created later, so that all our page la s can be consistent.

This login template is obviously different from a common HTML form. It uses the template parameter {{...}} to instantiate a form field, and the form field comes from the form class we just defined. The form name is used in the template parameters. When using a view function to reference a form class and render it to a template, pay special attention to the variable name that passes the Form class to the template.

The CSRF feature is enabled in the configuration. The template parameter {form. hidden_tag ()} is replaced with a hidden form field that prevents CSRF. After the CSRF function is enabled, you must add this template parameter to all template forms.

Fields in the form object we define can also be rendered by the template. You only need to add fields similar to {form. for template parameters such as field_name}, the related fields will appear at the defined position. There are also some fields that can be passed through. For example, the openid field, we add a parameter to increase the display width to 80 characters.

Because we do not define a button for the Submission function in the form, we can only do this in the form field mode. However, a button in a form does not have to be defined in the Form class.

Form View

The last step to witness the miracle is to write a view function that renders the login form object to the template.

This function is quite simple and boring, because we only need to pass the form object to the template. The following is all the content of our view function (fileapp/views. py ):

?

1

2

3

4

5

6

7

8

9

10

11

12

From flask import render_template, flash, redirect

From app import app

From forms import LoginForm

 

# Index view function suppressed for brespon

 

@ App. route ('/login', methods = ['get', 'post'])

Def login ():

Form = LoginForm ()

Return render_template('login.html ',

Title = 'sign in ',

Form = form)

We introduce the login form class, instantiate it into a variable, and finally pass the variable to the template. This is what is necessary to render form fields.

The above Code also introduces two new objects: falsh and redirect, which can be used later.

In addition, a new method is added to the route modifier. Let Flask understand that our view function supports GET and POST requests. Otherwise, this view function only responds to the GET request. We need to obtain the data submitted after the user fills out the form, which is passed in from the POST request.

You can test this program in a browser to learn about the above. According to the routing associated with the view function, you should enter http: // localhost: 5000/login in the browser

Since we have not written any code to receive data, the submit button on the page does not work.

Receive data from the form

It is also worth mentioning that the processing of the data submitted by the Flask-WTF form simplifies what we will do next. The following is the new version of the logon view function, which includes form data verification and processing (fileapp/views. py ):

?

1

2

3

4

5

6

7

8

9

@ App. route ('/login', methods = ['get', 'post'])

Def login ():

Form = LoginForm ()

If form. validate_on_submit ():

Flash ('login requested for OpenID = "'+ form. openid. data +'", remember_me = '+ str (form. remember_me.data ))

Return redirect ('/Index ')

Return render_template('login.html ',

Title = 'sign in ',

Form = form)

The validate_on_submit () method does all the work of form processing. If you call this method when the form provides data to the user (for example, the user modifies the submitted data before it), it returns False. When this happens, you know. Don't you understand? If the submitted data verification fails, you need to continue rendering the template.

After the validate_on_submit () method of the form is called when a request is submitted, it obtains all submitted data from the request and then uses the verification function bound to the form field for data verification. True is returned when all data passes verification. This means you can use the form data with confidence.

If a field fails verification, False is returned. In this case, we need to return the data to the user to correct the error data. Next, we will see how to display the error message to the user when data verification fails.

When the validate_on_submit () method returns True, our view function calls two new functions. They are all introduced from Flask. flash functions are used to display defined messages on the next open page. Now we use it for debugging. Because we have not yet created a user logon module, we only need to display the data submitted by the user. Flash functions are very useful, such as providing message feedback for some operations.

The messages provided by the flash function are not automatically displayed on our website page, so we need to do something to display them on the page. To make all our pages have this exciting feature, add it to the basic template. below is the updated Basic Template (fileapp/templates/base.html ):

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

<Html>

<Head>

{% If title %}

<Title >{{ title }}- microblog </title>

{% Else %}

<Title> microblog </title>

{% Endif %}

</Head>

<Body>

<Div> Microblog: <a href = "/index"> Home </a> </div>

<Hr>

{% With messages = get_flashed_messages () %}

{% If messages %}

<Ul>

{% For message in messages %}

<Li >{{ message }}</li>

{% Endfor %}

</Ul>

{% Endif %}

{% Endwith %}

{% Block content %} {% endblock %}

</Body>

</Html>

We hope you can understand the flash message display function in the template.

Another new function we use in the view function is redirect. This function will notify the user's browser to jump to the specified address. In our view function, we use it to jump to the homepage. Note: after the jump ends, the page will display the flash function message.

It was an exciting time to run our program and see how the form works. Do not fill in the openid field in the form to see how the Required verification function powers and block all requests that initiate empty data thousands of miles away.

Improve field verification

Our program is currently in good condition. Submitting Unqualified Data will be blocked, and a form will be returned for users to modify, basically meeting our requirements.

But it seems that there is nothing left. If we give a prompt to the user after the user fails to submit the data, let them know why it is caused! Fortunately, using Flask-WTF can easily solve this problem.

When the form field verification fails, Flask-WTF adds an error message to the form object. These messages can also be used in the template, so we only need to add a little bit in the template to OK.

This is the login template (fileapp/templates/login.html) that we added to the verification message ):

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

<! -- Extend base layout -->

{% Extends "base.html" %}

 

{% Block content %}

<H1> Sign In

<Form action = "" method = "post" name = "login">

{Form. hidden_tag ()}}

<P>

Please enter your OpenID: <br>

{Form. openid (size = 80) }}< br>

{% For error in form. errors. openid %}

<Span style = "color: red;"> [{error}] </span>

{% Endfor %} <br>

</P>

<P >{{ form. remember_me }} Remember Me </p>

<P> <input type = "submit" value = "Sign In"> </p>

</Form>

{% Endblock %}

We only add a loop statement to the right of the openid field, which will display all messages that fail to verify the openid field. Regardless of the number of fields in your form, the form. errors. Field name can be used in error messages that fail to verify all form fields. In this form, we use form. errors. openid. In order for the error message to attract the user's attention, we also added a red css style to the message.

Process OpenID Logon

In real life, we find that many people do not know that they have some public accounts. Some big-name websites or service providers provide public account authentication for their members. For example, if you have a google account, you actually have a public account, such as Yahoo, AOL, and Flickr.

To make it easier for our users to use their public accounts, we will add the links to these public accounts to a list so that users do not have to manually enter them.

Let's define some public account service providers that provide users to a list. Put this list in the configuration file (fileconfig. py ):

?

1

2

3

4

5

6

7

8

9

CSRF_ENABLED = True

SECRET_KEY = 'you-will-never-guess'

 

OPENID_PROVIDERS = [

{'Name': 'Google ', 'url': 'https: // www.google.com/accounts/o8/id '},

{'Name': 'yahoo ', 'url': 'https: // me.yahoo.com '},

{'Name': 'aol ', 'url': 'http: // openid.aol.com/<username> '},

{'Name': 'flickr', 'url': 'http: // www.flickr.com/<username> '},

{'Name': 'myopenid', 'url': 'https: // www.myopenid.com '}]

Next we will use this list in our logon view function:

?

1

2

3

4

5

6

7

8

9

10

@ App. route ('/login', methods = ['get', 'post'])

Def login ():

Form = LoginForm ()

If form. validate_on_submit ():

Flash ('login requested for OpenID = "'+ form. openid. data +'", remember_me = '+ str (form. remember_me.data ))

Return redirect ('/Index ')

Return render_template('login.html ',

Title = 'sign in ',

Form = form,

Providers = app. config ['openid _ PROVIDERS '])

We introduced the configuration list of the public account service provider from app. config, and then introduced it as a parameter to the template through the render_template function.

As you can guess, we need to display the links of these service providers in the logon template.

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

<! -- Extend base layout -->

{% Extends "base.html" %}

 

{% Block content %}

<Script type = "text/javascript">

Function set_openid (openid, pr)

{

U = openid. search ('<username> ')

If (u! =-1 ){

// Openid requires username

User = prompt ('enter your' + pr + 'username :')

Openid = openid. substr (0, u) + user

}

Form = document. forms ['login'];

Form. elements ['openid']. value = openid

}

</Script>

<H1> Sign In

<Form action = "" method = "post" name = "login">

{Form. hidden_tag ()}}

<P>

Please enter your OpenID, or select one of the providers below: <br>

{Form. openid (size = 80 )}}

{% For error in form. errors. openid %}

<Span style = "color: red;"> [{error}] </span>

{% Endfor %} <br>

| {% For pr in providers %}

<A href = "javascript: set_openid ('{pr. url} ',' {pr. name} '); ">{{ pr. name }}</a> |

{% Endfor %}

</P>

<P >{{ form. remember_me }} Remember Me </p>

<P> <input type = "submit" value = "Sign In"> </p>

</Form>

{% Endblock %}

This time the template seems to have added a lot of things. Some public accounts need to provide user names. To solve this problem, we use javascript. When a user clicks the relevant public account link, the public account that requires the user name will prompt the user to enter the user name, and javascript will process the user name as an available public account, then insert it into the text box of the openid field.

The following figure is displayed after you click the google link on the logon page:

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.