python web開發 框架 模板 MVC


我是跟着廖雪峰老師學習的,對於我這樣的純小白來說,跟着他的網站學習,簡直是被媽媽抱在懷里一樣無憂無慮,這樣的學習本來沒有記錄下來的必要,但是由於我的粗心大意,經常會出現一些錯誤,所以我決定把這些錯誤記錄下來,順便把知識網絡也記下來

網站地址:https://www.liaoxuefeng.com/wiki/0014316089557264a6b348958f449949df42a6d3a2e542c000/001432012393132788f71e0edad4676a3f76ac7776f3a16000

參考鏈接:https://aiohttp.readthedocs.io/en/stable/web_quickstart.html#run-a-simple-web-server

一、WSGI接口

  可以通過這個接口,將更復雜的HTTP協議交給模塊處理,而只專注與web業務

  通過WSGI接口,只要求開發者實現一個函數,就能響應HTTP請求

  無多多么復雜的web應用程序,入口都是一個WSGI處理函數。HTTP請求的所有輸入信息都可以通過 environ 獲得,HTTP響應的輸出都可以通過 start_response() 加上函數返回值作為Body

  復雜的web應用程序,光靠一個WSGI函數來處理還是太底層了,我們需要在WSGI之上在抽象出來一些框架,進一步簡化Web開發

   

出現的問題:

  問題:UnicodeDecodeError: 'utf-8' codec can't decode byte 0xb3 in position 0: invalid start byte

  解決辦法:計算機名字是中文的,改成英文的

  

  問題:localhost 拒絕了我們的連接請求。

  解決辦法:因為我是在虛擬環境里運行的程序,但是為了編輯方便,我就打開了IDLE(在IDLE里編輯,然后在命令行里運行)結果就出現了這個錯誤,把IDLE關了就好了

 

二、使用Web框架

  通過使用框架,能讓我們只專注於一個函數處理一個URL,而不必關注與URL到函數之間的映射,則交給web框架去完成,web框架完成了在WSGI接口上進一步的抽象,有很多框架可以供我們使用,這里以Flask為例

  每個URL對應的GET和POST請求(當然還有其他的請求)都可以單獨映射為兩個函數處理或交給一個函數去處理,使用框架后,框架通過python的裝飾器在內部自動的把不同的URL映射到相應的函數

  

from flask import Flask
from flask import request

app=Flask(__name__)

@app.route('/',methods=['GET','POST'])#路徑和請求方式,默認是127.0.0.1,怎么配置別的我還不知道
def home():
    return '<h1>Home</h1>'

@app.route('/signin',methods=['GET'])
def singnin_form():
    return'''<form action="/signin" method="post">#action代表提交到的地址
             <p><input name="username"></p>
             <p><input name="password" type="password"></p>
             <p><button type="submit">Sign In</button></p>
             </form>'''

@app.route('/signin',methods=['POST'])
def singin():
    #需要從request對象讀取表單內容:
    if request.form['username']=='admin' and request.form['password']=='123':#獲取表單內容的方式
        return'<h3>Hello admin</h3>'
    return '<h3>Bad username or password.</h3>'

if __name__=='__main__':
    app.run()

  在編寫URL處理函數時,除了配置URL外,從HTTP請求拿到用戶數據也是非常重要的。Web框架都提供了自己的API來實現這些功能。Flask通過 request.form['name'] 來獲取表單的內容。

  教程地址:https://www.liaoxuefeng.com/wiki/0014316089557264a6b348958f449949df42a6d3a2e542c000/001432012745805707cb9f00a484d968c72dbb7cfc90b91000#0

 

出現的問題

  問題:按下表單按鈕后沒有反應,並且鏈接也變成了 http://127.0.0.1:5000/signin?username=admin&password= 

  解決辦法:一開始為認為如果沒有響應,那么一定是映射的問題(后來才知道其實還可能是部件寫錯了)。是以為對函數的映射出了問題,然后去找沒有發現,后來經過與老師代碼的比對才發現構建表單時的代碼寫錯了

<form action="/signin" methods="post">#action代表提交到的地址
#應該是
<form action="/signin" method="post">#action代表提交到的地址

  

三、使用模板

  通過字符串來構建web頁面是不可行的,所以模板技術出現了。使用模板,我們必須先准備一個HTML文檔,這個文檔並不是普通的HTML文檔,而是帶有參數和變量的,然后根據我們傳入的數據,替換后,得到最終的HTML,發給用戶。

  這就是MVC(model-view-controller)模型視圖 控制器

  控制器負責任務邏輯,比如登錄時檢查用戶名和密碼是否正確,python中處理URL的相應函數就是控制器

  視圖就是用來展示給用戶的界面,不過需要經過處理。需要填入一些我們的數據

  模型就是要向視圖中填入的數據,是用來傳給view的,view在替換變量的時候,就從model中取出相應的數據

  只是因為Python支持關鍵字參數,很多Web框架允許傳入關鍵字參數,然后,在框架內部組裝出一個dict作為Model。

  

使用:

  Flask通過 render_template() 函數來實現模板的渲染。和Web框架類似,Python的模板也有很多種。Flask默認支持的模板是jinja2,所以我們需要先直接安裝jinja2

  在Jinja2模板中,我們用 {{ name }} 表示一個需要替換的變量。很多時候,還需要循環、條件判斷等指令語句,在Jinja2中,用 {% ... %} 表示指令。

from flask import Flask, request, render_template

app = Flask(__name__)

@app.route('/', methods=['GET', 'POST'])
def home():
    return render_template('home.html')
--snip--

 

  然后,開始編寫jinja2模板:

#代碼見鏈接
#home.html 用來顯示首頁的模板: --snip-- #form.html 用來顯示登錄表單的模板
<html> <head> <title>Please Sign In</title> </head> <body> {% if message %}#命令 <p style="color:red">{{ message }}</p>#參數 {% endif %} <form action="/signin" method="post"> <legend>Please sign in:</legend> <p><input name="username" placeholder="Username" value="{{ username }}"></p> <p><input name="password" placeholder="Password" type="password"></p> <p><button type="submit">Sign In</button></p> </form> </body> </html> #signin-ok.html登錄成功的模板:
--snip--

 

指令的使用方法實例  

{% for i in page_list %}#如果page_list是一個列表:1、2、3,下面代碼會輸出5個超鏈接
    <a href="/page/{{ i }}">{{ i }}</a>
{% endfor %}

     

最后,一定要把模板放到正確的 templates 目錄下, templates 和 app.py 在同級目錄下,這個templates需要新建

通過MVC,我們在Python代碼中處理M:Model(就是個性化的數據)和C:Controller,而V:View是通過模板處理的(由模板是大部分已經完成的,只是還需要些數據),這樣,我們就成功地把Python代碼和HTML代碼最大限度地分離了。

 

遇到問題:

  問題:500 internal server error

 

Traceback (most recent call last):
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\flask\app.py", line 2292, in wsgi_app
    response = self.full_dispatch_request()
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\flask\app.py", line 1815, in full_dispatch_request
    rv = self.handle_user_exception(e)
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\flask\app.py", line 1718, in handle_user_exception
    reraise(exc_type, exc_value, tb)
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\flask\_compat.py", line 35, in reraise

    raise value
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\flask\app.py", line 1813, in full_dispatch_request
    rv = self.dispatch_request()
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\flask\app.py", line 1799, in dispatch_request
    return self.view_functions[rule.endpoint](**req.view_args)
  File "./envs/web_go/app.py", line 21, in singin
    return render_template('signin_ok.html',username=username)
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\flask\templating.py", line 134, in render_template
    return _render(ctx.app.jinja_env.get_or_select_template(template_name_or_list),
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\jinja2\environment.py", line 869, in get_or_select_template
    return self.get_template(template_name_or_list, parent, globals)
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\jinja2\environment.py", line 830, in get_template
    return self._load_template(name, self.make_globals(globals))
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\jinja2\environment.py", line 804, in _load_template
    template = self.loader.load(self, name, globals)
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\jinja2\loaders.py", line 113, in load
    source, filename, uptodate = self.get_source(environment, name)
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\flask\templating.py", line 58, in get_source
    return self._get_source_fast(environment, template)
  File "C:\Users\Administrator.SC-201605202132\Envs\web_go\lib\site-packages\flask\templating.py", line 86, in _get_source_fast
    raise TemplateNotFound(template)
jinja2.exceptions.TemplateNotFound: signin_ok.html
127.0.0.1 - - [18/Mar/2019 14:23:12] "POST /signin HTTP/1.1" 500 -

  解決辦法: 閱讀錯誤信息,發現是目標頁面的名字拼錯了(要認真閱讀提示)


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM