-
-
Save Mastersam07/d4c416a490e1f3eb00803ca687a47dea to your computer and use it in GitHub Desktop.
Deep link service with firebase impl
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| import 'dart:async'; | |
| import 'package:flutter/material.dart'; | |
| import '../../core/app_view_model/api_response.dart'; | |
| abstract class DeepLinkService { | |
| @mustCallSuper | |
| void configure(DeepLinkConfiguration config) { | |
| this.config = config; | |
| } | |
| @protected | |
| late DeepLinkConfiguration config; | |
| FutureOr<void> handlePendingLink(); | |
| Future<Uri?> getPendingLink([Uri? uri]); | |
| Future<DataResponse<String>> createDeepLink( | |
| Uri link, { | |
| bool shortenUrl = true, | |
| String? metadataTitle, | |
| String? metadataDescription, | |
| String? metadataImageUrl, | |
| }); | |
| } | |
| class DeepLinkConfiguration { | |
| /// Set a uri prefix you've created on the Firebase console of this project | |
| final String uriPrefixFromFirebase; | |
| // final String linkDataUrl; | |
| /// Link to open instead of opening PlayStore or AppStore to download | |
| /// this app. | |
| /// | |
| /// If ```==null``` dynamic link will launch store if app is not installed. | |
| /// | |
| /// Else dynamic link will launch app page on the device store. | |
| final Uri? fallbackUrl; | |
| /// Package name of this project. | |
| final String packageName; | |
| final String appStoreID; | |
| final String? metadataDefaultTitle; | |
| final String? metadataDefaultDescription; | |
| final String? metadataDefaultImageUrl; | |
| /// Callback to run when handling dynamic link. | |
| /// | |
| /// When data is received, this function is run with the data | |
| final void Function(Uri link) linkHandler; | |
| /// Callback to run when handling dynamic link. | |
| /// | |
| /// When error is generated this function runs with an [errorDescription] | |
| /// String | |
| final void Function(dynamic error)? onError; | |
| const DeepLinkConfiguration({ | |
| required this.uriPrefixFromFirebase, | |
| required this.packageName, | |
| required this.appStoreID, | |
| required this.linkHandler, | |
| // this.linkDataUrl, | |
| this.fallbackUrl, | |
| this.metadataDefaultTitle, | |
| this.metadataDefaultDescription = '', | |
| this.metadataDefaultImageUrl, | |
| this.onError, | |
| }); | |
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| import 'package:firebase_dynamic_links/firebase_dynamic_links.dart'; | |
| import '../../core/app_data/api_response_impl.dart'; | |
| import '../../core/app_data/exceptions.dart'; | |
| import '../../core/app_view_model/api_response.dart'; | |
| import '../../core/app_view_model/failure.dart'; | |
| import 'deep_link_service.dart'; | |
| class FirebaseDynamicLinkService extends DeepLinkService { | |
| void _handleDeepLink(PendingDynamicLinkData data) { | |
| config.linkHandler(data.link); | |
| } | |
| @override | |
| void configure(DeepLinkConfiguration config) { | |
| FirebaseDynamicLinks.instance.onLink.listen( | |
| _handleDeepLink, | |
| onError: ((error, stackTrace) { | |
| final errorCallback = config.onError; | |
| if (errorCallback != null) errorCallback(error); | |
| }), | |
| ); | |
| super.configure(config); | |
| } | |
| @override | |
| Future<void> handlePendingLink() async { | |
| final data = await FirebaseDynamicLinks.instance.getInitialLink(); | |
| if (data != null) _handleDeepLink(data); | |
| } | |
| @override | |
| Future<Uri?> getPendingLink([Uri? uri]) async { | |
| final linkInfo = await FirebaseDynamicLinks.instance.getDynamicLink( | |
| uri ?? Uri.base, | |
| ); | |
| return linkInfo?.link; | |
| } | |
| @override | |
| Future<DataResponse<String>> createDeepLink( | |
| Uri link, { | |
| bool shortenUrl = true, | |
| String? metadataTitle, | |
| String? metadataDescription, | |
| String? metadataImageUrl, | |
| }) async { | |
| final parameters = DynamicLinkParameters( | |
| uriPrefix: config.uriPrefixFromFirebase, | |
| link: link, | |
| navigationInfoParameters: | |
| const NavigationInfoParameters(forcedRedirectEnabled: true), | |
| androidParameters: AndroidParameters( | |
| packageName: config.packageName, | |
| fallbackUrl: config.fallbackUrl, | |
| ), | |
| iosParameters: IOSParameters( | |
| bundleId: config.packageName, | |
| appStoreId: config.appStoreID, | |
| fallbackUrl: config.fallbackUrl, | |
| ), | |
| socialMetaTagParameters: SocialMetaTagParameters( | |
| title: metadataTitle ?? config.metadataDefaultTitle, | |
| description: metadataDescription ?? config.metadataDefaultDescription, | |
| imageUrl: Uri.tryParse( | |
| metadataImageUrl ?? config.metadataDefaultImageUrl ?? ''), | |
| ), | |
| ); | |
| try { | |
| final shortLink = await FirebaseDynamicLinks.instance | |
| .buildShortLink(parameters) | |
| .catchError((_) => throw NetworkException()); | |
| final shareLink = shortLink.shortUrl.toString(); | |
| return ApiResponse(data: shareLink); | |
| } catch (e) { | |
| return ApiResponse( | |
| error: InputFailure(message: 'Could not generate link'), | |
| ); | |
| } | |
| } | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment