我正在使用flask应用(使用flask-login和PyMongo),我的用户有这个类,还有这个加载器(这是完整的user.py文件)。
from werkzeug.security import check_password_hash
from app import login, mongo
class User():
def __init__(self, username, first_name, last_name, email, _id, is_admin):
self.username = username
self.first_name = first_name
self.last_name = last_name
self.email = email
self._id = _id
self.is_admin = is_admin
def is_authenticated(self):
return True
def is_active(self):
return True
def is_anonymous(self):
return False
def get_id(self):
return self.username
@staticmethod
def check_password(password_hash, password):
return check_password_hash(password_hash, password)
@login.user_loader
def load_user(username):
user = mongo.db.users.find_one({'username': username})
if not user:
return None
return User(user['username'], user['first_name'], user['last_name'], user['email'], user['_id'], user['is_admin'])
注册,登录和注销路径工作正常,但我的update_account路径有问题,它更新了用户信息。我可以更新数据库中的所有字段,但当我更新时 ‘username’
我被注销了,或者说是注销后被重定向到了 /login?next=%2Faccount HTTP
(尽管字段得到正确的更新).我意识到我的类有问题,所以我试着修改它的结尾和加载器,通过用 _id
,如。
class User():
def __init__(self, username, first_name, last_name, email, _id, is_admin):
self.username = username
self.first_name = first_name
self.last_name = last_name
self.email = email
self._id = _id
self.is_admin = is_admin
def is_authenticated(self):
return True
def is_active(self):
return True
def is_anonymous(self):
return False
def get_id(self):
return self._id
@login.user_loader
def load_user(_id):
user = mongo.db.users.find_one({'_id': _id})
if not user:
return None
return User(user['username'], user['first_name'], user['last_name'], user['email'], user['_id'] , user['is_admin'])
但是,我得到一个 TypeError: Object of type ObjectId is not JSON serializable
.
额外的信息。当我更新任何其他字段时,我在我的控制台中正确地得到:
127.0.0.1 - -"POST /account HTTP/1.1" 302 -
127.0.0.1 - -"GET /account HTTP/1.1" 200 -
但是更新用户名会引起:
127.0.0.1 - -"POST /account HTTP/1.1" 302 -
127.0.0.1 - -"GET /account HTTP/1.1" 302 -
127.0.0.1 - -"GET /login?next=%2Faccount HTTP/1.1" 200 -
如果能帮上忙的话,这是我编辑账户的途径。 In case it helps, this is my route to edit the account:
@app.route('/account', methods=['POST', 'GET'])
@login_required
def account():
form = UpdateAccountForm()
updated_user = {'username': form.username.data, 'first_name': form.first_name.data,
'last_name': form.last_name.data, 'email': form.email.data}
if form.validate_on_submit():
mongo.db.users.update_one(
{'_id': current_user._id}, {"$set": updated_user})
flash('Updated!', 'info')
return redirect(url_for('account'))
elif request.method == 'GET':
form.username.data = current_user.username
form.first_name.data = current_user.first_name
form.last_name.data = current_user.last_name
form.email.data = current_user.email
return render_template('account.html', title="About", form=form)
你们谁能帮我解决这个问题?谢谢你!
这个 _id
字段在pymongo中被表示为ObjectId实例(从 bson
库)。)
要么从违规函数中删除这个字段,要么先把它转换为字符串。
我在更新的时候,在同一条路由内,立即登录用户,就解决了这个问题。所以有点后端技巧,但用户是察觉不到的。