这真是个让人头疼的问题。我有一个云函数https.onCall(). 此函数调用是从我的计算机上的密码保护区域触发的
(我正在使用
作为我的服务器)。为了访问这个区域,我强制用户重新输入他们的密码,然后调用FirebaseAuth.getInstance().getCurrentUser().reauthenticate()。
我已经运行了调用https.onCall()云函数没有重新身份验证,并且该函数保留用户的身份验证凭据,因此我将其缩小到重新身份验证时的范围。我错过什么了吗?我需要做些什么来通知云功能身份验证更新吗?
const adminUID = context.auth.uid;
假设是因为我没有得到上面的错误,是因为没有经过身份验证的数据通过上下文进入。
为了更好地阐明发生了什么,我的流程如下:
用户从选项菜单中选择“帐户”。这将启动一个询问用户密码的dialogFragment:
dialogFragment中的按钮代码:
loginButton.setOnClickListener(new View.OnClickListener()
{
public void onClick(View view) {
//execute the loginReAuth method
authenticateSession.loginAdminReAuth(adminEmailAddress, passwordField);
}
});
选择loginButton并输入用户密码后,我们将数据传递给重新验证方法:
重新验证代码:
public void loginAdminReAuth(final String email, TextView passwordText) {
user = FirebaseAuth.getInstance().getCurrentUser();
String password = passwordText.getText().toString();
AuthCredential credential = EmailAuthProvider.getCredential(email, password);
user.reauthenticate(credential)
.addOnCompleteListener(new OnCompleteListener<Void>() {
@Override
public void onComplete(@NonNull Task<Void> task) {
if (task.isSuccessful()) {
Intent intent = new Intent(context, AccountSettingsActivity.class);
context.startActivity(intent);
} else {
// If sign in fails, display a message to the user.
Log.w(TAG, "re-authenticate:failure", task.getException());
Toast.makeText(MyApplication.getContext(), task.getException().getMessage(),
Toast.LENGTH_SHORT).show();
}
}
});
}
当重新验证成功时,我们运行intent并将它们带到AccountSettingsActivity。在这个活动中,我有一个方法:deleteAccount(),它是由alertDialog中的一个按钮点击来触发的,该按钮确认了这个操作。
下面是触发该方法的按钮:
@Override
public void onDialogOKPressed(DialogFragment dialog) {
dialog.dismiss();
if (buttonSelected.equals("accountUpdateButton")) {
//update code here.
}
else if (buttonSelected.equals("accountDeleteButton")) {
deleteAccount(admin);
}
}
调用云函数的方法:
private Task<String> deleteAccount(Admin selectedAdmin) {
Gson gson = new Gson();
String selectedAdminJson;
selectedAdminJson = gson.toJson(selectedAdmin);
Map<String, Object> data = new HashMap<>();
data.put("selectedAdminJson", selectedAdminJson);
return mFunctions
.getHttpsCallable("deleteAccount")
.call(data)
.continueWith(new Continuation<HttpsCallableResult, String>() {
@Override
public String then(@NonNull Task<HttpsCallableResult> task) throws Exception {
// This continuation runs on either success or failure, but if the task
// has failed then getResult() will throw an Exception which will be
// propagated down.
Log.d(TAG, "results from deleteAccount: " + task.getResult().getData().toString());
String result = (String) task.getResult().getData();
return result;
}
});
}
最后,这里是执行请求的cloudfirestore代码。
// The Cloud Functions for Firebase SDK to create Cloud Functions and setup triggers.
import * as functions from 'firebase-functions';
// The Firebase Admin SDK to access the Firebase Realtime Database.
import * as admin from 'firebase-admin'
export = module.exports = functions.https
.onCall(async (data, context) => {
//selectedAdminJson received from app client and converted to admin object class
const selectedAdminJson = data.selectedAdminJson;
const adminUID = context.auth.uid;
//Error checking
// Checking attribute.
if (!(typeof selectedAdminJson === 'string') || selectedAdminJson.length === 0) {
// Throwing an HttpsError so that the client gets the error details.
throw new functions.https.HttpsError('invalid-argument', 'The function must be called with ' +
'one arguments "JSON object" containing selectedAdmin to add.');
}
// Checking that the user is authenticated OR if the calling adminID doesn't match the data received
if (!context.auth) {
// Throwing an HttpsError so that the client gets the error details.
throw new functions.https.HttpsError('failed-precondition', 'The function must be called ' +
'while authenticated.');
}
try {
//METHODS EXECUTED HERE
} catch (error) {
console.error("Error removing adminUserGroup data: ", error);
}
// Returning result to the client.
return {
selectedAdminJson: "selectedAdminJson received and processing."
};
});
再来一块。这是我生活的一部分索引.ts:
import * as admin from 'firebase-admin'
admin.initializeApp();
if (!process.env.FUNCTION_NAME || process.env.FUNCTION_NAME === 'deleteAccount') {
exports.deleteAccount = require('./deleteAccount');
}