communicator
A simple communication layer to keep database records in sync between two Rails apps.
Setup
Install in Rails apps by adding this to your Gemfile:
gem 'communicator'
Import rake tasks in your Rails.root/Rakefile:
require 'communicator/tasks'
Set up the database tables for the messages by importing the corresponding migrations from the gem:
$ rake communicator:update_migrations
$ rake db:migrate
After doing these steps, you can proceed to configure either the server or client. On both sides, you’ll have to configure the client and server. You can do so by placing a configuration file in Rails.root/config/communicator.yml that looks somewhat like this:
defaults: &defaults
username: communicator
password: verysecret
base_uri: localhost:3001 # Can be ommitted for server config
test:
<<: *defaults
development:
<<: *defaults
production:
<<: *defaults
password: Uber!Secret
base_uri: 192.168.0.104:4000 # Can be ommitted for server config
The configuration for the current ‘Rails.env` will then be automatically loaded when you `require ’communicator’‘.
You can also skip the YAML configuration and set up the credentials programmatically:
Communicator::Server.username = 'foo'
Communicator::Server.password = 'bar'
Communicator::Client.username = 'foo'
Communicator::Client.password = 'bar'
Communicator::Client.base_uri 'localhost:1234'
Server side
On the server side, you can mount the server component in a Rails 2.3 app as a rack middleware inside environment.rb:
require 'communicator'
config.middleware.use 'Communicator::Server'
It will then be mounted at /messages.json for GET and POST requests, requesting HTTP Basic Auth with the configured credentials.
Client side
Tell the client the server url and port as well as the auth credentials inside your environment.rb:
require 'communicator'
When everything’s fine, you should be able to push and pull using the client:
Communicator::Client.push
Communicator::Client.pull
Active Record integration
To keep models in sync, specify the model class (in underscored type) the local class receives updates from like this:
class Post < ActiveRecord::Base
receives_from :post
end
If you want to skip some remote attributes and not let them progapate into local instances, use ‘receives_from :post, :except => [:user_id]`.
Attributes that are not physically present in the local database will be skipped automatically.
Use the automatically added ‘publish` instance method on your models to push changes to the other side. They will be enqueued in the local `outbound_messages` table and will arrive at the other side when a client pulls or pushes.
When an update is received from a remote side, the message will be stored in ‘inbound_messages` and the received changes will be applied to the local record, either updating existing or creating new records.
Compatibility
Communicator is currently only proven to work on Rails 2 apps using either REE, 1.8.7, 1.9.1 or 1.9.2.
Note on Patches/Pull Requests
-
Fork the project.
-
Make your feature addition or bug fix.
-
Add tests for it. This is important so I don’t break it in a future version unintentionally.
-
Commit, do not mess with rakefile, version, or history. (if you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull)
-
Send me a pull request. Bonus points for topic branches.
Copyright
Copyright © 2010 Capita Unternehmensberatung GmbH. See LICENSE for details.