platform :ios,'12.0'target 'MyAwesomeApp'do pod 'OkHi','~> 1.9.9'end
4. Run the following command:
podinstall
5. Don’t forget to use the .xcworkspace file to open your project in Xcode, instead of the .xcodeproj file, from here on out.
Address verification requires AlwaysAndWhenInUseUsage location to verify the user's address
To satisfy these requirements add the following to your info.plist file and provide a useful description as to why your application needs access to the user's location.
<key>NSLocationWhenInUseUsageDescription</key>
<string>String that explains why you need this permission</string>
<key>NSLocationAlwaysUsageDescription</key>
<string>String that explains why you need this permission</string>
<key>NSLocationAlwaysAndWhenInUseUsageDescription</key>
<string>String that explains why you need this permission</string>
Background Modes Capabilities
OkVerify obtains and transmits verification signals in the background, to enable this make sure to add "Location updates" and "Background fetch" at Background Modes under Signing & Capabilities of your target
Authentication
In your AppDelegate.swift file configure the OkHi Auth object with your client key and branch ID. Sign up here. Make sure to also setup your app's context with meta data about your application
In your SceneDelegate.swift file call the onStart method in the sceneDidBecomeActive method
importOkHiclassSceneDelegate:UIResponder, UIWindowSceneDelegate {//... other class methodsfuncsceneDidBecomeActive(_scene: UIScene) {// Called when the scene has moved from an inactive state to an active state.// Use this method to restart any tasks that were paused (or not yet started) when the scene was inactive. OkVerify.onStart() }}
The OkVerify.onStart() should be called each time your user opens the app
2. Create and verify an address (Client-side)
2.1 Digital Verification (Default)
Add a button to your UI that would enable launching of OkHi address collection tool.
We recommend that you persist the verification state of the user in your app local storage. This state can be used to ensure that a user may only verify a predefined number of addresses. Usually one address for most use cases.
For OkVerify to work correctly "Always" Location permission needs to be granted by your users. The library provides the requestBackgroundLocationPermission method that enables you to manage these permission requirements as shown below.
Always use your phone number or a phone number you own during testing as a message will be sent to this number after an address is created.
importUIKitimportOkHiimportCoreLocationclassViewController:UIViewController {privatelet okCollect =OkCollect()privatelet okVerify =OkVerify()overridefuncviewDidLoad() { super.viewDidLoad()// Do any additional setup after loading the view. okCollect.delegate = self okVerify.delegate = self }@IBActionfunconButtonPress(_sender: UIButton) {if okVerify.isLocationServicesEnabled() {if okVerify.isBackgroundLocationPermissionGranted() {startAddressCreation() } else {// TODO: Show location permissions primer here okVerify.requestBackgroundLocationPermission() } } }funcstartAddressCreation() {let okHiTheme =OkHiTheme() .with(logoUrl:"https://cdn.okhi.co/icon.png") .with(appBarColor:"#ba0c2f") .with(appName:"OkHi")let okHiConfig =OkHiConfig().enableStreetView().enableAppBar()guardlet vc = okCollect.viewController( with: OkHiUser(phoneNumber: "+234xxxxx") // It is important to provide your actual phone number, as a message will be sent to this number
.with(firstName:"Gift") .with(lastName:"Moore") .with(email:"giftmoore@okhi.com"), okHiTheme: okHiTheme, okHiConfig: okHiConfig)else {return } self.present(vc, animated:true, completion:nil) }funcstartAddressVerification(user: OkHiUser, location: OkHiLocation) { okVerify.startAddressVerification(user: user, location: location)// TODO persist address verification state in app local database store }}extensionViewController:OkCollectDelegate {funccollect(didEncounterErrorerror: OkHiError) {// handle errordebugPrint(error) }funccollect(didSelectAddressuser: OkHiUser, location: OkHiLocation) {startAddressVerification(user: user, location: location) }}extensionViewController:OkVerifyDelegate { func verify(_ okverify: OkVerify, didChangeLocationPermissionStatus requestType: OkVerifyLocationPermissionRequestType, status: Bool) {
if requestType == .always && status {startAddressCreation() } }funcverify(_okverify: OkVerify, didInitializeresult: Bool) {print("initialized successfully") }funcverify(_okverify: OkVerify, didEncounterErrorerror: OkVerifyError) {debugPrint(error) }funcverify(_okverify: OkVerify, didStartAddressVerificationForlocationId: String) {print("started verification for: \(locationId)") }funcverify(_okverify: OkVerify, didStopVerificationForlocationId: String) {print("stopped verification for: \(locationId)") }funcverify(_okverify: OkVerify, didUpdateLocationPermissionStatusstatus: CLAuthorizationStatus) {// called on each status changeprint("location permission status updated") }funcverify(_okverify: OkVerify, didUpdateNotificationPermissionStatusstatus: Bool) {print("push notification permission status updated") }}
Test
Verification has started successfully:
When you simulate a change in the location of the device, you should see the GPS icon lighting up at the top of the screen
Common issues:
if background location permission is not granted, verification will not start
2.2 Physical Verification
If you'd like to only have physical verification done you can include verification types as part of the OkHiConfig
let okHiConfig =OkHiConfig().withVerificationTypes(verificationTypes: [.physical])
Physical verification only requires "whenInUse" location permission
2.3 Both Physical & Digital Verification
It's possible to have both physical and digital verification to run at the same time for a given address. Include both verification types as part of the array in the OkHiConfig
let okHiConfig =OkHiConfig().withVerificationTypes(verificationTypes: [.physical, .digital])
3. Add address endpoint (Server-side)
Here's a sample address payload that the client would get on successful address collection:
Create a secure endpoint on your server that your app can use to pass address details to your server. Remember to handle corner cases such as, address updates, multiple addresses if your app supports it.
//Secure new address endpointapp.post("/users/addresses",async (req) => {const { user,location } =req.body;const { id,firstName,lastName,phone } = user;const { id: locationId, displayTitle, title, subtitle, country, state, city, countryCode, lat, lon, plusCode, propertyName, streetName, url, streetViewPanoId, streetViewPanoUrl
} = location;console.log(user, location);// Store the location.id. Used to match webhook updatesreturn;});
4. Handle verification events (Server-side)
OkHi sends verification status updates over a few days while verification is on going. Follow the webhook guide to setup a webhook and receive these verification status updates and run actions such as upgrading a user's KYC level.
5. Show verification status in app(Server- & Client-side)
Create a secure endpoint to enable your app to retrieve address details, including the verification status received from the webhook
// Secure address retrieval endpointapp.get("/users/addresses", (req) => {// Get data from db. Example result:constdbResult= {"id":"8F0yPK1Zdj","status":"verified","displayTitle":"10, Raymond Njoku Street","title":"Raymond Njoku Street","subtitle":"10","country":"Nigeria","state":"Lagos","city":"Eti-Osa","countryCode":"ng", }return dbResult;});
Show the resulting address details and status on the address page in your app.
6. Test the integration
7. Customise the integration
Create a location permissions primer (Required)
Create your custom location permissions primer to educate your user on the requirement for location permissions. Make sure to follow our design best practices to ensure you meet the Google Play store and AppStore requirements.
Customise OkCollect (optional)
Its possible to completely transform the default appearance of OkHiLocationManager to better match your brand by providing values to the theme prop
Its possible to completely transform the default apperance of OkHiLocationManager to better match your brand by providing values to the okHiTheme prop
You may turn off either of the OkHi address types. This is to allow your users to create either home or work addresses to better suit your use-case. By default both address types are on.
let okHiConfig =OkHiConfig().enableStreetView().enableAppBar().withAddressTypes(work:true, home:false)
8. Getting ready to go live
Production credentials
Notify us that you'd like to cut a production build so we can supply production credentials.
Prepare for submission to App Store
Submitting an app to App Store that has background location permissions has a few extra requirements. Follow these guide to know what to expect and how to handle the extra requirements:
Address creation succeeds and verification is initiated
Launch OkHi's address manager via the button you created and create an address.
A sticky notification appears on android.
Dashboard
When verification is initiated, the address shows up on OkDash
Check OkDash, you should see a list of all the addresses created.
It takes ~3min for addresses to show up on OkDash
Proof of address
When an address is verified, the webhook receives the status update and the app shows the correct verification status.
A proof of address certificate is made available on OkDash.
Install your app on your personal device that you move around with and create your home address. Check okDash in 3 days for your proof of address certificate once your address has been verified.
Business logic
When an address is verified or not, the correct business logic is applied successfully.
Conduct a comprehensive test with multiple users, wherein they create various addresses to observe diverse outcomes. These outcomes may include successful creation of home addresses, entering incorrect addresses, refusing to grant necessary location permissions, or uninstalling the app immediately after initiating the address verification process, among other scenarios.