flutter mockito:如何调用存储库函数进行测试
Posted
技术标签:
【中文标题】flutter mockito:如何调用存储库函数进行测试【英文标题】:flutter mockito: How to call repository function for testing 【发布时间】:2021-11-11 02:01:01 【问题描述】:开发中没有问题。此问题正在测试中。
备选方案 1
void main() async
SoldRepository repository;
FirebaseFirestore _firestore;
final sold = Sold(
buyerDisplayName: UserDisplayNameSold("Saugat Thapa"),
buyerEmail: EmailAddressBought("saugat26@gmail.com", true),
buyerPhotoUrl: UserPhotoUrlSold(
" https://s3.amazonaws.com/uifaces/faces/twitter/salvafc/128.jpg"),
buyerUserId: UserIdSold("haSW0s5MxOOENWnc5T1cLinekj2"),
id: UniqueId(),
quotations: List3Sold(KtList.of(
Quotation(
id: UniqueId(),
measuremntUnit: QuotationUnit("Kilogram"),
quantity: QuotationQuantity(10),
rate: QuotationRate(12),
title: QuotationTitle("Onion"),
index: QuotationIndex(8),
isSelected: QuotationSelected(false)),
)),
sellerDisplayName: UserDisplayNameSold("riwat rai"),
sellerEmail: EmailAddressSold("riwatj@gmail.com"),
sellerPhotoUrl: UserPhotoUrlSold(
" https://s3.amazonaws.com/uifaces/faces/twitter/salvafc/128.jpg"),
sellerUserId: UserIdSold("DULkECyxWzfBosXXBbOMpfnij1"),
total: SoldTotalHere(10));
// User sellerUserDetail;
final auth = MockFirebaseAuth();
final googleSignIn = MockGoogleSignIn();
u.User sellerUserDetail;
sellerUserDetail = u.User(
email: "ku1438693@gmail.com",
photoUrl:
"https://lh6.googleusercontent.com/-5HXS8qkwKnw/AAAAAAAAAAI/AAAAAAAAAAA/AAKWJJMiRHRadk3nDhlaLa-sU0_fsPrHhQ/photo.jpg",
id: UniqueId(),
displayName: "Lila Kunwar");
setUp(() async
repository = SoldRepository(_firestore);
);
test('creates bill in collection sold', () async
//arrange
//act
repository.createTest(sold, sellerUserDetail);
// assert
expect(result, right(sold));
);
调用 repository.createTest(sold, sellerUserDetail)
并出现错误。
我预计FirebaseFirestore _firestore;
会出现问题,但我该如何克服这个问题。
abstract class ISoldRepository
Future<Either<SoldFailure, Unit>> createTest(
Sold sold, User sellerUserDetail);
/* import 'dart:ui';
import 'package:cloud_firestore/cloud_firestore.dart';
import 'package:freezed_annotation/freezed_annotation.dart';
import 'package:mobile_shamagri_bloc/domain/core/value_objects.dart'; */
import 'dart:developer';
import 'package:cloud_firestore/cloud_firestore.dart';
// import 'package:flutter/services.dart';
import 'package:injectable/injectable.dart';
import 'package:dartz/dartz.dart';
import 'package:kt_dart/kt.dart';
import 'package:logger/logger.dart';
import 'package:mobile_shamagri_bloc/domain/auth/i_auth_facade.dart';
import 'package:mobile_shamagri_bloc/domain/auth/user.dart';
import 'package:mobile_shamagri_bloc/domain/core/errors.dart';
import 'package:mobile_shamagri_bloc/domain/sold/i_sold_repository.dart';
import 'package:mobile_shamagri_bloc/domain/sold/sold_failure.dart';
import 'package:mobile_shamagri_bloc/domain/sold/sold.dart';
import 'package:mobile_shamagri_bloc/domain/sold_not_form/sold_not_form.dart';
import 'package:mobile_shamagri_bloc/domain/sold_not_form/sold_not_form_failure.dart';
import 'package:mobile_shamagri_bloc/infrastructure/core/firestore_helpers.dart';
import 'package:mobile_shamagri_bloc/infrastructure/sold_reso/sold_dtos.dart';
import 'package:mobile_shamagri_bloc/injection.dart';
// import 'package:mobile_shamagri_bloc/infrastructure/sold_reso/sold_dtos.dart';
import 'package:rxdart/rxdart.dart';
@LazySingleton(as: ISoldRepository)
class SoldRepository implements ISoldRepository
final FirebaseFirestore _firestore;
SoldRepository(this._firestore);
String buyerUserID;
String buyerDisplayName;
String buyerPhotoUrl;
Future<Either<SoldFailure, Unit>> createTest(
Sold sold, User sellerUserDetail) async
try
final soldDto = SoldDto.fromDomain(
sold,
sellerUserDetail,
sold.buyerUserId.getOrCrash(),
sold.buyerDisplayName.getOrCrash(),
sold.buyerPhotoUrl.getOrCrash());
await _firestore
.collection("sold")// here is the error
.doc(soldDto.soldId)
.collection("invoice")
.doc()
.set(soldDto.toJson());
return right(unit);
on FirebaseException catch (e)
if (e.message.contains('PERMISSION_DENIED'))
return left(const SoldFailure.insufficientPermission());
else
var logger = Logger();
logger.wtf("unexpected error " + e.toString());
return left(const SoldFailure.unexpected());
我怎么不能在 null 上调用方法 'collection'?
creates bill in collection sold [E]
NoSuchMethodError: The method 'collection' was called on null.
Receiver: null
Tried calling: collection("sold")
dart:core Object.noSuchMethod
package:mobile_shamagri_bloc/infrastructure/sold_reso/sold_repository.dart 228:12 SoldRepository.createTest
test\features\sold\presentation\bloc\create.dart 85:21 main.<fn>
test\features\sold\presentation\bloc\create.dart 83:43 main.<fn>
===== asynchronous gap ===========================
dart:async _completeOnAsyncError
package:mobile_shamagri_bloc/infrastructure/sold_reso/sold_repository.dart SoldRepository.createTest
test\features\sold\presentation\bloc\create.dart 85:21 main.<fn>
test\features\sold\presentation\bloc\create.dart 83:43 main.<fn>
NoSuchMethodError: The method 'collection' was called on null.
Receiver: null
Tried calling: collection("sold")
dart:core Object.noSuchMethod
package:mobile_shamagri_bloc/infrastructure/sold_reso/sold_repository.dart 228:12 SoldRepository.createTest
test\features\sold\presentation\bloc\create.dart 88:31 main.<fn>
test\features\sold\presentation\bloc\create.dart 83:43 main.<fn>
===== asynchronous gap ===========================
dart:async _completeOnAsyncError
package:mobile_shamagri_bloc/infrastructure/sold_reso/sold_repository.dart SoldRepository.createTest
test\features\sold\presentation\bloc\create.dart 88:31 main.<fn>
test\features\sold\presentation\bloc\create.dart 83:43 main.<fn>
Expected: Right<dynamic, Sold>:<Right(Sold(id: Value(Right(6f567c00-16a0-11ec-b349-256f5961cbea)), total: Value(Right(10)), buyerEmail: Value(Right(saugat26@gmail.com)), quotations: Value(Right([Quotation(id: Value(Right(6f56ca20-16a0-11ec-8c22-5db758776962)), title: Value(Right(Onion)), measuremntUnit: Value(Right(Kilogram)), rate: Value(Right(12)), quantity: Value(Right(10)), isSelected: Value(Right(false)), index: Value(Right(8)))])), sellerEmail: Value(Right(rrj@gmail.com)), sellerUserId: Value(Right(DULkEuiCyzfBosXXBbOMpfnij1)), buyerUserId: Value(Right(hanSW0s5MxOONWnc5T1cLinekj2)), sellerDisplayName: Value(Right(riwat rai)), buyerDisplayName: Value(Right(Saugat Thapa)), sellerPhotoUrl: Value(Right( https://s3.amazonaws.com/uifaces/faces/twitter/salvafc/128.jpg)), buyerPhotoUrl: Value(Right( https://s3.amazonaws.com/uifaces/faces/twitter/salvafc/128.jpg))))>
Actual: <Instance of 'Future<Either<SoldFailure, Unit>>'>
package:test_api expect
package:flutter_test/src/widget_tester.dart 428:3 expect
test\features\sold\presentation\bloc\create.dart 90:5 main.<fn>
test\features\sold\presentation\bloc\create.dart 83:43 main.<fn>
备选方案 2
void main() async
SoldRepository repository;
FirebaseFirestore _firestore;
final sold = Sold(
buyerDisplayName: UserDisplayNameSold("Saugat Thapa"),
buyerEmail: EmailAddressBought("saugat26@gmail.com", true),
buyerPhotoUrl: UserPhotoUrlSold(
" https://s3.amazonaws.com/uifaces/faces/twitter/salvafc/128.jpg"),
buyerUserId: UserIdSold("hanSW0s5MxOOENWnc5T1cLinekj2"),
id: UniqueId(),
quotations: List3Sold(KtList.of(
Quotation(
id: UniqueId(),
measuremntUnit: QuotationUnit("Kilogram"),
quantity: QuotationQuantity(10),
rate: QuotationRate(12),
title: QuotationTitle("Onion"),
index: QuotationIndex(8),
isSelected: QuotationSelected(false)),
)),
sellerDisplayName: UserDisplayNameSold("riwat rai"),
sellerEmail: EmailAddressSold("riwatj@gmail.com"),
sellerPhotoUrl: UserPhotoUrlSold(
" https://s3.amazonaws.com/uifaces/faces/twitter/salvafc/128.jpg"),
sellerUserId: UserIdSold("DULkEuiCyxWzfBosXXBbOMpfnij1"),
total: SoldTotalHere(10));
// User sellerUserDetail;
final auth = MockFirebaseAuth();
final googleSignIn = MockGoogleSignIn();
u.User sellerUserDetail;
sellerUserDetail = u.User(
email: "ku143863@gmail.com",
photoUrl:
"https://lh6.googleusercontent.com/-5HXS8qkwKnw/AAAAAAAAAAI/AAAAAAAAAAA/AAKWJJMiRHRadk3nDhlaLa-sU0_fsPrHhQ/photo.jpg",
id: UniqueId(),
displayName: "Lila Kunwar");
setUp(() async
repository = SoldRepository(_firestore);
);
test('creates bill in collection sold', () async
//arrange
//act
ISoldRepository repository;
final globalResult = repository.createTest(sold, sellerUserDetail);
expect(globalResult, d.right(sold));
);
00:02 +0 -1: creates bill in collection sold [E]
NoSuchMethodError: The method 'createTest' was called on null.
Receiver: null
Tried calling: createTest(Instance of '_$_Sold', Instance of '_$_User')
dart:core Object.noSuchMethod
test\features\sold\presentation\bloc\create.dart 88:37 main.<fn>
test\features\sold\presentation\bloc\create.dart 83:43 main.<fn>
【问题讨论】:
【参考方案1】:在 Alternative 1
中,您在 null 上调用 .collection
,因为
_firestore
变量只是声明了但没有赋值。
在Alternative 2
中,您在null 上调用.createTest
,因为调用.createTest
的repository
变量是在下面的test
方法中声明的变量,并且它为null,因为它没有被分配任何值。
test('creates bill in collection sold', () async
ISoldRepository repository;
final globalResult = repository.createTest(sold, sellerUserDetail);
expect(globalResult, d.right(sold));
);
您可以使用 mockito 模拟 FirebaseFirestore
并将其分配给您的 _firestore
变量。查看article,了解如何使用 Firestore 编写单元测试。
【讨论】:
以上是关于flutter mockito:如何调用存储库函数进行测试的主要内容,如果未能解决你的问题,请参考以下文章
使用 Mockito 的 FutureBuilder 快照数据为空 - Flutter