摘要:的模型使用模型的原因當(dāng)項(xiàng)目越來(lái)越大的時(shí)候會(huì)出現(xiàn)很多問(wèn)題原生較多重復(fù)使用率低如果你的數(shù)據(jù)庫(kù)發(fā)生了改變所有的原生就都要進(jìn)行修改寫(xiě)原生的時(shí)候會(huì)有安全隱患中文件關(guān)系對(duì)象的映射使用去操作數(shù)據(jù)庫(kù)的時(shí)候不會(huì)再去寫(xiě)原生的了通過(guò)把表映射成類(lèi)字段為你的屬性在
Flask-SQLalchemy flask的ORM模型 使用ORM模型的原因
當(dāng)項(xiàng)目越來(lái)越大的時(shí)候 會(huì)出現(xiàn)很多問(wèn)題
原生SQL較多 重復(fù)使用率低
如果你的數(shù)據(jù)庫(kù)發(fā)生了改變 所有的原生SQL就都要進(jìn)行修改
寫(xiě)原生SQL的時(shí)候 會(huì)有安全隱患
ORM:中文件關(guān)系對(duì)象的映射 使用ORM去操作數(shù)據(jù)庫(kù)的時(shí)候 不會(huì)再去寫(xiě)原生的SQL了 通過(guò)把表映射成 類(lèi) 字段為你的屬性 ORM在執(zhí)行的時(shí)候 也會(huì)最終轉(zhuǎn)換為 SQL語(yǔ)句 去操作數(shù)據(jù)庫(kù)
易用性 使用ORM可以減少重復(fù)SQL的概率 寫(xiě)出來(lái)的模型也更加的直觀清晰
可移植性 ORM支持很多不同的數(shù)據(jù)庫(kù)
安裝:
sudo pip3 install flask-sqlalchemy
一、執(zhí)行原生SQL (1) 創(chuàng)建數(shù)據(jù)庫(kù)create database if not exists 庫(kù)名 character set utf8;
(2) 安裝pymysqlsudo pip3 install pymysql
(3) 配置數(shù)據(jù)庫(kù)DB_URI = "mysql+pymysql://用戶(hù)名:密碼@主機(jī):端口號(hào)/庫(kù)名"
實(shí)例
from sqlalchemy import create_engine DATABASE = "hz03" USERNAME = "root" PASSWORD = "123456" HOST = "127.0.0.1" PORT = "3306" #創(chuàng)建連接和操作數(shù)據(jù)庫(kù)的URI DB_URI = "mysql+pymysql://{}:{}@{}:{}/{}".format(USERNAME,PASSWORD,HOST,PORT,DATABASE) #創(chuàng)建操作數(shù)據(jù)庫(kù)的引擎 engine = create_engine(DB_URI) with engine.connect() as con: # con.execute("create table user(id int,username varchar(255),sex tinyint)") con.execute("insert into user values(1,"xxx",1)")二、在flask中使用ORM (1) 當(dāng)前字段類(lèi)型
類(lèi)型名 | 說(shuō)明 |
---|---|
integer | 整形 |
SmallInteger | 小整形 |
BigInteger | 長(zhǎng)整型 |
Float | 浮點(diǎn)型 |
String | varchar類(lèi)型 |
Text | 長(zhǎng)文本 |
Boolean | tingint |
Date | 日期 datetime.date |
Time | 時(shí)間 datetime.time |
DateTime | 時(shí)間和日期 datetime.datetim |
選項(xiàng) | 選項(xiàng)說(shuō)明 |
---|---|
primary_key | 主鍵 默認(rèn) False |
index | 常規(guī) 默認(rèn) False |
Unique | 唯一 默認(rèn) False |
nullable | 是否為null 默認(rèn)True |
default | 默認(rèn)值 |
注意:
其中的default默認(rèn)值 并不是更改表結(jié)構(gòu)的默認(rèn)值 而是在插入數(shù)據(jù)的時(shí)候 如果不插入數(shù)據(jù) 則插入默認(rèn)值
實(shí)例
配置from flask import Flask,render_template from flask_script import Manager from flask_sqlalchemy import SQLAlchemy app = Flask(__name__) #創(chuàng)建連接數(shù)據(jù)的URI app.config["SQLALCHEMY_DATABASE_URI"] = "mysql+pymysql://root:123456@127.0.0.1:3306/hz03" app.config["SQLALCHEMY_COMMIT_ON_TEARDOWN"] = True #開(kāi)啟自動(dòng)提交 #數(shù)據(jù)的追蹤 當(dāng)數(shù)據(jù)發(fā)生改變時(shí) 會(huì)返回信號(hào)量 進(jìn)行關(guān)閉 app.config["SQLALCHEMY_TRACK_MODIFICATIONS"] = False db = SQLAlchemy(app) manager = Manager(app)創(chuàng)建模型
class User(db.Model): id = db.Column(db.Integer,primary_key=True) username = db.Column(db.String(20),index=True) age = db.Column(db.Integer) icon = db.Column(db.String(40),default="default.jpg")數(shù)據(jù)的添加修改刪除
@app.route("/create_table/") def create_table(): db.drop_all() #刪除 和當(dāng)前模型類(lèi)同名的表 db.create_all() #創(chuàng)建當(dāng)前模型類(lèi)的表 return "創(chuàng)建表" @app.route("/insert/") def insert(): try: u = User(username="張三",age=18) # print(u) db.session.add(u) db.session.commit() #因?yàn)閟qlalchemy開(kāi)啟事物 所有所以需要提交或者回滾 except: db.session.rollback() return "添加數(shù)據(jù)" #開(kāi)啟了自動(dòng)提交功能 不需要手動(dòng)commit了 @app.route("/insert_two/") def insert_two(): u = User(username="李四",age=20) db.session.add(u) return "走我了" #修改 @app.route("/update/") def update(): u = User.query.get(1) # print(u.id) # print(u.username) u.username = "王五" db.session.add(u) return "update" #刪除 @app.route("/delete/") def delete(): u = User.query.get(2) #查詢(xún)成功返回 對(duì)象 失敗返回None # print(u) db.session.delete(u) return "刪除"拆分MVT 目錄結(jié)構(gòu)
project/ App/ __init__.py 包文件必須的 model.py 模塊 views.py 視圖 ext.py extensions.py 加載第三方擴(kuò)展的文件 settings.py 配置文件 static/ templates/ manage.py 啟動(dòng)項(xiàng)細(xì)致的
project/ App/ __init__.py static/ js/ img/ upload/ css/ templates/ common/ ... forms/ __init__.py ... models/ __init__.py views/ __init.py__.py ... settings.py email.py extensions.py manager.py migrations/ venv/三、數(shù)據(jù)的操作
創(chuàng)建模型類(lèi)
class User(Base,db.Model): __tablename__ = "user" #給表起名 id = db.Column(db.Integer,primary_key=True) username = db.Column(db.String(20),index=True) age = db.Column(db.Integer) icon = db.Column(db.String(40),default="default.jpg") def __init__(self,username="",age=0,icon="default.jpg"): self.username = username self.age = age self.icon = icon(1) 添加 add add_all 添加一條
@main.route("/add/") def add(): u = User(username="張三",age=18) db.session.add(u) db.session.commit() return "數(shù)據(jù)添加一條成功"添加多條
@main.route("/add_all/") def add_all(): u1 = User(username="李四",age=20) u2 = User(username="王五",age=22) db.session.add_all([u1,u2]) db.session.commit() return "添加多條"(2) 自定義增刪改的基礎(chǔ)類(lèi)
class Base: #定義一個(gè)添加一條數(shù)據(jù)的方法 def save(self): try: db.session.add(self) db.session.commit() except: db.session.rollback() #定義添加多條數(shù)據(jù)的方法 @staticmethod def save_all(*args): try: db.session.add_all(args) db.session.commit() except: db.session.rollback() #自定義刪除方法 def delete(self): try: db.session.delete(self) db.session.commit() except: db.session.rollback()
使用
class User(Base,db.Model): ...
在視圖中使用
@main.route("/add/") def add(): # u = User(username="張三",age=18) u = User("張三",18) # db.session.add(u) # db.session.commit() u.save() #使用自定義的添加方法 return "數(shù)據(jù)添加一條成功" @main.route("/add_all/") def add_all(): # u1 = User(username="李四",age=20) # u2 = User(username="王五",age=22) u1 = User("趙六",27) u2 = User("李七",12) # db.session.add_all([u1,u2]) # db.session.commit() User.save_all(u1,u2) return "添加多條" @main.route("/delete/") def delete(): u = User.query.get(1) u.delete() return "刪除"四、數(shù)據(jù)庫(kù)操作 查詢(xún)集
查詢(xún)數(shù)據(jù)的集合
分類(lèi)
原始查詢(xún)集
類(lèi)名.query得到的結(jié)果就為原始查詢(xún)集
數(shù)據(jù)查詢(xún)集
加上各種的過(guò)濾器的方法 最終返回的結(jié)果 為數(shù)據(jù)查詢(xún)集 都使用數(shù)據(jù)查詢(xún)集
過(guò)濾器 (1) all 查詢(xún)所有 以列表形式返回 不支持連貫操作類(lèi)名.query.all()
@main.route("/all/") def all(): data = User.query.all() print(data) return render_template("show.html",data=data)(2) filter() 過(guò)濾
類(lèi)名.query.filter([類(lèi)名.屬性名 條件操作符 值])
默認(rèn)返回所有
#支持連貫操作 @main.route("/filter/") def filter(): # data = User.query.filter() #返回所有 # data = User.query.filter(User.age>20) #查詢(xún)年齡大于20的數(shù)據(jù) data = User.query.filter(User.age>20,User.age<40) #查詢(xún)年齡大于20的數(shù)據(jù) and 小于40 print(data) return render_template("show.html",data=data)(3) filter_by 只支持參數(shù)為關(guān)鍵字參數(shù)
類(lèi)名.query.filter_by(屬性名=值...)
@main.route("/filter_by/") def filter_by(): # data = User.query.filter_by(id=2) # data = User.query.filter_by(id>2) #錯(cuò)誤寫(xiě)法 data = User.query.filter_by(id=2,age=27) return render_template("show.html",data=data)(4) offset 偏移量
offset(num)
#偏移量取值 @main.route("/offset/") def offset(): data = User.query.filter().offset(2) return render_template("show.html",data=data)(5) limit 取值
limit(num)
@main.route("/limit/") def limit(): # data = User.query.limit(2) data = User.query.filter(User.age>30).limit(2) return render_template("show.html",data=data)(6) offset和limit組合使用
@main.route("/offsetlimit/") def offsetlimit(): data = User.query.offset(2).limit(2) # limit 2,2 return render_template("show.html",data=data)(7) order_by() 排序
@main.route("/order_by/") def order_by(): # data = User.query.order_by(User.age) #升序 data = User.query.order_by(-User.age) #降序 return render_template("show.html",data=data)(8) first 取出第一條數(shù)據(jù) 返回對(duì)象
@main.route("/first/") def first(): # data = User.query.first() == User.query.get(2) print(data) print(data.id) print(data.username) return "取出第一條數(shù)據(jù)"(9) get 獲取id對(duì)應(yīng)的數(shù)據(jù)
查詢(xún)成功返回對(duì)象 查詢(xún)失敗 返回None
@main.route("/first/") def first(): data = User.query.get(2) return "取出第一條數(shù)據(jù)"(10) contains 包含關(guān)系
@main.route("/contains/") def contains(): #username中包含數(shù)字7的數(shù)據(jù) data = User.query.filter(User.username.contains("7")) return render_template("show.html",data=data)(11) like 模糊查詢(xún)
@main.route("/like/") def like(): #username中包含數(shù)字7的數(shù)據(jù) # data = User.query.filter(User.username.like("%7%")) # data = User.query.filter(User.username.like("李%")) #以李作為開(kāi)頭的 data = User.query.filter(User.username.like("%6")) #以6作為結(jié)尾的數(shù)據(jù) return render_template("show.html",data=data)(12) startswith endswith 以...開(kāi)頭 以...結(jié)尾
#startswith endswith @main.route("/startend/") def startend(): # data = User.query.filter(User.username.startswith("李")) data = User.query.filter(User.username.endswith("6")) return render_template("show.html",data=data)(13) 比較運(yùn)算符
__gt__
__ge__
__lt__
__le__
>
<
>=
<=
==
!=
@main.route("/bjiao/") def bjiao(): # data = User.query.filter(User.age.__gt__(20)) # data = User.query.filter(User.age.__ge__(99)) data = User.query.filter(User.age!=99) return render_template("show.html",data=data)(14) in 和 not in
@main.route("/in/") def myIn(): # data = User.query.filter(User.age.in_([27,12,1,30,40,50])) data = User.query.filter(~User.age.in_([27,12,1,30,40,50])) return render_template("show.html",data=data)(15) is null
@main.route("/null/") def null(): # data = User.query.filter(User.username == None) # data = User.query.filter(User.username != None) # data = User.query.filter(User.username.is_(None)) data = User.query.filter(User.username.isnot(None)) return render_template("show.html",data=data)(16) and_
多個(gè)條件 用逗號(hào)隔開(kāi),為and操作
from sqlalchemy import and_
@main.route("/and/") def myAnd(): # data = User.query.filter(User.age==27,User.id==2) data = User.query.filter(and_(User.age==27,User.id==2)) return render_template("show.html",data=data)(17) or_
from sqlalchemy import or_
@main.route("/and/") def myAnd(): data = User.query.filter(or_(User.age==27,User.id==2)) data = User.query.filter(and_(User.username.like("%6%")),or_(User.age>=27,User.id==2)) return render_template("show.html",data=data)(18) not_
from sqlalchemy import not_
@main.route("/and/") def myAnd(): # data = User.query.filter(not_(User.age>27,User.id==1)) #錯(cuò)誤寫(xiě)法只能給一個(gè)條件取反 data = User.query.filter(not_(User.age>27)) return render_template("show.html",data=data)(19) count 統(tǒng)計(jì)
data = User.query.filter(not_(User.age>27)).count()四、文件的遷移
模塊:
pip install flask-migrate
pip install flask-script
使用 (1) 實(shí)例化from flask_migrate import Migrate,MigrateCommand from flask_sqlalchemy import SQLalchemy app = Flask(__name__) db = SQLalchemy(app) migrate = Migrate(app,db=db) manager = Manager(app) manager.add_command("db",MigrateCommand)(2) 初始化 遷移文件目錄
python manage.py db init
(3) 生成遷移文件python manage.py db migrate
(4) 執(zhí)行遷移文件python manage.py db upgrade
注意
如果當(dāng)前存在 模型 但是執(zhí)行創(chuàng)建遷移文件的時(shí)候 提示沒(méi)有任何改變的時(shí)候 需要查看當(dāng)前的模型類(lèi)是否有使用(導(dǎo)入)
文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://specialneedsforspecialkids.com/yun/41833.html
摘要:文件上傳郵件發(fā)送一原生文件上傳修改頭像提交文件上傳的視圖函數(shù)有文件上傳了拿到文件名稱(chēng)圖片上傳保存的路徑使用和渲染文件上傳自定義一個(gè)文件上傳的表單類(lèi)修改頭像文件不能為空該文件類(lèi)型不允許上傳提交生成隨機(jī)的圖片名稱(chēng)獲取圖片大小設(shè)置尺寸當(dāng)前縮放 文件上傳郵件發(fā)送 一、原生文件上傳 form.html 修改頭像 manage.py...
摘要:我們的論壇項(xiàng)目就使用了該框架。此外,麥子學(xué)院也有一個(gè)入門(mén)視頻教程,一共小時(shí)的視頻教程,涵蓋開(kāi)發(fā)的方方面面,包括環(huán)境的搭建,語(yǔ)法介紹,項(xiàng)目結(jié)構(gòu)的組織,全球化,單元測(cè)試等內(nèi)容。博客地址更多閱讀的機(jī)制三個(gè)框架的對(duì)比 前面兩篇文章中我們已經(jīng)了解 Web(HTTP)服務(wù)器,Web應(yīng)用程序,Web框架,WSGI這些 Python Web 開(kāi)發(fā)中的概念。我們知道,Web框架通過(guò)將不同Web應(yīng)用程序中...
摘要:表單一原生表單原生表單用戶(hù)名請(qǐng)輸入用戶(hù)名密碼請(qǐng)輸入密碼提交接收表單的數(shù)據(jù)提交過(guò)來(lái)了將倆個(gè)路由地址合并為同一個(gè)二使用表單擴(kuò)展庫(kù)作用是一個(gè)用于表單處理的擴(kuò)展庫(kù)提供表單的校驗(yàn)的功能使用字段類(lèi)型字段名稱(chēng)字段類(lèi)型普通文本字段密碼框提交按鈕多行文本 flask 表單 一、原生表單 form.html {% extends common/base.html %} {% block title %} ...
閱讀 2804·2021-11-19 11:35
閱讀 2582·2021-11-02 14:40
閱讀 1396·2021-09-04 16:48
閱讀 3009·2019-08-30 15:55
閱讀 1753·2019-08-30 13:11
閱讀 1956·2019-08-29 11:12
閱讀 1088·2019-08-27 10:52
閱讀 3157·2019-08-26 18:36