Firebase注销()问题(颤振)
我有一个使用firebase的应用程序,我在RootPage中处理登录或登录,然后它会传递到我的第一页,如果我直接注销而没有从第一页转到任何路径,它工作正常,并将我引导到我的RootPage未签名版本,但是如果我从第一页转到任何路径,然后尝试注销它,请给出以下错误:Firebase注销()问题(颤振),firebase,flutter,firebase-authentication,Firebase,Flutter,Firebase Authentication,我有一个使用firebase的应用程序,我在RootPage中处理登录或登录,然后它会传递到我的第一页,如果我直接注销而没有从第一页转到任何路径,它工作正常,并将我引导到我的RootPage未签名版本,但是如果我从第一页转到任何路径,然后尝试注销它,请给出以下错误: D/FirebaseAuth(10720): Notifying id token listeners about a sign-out event. D/FirebaseAuth(10720): Notifying auth st
D/FirebaseAuth(10720): Notifying id token listeners about a sign-out event.
D/FirebaseAuth(10720): Notifying auth state listeners about a sign-out event.
I/flutter (10720): NoSuchMethodError: The method 'call' was called on null.
I/flutter (10720): Receiver: null
I/flutter (10720): Tried calling: call()
我有一个movetohome函数,可以从任何页面返回我的第一页,我认为它缺少了一些东西,我的函数如下
_moveToHome(BuildContext context) {
Route route = MaterialPageRoute(builder: (context) => MyFirstPage(auth: FirebaseAuth.instance,userId: userId,));
Navigator.push(context, route);
}
你可以在我的网页上找到firebase相关的部分
main.dart:
void main() => runApp(new MyApp());
class MyApp extends StatelessWidget {
const MyApp();
@override
Widget build(BuildContext context) {
return DynamicTheme(
defaultBrightness: Brightness.light,
data: (brightness) => ThemeData(
pageTransitionsTheme: PageTransitionsTheme(
builders: {
TargetPlatform.android: CupertinoPageTransitionsBuilder(),
TargetPlatform.iOS: CupertinoPageTransitionsBuilder(),
}
),
primarySwatch: Colors.blueGrey,
accentColor: Colors.blueGrey,
fontFamily: 'AvenirNext',
brightness: brightness,
),
themedWidgetBuilder: (context, theme) {
return MaterialApp(
theme: theme,
home: new RootPage(auth: new Auth()),
routes: <String, WidgetBuilder>{
MyFirstPage.routeName: (context) => new MyFirstPage(auth: new Auth()),
DetailPage.routeName: (context) => new DetailPage(auth: new Auth()),
GenrePage.routeName: (context) => new GenrePage(auth: new Auth())
},
);
});
}
}
void main()=>runApp(新的MyApp());
类MyApp扩展了无状态小部件{
常量MyApp();
@凌驾
小部件构建(构建上下文){
返回动态模式(
defaultBrightness:Brightness.light,
数据:(亮度)=>主题数据(
pageTransitionsTheme:pageTransitionsTheme(
建筑商:{
TargetPlatform.android:CupertinoPageTransitionsBuilder(),
TargetPlatform.iOS:CupertinoPageTransitionsBuilder(),
}
),
原始样本:颜色。蓝灰色,
颜色:颜色。蓝灰色,
fontFamily:“AvenirNext”,
亮度:亮度,
),
主题WidgetBuilder:(上下文,主题){
返回材料PP(
主题:主题,,
主页:新建根页面(auth:new auth()),
路线:{
MyFirstPage.routeName:(上下文)=>新建MyFirstPage(auth:new auth()),
DetailPage.routeName:(上下文)=>new DetailPage(auth:new auth()),
GenrePage.routeName:(上下文)=>新的GenrePage(auth:new auth())
},
);
});
}
}
根页面:
import 'package:flutter/material.dart';
import 'package:randommoviefinal/screens/login_singup_page.dart';
import 'package:randommoviefinal/services/authentication.dart';
import 'package:randommoviefinal/screens/HomePage.dart';
enum AuthStatus {
NOT_DETERMINED,
NOT_LOGGED_IN,
LOGGED_IN,
}
class RootPage extends StatefulWidget {
RootPage({this.auth});
final BaseAuth auth;
@override
State<StatefulWidget> createState() => new _RootPageState();
}
class _RootPageState extends State<RootPage> {
AuthStatus authStatus = AuthStatus.NOT_DETERMINED;
String _userId = "";
@override
void initState() {
super.initState();
widget.auth.getCurrentUser().then((user) {
setState(() {
if (user != null) {
_userId = user?.uid;
}
authStatus =
user?.uid == null ? AuthStatus.NOT_LOGGED_IN : AuthStatus.LOGGED_IN;
});
});
}
void loginCallback() {
widget.auth.getCurrentUser().then((user) {
setState(() {
_userId = user.uid.toString();
});
});
setState(() {
authStatus = AuthStatus.LOGGED_IN;
});
}
void logoutCallback() {
setState(() {
authStatus = AuthStatus.NOT_LOGGED_IN;
_userId = "";
});
}
Widget buildWaitingScreen() {
return Scaffold(
body: Container(
alignment: Alignment.center,
child: CircularProgressIndicator(),
),
);
}
@override
Widget build(BuildContext context) {
switch (authStatus) {
case AuthStatus.NOT_DETERMINED:
return buildWaitingScreen();
break;
case AuthStatus.NOT_LOGGED_IN:
return new LoginSignupPage(
auth: widget.auth,
loginCallback: loginCallback,
);
break;
case AuthStatus.LOGGED_IN:
if (_userId.length > 0 && _userId != null) {
return new MyFirstPage(
userId: _userId,
auth: widget.auth,
logoutCallback: logoutCallback,
);
} else
return buildWaitingScreen();
break;
default:
return buildWaitingScreen();
}
}
}
导入“包装:颤振/材料.省道”;
导入“package:randommoviefinal/screens/login_singup_page.dart”;
导入“package:randommoviefinal/services/authentication.dart”;
导入“package:randommoviefinal/screens/HomePage.dart”;
枚举身份验证状态{
没有决心,
没有登录,
登录,
}
类RootPage扩展了StatefulWidget{
RootPage({this.auth});
最终BaseAuth-auth;
@凌驾
State createState()=>new_RootPageState();
}
类_RootPageState扩展了状态{
AuthStatus AuthStatus=未确定AuthStatus;
字符串_userId=“”;
@凌驾
void initState(){
super.initState();
widget.auth.getCurrentUser().then((用户){
设置状态(){
如果(用户!=null){
_userId=user?.uid;
}
身份=
user?.uid==null?AuthStatus.NOT_LOGGED_IN:AuthStatus.LOGGED_IN;
});
});
}
void loginCallback(){
widget.auth.getCurrentUser().then((用户){
设置状态(){
_userId=user.uid.toString();
});
});
设置状态(){
authStatus=authStatus.LOGGED\u登录;
});
}
void logoutCallback(){
设置状态(){
authStatus=authStatus.NOT\u LOGGED\u IN;
_userId=“”;
});
}
Widget BuildingWaitingScreen(){
返回脚手架(
主体:容器(
对齐:对齐.center,
子对象:CircularProgressIndicator(),
),
);
}
@凌驾
小部件构建(构建上下文){
交换机(身份验证状态){
案例身份。未确定:
返回BuildingWaitingScreen();
打破
案例身份验证状态。未登录:
返回新的LoginSignupPage(
auth:widget.auth,
loginCallback:loginCallback,
);
打破
案例AuthStatus.LOGGED\u登录:
如果(_userId.length>0&&u userId!=null){
返回新的MyFirstPage(
userId:\u userId,
auth:widget.auth,
logoutCallback:logoutCallback,
);
}否则
返回BuildingWaitingScreen();
打破
违约:
返回BuildingWaitingScreen();
}
}
}
我的首页:
class MyFirstPage extends StatefulWidget {
MyFirstPage({Key key, this.auth, this.userId, this.logoutCallback})
: super(key: key);
final auth;
final VoidCallback logoutCallback;
final String userId;
static String routeName = "/MyFirstPage";
@override
_MyFirstPageState createState() => new _MyFirstPageState();
}
class _MyFirstPageState extends State<MyFirstPage> {
String userId;
List<Movies> _moviesList;
final FirebaseDatabase _database = FirebaseDatabase.instance;
final GlobalKey<FormState> formKey = GlobalKey<FormState>();
Query _moviesQuery;
StreamSubscription<Event> _onMoviesAddedSubscription;
StreamSubscription<Event> _onMoviesChangedSubscription;
@override
void initState() {
// TODO: implement initState
super.initState();
_moviesList = new List();
_moviesQuery = _database
.reference()
.child("movies")
.orderByChild("userId")
.equalTo(widget.userId);
_onMoviesAddedSubscription = _moviesQuery.onChildAdded.listen(onEntryAdded);
_onMoviesChangedSubscription =
_moviesQuery.onChildChanged.listen(onEntryChanged);
}
void dispose() {
_onMoviesAddedSubscription.cancel();
_onMoviesChangedSubscription.cancel();
super.dispose();
}
onEntryChanged(Event event) {
var oldEntry = _moviesList.singleWhere((entry) {
return entry.key == event.snapshot.key;
});
setState(() {
_moviesList[_moviesList.indexOf(oldEntry)] =
Movies.fromSnapshot(event.snapshot);
});
}
onEntryAdded(Event event) {
setState(() {
_moviesList.add(Movies.fromSnapshot(event.snapshot));
});
}
signOut() async {
try {
await widget.auth.signOut();
widget.logoutCallback();
} catch (e) {
print(e);
}
}
updateMovies(Movies movies) {
//Toggle completed
movies.watched = !movies.watched;
if (movies != null) {
_database.reference().child("movies").child(movies.key).set(movies.toJson());
}
}
deleteMovies(String moviesId, int index) {
_database.reference().child("movies").child(moviesId).remove().then((_) {
print("Delete $moviesId successful");
setState(() {
_moviesList.removeAt(index);
});
});
}
类MyFirstPage扩展StatefulWidget{
MyFirstPage({Key Key,this.auth,this.userId,this.logoutCallback})
:super(key:key);
最终授权;
最终作废回拨注销回拨;
最终字符串用户标识;
静态字符串routeName=“/MyFirstPage”;
@凌驾
_MyFirstPageState createState()=>new_MyFirstPageState();
}
类_MyFirstPageState扩展状态{
字符串用户标识;
列表(电影列表),;
final FirebaseDatabase _database=FirebaseDatabase.instance;
最终GlobalKey formKey=GlobalKey();
查询-电影查询;
流式订阅-移动附加订阅;
StreamSubscription _onMovieChangedSubscription;
@凌驾
void initState(){
//TODO:实现initState
super.initState();
_moviesList=新列表();
_moviesQuery=\u数据库
.reference()
.儿童(“电影”)
.orderByChild(“用户ID”)
.equalTo(widget.userId);
_onMoviesAddedSubscription=\u moviesQuery.onChildAdded.listen(onEntryAdded);
_OnMovieChangedSubscription=
_moviesQuery.onChildChanged.listen(onEntryChanged);
}
无效处置(){
_onMoviesAddedSubscription.cancel();
_onMovieChangedSubscription.cancel();
super.dispose();
}
onEntryChanged(事件){
var oldEntry=_moviesList.singleWhere((条目){
return entry.key==event.snapshot.key;
});
设置状态(){
_电影列表[_moviesList.indexOf(旧条目)]=
Movies.fromSnapshot(event.snapshot);
});
}
onEntryAdded(事件){
设置状态(){
_添加(Movies.fromsapshot(event.snapshot));
});
}
signOut()异步{
试一试{
等待widget.auth.signOut();
logoutCallback();
}捕获(e){
印刷品(e);
}
}
更新视频(电影){
//切换完成
movies.waved=!movies.waved;
如果(电影!=null){
_database.reference().child(“movies”).child(movies.key).set(movies.toJson());
}
}
deleteMovies(字符串moviesId,int索引)
class DetailPage extends StatefulWidget {
MovieDetailPage({Key key, this.title, this.auth, this.userId})
: super(key: key);
final auth;
final String userId;
static String routeName = "/MyHomePage";
final String title;
@override
_DetailPageState createState() => _DetailPageState();}
class _DetailPageState extends State<MovieDetailPage> {
String userId;
final FirebaseDatabase _database = FirebaseDatabase.instance;
final GlobalKey<FormState> formKey = GlobalKey<FormState>();
StreamSubscription<Event> _onMoviesAddedSubscription;
StreamSubscription<Event> _onMoviesChangedSubscription;
Query _moviesQuery;
List<Movies> _moviesList;
_moveToHome(BuildContext context) {
Route route = MaterialPageRoute(builder: (context) => MyFirstPage(auth: FirebaseAuth.instance,userId: userId,));
Navigator.push(context, route);}
@override
void initState() {
// TODO: implement initState
super.initState();
_moviesList = new List();
_moviesQuery = _database
.reference()
.child("movies")
.orderByChild("userId")
.equalTo(widget.userId);
_onMoviesAddedSubscription = _moviesQuery.onChildAdded.listen(onEntryAdded);
_onMoviesChangedSubscription =
_moviesQuery.onChildChanged.listen(onEntryChanged);
widget.auth.getCurrentUser().then((user) {
if (user != null) {
userId = user?.uid;
}});
}
void dispose() {
_onMoviesAddedSubscription.cancel();
_onMoviesChangedSubscription.cancel();
super.dispose();
}
onEntryChanged(Event event) {
var oldEntry = _moviesList.singleWhere((entry) {
return entry.key == event.snapshot.key;
});
setState(() {
_moviesList[_moviesList.indexOf(oldEntry)] =
Movies.fromSnapshot(event.snapshot);
});
}
onEntryAdded(Event event) {
setState(() {
_moviesList.add(Movies.fromSnapshot(event.snapshot));
});
}
updateMovies(Movies movies) {
//Toggle completed
movies.watched = !movies.watched;
if (movies != null) {
_database.reference().child("movies").child(movies.key).set(movies.toJson());
}
}
deleteMovies(String moviesId, int index) {
_database.reference().child("movies").child(moviesId).remove().then((_) {
print("Delete $moviesId successful");
setState(() {
_moviesList.removeAt(index);
});
});
}
...
IconButton(
icon: Icon(Icons.home),
iconSize: 35,
onPressed: () {
_moveToHome(context);
},
),
...
import 'dart:async';
import 'package:firebase_auth/firebase_auth.dart';
abstract class BaseAuth {
Future<String> signIn(String email, String password);
Future<String> signUp(String email, String password);
Future<FirebaseUser> getCurrentUser();
Future<void> sendEmailVerification();
Future<void> signOut();
Future<bool> isEmailVerified();
}
class Auth implements BaseAuth {
final FirebaseAuth _firebaseAuth = FirebaseAuth.instance;
Future<String> signIn(String email, String password) async {
AuthResult result = await _firebaseAuth.signInWithEmailAndPassword(
email: email, password: password);
FirebaseUser user = result.user;
return user.uid;
}
Future<String> signUp(String email, String password) async {
AuthResult result = await _firebaseAuth.createUserWithEmailAndPassword(
email: email, password: password);
FirebaseUser user = result.user;
return user.uid;
}
Future<FirebaseUser> getCurrentUser() async {
FirebaseUser user = await _firebaseAuth.currentUser();
return user;
}
Future<void> signOut() async {
return _firebaseAuth.signOut();
}
Future<void> sendEmailVerification() async {
FirebaseUser user = await _firebaseAuth.currentUser();
user.sendEmailVerification();
}
Future<bool> isEmailVerified() async {
FirebaseUser user = await _firebaseAuth.currentUser();
return user.isEmailVerified;
}
}
final FirebaseAuth _firebaseAuth = FirebaseAuth.instance;
class Auth implements BaseAuth {
//Rest of class