I use Firebase to manage authentication within my app. This has a singleton object for the logged in user: Auth.auth().currentUser
In part of my code I check that the uid
of the logged in user is equal to a userId
associated with an object.
I need to test code that uses this check. For this I need to be able to inject a mock Firebase Auth object.
How can I mock the Firebase Auth object? Has anyone had experience with this before?
Copy the contents of: https://github.com/FirebaseExtended/flutterfire/blob/master/packages/firebase_auth/firebase_auth/test/mock.dart into a file, that you can import into your tests, where you need to initialize a Firebase app. Call setupFirebaseAuthMocks(); at the top of your main function for all your tests.
In the Firebase console, open the Authentication section. In the Sign in method tab, enable the Phone provider if you haven't already. Open the Phone numbers for testing accordion menu. Provide the phone number you want to test, for example: +1 650-555-3434.
So I solved this by creating a few protocols for authentication and making User
conform to that protocol:
protocol AuthUser {
var uid: String {get}
var displayName: String? {get}
var email: String? {get}
var photoURL: URL? {get}
}
extension User : AuthUser {}
protocol AuthenticationProtocol {
var currentUser: AuthUser? {get}
}
Then I created an Authentication
class that conforms to the AuthenticationProtocol
:
final class Authentication: AuthenticationProtocol {
static let shared = Authentication()
private let auth = Auth.auth()
var currentUser: AuthUser? {
return auth.currentUser
}
When I have a class that needs authentication in my app I inject a class that conforms to AuthenticationProtocol
like this:
final class MyClass {
private let auth: AuthenticationProtocol
init(auth: AuthenticationProtocol = Authentication.shared) {
self.auth = auth
}
Then I can get the id of the current logged in user by calling auth.currentUser?.uid
.
For tests I then create a mock class that conforms to AuthenticationProtocol
like this:
final class AuthenticationMock : AuthenticationProtocol {
private let uid: String
let currentUser: AuthUser?
init(currentUser: AuthUser) {
self.currentUser = currentUser
}
}
And then I can inject that when I call MyClass(auth: <Authentication Mock Instance>)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With