viberroo 0.2.1 → 0.3.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 8d918d24a9f1cacebd5982601ec2e88efaad61517c8a969d7b78dd74205229c5
4
- data.tar.gz: 3163feb39d9c4f9e9148bca976dabccf7b8b0fc170268149f21b5e87a9f7adab
3
+ metadata.gz: d57993081fac92ff1ebeb1b7ae2da6a269e63d5fdb311f139798e8e4868cf072
4
+ data.tar.gz: '0990bb91aad353fe640c1b4e491fdec405a42a3c3676fe2e3c8bf6bb78dfce9c'
5
5
  SHA512:
6
- metadata.gz: 8d9f58550c03b4a8069ffca12e12aa7ee84c9a9e0906c29db088b598b395197793e47cbbe1cbb31d07b4f90f4ffbe0dff43996f8626dfa051add28e56fac4bd6
7
- data.tar.gz: eaf3eaf19a685622bed73f97b196dd054333e7502844eb3d74021e215fe3073aec48d033bd8f6fd09f6a51394c63546014010254c4fe9d368e3ced1484bc3c87
6
+ metadata.gz: 9b79c7790edd6f836a8a4acd5b5b3bfa10dba7dc4cbecf64ab61131fd9a913a940d1d21331f4a1d6d98e1f58e9d03be60caa5264d7c03c5382a6b4939b026ec3
7
+ data.tar.gz: 9720b62c4fb5f76d42893763ecac41a9cdf5f1d3dc74022ff886d85fb75480e988e673d6c5261aedc83bf0157d3c40a852cbcce692b29dec2d4dcce5d264f0f8
@@ -1,13 +1,18 @@
1
1
  require 'json'
2
- require 'faraday'
3
2
  require 'viberroo/configuration'
4
3
  require 'viberroo/message'
5
4
  require 'viberroo/input'
6
- require 'viberroo/callback'
5
+ require 'viberroo/response'
7
6
  require 'viberroo/bot'
8
7
  require 'logger'
9
8
 
9
+ ##
10
+ # Top namespace for all Viberroo code.
11
+ #
10
12
  module Viberroo
13
+ ##
14
+ # API endpoints.
15
+ #
11
16
  module URL
12
17
  API = 'https://chatapi.viber.com/pa'.freeze
13
18
  WEBHOOK = "#{API}/set_webhook".freeze
@@ -1,92 +1,244 @@
1
+ require 'net/http'
2
+ require 'uri'
3
+
1
4
  module Viberroo
5
+ ##
6
+ # This class represents a server bot/client which communicates to Viber API. Each request sends a http POST request to a particular endpoint, each returns either http response, or parsed response body as specified in configuration.
7
+ #
8
+ # @see Configuration
9
+ #
2
10
  class Bot
3
- def initialize(token: nil, callback: nil)
11
+ ##
12
+ # @example Initializing
13
+ # class ViberController < ApplicationController
14
+ # skip_before_action :verify_authenticity_token
15
+ #
16
+ # def callback
17
+ # @response = Viberroo::Response.new(params.permit!)
18
+ # @bot = Viberroo::Bot.new(response: @response)
19
+ #
20
+ # head :ok
21
+ # end
22
+ # end
23
+ #
24
+ # @param [Response] response **Required**. A callback response.
25
+ # @param [String] token **Optional**. Normally should be provided by `Viberroo.configure.auth_token` but is available here as a shortcut when predefined configuration is undesirable. Takes precedence over `Viberroo.configure.auth_token`.
26
+ #
27
+ # @see Response
28
+ # @see Configuration
29
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#authentication-token
30
+ #
31
+ def initialize(response:, token: nil)
4
32
  Viberroo.configure
5
33
 
6
34
  @headers = {
7
35
  'X-Viber-Auth-Token': token || Viberroo.config.auth_token,
8
36
  'Content-Type': 'application/json'
9
37
  }
10
- @callback = callback
11
- end
12
-
38
+ @response = response
39
+ end
40
+
41
+ ##
42
+ # Sets a webhook by making a request to `/set_webhook`. Necessary for receiving callbacks from Viber.
43
+ # For security reasons only URLs with valid and official SSL certificate from a trusted CA will be allowed. `ngrok` is a good workaround for development convenience.
44
+ #
45
+ # @example Setup webhook with rake task
46
+ # namespace :viber do
47
+ # task set_webhook: :environment do
48
+ # Viberroo::Bot.new.set_webhook(
49
+ # url: 'https://<your_ngrok_public_address>/viber',
50
+ # event_types: %w[conversation_started subscribed unsubscribed],
51
+ # send_name: true,
52
+ # send_photo: true
53
+ # )
54
+ # end
55
+ # end
56
+ #
57
+ # @param [String] url **Required**. HTTPs callback URL.
58
+ # @param [Array] event_types **Optional**. Indicates the types of Viber events that the bot will receive. Leaving this parameter out will include all events. **API default**: `%w[delivered seen failed subscribed unsubscribed conversation_started]`.
59
+ # @param [true, false] send_name **Optional**. Indicates whether or not the bot should receive the user name. **API default**: `false`.
60
+ # @param [true, false] send_photo **Optional**. Indicates whether or not the bot should receive the user photo. **API default**: `false`.
61
+ #
62
+ # @return [Net::HTTPResponse || Hash]
63
+ #
64
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#webhooks
65
+ #
13
66
  def set_webhook(url:, event_types: nil, send_name: nil, send_photo: nil)
14
67
  request(URL::WEBHOOK, url: url, event_types: event_types,
15
68
  send_name: send_name, send_photo: send_photo)
16
69
  end
17
70
 
18
- def set_webhook!(url:, event_types: nil, send_name: nil, send_photo: nil)
19
- parse set_webhook(url: url, event_types: event_types,
20
- send_name: send_name, send_photo: send_photo)
21
- end
22
-
71
+ ##
72
+ # Removes a webhook by making a request to `/set_webhook`.
73
+ #
74
+ # @example Remove webhook with rake task
75
+ # namespace :viber do
76
+ # task remove_webhook: :environment do
77
+ # Viberroo::Bot.new.remove_webhook
78
+ # end
79
+ # end
80
+ #
81
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#removing-your-webhook
82
+ #
83
+ # @return [Net::HTTPResponse || Hash]
84
+ #
23
85
  def remove_webhook
24
86
  request(URL::WEBHOOK, url: '')
25
87
  end
26
88
 
27
- def remove_webhook!
28
- parse remove_webhook
29
- end
30
-
89
+ ##
90
+ # Sends a message to a user by making a request to `/send_message`.
91
+ #
92
+ # @example Send a plain message
93
+ # go_somewhere = Viberroo::Input.url_button({
94
+ # Columns: 3,
95
+ # Rows: 2,
96
+ # Text: 'Mystery link',
97
+ # ActionBody: 'somewhere.com'
98
+ # })
99
+ #
100
+ # keyboard = Viberroo::Input.keyboard(Buttons: [go_somewhere])
101
+ # message = Viberroo::Message.plain(text: 'Click if you dare.')
102
+ #
103
+ # @bot.send(message: message, keyboard: keyboard)
104
+ #
105
+ # @example Send a rich media
106
+ # search = Viberroo::Input.reply_button({
107
+ # Columns: 4,
108
+ # Rows: 3,
109
+ # ActionBody: '/search',
110
+ # Text: 'Search something...'
111
+ # }
112
+ #
113
+ # locate = Viberroo::Input.reply_button({
114
+ # Columns: 4,
115
+ # Rows: 3,
116
+ # ActionBody: '/near_me'
117
+ # }
118
+ #
119
+ # browse = Viberroo::Input.url_button({
120
+ # Columns: 4,
121
+ # Rows: 2,
122
+ # ActionBody: 'parrot.live',
123
+ # Text: 'Browse something wierd'
124
+ # }
125
+ #
126
+ # rich_message = Viberroo::Message.rich(rich_media: { ButtonsGroupColumns: 4,
127
+ # ButtonsGroupRows: 6,
128
+ # Buttons: [search, locate, browse] })
129
+ #
130
+ # @bot.send(message: rich_message)
131
+ #
132
+ # @param [Hash] message **Required**. One of the message types to send.
133
+ # @param [Hash] keyboard **Optional**. A keyboard that can be attached to a message.
134
+ #
135
+ # @return [Net::HTTPResponse || Hash]
136
+ #
137
+ # @see Message
138
+ # @see Input
139
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#send-message
140
+ # @see https://viber.github.io/docs/tools/keyboards/#buttons-parameters
141
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#keyboards
142
+ #
31
143
  def send(message:, keyboard: {})
32
144
  request(URL::MESSAGE,
33
- { receiver: @callback&.user_id }.merge(message).merge(keyboard))
34
- end
35
-
36
- def send!(message:, keyboard: {})
37
- parse self.send(message: message, keyboard: keyboard)
38
- end
39
-
145
+ { receiver: @response&.user_id }.merge(message).merge(keyboard))
146
+ end
147
+
148
+ ##
149
+ # @note This request has a rate limit of 500 requests in a 10 seconds window.
150
+ #
151
+ # Broadcasts a messages to subscribed users by making a request to `/broadcast_message`.
152
+ #
153
+ # @example Broadcast simple message
154
+ # message = Viberroo::Message.plain(text: 'Howdy.')
155
+ # response = @bot.broadcast(message: message, to: ViberSubscriber.sample(500).pluck(:viber_id))
156
+ #
157
+ # @param [Hash] message **Required**. One of the message types to broadcast.
158
+ # @param [Array] to **Required**. List of user ids to broadcast to. Specified users need to be subscribed.
159
+ #
160
+ # @return [Net::HTTPResponse || Hash]
161
+ #
162
+ # @see Message
163
+ # @see Input
164
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#broadcast-message
165
+ #
40
166
  def broadcast(message:, to:)
41
167
  request(URL::BROADCAST_MESSAGE, message.merge(broadcast_list: to))
42
168
  end
43
169
 
44
- def broadcast!(message:, to:)
45
- parse broadcast(message: message, to: to)
46
- end
47
-
170
+ ##
171
+ # Retrieves account info by making a request to `/get_account_info`. These settings can be set in you Viber admin panel.
172
+ #
173
+ # @return [Net::HTTPResponse || Hash]
174
+ #
175
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#get-account-info
176
+ #
48
177
  def get_account_info
49
178
  request(URL::GET_ACCOUNT_INFO)
50
179
  end
51
180
 
52
- def get_account_info!
53
- parse get_account_info
54
- end
55
-
181
+ ##
182
+ # @note This request can be sent twice during a 12 hours period for each user ID.
183
+ #
184
+ #
185
+ # @example
186
+ # response = @bot.get_user_details(id: ViberSubscriber.sample.viber_id)
187
+ #
188
+ # Retrieves details of particular user by making a request to `/get_user_details`.
189
+ #
190
+ # @return [Net::HTTPResponse || Hash]
191
+ #
192
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#get-user-details
193
+ #
56
194
  def get_user_details(id:)
57
195
  request(URL::GET_USER_DETAILS, id: id)
58
196
  end
59
197
 
60
- def get_user_details!(id:)
61
- parse get_user_details(id: id)
62
- end
63
-
198
+ ##
199
+ # @note The API supports up to 100 user id per request and those users must be subscribed to the account.
200
+ #
201
+ # Retrieves a list of user status by making a request to `get_online`.
202
+ #
203
+ #
204
+ # @example
205
+ # response = @bot.get_online(ids: ViberSubscriber.sample(100).pluck(:viber_id))
206
+ #
207
+ # @param [Array] message **Required**. List of user ids.
208
+ #
209
+ # @return [Net::HTTPResponse || Hash]
210
+ #
211
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#get-online
212
+ #
64
213
  def get_online(ids:)
65
214
  request(URL::GET_ONLINE, ids: ids)
66
215
  end
67
216
 
68
- def get_online!(ids:)
69
- parse get_online(ids: ids)
70
- end
71
-
72
217
  private
73
218
 
219
+ # @!visibility private
74
220
  def request(url, params = {})
75
- response = Faraday.post(url, compact(params).to_json, @headers)
76
- message = "##{caller_name} -- #{response.body}"
77
- Viberroo.config.logger&.info(message)
221
+ uri = URI(url)
78
222
 
79
- response
80
- end
223
+ response = Net::HTTP.start(uri.host, uri.port, use_ssl: true) do |http|
224
+ request = Net::HTTP::Post.new(uri, @headers)
225
+ request.body = compact(params).to_json
226
+
227
+ http.request(request)
228
+ end
229
+
230
+ Viberroo.config.logger&.info("##{caller_name} -- #{response.body}")
81
231
 
82
- def parse(request)
83
- JSON.parse(request.body)
232
+ Viberroo.config.parse_response_body ? JSON.parse(response.body) : response
84
233
  end
85
234
 
235
+ # @!visibility private
236
+ # Extends Ruby version compability from 2.4 to 2.3.
86
237
  def compact(params)
87
238
  params.delete_if { |_, v| v.nil? }
88
239
  end
89
240
 
241
+ # @!visibility private
90
242
  def caller_name
91
243
  caller[1][/`.*'/][1..-2]
92
244
  end
@@ -1,15 +1,53 @@
1
1
  module Viberroo
2
2
  class << self
3
+ # Accessor for global configuration.
3
4
  attr_accessor :config
4
5
  end
5
6
 
7
+ ##
8
+ # Yields the global configuration to a block. Returns existing configuration
9
+ # if one was defined earlier.
10
+ # @yield [Configuration] global configuration
11
+ #
12
+ # @example
13
+ # RSpec.configure do |config|
14
+ # config.auth_token = '445da6az1s345z78-dazcczb2542zv51a-e0vc5fva17480im9'
15
+ # config.parse_response_body = false
16
+ # end
17
+ #
18
+ # @see Viberroo::Configuration
19
+ #
6
20
  def self.configure
7
21
  self.config ||= Configuration.new
8
22
  yield(config) if block_given?
9
23
  end
10
24
 
25
+ ##
26
+ # Stores runtime configuration information.
27
+ #
11
28
  class Configuration
12
- attr_accessor :logger, :auth_token
29
+ ##
30
+ # Specifies logger.
31
+ #
32
+ # @return [Logger]
33
+ attr_accessor :logger
34
+
35
+ ##
36
+ # Stores Viber API authentication token.
37
+ # Necessary for the bot to send API requests.
38
+ #
39
+ # @return [String]
40
+ #
41
+ # @see Bot#set_webhook
42
+ attr_accessor :auth_token
43
+
44
+ ##
45
+ # Specifies whether to parse response body of Bot requests.
46
+ #
47
+ # @return [true || false]
48
+ #
49
+ # @see Bot
50
+ attr_accessor :parse_response_body
13
51
 
14
52
  def initialize
15
53
  @auth_token = nil
@@ -18,6 +56,8 @@ module Viberroo
18
56
  @logger.formatter = proc do |severity, datetime, _, msg|
19
57
  "[#{datetime}] #{severity} Viberroo::Bot #{msg}\n"
20
58
  end
59
+
60
+ @parse_response_body = true
21
61
  end
22
62
  end
23
63
  end
@@ -1,29 +1,108 @@
1
1
  module Viberroo
2
+ ##
3
+ # This class' methods serve as declarative wrappers with predefined
4
+ # types for UI elements such as buttons and keyboards. Buttons can be combined
5
+ # with a keyboard or used in rich messages. Only basic parameters are
6
+ # specified in this documentation, to see all possibilities please consult
7
+ # official Viber API documentation.
8
+ #
9
+ # @see https://viber.github.io/docs/tools/keyboards/#general-keyboard-parameters
10
+ # @see https://viber.github.io/docs/tools/keyboards/#buttons-parameters
11
+ #
2
12
  class Input
13
+ ##
14
+ # A keyboard that can be attached to any message.
15
+ #
16
+ # @example
17
+ # go_somewhere = Viberroo::Input.url_button({
18
+ # Columns: 3,
19
+ # Rows: 2,
20
+ # Text: 'Mystery link',
21
+ # ActionBody: 'somewhere.com'
22
+ # })
23
+ #
24
+ # keyboard = Input.keyboard(Buttons: [go_somewhere])
25
+ #
26
+ # @see https://developers.viber.com/docs/tools/keyboards/#general-keyboard-parameters
27
+ #
3
28
  def self.keyboard(params)
4
29
  { keyboard: { Type: 'keyboard' }.merge(params) }
5
30
  end
6
31
 
32
+ ##
33
+ # A reply button, when tapped sends it's body as a message.
34
+ #
35
+ # @example
36
+ # button = Viberroo::Input.reply_button({
37
+ # Columns: 4,
38
+ # Rows: 3,
39
+ # ActionBody: '/search_cookies',
40
+ # Text: 'I want some cookies.'
41
+ # }
42
+ #
43
+ # @see https://developers.viber.com/docs/tools/keyboards/#buttons-parameters
44
+ #
7
45
  def self.reply_button(params)
8
46
  { ActionType: 'reply' }.merge(params)
9
47
  end
10
48
 
49
+ ##
50
+ # A URL button, when tapped opens specified URL.
51
+ #
52
+ # @example
53
+ # button = Viberroo::Input.url_button({
54
+ # Columns: 4,
55
+ # Rows: 2,
56
+ # ActionBody: 'parrot.live',
57
+ # Text: 'Browse something weird'
58
+ # }
59
+ #
60
+ # @see https://developers.viber.com/docs/tools/keyboards/#buttons-parameters
61
+ #
11
62
  def self.url_button(params)
12
63
  { ActionType: 'open-url' }.merge(params)
13
64
  end
14
65
 
66
+ ##
67
+ # @note Not supported on desktop.
68
+ #
69
+ # Location picker button, gives ability to pick a location on the map.
70
+ #
71
+ # @example
72
+ # button = Viberroo::Input.location_picker_button(location: { lat: 48.9215, lon: 24.7097 })
73
+ #
74
+ # @see https://developers.viber.com/docs/tools/keyboards/#buttons-parameters
75
+ #
15
76
  def self.location_picker_button(params)
16
77
  { ActionType: 'location-picker',
17
78
  min_api_version: 3
18
79
  }.merge(params)
19
80
  end
20
81
 
82
+ ##
83
+ # @note Not supported on desktop.
84
+ #
85
+ # Share phone button.
86
+ #
87
+ # @example
88
+ # button = Viberroo::Input.share_phone_button(contact: { name: 'Gwythyr', phone_number: '12343214' })
89
+ #
90
+ # @see https://developers.viber.com/docs/tools/keyboards/#buttons-parameters
91
+ #
21
92
  def self.share_phone_button(params)
22
93
  { ActionType: 'share-phone',
23
94
  min_api_version: 3
24
95
  }.merge(params)
25
96
  end
26
97
 
98
+ ##
99
+ # A button that does nothing, for decoration purposes.
100
+ #
101
+ # @example
102
+ # button = Viberroo::Input.none_button(Text: 'Purely decorative.')
103
+ #
104
+ # @see https://developers.viber.com/docs/tools/keyboards/#buttons-parameters
105
+ #
27
106
  def self.none_button(params = {})
28
107
  { ActionType: 'none' }.merge(params)
29
108
  end
@@ -1,37 +1,191 @@
1
1
  module Viberroo
2
+ ##
3
+ # This class' methods serve as declarative wrappers with predefined types for
4
+ # each message type Viber API offers.
5
+ #
6
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#message-types
7
+ #
2
8
  class Message
9
+ ##
10
+ # Simple text message.
11
+ #
12
+ # @example
13
+ # message = Viberroo::Message.plain(text: 'Hello there!')
14
+ #
15
+ # @param [Hash] params
16
+ # @option params [String] text **Required**.
17
+ #
18
+ # @return [Hash]
19
+ #
20
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#text-message
21
+ #
3
22
  def self.plain(params)
4
23
  { type: :text }.merge(params)
5
24
  end
6
25
 
26
+ ##
27
+ # The Rich Media message type allows sending messages with pre-defined layout,
28
+ # including height (rows number), width (columns number), text, images and buttons.
29
+ #
30
+ # @example Send a rich media
31
+ # search = Button.reply({
32
+ # Columns: 4,
33
+ # Rows: 3,
34
+ # ActionBody: '/search',
35
+ # Text: 'Search something...'
36
+ # }
37
+ #
38
+ # locate = Button.reply({
39
+ # Columns: 4,
40
+ # Rows: 3,
41
+ # ActionBody: '/near_me'
42
+ # }
43
+ #
44
+ # browse = Button.url({
45
+ # Columns: 4,
46
+ # Rows: 2,
47
+ # ActionBody: 'parrot.live',
48
+ # Text: 'Browse something wierd'
49
+ # }
50
+ #
51
+ # @bot.send_rich_media(
52
+ # rich_media: {
53
+ # ButtonsGroupColumns: 4,
54
+ # ButtonsGroupRows: 6,
55
+ # Buttons: [search, locate, browse]
56
+ # }
57
+ # )
58
+ #
59
+ # @param [Hash] params
60
+ # @option params [Hash] rich_media
61
+ # @option params [Integer] rich_media.ButtonsGroupColumns Number of columns per carousel content block. Possible values 1 - 6. **API Default**: 6.
62
+ # @option params [Integer] rich_media.ButtonsGroupRows Number of rows per carousel content block. Possible values 1 - 7. **API Default**: 7.
63
+ # @option params [Hash] rich_media.Buttons Array of buttons. Max of 6 * `ButtonsGroupColumns` * `ButtonsGroupRows`.
64
+ #
65
+ # @return [Hash]
66
+ #
67
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#rich-media-message--carousel-content-message
68
+ #
7
69
  def self.rich(params)
8
70
  { type: :rich_media, min_api_version: 2 }.merge(params)
9
71
  end
10
72
 
73
+ ##
74
+ # Location message.
75
+ #
76
+ # @example
77
+ # message = Message.location(location: { lat: '48.9215', lon: '24.7097' })
78
+ #
79
+ # @param [Hash] params
80
+ # @option params [Hash] location
81
+ # @option params [Float] location.lat **Required**. Latitude
82
+ # @option params [Float] location.lon **Required**. Longitude
83
+ #
84
+ # @return [Hash]
85
+ #
86
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#location-message
87
+ #
11
88
  def self.location(params)
12
89
  { type: :location }.merge(params)
13
90
  end
14
91
 
92
+ ##
93
+ # Picture message.
94
+ #
95
+ # @note Max image size: 1MB on iOS, 3MB on Android.
96
+ #
97
+ # @param [Hash] params
98
+ # @option params [String] media **Required**. Image URL. Allowed extensions: .jpeg, .png .gif. Animated GIFs can be sent as URL messages or file messages.
99
+ # @option params [String] text **Optional**. Max 120 characters.
100
+ # @option params [String] thumbnail **Optional**. Thumbnail URL. Max size 100 kb. Recommended: 400x400.
101
+ #
102
+ # @return [Hash]
103
+ #
104
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#picture-message
105
+ #
15
106
  def self.picture(params = {})
16
107
  { type: :picture, text: '' }.merge(params)
17
108
  end
18
109
 
110
+ ##
111
+ # Video message.
112
+ #
113
+ # @note Max video size is 26MB.
114
+ #
115
+ # @param [Hash] params
116
+ # @option params [String] media **Required**. URL of the video (MP4, H264). Only MP4 and H264 are supported.
117
+ # @option params [Integer] size **Required**. Size of the video in bytes.
118
+ # @option params [Integer] duration **Optional**. Duration in seconds. Max value - 180.
119
+ # @option params [String] thumbnail **Optional**. Thumbnail URL. Max size 100 kb. Recommended: 400x400. Only JPEG format is supported.
120
+ #
121
+ # @return [Hash]
122
+ #
123
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#video-message
124
+ #
19
125
  def self.video(params = {})
20
126
  { type: :video }.merge(params)
21
127
  end
22
128
 
129
+ ##
130
+ # File message.
131
+ #
132
+ # @note Max file size is 50MB.
133
+ #
134
+ # @param [Hash] params
135
+ # @option params [String] media **Required**. File URL.
136
+ # @option params [Integer] size **Required**. File size in bytes.
137
+ # @option params [String] file_name **Required**. Name of the file, should include extension. Max 256 characters (including extension).
138
+ #
139
+ # @return [Hash]
140
+ #
141
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#file-message
142
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#forbiddenFileFormats
143
+ #
23
144
  def self.file(params = {})
24
145
  { type: :file }.merge(params)
25
146
  end
26
147
 
148
+ ##
149
+ # Contact message.
150
+ #
151
+ # @param [Hash] params
152
+ # @option params [Hash] contact
153
+ # @option params [Float] contact.name **Required**. Name of the contact. Max 28 characters.
154
+ # @option params [Float] contact.phone_number **Required**. Phone number of the contact. Max 18 characters.
155
+ #
156
+ # @return [Hash]
157
+ #
158
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#contact-message
159
+ #
27
160
  def self.contact(params = {})
28
161
  { type: :contact }.merge(params)
29
162
  end
30
163
 
164
+ ##
165
+ # URL message.
166
+ #
167
+ # @param [Hash] params
168
+ # @option params [String] media **Required**. Max 2000 characters.
169
+ #
170
+ # @return [Hash]
171
+ #
172
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#url-message
173
+ #
31
174
  def self.url(params = {})
32
175
  { type: :url }.merge(params)
33
176
  end
34
177
 
178
+ ##
179
+ # Sticker message.
180
+ #
181
+ # @param [Hash] params
182
+ # @option params [Integer] sticker_id **Required**. Max 2000 characters.
183
+ #
184
+ # @return [Hash]
185
+ #
186
+ # @see https://developers.viber.com/docs/api/rest-bot-api/#sticker-message
187
+ # @see https://developers.viber.com/docs/tools/sticker-ids/
188
+ #
35
189
  def self.sticker(params = {})
36
190
  { type: :sticker }.merge(params)
37
191
  end
@@ -0,0 +1,51 @@
1
+ require 'recursive-open-struct'
2
+
3
+ module Viberroo
4
+ ##
5
+ # Wraps callback response and provides helper methods for easier parameter
6
+ # access.
7
+ class Response
8
+
9
+ ##
10
+ # Accessor for response parameters.
11
+ attr_reader :params
12
+
13
+ ##
14
+ # @example
15
+ # class ViberController < ApplicationController
16
+ # skip_before_action :verify_authenticity_token
17
+ #
18
+ # def callback
19
+ # @response = Viberroo::Response.new(params.permit!)
20
+ # @bot = Viberroo::Bot.new(response: @response)
21
+ #
22
+ # head :ok
23
+ # end
24
+ # end
25
+ #
26
+ # @param [Hash] params Parameters from API callback.
27
+ #
28
+ def initialize(params)
29
+ @params = RecursiveOpenStruct.new(params.to_h)
30
+ end
31
+
32
+ ##
33
+ # Unifies user id access. Different callback events return user id differently.
34
+ # This method unifies user id access interface based on callback event type.
35
+ # Original user id params remain available in `params` attribute reader.
36
+ # @return [Integer || nil]
37
+ #
38
+ def user_id
39
+ case @params.event
40
+ when 'conversation_started', 'subscribed'
41
+ @params.user.id
42
+ when 'unsubscribed', 'delivered', 'seen', 'failed'
43
+ @params.user_id
44
+ when 'message'
45
+ @params.sender.id
46
+ else
47
+ @params.dig(:user, :id)
48
+ end
49
+ end
50
+ end
51
+ end
@@ -1,3 +1,3 @@
1
1
  module Viberroo
2
- VERSION = '0.2.1'.freeze
2
+ VERSION = '0.3.2'.freeze
3
3
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: viberroo
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.1
4
+ version: 0.3.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Viktor Habchak
@@ -10,20 +10,6 @@ bindir: bin
10
10
  cert_chain: []
11
11
  date: 2020-03-19 00:00:00.000000000 Z
12
12
  dependencies:
13
- - !ruby/object:Gem::Dependency
14
- name: faraday
15
- requirement: !ruby/object:Gem::Requirement
16
- requirements:
17
- - - "~>"
18
- - !ruby/object:Gem::Version
19
- version: 1.0.0
20
- type: :runtime
21
- prerelease: false
22
- version_requirements: !ruby/object:Gem::Requirement
23
- requirements:
24
- - - "~>"
25
- - !ruby/object:Gem::Version
26
- version: 1.0.0
27
13
  - !ruby/object:Gem::Dependency
28
14
  name: recursive-open-struct
29
15
  requirement: !ruby/object:Gem::Requirement
@@ -46,10 +32,10 @@ extra_rdoc_files: []
46
32
  files:
47
33
  - lib/viberroo.rb
48
34
  - lib/viberroo/bot.rb
49
- - lib/viberroo/callback.rb
50
35
  - lib/viberroo/configuration.rb
51
36
  - lib/viberroo/input.rb
52
37
  - lib/viberroo/message.rb
38
+ - lib/viberroo/response.rb
53
39
  - lib/viberroo/version.rb
54
40
  homepage: https://github.com/vikdotdev/viberroo
55
41
  licenses:
@@ -73,5 +59,5 @@ requirements: []
73
59
  rubygems_version: 3.0.3
74
60
  signing_key:
75
61
  specification_version: 4
76
- summary: Viber bot for Ruby.
62
+ summary: Viber bot for Ruby / Rails.
77
63
  test_files: []
@@ -1,24 +0,0 @@
1
- require 'recursive-open-struct'
2
-
3
- module Viberroo
4
- class Callback
5
- attr_reader :params
6
-
7
- def initialize(params)
8
- @params = RecursiveOpenStruct.new params.to_h
9
- end
10
-
11
- def user_id
12
- case @params.event
13
- when 'conversation_started', 'subscribed'
14
- @params.user.id
15
- when 'unsubscribed', 'delivered', 'seen', 'failed'
16
- @params.user_id
17
- when 'message'
18
- @params.sender.id
19
- else
20
- @params.dig(:user, :id)
21
- end
22
- end
23
- end
24
- end