Google Drive SDK
Feedback on this document

Run a Drive app on iOS

To get started with Drive app development in Objective-C for iOS devices, you can inspect and run this simple photo upload app. Completing the steps described in this guide typically takes about five minutes. If you like, you can view a video of Google engineers guiding you through the steps.

The requirements for completing the steps are:

  • Access to the internet and a web browser.
  • A Google account with Drive enabled.
  • XCode 4.2 or newer

Complete the steps described in the rest of this page, and in a few minutes you'll have a simple Drive app that uploads a file to Google Drive.

Step 1: Enable the Drive API

First, you need to enable the Drive API for your app. You can do this in your app's API project in the Google APIs Console.

  1. Create an API project in the Google APIs Console.
  2. Select the Services tab in your API project, and enable the Drive API.
  3. Select the API Access tab in your API project, and click Create an OAuth 2.0 client ID.
  4. In the Branding Information section, provide a name for your application (e.g. "Drive Quickstart Sample"), and click Next. Providing a product logo is optional.
  5. In the Client ID Settings section, do the following:
    1. Select Installed application for the Application type
    2. Select Other for the Installed application type.
    3. Click Create Client ID.
  6. In the API Access page, locate the section Client ID for installed applications and note or copy the two pieces of information you'll need later to run the sample: the Client ID and the Client Secret.

Client ID and Secret for quickstart sample

Step 2: Install the Google Client Library

To use the Google APIs Client Library for Objective-C start by downloading the source with SVN.

svn checkout http://google-api-objectivec-client.googlecode.com/svn/trunk/ google-api-objectivec-client-read-only

Step 3: Create and Configure an XCode Project

  1. In Xcode, create a new workspace to contain the sample app and the Drive SDK which you'll add later on.
  2. Create a new project for the app using the Single View Application template. Fill in the product, organization, and company identifier.
  3. Add the client library by dragging GTL.xcodeproj into the workspace
  4. Update the application project's Build Phases "Link Binary with Libraries" list to include:
    1. libGTLTouchStaticLib.a from the GTL project. This is the client library.
    2. Security.framework and SystemConfiguration.framework are required dependencies from the client library and also must be included.
    3. MobileCoreServices.framework which contains code useful for accessing the camera.
  5. Add -ObjC -all_load to the Other Linker Flags setting in the application project's Build Settings.
  6. Also in the application project's Build Settings, add the client library headers to the application project by adding the Source directory of the GTL project to the User headers search path section with the recursive option.
  7. Drag GTMOAuth2ViewTouch.xib from client library's Source/OAuth2/Touch folder into the app's Supporting Files folder.
  8. Add the Google Drive service by adding GTLDrive.h and GTLDrive_Sources.m from the Source/Services/Drive/Generated folder directly to the application project.

Step 4: Set up the sample

Now that the project is created, you'll need to edit the view controller that was created for the project.

Copy the source for ViewController.h below.

#import <UIKit/UIKit.h>
#import <MobileCoreServices/MobileCoreServices.h>

#import "GTMOAuth2ViewControllerTouch.h"
#import "GTLDrive.h"

@interface ViewController : UIViewController <UINavigationControllerDelegate, UIImagePickerControllerDelegate>

@property (nonatomic, retain) GTLServiceDrive *driveService;

@end

For the implementation, copy the source for ViewController.m below. You'll also need to replace YOUR_CLIENT_ID and YOUR_CLIENT_SECRET with the Client ID and Client Secret you generated in the "Enable the Drive API" step.

#import "ViewController.h"

static NSString *const kKeychainItemName = @"Google Drive Quickstart";
static NSString *const kClientID = @"YOUR_CLIENT_ID";
static NSString *const kClientSecret = @"YOUR_CLIENT_SECRET";

@implementation ViewController

@synthesize driveService;

- (void)viewDidLoad
{
    [super viewDidLoad];

    // Initialize the drive service & load existing credentials from the keychain if available
    self.driveService = [[GTLServiceDrive alloc] init];
    self.driveService.authorizer = [GTMOAuth2ViewControllerTouch authForGoogleFromKeychainForName:kKeychainItemName
                                                                                         clientID:kClientID
                                                                                     clientSecret:kClientSecret];
}

- (void)viewDidAppear:(BOOL)animated
{
    // Always display the camera UI.
    [self showCamera];
}

- (void)showCamera
{
    UIImagePickerController *cameraUI = [[UIImagePickerController alloc] init];
    if ([UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera])
    {
        cameraUI.sourceType = UIImagePickerControllerSourceTypeCamera;
    }
    else
    {
        // In case we're running the iPhone simulator, fall back on the photo library instead.
        cameraUI.sourceType = UIImagePickerControllerSourceTypePhotoLibrary;
        if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPad)
        {
            [self showAlert:@"Error" message:@"Sorry, iPad Simulator not supported!"];
            return;
        }
    };
    cameraUI.mediaTypes = [[NSArray alloc] initWithObjects: (NSString *) kUTTypeImage, nil];
    cameraUI.allowsEditing = YES;
    cameraUI.delegate = self;
    [self presentModalViewController:cameraUI animated:YES];

    if (![self isAuthorized])
    {
        // Not yet authorized, request authorization and push the login UI onto the navigation stack.
        [cameraUI pushViewController:[self createAuthController] animated:YES];
    }
}

// Handle selection of an image
- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
{
    UIImage *image = [info valueForKey:UIImagePickerControllerOriginalImage];
    [self dismissModalViewControllerAnimated:YES];
    [self uploadPhoto:image];
}

// Handle cancel from image picker/camera.
- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker
{
    [self dismissModalViewControllerAnimated:YES];
}

// Helper to check if user is authorized
- (BOOL)isAuthorized
{
    return [((GTMOAuth2Authentication *)self.driveService.authorizer) canAuthorize];
}

// Creates the auth controller for authorizing access to Google Drive.
- (GTMOAuth2ViewControllerTouch *)createAuthController
{
    GTMOAuth2ViewControllerTouch *authController;
    authController = [[GTMOAuth2ViewControllerTouch alloc] initWithScope:kGTLAuthScopeDriveFile
                                                                clientID:kClientID
                                                            clientSecret:kClientSecret
                                                        keychainItemName:kKeychainItemName
                                                                delegate:self
                                                        finishedSelector:@selector(viewController:finishedWithAuth:error:)];
    return authController;
}

// Handle completion of the authorization process, and updates the Drive service
// with the new credentials.
- (void)viewController:(GTMOAuth2ViewControllerTouch *)viewController
      finishedWithAuth:(GTMOAuth2Authentication *)authResult
                 error:(NSError *)error
{
    if (error != nil)
    {
        [self showAlert:@"Authentication Error" message:error.localizedDescription];
        self.driveService.authorizer = nil;
    }
    else
    {
        self.driveService.authorizer = authResult;
    }
}

// Uploads a photo to Google Drive
- (void)uploadPhoto:(UIImage*)image
{
    NSDateFormatter *dateFormat = [[NSDateFormatter alloc] init];
    [dateFormat setDateFormat:@"'Quickstart Uploaded File ('EEEE MMMM d, YYYY h:mm a, zzz')"];

    GTLDriveFile *file = [GTLDriveFile object];
    file.title = [dateFormat stringFromDate:[NSDate date]];
    file.descriptionProperty = @"Uploaded from the Google Drive iOS Quickstart";
    file.mimeType = @"image/png";

    NSData *data = UIImagePNGRepresentation((UIImage *)image);
    GTLUploadParameters *uploadParameters = [GTLUploadParameters uploadParametersWithData:data MIMEType:file.mimeType];
    GTLQueryDrive *query = [GTLQueryDrive queryForFilesInsertWithObject:file
                                                       uploadParameters:uploadParameters];

    UIAlertView *waitIndicator = [self showWaitIndicator:@"Uploading to Google Drive"];

    [self.driveService executeQuery:query
        completionHandler:^(GTLServiceTicket *ticket,
                            GTLDriveFile *insertedFile, NSError *error) {
            [waitIndicator dismissWithClickedButtonIndex:0 animated:YES];
            if (error == nil)
            {
                NSLog(@"File ID: %@", insertedFile.identifier);
                [self showAlert:@"Google Drive" message:@"File saved!"];
            }
            else
            {
                NSLog(@"An error occurred: %@", error);
                [self showAlert:@"Google Drive" message:@"Sorry, an error occurred!"];
            }
        }];
}

// Helper for showing a wait indicator in a popup
- (UIAlertView*)showWaitIndicator:(NSString *)title
{
    UIAlertView *progressAlert;
    progressAlert = [[UIAlertView alloc] initWithTitle:title
                                               message:@"Please wait..."
                                              delegate:nil
                                     cancelButtonTitle:nil
                                     otherButtonTitles:nil];
    [progressAlert show];

    UIActivityIndicatorView *activityView;
    activityView = [[UIActivityIndicatorView alloc] initWithActivityIndicatorStyle:UIActivityIndicatorViewStyleWhite];
    activityView.center = CGPointMake(progressAlert.bounds.size.width / 2,
                                      progressAlert.bounds.size.height - 45);

    [progressAlert addSubview:activityView];
    [activityView startAnimating];
    return progressAlert;
}

// Helper for showing an alert
- (void)showAlert:(NSString *)title message:(NSString *)message
{
    UIAlertView *alert;
    alert = [[UIAlertView alloc] initWithTitle: title
                                               message: message
                                              delegate: nil
                                     cancelButtonTitle: @"OK"
                                     otherButtonTitles: nil];
    [alert show];
}

@end

Step 5: Run the sample

After you have set up your Google API project, installed the Google API client library, and set up the sample source code, the sample is ready to run. You can run the sample using the iPhone simulator or use a configured device.

When running the sample on a simulator where no camera is available, the photo library is used instead. If needed, you can add photos to the library using the following steps:

  1. Drag an image from Finder on to the simulator.
  2. Click-hold on the image in Safari.
  3. Click Save Image to store the image in the photo library.

When the sample runs for the first time, you'll be prompted to log in to your Google account and approve access. Once authorized, select an image from the library or take a photo to upload it to Google Drive.

Once you have things working, try experimenting with other API methods. Or try the more detailed sample app to see more of the Drive API in action.

Optional: View a quickstart video

Videos from the ongoing Drive Google Developers Live sessions cover the setup and running of each quickstart sample in detail. If you'd like to see the iOS quickstart sample demonstrated by some of the same developers who wrote it, click play, sit back, and enjoy.

Authentication required

You need to be signed in with Google+ to do that.

Signing you in...

Google Developers needs your permission to do that.