facebook-google-calendar-sync 0.0.2 → 0.1.0
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/README.md +1 -1
- data/lib/facebook_google_calendar_sync/event_converter.rb +81 -0
- data/lib/facebook_google_calendar_sync/google_calendar_client.rb +7 -2
- data/lib/facebook_google_calendar_sync/synchroniser.rb +13 -12
- data/lib/facebook_google_calendar_sync/version.rb +1 -1
- metadata +4 -10
- data/lib/facebook_google_calendar_sync/event.rb +0 -36
data/README.md
CHANGED
@@ -30,7 +30,7 @@ Create a Goggle permissions file to allow the gem to access your Google Calendar
|
|
30
30
|
|
31
31
|
$ bundle exec google-api oauth-2-login --scope=https://www.googleapis.com/auth/calendar --client-id=436161995365.apps.googleusercontent.com --client-secret=WgTEjg-b8rXCRL28hweLcSuV
|
32
32
|
|
33
|
-
You will now have a .google-api.yaml file in your home directory.
|
33
|
+
You will now have a .google-api.yaml file in your home directory. Note: the gem can only access your calendar data if it has this file. The synchronisation process will run locally on your computer - no external service will have access to your Google Calendar.
|
34
34
|
|
35
35
|
For more information on the last step see https://developers.google.com/google-apps/calendar/firstapp#register and the Ruby tab on https://developers.google.com/google-apps/calendar/instantiate
|
36
36
|
|
@@ -0,0 +1,81 @@
|
|
1
|
+
module FacebookGoogleCalendarSync
|
2
|
+
|
3
|
+
class EventConverter
|
4
|
+
|
5
|
+
attr_accessor :facebook_event, :google_calendar_id, :timezone
|
6
|
+
STATUS_MAPPINGS = {'NEEDS-ACTION' => 'needsAction', 'ACCEPTED' => 'accepted'}
|
7
|
+
|
8
|
+
def initialize facebook_event, google_calendar_id, timezone
|
9
|
+
@facebook_event = facebook_event
|
10
|
+
@google_calendar_id = google_calendar_id
|
11
|
+
@timezone = timezone
|
12
|
+
end
|
13
|
+
|
14
|
+
def uid
|
15
|
+
facebook_event.uid
|
16
|
+
end
|
17
|
+
|
18
|
+
def last_modified
|
19
|
+
facebook_event.last_modified.convert_time_zone(timezone)
|
20
|
+
end
|
21
|
+
|
22
|
+
def summary
|
23
|
+
facebook_event.summary
|
24
|
+
end
|
25
|
+
|
26
|
+
def created
|
27
|
+
facebook_event.created
|
28
|
+
end
|
29
|
+
|
30
|
+
def to_hash
|
31
|
+
{
|
32
|
+
'summary' => facebook_event.summary,
|
33
|
+
'start' => date_hash(facebook_event.dtstart),
|
34
|
+
'end' => date_hash(facebook_event.dtend),
|
35
|
+
'iCalUID' => facebook_event.uid,
|
36
|
+
'description' => description,
|
37
|
+
'location' => facebook_event.location,
|
38
|
+
'organizer' => organiser,
|
39
|
+
'attendees' => attendees,
|
40
|
+
'transparency' => transparency
|
41
|
+
}
|
42
|
+
end
|
43
|
+
|
44
|
+
def attendees
|
45
|
+
[{"email"=>google_calendar_id, 'responseStatus' => partstat}]
|
46
|
+
end
|
47
|
+
|
48
|
+
def description
|
49
|
+
"#{facebook_event.description}\n\nOrganiser: #{organiser_name}"
|
50
|
+
end
|
51
|
+
|
52
|
+
def partstat
|
53
|
+
STATUS_MAPPINGS[facebook_event.to_s.scan(/PARTSTAT::(.*)/).flatten.first()]
|
54
|
+
end
|
55
|
+
|
56
|
+
def transparency
|
57
|
+
partstat == 'accepted' ? 'opaque' : 'transparent'
|
58
|
+
end
|
59
|
+
|
60
|
+
def organiser_name
|
61
|
+
matches = facebook_event.organizer_property.to_s.scan(/CN=(.*):MAILTO:(.*)/).flatten
|
62
|
+
matches[0]
|
63
|
+
end
|
64
|
+
|
65
|
+
def organiser
|
66
|
+
{
|
67
|
+
'email' => 'noreply@facebook.com',
|
68
|
+
}
|
69
|
+
end
|
70
|
+
|
71
|
+
private
|
72
|
+
|
73
|
+
def date_hash date_time
|
74
|
+
if date_time.instance_of? Date
|
75
|
+
{'date' => date_time.strftime('%Y-%m-%d')}
|
76
|
+
else
|
77
|
+
{'dateTime' => date_time.convert_time_zone(timezone).strftime('%Y-%m-%dT%H:%M:%S.000%:z')}
|
78
|
+
end
|
79
|
+
end
|
80
|
+
end
|
81
|
+
end
|
@@ -2,6 +2,7 @@ require 'yaml'
|
|
2
2
|
require 'pathname'
|
3
3
|
require 'google/api_client'
|
4
4
|
require 'ostruct'
|
5
|
+
require 'facebook_google_calendar_sync/version'
|
5
6
|
|
6
7
|
module FacebookGoogleCalendarSync
|
7
8
|
|
@@ -14,7 +15,7 @@ end
|
|
14
15
|
yield @@config
|
15
16
|
|
16
17
|
oauth_yaml = YAML.load_file(@@config.google_api_config_file)
|
17
|
-
@@client = Google::APIClient.new({:application_name => "Facebook to Google Calendar Sync", :application_version =>
|
18
|
+
@@client = Google::APIClient.new({:application_name => "Facebook to Google Calendar Sync", :application_version => FacebookGoogleCalendarSync::VERSION})
|
18
19
|
@@client.authorization.client_id = oauth_yaml["client_id"]
|
19
20
|
@@client.authorization.client_secret = oauth_yaml["client_secret"]
|
20
21
|
@@client.authorization.scope = oauth_yaml["scope"]
|
@@ -28,6 +29,10 @@ end
|
|
28
29
|
@@calendar_service = @@client.discovered_api('calendar', 'v3')
|
29
30
|
end
|
30
31
|
|
32
|
+
def get_calendar_metadata calendar_id
|
33
|
+
make_call :api_method => calendar_service.calendars.get, :parameters => {'calendarId' => calendar_id}
|
34
|
+
end
|
35
|
+
|
31
36
|
def find_calendar_details_by_summary calendar_summary
|
32
37
|
get_calendar_list.items.find { | calendar | calendar.summary == calendar_summary && calendar.accessRole == 'owner'}
|
33
38
|
end
|
@@ -45,7 +50,7 @@ end
|
|
45
50
|
end
|
46
51
|
|
47
52
|
def add_event calendar_id, event
|
48
|
-
make_call :api_method => calendar_service.events.
|
53
|
+
make_call :api_method => calendar_service.events.import,
|
49
54
|
:parameters => {'calendarId' => calendar_id},
|
50
55
|
:body_object => event
|
51
56
|
end
|
@@ -1,11 +1,10 @@
|
|
1
|
-
require 'facebook_google_calendar_sync/event'
|
2
1
|
require 'facebook_google_calendar_sync/google_calendar_client'
|
3
2
|
require 'facebook_google_calendar_sync/google_calendar_description'
|
4
3
|
require 'time_zone_hack'
|
4
|
+
require 'facebook_google_calendar_sync/event_converter'
|
5
5
|
|
6
6
|
module FacebookGoogleCalendarSync
|
7
7
|
class Synchroniser
|
8
|
-
include Event
|
9
8
|
include Logging
|
10
9
|
include GoogleCalendarDescription
|
11
10
|
include GoogleCalendarClient
|
@@ -31,11 +30,12 @@ module FacebookGoogleCalendarSync
|
|
31
30
|
def synchronise_events
|
32
31
|
facebook_calendar.events.each do | facebook_event |
|
33
32
|
begin
|
34
|
-
synchronise_event facebook_event
|
33
|
+
synchronise_event EventConverter.new(facebook_event, google_calendar.id, google_calendar.timezone)
|
35
34
|
rescue StandardError => e
|
36
35
|
logger.error e
|
37
36
|
logger.error "Error synchronising event. Please note that if this was a new event, it will not have been added to your calendar."
|
38
|
-
logger.error
|
37
|
+
logger.error facebook_event.summary
|
38
|
+
raise e
|
39
39
|
end
|
40
40
|
end
|
41
41
|
end
|
@@ -52,7 +52,7 @@ module FacebookGoogleCalendarSync
|
|
52
52
|
def handle_google_event_not_found facebook_event
|
53
53
|
if event_created_since_calendar_last_modified facebook_event
|
54
54
|
logger.info "Adding '#{facebook_event.summary}' to #{google_calendar.summary}"
|
55
|
-
add_event google_calendar.id,
|
55
|
+
add_event google_calendar.id, facebook_event.to_hash
|
56
56
|
else
|
57
57
|
logger.info "Not updating '#{facebook_event.summary}' as it has been deleted from the target calendar since #{google_calendar.last_known_event_update}."
|
58
58
|
end
|
@@ -61,9 +61,9 @@ module FacebookGoogleCalendarSync
|
|
61
61
|
def handle_google_event_found facebook_event, google_event
|
62
62
|
if event_updated_since_calendar_last_modified facebook_event
|
63
63
|
logger.info "Updating '#{facebook_event.summary}' in #{google_calendar.summary}"
|
64
|
-
update_event google_calendar.id, google_event.id,
|
64
|
+
update_event google_calendar.id, google_event.id, facebook_event.to_hash.merge(google_event)
|
65
65
|
else
|
66
|
-
logger.info "Not updating '#{facebook_event.summary}' in #{google_calendar.summary} as #{
|
66
|
+
logger.info "Not updating '#{facebook_event.summary}' in #{google_calendar.summary} as #{facebook_event.last_modified} is not later than #{to_local(google_event.updated)}"
|
67
67
|
end
|
68
68
|
end
|
69
69
|
|
@@ -75,10 +75,6 @@ module FacebookGoogleCalendarSync
|
|
75
75
|
facebook_event.created > google_calendar.last_known_event_update
|
76
76
|
end
|
77
77
|
|
78
|
-
def date_of_most_recent_event_update
|
79
|
-
to_local(date_of_most_recent_update(facebook_calendar.events))
|
80
|
-
end
|
81
|
-
|
82
78
|
def update_last_known_event_update
|
83
79
|
last_modified = date_of_most_recent_event_update
|
84
80
|
if last_modified != google_calendar.last_known_event_update
|
@@ -86,7 +82,7 @@ module FacebookGoogleCalendarSync
|
|
86
82
|
details = google_calendar.details.to_hash.merge({'description' => create_description(date_of_most_recent_event_update, current_time_in_google_calendar_timezone)})
|
87
83
|
update_calendar google_calendar.id, details
|
88
84
|
else
|
89
|
-
logger.info "Not updating description of '#{google_calendar.summary}' as the date of the most recent update has not changed from #{google_calendar.last_known_event_update}."
|
85
|
+
logger.info "Not updating description of '#{google_calendar.summary}' as the date of the most recent update has not changed from #{to_local(google_calendar.last_known_event_update)}."
|
90
86
|
end
|
91
87
|
end
|
92
88
|
|
@@ -97,5 +93,10 @@ module FacebookGoogleCalendarSync
|
|
97
93
|
def to_local date_or_time
|
98
94
|
date_or_time.convert_time_zone(google_calendar.timezone)
|
99
95
|
end
|
96
|
+
|
97
|
+
def date_of_most_recent_event_update
|
98
|
+
most_recently_modified_event = facebook_calendar.events.max{ | event_a, event_b | event_a.last_modified <=> event_b.last_modified }
|
99
|
+
most_recently_modified_event.last_modified
|
100
|
+
end
|
100
101
|
end
|
101
102
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: facebook-google-calendar-sync
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0
|
4
|
+
version: 0.1.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2013-04-
|
12
|
+
date: 2013-04-18 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: google-api-client
|
@@ -159,7 +159,7 @@ files:
|
|
159
159
|
- facebook-google-calendar-sync.gemspec
|
160
160
|
- lib/facebook_google_calendar_sync.rb
|
161
161
|
- lib/facebook_google_calendar_sync/cli.rb
|
162
|
-
- lib/facebook_google_calendar_sync/
|
162
|
+
- lib/facebook_google_calendar_sync/event_converter.rb
|
163
163
|
- lib/facebook_google_calendar_sync/google_calendar.rb
|
164
164
|
- lib/facebook_google_calendar_sync/google_calendar_client.rb
|
165
165
|
- lib/facebook_google_calendar_sync/google_calendar_description.rb
|
@@ -183,21 +183,15 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
183
183
|
- - ! '>='
|
184
184
|
- !ruby/object:Gem::Version
|
185
185
|
version: '0'
|
186
|
-
segments:
|
187
|
-
- 0
|
188
|
-
hash: -611403339403696087
|
189
186
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
190
187
|
none: false
|
191
188
|
requirements:
|
192
189
|
- - ! '>='
|
193
190
|
- !ruby/object:Gem::Version
|
194
191
|
version: '0'
|
195
|
-
segments:
|
196
|
-
- 0
|
197
|
-
hash: -611403339403696087
|
198
192
|
requirements: []
|
199
193
|
rubyforge_project:
|
200
|
-
rubygems_version: 1.8.
|
194
|
+
rubygems_version: 1.8.23
|
201
195
|
signing_key:
|
202
196
|
specification_version: 3
|
203
197
|
summary: Syncs Facebook calendar to Google calendar
|
@@ -1,36 +0,0 @@
|
|
1
|
-
require 'date'
|
2
|
-
|
3
|
-
module FacebookGoogleCalendarSync
|
4
|
-
module Event
|
5
|
-
|
6
|
-
def convert_event_to_hash ical_event
|
7
|
-
{
|
8
|
-
'summary' => ical_event.summary,
|
9
|
-
'start' => date_hash(ical_event.dtstart),
|
10
|
-
'end' => date_hash(ical_event.dtend),
|
11
|
-
'iCalUID' => ical_event.uid,
|
12
|
-
'description' => ical_event.description,
|
13
|
-
'location' => ical_event.location
|
14
|
-
}
|
15
|
-
end
|
16
|
-
|
17
|
-
def merge_events google_event, facebook_event
|
18
|
-
google_event.to_hash.merge(convert_event_to_hash(facebook_event))
|
19
|
-
end
|
20
|
-
|
21
|
-
def date_of_most_recent_update facebook_events
|
22
|
-
most_recently_modified_event = facebook_events.max{ | event_a, event_b | event_a.last_modified <=> event_b.last_modified }
|
23
|
-
most_recently_modified_event.last_modified
|
24
|
-
end
|
25
|
-
|
26
|
-
private
|
27
|
-
|
28
|
-
def date_hash date_time
|
29
|
-
if date_time.instance_of? Date
|
30
|
-
{'date' => date_time.strftime('%Y-%m-%d')}
|
31
|
-
else
|
32
|
-
{'dateTime' => date_time.strftime('%Y-%m-%dT%H:%M:%S.000%:z')}
|
33
|
-
end
|
34
|
-
end
|
35
|
-
end
|
36
|
-
end
|