旺崽的博客

要么天赋异禀,要么天道酬勤

0%

Flask 开发问题总结

毕设用 Flask 框架开发了一个 Web 网站 ,在开发过程中遇到了很多问题,今天这里做一个总结,避免以后遇到同样的问题。

问题 1

1
2
# 问题代码
Error: While importing 'xxx', an ImportError was raised.

import 语句有误,检查所有 py 文件里的 import 语句,可能的错误一种是包名有误,另一种是引用其他 py 文件里的函数时需要给出完整路径 “项目名.文件夹名.文件名.函数名” 的形式
注意直接使用 flask run 指令运行项目时报错很模糊,可以直接在编译器上运行 app.py 文件,这样可以获得比较清晰的错误提示

问题 2

1
云服务器上用 flask run 命令运行项目后,本地输入云服务器 ip 无法访问

在运行指令后加上主机地址以监听所有外部请求,如下所示:

1
flask run --host=0.0.0.0

问题 3

1
2
# 问题代码
TypeError: Rule.__init__() got an unexpected keyword argument 'method'

视图函数的装饰器里的 method 漏了 s,如下所示:

1
2
# 错误代码
user_bp.route('/settings/data', method=['GET', 'POST'])

问题 4

1
2
# 问题代码
AssertionError: View function mapping is overwriting an existing endpoint function: blog.change_theme

函数名重复,文件中有两个 change_theme 函数

问题 5

1
TypeError: The view function for 'xxx' did not return a valid response. The function either returned None or ended without a return statement.

视图函数中的 return 位置有误,通常是多余的 tab 键导致函数缺少返回语句

问题 6

1
2
3
4
# 错误代码
TypeError: 'bool' object is not callable
# 错误处
if current_user.is_admin()

注意属性和方法的区别,属性不需要加括号,方法需要加括号

问题 7

1
2
# 错误代码
Method Not Allowed.The method is not allowed for the requested URL.

视图函数里只有 post 方法而没有 request 方法,所以直接访问会报错

问题 8

1
2
3
4
5
6
7
# 错误代码
RuntimeError
RuntimeError: Working outside of request context.

This typically means that you attempted to use functionality that needed
an active HTTP request. Consult the documentation on testing for
information about how to avoid this problem.

flask 中的 request 对象只能在视图函数下使用,在其他地方使用会报错

问题 9

1
2
# 错误代码
sqlalchemy.exc.OperationalError: (pymysql.err.OperationalError) (2003, "Can't connect to MySQL server on '@rm-bp1o019zha4dfz18h2o.mysql.rds.aliyuncs.com' ([Errno 11003] getaddrinfo failed)")

因为 password 中有特殊字符导致无法正常连接数据库,一般是密码中含有 @ 字符,修改密码即可解决

问题 10

1
2
# 错误代码
sqlalchemy.exc.InvalidRequestError: Mapper 'mapped class User->user' has no property 'role'

User 模型中未添加 role 属性

问题 11

1
sqlalchemy.exc.InvalidRequestError: Could not locate a property which relates instances of class 'Collect' to instances of class 'User'

Collect 模型和 User 模型之间未建立联系

问题 12

1
2
3
4
5
# 错误代码
SAWarning: Attribute 'BSCV
A' on class <class 'mw.models.Cornea'> appears to be a non-schema 'sqlalchemy.sql.column()' object; this won't be part of the declarative mapping
# 错误处
BSCVA = db.column(db.DECIMAL(2, 1))

column 首字母未大写,导致数据库表声明错误

问题 13

1
2
# 错误代码
AttributeError: 'User' object has no attribute 'translate'

数据提交到数据库时类型有误,如代码所示,此时需要检查提交到 User 表中的所有数据类型是否和声明一致

问题 14

1
2
3
sqlalchemy.exc.NoForeignKeysError: Could not determine join condition between parent/child tables on relationship User.comments - there
are no foreign keys linking these tables. Ensure that referencing columns are associated with a ForeignKey or ForeignKeyConstraint, o
r specify a 'primaryjoin' expression.

关系建立有误,可以将目标表的关系逐一对照查错

问题 15

1
smtplib.SMTPServerDisconnected: please run connect() first

使用 smtp 服务发送邮件时报错,服务涉及的账号密码等都存在 .env 文件中,Flask 会自动读取 .env 文件里的参数,但是该文件必须放在项目根目录下,否则会因无法读取报错

问题 16

1
2
self.port = int(port)
ValueError: invalid literal for int() with base 10: 'None'

SQLAlchemy 把一个引擎的源表示为一个连同设定引擎选项的可选字符串参数的 URI,URI 的形式是:

1
2
3
return self.registry[key]
KeyError: 140581010807680
dialect+driver://username:password@host:port/database

出现上述错误的原因是程序未读出 URI 中的 port,此时要检查环境变量配置文件,如果配置准确无误但还是无法读出配置文件中的 port 值注意以下问题:

在开发时,因为安装了 python-dotenv,使用 flask run 命令启动开发服务器时 Flask 会自动导入存储在 .flaskenv 或 .env 文件中的环境变量。在生产环境下,我们需要使用性能更高的生产服务器,所以不能再使用这个命令启动程序,这时我们需要手动导入环境变量。

我们应该尽可能地提前导入环境变量操作,这样才能确保程序中获取环境变量的代码正常工作,因此最佳的导入位置就是在 wsgi.py 脚本中,其次是程序包构造文件的顶部。在wsgi.py脚本中,我们使用 python-dotenv 提供的 load_dotenv() 函数手动导入 .env 文件中设置的环境变量,如下所示:

1
2
3
4
5
6
7
8
from dotenv import load_dotenv

dotenv_path = os.path.join(os.path.dirname(__file__), '.env')
if os.path.exists(dotenv_path):
load_dotenv(dotenv_path)

from bluelog import create_app
app = create_app('production')

上面这段代码中的顺序非常重要,手动导入环境变量的语句必须在最前面,否则会导致一些环境变量无法读出造成程序崩溃。

问题 17

1
AttributeError: 'int' object has no attribute '_sa_instance_state'

Flask 数据库外键字段在创建对象赋值时,需要赋值对象,而不是该对象的 id 或者其他单独的字段。