contextio-lite 0.0.2
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.
- checksums.yaml +7 -0
- data/.gitignore +14 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +22 -0
- data/README.md +114 -0
- data/Rakefile +2 -0
- data/contextio-lite.gemspec +27 -0
- data/lib/contextio.rb +14 -0
- data/lib/contextio/api/abstract_api.rb +213 -0
- data/lib/contextio/api/association_helpers.rb +17 -0
- data/lib/contextio/api/resource.rb +248 -0
- data/lib/contextio/api/resource_collection.rb +193 -0
- data/lib/contextio/lite.rb +43 -0
- data/lib/contextio/lite/api.rb +30 -0
- data/lib/contextio/lite/email_account.rb +48 -0
- data/lib/contextio/lite/email_account_collection.rb +44 -0
- data/lib/contextio/lite/folder.rb +18 -0
- data/lib/contextio/lite/folder_collection.rb +17 -0
- data/lib/contextio/lite/message.rb +77 -0
- data/lib/contextio/lite/message_collection.rb +15 -0
- data/lib/contextio/lite/url_builder.rb +95 -0
- data/lib/contextio/lite/user.rb +61 -0
- data/lib/contextio/lite/user_collection.rb +40 -0
- data/lib/contextio/lite/webhook.rb +43 -0
- data/lib/contextio/lite/webhook_collection.rb +28 -0
- metadata +139 -0
@@ -0,0 +1,30 @@
|
|
1
|
+
require 'contextio/api/abstract_api'
|
2
|
+
require_relative 'url_builder'
|
3
|
+
|
4
|
+
module ContextIO
|
5
|
+
class Lite
|
6
|
+
class API < ContextIO::API::AbstractAPI
|
7
|
+
|
8
|
+
VERSION = 'lite'
|
9
|
+
|
10
|
+
def self.user_agent_string
|
11
|
+
"contextio-#{self.version}-ruby-#{ContextIO.version}"
|
12
|
+
end
|
13
|
+
|
14
|
+
# @param [Object] resource The resource you want the URL for.
|
15
|
+
#
|
16
|
+
# @return [String] The URL for the resource in the API.
|
17
|
+
def self.url_for(resource)
|
18
|
+
ContextIO::Lite::URLBuilder.url_for(resource)
|
19
|
+
end
|
20
|
+
|
21
|
+
# @param [Object] resource The resource you want the URL for.
|
22
|
+
#
|
23
|
+
# @return [String] The URL for the resource in the API.
|
24
|
+
def url_for(resource)
|
25
|
+
ContextIO::Lite::API.url_for(resource)
|
26
|
+
end
|
27
|
+
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
@@ -0,0 +1,48 @@
|
|
1
|
+
require 'contextio/api/resource'
|
2
|
+
require 'contextio/api/association_helpers'
|
3
|
+
|
4
|
+
module ContextIO
|
5
|
+
class Lite
|
6
|
+
class EmailAccount
|
7
|
+
include ContextIO::API::Resource
|
8
|
+
|
9
|
+
self.primary_key = :label
|
10
|
+
self.association_name = :email_account
|
11
|
+
|
12
|
+
has_many :folders
|
13
|
+
|
14
|
+
lazy_attributes :server, :label, :username, :port, :authentication_type,
|
15
|
+
:status, :service_level, :sync_period, :use_ssl, :type
|
16
|
+
private :use_ssl
|
17
|
+
|
18
|
+
# @!attribute [r] use_ssl?
|
19
|
+
# @return [Boolean] Whether or not this source uses SSL.
|
20
|
+
def use_ssl?
|
21
|
+
use_ssl
|
22
|
+
end
|
23
|
+
|
24
|
+
# Updates the email_account.
|
25
|
+
#
|
26
|
+
# @params [Hash{String, Symbol => String}] options See the Context.IO docs
|
27
|
+
# for more details on these fields.
|
28
|
+
def update(options={})
|
29
|
+
it_worked = api.request(:post, resource_url, options)['success']
|
30
|
+
|
31
|
+
if it_worked
|
32
|
+
options.each do |key, value|
|
33
|
+
key = key.to_s.gsub('-', '_')
|
34
|
+
|
35
|
+
instance_variable_set("@#{key}", value)
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
it_worked
|
40
|
+
end
|
41
|
+
|
42
|
+
def delete
|
43
|
+
api.request(:delete, resource_url)['success']
|
44
|
+
end
|
45
|
+
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
@@ -0,0 +1,44 @@
|
|
1
|
+
require 'contextio/api/resource_collection'
|
2
|
+
require_relative 'email_account'
|
3
|
+
|
4
|
+
module ContextIO
|
5
|
+
class Lite
|
6
|
+
class EmailAccountCollection
|
7
|
+
include ContextIO::API::ResourceCollection
|
8
|
+
|
9
|
+
self.resource_class = ContextIO::Lite::EmailAccount
|
10
|
+
self.association_name = :email_accounts
|
11
|
+
|
12
|
+
belongs_to :user
|
13
|
+
|
14
|
+
# Creates a new email_account for an user.
|
15
|
+
#
|
16
|
+
# @param [String] email The email address for the new source.
|
17
|
+
# @param [String] server The address of the server for the source.
|
18
|
+
# @param [String] username The name for logging into the server. Often the
|
19
|
+
# same as the email.
|
20
|
+
# @param [Boolean] use_ssl Whether to use SSL for the new source.
|
21
|
+
# @param [Numeric, String] port The port to connect on.
|
22
|
+
# @param [String] type Currently, only 'IMAP' is supported.
|
23
|
+
# @param [Hash{String, Symbol => String}] options Information you can
|
24
|
+
# provide at creation. Check out the Context.IO documentation for what's
|
25
|
+
# required and what's optional.
|
26
|
+
def create(email, server, username, use_ssl, port, type, options={})
|
27
|
+
api_args = options.merge(
|
28
|
+
:email => email,
|
29
|
+
:server => server,
|
30
|
+
:username => username,
|
31
|
+
:use_ssl => use_ssl ? '1' : '0',
|
32
|
+
:port => port.to_s,
|
33
|
+
:type => type
|
34
|
+
)
|
35
|
+
|
36
|
+
result_hash = api.request(:post, resource_url, api_args)
|
37
|
+
|
38
|
+
result_hash.delete('success')
|
39
|
+
|
40
|
+
resource_class.new(api, result_hash)
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
require 'contextio/api/resource'
|
2
|
+
require 'contextio/api/association_helpers'
|
3
|
+
|
4
|
+
module ContextIO
|
5
|
+
class Lite
|
6
|
+
class Folder
|
7
|
+
include ContextIO::API::Resource
|
8
|
+
|
9
|
+
self.primary_key = :name
|
10
|
+
self.association_name = :folder
|
11
|
+
|
12
|
+
has_many :messages
|
13
|
+
|
14
|
+
lazy_attributes :name, :delimiter, :nb_messages, :nb_unseen_messages
|
15
|
+
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
require 'contextio/api/resource_collection'
|
2
|
+
require_relative 'folder'
|
3
|
+
|
4
|
+
module ContextIO
|
5
|
+
class Lite
|
6
|
+
class FolderCollection
|
7
|
+
include ContextIO::API::ResourceCollection
|
8
|
+
|
9
|
+
self.resource_class = ContextIO::Lite::Folder
|
10
|
+
self.association_name = :folders
|
11
|
+
|
12
|
+
belongs_to :email_account
|
13
|
+
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
@@ -0,0 +1,77 @@
|
|
1
|
+
require 'contextio/api/resource'
|
2
|
+
require 'contextio/api/association_helpers'
|
3
|
+
|
4
|
+
module ContextIO
|
5
|
+
class Lite
|
6
|
+
class Message
|
7
|
+
include ContextIO::API::Resource
|
8
|
+
|
9
|
+
self.primary_key = :message_id
|
10
|
+
self.association_name = :message
|
11
|
+
|
12
|
+
# has_many :body_parts
|
13
|
+
|
14
|
+
lazy_attributes :sent_at, :addresses, :person_info, :email_message_id, :message_id,
|
15
|
+
:attachments, :subject, :folders, :bodies, :references, :in_reply_to,
|
16
|
+
:list_headers, :received_headers
|
17
|
+
|
18
|
+
FLAG_KEYS = %w(seen answered flagged draft deleted)
|
19
|
+
|
20
|
+
private :sent_at, :bodies, :addresses
|
21
|
+
|
22
|
+
def sent
|
23
|
+
@sent ||= Time.at(sent_at)
|
24
|
+
end
|
25
|
+
|
26
|
+
%w(from to bcc cc reply_to).each do |f|
|
27
|
+
define_method(f) do
|
28
|
+
addresses[f]
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
def body_plain
|
33
|
+
self.body(type:'text/plain').map{|b| b['content']}.join
|
34
|
+
end
|
35
|
+
|
36
|
+
def body_html
|
37
|
+
self.body(type:'text/html').map{|b| b['content']}.join
|
38
|
+
end
|
39
|
+
|
40
|
+
def body(options={})
|
41
|
+
@body ||= if @with_constraints.has_key?(:include_body) && @with_constraints[:include_body]==1 then
|
42
|
+
options.has_key?('type') ?
|
43
|
+
self.api_attributes['bodies'].select { |b| b['type']==options['type'] } :
|
44
|
+
self.api_attributes['bodies']
|
45
|
+
else
|
46
|
+
api.request(:get, "#{resource_url}/body", options)['bodies']
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
def flags
|
51
|
+
if @with_constraints.has_key?(:include_flags) && @with_constraints[:include_flags]==1
|
52
|
+
@flags = self.api_attributes['flags']
|
53
|
+
else
|
54
|
+
@flags ||= api.request(:get, "#{resource_url}/flags")['flags']
|
55
|
+
@flags['seen'] = @flags.delete 'read' if @flags.has_key? 'read'
|
56
|
+
@flags = Hash[FLAG_KEYS.map{|f| [f, @flags.include?(f) && @flags[f]]}]
|
57
|
+
end
|
58
|
+
@flags
|
59
|
+
end
|
60
|
+
|
61
|
+
def headers
|
62
|
+
@headers ||= @with_constraints.has_key?(:include_headers) && @with_constraints[:include_headers]==1 ?
|
63
|
+
self.api_attributes['headers'] :
|
64
|
+
api.request(:get, "#{resource_url}/headers")['headers']
|
65
|
+
end
|
66
|
+
|
67
|
+
def raw
|
68
|
+
api.raw_request(:get, "#{resource_url}/raw")
|
69
|
+
end
|
70
|
+
|
71
|
+
def read
|
72
|
+
api.request(:post, "#{resource_url}/read")['success']
|
73
|
+
end
|
74
|
+
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
require 'contextio/api/resource_collection'
|
2
|
+
require_relative 'message'
|
3
|
+
|
4
|
+
module ContextIO
|
5
|
+
class Lite
|
6
|
+
class MessageCollection
|
7
|
+
include ContextIO::API::ResourceCollection
|
8
|
+
|
9
|
+
self.resource_class = ContextIO::Lite::Message
|
10
|
+
self.association_name = :messages
|
11
|
+
|
12
|
+
belongs_to :folder
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,95 @@
|
|
1
|
+
require_relative 'email_account_collection'
|
2
|
+
require_relative 'folder_collection'
|
3
|
+
require_relative 'message_collection'
|
4
|
+
require_relative 'user_collection'
|
5
|
+
require_relative 'webhook_collection'
|
6
|
+
|
7
|
+
module ContextIO
|
8
|
+
class Lite
|
9
|
+
class URLBuilder
|
10
|
+
class Error < StandardError; end
|
11
|
+
|
12
|
+
# Tells you the right URL for a resource to fetch attributes from.
|
13
|
+
#
|
14
|
+
# @param [Contextio::Resource, Contextio::ResourceCollection] resource The
|
15
|
+
# resource or resource collection.
|
16
|
+
#
|
17
|
+
# @return [String] The path for that resource in the API.
|
18
|
+
def self.url_for(resource)
|
19
|
+
if (builder = @registered_urls[resource.class])
|
20
|
+
builder.call(resource)
|
21
|
+
else
|
22
|
+
raise Error, "URL could not be built for unregistered Class: #{resource.class}."
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
# Register a block that calculates the URL for a given resource.
|
27
|
+
#
|
28
|
+
# @param [Class] resource_class The class of the resource you are
|
29
|
+
# registering.
|
30
|
+
# @param [Block] block The code that will compute the url for the
|
31
|
+
# resource. This is actually a path. Start after the version number of
|
32
|
+
# the API in the URL. When a URL is being calculated for a specific
|
33
|
+
# resource, the resource instance will be yielded to the block.
|
34
|
+
#
|
35
|
+
# @example For Accounts
|
36
|
+
# register_url ContextIO::Account do |account|
|
37
|
+
# "accounts/#{account.id}"
|
38
|
+
# end
|
39
|
+
def self.register_url(resource_class, &block)
|
40
|
+
@registered_urls ||= {}
|
41
|
+
@registered_urls[resource_class] = block
|
42
|
+
end
|
43
|
+
|
44
|
+
register_url ContextIO::Lite::UserCollection do
|
45
|
+
'users'
|
46
|
+
end
|
47
|
+
|
48
|
+
register_url ContextIO::Lite::User do |user|
|
49
|
+
"users/#{user.id}"
|
50
|
+
end
|
51
|
+
|
52
|
+
register_url ContextIO::Lite::EmailAccountCollection do |email_accounts|
|
53
|
+
"users/#{email_accounts.user.id}/email_accounts"
|
54
|
+
end
|
55
|
+
|
56
|
+
register_url ContextIO::Lite::EmailAccount do |email_account|
|
57
|
+
"users/#{email_account.user.id}/email_accounts/#{email_account.label}"
|
58
|
+
end
|
59
|
+
|
60
|
+
register_url ContextIO::Lite::FolderCollection do |folders|
|
61
|
+
"users/#{folders.email_account.user.id}/email_accounts/#{uri_encode folders.email_account.label}/folders"
|
62
|
+
end
|
63
|
+
|
64
|
+
register_url ContextIO::Lite::Folder do |folder|
|
65
|
+
"users/#{folder.email_account.user.id}/email_accounts/#{uri_encode folder.email_account.label}/folders/#{uri_encode folder.name}"
|
66
|
+
end
|
67
|
+
|
68
|
+
register_url ContextIO::Lite::MessageCollection do |messages|
|
69
|
+
"users/#{messages.folder.email_account.user.id}/email_accounts/#{uri_encode messages.folder.email_account.label}/folders/#{uri_encode messages.folder.name}/messages"
|
70
|
+
end
|
71
|
+
|
72
|
+
register_url ContextIO::Lite::Message do |message|
|
73
|
+
"users/#{message.folder.email_account.user.id}/email_accounts/#{uri_encode message.folder.email_account.label}/folders/#{uri_encode message.folder.name}/messages/#{uri_encode message.message_id}"
|
74
|
+
end
|
75
|
+
|
76
|
+
|
77
|
+
register_url ContextIO::Lite::WebhookCollection do |webhooks|
|
78
|
+
"users/#{webhooks.user.id}/webhooks"
|
79
|
+
end
|
80
|
+
|
81
|
+
register_url ContextIO::Lite::Webhook do |webhook|
|
82
|
+
"users/#{webhook.user.id}/webhooks/#{webhook.webhook_id}"
|
83
|
+
end
|
84
|
+
|
85
|
+
def self.uri_encode(param)
|
86
|
+
if param.is_a? String
|
87
|
+
URI.encode param
|
88
|
+
else
|
89
|
+
param
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
end
|
94
|
+
end
|
95
|
+
end
|
@@ -0,0 +1,61 @@
|
|
1
|
+
require 'contextio/api/resource'
|
2
|
+
require 'contextio/api/association_helpers'
|
3
|
+
|
4
|
+
module ContextIO
|
5
|
+
class Lite
|
6
|
+
class User
|
7
|
+
include ContextIO::API::Resource
|
8
|
+
|
9
|
+
self.primary_key = :id
|
10
|
+
self.association_name = :user
|
11
|
+
|
12
|
+
has_many :email_accounts
|
13
|
+
has_many :webhooks
|
14
|
+
|
15
|
+
# @!attribute [r] id
|
16
|
+
# @return [String] The id assigned to this account by Context.IO.
|
17
|
+
# @!attribute [r] username
|
18
|
+
# @return [String] The username assigned to this account by Context.IO.
|
19
|
+
# @!attribute [r] first_name
|
20
|
+
# @return [String] The account holder's first name.
|
21
|
+
# @!attribute [r] last_name
|
22
|
+
# @return [String] The account holder's last name.
|
23
|
+
lazy_attributes :id, :email_addresses, :username, :created, :first_name, :last_name
|
24
|
+
private :created
|
25
|
+
|
26
|
+
# @!attribute [r] created_at
|
27
|
+
# @return [Time] The time this account was created (with Context.IO).
|
28
|
+
def created_at
|
29
|
+
@created_at ||= Time.at(created)
|
30
|
+
end
|
31
|
+
|
32
|
+
# Updates the account.
|
33
|
+
#
|
34
|
+
# @param [Hash{String, Symbol => String}] options You can update first_name
|
35
|
+
# or last_name (or both).
|
36
|
+
def update(options={})
|
37
|
+
first_name = options[:first_name] || options['first_name']
|
38
|
+
last_name = options[:last_name] || options['last_name']
|
39
|
+
|
40
|
+
attrs = {}
|
41
|
+
attrs[:first_name] = first_name if first_name
|
42
|
+
attrs[:last_name] = last_name if last_name
|
43
|
+
|
44
|
+
return nil if attrs.empty?
|
45
|
+
|
46
|
+
it_worked = api.request(:post, resource_url, attrs)['success']
|
47
|
+
|
48
|
+
if it_worked
|
49
|
+
@first_name = first_name || @first_name
|
50
|
+
@last_name = last_name || @last_name
|
51
|
+
end
|
52
|
+
|
53
|
+
it_worked
|
54
|
+
end
|
55
|
+
|
56
|
+
def delete
|
57
|
+
api.request(:delete, resource_url)['success']
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
@@ -0,0 +1,40 @@
|
|
1
|
+
require 'contextio/api/resource_collection'
|
2
|
+
require_relative 'user'
|
3
|
+
|
4
|
+
module ContextIO
|
5
|
+
class Lite
|
6
|
+
class UserCollection
|
7
|
+
include ContextIO::API::ResourceCollection
|
8
|
+
|
9
|
+
self.resource_class = ContextIO::Lite::User
|
10
|
+
self.association_name = :accounts
|
11
|
+
|
12
|
+
# Creates a new email account for your Context.IO account.
|
13
|
+
#
|
14
|
+
# @param [Hash{String, Symbol => String}] options Information you can
|
15
|
+
# provide at creation: email, first_name and/or last_name. If the
|
16
|
+
# collection isn't already limited by email, then you must provide it.
|
17
|
+
#
|
18
|
+
# @return [Account] A new email account instance based on the data you
|
19
|
+
# input.
|
20
|
+
def create(options={})
|
21
|
+
email = options.delete(:email) || options.delete('email') ||
|
22
|
+
where_constraints[:email] || where_constraints['email']
|
23
|
+
|
24
|
+
if email.nil?
|
25
|
+
raise ArgumentError, 'You must provide an email for new Users.'
|
26
|
+
end
|
27
|
+
|
28
|
+
result_hash = api.request(
|
29
|
+
:post,
|
30
|
+
resource_url,
|
31
|
+
options.merge(email: email)
|
32
|
+
)
|
33
|
+
|
34
|
+
result_hash.delete('success')
|
35
|
+
|
36
|
+
resource_class.new(api, result_hash)
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|