Python's Tornado framework implements asynchronous non-blocking access to the database

Source: Internet
Author: User
Tags install mongodb
Tornado is an HTTP non-blocking server to use, we will use the Tornado framework, MONGODB Database and motor (MongoDB asynchronous driver). To implement the Tornado non-blocking function simply.

Other environment-supported downloads and installations

1. Installing MongoDB

$ sudo apt-get install update$ sudo apt-get install MongoDB

2. Install motor

$ pip Install motor

Non-blocking

# Conf.pyimport Osimport motorfrom Handlers Import index, Authbase_dir = Os.path.join (__file__) handlers = [  (R ' ^/$ ', I Ndex. Indexhandler),  (R ' ^/auth/register$ ', auth. Registerhandler),  (R ' ^/auth/login$ ', auth. Loginhandler),]settings = Dict (  debug = True,  template_path = Os.path.join (base_dir, ' templates '),  static _path = Os.path.join (Base_dir, ' static '), client = motor. Motorclient ("127.0.0.1") db = Client.meet

First connect to the database in the configuration file, Client.db_name db_name is the name of the database

# Handlers/__init__.pyclass Basehandler (Tornado.web.RequestHandler, templaterendering):  def initialite (self):    ...  @property  def db (self):    return self.application.db

Add db () and use property decorations to access the database like attributes.

# auth.pyimport OS import time import tornado.webfrom Tornado import Genfrom. Import Basehandlerclass Registerhandler (Basehandler):  def get (self):    self.render_html (' register.html ')  @tornado. web.asynchronous  @gen. Coroutine  def post (self):    username = self.get_argument (' username ' , none)    email = self.get_argument (' email ', none)    password = self.get_argument (' password ', none)    data = {      ' username ': username,      ' email ': email,      ' password ': password,      ' timestamp ': time.time () * 1000,    }    If username and email:      yield self.db.user.insert (data)    self.redirect ('/') class Loginhandler (Basehandler):    @tornado. web.asynchronous  @gen. Coroutine  def get (self):    username = self.get_argument (' Useranme ')    user = yield Self.db.user.find_one ({' username ': username})    self.render_html (' login.html ', user =user)

@gen. Coroutine decoration makes the function non-blocking and returns a generator instead of using a callback function. Motor is also asynchronous by yield (or return a callback function). In fact, this example does not reflect that the problem with blocking is that time is too short.
Let's change the code.

# before yield Self.db.user.insert (data) # yield Tornado.gen.Task (Tornado.ioloop.IOLoop.instance (). Add_timeout, Time.time () + 10)

Here through the Tornado.ioloop.IOLoop.instance (). Add_timeout blocking application, which is a non-blocking implementation of Time.sleep, If you use time.sleep here because Tornado is a single thread that will block the entire application, other handler cannot be accessed.
You can see that I registered on the registration page, during blocking, click/auth/login directly to access the login page to complete non-blocking.

The problem of redirect under asynchronous
In the use of tornado often encountered some problems, special will encounter problems and solutions to write (thank you for helping me to answer the doubts of the Pythonista)

1. Questions

I want to implement a registered user feature, and the web framework uses the Tornado database to use MongoDB but exception redirect errors occur while registering. Now put the code:

Class Register (Basehandler): Def get (self): self.render_html (' register.html ') @tornado. web.aynchronous @gen. Coroutin E def post (self): username = self.get_argument (' username ') email = self.get_argument (' email ') Password = self.ge T_argument (' password ') Captcha = self.get_argument (' captcha ') _verify_username = yield Self.db.user.find_one ({' Usern Ame ': username}) if _verify_username:self.flash (U ' user name already exists ', ' Error ') self.redirect ('/auth/register ') _veri Fy_email = Yield Self.db.user.find_one ({' Email ': email}) If _verify_email:self.flash (U ' mailbox registered ', ' error ') self . Redirect ('/auth/register ') if captcha and captcha = = Self.get_secure_cookie (' captcha '). Replace (', '): Self.flas H (U ' Verification code input correct ', ' info ') else:self.flash (U ' captcha input error ', ' Error ') self.redirect ('/auth/register ') password = has          LIB.MD5 (password + self.settings[' site '). Hexdigest () profile = {' headimg ': ', ' site ': ', ' job ': ', ' signature ': ', ' GitHub ': ', 'Description ': '} user_profile = yield Self.db.profile.insert (profile) user = {' username ': username, ' email ': email, ' Password ': password, ' timestamp ': time.time (), ' profile_id ': str (user_profile)} yield Self.db.user.insert (user ) Self.set_secure_cookie (' user ', username) self.redirect ('/')

I would like to jump to the registration page if the user code input error, but the problem is that the CAPTCHA error will continue to execute the code. Although adding self.finish will terminate the code after self.redirect, there are two code that reported an abnormal termination because there is already self.finish in the Self.redirect function.
Because the above reason code will not be terminated, the CAPTCHA error will be registered by the user.

2. Solution

Return Self.redirect ('/auth/register ')

Or

Self.redirect ('/auth/register ') return

(1) Segmentdefault of enthusiastic user rsj217 the answer
Self.finish will turn off the request because @tornado.web.aynchronous tells Tornado to wait for the request (long link). Self.redirect equals the Location property of the headers that set the response.

(2) The answer of the enthusiastic user Evian in Segmentdefault
Self.finish certainly does not jump out of the function, or else want to do something after the request is over.

3. Summary

Because of the mistake of Self.finish as a function of jumping out of the above problems

Self.redirect will set the location in request.headers for jumping.

Self.finish turns off the request, but does not jump out of the function

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.