rubysync 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/bin/rubysync +312 -0
- data/examples/ar_client_webapp/README +182 -0
- data/examples/ar_client_webapp/Rakefile +10 -0
- data/examples/ar_client_webapp/app/controllers/application.rb +7 -0
- data/examples/ar_client_webapp/app/controllers/user_controller.rb +5 -0
- data/examples/ar_client_webapp/app/helpers/application_helper.rb +3 -0
- data/examples/ar_client_webapp/app/helpers/user_helper.rb +2 -0
- data/examples/ar_client_webapp/app/models/user.rb +2 -0
- data/examples/ar_client_webapp/config/boot.rb +45 -0
- data/examples/ar_client_webapp/config/database.yml +36 -0
- data/examples/ar_client_webapp/config/environment.rb +60 -0
- data/examples/ar_client_webapp/config/environments/development.rb +21 -0
- data/examples/ar_client_webapp/config/environments/production.rb +18 -0
- data/examples/ar_client_webapp/config/environments/test.rb +19 -0
- data/examples/ar_client_webapp/config/routes.rb +23 -0
- data/examples/ar_client_webapp/db/migrate/001_create_users.rb +13 -0
- data/examples/ar_client_webapp/db/schema.rb +13 -0
- data/examples/ar_client_webapp/doc/README_FOR_APP +2 -0
- data/examples/ar_client_webapp/public/404.html +30 -0
- data/examples/ar_client_webapp/public/500.html +30 -0
- data/examples/ar_client_webapp/public/dispatch.cgi +10 -0
- data/examples/ar_client_webapp/public/dispatch.fcgi +24 -0
- data/examples/ar_client_webapp/public/dispatch.rb +10 -0
- data/examples/ar_client_webapp/public/favicon.ico +0 -0
- data/examples/ar_client_webapp/public/images/rails.png +0 -0
- data/examples/ar_client_webapp/public/index.html +277 -0
- data/examples/ar_client_webapp/public/javascripts/application.js +2 -0
- data/examples/ar_client_webapp/public/javascripts/controls.js +833 -0
- data/examples/ar_client_webapp/public/javascripts/dragdrop.js +942 -0
- data/examples/ar_client_webapp/public/javascripts/effects.js +1088 -0
- data/examples/ar_client_webapp/public/javascripts/prototype.js +2515 -0
- data/examples/ar_client_webapp/public/robots.txt +1 -0
- data/examples/ar_client_webapp/script/about +3 -0
- data/examples/ar_client_webapp/script/breakpointer +3 -0
- data/examples/ar_client_webapp/script/console +3 -0
- data/examples/ar_client_webapp/script/destroy +3 -0
- data/examples/ar_client_webapp/script/generate +3 -0
- data/examples/ar_client_webapp/script/performance/benchmarker +3 -0
- data/examples/ar_client_webapp/script/performance/profiler +3 -0
- data/examples/ar_client_webapp/script/plugin +3 -0
- data/examples/ar_client_webapp/script/process/inspector +3 -0
- data/examples/ar_client_webapp/script/process/reaper +3 -0
- data/examples/ar_client_webapp/script/process/spawner +3 -0
- data/examples/ar_client_webapp/script/runner +3 -0
- data/examples/ar_client_webapp/script/server +3 -0
- data/examples/ar_client_webapp/test/fixtures/users.yml +5 -0
- data/examples/ar_client_webapp/test/functional/user_controller_test.rb +18 -0
- data/examples/ar_client_webapp/test/test_helper.rb +28 -0
- data/examples/ar_client_webapp/test/unit/user_test.rb +10 -0
- data/examples/ar_webapp/README +1 -0
- data/examples/ar_webapp/Rakefile +10 -0
- data/examples/ar_webapp/app/controllers/application.rb +7 -0
- data/examples/ar_webapp/app/controllers/hobbies_controller.rb +10 -0
- data/examples/ar_webapp/app/controllers/interests_controller.rb +9 -0
- data/examples/ar_webapp/app/controllers/people_controller.rb +14 -0
- data/examples/ar_webapp/app/controllers/ruby_sync_associations_controller.rb +10 -0
- data/examples/ar_webapp/app/helpers/application_helper.rb +3 -0
- data/examples/ar_webapp/app/models/hobby.rb +5 -0
- data/examples/ar_webapp/app/models/interest.rb +6 -0
- data/examples/ar_webapp/app/models/person.rb +9 -0
- data/examples/ar_webapp/app/models/ruby_sync_association.rb +5 -0
- data/examples/ar_webapp/app/models/ruby_sync_event.rb +9 -0
- data/examples/ar_webapp/app/models/ruby_sync_observer.rb +28 -0
- data/examples/ar_webapp/app/models/ruby_sync_operation.rb +20 -0
- data/examples/ar_webapp/app/models/ruby_sync_state.rb +2 -0
- data/examples/ar_webapp/app/models/ruby_sync_value.rb +7 -0
- data/examples/ar_webapp/app/views/layouts/application.rhtml +19 -0
- data/examples/ar_webapp/app/views/people/show.rhtml +18 -0
- data/examples/ar_webapp/config/boot.rb +45 -0
- data/examples/ar_webapp/config/database.yml +36 -0
- data/examples/ar_webapp/config/environment.rb +61 -0
- data/examples/ar_webapp/config/environments/development.rb +21 -0
- data/examples/ar_webapp/config/environments/production.rb +18 -0
- data/examples/ar_webapp/config/environments/test.rb +19 -0
- data/examples/ar_webapp/config/routes.rb +23 -0
- data/examples/ar_webapp/db/migrate/001_create_people.rb +12 -0
- data/examples/ar_webapp/db/migrate/002_create_interests.rb +12 -0
- data/examples/ar_webapp/db/migrate/003_create_hobbies.rb +11 -0
- data/examples/ar_webapp/db/migrate/004_create_ruby_sync_associations.rb +18 -0
- data/examples/ar_webapp/db/migrate/005_create_ruby_sync_events.rb +16 -0
- data/examples/ar_webapp/db/migrate/006_create_ruby_sync_operations.rb +15 -0
- data/examples/ar_webapp/db/migrate/007_create_ruby_sync_values.rb +12 -0
- data/examples/ar_webapp/db/migrate/008_ruby_sync_tracking.rb +16 -0
- data/examples/ar_webapp/db/migrate/009_create_ruby_sync_states.rb +10 -0
- data/examples/ar_webapp/db/schema.rb +56 -0
- data/examples/ar_webapp/doc/README_FOR_APP +2 -0
- data/examples/ar_webapp/public/404.html +30 -0
- data/examples/ar_webapp/public/500.html +30 -0
- data/examples/ar_webapp/public/dispatch.cgi +10 -0
- data/examples/ar_webapp/public/dispatch.fcgi +24 -0
- data/examples/ar_webapp/public/dispatch.rb +10 -0
- data/examples/ar_webapp/public/favicon.ico +0 -0
- data/examples/ar_webapp/public/images/rails.png +0 -0
- data/examples/ar_webapp/public/index.html +277 -0
- data/examples/ar_webapp/public/javascripts/application.js +2 -0
- data/examples/ar_webapp/public/javascripts/controls.js +833 -0
- data/examples/ar_webapp/public/javascripts/dragdrop.js +942 -0
- data/examples/ar_webapp/public/javascripts/effects.js +1088 -0
- data/examples/ar_webapp/public/javascripts/prototype.js +2515 -0
- data/examples/ar_webapp/public/robots.txt +1 -0
- data/examples/ar_webapp/script/about +3 -0
- data/examples/ar_webapp/script/breakpointer +3 -0
- data/examples/ar_webapp/script/console +3 -0
- data/examples/ar_webapp/script/destroy +3 -0
- data/examples/ar_webapp/script/generate +3 -0
- data/examples/ar_webapp/script/performance/benchmarker +3 -0
- data/examples/ar_webapp/script/performance/profiler +3 -0
- data/examples/ar_webapp/script/plugin +3 -0
- data/examples/ar_webapp/script/process/inspector +3 -0
- data/examples/ar_webapp/script/process/reaper +3 -0
- data/examples/ar_webapp/script/process/spawner +3 -0
- data/examples/ar_webapp/script/runner +3 -0
- data/examples/ar_webapp/script/server +3 -0
- data/examples/ar_webapp/test/fixtures/association_keys.yml +5 -0
- data/examples/ar_webapp/test/fixtures/hobbies.yml +5 -0
- data/examples/ar_webapp/test/fixtures/interests.yml +5 -0
- data/examples/ar_webapp/test/fixtures/people.yml +9 -0
- data/examples/ar_webapp/test/fixtures/ruby_sync_events.yml +5 -0
- data/examples/ar_webapp/test/fixtures/ruby_sync_operations.yml +5 -0
- data/examples/ar_webapp/test/fixtures/ruby_sync_states.yml +5 -0
- data/examples/ar_webapp/test/fixtures/ruby_sync_values.yml +5 -0
- data/examples/ar_webapp/test/test_helper.rb +28 -0
- data/examples/ar_webapp/test/unit/association_key_test.rb +8 -0
- data/examples/ar_webapp/test/unit/hobby_test.rb +10 -0
- data/examples/ar_webapp/test/unit/interest_test.rb +10 -0
- data/examples/ar_webapp/test/unit/person_test.rb +10 -0
- data/examples/ar_webapp/test/unit/ruby_sync_event_test.rb +12 -0
- data/examples/ar_webapp/test/unit/ruby_sync_observer_test.rb +57 -0
- data/examples/ar_webapp/test/unit/ruby_sync_operation_test.rb +10 -0
- data/examples/ar_webapp/test/unit/ruby_sync_state_test.rb +10 -0
- data/examples/ar_webapp/test/unit/ruby_sync_value_test.rb +10 -0
- data/examples/ims2/connectors/hr_db_connector.rb +8 -0
- data/examples/ims2/connectors/my_csv_connector.rb +12 -0
- data/examples/ims2/pipelines/hr_import_pipeline.rb +33 -0
- data/examples/my_ims/connectors/corp_directory_connector.rb +12 -0
- data/examples/my_ims/connectors/finance_connector.rb +7 -0
- data/examples/my_ims/connectors/hr_db_connector.rb +7 -0
- data/examples/my_ims/pipelines/finance_pipeline.rb +33 -0
- data/examples/my_ims/pipelines/hr_import_pipeline.rb +29 -0
- data/lib/ruby_sync/connectors/active_record_connector.rb +198 -0
- data/lib/ruby_sync/connectors/base_connector.rb +317 -0
- data/lib/ruby_sync/connectors/connector_event_processing.rb +78 -0
- data/lib/ruby_sync/connectors/csv_file_connector.rb +95 -0
- data/lib/ruby_sync/connectors/file_connector.rb +74 -0
- data/lib/ruby_sync/connectors/ldap_connector.rb +192 -0
- data/lib/ruby_sync/connectors/memory_connector.rb +185 -0
- data/lib/ruby_sync/event.rb +220 -0
- data/lib/ruby_sync/operation.rb +82 -0
- data/lib/ruby_sync/pipelines/base_pipeline.rb +360 -0
- data/lib/ruby_sync/util/metaid.rb +24 -0
- data/lib/ruby_sync/util/utilities.rb +115 -0
- data/lib/ruby_sync.rb +81 -0
- data/test/hashlike_tests.rb +111 -0
- data/test/ruby_sync_test.rb +48 -0
- data/test/test_active_record_vault.rb +113 -0
- data/test/test_csv_file_connector.rb +75 -0
- data/test/test_event.rb +40 -0
- data/test/test_ldap_connector.rb +89 -0
- data/test/test_memory_connectors.rb +40 -0
- data/test/ts_rubysync.rb +20 -0
- metadata +316 -0
@@ -0,0 +1 @@
|
|
1
|
+
# See http://www.robotstxt.org/wc/norobots.html for documentation on how to use the robots.txt file
|
@@ -0,0 +1,28 @@
|
|
1
|
+
ENV["RAILS_ENV"] = "test"
|
2
|
+
require File.expand_path(File.dirname(__FILE__) + "/../config/environment")
|
3
|
+
require 'test_help'
|
4
|
+
|
5
|
+
class Test::Unit::TestCase
|
6
|
+
# Transactional fixtures accelerate your tests by wrapping each test method
|
7
|
+
# in a transaction that's rolled back on completion. This ensures that the
|
8
|
+
# test database remains unchanged so your fixtures don't have to be reloaded
|
9
|
+
# between every test method. Fewer database queries means faster tests.
|
10
|
+
#
|
11
|
+
# Read Mike Clark's excellent walkthrough at
|
12
|
+
# http://clarkware.com/cgi/blosxom/2005/10/24#Rails10FastTesting
|
13
|
+
#
|
14
|
+
# Every Active Record database supports transactions except MyISAM tables
|
15
|
+
# in MySQL. Turn off transactional fixtures in this case; however, if you
|
16
|
+
# don't care one way or the other, switching from MyISAM to InnoDB tables
|
17
|
+
# is recommended.
|
18
|
+
self.use_transactional_fixtures = true
|
19
|
+
|
20
|
+
# Instantiated fixtures are slow, but give you @david where otherwise you
|
21
|
+
# would need people(:david). If you don't want to migrate your existing
|
22
|
+
# test cases which use the @david style and don't mind the speed hit (each
|
23
|
+
# instantiated fixtures translates to a database query per test method),
|
24
|
+
# then set this back to true.
|
25
|
+
self.use_instantiated_fixtures = false
|
26
|
+
|
27
|
+
# Add more helper methods to be used by all tests here...
|
28
|
+
end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/../test_helper'
|
2
|
+
|
3
|
+
class RubySyncEventTest < Test::Unit::TestCase
|
4
|
+
fixtures :ruby_sync_events
|
5
|
+
|
6
|
+
# Replace this with your real tests.
|
7
|
+
def test_event_type
|
8
|
+
assert_nil RubySyncEvent.find_by_event_type(:add), "Already add events"
|
9
|
+
event = RubySyncEvent.create :event_type=>:add
|
10
|
+
assert_not_nil event = RubySyncEvent.find_by_event_type(:add), "Add event not created"
|
11
|
+
end
|
12
|
+
end
|
@@ -0,0 +1,57 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/../test_helper'
|
2
|
+
|
3
|
+
class RubySyncObserverTest < Test::Unit::TestCase
|
4
|
+
fixtures :people
|
5
|
+
|
6
|
+
def test_destroy
|
7
|
+
assert_nil RubySyncEvent.find_by_event_type('delete'), "Delete events already present"
|
8
|
+
Person.destroy people('bob')
|
9
|
+
event = RubySyncEvent.find_by_event_type 'delete'
|
10
|
+
assert_not_nil event, "Delete event not created on destroy"
|
11
|
+
assert_equal people('bob').id, event.trackable_id
|
12
|
+
assert_equal 'Person', event.trackable_type
|
13
|
+
end
|
14
|
+
|
15
|
+
|
16
|
+
def test_add
|
17
|
+
assert_nil RubySyncEvent.find_by_event_type('add'), "Add events already present"
|
18
|
+
p = Person.create(:first_name=>"Ritchie", :last_name=>"Young")
|
19
|
+
event = RubySyncEvent.find_by_event_type 'add'
|
20
|
+
assert_not_nil event, "Add event not created on create"
|
21
|
+
assert_equal p.id, event.trackable_id
|
22
|
+
assert_equal 'Person', event.trackable_type
|
23
|
+
# Ensure the fields were populated correctly
|
24
|
+
fn = event.operations.find_by_operation_and_field_name 'add', 'first_name'
|
25
|
+
assert_not_nil fn, "No add first_name operation"
|
26
|
+
assert_equal 1, fn.values.length
|
27
|
+
assert_equal "Ritchie", fn.values[0].value
|
28
|
+
fn = event.operations.find_by_operation_and_field_name 'add', 'last_name'
|
29
|
+
assert_not_nil fn, "No add last_name operation"
|
30
|
+
assert_equal 1, fn.values.length
|
31
|
+
assert_equal "Young", fn.values[0].value
|
32
|
+
#TODO: Add support for multi-value fields (AKA has_many associations)
|
33
|
+
end
|
34
|
+
|
35
|
+
|
36
|
+
def test_modify
|
37
|
+
assert_nil RubySyncEvent.find_by_event_type('modify'), "Modify events already present"
|
38
|
+
p = Person.find people('bob').id
|
39
|
+
assert_not_nil p, "Couldn't find bob"
|
40
|
+
p.first_name = "Mary"
|
41
|
+
p.save
|
42
|
+
event = RubySyncEvent.find_by_event_type 'modify'
|
43
|
+
assert_not_nil event, "Modify event not created on save"
|
44
|
+
assert_equal people('bob').id, event.trackable_id
|
45
|
+
assert_equal 'Person', event.trackable_type
|
46
|
+
# Ensure the fields were populated correctly
|
47
|
+
fn = event.operations.find_by_operation_and_field_name 'replace', 'first_name'
|
48
|
+
assert_not_nil fn, "No replace first_name operation"
|
49
|
+
assert_equal 1, fn.values.length
|
50
|
+
assert_equal "Mary", fn.values[0].value
|
51
|
+
#TODO: Add support for multi-value fields (AKA has_many associations)
|
52
|
+
end
|
53
|
+
|
54
|
+
|
55
|
+
|
56
|
+
|
57
|
+
end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
class MyCsvConnector < RubySync::Connectors::CsvFileConnector
|
2
|
+
options(
|
3
|
+
:name=>"MyCSV",
|
4
|
+
:field_names=>['given name', 'last name', 'phone number', 'email'],
|
5
|
+
:path_field=>'email',
|
6
|
+
:in_path=>'/tmp/csv/in',
|
7
|
+
:out_path=>'/tmp/csv/out',
|
8
|
+
:in_glob=>'*.csv',
|
9
|
+
:out_extension=>'.csv'
|
10
|
+
)
|
11
|
+
|
12
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
class HrImportPipeline < RubySync::Pipelines::BasePipeline
|
2
|
+
|
3
|
+
client :my_csv
|
4
|
+
|
5
|
+
vault :hr_db
|
6
|
+
|
7
|
+
# Remove any fields that you don't want to set in the client from the vault
|
8
|
+
allow_out :first_name, :last_name
|
9
|
+
|
10
|
+
# Remove any fields that you don't want to set in the vault from the client
|
11
|
+
allow_in :first_name, :last_name
|
12
|
+
|
13
|
+
# If the client and vault have different names for the same field, define the
|
14
|
+
# the mapping here. For example, if the vault has a field called "first name" and
|
15
|
+
# the client has a field called givenName you may put:
|
16
|
+
# 'first name' => 'givenName'
|
17
|
+
# separate each mapping with a comma.
|
18
|
+
# The following fields were detected on the client:
|
19
|
+
# 'given name', 'last name', 'phone number', 'email'
|
20
|
+
map_vault_to_client(
|
21
|
+
'first_name' => 'given name',
|
22
|
+
'last_name' => 'last name'
|
23
|
+
)
|
24
|
+
|
25
|
+
# "in" means going from client to vault
|
26
|
+
#in_transform do
|
27
|
+
#end
|
28
|
+
|
29
|
+
# "out" means going from vault to client
|
30
|
+
#out_transform do
|
31
|
+
#end
|
32
|
+
|
33
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
class FinancePipeline < RubySync::Pipelines::BasePipeline
|
2
|
+
|
3
|
+
client :finance
|
4
|
+
|
5
|
+
vault :hr_db
|
6
|
+
|
7
|
+
# Remove any fields that you don't want to set in the client from the vault
|
8
|
+
allow_out :first_name
|
9
|
+
|
10
|
+
# Remove any fields that you don't want to set in the vault from the client
|
11
|
+
allow_in :first_name, :last_name
|
12
|
+
|
13
|
+
# If the client and vault have different names for the same field, define the
|
14
|
+
# the mapping here. For example, if the vault has a field called "first name" and
|
15
|
+
# the client has a field called givenName you may put:
|
16
|
+
# 'first name' => 'givenName'
|
17
|
+
# separate each mapping with a comma.
|
18
|
+
# The following fields were detected on the client:
|
19
|
+
# 'username', 'name', 'email'
|
20
|
+
map_vault_to_client(
|
21
|
+
'first_name' => 'name'
|
22
|
+
#'last_name' => 'a_client_field'
|
23
|
+
)
|
24
|
+
|
25
|
+
# in means going from client to vault
|
26
|
+
#in_transform do
|
27
|
+
#end
|
28
|
+
|
29
|
+
# out means going from vault to client
|
30
|
+
#out_transform do
|
31
|
+
#end
|
32
|
+
|
33
|
+
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
class HrImportPipeline < RubySync::Pipelines::BasePipeline
|
2
|
+
|
3
|
+
client :corp_directory
|
4
|
+
vault :hr_db
|
5
|
+
|
6
|
+
map_client_to_vault :givenname => :first_name,
|
7
|
+
:sn => :last_name
|
8
|
+
|
9
|
+
|
10
|
+
|
11
|
+
allow_out :first_name, :last_name
|
12
|
+
allow_in :first_name, :last_name
|
13
|
+
|
14
|
+
|
15
|
+
# in means going from client to vault
|
16
|
+
#in_transform do
|
17
|
+
#end
|
18
|
+
|
19
|
+
# out means going from vault to client
|
20
|
+
out_transform do
|
21
|
+
add_default :cn, "Ritchie"
|
22
|
+
end
|
23
|
+
|
24
|
+
def out_place event
|
25
|
+
#event.target_path = "blah"
|
26
|
+
event.target_path = "cn=Ritchie,dc=example,dc=com"
|
27
|
+
end
|
28
|
+
|
29
|
+
end
|
@@ -0,0 +1,198 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
#
|
3
|
+
# Copyright (c) 2007 Ritchie Young. All rights reserved.
|
4
|
+
#
|
5
|
+
# This file is part of RubySync.
|
6
|
+
#
|
7
|
+
# RubySync is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License
|
8
|
+
# as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version.
|
9
|
+
#
|
10
|
+
# RubySync is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied
|
11
|
+
# warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
|
12
|
+
#
|
13
|
+
# You should have received a copy of the GNU General Public License along with RubySync; if not, write to the
|
14
|
+
# Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
|
15
|
+
|
16
|
+
require 'erb'
|
17
|
+
$VERBOSE=false
|
18
|
+
require "active_record"
|
19
|
+
#$VERBOSE=true
|
20
|
+
require "ruby_sync/connectors/base_connector"
|
21
|
+
|
22
|
+
|
23
|
+
module RubySync::Connectors
|
24
|
+
|
25
|
+
# You can initialize this connector with the name of a model and the path to a rails application:
|
26
|
+
# eg: vault :ActiveRecord, :application=>'path/to/rails/application', :model=>:user
|
27
|
+
class ActiveRecordConnector < RubySync::Connectors::BaseConnector
|
28
|
+
|
29
|
+
|
30
|
+
attr_accessor :ar_class, :model, :application, :rails_env, :db_type, :db_host, :db_name
|
31
|
+
|
32
|
+
def initialize options={}
|
33
|
+
super options
|
34
|
+
@rails_env ||= 'development'
|
35
|
+
@db_type ||= 'mysql'
|
36
|
+
@db_host ||= 'localhost'
|
37
|
+
@db_name ||= "rubysync_#{@rails_env}"
|
38
|
+
# Default db_config in case we're not sucking the config out of a rails app
|
39
|
+
@db_config = {
|
40
|
+
:adapter=>@db_type,
|
41
|
+
:host=>@db_host,
|
42
|
+
:database=>@db_name
|
43
|
+
}
|
44
|
+
|
45
|
+
# Rails app specified, use it to configure
|
46
|
+
if defined? @application
|
47
|
+
# Load the database configuration
|
48
|
+
rails_app_path = File.expand_path(@application, File.dirname(__FILE__))
|
49
|
+
db_config_filename = File.join(rails_app_path, 'config', 'database.yml')
|
50
|
+
@db_config = YAML::load(ERB.new(IO.read(db_config_filename)).result)[@rails_env]
|
51
|
+
# Require the models
|
52
|
+
log.debug "Loading the models for #{self.class.name}:"
|
53
|
+
Dir.chdir(File.join(rails_app_path,'app','models')) do
|
54
|
+
Dir.glob('*.rb') do |filename|
|
55
|
+
log.debug("\t#{filename}")
|
56
|
+
require filename
|
57
|
+
class_name = filename[0..-4].camelize
|
58
|
+
klass = class_name.constantize
|
59
|
+
klass.establish_connection @db_config if defined? klass.establish_connection
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
64
|
+
@model ||= :user
|
65
|
+
@ar_class ||= @model.to_s.camelize.constantize
|
66
|
+
end
|
67
|
+
|
68
|
+
|
69
|
+
def self.fields
|
70
|
+
c = self.new
|
71
|
+
c.ar_class.content_columns.map {|col| col.name }
|
72
|
+
end
|
73
|
+
|
74
|
+
def self.sample_config
|
75
|
+
return <<END
|
76
|
+
options(
|
77
|
+
#:application=>'/path/to/a/rails/application',
|
78
|
+
#:model=>'name_of_model_to_sync'
|
79
|
+
)
|
80
|
+
END
|
81
|
+
end
|
82
|
+
|
83
|
+
|
84
|
+
# Process each RubySyncEvent and then delete it from the db.
|
85
|
+
def check
|
86
|
+
::RubySyncEvent.find(:all).each do |rse|
|
87
|
+
event = RubySync::Event.new(rse.event_type, self, rse.trackable_id, nil, to_payload(rse))
|
88
|
+
yield event
|
89
|
+
::RubySyncEvent.delete rse
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
# Create a hash suitable to use as rubysync event payload
|
94
|
+
def to_payload ar_event
|
95
|
+
ar_event.operations.map do |op|
|
96
|
+
RubySync::Operation.new(op.operation.to_sym, op.field_name, op.values.map {|v| v.value})
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
# Override default perform_add because ActiveRecord is different in that
|
101
|
+
# the target path is ignored when adding a record. ActiveRecord determines
|
102
|
+
# the id on creation.
|
103
|
+
def perform_add event
|
104
|
+
log.info "Adding '#{event.target_path}' to '#{name}'"
|
105
|
+
@ar_class.new() do |record|
|
106
|
+
populate(record, perform_operations(event.payload))
|
107
|
+
log.info(record.inspect)
|
108
|
+
record.save!
|
109
|
+
if is_vault?
|
110
|
+
associate event.association, record.id
|
111
|
+
end
|
112
|
+
record.id
|
113
|
+
end
|
114
|
+
rescue => ex
|
115
|
+
log.warn ex
|
116
|
+
#puts ex.backtrace.join("\n")
|
117
|
+
return nil
|
118
|
+
end
|
119
|
+
|
120
|
+
|
121
|
+
def modify(path, operations)
|
122
|
+
@ar_class.find(path) do |record|
|
123
|
+
populate(record, perform_operations(operations))
|
124
|
+
record.save
|
125
|
+
end
|
126
|
+
end
|
127
|
+
|
128
|
+
def delete(path)
|
129
|
+
@ar_class.destroy path
|
130
|
+
end
|
131
|
+
|
132
|
+
# Implement vault functionality
|
133
|
+
|
134
|
+
def associate association, path
|
135
|
+
log.debug "Associating '#{association}' with '#{path}'"
|
136
|
+
ruby_sync_association.create :synchronizable_id=>path, :synchronizable_type=>@ar_class.name,
|
137
|
+
:context=>association.context, :key=>association.key
|
138
|
+
end
|
139
|
+
|
140
|
+
def find_associated association
|
141
|
+
ruby_sync_association.find_by_context_and_key association.context, association.key
|
142
|
+
end
|
143
|
+
|
144
|
+
def path_for_association association
|
145
|
+
assoc = ruby_sync_association.find_by_context_and_key association.context, association.key
|
146
|
+
(assoc)? assoc.synchronizable_id : nil
|
147
|
+
end
|
148
|
+
|
149
|
+
def association_key_for context, path
|
150
|
+
record = ruby_sync_association.find_by_synchronizable_id_and_synchronizable_type_and_context path, @model.to_s, context
|
151
|
+
record and record.key
|
152
|
+
end
|
153
|
+
|
154
|
+
def associations_for(path)
|
155
|
+
ruby_sync_association.find_by_synchronizable_id_and_synchronizable_type(path, @model.to_s)
|
156
|
+
rescue ActiveRecord::RecordNotFound
|
157
|
+
return nil
|
158
|
+
end
|
159
|
+
|
160
|
+
def remove_association association
|
161
|
+
ruby_sync_association.find_by_context_and_key(association.context, association.key).destroy
|
162
|
+
rescue ActiveRecord::RecordNotFound
|
163
|
+
return nil
|
164
|
+
end
|
165
|
+
|
166
|
+
|
167
|
+
def [](path)
|
168
|
+
@ar_class.find(path)
|
169
|
+
rescue ActiveRecord::RecordNotFound
|
170
|
+
return nil
|
171
|
+
end
|
172
|
+
|
173
|
+
private
|
174
|
+
|
175
|
+
def ruby_sync_association
|
176
|
+
unless @ruby_sync_association
|
177
|
+
@ruby_sync_association = ::RubySyncAssociation
|
178
|
+
::RubySyncAssociation.establish_connection(@db_config)
|
179
|
+
end
|
180
|
+
@ruby_sync_association
|
181
|
+
end
|
182
|
+
|
183
|
+
def populate record, content
|
184
|
+
@ar_class.content_columns.each do |c|
|
185
|
+
record[c.name] = content[c.name][0] if content[c.name]
|
186
|
+
end
|
187
|
+
end
|
188
|
+
|
189
|
+
def create_operations_for_active_record record
|
190
|
+
operations = record.class.content_columns.map do |col|
|
191
|
+
key = col.name
|
192
|
+
value = record.send key
|
193
|
+
RubySync::Operation.new(:add, key.to_s, value) if key and value
|
194
|
+
end
|
195
|
+
operations.compact
|
196
|
+
end
|
197
|
+
end
|
198
|
+
end
|