Flask高效數據庫操作指南

Flask-SQLAlchemy 數據庫操作

關于Flask數據庫

Flask中沒有指定使用的數據庫,可以自由選擇不管你是使用關系型數據庫,還是非關系型數據庫都可以,不像django提供了orm 數據庫抽象層,可以直接采用對象的方式操作數據庫。但是為了開發效率,在開發Flask項目中我們一般會選擇 SQLALchemy 來操作數據庫,類似于Django的ORM。SQLALchemy實際上是對數據庫的抽象,讓開發者不直接使用sql語句做開發,而是通過Python對象來操作數據庫,在舍棄一些性能開銷的同時,換來的是開發效率的較大提升。

SQLAlchemy是一個關系型數據庫框架,它提供了高層的ORM和底層的原生數據庫的操作。為了簡化配置和操作,我們使 Flask-SQLAlchemy,這個 Flask 擴展封裝了 SQLAlchemy 框架。

安裝 Flask-SQLAlchemy

pip install Flask-SQLAlchemy

要連接mysql數據庫還需要安裝flask-mysqldb

pip install flask-mysqldb

如果安裝報下面錯誤

Command "python setup.py egg_info" failed with error code 1

請先安裝執行下面這條命令:(Linux)

sudo apt-get install mysql-server libmysqld-dev

示例:

from flask import Flask
from flask_sqlalchemy import SQLAlchemy
?
app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'mysql://root:xxxxxx@127.0.0.1/flask01'
app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = True ?# 追蹤對象的修改并且發送信號
db = SQLAlchemy(app)
?
class User(db.Model):# SQLAlchemy 需要手動執行主鍵列,第一個參數是 字段類型,第二個參數是約束條件id = db.Column(db.Integer,primary_key=True)name = db.Column(db.String(20),unique=True)
?
if __name__ == '__main__':with app.app_context(): ?# 添加應用上下文# 創建所有表db.create_all()

1. 數據庫連接配置

from flask import Flask
from flask_sqlalchemy import SQLAlchemy
?
app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'mysql://root:mysql@127.0.0.1:3306/py'
app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = True ?# 追蹤對象的修改并且發送信號
db = SQLAlchemy(app)

配置鍵說明

配置鍵說明
SQLALCHEMY_DATABASE_URI設置連接數據庫<br>格式:mysql://username:password@server/db
SQLALCHEMY_BINDS一個映射綁定 (bind) 鍵到 SQLAlchemy 連接 URIs 的字典。更多的信息請參閱 綁定多個數據庫。
SQLALCHEMY_ECHO如果設置成 True,SQLAlchemy 將會記錄所有 發送 標準輸出(stderr)的語句,這對調試很有幫助。
SQLALCHEMY_RECORD_QUERIES可以用于顯式地禁用或者啟用查詢記錄。查詢記錄 在調試或者測試模式下自動啟用。更多信息請參閱 get_debug_queries()。
SQLALCHEMY_NATIVE_UNICODE可以用于顯式地禁用支持原生的 unicode。這是 某些數據庫適配器必須的(像在 Ubuntu 某些版本上 的 PostgreSQL),當使用不合適的指定無編碼的數 據庫 默認值時。
SQLALCHEMY_POOL_SIZE數據庫連接池的大小、默認是數據庫引擎的默認值 (通常是 5)。
SQLALCHEMY_POOL_TIMEOUT指定數據庫連接池的超時時間。默認是 10。
SQLALCHEMY_POOL_RECYCLE自動回收連接的秒數。這對 MySQL 是必須的,默認 情況下 MySQL 會自動移除閑置 8 小時或者以上的連 接。需要注意的是如果使用 MySQL 的話,Flask-SQLAlchemy 會自動地設置這個值為 2 小時。
SQLALCHEMY_MAX_OVERFLOW控制在連接池達到最大值后可以創建的連接數。當這 些額外的連接回收到連接池后將會被斷開和拋棄。
SQLALCHEMY_TRACK_MODIFICATIONS如果設置成 True (默認情況),Flask-SQLAlchemy 將 會追蹤對象的修改并且發送信號。這需要額外的內 存,如果不必要的可以禁用它。
SQLALCHEMY_COMMIT_ON_TEARDOWN每次請求結束后會自動提交數據庫中的改動

數據庫URI格式

數據庫URI格式
MySQLmysql://username:password@hostname/database
Postgrespostgresql://username:password@hostname/database
SQLite (Unix)sqlite:////python/data/database
SQLite (Windows)sqlite:///c:/db/data/database
Oracleoracle://scott:tiger@127.0.1:1521/sidname

字段說明: username:登錄數據庫的用戶名 password:登錄數據庫的密碼 hostname:服務器主機 ip,可以是本地主機(localhost)也可以是遠程服務器 database:表示要使用的數據庫


2. 模型類定義

字段類型

類型名Python中類型說明
Integerint普通整數,一般是32位
SmallIntegerint小整數
BigIntegerint或long大整數
Floatfloat浮點數
Numericdecimal.Decimal普通整數,一般是32位
Stringstr變長字符串
Textstr變長字符串,對較長或不限長度的字符串做了優化
Unicodeunicode變長Unicode字符串
UnicodeTextunicode變長Unicode字符串,對較長或不限長度的字符串做了優化
Booleanbool布爾值
Datedatetime.date時間
Timedatetime.datetime日期和時間
LargeBinarystr二進制文件

約束條件

約束說明
primary_key主鍵
unique唯一約束,True不允許重復
index索引,如果為True,為這列創建索引,提高查詢效率
nullable空值,如果為True,允許有空值,如果為False,不允許有空值
default默認值

關系類型

關系說明
One To Many(一對多)表示一對多的關系時,在子表類中通過 foreign key (外鍵)引用父表類,在父表類中通過 relationship() 方法來引用了表的類
One To One(一對一)一對一是兩張表之間本質上的雙向關系。只需要在一對多關系基礎上的父表中使用 uselist=False 參數來表示
Many To Many(多對多)多對多關系會在兩個類之間增加一個關聯的表,連個關系表中使用 relationship() 方法中通過 secondary 來引用關聯表,關聯表通過 MetaData 對象與聲明基類關聯,使用ForeignKey 連接接來定位到遠程的表

3. 關系模型

一對多關系
class Father(db.Model):"""創建一個父表模型類"""# 表名__tablename__ = 'father'# id主鍵列,整數類型,自增id = db.Column(db.Integer, primary_key=True)# name,可變長字符串類型name = db.Column(db.String(20))# 關系字段,不是數據庫中真實存在的字段,而是為了方便查詢添加的屬性son = db.relationship('Son', backref='father')
?
class Son(db.Model):"""創建一個子表模型類"""# 表名__tablename__ = 'son'# id主鍵列,整數類型,自增id = db.Column(db.Integer, primary_key=True)# name,可變長字符串類型name = db.Column(db.String(20))# 外鍵,需要指定字段類型,以及關聯那個表的那個字段father_id = db.Column(db.Integer, db.ForeignKey('father.id'))
一對一關系
class Father(db.Model):"""創建一個父類模型類"""# 表名__tablename__ = 'father'# id主鍵列,整數類型,自增id = db.Column(db.Integer, primary_key=True)# name,可變長字符串類型name = db.Column(db.String(20))# 關系字段,不是數據庫中真實存在的字段,而是為了方便查詢添加的屬性son = db.relationship('Son', backref='father', uselist=False)
?
class Son(db.Model):"""創建一個子表模型類"""# 表名__tablename__ = 'son'# id主鍵列,整數類型,自增id = db.Column(db.Integer, primary_key=True)# name,可變長字符串類型name = db.Column(db.String(20))# 外鍵,需要指定字段類型,以及關聯那個表的那個字段father_id = db.Column(db.Integer, db.ForeignKey('father.id'))
多對多關系
# 多對多關系中的兩個表之間的一個關聯表
association_table = db.Table('association', db.metadata,db.Column('author_id', db.Integer, db.ForeignKey('author.id')),db.Column('book_id', db.Integer, db.ForeignKey('book.id'))
)
?
class Author(db.Model):"""創建作者模型類"""# 指定表名,如果沒有指定將默認使用模型類的名稱__tablename__ = 'author'# id 類型是整數 主鍵列id = db.Column(db.Integer, primary_key=True)# name 類型是可變長字符串,唯一name = db.Column(db.String(20), unique=True)# 關聯中間表,不是數據庫中真實存在的字段,而是為了方便查詢添加的屬性book = db.relationship('Book', back_populates='author',secondary=association_table)
?
class Book(db.Model):"""創建書模型類"""# 指定表名,如果不指定將使用模型類名稱作為表名__tablename__ = 'book'id = db.Column(db.Integer, primary_key=True)name = db.Column(db.String(20))# 關聯中間表,不是數據庫中真實存在的字段,而是為了方便查詢添加的屬性author = db.relationship("Author", secondary=association_table,back_populates="book")

4. 數據操作

創建表

if __name__ == '__main__':# 刪除所有表,注意這條是危險命令,會將模型類對應數據庫中的表物理刪除。在實際生產環境下勿用。db.drop_all()# 創建所有表db.create_all()

添加數據

# 創建一個 father對象
f = Father(name='小頭爸爸')
# 將數據添加到會話
db.session.add(f)
# 提交會話數據
db.session.commit()
?
# 創建兩個Son對象,這里利用到father對象id,需要先將Father對象提交才能拿到id
s = Son(name='大頭兒子', father_id=f.id)
s1 = Son(name='中頭兒子', father_id=f.id)
# 同時添加多個數據,接收一個列表做參數
db.session.add_all([s, s1])
# 提交會話數據
db.session.commit()

事務管理

# 創建一個 mother
m = Father(name='圍裙媽媽')
db.session.add(m)
?
# 創建了一個媽媽,但是我們這里是Father類,需要回滾會話
db.session.rollback()

刪除數據

# 刪除演員表中的'吳孟達'
# 將數據查詢出來
actor = Cast.query.filter(Cast.name=='吳孟達').first()
# 刪除對象
db.session.delete(actor)
# 提交到數據庫
db.session.commit()

更新數據

# 第一種方式:查詢后修改
# 先將'梁小龍'查詢出來
actor = Cast.query.filter(Cast.name=='梁小龍').first()
# 將'梁小龍'的名字改成'火云邪神'
actor.name = '火云邪神'
db.session.add(actor)
db.session.commit()
?
# 第二種方式:update方式
# 將'朱茵'修改成'紫霞仙子'
Cast.query.filter(Cast.name=='朱茵').update({'name':'紫霞仙子'})
db.session.commit()

5. 數據查詢

基本查詢方法

方法作用
all()返回數據庫中所有數據,列表形式返回
first()返回查詢的第一個結果,如果未查到,返回None
first_or_404()返回查詢的第一個結果,如果未查到,返回404
get()返回指定主鍵對應的行,如不存在,返回None
get_or_404()返回指定主鍵對應的行,如不存在,返回404
count()返回查詢結果的數量
paginate()返回一個Paginate對象,它包含指定范圍內的結果

查詢過濾器

過濾器說明
filter()把過濾器添加到原查詢上,返回一個新查詢
filter_by()把等值過濾器添加到原查詢上,返回一個新查詢
limit使用指定的值限定原查詢返回的結果
offset()偏移原查詢返回的結果,返回一個新查詢
order_by()根據指定條件對原查詢結果進行排序,返回一個新查詢
group_by()根據指定條件對原查詢結果進行分組,返回一個新查詢

查詢示例

# filter_by 精確匹配查詢,條件只能是本表的字段
Cast.query.filter_by(name='周星馳').all()
?
# first()返回查詢到的第一個對象
Cast.query.first()
?
# all()返回查詢到的所有對象
Cast.query.all()
?
# filter 模糊查詢
Cast.query.filter(Cast.name.startswith('周'))
Cast.query.filter(Cast.name.endswith('龍'))
Cast.query.filter(Cast.name=='周星馳').all()
?
# like 正則模糊匹配
Cast.query.filter(Cast.name.like('周%%'))

邏輯運算查詢

from sqlalchemy import and_, or_, not_
?
# 查詢名字為'周星馳'并且movie_id為2的演員數據
cast.query.filter(and_(cast.name=='周星馳', cast.movie_id==2)).all()
?
# 查詢名字為'周星馳'或者id為2的演員數據
cast.query.filter(or_(cast.name=='周星馳', cast.movie_id==2)).all()
?
# 查詢名字不為'周星馳'的演員
cast.query.filter(not_(cast.name=='周星馳')).all()

關聯查詢

# 查詢名字為朱茵的演員,并且查出她出演的電影
# 查詢出演員'朱茵'
actor = Cast.query.filter(Cast.name=='朱茵').all()
# 直接通過 relationship 中定義的 backref 屬性可以直接查詢出演員對應的電影
movie = actor[0].Movie
# 通過電影直接查詢出所有演員
actors = movie.cast

添加repr方法

def __repr__(self):return "Father: %s" % self.name

6. 完整示例

from flask import Flask
from flask_sqlalchemy import SQLAlchemy
?
app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'mysql://root:mysql@192.168.20.233:3306/py'
app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = True
db = SQLAlchemy(app)
?
class Movie(db.Model):"""創建一個電影模型類"""# 表名__tablename__ = 'movie'# id主鍵列,整數類型,自增id = db.Column(db.Integer, primary_key=True)# name,可變長字符串類型name = db.Column(db.String(20))# 關系字段,不是數據庫中真實存在的字段,而是為了方便查詢添加的屬性cast = db.relationship('Cast', backref='Movie')def __repr__(self):return "Movie: %s " % self.name
?
class Cast(db.Model):"""演員模型類"""# id主鍵列,整數類型,自增id = db.Column(db.Integer, primary_key=True)# name,可變長字符串類型name = db.Column(db.String(20))# 外鍵關聯idmovie_id = db.Column(db.Integer, db.ForeignKey('movie.id'))def __repr__(self):return "Cast: %s " % self.name
?
if __name__ == '__main__':# 刪除所有表db.drop_all()# 創建所有表db.create_all()# 創建電影數據m1 = Movie(name='大話西游')m2 = Movie(name='功夫')db.session.add_all([m1, m2])db.session.commit()# 創建演員數據cast_list = []for i in ['周星馳','朱茵','吳孟達','莫文蔚']:c = Cast(name=i, movie_id=m1.id)cast_list.append(c)for i in ['周星馳','梁小龍','元華']:c = Cast(name=i, movie_id=m2.id)cast_list.append(c)db.session.add_all(cast_list)db.session.commit()

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/pingmian/93725.shtml
繁體地址,請注明出處:http://hk.pswp.cn/pingmian/93725.shtml
英文地址,請注明出處:http://en.pswp.cn/pingmian/93725.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Camera相機人臉識別系列專題分析之十九:MTK ISP6S平臺FDNode原生代碼

【關注我,后續持續新增專題博文,謝謝!!!】 上一篇我們講了: 這一篇我們開始講: 目錄 一、問題背景 二、MTK ISP6S平臺FDNodeImp.cpp 2.1:原生代碼

S32K3 的圖形化配置和EB配置mcal差異

32K3系列的圖形化配置工具&#xff08;如S32 Design Studio, S32DS&#xff09;與EB配置工具&#xff08;基于EB tresos Studio&#xff09;在配置MCAL&#xff08;Microcontroller Abstraction Layer&#xff09;時存在關鍵差異&#xff0c;主要體現在工具環境、配置流程、代碼…

Meta 再次重組人工智能部門

每周跟蹤AI熱點新聞動向和震撼發展 想要探索生成式人工智能的前沿進展嗎&#xff1f;訂閱我們的簡報&#xff0c;深入解析最新的技術突破、實際應用案例和未來的趨勢。與全球數同行一同&#xff0c;從行業內部的深度分析和實用指南中受益。不要錯過這個機會&#xff0c;成為AI領…

在nodejs中 有哪些是 “假值“和怎么寫 “雙重否定”

1.在 Node.js&#xff08;以及 JavaScript&#xff09;中&#xff0c;以下值在布爾上下文&#xff08;例如 if 語句、while 循環條件等&#xff09;中被視為 “假值”&#xff1a;false&#xff1a;布爾類型的 false 值&#xff0c;這是最直接的假值。if (false) {console.log(…

車載軟件架構 --- 贏得汽車軟件開發競賽

我是穿拖鞋的漢子,魔都中堅持長期主義的汽車電子工程師。 老規矩,分享一段喜歡的文字,避免自己成為高知識低文化的工程師: 做到欲望極簡,了解自己的真實欲望,不受外在潮流的影響,不盲從,不跟風。把自己的精力全部用在自己。一是去掉多余,凡事找規律,基礎是誠信;二是…

機器學習總復習

這段時間學習了 KNN&#xff0c;線性回歸&#xff0c;邏輯回歸&#xff0c;貝葉斯&#xff0c;聚類&#xff08;K-means,DBSCAN&#xff09;&#xff0c;決策樹&#xff0c;集成學習&#xff08;隨機森林&#xff0c;XGboost&#xff09;&#xff0c;SVM支持向量機&#xff0c;…

深入解析EventPoller:Disruptor的輪詢式事件處理機制

EventPoller 是什么&#xff1f;EventPoller 是 Disruptor 框架中一種 基于輪詢&#xff08;poll-based&#xff09; 的事件消費機制。它與我們更常見的 BatchEventProcessor&#xff08;基于獨立的消費者線程&#xff09;形成了對比。核心區別在于&#xff1a;BatchEventProce…

K8S-Secret資源對象

目錄 一、Secret概述 二、Secret 類型 kubectl 創建類型 三、Secret 使用 Opaque 類型 Secret 的使用 創建 yaml 一、Secret概述 k8s secrets用于存儲和管理一些敏感數據&#xff0c;比如密碼&#xff0c;token&#xff0c;密鑰等敏感信息。它把 Pod 想要訪問的加密數據…

lua入門以及在Redis中的應用

1.基本語法1.1變量lua的變量有&#xff1a;無效值nil&#xff0c;布爾值boolean&#xff0c;數字number、字符串string、函數function、自定義類型userdata、線程thread、表table&#xff08;key-value結構&#xff09;1.2循環數值循環for i起始值, 結束值 ,間隔值 do---option…

淘寶電商大數據采集【采集內容||采集方法|工具||合規性||應用】

淘寶電商大數據采集是指通過技術手段、工具或平臺&#xff0c;系統性收集淘寶&#xff08;及旗下天貓等&#xff09;生態內的各類數據&#xff0c;用于分析市場趨勢、用戶行為、商品表現、競品動態等&#xff0c;為電商運營、決策提供數據支持。以下從采集內容、工具方法、合規…

ROS2核心模塊

1.創建工作空間先創建工作空間ws01_plumbing&#xff0c;終端下進入工作空間的src目錄&#xff0c;執行如下命令&#xff1a;ros2 pkg create --build-type ament_cmake base_interfaces_demo2.話題通信話題通信是ROS中使用頻率最高的一種通信模式&#xff0c;話題通信是基于發…

Mac 上安裝并使用 frpc(FRP 內網穿透客戶端)指南

一、先裝好 Homebrew&#xff08;macOS 的包管理器&#xff09;打開終端&#xff08;Terminal&#xff09;&#xff0c;先裝命令行開發工具 xcode-select --install彈窗點“安裝”&#xff0c;等待 3~5 分鐘。一鍵安裝 Homebrew /bin/bash -c "$(curl -fsSL https://raw.g…

04_接口與包管理

第4課:接口與包管理 課程目標 深入理解Go語言接口的概念和用法 掌握接口的組合和空接口 學會使用Go Modules進行包管理 理解包的導入和導出規則 1. 接口基礎 1.1 接口定義 // 基本接口定義 type Shape interface {Area() float64Perimeter()

福昕PDF編輯軟件高級版下載與詳細圖文安裝教程!!

軟件下載 【軟件名稱】&#xff1a; 福昕PDF編輯器高級版 【軟件大小】&#xff1a;668.9MBa a【系統要求】&#xff1a;awin10/win11或更高 福昕&#xff0c;軟件下載&#xff08;夸克網盤需手機打開&#xff09;&#xff1a;&#xff1a;福昕丨夸克網盤-資源免費下載 軟件介…

利用無事務方式插入數據庫解決并發插入問題(最小主鍵id思路)

一、背景 由于某業務需要回退某產品數據緩存列表Asset資源&#xff0c;主任務執行后&#xff0c;通過并行執行批量子任務進行數據回退&#xff0c;子任務中會記錄緩存列表Asset和緩存列表行AssetLine數據&#xff0c;并行執行過程會出現緩存列表行AssetLine重復插入問題&#…

如何制作免費的比特幣冷錢包

本文主要從技術上討論冷錢包的操作機制和原理&#xff0c;并不作為投資建議。對于國外的比特幣玩家&#xff0c;或者打算長期囤幣來對抗通貨膨脹的&#xff0c;或者是想短期持有的&#xff0c;那么將比特幣存儲在哪里是一個Common的問題。一般是兩類選擇。第一種選擇是存儲在交…

新手向:Python制作簡易音樂播放器

使用Python構建簡易音樂播放器音樂播放器是現代數字生活中不可或缺的工具&#xff0c;從智能手機到電腦系統&#xff0c;幾乎每個設備都內置了音樂播放功能。對于Python初學者來說&#xff0c;開發一個簡易的音樂播放器是一個很好的實踐項目&#xff0c;既能學習編程基礎&#…

【StarRocks】TabletChecker邏輯

TabletChecker是StarRocks FE里的一個組件,它的主要工作是檢查出所有的處于不健康狀態的tablets。 注意,它的職責就是check(檢查)。 至于tablet修復、均衡等調度工作不是TabletChecker的職責。 相關配置項 // 20秒執行一次check,代碼里是執行runAfterCatalogReady()publi…

低空經濟展 | 優翼仿真攜eVTOL全動飛行模擬器亮相2025深圳eVTOL展

2025深圳eVTOL展將于2025年9月23-25日在深圳坪山燕子湖國際會展中心舉行。展會以“低空經濟?eVTOL?航空應急救援?商載大型無人運輸機”為主題&#xff0c;以 “2天大會3天展覽項目考察飛行表演頒獎盛典項目路演”的多元模式&#xff0c;打造覆蓋 eVTOL全產業鏈的專業化合作平…

AI驅動商業革新:開源大模型與零售精準營銷引領產業升級

在當今數字化浪潮中&#xff0c;AI 正以迅猛之勢滲透至商業的每一處脈絡&#xff0c;掀起一場影響深遠的變革風暴&#xff0c;從根本上改寫著商業運轉的底層邏輯&#xff0c;創造出無數嶄新的商業契機。基礎模型領域&#xff0c;新的突破正在重塑行業格局。Meta 旗下的 LLaMA 3…