Follow instruction from How To Add Firebase To Android to complete Connect your app to Firebase.
Add Firebase AppInvite
Click Add Firebase Invites to your app.
I avoid clicking Accept Changes as it will reformat my project's build.gradle
config file. I prefer to add the following entry manually.
Edit project's build.gradle
.
...
dependencies {
...
compile 'com.google.firebase:firebase-invites:11.0.2'
// if the following is used previously, it is no longer necessary
// compile 'com.google.android.gms:play-services-appinvite:x.x.x
}
apply plugin: 'com.google.gms.google-services'
Edit root level build.gradle
.
buildscript {
...
dependencies {
...
classpath 'com.google.gms:google-services:3.1.0'
}
}
Add the following declaration at activity or fragment.
private static final int REQUEST_INVITE = 1;
Add the following code to the action (e.g. button click) to trigger the invite action. If you want to support iOS version of your app as well, refer to the official documentation.
/*Trigger invite actionurl = "https://www.mydomain.com/_invites/resourceId" - '/_invites/' to indicate this is a invite request - 'resourceId' to indicate which resource to retrieve and display to user */Intent intent = new AppInviteInvitation.IntentBuilder(title) .setMessage(message) .setDeepLink(Uri.parse(url)) .setCustomImage(Uri.parse(imageUrl)) .setCallToActionText(action) .build();startActivityForResult(intent, REQUEST_INVITE);
The above intent will open contact chooser for user to select contacts to invite (email or SMS). After the intent is completed, you will received a callback.
protected void onActivityResult(int requestCode, int resultCode, Intent data) { if (requestCode == REQUEST_INVITE) { if (resultCode == RESULT_OK) { // Get the invitation IDs of all sent messages String[] ids = AppInviteInvitation.getInvitationIds(resultCode, data); for (String id : ids) { Log.d(TAG, "onActivityResult: sent invitation " + id); } Toast.makeText(context, ids.length + " Invites sent", Toast.LENGTH_LONG).show(); } else { // Sending failed or it was canceled, show failure message to the user Toast.makeText(context, "Cancel", Toast.LENGTH_LONG).show(); } }}
The follow code should be put at the main activity to receive invites. When user click on an invite link (email or SMS), it shall trigger the following code (if user has yet to install the app, it will trigger the installation process through Google Play Store then trigger the receive invites code below).
// Check for App Invite invitations and launch deep-link activity if possible.// Requires that an Activity is registered in AndroidManifest.xml to handle// deep-link URLs.FirebaseDynamicLinks.getInstance().getDynamicLink(activityRef.get().getIntent()) .addOnSuccessListener(getActivity(), new OnSuccessListener<PendingDynamicLinkData>() { @Override public void onSuccess(PendingDynamicLinkData data) { if (data == null) { Log.d(TAG, "getInvitation: no data"); return; } // Get the deep link Uri deepLink = data.getLink(); // Extract invite FirebaseAppInvite invite = FirebaseAppInvite.getInvitation(data); if (invite != null) { String invitationId = invite.getInvitationId(); } Log.d(TAG, "deepLink:" + deepLink); if (deepLink != null) { Intent intent = new Intent(Intent.ACTION_VIEW); intent.setPackage(activityRef.get().getPackageName()); intent.setData(deepLink); startActivity(intent); } } }) .addOnFailureListener(getActivity(), new OnFailureListener() { @Override public void onFailure(@NonNull Exception e) { Log.w(TAG, "getDynamicLink:onFailure", e); } });
Note: Though The code above requires a connected GoogleApiClient with AppInvite.API enabled
is mentioned in the official documentation, but such requirement is deprecated since v11.
Create an OpenInviteActivity to handle loading of the invite content.
@Overridepublic void onStart() { super.onStart(); if (getIntent() != null && getIntent().getData() != null) { Uri data = getIntent().getData(); processReferralIntent(data); }}private void processReferralIntent(Uri uri) { Log.d(TAG, "invite:processReferralIntent"); Log.d(TAG, "invite:deepLink="+uri.toString()); // uri.getPath() = /_invites/resourceId String urlName = uri.getPath(); // not sure if first "/" is provided, handle properly just in case if (urlName.startsWith("/")) { urlName = urlName.substring(1); } if (urlName.startsWith("_invite/")){ String resourceId = urlName.replaceFirst("_invite/", ""); Log.d(TAG, "invite:deepLink.resourceId="+resourceId); // use resourceId to load the relevant information, such as retrieve info from database or API }}
Edit AndroidManifest.xml
. OpenInviteActivity is the actual activity which handle the invite request and display the relevant info.
<manifest ...>
...
<application ...>
...
<activity
android:name=".OpenInviteActivity"
...>
<!-- [START deep_link_filter] -->
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<!-- Relevant to the AppInviteInvitation.IntentBuilder -->
<data
android:host="www.mydomain.com"
android:pathPrefix="/_invite/"
android:scheme="http" />
<data
android:host="www.mydomain.com"
android:pathPrefix="/_invite/"
android:scheme="https" />
</intent-filter>
<!-- [END deep_link_filter] -->
</activity>
</application>
</manifest>