当前位置: 首页 > news >正文

Flask数据库操作(第四阶段)

目录

  • Flask数据库操作
    • 一、数据库基础
      • 1.1 关系型数据库与非关系型数据库
        • 选择数据库
    • 二、Flask-SQLAlchemy
      • 2.1 安装 Flask-SQLAlchemy
      • 2.2 创建数据库模型
        • 2.2.1 创建 Flask 应用
        • 2.2.2 定义模型
      • 2.3 执行 CRUD 操作
        • 2.3.1 创建(Create)
        • 2.3.2 读取(Read)
        • 2.3.3 更新(Update)
        • 2.3.4 删除(Delete)
      • 2.4 关系建模(一对多、多对多关系)
    • 三、迁移工具
      • 3.1 安装 Flask-Migrate
      • 3.2 配置 Flask-Migrate
      • 3.3 初始化迁移环境
      • 3.4 创建迁移
      • 3.5 应用迁移
      • 3.6 管理数据库版本
    • 四、完整示例
    • 总结

Flask数据库操作

在现代应用程序中,数据库操作是必不可少的。在本教程中,我们将详细学习关系型数据库与非关系型数据库的基本概念,选择合适的数据库,然后使用 Flask 的扩展工具 Flask-SQLAlchemy 和 Flask-Migrate 来执行 CRUD 操作和数据迁移。你将通过丰富的案例来理解数据库模型的创建和关系建模。

一、数据库基础

1.1 关系型数据库与非关系型数据库

关系型数据库(Relational Database)是指以表格形式存储数据的数据库。它使用结构化查询语言(SQL)来操作数据。常见的关系型数据库有 PostgreSQL、MySQL、SQLite 等。

非关系型数据库(NoSQL Database)使用灵活的数据模型,可以是键值对、文档、图形或列存储。常见的 non-SQL 数据库有 MongoDB、Redis、Cassandra 等。

选择数据库

在本教程中,我们将采用 SQLite 作为开发阶段的数据库,因为它轻量级、易于使用且不需要额外的配置。在生产环境中,你可以考虑使用 PostgreSQL 或 MySQL 等成熟的关系型数据库。

二、Flask-SQLAlchemy

2.1 安装 Flask-SQLAlchemy

首先,确保你已安装 Flask-SQLAlchemy:

pip install Flask-SQLAlchemy

2.2 创建数据库模型

我们将创建一个简单的博客应用,具有用户和文章两个模型。

2.2.1 创建 Flask 应用

首先,创建一个新的 Flask 应用并设置数据库连接:

import os
from flask import Flask
from flask_sqlalchemy import SQLAlchemyapp = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///blog.db'
app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = False
db = SQLAlchemy(app)
2.2.2 定义模型

接下来,我们将定义用户和文章的模型。每个用户可以有多篇文章,这意味着我们将实现一对多关系。

class User(db.Model):id = db.Column(db.Integer, primary_key=True)username = db.Column(db.String(80), unique=True, nullable=False)articles = db.relationship('Article', backref='author', lazy=True)class Article(db.Model):id = db.Column(db.Integer, primary_key=True)title = db.Column(db.String(200), nullable=False)content = db.Column(db.Text, nullable=False)user_id = db.Column(db.Integer, db.ForeignKey('user.id'), nullable=False)def __repr__(self):return f'<Article {self.title}>'

在这里,我们为 User 模型和 Article 模型创建了表,其中 articles 是与 User 一对多关系的反向引用,user_id 是外键。

2.3 执行 CRUD 操作

现在,我们来看看如何执行 CRUD 操作。

2.3.1 创建(Create)

创建用户和文章,这是一个简单的示例:

@app.route('/create_user/<username>')
def create_user(username):new_user = User(username=username)db.session.add(new_user)db.session.commit()return f'User {username} created!'@app.route('/create_article/<user_id>/<title>/<content>')
def create_article(user_id, title, content):new_article = Article(title=title, content=content, user_id=user_id)db.session.add(new_article)db.session.commit()return f'Article {title} created!'
2.3.2 读取(Read)

读取用户及其文章的信息:

@app.route('/user/<int:user_id>')
def get_user_articles(user_id):user = User.query.get(user_id)if user:articles = user.articlesreturn f'User: {user.username}, Articles: {", ".join([a.title for a in articles])}'return "User not found"
2.3.3 更新(Update)

更新用户或文章的信息:

@app.route('/update_user/<int:user_id>/<new_username>')
def update_user(user_id, new_username):user = User.query.get(user_id)if user:user.username = new_usernamedb.session.commit()return f'User ID {user_id} updated to {new_username}!'return "User not found"
2.3.4 删除(Delete)

删除用户或文章:

@app.route('/delete_user/<int:user_id>')
def delete_user(user_id):user = User.query.get(user_id)if user:db.session.delete(user)db.session.commit()return f'User ID {user_id} deleted!'return "User not found"

2.4 关系建模(一对多、多对多关系)

我们已经实现了一对多的关系,如果要实现多对多关系,可以创建一个中间表。比如我们可以创建一个 Tag 模型,一个文章可以有多个标签,而一个标签可以应用于多篇文章。

article_tags = db.Table('article_tags',db.Column('article_id', db.Integer, db.ForeignKey('article.id')),db.Column('tag_id', db.Integer, db.ForeignKey('tag.id'))
)class Tag(db.Model):id = db.Column(db.Integer, primary_key=True)name = db.Column(db.String(50), unique=True, nullable=False)articles = db.relationship('Article', secondary=article_tags, lazy='subquery',backref=db.backref('tags', lazy=True))

三、迁移工具

3.1 安装 Flask-Migrate

Flask-Migrate 是用于处理数据库迁移的工具,建立在 Alembic 的基础之上。

安装 Flask-Migrate:

pip install Flask-Migrate

3.2 配置 Flask-Migrate

在 Flask 应用中集成 Flask-Migrate:

from flask_migrate import Migratemigrate = Migrate(app, db)

3.3 初始化迁移环境

首先,初始化迁移环境:

flask db init

3.4 创建迁移

如果你已经定义了模型,可以创建迁移文件:

flask db migrate -m "Initial migration."

3.5 应用迁移

应用迁移到数据库:

flask db upgrade

3.6 管理数据库版本

你可以使用以下命令查看当前的数据库版本:

flask db current

如果你更改了模型,需要更新数据库,可以重复执行 flask db migrateflask db upgrade

四、完整示例

将上述代码整合在一个应用中:

import os
from flask import Flask
from flask_sqlalchemy import SQLAlchemy
from flask_migrate import Migrateapp = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///blog.db'
app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = False
db = SQLAlchemy(app)
migrate = Migrate(app, db)class User(db.Model):# 用户模型id = db.Column(db.Integer, primary_key=True)username = db.Column(db.String(80), unique=True, nullable=False)articles = db.relationship('Article', backref='author', lazy=True)class Article(db.Model):# 文章模型id = db.Column(db.Integer, primary_key=True)title = db.Column(db.String(200), nullable=False)content = db.Column(db.Text, nullable=False)user_id = db.Column(db.Integer, db.ForeignKey('user.id'), nullable=False)class Tag(db.Model):# 标签模型id = db.Column(db.Integer, primary_key=True)name = db.Column(db.String(50), unique=True, nullable=False)articles = db.relationship('Article', secondary=article_tags, lazy='subquery',backref=db.backref('tags', lazy=True))@app.route('/create_user/<username>')
def create_user(username):# 创建用户...@app.route('/create_article/<user_id>/<title>/<content>')
def create_article(user_id, title, content):# 创建文章...# 添加更多的路由和功能if __name__ == '__main__':db.create_all()  # 创建所有表app.run(debug=True)

总结

在本教程中,我们学习了如何使用 Flask-SQLAlchemy 和 Flask-Migrate 进行数据库操作,从基础的模型定义到 CRUD 操作,再到数据库迁移。希望此教程能帮助你更好地理解 Flask 中的数据库操作,为你后续的项目提供帮助。随着你的项目复杂度增加,掌握这些工具和技巧将极大地提升开发效率。

相关文章:

Flask数据库操作(第四阶段)

目录 Flask数据库操作一、数据库基础1.1 关系型数据库与非关系型数据库选择数据库 二、Flask-SQLAlchemy2.1 安装 Flask-SQLAlchemy2.2 创建数据库模型2.2.1 创建 Flask 应用2.2.2 定义模型 2.3 执行 CRUD 操作2.3.1 创建&#xff08;Create&#xff09;2.3.2 读取&#xff08;…...

C语言问答进阶--5、基本表达式和基本语句

赋值表达式 表达式是什么&#xff1f;表达式是由运算符和操作数组成的式子。 如下的代码 #include "iostream.h" int main() { int a1,b2,sum; cout<<(sumab)<<endl; return 0; } 那么如下的呢&#xff1f; #include "iostream.h" int mai…...

uniapp3.0实现图片上传公用组件上传uni-file-picker,uni.uploadFile

用uniapp3.0的写法组合式api&#xff0c;setup形式封装一个图片上传公用组件&#xff0c;要求 1、使用uni-file-picker选择文件 2、uni.uploadFile上传图片 3、要能支持上传接口动态化 4、支持删除如片列表中已上传项 5、可以预览已上传列表图片 6、支持动态化限制图片格…...

Unity游戏开发002

Unity游戏开发002 目录 第一章&#xff1a;Hello&#xff0c;Unity&#xff01;第二章&#xff1a;创建一个游戏体 本文目录 Unity游戏开发 Unity游戏开发002目录本文目录前言一、创建一个游戏体1. 编辑器语言设置2. 创建游戏对象的两种方法3. 快速复制和粘贴物体4. 注意事项…...

MySQL基础练习题38-每位教师所教授的科目种类的数量

目录 题目 准备数据 分析数据 总结 题目 查询每位老师在大学里教授的科目种类的数量。 准备数据 ## 创建库 create database db; use db;## 创建表 Create table If Not Exists Teacher (teacher_id int, subject_id int, dept_id int)## 向表中插入数据 Truncate table…...

haproxy 原理+实战

haproxy 1 haproxy简介1.1 定义1.2 原理讲解1.3 HAProxy的优点&#xff1a; 2. haproxy的基本部署2.1 实验环境2.1.2 haproxy主机配置2.1.3 webserver1配置2.1.4 webserver2配置 3. haproxy的全局配置4. haproxy代理参数5. haporxy的热处理6.haproxy的算法6.1 静态算法6.1.1sta…...

OSPF进阶

一、LSA详解 Type&#xff1a;LSA的类型&#xff08;1、2、3、4、5、7类&#xff09; link-state-ID&#xff1a;链路状态表示符 ADV router&#xff1a;产生该LSA的路由器 age&#xff1a;老化时间 Metric&#xff1a;开销值&#xff0c;一般都为ADV router到达该路由的开…...

SuccBI+低代码文档中心 — 可视化分析(仪表板)(下)

制作仪表板 引入数据模型 仪表板所需模型已经在数据模块中准备好&#xff0c;可以将对应模型表添加到数据模型中。提供了两种添加方式&#xff1a; 在数据栏中点击添加按钮&#xff0c;在弹出框中通过搜索或直接在其所在目录下选中该模型&#xff0c;点击确定。 点击数据按钮…...

前端创作纪念日

机缘 作者也是一名新人大学生&#xff0c;在学习过程中总是get不到专业的知识体系&#xff0c;机缘巧合下了解通过md文档记笔记然后分享在各大博客平台上面&#xff0c;可以吸引社区博客朋友们的关注的鼓励&#xff0c;使得直接创作努力学习的心更加澎湃。 实战项目中的经验分…...

丰收季遇科技之光:北斗卫星导航引领现代农业新篇章

在这个金风送爽、硕果累累的丰收时节&#xff0c;广袤的田野上洋溢着农民们欢声笑语&#xff0c;每一粒饱满的果实都是大自然与辛勤耕耘者的共同馈赠。而在这片希望的田野上&#xff0c;一项科技革命的浪潮正悄然改变着传统农业的面貌——北斗卫星导航系统&#xff0c;正以它精…...

解决windows7虚拟机安装不了vmtools问题

安装不了vmtools问题所在&#xff1a; 没打补丁 ​ 打补丁问题 补丁在本地下载之后无法传到win7虚拟机中 补丁获取 补丁链接如下&#xff1a; https://catalog.s.download.windowsupdate.com/c/msdownload/update/software/secu/2019/09/windows6.1-kb4474419-v3-x64_b5614c6…...

Microsoft VBA Excel VBA函数学习笔记——数据切分熟练度+1

问题场景 123456Stock006006006002002002MarketUSUSUSUSUSUSWeight0.010.1090.2280.2220.2390.72CurrencyEURUSDCNYEURUSDCNYTerm10.0740.0820.0120.0470.0580.067Term20.040.020.010.070.0580.067Term30.0540.0520.0140.0870.0480.017Term40.0710.0840.0020.0170.0180.097………...

uniapp获取swiper中子组件的内容高度

swiper有默认高度,如果不单独设置一个具体高度&#xff0c;swiper后面的内容将不会展示 这里展示的例子是: swiper中放有一个子组件,想要完整展示子组件的内容&#xff0c;swiper就需要获取到子组件的内容高度并设置 <!-- 注意: 这里的单位是 px,不是rpx --><swiper…...

基于计算机爱心小屋公益机构智慧管理(源码+论文+部署讲解等)

博主介绍&#xff1a; ✌我是阿龙&#xff0c;一名专注于Java技术领域的程序员&#xff0c;全网拥有10W粉丝。作为CSDN特邀作者、博客专家、新星计划导师&#xff0c;我在计算机毕业设计开发方面积累了丰富的经验。同时&#xff0c;我也是掘金、华为云、阿里云、InfoQ等平台的优…...

详细学习PyQt5的样式表与界面美化

Pyqt5相关文章: 快速掌握Pyqt5的三种主窗口 快速掌握Pyqt5的2种弹簧 快速掌握Pyqt5的5种布局 快速弄懂Pyqt5的5种项目视图&#xff08;Item View&#xff09; 快速弄懂Pyqt5的4种项目部件&#xff08;Item Widget&#xff09; 快速掌握Pyqt5的6种按钮 快速掌握Pyqt5的10种容器&…...

遥控器android设备键值原理

输入设备触发事件发送数据-》将键值映射到内核中预定义的键值-》上报键值&#xff0c;通过kl文件将按键码转化为标签字符串 内核获取键码&#xff0c;扫描码 按键标签其实对应的也是一个按键码。与kernel上报的按键码不同&#xff0c;按键标签所对应的按键…...

零基础也想学编程?Java零基础入门学习路线 + Java教程已准备好!

本文作者&#xff1a;程序员鱼皮 免费编程学习 - 编程导航网&#xff1a;https://www.code-nav.cn 符号表 可以通过路线知识点前的表情字符&#xff0c;根据自己的实际情况选择学习&#xff1a; &#x1f315; 所有同学必须学习&#xff01;&#xff01;&#xff01;&#x1…...

Avnet ZUBoard 1CG开发板上手—深度学习新选择

Avnet ZUBoard 1CG 开发板上手—深度学习新选择 摘要 本文主要介绍了 Avnet ZUBoard 1CG 开发板的特性、架构、硬件单元等概念&#xff0c;并对如何使用以太网接口和串口连接开发板进行基本介绍&#xff0c;同时辅以两个应用例程演示其功能。 原文链接&#xff1a; FreakSt…...

C/C++复习 day1

C/C复习 day1 文章目录 C/C复习 day1前言一、C语言1.memcpy函数2.memmove函数3.strstr函数4.宏定义的函数5.大小端的介绍以及判断 二、C入门基础1.C是如何支持函数重载的&#xff1f;2.建议用const enum inline去替代宏 三、C类和对象1.类大小的计算2.移动构造和移动赋值1.右值…...

再见Figma!!新的设计,代码协作神器!【送源码】

软件介绍 Penpot 是一款专门用来帮助设计师和开发者更好地合作的软件。它可以让设计师轻松地做出漂亮的设计稿&#xff0c;还能让这些设计稿变成真正的网站或者应用的一部分。这样&#xff0c;设计师和开发者之间就不会因为沟通不畅而产生麻烦了。 Penpot 专为设计师与开发者之…...

376. Wiggle Subsequence

376. Wiggle Subsequence 代码 class Solution { public:int wiggleMaxLength(vector<int>& nums) {int n nums.size();int res 1;int prediff 0;int curdiff 0;for(int i 0;i < n-1;i){curdiff nums[i1] - nums[i];if( (prediff > 0 && curdif…...

Java - Mysql数据类型对应

Mysql数据类型java数据类型备注整型INT/INTEGERint / java.lang.Integer–BIGINTlong/java.lang.Long–––浮点型FLOATfloat/java.lang.FloatDOUBLEdouble/java.lang.Double–DECIMAL/NUMERICjava.math.BigDecimal字符串型CHARjava.lang.String固定长度字符串VARCHARjava.lang…...

【ROS】Nav2源码之nav2_behavior_tree-行为树节点列表

1、行为树节点分类 在 Nav2(Navigation2)的行为树框架中,行为树节点插件按照功能分为 Action(动作节点)、Condition(条件节点)、Control(控制节点) 和 Decorator(装饰节点) 四类。 1.1 动作节点 Action 执行具体的机器人操作或任务,直接与硬件、传感器或外部系统…...

Cinnamon修改面板小工具图标

Cinnamon开始菜单-CSDN博客 设置模块都是做好的&#xff0c;比GNOME简单得多&#xff01; 在 applet.js 里增加 const Settings imports.ui.settings;this.settings new Settings.AppletSettings(this, HTYMenusonichy, instance_id); this.settings.bind(menu-icon, menu…...

Module Federation 和 Native Federation 的比较

前言 Module Federation 是 Webpack 5 引入的微前端架构方案&#xff0c;允许不同独立构建的应用在运行时动态共享模块。 Native Federation 是 Angular 官方基于 Module Federation 理念实现的专为 Angular 优化的微前端方案。 概念解析 Module Federation (模块联邦) Modul…...

DBAPI如何优雅的获取单条数据

API如何优雅的获取单条数据 案例一 对于查询类API&#xff0c;查询的是单条数据&#xff0c;比如根据主键ID查询用户信息&#xff0c;sql如下&#xff1a; select id, name, age from user where id #{id}API默认返回的数据格式是多条的&#xff0c;如下&#xff1a; {&qu…...

【C语言练习】080. 使用C语言实现简单的数据库操作

080. 使用C语言实现简单的数据库操作 080. 使用C语言实现简单的数据库操作使用原生APIODBC接口第三方库ORM框架文件模拟1. 安装SQLite2. 示例代码:使用SQLite创建数据库、表和插入数据3. 编译和运行4. 示例运行输出:5. 注意事项6. 总结080. 使用C语言实现简单的数据库操作 在…...

Java入门学习详细版(一)

大家好&#xff0c;Java 学习是一个系统学习的过程&#xff0c;核心原则就是“理论 实践 坚持”&#xff0c;并且需循序渐进&#xff0c;不可过于着急&#xff0c;本篇文章推出的这份详细入门学习资料将带大家从零基础开始&#xff0c;逐步掌握 Java 的核心概念和编程技能。 …...

【HarmonyOS 5 开发速记】如何获取用户信息(头像/昵称/手机号)

1.获取 authorizationCode&#xff1a; 2.利用 authorizationCode 获取 accessToken&#xff1a;文档中心 3.获取手机&#xff1a;文档中心 4.获取昵称头像&#xff1a;文档中心 首先创建 request 若要获取手机号&#xff0c;scope必填 phone&#xff0c;permissions 必填 …...

【C++特殊工具与技术】优化内存分配(一):C++中的内存分配

目录 一、C 内存的基本概念​ 1.1 内存的物理与逻辑结构​ 1.2 C 程序的内存区域划分​ 二、栈内存分配​ 2.1 栈内存的特点​ 2.2 栈内存分配示例​ 三、堆内存分配​ 3.1 new和delete操作符​ 4.2 内存泄漏与悬空指针问题​ 4.3 new和delete的重载​ 四、智能指针…...