Last Mile Fleet Solution n'est actuellement disponible que pour certains clients. Contactez le service commercial pour en savoir plus.

Premiers pas avec le SDK Driver pour iOS

Restez organisé à l'aide des collections Enregistrez et classez les contenus selon vos préférences.

Le SDK Driver est une bibliothèque que vous intégrez à votre application de pilote. Elle permet de mettre à jour Fleet Engine en indiquant l'emplacement, l'itinéraire, la distance restante et l'heure d'arrivée prévue du pilote. Il s'intègre également au SDK Navigation, qui fournit des instructions de navigation détaillées au conducteur.

Configuration système minimale requise

L'appareil mobile doit être équipé d'iOS 12 ou version ultérieure.

Conditions préalables

Ce guide suppose que votre application implémente déjà le SDK Navigation et que le backend de Fleet Engine est configuré et disponible. Cependant, l'exemple de code fournit un exemple de configuration du SDK Navigation.

Vous devez également activer le SDK Maps pour iOS dans votre projet Google Cloud et obtenir une clé API.

Obtenir l'accès

Si vous êtes un client Google Workspace, créez un groupe Workspace tel que google-maps-platform-sdk-users@workspacedomain.com lors de l'intégration et indiquez le nom à Google. Il s'agit de l'approche recommandée. Votre groupe d'espaces de travail sera ensuite ajouté à une liste d'autorisation qui accorde l'accès aux dépôts CocoaPods appropriés. Vérifiez que l'adresse e-mail de l'utilisateur et l'adresse e-mail du compte de service qui ont besoin d'un accès sont incluses dans cette liste.

Si votre organisation ne peut pas créer de groupes Workspace, envoyez à Google la liste des adresses e-mail des utilisateurs et des comptes de service qui ont besoin d'accéder à ces artefacts.

Développement local

Pour le développement local, une connexion avec le SDK Cloud suffit.

gcloud

gcloud auth login

L'adresse e-mail utilisée pour se connecter doit faire partie du groupe Workspace.

Automatisation (systèmes de compilation ou intégration continue)

Configurez vos hôtes d'automatisation conformément aux bonnes pratiques:

  • Si votre processus s'exécute dans un environnement Google Cloud, utilisez la détection automatique des identifiants.

  • Sinon, stockez le fichier de clé du compte de service dans un emplacement sécurisé du système de fichiers de l'hôte et définissez la variable d'environnement GOOGLE_APPLICATION_CREDENTIALS de manière appropriée.

L'adresse e-mail du compte de service associé aux identifiants doit être membre du groupe de travail Workspace.

Configuration du projet

Vous pouvez configurer le SDK Driver pour iOS à l'aide de CocoaPods ou manuellement.

Utiliser CocoaPods

Afin de configurer le SDK Driver pour iOS, vous avez besoin des éléments suivants:

  • Outil CocoaPods: pour installer cet outil, ouvrez le terminal et exécutez la commande suivante.

    sudo gem install cocoapods
    

    Pour en savoir plus, consultez le guide de démarrage de CocoaPods.

  • Votre compte de développement dans la liste de contrôle d'accès (LCA) de Google : le dépôt du pod du SDK ne se trouve pas dans une source publique. Pour accéder au pod, contactez l'ingénieur client Google. Il ajoute votre compte de développement à la LCA, puis définit un cookie pour l'authentification.

Une fois votre projet sur la LCA, vous pouvez accéder au pod.

  1. Créez un fichier Podfile pour le SDK Delivery pour iOS et utilisez-le pour installer l'API et ses dépendances: créez un fichier nommé Podfile dans le répertoire de votre projet. Ce fichier définit les dépendances de votre projet. Modifiez le fichier Podfile et ajoutez vos dépendances. Voici un exemple qui inclut les dépendances:

    source "https://cpdc-eap.googlesource.com/ridesharing-driver-sdk.git"
    source "https://cpdc-eap.googlesource.com/geo-nav-sdk.git"
    source "https://github.com/CocoaPods/Specs.git"
    
    target 'YOUR_APPLICATION_TARGET_NAME_HERE' do
      pod 'GoogleDeliveryDriver'
    end
    
  2. Enregistrez le fichier Podfile. Ouvrez un terminal et accédez au répertoire contenant le Podfile:

    cd <path-to-project>
    
  3. Exécutez la commande d'installation du pod. Les API spécifiées dans le Podfile seront installées, ainsi que toutes les dépendances éventuelles.

    pod install
    
  4. Fermez Xcode, puis ouvrez (double-cliquez) le fichier .xcworkspace de votre projet pour lancer Xcode. À partir de ce moment, vous devez utiliser le fichier .xcworkspace pour ouvrir le projet.

Configurer manuellement

Pour configurer manuellement le SDK Driver for iOS:

  1. Installer le SDK Maps pour iOS

    Le framework de livraison nécessite le SDK Maps pour iOS (framework GoogleMaps). En savoir plus sur l'installation du SDK Maps pour iOS

  2. Ajouter le framework et les ressources de diffusion

    1. Décompressez le fichier ZIP source que vous avez reçu.

    2. Lancez Xcode et ouvrez un projet existant ou créez-en un nouveau.

    3. Sélectionnez votre projet dans le navigateur de projet et choisissez la cible de votre application.

    4. Ouvrez l'onglet Build Phases (Phases de compilation) et, sous Link Binary with Libraries (Associer le binaire avec des bibliothèques), cliquez sur le bouton Plus (+).

    5. Cliquez sur Add Other (Ajouter un autre) et sélectionnez le framework de diffusion.

    6. Dans le répertoire "Framework de diffusion", sélectionnez le framework de diffusion. GoogleDeliveryDriver.framework

  3. Ajouter des ressources

    1. Dans Xcode, ouvrez les phases de compilation du projet, puis dans Copier les ressources du bundle, cliquez sur le bouton Plus (+).

    2. Cliquez sur Add Other (Ajouter un autre) et sélectionnez le framework de diffusion.

    3. Dans le répertoire Framework de livraison, sélectionnez le fichier suivant:

      • gRPCCertificates.bundle (non requis si vous utilisez déjà gRPC dans votre projet).
    4. Sous Sélectionner des options pour ajouter les fichiers, cochez la case Copier les éléments si nécessaire.

Implémenter l'autorisation et l'authentification

Lorsque votre application de pilote génère et envoie des mises à jour au backend Fleet Engine, les requêtes doivent inclure des jetons d'accès valides. Pour autoriser et authentifier ces requêtes, le SDK Driver appelle votre objet conformément au protocole GMTDAuthorization. L'objet se charge de fournir le jeton d'accès requis.

En tant que développeur de l'application, vous choisissez comment les jetons sont générés. Votre mise en œuvre doit permettre:

  • Récupérez un jeton d'accès, éventuellement au format JSON, à partir d'un serveur HTTPS.
  • Analyser et mettre en cache le jeton
  • Actualisez le jeton lorsqu'il expire.

Pour en savoir plus sur les jetons attendus par le serveur Fleet Engine, consultez la section Créer un jeton Web JSON (JWT) pour l'autorisation.

L'ID du fournisseur est identique à l'ID du projet Google Cloud. Pour en savoir plus, consultez le guide de l'utilisateur de l'API Fleet Engine Deliveries.

L'exemple suivant met en œuvre un fournisseur de jetons d'accès:

#import "SampleAccessTokenProvider.h"
#import <GoogleRidesharingDriver/GoogleRidesharingDriver.h>

// SampleAccessTokenProvider.h
@interface SampleAccessTokenProvider : NSObject<GMTDAuthorization>
@end

static NSString *const PROVIDER_URL = @"INSERT_YOUR_TOKEN_PROVIDER_URL";

// SampleAccessTokenProvider.m
@implementation SampleAccessTokenProvider{
  // The cached vehicle token.
  NSString *_cachedVehicleToken;
  // Keep track of the vehicle ID the cached token is for.
  NSString *_lastKnownVehicleID;
  // Keep track of when tokens expire for caching.
  NSTimeInterval _tokenExpiration;
}

- (void)fetchTokenWithContext:(nullable GMTDAuthorizationContext *)authorizationContext
                   completion:(nonnull GMTDAuthTokenFetchCompletionHandler)completion {
  if (!completion) {
    NSAssert(NO, @"%s encountered an unexpected nil completion.", __PRETTY_FUNCTION__);
    return;
  }

  // Get the vehicle ID from the authorizationContext. This is set by the Driver SDK.
  NSString *vehicleID = authorizationContext.vehicleID;
  if (!vehicleID) {
    NSAssert(NO, @"Vehicle ID is missing from authorizationContext.");
    return;
  }

// Clear cached vehicle token if vehicle ID has changed.
  if (![_lastKnownVehicleID isEqual:vehicleID]) {
    _tokenExpiration = 0.0;
    _cachedVehicleToken = nil;
  }
  _lastKnownVehicleID = vehicleID;

  // Clear cached vehicle token if it has expired.
  if ([[NSDate date] timeIntervalSince1970] > _tokenExpiration) {
    _cachedVehicleToken = nil;
  }

  // If appropriate, use the cached token.
  if (_cachedVehicleToken) {
    completion(_cachedVehicleToken, nil);
    return;
  }
  // Otherwise, try to fetch a new token from your server.
  NSURL *requestURL = [NSURL URLWithString:PROVIDER_URL];
  NSMutableURLRequest *request = 
                          [[NSMutableURLRequest alloc] initWithURL:requestURL];
  request.HTTPMethod = @"GET";
  // Replace the following key values with the appropriate keys based on your
  // server's expected response.
  NSString *vehicleTokenKey = @"VEHICLE_TOKEN_KEY";
  NSString *tokenExpirationKey = @"TOKEN_EXPIRATION";
  __weak typeof(self) weakSelf = self;
  void (^handler)(NSData *_Nullable data, NSURLResponse *_Nullable response,
                  NSError *_Nullable error) =
      ^(NSData *_Nullable data, NSURLResponse *_Nullable response, NSError *_Nullable error) {
        typeof(self) strongSelf = weakSelf;
        if (error) {
          completion(nil, error);
          return;
        }

        NSError *JSONError;
        NSMutableDictionary *JSONResponse =
            [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&JSONError];

        if (JSONError) {
          completion(nil, JSONError);
          return;
        } else {
          // Sample code only. No validation logic.
          id expirationData = JSONResponse[tokenExpirationKey];
          if ([expirationData isKindOfClass:[NSNumber class]]) {
            NSTimeInterval expirationTime = ((NSNumber *)expirationData).doubleValue;
            strongSelf->_tokenExpiration = [[NSDate date] timeIntervalSince1970] + expirationTime;
          }
          strongSelf->_cachedVehicleToken = JSONResponse[vehicleTokenKey];
          completion(JSONResponse[vehicleTokenKey], nil);
        }
    };
NSURLSessionConfiguration *config = [NSURLSessionConfiguration defaultSessionConfiguration];
NSURLSession *mainQueueURLSession =  
       [NSURLSession  sessionWithConfiguration:config delegate:nil
delegateQueue:[NSOperationQueue mainQueue]];
NSURLSessionDataTask *task = [mainQueueURLSession dataTaskWithRequest:request completionHandler:handler];
[task resume];
}

@end

Créer une instance DeliveryDriverAPI

Pour obtenir une instance GMTDDeliveryVehicleReporter, vous devez d'abord créer une instance GMTDDeliveryDriverAPI en utilisant l'ID fournisseur, l'ID de véhicule, le paramètre "ContextContext" et l'accessaccessProvider. L'ID du fournisseur est identique à l'ID du projet Google Cloud. Vous pouvez également accéder directement à l'instance GMTDDeliveryVehicleReporter à partir de l'API du pilote.

L'exemple suivant crée une instance GMTDDeliveryDriverAPI:

#import “SampleViewController.h”
#import “SampleAccessTokenProvider.h”
#import <GoogleDeliveryDriver/GoogleDeliveryDriver.h>

static NSString *const PROVIDER_ID = @"INSERT_YOUR_PROVIDER_ID";

@implementation SampleViewController {
 GMSMapView *_mapView; 
}

- (void)viewDidLoad {
  NSString *vehicleID = @"INSERT_CREATED_VEHICLE_ID";
  SampleAccessTokenProvider *accessTokenProvider = 
                                [[SampleAccessTokenProvider alloc] init];
  GMTDDriverContext *driverContext = 
     [[GMTDDriverContext alloc] initWithAccessTokenProvider:accessTokenProvider
                                                 providerID:PROVIDER_ID 
                                              vehicleID:vehicleID 
      navigator:_mapView.navigator];

  GMTDDeliveryDriverAPI *deliveryDriverAPI = [[GMTDDeliveryDriverAPI alloc] initWithDriverContext:driverContext];
}

Écouter les événements VehicleReporter (facultatif)

GMTDDeliveryVehicleReporter met régulièrement à jour le véhicule lorsque locationTrackingEnabled est défini sur "YES". Pour répondre à ces mises à jour périodiques, n'importe quel objet peut s'abonner à des événements GMTDDeliveryVehicleReporter en respectant le protocole GMTDVehicleReporterListener.

Vous pouvez gérer les événements suivants:

  • vehicleReporter:didSucceedVehicleUpdate

    Indique à l'application Driver que les services de backend ont bien reçu la mise à jour de l'emplacement et de l'état du véhicule.

  • vehicleReporter:didFailVehicleUpdate:withError

    Indique à l'écouteur qu'une mise à jour du véhicule a échoué. Tant que le suivi de la position est activé, GMTDDeliveryVehicleReporter continue d'envoyer les dernières données au backend de Fleet Engine.

L'exemple suivant gère ces événements:

SampleViewController.h
@interface SampleViewController : UIViewController<GMTDVehicleReporterListener>
@end

SampleViewController.m
#import “SampleViewController.h”
#import “SampleAccessTokenProvider.h”
#import <GoogleDeliveryDriver/GoogleDeliveryDriver.h>

static NSString *const PROVIDER_ID = @"INSERT_YOUR_PROVIDER_ID";

@implementation SampleViewController {
 GMSMapView *_mapView;
}


- (void)viewDidLoad {
  // ASSUMES YOU IMPLEMENTED HAVE THE SAMPLE CODE UP TO THIS STEP.
  [ridesharingDriverAPI.vehicleReporter addListener:self];
}

- (void)vehicleReporter:(GMTDDeliveryVehicleReporter *)vehicleReporter didSucceedVehicleUpdate:(GMTDVehicleUpdate *)vehicleUpdate {
  // Handle update succeeded.
}

- (void)vehicleReporter:(GMTDDeliveryVehicleReporter *)vehicleReporter didFailVehicleUpdate:(GMTDVehicleUpdate *)vehicleUpdate withError:(NSError *)error {
  // Handle update failed.
}

@end

Activer le suivi de la position géographique

Pour activer le suivi de la position, votre application peut définir locationTrackingEnabled sur YES sur GMTDDeliveryVehicleReporter. Ensuite, GMTDDeliveryVehicleReporter enverra automatiquement les mises à jour de la position. Lorsque GMSNavigator est en mode navigation (lorsqu'une destination est définie via setDestinations) et que locationTrackingEnabled est défini sur YES, GMTDDeliveryVehicleReporter envoie automatiquement les mises à jour de l'itinéraire et de l'heure d'arrivée.

L'itinéraire défini lors de ces mises à jour sera le même que celui que le conducteur emprunte pendant la session de navigation. Ainsi, pour que le suivi des livraisons fonctionne correctement, le point de cheminement défini via -setDestinations:callback: doit correspondre à la destination définie dans le backend Fleet Engine.

L'exemple suivant active le suivi de la position géographique:

SampleViewController.m
#import “SampleViewController.h”
#import “SampleAccessTokenProvider.h”
#import <GoogleDeliveryDriver/GoogleDeliveryDriver.h>

static NSString *const PROVIDER_ID = @"INSERT_YOUR_PROVIDER_ID";

@implementation SampleViewController {
 GMSMapView *_mapView; 
}

- (void)viewDidLoad {
  // ASSUMES YOU IMPLEMENTED HAVE THE SAMPLE CODE UP TO THIS STEP.
  deliveryDriverAPI.vehicleReporter.locationTrackingEnabled = YES;
}

@end

Par défaut, l'intervalle de rapport est de 10 secondes, mais vous pouvez le modifier avec locationUpdateInterval. L'intervalle de mise à jour compatible minimal est d'une seconde. L'intervalle de mise à jour maximal autorisé est de 60 secondes. Des mises à jour plus fréquentes peuvent ralentir les requêtes et les erreurs.

Désactiver les mises à jour de la position géographique

Votre appli peut désactiver les mises à jour de la position pour un véhicule. Par exemple, à la fin du travail d'un conducteur, votre application peut définir locationTrackingEnabled sur NO.

  _vehicleReporter.locationTrackingEnabled = NO