Skip to end of metadata
Go to start of metadata


This article aims at helping an iOS developer to get started with a simple 'application'  which the following

  1. Registration of the user automatically with the SUP Server using a predefined set of constraints like the Application Connection, Security Configuration.
  2. A simple GET call to the back-end Gateway to fetch the service document definition.

This helps the application developer to get a hang of the flow off the application as the subsequent calls will be similar to the first GET call. What will not be covered in this article is the parsing functionality as that by itself a topic good enough for another blog or a wiki. Also this article assumes that the application developer is not a  complete novice to the iOS development environment. The assumptions made are not huge as this article touches upon important configurations that need to be made to the project.

This article is for the already release 2.1 version of the SUP-ODP online mobile solution. The version of the XCode IDE used for demonstrating the example will be 4.2 (iOS5 SDK), but the deployment target for the project will be iOS version 4.2 and above.

Getting Started

Setting up the project

As mentioned before, every single detail about setting up the project will not be covered in this section. This section will talk more about how to get the client libraries from the Mobile SDK client installer and how to set the project by including all the necessary files from the client libraries.

  • Create an XCode 4.2 project with a single view for minimal interaction with the user.
  • Get the client libraries as .zip files from <unwiredplatform_installdir>/MobileSDK/OData/iOS/. This location will contain 2  .zip files namely* and*.
  • Unzip the files and transfer the contents on to project folder. Both the zip files will have the same parent folder name 'iOS'. Rename them to ODATA and ODP respectively.
  • At the end of all the above operations the project structure should look like below.
  • Once the files are in place, go to the project. Navigate to 'Build Settings' of the active target. Search for the settings 'Header Search Path' and enter the following values for it(including the double quotes)  "$(PROJECT_DIR)/ODATA/includes/public/SDMConnectivity" and "$(PROJECT_DIR)/ODP/includes/public/SUPProxyClient". By doing this, we are giving the reference of the required header files to the project. "$(PROJECT_DIR)" is an XCode environment variable which dynamically gives the root of the current project folder. This is used to make the project portable. We are only taking into account those header files which we need for our test demo application. Others will be ignored for the current scope.
  • In the same 'Build Settings' tab, search for 'Library Search Path' and enter the following values. "$(PROJECT_DIR)/ODATA/libraries/$(BUILD_STYLE)-universal" and "$(PROJECT_DIR)/ODP/libraries/$(BUILD_STYLE)-universal".  Search for a setting called 'Other Linker Flags' and add 2 values to it namely '-ObjC' and '-all_load'.
  • In the 'Build Phase' tab, go to the 'Link Binary with Libraries' option and click on the '+' and by using the 'Add Other...' button at the bottom, add the libraries from the above path to this section. This is mandatory without which the project build can give compilation errors.
  • Once the external libraries are added, follow the same steps again, but instead of clicking on the 'Add Other...' option, select the following frameworks from the list shown in the popup. For more information on this and the previous point, the screenshot below can be referenced. With this, the project is now ready for application coding.

User Registration

The User registration process involves activities from the server side as well as the client side. The administrator of the SUP-ODP server has to make sure that the following things are already taken care of before the client tries to register a user automatically with the server. The below topics will not be explained in great detail here. This article is purely dedicated for client development.

  1. An Application Id has to be created on the server for this application specifically.
  2. A security configuration also has to be created for the type of automatic registration the client wishes to go through.
  3. An application connection has to be created linking the application Id and the security configuration created above and by selecting the right domain.

Once these are in place, the application can be coded for user registration. One thing to be noted here is that all the values will be hard-coded against the function calls and there will be no much UI interaction involved.

For User registration API, include the "LiteSUPUserManager.h" header file.

In the .m file of the main view controller, the code can be put under the '(void)viewDidLoad' event so that the code gets executed when the view loads. The code is as below.

    @try {
        LiteSUPUserManager* manager = [LiteSUPUserManager getInstance:@"APPLICATIONID"];
        if (![manager isUserRegistered]) {
            [manager setConnectionProfile:@"" withSupPort:5001 withServerFarmID:@"0"];
            [manager registerUser:@"TESTUSER" withSecurityConfig:@"SECCONFIG" withPassword:@"password" withVaultPassword:@"vaultpassword"];
    @catch (NSException *exception) {
        UIAlertView* alertView = [[UIAlertView alloc] initWithTitle:@"Error" message:[exception reason] delegate:self cancelButtonTitle:@"OK" otherButtonTitles:nil];
        [alertView show];
        [alertView release];

Once you run the application with this code, provided the right values are passed, the user is successfully created on the server and the connection successfully established. If there are any errors, the exception block in invoked and showing an error message the control returns from the code.

A few things to be noted here are that the string literals @"APPLICATIONID", @"SECCONFIG" should match with the Application ID and the security configuration that have been created on the server case-sensitive. And the User should have an account with the Security configuration authentication provider and the back-end gateway with the password that is passed satisfying the conditions for that particular security configuration.

There is another addition in the above function call, namely the 'Vault Password'. By passing this to the function call, the application developer completely hands over the responsibility of storing sensitive data like the password to the ODP framework.

DISCLAIMER : Since this is a demonstration of the sample application, we are hard-coding the values against the input parameters. The same should not be done in case of a productive application, more so with a parameter like password.

Data fetch : A simple GET call

If the user registration returns successfully, then the control comes to the next piece of code written after the above code. In all other error cases, the control moves out of this block because of the 'return' statement in the exception block.

For data fetch, we use a factory class called the "SDMRequestBuilder" to instantiate an object of the type the protocol "SDMRequesting". Hence we import both the header files "SDMRequesting.h" and the "SDMRequestBuilder.h".

Once the imports are done, the code for the data fetch will be written immediately after the above piece of code for user registration. In total, the code will wholly look like below.

    // User Registration
    @try {
        LiteSUPUserManager* manager = [LiteSUPUserManager getInstance:@"APPLICATIONID"];
        if (![manager isUserRegistered]) {
            [manager setConnectionProfile:@"" withSupPort:5001 withServerFarmID:@"0"];
            [manager registerUser:@"TESTUSER" withSecurityConfig:@"SECCONFIG" withPassword:@"password" withVaultPassword:@"vaultpassword"];
    @catch (NSException *exception) {
        UIAlertView* alertView = [[UIAlertView alloc] initWithTitle:@"Error" message:[exception reason] delegate:self cancelButtonTitle:@"OK" otherButtonTitles:nil];
        [alertView show];
        [alertView release];

    // Data Fetch
    LiteSUPUserManager* userManager = [LiteSUPUserManager getInstance:@"APPLICATIONID"];
    [userManager unlock:@"vaultpassword"];
    id<SDMRequesting> request = [SDMRequestBuilder requestWithURL:[NSURL URLWithString:@""]];
    [request setRequestMethod:@"GET"];
    [request addRequestHeader:@"DUMMY-HEADER" value:@"XYZ"];
    [request setTimeOutSeconds:100];
    [request startSynchronous];
    if ([request error] != nil ) {
        UIAlertView* alertView = [[UIAlertView alloc] initWithTitle:@"Request Error" message:[[request error] localizedDescription] delegate:self cancelButtonTitle:@"OK" otherButtonTitles:nil];
        [alertView show];
        [alertView release];
    NSLog(@"%@", [request responseString]);
    NSData* respData = [request responseData];

From the code above, if we focus on the data fetch code we can notice a few things.

  1. The SDMRequesting interface is an interface implemented by the SUPRequest class which is abstracted to the application developer and instantiated by the factory class SDMRequestBuilder.
  2. We also observe that we have declared a second object to get the instance of the User Manager class. Since the class is a singleton, the same instance is returned if any code in the application asks for the instance. Hence this code is put in 2 places to convey this.
  3. We see that no credentials are passed to the request object before making a call, but there is a call to the 'unlock' message of the User Manager class passing the vault password. This will indicate the framework that it should take care of passing credentials since it is responsible for storing sensitive data (as mentioned above).
  4. We also see a couple of examples about the flexibility of the request object i.e. to take in time out seconds and the custom headers.

Since the request is a synchronous call, there is a waiting period before the request finishes and once it finishes, the control immediately comes to the next line where we check for any errors caused during the framework execution and return from the execution if any.

The last 2 lines are an example that the response can either be fetched in the format of a string or a binary stream, however the developer deems appropriate.


  1. Former Member


    would you please tell me when it will be possible to use the OData SDK together with xCode 4.2 and deployment target iOS 5?

    Thanks and kind regards,


  2. Unknown User (t2qpp4t)

    Many Many tanx for this exemple, it is a realy good startup!!!

    Do you plan on provide more exemples ?


  3. Hi,

    Many thanks for this wonderful tutorial... I was able to make it work in a plain xCode project.

    I'm trying now to integrate this code with phonegap 1.5, I did the same steps, but now I'm getting an exception when calling registerUser:

    ERROR :: MessagingClientException:RuntimeException: Failure in setConfigProperty/Location:-[LiteSUPUserManager registerUser:withActivationCode:] + 152

    Any thoughts ?



  4. Unknown User (j4iihxt)


    > Alan Rubin wrote

    > ERROR :: MessagingClientException:RuntimeException: Failure in setConfigProperty/Location:-[LiteSUPUserManager registerUser:withActivationCode:] + 152

    I am running into the same problem. Does anyone have any solution to this?



  5. Unknown User (106oj4fj4)


    thanks for the nice tutorial! I noticed that under the last step of "Setting up the project", the list of the required libraries is missing. I found the list in another SUP Developer Guide, here it is:

    • CoreFoundation.framework
    • QuartzCore.framework
    • Security.framework
    • libicucore.A.dylib
    • libstdc++.dylib
    • libz.1.2.5.dylib
    • CFNetwork.framework
    • MobileCoreServices.framework
    • SystemConfiguration.framework
    • MessageUI.framework

  6. Unknown User (x7di16d)

    Hey thanks for the tutorial. Followed it closely but buildings fails and I get the following Apple Mach-o Linker Error:

    Undefined symbols for architecture i386:

    "OBJC_CLASS$_LiteSUPUserManager", referenced from:

    objc-class-ref in ViewController.o

    ld: symbol(s) not found for architecture i386

    clang: error: linker command failed with exit code 1 (use -v to see invocation)

    Help is much appreciated :)