Some things are just better when they are put together: there is Peanut Butter and Chocolate, and now the Force.com platform and Google Wave. This article shall introduce the Force.com Toolkit for Google Wave (affectionately also known as Waveforce), provide step-by-step instructions for getting up and running with the toolkit, and how to build your first WaveForce app. Upon familiar with the basic use of the toolkit, the article will demonstrate an application, WaveForce Workspaces, built with the toolkit to enable real-time collaboration.
During Dreamforce 2009, I co-presented a session titled Get Ready to Ride the Google Wave, with Jeff Eddings from Google (Dan Peterson, Google Wave PM, unfortunately fell sick hours before the session was due to begin). Ever since that time, I could see the possibilities for using Google Wave and Force.com to create some truly game-changing applications. The first of these, presented during that Dreamforce session involved a support 'agent'---a Google Wave robot---interacting with a customer to help solve their issue by using knowledge articles within Salesforce.com. If the customer did not find a satisfactory answer to their question, all they had to do was click a button and a 'real' agent would be added to the wave. It was a fantastic mix of automated customer service, with the option to involve a real person if required.
The possibilities integration with Force.com and Google Wave were clear. What was needed was a way to make it easier for developers to begin creating these collaborative applications. This article, and the Force.com for Google Wave Toolkit intends to address this need. Throughout the article I will often refer to the Force.com for Google Wave Toolkit as Waveforce.
This article will walk through the configuration steps required to use the toolkit, and build a simple Waveforce app which, after being authenticated with Salesforce.com, using oAuth will retrieve a list of contacts. This simple example will touch on many of the key toolkit components, and provide a great starting point for building more sophisticated, collaborative apps. Once familar with the toolkit, we will demostrate (and provide all the code for) another application, Waveforce Workspaces, which leverages the new Google Wave Active Robot API and Force.com to enable a truly collaborative app.
So what is Google App Engine, and Google Wave? According to Wikipedia, Google App Engine, or GAE "is a platform for developing and hosting web applications in Google-managed data centers." This sounds a lot like the Force.com platform, and in particular the recent announcement of VMforce. A complete discussion of what GAE is and what isn't is, and how it relates to Force.com is beyond the scope of this article. Needless to say, GAE is a popular cloud platform, and most importantly for the sake of Waveforce, GAE is where Google Wave extensions (see below) are deployed. In my experience, the best applications, are those that focus on convergent technologies. Connecting clouds such as GAE and the Force.com platform is one such convergence with massive potential.
Google Wave, is a revolutionary approach to communication. Unlike email, which requires messages to sent back and forth with the context of the conversation often buried somewhere in the string of responses, Google Wave maintains the conversation in the cloud: you can easily reply to a conversation, add a new participant who can view the discussions he or she missed, and what's more you can extend the experience by leveraging Gadgets and Robots. For convenience, these Gadgets and Robots are often deployed in GAE (though that's not a requirement)
We are going to talking a lot about Google Wave, so a quick primer of some key terms will help. If you want a deeper understanding of what Google Wave is check out http://wave.google.com. The terms and concepts below have been included because they are relevant to Waveforce, and will assist in understanding what the toolkit is, and how it works.
A Wave contains the conversation. Participants can be added and removed. For the toolkits perspective, we can group participants into two groups: Salesforce users, and external users. All users will have a @googlewave.com address---like a email address for Google Wave. Salesforce users, for example may have their @googlewave.com address added as a custom field on the User object.
Robots are automated participants within a wave. They can respond to events raised from the Wave when participants add a message, buttons are clicked etc. The Active Robot API, provides the ability to create new waves. (We will cover the Active Robot API in part 2. For now, knowing that it is possible should be sufficient to start your mind ticking with ideas). The WaveForce toolkit provides an Agent Framework for separating much of the Salesforce vs. Robot logic, and encapsulates activities to make building applications easier, and more maintainable.
A blip is a snippet of conversation within a wave. Robots can respond to blips, take actions based on their content etc.
Now that we have a general understanding of GAE, and Google Wave, it is time to get familiar with the components of Waveforce. The following diagram provides a high level depiction of the toolkit, and it's relationship, and dependencies on other technologies.
Waveforce relies on the Force.com Toolkit for GAE toolkit for access to the Force.com SOAP API from within Google App Engine Applications (Google Wave Robots, and Gadgets fall into this category). More information regarding the Force.com for GAE Toolkit can be found here.
A series of Utility classes have been provided in the toolkit. These classes built upon the Force.com for GAE toolkit to perform common salesforce, and Google Wave functions such as creating records, querying Salesforce, and formating/retriving Wave Ids. The utility classes leverage the partner libraries ( as provided by the Force.com for GAE Toolkit). Utilizing the partner libraries, and in particular generic SObjects, makes your project much easier to extend, and be portable as you are not using strongly typed objects. (as generated from the Salesforce.com Enterprise WSDL)
oAuth provides a standard approach for authorization, and removes the requirement for spreading passwords around, and storing them in config, or property files. In respects to Waveforce, oAuth is used by the Agent Framework to authorize Wave users to connect to Salesforce.com in a secure manner. The oAuth implementation provided in the toolkit utilizes GAE caching mechanisms to make store oAuth tokens and sessions on a per Wave user basis. What this means is that during a conversation within Google Wave, each user who wishes to interact with Salesforce must authorize individually. Such a use case demonstrates the power of oAuth; Without such an API, users would have have to provide usernames and passwords to an application who would do little more than *login* on the users behalf. The result would be the potential compromise of a user's credentials.
For a great introduction to oAuth, be sure to check out the getting started guide provided on oAuth.net, or the article by Jeff Douglas on http://developer.force.com. Much of the code for the oAuth implementation in the toolkit was provided by Jeff, and extended to support authorization based on individual Wave addressed.
The Agent Framework provides an architectural pattern (the Command Pattern) for rapidly creating classes that are loosely coupled with Google Wave Robots. The Agent Framework is made up of the following classes:
The intent is that developers will create concrete instances of SFDCAgent to encapsulate interaction logic with Salesforce.com. The ContactsAgent is a simple agent we will build soon, which demonstrates authenticating against Salesforce.com and listing Contacts
The final setup item you need to do to get started with the toolkit is to retrieve the code from Code Share and sync it into your project. If you are using Eclipse, Subclipse works great, and is the tool I used throughout this article. The repository details should like something like:
Once configured, expand the repository until you see trunk-->My First Waveforce. Right Checkout. Select "Check out as a project in the workspace", then click finish. Make sure the type of project is a Google Web App, and uncheck "Use Google Web Toolkit"
Finish the wizard and you should end up with a new Google Web Application Project with the basic components of the toolkit installed. This project already includes all the dependent libraries required, but libraries change regularly, and should be retrieved 'fresh' when you first create your project. The following steps show you how.
With your web project in place, you will need to retrieve the libraries provided in the Force.com Toolkit for Google App Engine (GAE). As indicated previously, these libraries provide the connectivity to Salesforce. Follow the instructions provided in the Force.com for Google App Engine. All you need from the Force.com Toolkit for GAE is the jar files provided for download. It should be noted that the Force.com for Google Wave Toolkit only uses the partner libraries, and not the enterprise libraries. Utilizing the partner libraries, and in particular generic SObjects, makes your project much easier to extend, and be portable as you are not using strongly typed objects. In my project, I have named the Salesforce partner jar to be partner-18.jar to indicate which version of the api this jar relates to.
Next, we have to retrieve the oAuth libraries from oAuth.net. Once you have the libraries (my jar is called oauth-20090617.jar, but by the time of publication, there may be a never version, and the datestamp on the jar file may be different to what I have here.) drop them into your WEB-INF/lib folder (the same place you dropped the Google App Engine libraries.)
At this point you should have a working Google App Engine project that includes the basic requirements for connecting to Salesforce, oAuth libraries and the Force.com for Google Wave Toolkit code. Take a break, give yourself a pat on the back. When you are ready, lets build something.
The toolkit comes pre-configured with a Robot called MyFirstRobot. You can find it in the com.sforce.waveforce package. This robot is a pretty typical of a Google Wave robot which you can read more about here. We are going to assume you are already familiar with Google Wave Robots and look at what is different. The intent of this robot is to respond to a button click and fetch contacts from Salesforce. If the user is not authenticated with Salesforce, they will be prompted to do so.
The first thing you will notice is a call within the init() method to get an agent from the AgentFactory:
This class is a simple Factory pattern that removes the requirement for concrete implementations of Agents vs. an Interface to be included in a robot. In our simple example, our Factory returns a concrete instance of ContactsFactory, but we can work with it as if it was a the Agent Interface.
The next section to look at is the onFormButtonClicked event. Here we see why using an interface (in this instance we are using the Command Pattern) is really helpful. The code doesn't need to know we are working with a ContactsFactory, just that the interface method is available.
ContactsAgent demonstrates the typical pattern for implementing Agents. Of importance in the ContactsAgent example is the authorization check which will result in a Google Gadget being displayed and rendered for the user to click on. Using the agent framework handles the authorization for you as long as you follow the example contained in ContactsAgent.
The last thing you need to do before uploading your robot is to configure the web.xml file. Robots are basically servlets in the end, and as such their configuration is handled the same way as you would expect a servlet to be. In our example, we also include two init-params to avoid hardcoding server names into our robot. Your servlet section should look something like this:
You will also notice another series of servlets defined by default in the web.xml included in the toolkit. These servlets handle the oAuth conversation when connecting back to Salesforce.com. You should not need to change these settings at all.
In addition to the servlet settings, the oAuth implementation relies on being able to render a Gadget within the wave. This gadget address is set to your webapp address + "/gadgets/auth/auth.xml". The gadget is already provided under the war/gadgets/auth folder in the sample webapp and will need a minor change before you can use it. You will need to set the window.open url to be that of your GAE application. For the sample application the line will look like this:
window.open("https://simplewaveforce.appspot.com/login?uid="+user, "WaveForce ", "menubar=0, toolbar=0, width=800, height=800");
Notice the name of my GAE application, simplewaveforce is set in the URL.
There is a few more change we need to make before our oAuth is setup, and that is to set the correct callback url, and consumer key and secret. These values are defined as static String in the class com.sforce.waveforce.sfdc.oauth.OauthSettings. Let's start with the URL_CALLBACK. This needs to be set to the following "https://yourapplication.appspot.com/callback", where you replace your application with the name of your deployed GAE application. In my case, this is simplewaveforce.
Now onto the CONSUMER_KEY and CONSUMER_SECRET. These values are retrieved from Salesforce under Setup | Remote Access. Create a new remote access, setting your callback url to that which we just defined. Click save and you will be presented with the consumer key and secret. Copy and paste these into OauthSettings.
We are almost there. Before you can interact with your new Robot you must upload the web project to Google App Engine. Instructions for how to do this are provided on the Google App Engine site. This site also includes a lot of information developers should become familiar with including how to access your applications log files should something go wrong.
Once your web app is deployed, you need to add your robot to a wave conversation. Your robots name will the same as the appengine Application you created with @appengine.com appended to it. In my instance the application name is "simplewaveforce", so my robots address is "[email protected]"
And that's it you are done! By this point, if you log into Google Wave you should be able to interact with your robot, and communicate securely with Salesforce.
So far, everything in this tutorial and toolkit has focused on the notion of creating a wave and adding a participant assuming you are currently logged into Google Wave via the standard interface. Google Wave however supports a number of other options for interacting with Waves; specifically the Embed API, and the Active Robot API. A complete discussion of these APIs is beyond the scope of this article but in order to demonstrate the power and potential of combining Google Wave and Salesforce, another sample application, Waveforce Workspaces has been created and available via Code Share. This Code Share project contains the Google App Engine code which includes a new robot, WorkspaceRobot, and a Java Servlet, Waveforce_WorkspaceServlet which can be called via a HTTP Post request to create a new wave utilizing the Active Robot Api.
Deploying the Application into GAE is the same as the simple wave example provided earlier in this article, with the one addition: In order for a Wave to be called via the Active Robot API, it must be setup to support oAuth with GAE. This is different from the oAuth between GAE and Salesforce. Follow the Active Robot Docs on how to Authenticate your Robots.
In addition to the deployed GAE app, you will need to install the Force.com package (click here to install.) This package includes a Visualforce page, and Controller which can communicate with the servlet indicated above. Once you have installed the package, you will need to add the appspot url of your GAE application as a remote site in Force.com:
The package installs two custom objects, WaveforceWorkspace__c and WaveforceWorkspaceParticipants__c. The Workspace is a 'handle' to a Google Wave conversation and the the Participants are Salesforce Users who have a @googlewave.com address on their User record (the package also installs a custom field on the User object to handle this requirement). In addition to being the handle to a Wave, the Workspace object contains an Endpoint URL. This Endpoint URL must point to the url of the GAE Java Servlet, Waveforce_WorkspaceServlet, you deployed previously. If you kept the naming convention that came with the project, the URL will be something similar to: http://myappname.appspot.com/wfw (Remember to add http://myappname.appspot.com as a valid Remote Site within Salesforce!)
The Force.com Toolkit for Google Wave provides the framework for building Salesforce enabled Waves. In particular, the inclusion of a ready-to-go oAuth implementation for working with Google Wave, Google App Engine, and Salesforce.com, one of the biggest barriers to entry---security---have been addressed in the toolkit.
The code contained within this article, and the associated toolkit is intended to be a starting point to get you up and running quickly so you can build your own apps. One such app Waveforce Workspaces, takes advantage of the powerful collaboration capabilities of Salesforce Chatter and Google Wave.
Download the code, build your Robots, Salesforce aware agents and start connecting the clouds!
Quinton Wall is a Developer Evangelist at Salesforce.com, and a aspiring fantasy author. He is a regular speaker at cloud events, contributor to the developer blogs, and twittersphere. When he is not working with the Force.com platform, or writing books, you can find him on the web.
Special thanks to Jeff Douglas from Appirio for a lot of the oauth code included in the Toolkit.