Firebase .orderByChild()。equalTo()。once()。then()当孩子不存在时承诺
我的API /auth/login
端点需要像这样的req.body
:
{ "email": "jacob@gmail.com", "password": "supersecretpassword" }
在端点上,我参考了我的Firebase数据库( https://jacob.firebaseio.com/users
)。 我search数据,当我find一个与req.body.email
相匹配的req.body.email
,我将密码与数据库中存储的密码进行比较。
我遵循这个Firebase博客文章中概述的承诺结构。
router.post('/login', function(req, res) { const ref = db.ref('/users'); ref.orderByChild('email') .equalTo(req.body.email) .once('child_added') .then(function (snapshot) { return snapshot.val(); }) .then(function (usr) { // Do my thing, throw any errors that come up }) .catch(function (err) { // Handle my errors with grace return; }); });
如果在ref
找不到孩子,则该function不会继续(请参阅此答案 )。 我甚至没有得到一个错误。
我的目标是在没有find用户的情况下运行代码(即没有find满足.equalTo(req.body.email)
ref
.equalTo(req.body.email)
),但是如果find用户,则不运行代码。 没有发现任何错误。
我试图在调用数据库的关键点添加return
语句(在我的.then()
promise的末尾),意图在代码运行之后完全脱离端点。 然后我把代码放到数据库的调用之后:
.then(function (usr) { // Do my thing, throw any errors that come up }) .catch(function (err) { // Handle my errors with grace return; }); res.status(401) .json({ error: 'No user found', )}; return; });
但是由于调用是asynchronous的,因此无论对数据库的调用是否成功,都会运行此代码。
如果对数据库的调用没有任何回应, 并且仍然使用Firebase承诺,我该如何应对这种调用?
child_added
事件仅在查询与users
下的至less一个密钥匹配时触发,并且如果有多个匹配,则将多次触发。
您可以改为使用value
事件 – 它只会触发一次,其快照将包含匹配的users
下的所有键,或者如果没有匹配,则其value
将为null
:
router.post('/login', function(req, res) { const ref = db.ref('/users'); ref.orderByChild('email') .equalTo(req.body.email) .once('value') .then(function (snapshot) { var value = snapshot.val(); if (value) { // value is an object containing one or more of the users that matched your email query // choose a user and do something with it } else { res.status(401) .json({ error: 'No user found', )}; } }); });
关于处理错误,你可以连接承诺,并表示error handling,如下所示:
router.post('/login', function(req, res, next) { const ref = db.ref('/users'); ref.orderByChild('email') .equalTo(req.body.email) .once('value') .then(function (snapshot) { ... }) .catch(next); });