viewpoint 0.1.27 → 1.0.0.beta.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.
Files changed (93) hide show
  1. data/README.md +196 -0
  2. data/lib/ews/calendar_accessors.rb +34 -0
  3. data/lib/ews/connection.rb +117 -0
  4. data/lib/ews/connection_helper.rb +35 -0
  5. data/lib/ews/ews_client.rb +71 -0
  6. data/lib/ews/exceptions/exceptions.rb +59 -0
  7. data/lib/ews/folder_accessors.rb +199 -0
  8. data/lib/ews/item_accessors.rb +157 -0
  9. data/lib/ews/mailbox_accessors.rb +87 -0
  10. data/lib/ews/message_accessors.rb +86 -0
  11. data/lib/ews/push_subscription_accessors.rb +33 -0
  12. data/lib/ews/soap.rb +63 -0
  13. data/lib/ews/soap/builders/ews_builder.rb +1011 -0
  14. data/lib/ews/soap/ews_response.rb +83 -0
  15. data/lib/ews/soap/ews_soap_availability_response.rb +58 -0
  16. data/lib/ews/soap/ews_soap_free_busy_response.rb +109 -0
  17. data/lib/ews/soap/ews_soap_response.rb +103 -0
  18. data/lib/ews/soap/exchange_availability.rb +61 -0
  19. data/lib/ews/soap/exchange_data_services.rb +742 -0
  20. data/lib/ews/soap/exchange_notification.rb +146 -0
  21. data/lib/ews/soap/exchange_user_configuration.rb +33 -0
  22. data/lib/ews/soap/exchange_web_service.rb +294 -0
  23. data/lib/{model/attendee.rb → ews/soap/parsers/ews_parser.rb} +20 -14
  24. data/lib/ews/soap/parsers/ews_sax_document.rb +66 -0
  25. data/lib/ews/soap/response_message.rb +78 -0
  26. data/lib/ews/soap/responses/create_attachment_response_message.rb +46 -0
  27. data/lib/{model/meeting_message.rb → ews/soap/responses/create_item_response_message.rb} +7 -10
  28. data/lib/ews/soap/responses/find_item_response_message.rb +80 -0
  29. data/lib/ews/soap/responses/get_events_response_message.rb +53 -0
  30. data/lib/ews/soap/responses/send_notification_response_message.rb +58 -0
  31. data/lib/{model/attachment.rb → ews/soap/responses/subscribe_response_message.rb} +17 -13
  32. data/lib/ews/templates/forward_item.rb +24 -0
  33. data/lib/ews/templates/message.rb +66 -0
  34. data/lib/ews/templates/reply_to_item.rb +25 -0
  35. data/lib/ews/types.rb +146 -0
  36. data/lib/ews/types/attachment.rb +77 -0
  37. data/lib/{model/meeting_cancellation.rb → ews/types/attendee.rb} +9 -8
  38. data/lib/ews/types/calendar_folder.rb +8 -0
  39. data/lib/ews/types/calendar_item.rb +37 -0
  40. data/lib/ews/types/contact.rb +7 -0
  41. data/lib/ews/types/contacts_folder.rb +8 -0
  42. data/lib/ews/types/copied_event.rb +51 -0
  43. data/lib/{soap/handsoap/builder.rb → ews/types/created_event.rb} +5 -2
  44. data/lib/{model/meeting_response.rb → ews/types/deleted_event.rb} +6 -6
  45. data/lib/ews/types/distribution_list.rb +7 -0
  46. data/lib/ews/types/event.rb +62 -0
  47. data/lib/ews/types/file_attachment.rb +65 -0
  48. data/lib/ews/types/folder.rb +60 -0
  49. data/lib/{model/distribution_list.rb → ews/types/free_busy_changed_event.rb} +6 -6
  50. data/lib/ews/types/generic_folder.rb +352 -0
  51. data/lib/ews/types/item.rb +381 -0
  52. data/lib/ews/types/item_attachment.rb +46 -0
  53. data/lib/{model → ews/types}/item_field_uri_map.rb +2 -2
  54. data/lib/ews/types/mailbox_user.rb +156 -0
  55. data/lib/ews/types/meeting_cancellation.rb +7 -0
  56. data/lib/ews/types/meeting_message.rb +7 -0
  57. data/lib/ews/types/meeting_request.rb +7 -0
  58. data/lib/ews/types/meeting_response.rb +7 -0
  59. data/lib/ews/types/message.rb +7 -0
  60. data/lib/ews/types/modified_event.rb +48 -0
  61. data/lib/{model/item_attachment.rb → ews/types/moved_event.rb} +33 -15
  62. data/lib/ews/types/new_mail_event.rb +24 -0
  63. data/lib/ews/types/out_of_office.rb +147 -0
  64. data/lib/ews/types/search_folder.rb +8 -0
  65. data/lib/ews/types/status_event.rb +39 -0
  66. data/lib/ews/types/task.rb +7 -0
  67. data/lib/ews/types/tasks_folder.rb +8 -0
  68. data/lib/viewpoint.rb +82 -106
  69. metadata +99 -67
  70. data/README +0 -114
  71. data/lib/exceptions/exceptions.rb +0 -46
  72. data/lib/model/calendar_folder.rb +0 -67
  73. data/lib/model/calendar_item.rb +0 -267
  74. data/lib/model/contact.rb +0 -238
  75. data/lib/model/contacts_folder.rb +0 -46
  76. data/lib/model/event.rb +0 -116
  77. data/lib/model/file_attachment.rb +0 -53
  78. data/lib/model/folder.rb +0 -47
  79. data/lib/model/generic_folder.rb +0 -471
  80. data/lib/model/item.rb +0 -313
  81. data/lib/model/mailbox_user.rb +0 -146
  82. data/lib/model/meeting_request.rb +0 -39
  83. data/lib/model/message.rb +0 -142
  84. data/lib/model/model.rb +0 -269
  85. data/lib/model/search_folder.rb +0 -48
  86. data/lib/model/task.rb +0 -121
  87. data/lib/model/tasks_folder.rb +0 -44
  88. data/lib/soap/handsoap/builders/ews_build_helpers.rb +0 -383
  89. data/lib/soap/handsoap/builders/ews_builder.rb +0 -146
  90. data/lib/soap/handsoap/ews_service.rb +0 -813
  91. data/lib/soap/handsoap/parser.rb +0 -104
  92. data/lib/soap/handsoap/parsers/ews_parser.rb +0 -246
  93. data/lib/soap/soap_provider.rb +0 -64
@@ -0,0 +1,381 @@
1
+ module Viewpoint::EWS::Types
2
+ module Item
3
+ include Viewpoint::EWS
4
+ include Viewpoint::EWS::Types
5
+ include ItemFieldUriMap
6
+
7
+ ITEM_KEY_PATHS = {
8
+ id: [:item_id, :attribs, :id],
9
+ change_key: [:item_id, :attribs, :change_key],
10
+ subject: [:subject, :text],
11
+ sensitivity: [:sensitivity, :text],
12
+ size: [:size, :text],
13
+ date_time_sent: [:date_time_sent, :text],
14
+ date_time_created: [:date_time_created, :text],
15
+ has_attachments?:[:has_attachments, :text],
16
+ is_associated?: [:is_associated, :text],
17
+ is_read?: [:is_read, :text],
18
+ is_draft?: [:is_draft, :text],
19
+ is_submitted?: [:is_submitted, :text],
20
+ conversation_id:[:conversation_id, :attribs, :id],
21
+ categories: [:categories, :elems],
22
+ internet_message_id:[:internet_message_id, :text],
23
+ internet_message_headers:[:internet_message_headers, :elems],
24
+ sender: [:sender, :elems, 0, :mailbox, :elems],
25
+ from: [:from, :elems, 0, :mailbox, :elems],
26
+ to_recipients: [:to_recipients, :elems],
27
+ attachments: [:attachments, :elems],
28
+ importance: [:importance, :text],
29
+ conversation_index: [:conversation_index, :text],
30
+ conversation_topic: [:conversation_topic, :text],
31
+ body_type: [:body, :attribs, :body_type],
32
+ body: [:body, :text]
33
+ }
34
+
35
+ ITEM_KEY_TYPES = {
36
+ size: ->(str){str.to_i},
37
+ date_time_sent: ->(str){DateTime.parse(str)},
38
+ date_time_created: ->(str){DateTime.parse(str)},
39
+ has_attachments?: ->(str){str.downcase == 'true'},
40
+ is_associated?: ->(str){str.downcase == 'true'},
41
+ is_read?: ->(str){str.downcase == 'true'},
42
+ is_draft?: ->(str){str.downcase == 'true'},
43
+ is_submitted?: ->(str){str.downcase == 'true'},
44
+ categories: ->(obj){obj.collect{|s| s[:string][:text]}},
45
+ internet_message_headers: ->(obj){obj.collect{|h|
46
+ {h[:internet_message_header][:attribs][:header_name] =>
47
+ h[:internet_message_header][:text]} } },
48
+ sender: :build_mailbox_user,
49
+ from: :build_mailbox_user,
50
+ attachments: :build_attachments,
51
+ }
52
+
53
+ ITEM_KEY_ALIAS = {
54
+ :read? => :is_read?,
55
+ :draft? => :is_draft?,
56
+ :submitted? => :is_submitted?,
57
+ :associated? => :is_associated?,
58
+ }
59
+
60
+ attr_reader :ews_item, :parent
61
+
62
+ # @param ews [SOAP::ExchangeWebService] the EWS reference
63
+ # @param ews_item [Hash] the EWS parsed response document
64
+ # @param parent [GenericFolder] an optional parent object
65
+ def initialize(ews, ews_item, parent = nil)
66
+ super(ews, ews_item)
67
+ @parent = parent
68
+ @body_type = false
69
+ simplify!
70
+ @new_file_attachments = []
71
+ @new_item_attachments = []
72
+ end
73
+
74
+ # Specify a body_type to fetch this item with if it hasn't already been fetched.
75
+ # @param body_type [String, Symbol, FalseClass] must be :best, :text, or
76
+ # :html. You can also set it to false to make it use the default.
77
+ def default_body_type=(body_type)
78
+ @body_type = body_type
79
+ end
80
+
81
+ def delete!(deltype = :hard)
82
+ opts = {
83
+ :delete_type => delete_type(deltype),
84
+ :item_ids => [{:item_id => {:id => id}}]
85
+ }
86
+ resp = @ews.delete_item(opts)
87
+ rmsg = resp.response_messages[0]
88
+ unless rmsg.success?
89
+ raise EwsError, "Could not delete #{self.class}. #{rmsg.response_code}: #{rmsg.message_text}"
90
+ end
91
+ true
92
+ end
93
+
94
+ def recycle!
95
+ delete! :recycle
96
+ end
97
+
98
+ def get_all_properties!
99
+ @ews_item = get_item(base_shape: 'AllProperties')
100
+ simplify!
101
+ end
102
+
103
+ # Mark an item as read or if you pass false, unread
104
+ # @param [Boolean] read mark read if true, unread if not.
105
+ def mark_read!(read = true)
106
+ resp = update_is_read_status read
107
+ end
108
+
109
+ # Move this item to a new folder
110
+ # @param [String,Symbol,GenericFolder] new_folder The new folder to move it to. This should
111
+ # be a subclass of GenericFolder, a DistinguishedFolderId (must me a Symbol) or a FolderId (String)
112
+ # @return [String] the new Id of the moved item
113
+ def move!(new_folder)
114
+ new_folder = new_folder.id if new_folder.kind_of?(GenericFolder)
115
+ move_opts = {
116
+ :to_folder_id => {:id => new_folder},
117
+ :item_ids => [{:item_id => {:id => self.id}}]
118
+ }
119
+ resp = @ews.move_item(move_opts)
120
+ rmsg = resp.response_messages[0]
121
+
122
+ if rmsg.success?
123
+ obj = rmsg.items.first
124
+ itype = obj.keys.first
125
+ obj[itype][:elems][0][:item_id][:attribs][:id]
126
+ else
127
+ raise EwsError, "Could not move item. #{resp.code}: #{resp.message}"
128
+ end
129
+ end
130
+
131
+ # Copy this item to a new folder
132
+ # @param [String,Symbol,GenericFolder] new_folder The new folder to move it to. This should
133
+ # be a subclass of GenericFolder, a DistinguishedFolderId (must me a Symbol) or a FolderId (String)
134
+ # @return [String] the new Id of the copied item
135
+ def copy(new_folder)
136
+ new_folder = new_folder.id if new_folder.kind_of?(GenericFolder)
137
+ copy_opts = {
138
+ :to_folder_id => {:id => new_folder},
139
+ :item_ids => [{:item_id => {:id => self.id}}]
140
+ }
141
+ resp = @ews.copy_item(copy_opts)
142
+ rmsg = resp.response_messages[0]
143
+
144
+ if rmsg.success?
145
+ obj = rmsg.items.first
146
+ itype = obj.keys.first
147
+ obj[itype][:elems][0][:item_id][:attribs][:id]
148
+ else
149
+ raise EwsError, "Could not copy item. #{rmsg.response_code}: #{rmsg.message_text}"
150
+ end
151
+ end
152
+
153
+ def add_file_attachment(file)
154
+ fa = OpenStruct.new
155
+ fa.name = File.basename(file.path)
156
+ fa.content = Base64.encode64(file.read)
157
+ @new_file_attachments << fa
158
+ end
159
+
160
+ def add_item_attachment(other_item, name = nil)
161
+ ia = OpenStruct.new
162
+ ia.name = (name ? name : other_item.subject)
163
+ ia.item = {id: other_item.id, change_key: other_item.change_key}
164
+ @new_item_attachments << ia
165
+ end
166
+
167
+ def submit!
168
+ if draft?
169
+ submit_attachments!
170
+ resp = ews.send_item(item_ids: [{item_id: {id: self.id, change_key: self.change_key}}])
171
+ rm = resp.response_messages[0]
172
+ if rm.success?
173
+ true
174
+ else
175
+ raise EwsSendItemError, "#{rm.code}: #{rm.message_text}"
176
+ end
177
+ else
178
+ false
179
+ end
180
+ end
181
+
182
+ def submit_attachments!
183
+ return false unless draft? && !(@new_file_attachments.empty? && @new_item_attachments.empty?)
184
+
185
+ opts = {
186
+ parent_id: {id: self.id, change_key: self.change_key},
187
+ files: @new_file_attachments,
188
+ items: @new_item_attachments
189
+ }
190
+ resp = ews.create_attachment(opts)
191
+ set_change_key resp.response_messages[0].attachments[0].parent_change_key
192
+ @new_file_attachments = []
193
+ @new_item_attachments = []
194
+ end
195
+
196
+ # If you want to add to the body set #new_body_content. If you set #body
197
+ # it will override the body that is there.
198
+ # @see MessageAccessors#send_message for options
199
+ # additional options:
200
+ # :new_body_content, :new_body_type
201
+ # @example
202
+ # item.forward do |i|
203
+ # i.new_body_content = "Add this to the top"
204
+ # i.to_recipients << 'test@example.com'
205
+ # end
206
+ def forward(opts = {})
207
+ msg = Template::ForwardItem.new opts.clone
208
+ yield msg if block_given?
209
+ msg.reference_item_id = {id: self.id, change_key: self.change_key}
210
+ dispatch_create_item! msg
211
+ end
212
+
213
+ def reply_to(opts = {})
214
+ msg = Template::ReplyToItem.new opts.clone
215
+ yield msg if block_given?
216
+ msg.reference_item_id = {id: self.id, change_key: self.change_key}
217
+ dispatch_create_item! msg
218
+ end
219
+
220
+ def reply_to_all(opts = {})
221
+ msg = Template::ReplyToItem.new opts.clone
222
+ yield msg if block_given?
223
+ msg.reference_item_id = {id: self.id, change_key: self.change_key}
224
+ msg.ews_type = :reply_all_to_item
225
+ dispatch_create_item! msg
226
+ end
227
+
228
+
229
+ private
230
+
231
+ def key_paths
232
+ super.merge(ITEM_KEY_PATHS)
233
+ end
234
+
235
+ def key_types
236
+ super.merge(ITEM_KEY_TYPES)
237
+ end
238
+
239
+ def key_alias
240
+ super.merge(ITEM_KEY_ALIAS)
241
+ end
242
+
243
+ def update_is_read_status(read)
244
+ field = :is_read
245
+ opts = {item_changes:
246
+ [
247
+ { item_id: {id: id, change_key: change_key},
248
+ updates: [
249
+ {set_item_field: {field_uRI: {field_uRI: FIELD_URIS[field][:text]},
250
+ message: {sub_elements: [{field => {text: read}}]}}}
251
+ ]
252
+ }
253
+ ]
254
+ }
255
+ resp = ews.update_item({conflict_resolution: 'AutoResolve'}.merge(opts))
256
+ rmsg = resp.response_messages[0]
257
+ unless rmsg.success?
258
+ raise EwsError, "#{rmsg.response_code}: #{rmsg.message_text}"
259
+ end
260
+ true
261
+ end
262
+
263
+ def simplify!
264
+ @ews_item = @ews_item[:elems].inject({}) do |o,i|
265
+ key = i.keys.first
266
+ if o.has_key?(key)
267
+ if o[key].is_a?(Array)
268
+ o[key] << i[key]
269
+ else
270
+ o[key] = [o.delete(key), i[key]]
271
+ end
272
+ else
273
+ o[key] = i[key]
274
+ end
275
+ o
276
+ end
277
+ end
278
+
279
+ # Get a specific item by its ID.
280
+ # @param [Hash] opts Misc options to control request
281
+ # @option opts [String] :base_shape IdOnly/Default/AllProperties
282
+ # @raise [EwsError] raised when the backend SOAP method returns an error.
283
+ def get_item(opts = {})
284
+ args = get_item_args(opts)
285
+ resp = ews.get_item(args)
286
+ get_item_parser(resp)
287
+ end
288
+
289
+ # Build up the arguements for #get_item
290
+ # @todo: should we really pass the ChangeKey or do we want the freshest obj?
291
+ def get_item_args(opts)
292
+ opts[:base_shape] ||= 'Default'
293
+ default_args = {
294
+ item_shape: {base_shape: opts[:base_shape]},
295
+ item_ids: [{item_id:{id: id, change_key: change_key}}]
296
+ }
297
+ default_args[:item_shape][:body_type] = @body_type if @body_type
298
+ default_args
299
+ end
300
+
301
+ def get_item_parser(resp)
302
+ rm = resp.response_messages[0]
303
+ if(rm.status == 'Success')
304
+ rm.items[0].values.first
305
+ else
306
+ raise EwsError, "Could not retrieve #{self.class}. #{rm.code}: #{rm.message_text}"
307
+ end
308
+ end
309
+
310
+ # Map a delete type to what EWS expects
311
+ # @param [Symbol] type. Must be :hard, :soft, or :recycle
312
+ def delete_type(type)
313
+ case type
314
+ when :hard then 'HardDelete'
315
+ when :soft then 'SoftDelete'
316
+ when :recycle then 'MoveToDeletedItems'
317
+ else 'MoveToDeletedItems'
318
+ end
319
+ end
320
+
321
+ def build_mailbox_user(mbox_ews)
322
+ MailboxUser.new(ews, mbox_ews)
323
+ end
324
+
325
+ def build_attachments(attachments)
326
+ attachments.collect do |att|
327
+ key = att.keys.first
328
+ class_by_name(key).new(self, att[key])
329
+ end
330
+ end
331
+
332
+ def set_change_key(ck)
333
+ p = resolve_key_path(ews_item, key_paths[:change_key][0..-2])
334
+ p[:change_key] = ck
335
+ end
336
+
337
+ # Handles the CreateItem call for Forward, ReplyTo, and ReplyAllTo
338
+ # It will handle the neccessary actions for adding attachments.
339
+ def dispatch_create_item!(msg)
340
+ if msg.has_attachments?
341
+ draft = msg.draft
342
+ msg.draft = true
343
+ resp = validate_created_item(ews.create_item(msg.to_ews))
344
+ msg.file_attachments.each do |f|
345
+ next unless f.kind_of?(File)
346
+ resp.add_file_attachment(f)
347
+ end
348
+ if draft
349
+ resp.submit_attachments!
350
+ resp
351
+ else
352
+ resp.submit!
353
+ end
354
+ else
355
+ resp = ews.create_item(msg.to_ews)
356
+ validate_created_item resp
357
+ end
358
+ end
359
+
360
+ # validate the CreateItem response.
361
+ # @return [Boolean, Item] returns true if items is empty and status is
362
+ # "Success" if items is not empty it will return the first Item since
363
+ # we are only dealing with single items here.
364
+ # @raise EwsCreateItemError on failure
365
+ def validate_created_item(response)
366
+ msg = response.response_messages[0]
367
+
368
+ if(msg.status == 'Success')
369
+ msg.items.empty? ? true : parse_created_item(msg.items.first)
370
+ else
371
+ raise EwsCreateItemError, "#{msg.code}: #{msg.message_text}"
372
+ end
373
+ end
374
+
375
+ def parse_created_item(msg)
376
+ mtype = msg.keys.first
377
+ message = class_by_name(mtype).new(ews, msg[mtype])
378
+ end
379
+
380
+ end
381
+ end
@@ -0,0 +1,46 @@
1
+ =begin
2
+ This file is part of Viewpoint; the Ruby library for Microsoft Exchange Web Services.
3
+
4
+ Copyright © 2011 Dan Wanek <dan.wanek@gmail.com>
5
+
6
+ Licensed under the Apache License, Version 2.0 (the "License");
7
+ you may not use this file except in compliance with the License.
8
+ You may obtain a copy of the License at
9
+
10
+ http://www.apache.org/licenses/LICENSE-2.0
11
+
12
+ Unless required by applicable law or agreed to in writing, software
13
+ distributed under the License is distributed on an "AS IS" BASIS,
14
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ See the License for the specific language governing permissions and
16
+ limitations under the License.
17
+ =end
18
+
19
+ module Viewpoint::EWS::Types
20
+ class ItemAttachment < Attachment
21
+
22
+ ITEM_ATTACH_KEY_PATHS = { }
23
+
24
+ ITEM_ATTACH_KEY_TYPES = { }
25
+
26
+ ITEM_ATTACH_KEY_ALIAS = { }
27
+
28
+
29
+ private
30
+
31
+
32
+ def key_paths
33
+ super.merge(ITEM_ATTACH_KEY_PATHS)
34
+ end
35
+
36
+ def key_types
37
+ super.merge(ITEM_ATTACH_KEY_TYPES)
38
+ end
39
+
40
+ def key_alias
41
+ super.merge(ITEM_ATTACH_KEY_ALIAS)
42
+ end
43
+
44
+ end
45
+ end
46
+
@@ -20,7 +20,8 @@ module Viewpoint
20
20
  module EWS
21
21
  module ItemFieldUriMap
22
22
 
23
- FIELD_URIS= {:folder_id => {:text => 'older:FolderId', :writable => true},
23
+ FIELD_URIS= {
24
+ :folder_id => {:text => 'older:FolderId', :writable => true},
24
25
  :parent_folder_id => {:text => 'folder:ParentFolderId', :writable => true},
25
26
  :display_name => {:text => 'folder:DisplayName', :writable => true},
26
27
  :unread_count => {:text => 'folder:UnreadCount', :writable => true},
@@ -218,7 +219,6 @@ module Viewpoint
218
219
  :item_ids => {:text => 'conversation:ItemIds', :writable => true},
219
220
  :global_item_ids => {:text => 'conversation:GlobalItemIds', :writable => true}
220
221
  }
221
-
222
222
  end
223
223
  end
224
224
  end
@@ -0,0 +1,156 @@
1
+ =begin
2
+ This file is part of Viewpoint; the Ruby library for Microsoft Exchange Web Services.
3
+
4
+ Copyright © 2011 Dan Wanek <dan.wanek@gmail.com>
5
+
6
+ Licensed under the Apache License, Version 2.0 (the "License");
7
+ you may not use this file except in compliance with the License.
8
+ You may obtain a copy of the License at
9
+
10
+ http://www.apache.org/licenses/LICENSE-2.0
11
+
12
+ Unless required by applicable law or agreed to in writing, software
13
+ distributed under the License is distributed on an "AS IS" BASIS,
14
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ See the License for the specific language governing permissions and
16
+ limitations under the License.
17
+ =end
18
+
19
+ module Viewpoint::EWS::Types
20
+
21
+ # This represents a Mailbox object in the Exchange data store
22
+ # @see http://msdn.microsoft.com/en-us/library/aa565036.aspx MSDN docs
23
+ # @todo Design a Class method that resolves to an Array of MailboxUsers
24
+ class MailboxUser
25
+ include Viewpoint::EWS
26
+ include Viewpoint::EWS::Types
27
+
28
+ MAILBOX_KEY_PATHS = {
29
+ name: [:name],
30
+ email_address: [:email_address],
31
+ }
32
+ MAILBOX_KEY_TYPES = {}
33
+ MAILBOX_KEY_ALIAS = {
34
+ email: :email_address,
35
+ }
36
+
37
+ def initialize(ews, mbox_user)
38
+ @ews = ews
39
+ @ews_item = mbox_user
40
+ simplify!
41
+ end
42
+
43
+ def out_of_office_settings
44
+ mailbox = {:address => self.email_address}
45
+ resp = @ews.get_user_oof_settings(mailbox)
46
+ ewsi = resp.response.clone
47
+ ewsi.delete(:response_message)
48
+ return OutOfOffice.new(self,ewsi)
49
+ s = resp[:oof_settings]
50
+ @oof_state = s[:oof_state][:text]
51
+ @oof_ext_audience = s[:external_audience][:text]
52
+ @oof_start = DateTime.parse(s[:duration][:start_time][:text])
53
+ @oof_end = DateTime.parse(s[:duration][:end_time][:text])
54
+ @oof_internal_reply = s[:internal_reply][:message][:text]
55
+ @oof_external_reply = s[:internal_reply][:message][:text]
56
+ true
57
+ end
58
+
59
+ # Get information about when the user with the given email address is available.
60
+ # @param [String] email_address The email address of the person to find availability for.
61
+ # @param [DateTime] start_time The start of the time range to check as an xs:dateTime.
62
+ # @param [DateTime] end_time The end of the time range to check as an xs:dateTime.
63
+ # @see http://msdn.microsoft.com/en-us/library/aa563800(v=exchg.140)
64
+ def get_user_availability(email_address, start_time, end_time)
65
+ opts = {
66
+ mailbox_data: [ :email =>{:address => email_address} ],
67
+ free_busy_view_options: {
68
+ time_window: {start_time: start_time, end_time: end_time},
69
+ }
70
+ }
71
+ resp = (Viewpoint::EWS::EWS.instance).ews.get_user_availability(opts)
72
+ if(resp.status == 'Success')
73
+ return resp.items
74
+ else
75
+ raise EwsError, "GetUserAvailability produced an error: #{resp.code}: #{resp.message}"
76
+ end
77
+ end
78
+
79
+ # Adds one or more delegates to a principal's mailbox and sets specific access permissions
80
+ # @see http://msdn.microsoft.com/en-us/library/bb856527.aspx
81
+ #
82
+ # @param [String,MailboxUser] delegate_email The user you would like to give delegate access to.
83
+ # This can either be a simple String e-mail address or you can pass in a MailboxUser object.
84
+ # @param [Hash] permissions A hash of folder type keys and permission type values. An example
85
+ # would be {:calendar_folder_permission_level => 'Editor'}. Possible keys are:
86
+ # :calendar_folder_permission_level, :tasks_folder_permission_level, :inbox_folder_permission_level
87
+ # :contacts_folder_permission_level, :notes_folder_permission_level, :journal_folder_permission_level
88
+ # and possible values are: None/Editor/Reviewer/Author/Custom
89
+ # @return [true] This method either returns true or raises an error with the message
90
+ # as to why this operation did not succeed.
91
+ def add_delegate!(delegate_email, permissions)
92
+ # Use a new hash so the passed hash is not modified in case we are in a loop.
93
+ # Thanks to Markus Roberts for pointing this out.
94
+ formatted_perms = {}
95
+ # Modify permissions so we can pass it to the builders
96
+ permissions.each_pair do |k,v|
97
+ formatted_perms[k] = {:text => v}
98
+ end
99
+
100
+ resp = (Viewpoint::EWS::EWS.instance).ews.add_delegate(self.email_address, delegate_email, formatted_perms)
101
+ if(resp.status == 'Success')
102
+ return true
103
+ else
104
+ raise EwsError, "Could not add delegate access for user #{delegate_email}: #{resp.code}, #{resp.message}"
105
+ end
106
+ end
107
+
108
+ def update_delegate!(delegate_email, permissions)
109
+ # Modify permissions so we can pass it to the builders
110
+ formatted_perms = {}
111
+ permissions.each_pair do |k,v|
112
+ formatted_perms[k] = {:text => v}
113
+ end
114
+
115
+ resp = (Viewpoint::EWS::EWS.instance).ews.update_delegate(self.email_address, delegate_email, formatted_perms)
116
+ if(resp.status == 'Success')
117
+ return true
118
+ else
119
+ raise EwsError, "Could not update delegate access for user #{delegate_email}: #{resp.code}, #{resp.message}"
120
+ end
121
+ end
122
+
123
+ def get_delegate_info()
124
+ resp = (Viewpoint::EWS::EWS.instance).ews.get_delegate(self.email_address)
125
+ # if(resp.status == 'Success')
126
+ # return true
127
+ # else
128
+ # raise EwsError, "Could not update delegate access for user #{delegate_email}: #{resp.code}, #{resp.message}"
129
+ # end
130
+ end
131
+
132
+
133
+ private
134
+
135
+
136
+ def simplify!
137
+ @ews_item = @ews_item.inject({}){|m,o|
138
+ m[o.keys.first] = o.values.first[:text];
139
+ m
140
+ }
141
+ end
142
+
143
+ def key_paths
144
+ @key_paths ||= super.merge(MAILBOX_KEY_PATHS)
145
+ end
146
+
147
+ def key_types
148
+ @key_types ||= super.merge(MAILBOX_KEY_TYPES)
149
+ end
150
+
151
+ def key_alias
152
+ @key_alias ||= super.merge(MAILBOX_KEY_ALIAS)
153
+ end
154
+
155
+ end # MailboxUser
156
+ end # Viewpoint::EWS::Types