Skip to content

Integrate with other apps

lramos edited this page Apr 15, 2015 · 4 revisions

There are some interfaces that need to be implemented in order to integrate Schedulizer with other external apps. The external app must have an authentication endpoint and a way to autocomplete the name of other users. Optionally it may have a way to post messages in groups (which allows the Remind Users feature to work).

Follow these steps to integrate with your app:

(1) Add your app name to the ExtAppType enum at src/main/java/com/yammer/schedulizer/auth/ExtAppType.java. For example:

public enum ExtAppType {
    yammer, facebook, myApp
}

(2) Create inside /src/main/java/com/yammer/schedulizer/auth an Authenticator for your app. For example: MyAppAuthenticator.java. It should extend ExtAppAuthenticator and implement the method getTokenOwner that receives an access token from your external app, makes a request to get the users information and returns an Employee instance. For example:

package com.yammer.schedulizer.auth;

import com.fasterxml.jackson.databind.JsonNode;
import com.sun.jersey.api.client.Client;
import com.yammer.schedulizer.entities.Employee;

import javax.ws.rs.core.MediaType;

public class MyAppAuthenticator extends ExtAppAuthenticator {
    private static final String MY_APP_CURRENT_USER_ENDPOINT = "https://my_app.com/me";
    private static final String ACCESS_TOKEN_PARAM = "access_token";

    public MyAppAuthenticator(Client client) {
        super(client);
    }

    @Override
    public Employee getTokenOwner(String accessToken) {
        JsonNode response = client.resource(MY_APP_CURRENT_USER_ENDPOINT)
                .queryParam(ACCESS_TOKEN_PARAM, accessToken)
                .accept(MediaType.APPLICATION_JSON_TYPE)
                .get(JsonNode.class);

        String myAppId = response.get("id").asText();
        String name = response.get("name").asText();
        String imageUrlTemplate = response.get("image_url").asText();

        Employee employee = new Employee(name, myAppId, ExtAppType.myApp);
        employee.setImageUrlTemplate(imageUrlTemplate);
        return employee;
    }
}

(3) Add your Authenticator to the Factory at src/main/java/com/yammer/schedulizer/auth/ExtAppAuthenticatorFactory.java

case myApp:
    return new MyAppAuthenticator(client);

(4) Now that the back end is all set, you must go to the front end. First you should add any necessary javascript sdk loading and initialization at the src/main/resources/com/yammer/schedulizer/freemarker/ext_app_config.ftl. For example, add the lines:

<#elseif extApp == "myApp">
    <script src="https://my_app.com/sdk.js"></script>
    <script>
       myApp.init('${extAppClientId}');
    </script>

(5) Now you should implement the request to your app endpoints. Do that by editing the file src/main/resources/assets/js/services/ext_app_api.js and adding your app to the big switch. Note that the map EXT_APP_TYPES comes from the backend, so your app is already an entry.

        case EXT_APP_TYPES.myApp:
            if (!myApp) { throw new Error('Could not load myApp api'); }
            extAppApi =  {
                // A me function
                getLoginStatus: function(callback) {
                    // get the login status and if user is logged return the user information to the callback
                    callback({
                        access_token: "access_token_got_from_the_app",
                        user: {
                            id: 1,
                            photo: 'users_photo_url',
                            full_name: 'Users full name'
                        }
                    });
                },
                login: function(callback){  
                    // login to the app
                    callback({
                        access_token: "access_token_got_from_the_app",
                        user: {
                            id: 1
                        }
                    });
                },
                autocomplete: function(prefix, callback, autocompleteType) {
                    if (autocompleteType === 'user') {
                        // search for user name that start or contain the prefix
                        var users = [
                            {
                                id: 1,
                                photo: 'photo_url_user1',
                                full_name: 'User 1 that starts with prefix'
                            },
                            {
                                id: 2,
                                photo: 'photo_url_user2',
                                full_name: 'User 2 that starts with prefix'  
                            }
                        ];
                        callback(users);
                    } else if (autocompleteType === 'group') {
                        // search for user name that start or contain the prefix
                        var groups = [
                            {
                                id: 1,
                                photo: 'photo_url_group1',
                                full_name: 'Group 1 that starts with prefix'
                            },
                            {
                                id: 2,
                                photo: 'photo_url_group2',
                                full_name: 'Group 2 that starts with prefix'  
                            }
                        ];
                        callback(groups);
                    }
 
                },
                post: function(groupId, message, tagList, callback) {
                    // this method should post the passage to the group with id groupId
                    // message is a text with {0}, {1}, and so on at the users name position
                    // {0} refers to tagList[0], {1} to tagList[1] and so on.
                    // you should replace these {i} with the given tags
                    // An auxiliar method called formatString is already implemented 
                    // (see the yammer implementation of the post function)
                    callback("post_url");
                }
            };
            break;

ps: If your app does not support group posting, that is fine.. just set post to undefined:

post: undefined

(6) Now that the front end and the backend are implemented you just have to make schedulizer use your app, by editing the app.yml file. Changing the extApp and the extAppClientId property.

extApp: myApp
extAppClientId: myAppClientId

(7) You are all set. Run schedulizer, test it and if everything is working properly create a pull request! :)

Clone this wiki locally