vonage 7.18.0 → 8.0.0.beta

Sign up to get free protection for your applications and to get access to all the features.
Files changed (72) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +10 -271
  3. data/lib/vonage/applications.rb +4 -12
  4. data/lib/vonage/client.rb +4 -32
  5. data/lib/vonage/client_error.rb +1 -1
  6. data/lib/vonage/config.rb +3 -7
  7. data/lib/vonage/errors.rb +20 -37
  8. data/lib/vonage/gsm7.rb +1 -1
  9. data/lib/vonage/jwt.rb +0 -17
  10. data/lib/vonage/keys.rb +7 -1
  11. data/lib/vonage/logger.rb +3 -5
  12. data/lib/vonage/messaging/channels/viber.rb +1 -8
  13. data/lib/vonage/messaging/channels/whats_app.rb +1 -3
  14. data/lib/vonage/messaging.rb +0 -11
  15. data/lib/vonage/namespace.rb +58 -128
  16. data/lib/vonage/numbers.rb +6 -29
  17. data/lib/vonage/server_error.rb +1 -1
  18. data/lib/vonage/signature.rb +5 -5
  19. data/lib/vonage/sms.rb +20 -20
  20. data/lib/vonage/version.rb +1 -1
  21. data/lib/vonage/video/archives.rb +187 -0
  22. data/lib/vonage/video/list_response.rb +11 -0
  23. data/lib/vonage/video/moderation.rb +73 -0
  24. data/lib/vonage/video/signals.rb +55 -0
  25. data/lib/vonage/video/streams.rb +76 -0
  26. data/lib/vonage/video.rb +91 -0
  27. data/lib/vonage/voice/actions/connect.rb +3 -27
  28. data/lib/vonage/voice/actions/pay.rb +107 -0
  29. data/lib/vonage/voice/actions/talk.rb +2 -11
  30. data/lib/vonage/voice/talk.rb +1 -11
  31. data/lib/vonage/voice.rb +0 -22
  32. data/lib/vonage.rb +0 -1
  33. data/vonage.gemspec +1 -2
  34. metadata +14 -59
  35. data/lib/vonage/api_error.rb +0 -33
  36. data/lib/vonage/meetings/applications.rb +0 -25
  37. data/lib/vonage/meetings/dial_in_numbers/list_response.rb +0 -11
  38. data/lib/vonage/meetings/dial_in_numbers.rb +0 -23
  39. data/lib/vonage/meetings/recordings.rb +0 -36
  40. data/lib/vonage/meetings/rooms/list_response.rb +0 -11
  41. data/lib/vonage/meetings/rooms.rb +0 -155
  42. data/lib/vonage/meetings/sessions/list_response.rb +0 -11
  43. data/lib/vonage/meetings/sessions.rb +0 -28
  44. data/lib/vonage/meetings/themes/list_response.rb +0 -11
  45. data/lib/vonage/meetings/themes.rb +0 -218
  46. data/lib/vonage/meetings.rb +0 -38
  47. data/lib/vonage/proactive_connect/events/list_response.rb +0 -11
  48. data/lib/vonage/proactive_connect/events.rb +0 -68
  49. data/lib/vonage/proactive_connect/item.rb +0 -104
  50. data/lib/vonage/proactive_connect/items/file_response.rb +0 -32
  51. data/lib/vonage/proactive_connect/items/list_response.rb +0 -11
  52. data/lib/vonage/proactive_connect/items.rb +0 -107
  53. data/lib/vonage/proactive_connect/list.rb +0 -168
  54. data/lib/vonage/proactive_connect/lists/list_response.rb +0 -11
  55. data/lib/vonage/proactive_connect/lists.rb +0 -35
  56. data/lib/vonage/proactive_connect.rb +0 -33
  57. data/lib/vonage/subaccounts/balance_transfers/list_response.rb +0 -11
  58. data/lib/vonage/subaccounts/credit_transfers/list_response.rb +0 -11
  59. data/lib/vonage/subaccounts/list_response.rb +0 -15
  60. data/lib/vonage/subaccounts.rb +0 -203
  61. data/lib/vonage/users/list_response.rb +0 -11
  62. data/lib/vonage/users.rb +0 -156
  63. data/lib/vonage/verify2/channels/email.rb +0 -38
  64. data/lib/vonage/verify2/channels/silent_auth.rb +0 -32
  65. data/lib/vonage/verify2/channels/sms.rb +0 -39
  66. data/lib/vonage/verify2/channels/voice.rb +0 -32
  67. data/lib/vonage/verify2/channels/whats_app.rb +0 -38
  68. data/lib/vonage/verify2/channels/whats_app_interactive.rb +0 -32
  69. data/lib/vonage/verify2/start_verification_options.rb +0 -62
  70. data/lib/vonage/verify2/workflow.rb +0 -39
  71. data/lib/vonage/verify2/workflow_builder.rb +0 -25
  72. data/lib/vonage/verify2.rb +0 -93
@@ -0,0 +1,187 @@
1
+ # typed: true
2
+ # frozen_string_literal: true
3
+
4
+ module Vonage
5
+ class Video::Archives < Namespace
6
+ include Keys
7
+
8
+ self.authentication = BearerToken
9
+
10
+ self.request_body = JSON
11
+
12
+ self.host = :video_host
13
+
14
+ # Get a list of archives for a specified Vonage application.
15
+ #
16
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
17
+ #
18
+ # @param [optional, Integer] :offset
19
+ #
20
+ # @param [optional, Integer] :count
21
+ #
22
+ # @param [optional, String] :session_id
23
+ #
24
+ # TODO: add auto_advance option
25
+ #
26
+ # @return [ListResponse]
27
+ #
28
+ # @see TODO: add docs link
29
+ #
30
+ def list(application_id: @config.application_id, **params)
31
+ # TODO: raise error if application_id is nil
32
+
33
+ request('/v2/project/' + application_id + '/archive', params: params, response_class: Video::ListResponse)
34
+ end
35
+
36
+ # Return information for specified archive.
37
+ #
38
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
39
+ #
40
+ # @param [required, String] archive_id
41
+ #
42
+ # @return [Response]
43
+ #
44
+ # @see TODO: add docs link
45
+ #
46
+ def info(application_id: @config.application_id, archive_id:)
47
+ # TODO: raise error if application_id is nil
48
+
49
+ request('/v2/project/' + application_id + '/archive/' + archive_id)
50
+ end
51
+
52
+ # Create a new archive.
53
+ #
54
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
55
+ #
56
+ # @param [required, String] :session_id
57
+ #
58
+ # @param [optional, String] :hasAudio
59
+ #
60
+ # @param [optional, String] :hasVideo
61
+ #
62
+ # @param [optional, String] :name
63
+ #
64
+ # @param [optional, String] :outputMode
65
+ #
66
+ # @param [optional, String] :resolution
67
+ #
68
+ # @param [optional, String] :streamMode
69
+ #
70
+ # @param [optional, String] :multiArchiveTag
71
+ #
72
+ # @param [optional, Hash] :layout
73
+ #
74
+ # @option layout [optional, String] :type
75
+ #
76
+ # @option layout [optional, String] :stylesheet
77
+ #
78
+ # @option layout [optional, String] :screenshareType
79
+ #
80
+ # @return [Response]
81
+ #
82
+ # @see TODO: add docs link
83
+ #
84
+ def start(application_id: @config.application_id, **params)
85
+ # TODO: raise error if application_id is nil
86
+ # TODO: raise error if session_id is nil
87
+
88
+ request('/v2/project/' + application_id + '/archive', params: params, type: Post)
89
+ end
90
+
91
+ # Stop recording a specified archive.
92
+ #
93
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
94
+ #
95
+ # @param [required, String] archive_id
96
+ #
97
+ # @return [Response]
98
+ #
99
+ # @see TODO: add docs link
100
+ #
101
+ def stop(application_id: @config.application_id, archive_id:)
102
+ # TODO: raise error if application_id is nil
103
+
104
+ request('/v2/project/' + application_id + '/archive/' + archive_id + '/stop', type: Post)
105
+ end
106
+
107
+ # Delete a specified archive.
108
+ #
109
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
110
+ #
111
+ # @param [required, String] archive_id
112
+ #
113
+ # @return [Response]
114
+ #
115
+ # @see TODO: add docs link
116
+ #
117
+ def delete(application_id: @config.application_id, archive_id:)
118
+ # TODO: raise error if application_id is nil
119
+
120
+ request('/v2/project/' + application_id + '/archive/' + archive_id, type: Delete)
121
+ end
122
+
123
+ # Add a stream to a composed archive that was started with the streamMode set to "manual".
124
+ #
125
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
126
+ #
127
+ # @param [required, String] archive_id
128
+ #
129
+ # @param [required, String] add_stream The ID of the stream to be added
130
+ #
131
+ # @param [optional, Boolean] has_audio
132
+ #
133
+ # @param [optional, Boolean] has_video
134
+ #
135
+ # @return [Response]
136
+ #
137
+ # @see TODO: add docs link
138
+ #
139
+ def add_stream(application_id: @config.application_id, archive_id:, **params)
140
+ # TODO: raise error if application_id is nil
141
+ # TODO: raise error if add_stream is nil
142
+
143
+ request('/v2/project/' + application_id + '/archive/' + archive_id + '/streams', params: camelcase(params), type: Patch)
144
+ end
145
+
146
+ # Remove a stream from a composed archive that was started with the streamMode set to "manual".
147
+ #
148
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
149
+ #
150
+ # @param [required, String] archive_id
151
+ #
152
+ # @param [required, String] remove_stream The ID of the stream to be removed
153
+ #
154
+ # @return [Response]
155
+ #
156
+ # @see TODO: add docs link
157
+ #
158
+ def remove_stream(application_id: @config.application_id, archive_id:, **params)
159
+ # TODO: raise error if application_id is nil
160
+ # TODO: raise error if remove_stream is nil
161
+
162
+ request('/v2/project/' + application_id + '/archive/' + archive_id + '/streams', params: camelcase(params), type: Patch)
163
+ end
164
+
165
+ # Change the layout of a composed archive while it is being recorded.
166
+ #
167
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
168
+ #
169
+ # @param [required, String] archive_id
170
+ #
171
+ # @param [optional, String] type
172
+ #
173
+ # @param [optional, String] stylesheet
174
+ #
175
+ # @param [optional, String] screenshare_type
176
+ #
177
+ # @return [Response]
178
+ #
179
+ # @see TODO: add docs link
180
+ #
181
+ def change_layout(application_id: @config.application_id, archive_id:, **params)
182
+ # TODO: raise error if application_id is nil
183
+
184
+ request('/v2/project/' + application_id + '/archive/' + archive_id + '/layout', params: camelcase(params), type: Put)
185
+ end
186
+ end
187
+ end
@@ -0,0 +1,11 @@
1
+ # typed: true
2
+
3
+ class Vonage::Video::ListResponse < Vonage::Response
4
+ include Enumerable
5
+
6
+ def each
7
+ return enum_for(:each) unless block_given?
8
+
9
+ @entity._embedded.calls.each { |item| yield item }
10
+ end
11
+ end
@@ -0,0 +1,73 @@
1
+ # typed: true
2
+ # frozen_string_literal: true
3
+
4
+ module Vonage
5
+ class Video::Moderation < Namespace
6
+ self.authentication = BearerToken
7
+
8
+ self.request_body = JSON
9
+
10
+ self.host = :video_host
11
+
12
+ # Force a client to disconnect from a session.
13
+ #
14
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
15
+ #
16
+ # @param [required, String] :session_id
17
+ #
18
+ # @param [required, String] :connection_id The connection ID of the specific participant to be disconnected from the session.
19
+ #
20
+ # @return [Response]
21
+ #
22
+ # @see TODO: add docs link
23
+ #
24
+ def force_disconnect(application_id: @config.application_id, session_id:, connection_id:)
25
+ # TODO: raise error if application_id is nil
26
+
27
+ request('/v2/project/' + application_id + '/session/' + session_id + '/connection/' + connection_id, type: Delete)
28
+ end
29
+
30
+ # Force mute a specific publisher stream in a session.
31
+ #
32
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
33
+ #
34
+ # @param [required, String] :session_id
35
+ #
36
+ # @param [required, String] :stream_id The stream ID of the specific stream to be muted.
37
+ #
38
+ # @return [Response]
39
+ #
40
+ # @see TODO: add docs link
41
+ #
42
+ def mute_single_stream(application_id: @config.application_id, session_id:, stream_id:)
43
+ application_id ||= @config.application_id
44
+ # TODO: raise error if application_id is nil
45
+
46
+ request('/v2/project/' + application_id + '/session/' + session_id + '/stream/' + stream_id + '/mute', type: Post)
47
+ end
48
+
49
+ # Force mute all publisher stream for a specific session.
50
+ #
51
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
52
+ #
53
+ # @param [required, String] :session_id
54
+ #
55
+ # @param [required, String] :active
56
+ #
57
+ # @param [required, Array<String>] :excludedStreamIds
58
+ #
59
+ # @return [Response]
60
+ #
61
+ # @see TODO: add docs link
62
+ #
63
+ def mute_multiple_streams(application_id: @config.application_id, session_id:, **params)
64
+ # TODO: raise error if application_id is nil
65
+ # TODO: camelcase params
66
+
67
+ request('/v2/project/' + application_id + '/session/' + session_id + '/mute', params: params, type: Post)
68
+ end
69
+
70
+ # TODO: add disable_force_mute ??
71
+ end
72
+ end
73
+
@@ -0,0 +1,55 @@
1
+ # typed: true
2
+ # frozen_string_literal: true
3
+
4
+ module Vonage
5
+ class Video::Signals < Namespace
6
+ self.authentication = BearerToken
7
+
8
+ self.request_body = JSON
9
+
10
+ self.host = :video_host
11
+
12
+ # Send a signal to a specific participant in an active Vonage Video session.
13
+ #
14
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
15
+ #
16
+ # @param [required, String] :session_id
17
+ #
18
+ # @param [required, String] :connection_id The connection ID of the specific participant.
19
+ #
20
+ # @param [required, String] :type Type of data that is being sent to the client.
21
+ #
22
+ # @param [required, String] :data Payload that is being sent to the client.
23
+ #
24
+ # @return [Response]
25
+ #
26
+ # @see TODO: add docs link
27
+ #
28
+ def send_to_one(application_id: @config.application_id, session_id:, connection_id:, **params)
29
+ # TODO: raise error if application_id is nil
30
+
31
+ request('/v2/project/' + application_id + '/session/' + session_id + '/connection/' + connection_id + '/signal', params: params, type: Post)
32
+ end
33
+
34
+ # Send a signal to all participants in an active Vonage Video session.
35
+ #
36
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
37
+ #
38
+ # @param [required, String] :session_id
39
+ #
40
+ # @param [required, String] :type Type of data that is being sent to the client.
41
+ #
42
+ # @param [required, String] :data Payload that is being sent to the client.
43
+ #
44
+ # @return [Response]
45
+ #
46
+ # @see TODO: add docs link
47
+ #
48
+ def send_to_all(application_id: @config.application_id, session_id:, **params)
49
+ # TODO: raise error if application_id is nil
50
+
51
+ request('/v2/project/' + application_id + '/session/' + session_id + '/signal', params: params, type: Post)
52
+ end
53
+ end
54
+ end
55
+
@@ -0,0 +1,76 @@
1
+ # typed: true
2
+ # frozen_string_literal: true
3
+
4
+ module Vonage
5
+ class Video::Streams < Namespace
6
+
7
+ self.authentication = BearerToken
8
+
9
+ self.request_body = JSON
10
+
11
+ self.host = :video_host
12
+
13
+ # Get a list of streams for a specified session.
14
+ #
15
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
16
+ #
17
+ # @param [required, String] :session_id
18
+ #
19
+ # TODO: add auto_advance option
20
+ #
21
+ # @return [ListResponse]
22
+ #
23
+ # @see TODO: add docs link
24
+ #
25
+ def list(application_id: @config.application_id, session_id:)
26
+ # TODO: raise error if application_id is nil
27
+
28
+ request('/v2/project/' + application_id + '/session/' + session_id + '/stream', response_class: Video::ListResponse)
29
+ end
30
+
31
+ # Get information about a specified stream.
32
+ #
33
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
34
+ #
35
+ # @param [required, String] :session_id
36
+ #
37
+ # @param [required, String] :stream_id
38
+ #
39
+ # @return [Response]
40
+ #
41
+ # @see TODO: add docs link
42
+ #
43
+ def info(application_id: @config.application_id, session_id:, stream_id:)
44
+ # TODO: raise error if application_id is nil
45
+
46
+ request('/v2/project/' + application_id + '/session/' + session_id + '/stream/' + stream_id)
47
+ end
48
+
49
+ # Change the layout for a list of specified streams.
50
+ #
51
+ # @param [optional, String] :application_id (Required unless already set at Client instantiation or set in ENV)
52
+ #
53
+ # @param [required, String] :session_id
54
+ #
55
+ # @param [optional, Array<Hash>] :items An array of hashes representing streams and the layout classes for those streams
56
+ #
57
+ # @option items [required, String] :id The stream ID
58
+ #
59
+ # @option items [required, Array<String>] :layoutClassList Array of CSS class names as strings
60
+ #
61
+ # @return [Response]
62
+ #
63
+ # @see TODO: add docs link
64
+ #
65
+ def change_layout(application_id: @config.application_id, session_id:, **params)
66
+ # TODO: raise error if application_id is nil
67
+ # TODO camelcase layout_class_list
68
+ # if params[:items]
69
+ # params[:items] = params[:items].map {|item| camelcase(item)}
70
+ # end
71
+
72
+ request('/v2/project/' + application_id + '/session/' + session_id + '/stream', params: params, type: Put)
73
+ end
74
+ end
75
+ end
76
+
@@ -0,0 +1,91 @@
1
+ # typed: true
2
+ # frozen_string_literal: true
3
+
4
+ module Vonage
5
+ class Video < Namespace
6
+ include Keys
7
+
8
+ self.authentication = BearerToken
9
+
10
+ self.host = :video_host
11
+
12
+ # Generate a new session.
13
+ #
14
+ # @example
15
+ # session = client.video.create_session({
16
+ # archive_mode: 'always',
17
+ # location: '10.1.200.30',
18
+ # media_mode: 'routed'
19
+ # })
20
+ #
21
+ # @params [optional, String] :archive_mode (either 'always' or 'manual')
22
+ #
23
+ # @param [optional, String] :location
24
+ #
25
+ # @params [optional, String] :media_mode (either 'routed' or 'relayed')
26
+ #
27
+ # @return [Response]
28
+ #
29
+ # @see TODO: Add document link here
30
+ #
31
+ def create_session(**params)
32
+ request_params = params.clone
33
+ request_params[:archive_mode] ||= 'manual'
34
+ media_mode = request_params.delete(:media_mode) || 'routed'
35
+
36
+ if media_mode == 'relayed' && request_params[:archive_mode] == 'manual'
37
+ request_params['p2p.preference'] = 'enabled'
38
+ else
39
+ request_params['p2p.preference'] = 'disabled'
40
+ end
41
+
42
+ response = request('/session/create', params: camelcase(request_params), type: Post)
43
+
44
+ public_response_data = {
45
+ session_id: response.entity[:session_id],
46
+ archive_mode: request_params[:archive_mode],
47
+ media_mode: media_mode,
48
+ location: request_params[:location]
49
+ }
50
+
51
+ entity = Entity.new(public_response_data)
52
+
53
+ response.class.new(entity, response.http_response)
54
+ end
55
+
56
+ def generate_client_token(session_id:, scope: 'session.connect', role: 'publisher', **params)
57
+ claims = {session_id: session_id, application_id: @config.application_id, scope: scope, role: role}
58
+ claims[:data] = params[:data] if params[:data]
59
+ claims[:initial_layout_class_list] = params[:initial_layout_class_list].join(' ') if params[:initial_layout_class_list]
60
+ claims[:exp] = params[:expire_time].to_i if params[:expire_time]
61
+
62
+ JWT.generate(claims, @config.private_key)
63
+ end
64
+
65
+ # @return [Streams]
66
+ #
67
+ def streams
68
+ @streams ||= Streams.new(@config)
69
+ end
70
+
71
+ # @return [Archives]
72
+ #
73
+ def archives
74
+ @archives ||= Archives.new(@config)
75
+ end
76
+
77
+ # @return [Archives]
78
+ #
79
+ def moderation
80
+ @moderation ||= Moderation.new(@config)
81
+ end
82
+
83
+ # @return [Archives]
84
+ #
85
+ def signals
86
+ @signals ||= Signals.new(@config)
87
+ end
88
+
89
+ # TODO: add token generator
90
+ end
91
+ end
@@ -2,9 +2,9 @@
2
2
  # frozen_string_literal: true
3
3
  require 'phonelib'
4
4
 
5
- module Vonage
5
+ module Vonage
6
6
  class Voice::Actions::Connect
7
- attr_accessor :endpoint, :from, :eventType, :timeout, :limit, :machineDetection, :advanced_machine_detection, :eventUrl, :eventMethod, :ringbackTone
7
+ attr_accessor :endpoint, :from, :eventType, :timeout, :limit, :machineDetection, :eventUrl, :eventMethod, :ringbackTone
8
8
 
9
9
  def initialize(attributes = {})
10
10
  @endpoint = attributes.fetch(:endpoint)
@@ -13,7 +13,6 @@ module Vonage
13
13
  @timeout = attributes.fetch(:timeout, nil)
14
14
  @limit = attributes.fetch(:limit, nil)
15
15
  @machineDetection = attributes.fetch(:machineDetection, nil)
16
- @advanced_machine_detection = attributes.fetch(:advanced_machine_detection, nil)
17
16
  @eventUrl = attributes.fetch(:eventUrl, nil)
18
17
  @eventMethod = attributes.fetch(:eventMethod, nil)
19
18
  @ringbackTone = attributes.fetch(:ringbackTone, nil)
@@ -40,10 +39,6 @@ module Vonage
40
39
  verify_machine_detection
41
40
  end
42
41
 
43
- if self.advanced_machine_detection
44
- verify_advanced_machine_detection
45
- end
46
-
47
42
  if self.eventUrl
48
43
  verify_event_url
49
44
  end
@@ -87,25 +82,6 @@ module Vonage
87
82
  raise ClientError.new("Invalid 'machineDetection' value, must be either: 'continue' or 'hangup' if defined") unless self.machineDetection == 'continue' || self.machineDetection == 'hangup'
88
83
  end
89
84
 
90
- def verify_advanced_machine_detection
91
- raise ClientError.new("Invalid 'advanced_machine_detection' value, must be a Hash") unless self.advanced_machine_detection.is_a?(Hash)
92
- verify_advanced_machine_detection_behavior if self.advanced_machine_detection[:behavior]
93
- verify_advanced_machine_detection_mode if self.advanced_machine_detection[:mode]
94
- verify_advanced_machine_detection_beep_timeout if self.advanced_machine_detection[:beep_timeout]
95
- end
96
-
97
- def verify_advanced_machine_detection_behavior
98
- raise ClientError.new("Invalid 'advanced_machine_detection[:behavior]' value, must be a `continue` or `hangup`") unless ['continue', 'hangup'].include?(self.advanced_machine_detection[:behavior])
99
- end
100
-
101
- def verify_advanced_machine_detection_mode
102
- raise ClientError.new("Invalid 'advanced_machine_detection[:mode]' value, must be a `detect` or `detect_beep`") unless ['detect', 'detect_beep'].include?(self.advanced_machine_detection[:mode])
103
- end
104
-
105
- def verify_advanced_machine_detection_beep_timeout
106
- raise ClientError.new("Invalid 'advanced_machine_detection[:beep_timeout]' value, must be between 45 and 120") unless self.advanced_machine_detection[:beep_timeout].between?(45, 120)
107
- end
108
-
109
85
  def verify_event_url
110
86
  uri = URI.parse(self.eventUrl)
111
87
 
@@ -220,4 +196,4 @@ module Vonage
220
196
  }
221
197
  end
222
198
  end
223
- end
199
+ end
@@ -0,0 +1,107 @@
1
+ # typed: true
2
+ # frozen_string_literal: true
3
+ module Vonage
4
+ class Voice::Actions::Pay
5
+ attr_accessor :amount, :currency, :eventUrl, :prompts, :voice
6
+
7
+ def initialize(attributes= {})
8
+ @amount = attributes.fetch(:amount)
9
+ @currency = attributes.fetch(:currency, nil)
10
+ @eventUrl = attributes.fetch(:eventUrl, nil)
11
+ @prompts = attributes.fetch(:prompts, nil)
12
+ @voice = attributes.fetch(:voice, nil)
13
+
14
+ after_initialize!
15
+ end
16
+
17
+ def action
18
+ create_pay!(self)
19
+ end
20
+
21
+ def create_pay!(builder)
22
+ ncco = [
23
+ {
24
+ action: 'pay',
25
+ amount: builder.amount
26
+ }
27
+ ]
28
+
29
+ ncco[0].merge!(currency: builder.currency) if builder.currency
30
+ ncco[0].merge!(eventUrl: builder.eventUrl) if builder.eventUrl
31
+ ncco[0].merge!(prompts: builder.prompts) if builder.prompts
32
+ ncco[0].merge!(voice: builder.voice) if builder.voice
33
+
34
+ ncco
35
+ end
36
+
37
+ private
38
+
39
+ def after_initialize!
40
+ verify_amount
41
+
42
+ if self.eventUrl
43
+ verify_event_url
44
+ end
45
+
46
+ if self.prompts
47
+ verify_prompts
48
+ end
49
+
50
+ if self.voice
51
+ verify_voice
52
+ end
53
+ end
54
+
55
+ def verify_amount
56
+ verify_amount_class
57
+ verify_amount_value
58
+ end
59
+
60
+ def verify_event_url
61
+ raise ClientError.new("Expected 'eventUrl' parameter to be an Array containing a single string item") unless self.eventUrl.is_a?(Array)
62
+
63
+ uri = URI.parse(self.eventUrl[0])
64
+
65
+ raise ClientError.new("Invalid 'eventUrl' value, must be a valid URL") unless uri.kind_of?(URI::HTTP) || uri.kind_of?(URI::HTTPS)
66
+ end
67
+
68
+ def verify_prompts
69
+ verify_prompts_structure
70
+ verify_prompts_values
71
+ end
72
+
73
+ def verify_voice
74
+ verify_voice_structure
75
+ verify_voice_style if self.voice[:style]
76
+ end
77
+
78
+ def verify_amount_class
79
+ raise ClientError.new("Invalid 'amount' value, must be a float") unless self.amount.is_a?(Float)
80
+ end
81
+
82
+ def verify_amount_value
83
+ raise ClientError.new("Invalid 'amount' value, must be greater than 0") unless self.amount > 0
84
+ end
85
+
86
+ def verify_prompts_structure
87
+ raise ClientError.new("Invalid 'prompt', must be an array of at least one hash") unless self.prompts.is_a?(Array) && !self.prompts.empty? && self.prompts.all?(Hash)
88
+ end
89
+
90
+ def verify_prompts_values
91
+ self.prompts.each do |prompt|
92
+ prompt_keys = prompt.keys
93
+ [:type, :text, :errors].each do |key|
94
+ raise ClientError.new("Invalid 'prompt', '#{key}' is required") unless prompt_keys.include?(key)
95
+ end
96
+ end
97
+ end
98
+
99
+ def verify_voice_structure
100
+ raise ClientError.new("Expected 'voice' value to be a Hash") unless self.voice.is_a?(Hash)
101
+ end
102
+
103
+ def verify_voice_style
104
+ raise ClientError.new("Expected 'style' value to be an Integer") unless self.voice[:style].is_a?(Integer)
105
+ end
106
+ end
107
+ end