Rhosync is a Ruby-based server to facilitate accessing information from backend applications and keeping that information
in sync with occasionally connected mobile devices. Specifically it is a Ruby on Rails application that allows managing groups of application objects exposed by a web service. The RhoSync server then manages synchronization of that information to and from mobile devices.
RhoSync retrieves data via web services (REST or SOAP) from backend enterprise applications for distribution to downstream mobile devices. It keeps a master store of all enterprise application data and keeps track of the information that users have received. It is written to be far simpler to be far simpler to deploy and configure than similar technologies that have come and gone over the past 20 years.
It is also more focused on the complete end to end ‘web service backend’ to mobile device (with an enabling master data store on the server) than earlier equivalents. These products were generally focused on the device endpoint syncing to a server-based database. With the success of Software as a Service (SaaS) products such as SugarCRM and SalesForce, synchronization directly to a server database is much more rarely a viable option. Instead we focus on the web service access scenario. RhoSync is also focused on arbitrary enterprise application data as opposed to being a PIM and email focused product such as Funambol.
There is a RhoSync client embedded in the Rhodes runtime, but other RhoSync clients could be created.
- Ruby w/ rubygems installed
- SQLite, MySQL or other database that plays nicely with Rails
Install your database driver of choice
sudo gem install sqlite3-ruby (-v=1.2.3 if you’re in windows) or sudo gem install msyqlIf you don’t have the file “log/development.log” then go ahead and create the file:
mkdir -p log; touch log/development.log (or create manually if in windows)Install required gems
sudo rake gems:installConfigure config/database.yml to tell rails how to connect to your database:
config/database.ymlThen run the db:bootstrap rake task provided, creating the database and associated tables that RhoSync needs. It will also load the source adapters that we ship with.
rake db:bootstrap
Then use your Rails server of choice to run the application. If you don’t have a Rails server, you can install mongrel with:
sudo gem install mongrel
Then start your server:
script/server
Then you can view the Sources from your web browser:
http://localhost:3000
If you login as “admin” (or create an account with the name “admin” by registering) you will see the default applications that RhoSync ships with (SugarCRM and Siebel), since they are by default owned by “admin”. Each of these has sync data sources associated with it.
h2. SET UP A DATA SOURCE
* Edit the “login”, “password” and “URL” fields if you are using one of the existing sources for SugarCRM or Siebel to correspond to your own URL
* Otherwise create a new Source from the application form and edit those same fields.
* If you are using another backend you will need to create an application and populate it with some data sources
* On the Source editing form supply Source Adapter class, the file for which must be located in the RhoSync /lib subdirectory
* OR you can create individual login, query, create, update and delete fields with the appropriate code. These methods (from the Source Adapter class or the form) will get called by the RhoSync server to populate data from a data source.
h2. HOW IT WORKS
Rhosync normalizes all backend application data into a common server-based database schema, in preparation for delivering the further downstream, generally to mobile devices.
Specifically the “master server data table” is a “property bag” (also known as an “entity-attribute-value” or EAV) model, which keeps track of data sources, individual objects and the name/value pairs for those objects. This allows handling of diverse backend application data structures within a single master store. It also provides for efficient delivery of single “fields” of data in either direction (e.g. just the status changing of a trouble ticket).
The connection code for logging into a backend application (via REST or SOAP APIs), calling the data retrieval, create, update and delete functions, logging off, and populating the master data table (OBJECT_VALUES described below) are each written in Ruby.
h2. DATABASE SCHEMA
There are three important tables that describe fully the universe of data sources and their contents for downstream syncing. These are the APPLICATIONS table, the SOURCES table and the OBJECT_VALUES table (and the corresponding Source and ObjectValues models).
h3. APPLICATIONS TABLE
A RhoSync Application is a grouped set of data source objects. It has the following columns:
* NAME – some string to identify the app
* DESCRIPTION – some text to describe the collection of source
* ADMIN (not exposed in the UI) – who “owns” the app, set to whoever created the app automatically by the RhoSync web UI
h3. SOURCES TABLE
This table contains all of the information necessary to connect to a given backend application object:
* URL – the URL to connect to (for REST adapters) or the URL to the WSDL (for SOAP services)
* SERVER – OPTIONAL a logical name for the data source server (AcmeCorpSugar)
* LOGIN – the username or logon ID for the backend
* PASSWORD – password (stored in the clear right now) for the backend system
* SOURCE ADAPTER – this is the name of a class used for login, query, create, update and delete operations. The Ruby file for this class needs to be placed in the /lib subdirectory of your RhoSync installation.
OR you can enter all of the code for each of the methods in the fields below
* LOGIN – a set of Ruby code generally for logging into the backend system. Generally this is a SOAP or REST call which populates a session_id variable (that variable must be used in the call code below).
* CALL – the actual code for getting data back (generally uses the session_id acquired in the prolog)
* CREATECALL – code to create records in the backend from the object values table
* UPDATECALL – update code for the backend
* DELETECALL – record deletion code for the backend
* LOGOUT – OPTIONAL, code to logoff the backend system
* SYNC – this is the code used to take apart the returned data and stuff it into the OBJECT_VALUES property bag table.
* APP_ID (not exposed in the UI) – this refers to the application that contains the data source
h3. OBJECT_VALUES
Thid table contains all of the actual instance data for all applications and sources.
* object – the unique identifier of the object (generally an integer “record ID” from the backend system)
* attribute – the name of the attribute (e.g. “Account Name”, “Industry”)
* value – the value of the attribute (e.g. “Acme Corp”, “software”)
* source_id – reference back to the source (see below) used for syncing
h2. GENERATING A SOURCE ADAPTER
The RhoGen utility supplied by Rhodes will generate a RhoSync Source Adapter class. For example:
rhogen source SugarAccounts
h2. SAMPLE SOURCE ADAPTER
This is a sample source adapter Rub class to retrieve and edit Sugar Account objects. It is the SugarAccounts.rb located in the /lib subdirectory of RhoSync.
class SugarAccounts < SourceAdapter
def initialize(source)
super(source)
end
def login
u =
source.login
p = Digest::MD5.hexdigest(
source.password)ua = {’user_name’ => u,‘password’ => p}
ss = client.login(ua,nil)
if ss.error.number.to_i != 0
p ‘failed to login – #{ss.error.description}’
return
else
session_id = ss['id']
uid = client.get_user_id(
session_id)end
end
def query
module_name = ‘Accounts’
query = ‘’ # gets all the acounts, you can also use SQL like ’accounts.name like ’%company%’’
order_by = ‘’ # in default order. you can also use SQL like ’accounts.name’
offset = 0
select_fields = [‘name’,‘industry’] # this can’t be an empty array
max_results = ‘10000’ # if set to 0 or ‘’, this doesn’t return all the results
deleted = 0 # whether you want to retrieve deleted records, too
result = client.get_entry_list(
session_id,module_name,query,order_by,offset,select_fields,max_results,deleted);end
def sync
result.entry_list.each do |x|
x.name_value_list.each do |y|
o=ObjectValue.new
o.source_id=
source.ido.object=x[‘id’]
o.attrib=y.name
o.value=y.value
o.save
end
end
end
def create(name_value_list)
result=client.set_entry(@session_id,‘Accounts’,name_value_list)
end
def update(name_value_list)
result=client.set_entry(@session_id,‘Accounts’,name_value_list)
end
def delete(name_value_list)
name_value_list.push({’name’=>’deleted’,‘value’=>’1’});
result=client.set_entry(@session_id,‘Accounts’,name_value_list)
end
def logoff
client.logout(@session_id)
end
end
h2. SUPPORT
Email us questions or, even better, post them to the Google Group called Rhomobile.