workato-connector-sdk 1.3.0 → 1.3.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 (34) hide show
  1. checksums.yaml +4 -4
  2. data/.yardopts +8 -0
  3. data/README.md +0 -4
  4. data/VERSION +1 -1
  5. data/lib/workato/cli/generate_command.rb +1 -0
  6. data/lib/workato/cli/main.rb +1 -0
  7. data/lib/workato/cli/push_command.rb +21 -5
  8. data/lib/workato/cli/schema_command.rb +18 -4
  9. data/lib/workato/connector/sdk/account_properties.rb +1 -1
  10. data/lib/workato/connector/sdk/block_invocation_refinements.rb +2 -1
  11. data/lib/workato/connector/sdk/connection.rb +8 -2
  12. data/lib/workato/connector/sdk/connector.rb +9 -0
  13. data/lib/workato/connector/sdk/dsl/aws.rb +10 -0
  14. data/lib/workato/connector/sdk/dsl/error.rb +2 -0
  15. data/lib/workato/connector/sdk/dsl/execution_context.rb +2 -0
  16. data/lib/workato/connector/sdk/dsl/http.rb +6 -1
  17. data/lib/workato/connector/sdk/dsl/stream_package.rb +1 -7
  18. data/lib/workato/connector/sdk/dsl/workato_package.rb +10 -4
  19. data/lib/workato/connector/sdk/dsl.rb +2 -0
  20. data/lib/workato/connector/sdk/object_definitions.rb +59 -18
  21. data/lib/workato/connector/sdk/operation.rb +1 -1
  22. data/lib/workato/connector/sdk/request.rb +6 -3
  23. data/lib/workato/connector/sdk/schema.rb +4 -3
  24. data/lib/workato/connector/sdk/settings.rb +3 -1
  25. data/lib/workato/connector/sdk/stream.rb +21 -2
  26. data/lib/workato/connector/sdk/streams.rb +1 -0
  27. data/lib/workato/connector/sdk/summarize.rb +2 -0
  28. data/lib/workato/connector/sdk.rb +1 -0
  29. data/lib/workato/extension/string.rb +9 -0
  30. data/lib/workato/testing/vcr_multipart_body_matcher.rb +1 -0
  31. data/lib/workato/types/binary.rb +44 -0
  32. data/lib/workato/types/unicode_string.rb +62 -0
  33. metadata +4 -17
  34. data/lib/workato/connector/sdk/schema/type/unicode_string.rb +0 -23
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 0e0a739fc6bc5fe15228d209dc24ac4858c3815b4252b5f6d9abd9ae0644b15d
4
- data.tar.gz: d4089c8dc7f6c8f9bd171730797a7b82eeb3192883d4b5883a5998985a20001a
3
+ metadata.gz: 2a456929ee155b6a048f547defcb4f3ccfcdd2172c1e0539ca601d8268bc0060
4
+ data.tar.gz: 588a1bae54828aa7fb750aaa53ca57336c14693478ac096b810b441008186fde
5
5
  SHA512:
6
- metadata.gz: f6a00086288382c03c024f351e69ca79749d6ef41a833141140274926bec885a7382ce505e9b4981c05a465efa2f1c97cb30697906b8ba6c63d02709dedc9de7
7
- data.tar.gz: b5b289bf86ac5970420e20762609256a6280f00a76ae604fcff206f65f40abb517f22c2207f93f1d439b250e4d725e4a5a91865904bf32c93459c52c932e70b3
6
+ metadata.gz: 5ab021777798644396d5d910c6d3c6f6ebf7ef23956ca7c3b5e79ec2d01d9f59776ea7afa4cbf8c9d501d18c4fc8142e1d4794e15bb3ade22692a3a95c94e4f4
7
+ data.tar.gz: e101977c93f1d878cd27c7170e143fbaf7f1221b52d80c489c5ca37915783662bd8571041bae0d4ad75094851ad74f00e6434c331da902d580e9e13098eb21a5
data/.yardopts ADDED
@@ -0,0 +1,8 @@
1
+ --title "Workato Connector SDK Ruby"
2
+ --main README.md
3
+ --no-private
4
+ --plugin sorbet
5
+ --exclude lib/workato/cli/
6
+ --exclude lib/workato/utilities/
7
+ --exclude lib/workato/web/
8
+ --exclude lib/workato/extension/
data/README.md CHANGED
@@ -339,7 +339,6 @@ Options:
339
339
  [--col-sep=COL_SEP] # Use separator for CSV converter
340
340
  # Default: comma
341
341
  # Possible values: comma, space, tab, colon, semicolon, pipe
342
- [--api-email=API_EMAIL] # Email for accessing Workato API or set WORKATO_API_EMAIL environment variable
343
342
  [--api-token=API_TOKEN] # Token for accessing Workato API or set WORKATO_API_TOKEN environment variable
344
343
  ```
345
344
 
@@ -425,8 +424,6 @@ Options:
425
424
  -l, [--logo=LOGO] # Path to connector logo: png or jpeg file
426
425
  -n, [--notes=NOTES] # Release notes
427
426
  -c, [--connector=CONNECTOR] # Path to connector source code
428
- [--api-email=API_EMAIL] # Email for accessing Workato API.
429
- # If present overrides value from WORKATO_API_EMAIL environment variable.
430
427
  [--api-token=API_TOKEN] # Token for accessing Workato API.
431
428
  # If present overrides value from WORKATO_API_TOKEN environment variable.
432
429
  [--environment=ENVIRONMENT] # Data center specific URL to push connector code.
@@ -1139,7 +1136,6 @@ jobs:
1139
1136
  run: bundle exec rspec
1140
1137
  # - name: Push to DEV workspace # Use this to push to DEV. This can be enabled when a PR is merged.
1141
1138
  # env:
1142
- # WORKATO_API_EMAIL: ${{ secrets.WORKATO_DEV_ENVIRONMENT_API_EMAIL}}
1143
1139
  # WORKATO_API_TOKEN: ${{ secrets.WORKATO_DEV_ENVIRONMENT_API_TOKEN}}
1144
1140
  # run: workato push
1145
1141
  ```
data/VERSION CHANGED
@@ -1 +1 @@
1
- 1.3.0
1
+ 1.3.1
@@ -50,6 +50,7 @@ module Workato
50
50
  enum: SchemaCommand::CSV_SEPARATORS,
51
51
  default: 'comma'
52
52
  method_option :api_email,
53
+ hide: true,
53
54
  type: :string,
54
55
  desc: 'Email for accessing Workato API or ' \
55
56
  "set #{Workato::Connector::Sdk::WORKATO_API_EMAIL_ENV} environment variable"
@@ -128,6 +128,7 @@ module Workato
128
128
  desc: 'Path to connector source code',
129
129
  lazy_default: Workato::Connector::Sdk::DEFAULT_CONNECTOR_PATH
130
130
  method_option :api_email,
131
+ hide: true,
131
132
  type: :string,
132
133
  desc: "Email for accessing Workato API.\n" \
133
134
  "If present overrides value from #{Workato::Connector::Sdk::WORKATO_API_EMAIL_ENV} " \
@@ -5,6 +5,7 @@ require 'uri'
5
5
  require 'ruby-progressbar'
6
6
  require 'zip'
7
7
  require 'fileutils'
8
+ require 'thor'
8
9
 
9
10
  module Workato
10
11
  module CLI
@@ -108,7 +109,7 @@ module Workato
108
109
  url = "#{api_base_url}#{API_IMPORT_PATH}/#{folder_id}"
109
110
  response = RestClient.post(
110
111
  url,
111
- File.open(zip_file_path),
112
+ File.open(zip_file_path, 'rb'),
112
113
  auth_headers.merge(
113
114
  'Content-Type' => 'application/zip'
114
115
  )
@@ -185,10 +186,25 @@ module Workato
185
186
  end
186
187
 
187
188
  def auth_headers
188
- {
189
- 'x-user-email' => api_email,
190
- 'x-user-token' => api_token
191
- }
189
+ @auth_headers ||=
190
+ if api_email.present?
191
+ warn <<~WARNING
192
+ You are using old authorization schema with --api-email and --api-token which is less secure and deprecated.
193
+ We strongly recommend migrating over to API Clients for authentication to Workato APIs.
194
+
195
+ Learn more: https://docs.workato.com/developing-connectors/sdk/cli/reference/cli-commands.html#workato-push
196
+
197
+ If you use API Client token but still see this message, ensure you do not pass --api-email param nor have #{Workato::Connector::Sdk::WORKATO_API_EMAIL_ENV} environment variable set.
198
+ WARNING
199
+ {
200
+ 'x-user-email' => api_email,
201
+ 'x-user-token' => api_token
202
+ }
203
+ else
204
+ {
205
+ 'Authorization' => "Bearer #{api_token}"
206
+ }
207
+ end
192
208
  end
193
209
 
194
210
  def folder_id
@@ -68,10 +68,24 @@ module Workato
68
68
  end
69
69
 
70
70
  def auth_headers
71
- {
72
- 'x-user-email' => api_email,
73
- 'x-user-token' => api_token
74
- }
71
+ if api_email.present?
72
+ warn <<~WARNING
73
+ You are using old authorization schema with --api-email and --api-token which is less secure and deprecated.
74
+ We strongly recommend migrating over to API Clients for authentication to Workato APIs.
75
+
76
+ Learn more: https://docs.workato.com/developing-connectors/sdk/cli/reference/cli-commands.html#workato-generate-schema
77
+
78
+ If you use API Client token but still see this message, ensure you do not pass --api-email param nor have #{Workato::Connector::Sdk::WORKATO_API_EMAIL_ENV} environment variable set.
79
+ WARNING
80
+ {
81
+ 'x-user-email' => api_email,
82
+ 'x-user-token' => api_token
83
+ }
84
+ else
85
+ {
86
+ 'Authorization' => "Bearer #{api_token}"
87
+ }
88
+ end
75
89
  end
76
90
 
77
91
  private_constant :API_GENERATE_SCHEMA_PATH
@@ -13,7 +13,7 @@ module Workato
13
13
 
14
14
  def self.from_yaml(path = DEFAULT_ACCOUNT_PROPERTIES_PATH)
15
15
  File.open(path) do |f|
16
- instance.load_data(YAML.safe_load(ERB.new(f.read).result, [::Symbol]).to_hash)
16
+ instance.load_data(YAML.safe_load(ERB.new(f.read).result, permitted_classes: [::Symbol]).to_hash)
17
17
  end
18
18
  end
19
19
 
@@ -4,7 +4,8 @@
4
4
  module Workato
5
5
  module Connector
6
6
  module Sdk
7
- # match proc's arguments, even if it's a lambda.
7
+ # Match proc's arguments, even if it's a lambda.
8
+ # @api private
8
9
  module BlockInvocationRefinements
9
10
  refine Proc do
10
11
  def call(*args, &block)
@@ -36,6 +36,7 @@ module Workato
36
36
 
37
37
  using BlockInvocationRefinements
38
38
 
39
+ # @api private
39
40
  sig { returns(HashWithIndifferentAccess) }
40
41
  attr_reader :source
41
42
 
@@ -56,11 +57,13 @@ module Workato
56
57
  @settings = T.let(settings, SorbetTypes::SettingsHash)
57
58
  end
58
59
 
60
+ # @api private
59
61
  sig { returns(SorbetTypes::SettingsHash) }
60
62
  def settings!
61
63
  @settings
62
64
  end
63
65
 
66
+ # @api private
64
67
  sig { returns(HashWithIndifferentAccess) }
65
68
  def settings
66
69
  # we can't freeze or memoise because some developers modify it for storing something temporary in it.
@@ -70,11 +73,13 @@ module Workato
70
73
  end
71
74
  end
72
75
 
76
+ # @api private
73
77
  sig { params(settings: SorbetTypes::SettingsHash).returns(SorbetTypes::SettingsHash) }
74
78
  def merge_settings!(settings)
75
79
  @settings.merge!(settings)
76
80
  end
77
81
 
82
+ # @api private
78
83
  sig { returns(T::Boolean) }
79
84
  def authorization?
80
85
  source[:authorization].present?
@@ -100,6 +105,7 @@ module Workato
100
105
  global_dsl_context.execute(self.settings, &source['base_uri'])
101
106
  end
102
107
 
108
+ # @api private
103
109
  sig do
104
110
  params(
105
111
  message: String,
@@ -267,6 +273,7 @@ module Workato
267
273
  end
268
274
  end
269
275
 
276
+ # @api private
270
277
  sig { params(settings: HashWithIndifferentAccess).returns(T.nilable(HashWithIndifferentAccess)) }
271
278
  def refresh!(settings)
272
279
  if oauth2?
@@ -300,6 +307,7 @@ module Workato
300
307
  end
301
308
  end
302
309
 
310
+ # @api private
303
311
  sig { returns(HashWithIndifferentAccess) }
304
312
  def source
305
313
  return @source unless multi?
@@ -381,8 +389,6 @@ module Workato
381
389
  Dsl::WithDsl.new(@connection)
382
390
  end
383
391
  end
384
-
385
- private_constant :Authorization
386
392
  end
387
393
  end
388
394
  end
@@ -13,6 +13,7 @@ module Workato
13
13
  class Connector
14
14
  extend T::Sig
15
15
 
16
+ # @api private
16
17
  sig { returns(HashWithIndifferentAccess) }
17
18
  attr_reader :source
18
19
 
@@ -208,6 +209,8 @@ module Workato
208
209
  end
209
210
  end
210
211
 
212
+ private_constant :ActionsProxy
213
+
211
214
  class MethodsProxy
212
215
  extend T::Sig
213
216
 
@@ -255,6 +258,8 @@ module Workato
255
258
  end
256
259
  end
257
260
 
261
+ private_constant :MethodsProxy
262
+
258
263
  class PickListsProxy
259
264
  extend T::Sig
260
265
 
@@ -306,6 +311,8 @@ module Workato
306
311
  end
307
312
  end
308
313
 
314
+ private_constant :PickListsProxy
315
+
309
316
  class TriggersProxy
310
317
  extend T::Sig
311
318
 
@@ -365,6 +372,8 @@ module Workato
365
372
  end
366
373
  end
367
374
  end
375
+
376
+ private_constant :TriggersProxy
368
377
  end
369
378
  end
370
379
  end
@@ -12,15 +12,25 @@ module Workato
12
12
  module Dsl
13
13
  module AWS
14
14
  TEMP_CREDENTIALS_REFRESH_TIMEOUT = 60 # seconds
15
+ private_constant :TEMP_CREDENTIALS_REFRESH_TIMEOUT
15
16
 
16
17
  DUMMY_AWS_IAM_EXTERNAL_ID = 'dummy-aws-iam-external-id'
18
+ private_constant :DUMMY_AWS_IAM_EXTERNAL_ID
19
+
17
20
  DUMMY_AWS_WORKATO_ACCOUNT_ID = 'dummy-aws-workato-account-id'
21
+ private_constant :DUMMY_AWS_WORKATO_ACCOUNT_ID
18
22
 
19
23
  AMAZON_ROLE_CLIENT_ID = ENV.fetch('AMAZON_ROLE_CLIENT_ID', nil)
24
+ private_constant :AMAZON_ROLE_CLIENT_ID
25
+
20
26
  AMAZON_ROLE_CLIENT_KEY = ENV.fetch('AMAZON_ROLE_CLIENT_KEY', nil)
27
+ private_constant :AMAZON_ROLE_CLIENT_KEY
28
+
21
29
  AMAZON_ROLE_CLIENT_SECRET = ENV.fetch('AMAZON_ROLE_CLIENT_SECRET', nil)
30
+ private_constant :AMAZON_ROLE_CLIENT_SECRET
22
31
 
23
32
  WWW_FORM_CONTENT_TYPE = 'application/x-www-form-urlencoded; charset=utf-8'
33
+ private_constant :WWW_FORM_CONTENT_TYPE
24
34
 
25
35
  def aws
26
36
  @aws ||= Private.new(connection: connection)
@@ -6,6 +6,8 @@ module Workato
6
6
  module Sdk
7
7
  module Dsl
8
8
  module Error
9
+ # @param message [String]
10
+ # @raise [Workato::Connector::Sdk::RuntimeError]
9
11
  def error(message)
10
12
  raise Sdk::RuntimeError, message
11
13
  end
@@ -38,6 +38,8 @@ module Workato
38
38
  T.unsafe(self).recipe_id.reverse
39
39
  end
40
40
  end
41
+
42
+ private_constant :ClassMethods
41
43
  end
42
44
  end
43
45
  end
@@ -8,8 +8,13 @@ module Workato
8
8
  # https://docs.workato.com/developing-connectors/sdk/sdk-reference/http.html#http-methods
9
9
  module HTTP
10
10
  PARALLEL_SUCCESS_INDEX = 0
11
+ private_constant :PARALLEL_SUCCESS_INDEX
12
+
11
13
  PARALLEL_RESULTS_INDEX = 1
14
+ private_constant :PARALLEL_RESULTS_INDEX
15
+
12
16
  PARALLEL_ERRORS_INDEX = 2
17
+ private_constant :PARALLEL_ERRORS_INDEX
13
18
 
14
19
  def get(url, params = {})
15
20
  http_request(url, method: 'GET').params(params).response_format_json
@@ -52,7 +57,7 @@ module Workato
52
57
  response = nil
53
58
  exception = nil
54
59
  begin
55
- response = request.execute!
60
+ response = request.response!
56
61
  rescue StandardError => e
57
62
  exception = e.to_s
58
63
  end
@@ -27,13 +27,7 @@ module Workato
27
27
  stream = out(stream[:name], stream[:input] || {})
28
28
  end
29
29
 
30
- Stream::Reader.new(
31
- stream: stream,
32
- from: from,
33
- frame_size: frame_size
34
- ).each_chunk do |chunk, byte_from, byte_to, eof, next_from|
35
- blk.call(chunk, byte_from, byte_to, eof, next_from)
36
- end
30
+ Stream.each_chunk(stream: stream, from: from, frame_size: frame_size, &blk)
37
31
  end
38
32
 
39
33
  sig { params(stream_name: String, input: SorbetTypes::StreamInputHash).returns(Stream::Proxy) }
@@ -13,9 +13,19 @@ module Workato
13
13
  module Dsl
14
14
  class WorkatoPackage
15
15
  JWT_ALGORITHMS = %w[RS256 RS384 RS512].freeze
16
+ private_constant :JWT_ALGORITHMS
17
+
16
18
  JWT_RSA_KEY_MIN_LENGTH = 2048
19
+ private_constant :JWT_RSA_KEY_MIN_LENGTH
17
20
 
18
21
  VERIFY_RCA_ALGORITHMS = %w[SHA SHA1 SHA224 SHA256 SHA384 SHA512].freeze
22
+ private_constant :VERIFY_RCA_ALGORITHMS
23
+
24
+ RANDOM_SIZE = 32
25
+ private_constant :RANDOM_SIZE
26
+
27
+ ALLOWED_KEY_SIZES = [128, 192, 256].freeze
28
+ private_constant :ALLOWED_KEY_SIZES
19
29
 
20
30
  def initialize(streams:, connection:)
21
31
  @streams = streams
@@ -76,8 +86,6 @@ module Workato
76
86
  SecureRandom.uuid
77
87
  end
78
88
 
79
- RANDOM_SIZE = 32
80
-
81
89
  def random_bytes(len)
82
90
  unless (len.is_a? ::Integer) && (len <= RANDOM_SIZE)
83
91
  raise "The requested length or random bytes sequence should be <= #{RANDOM_SIZE}"
@@ -86,8 +94,6 @@ module Workato
86
94
  Types::Binary.new(::OpenSSL::Random.random_bytes(len))
87
95
  end
88
96
 
89
- ALLOWED_KEY_SIZES = [128, 192, 256].freeze
90
-
91
97
  def aes_cbc_encrypt(string, key, init_vector = nil)
92
98
  key_size = key.bytesize * 8
93
99
  unless ALLOWED_KEY_SIZES.include?(key_size)
@@ -25,9 +25,11 @@ module Workato
25
25
 
26
26
  abstract!
27
27
 
28
+ # @api private
28
29
  sig { abstract.returns(Streams) }
29
30
  def streams; end
30
31
 
32
+ # @api private
31
33
  sig { abstract.returns(Connection) }
32
34
  def connection; end
33
35
 
@@ -1,4 +1,4 @@
1
- # typed: true
1
+ # typed: strict
2
2
  # frozen_string_literal: true
3
3
 
4
4
  require_relative './block_invocation_refinements'
@@ -6,31 +6,45 @@ require_relative './block_invocation_refinements'
6
6
  module Workato
7
7
  module Connector
8
8
  module Sdk
9
+ module SorbetTypes
10
+ ObjectDefinitionOutput = T.type_alias { T::Array[HashWithIndifferentAccess] }
11
+ end
12
+
9
13
  class ObjectDefinitions
14
+ extend T::Sig
15
+
10
16
  using BlockInvocationRefinements
11
17
 
18
+ sig do
19
+ params(
20
+ object_definitions: SorbetTypes::SourceHash,
21
+ connection: Connection,
22
+ methods: SorbetTypes::SourceHash
23
+ ).void
24
+ end
12
25
  def initialize(object_definitions:, connection:, methods:)
13
26
  @object_definitions_source = object_definitions
14
27
  @methods_source = methods
15
28
  @connection = connection
16
- define_object_definition_methods(object_definitions)
29
+ @object_definitions = T.let({}, T::Hash[T.any(String, Symbol), ObjectDefinition])
30
+ define_object_definition_methods
17
31
  end
18
32
 
33
+ sig do
34
+ params(
35
+ settings: T.nilable(SorbetTypes::SettingsHash),
36
+ config_fields: SorbetTypes::OperationInputHash
37
+ ).returns(HashWithIndifferentAccess)
38
+ end
19
39
  def lazy(settings = nil, config_fields = {})
20
40
  DupHashWithIndifferentAccess.new do |object_definitions, name|
21
41
  fields_proc = object_definitions_source.dig(name, :fields)
22
42
  raise Workato::Connector::Sdk::UnresolvedObjectDefinitionError, name unless fields_proc
23
43
 
24
44
  begin
25
- object_definitions[name] = Action.new(
26
- action: {
27
- execute: lambda do |connection, input|
28
- instance_exec(connection, input, object_definitions, &fields_proc)
29
- end
30
- },
31
- methods: methods_source,
32
- connection: connection
33
- ).execute(settings, config_fields)
45
+ object_definitions[name] = create_operation.execute(settings, config_fields) do |connection, input|
46
+ instance_exec(connection, input, object_definitions, &fields_proc)
47
+ end
34
48
  rescue SystemStackError => e
35
49
  raise Workato::Connector::Sdk::CircleReferenceObjectDefinitionError.new(name, e.backtrace)
36
50
  end
@@ -39,40 +53,67 @@ module Workato
39
53
 
40
54
  private
41
55
 
56
+ sig { returns(SorbetTypes::SourceHash) }
42
57
  attr_reader :methods_source
58
+
59
+ sig { returns(Connection) }
43
60
  attr_reader :connection
44
- attr_reader :settings
61
+
62
+ sig { returns(SorbetTypes::SourceHash) }
45
63
  attr_reader :object_definitions_source
46
64
 
47
- def define_object_definition_methods(object_definitions)
48
- object_definitions.each do |(object, _definition)|
65
+ sig { void }
66
+ def define_object_definition_methods
67
+ object_definitions_source.each do |(object, _definition)|
49
68
  define_singleton_method(object) do
50
- @object_definitions ||= {}
51
69
  @object_definitions[object] ||= ObjectDefinition.new(name: object, object_definitions: self)
52
70
  end
53
71
  end
54
72
  end
55
73
 
74
+ sig { returns(Operation) }
75
+ def create_operation
76
+ Operation.new(methods: methods_source, connection: connection)
77
+ end
78
+
56
79
  class ObjectDefinition
80
+ extend T::Sig
81
+
82
+ sig { params(name: T.any(String, Symbol), object_definitions: ObjectDefinitions).void }
57
83
  def initialize(name:, object_definitions:)
58
- @object_definitions = object_definitions
59
84
  @name = name
85
+ @object_definitions = object_definitions
60
86
  end
61
87
 
88
+ sig do
89
+ params(
90
+ settings: T.nilable(SorbetTypes::SettingsHash),
91
+ config_fields: SorbetTypes::OperationInputHash
92
+ ).returns(SorbetTypes::ObjectDefinitionOutput)
93
+ end
62
94
  def fields(settings = nil, config_fields = {})
63
95
  object_definitions_lazy_hash = @object_definitions.lazy(settings, config_fields)
64
96
  object_definitions_lazy_hash[@name]
65
97
  end
66
98
  end
67
99
 
100
+ private_constant :ObjectDefinition
101
+
68
102
  class DupHashWithIndifferentAccess < HashWithIndifferentAccess
103
+ extend T::Sig
104
+ extend T::Generic
105
+
106
+ K = type_member { { fixed: T.any(String, Symbol) } }
107
+ V = type_member { { fixed: T.untyped } }
108
+ Elem = type_member { { fixed: T.untyped } }
109
+
110
+ sig { params(name: K).returns(V) }
69
111
  def [](name)
70
112
  super.deep_dup
71
113
  end
72
114
  end
73
115
 
74
- private_constant 'ObjectDefinition'
75
- private_constant 'DupHashWithIndifferentAccess'
116
+ private_constant :DupHashWithIndifferentAccess
76
117
  end
77
118
  end
78
119
  end
@@ -225,7 +225,7 @@ module Workato
225
225
  def resolve_request(request_or_result)
226
226
  case request_or_result
227
227
  when Request
228
- resolve_request(request_or_result.execute!)
228
+ resolve_request(request_or_result.response!)
229
229
  when ::Array
230
230
  request_or_result.each_with_index.inject(request_or_result) do |acc, (item, index)|
231
231
  response_item = resolve_request(item)
@@ -39,10 +39,10 @@ module Workato
39
39
  end
40
40
 
41
41
  def method_missing(...)
42
- execute!.send(...)
42
+ response!.send(...)
43
43
  end
44
44
 
45
- def execute!
45
+ def response!
46
46
  __getobj__ || __setobj__(response)
47
47
  rescue RestClient::Exceptions::Timeout => e
48
48
  Kernel.raise RequestTimeoutError, e
@@ -254,7 +254,7 @@ module Workato
254
254
  end
255
255
 
256
256
  def try(...)
257
- execute!.try(...)
257
+ response!.try(...)
258
258
  end
259
259
 
260
260
  private
@@ -513,6 +513,8 @@ module Workato
513
513
  attr_reader :original_filename
514
514
  end
515
515
 
516
+ private_constant :Part
517
+
516
518
  class RestClientRequest < ::RestClient::Request
517
519
  def initialize(args)
518
520
  super
@@ -540,6 +542,7 @@ module Workato
540
542
  net
541
543
  end
542
544
  end
545
+
543
546
  private_constant :RestClientRequest
544
547
  end
545
548
  end
@@ -101,7 +101,7 @@ module Workato
101
101
  return Type::Time.from_date_time(value)
102
102
  when ::Date
103
103
  return value.to_date
104
- when ::Numeric, ::TrueClass, ::FalseClass, Workato::Types::Binary, Type::UnicodeString,
104
+ when ::Numeric, ::TrueClass, ::FalseClass, Workato::Types::Binary, Workato::Types::UnicodeString,
105
105
  ::Array, ::Hash, Stream::Proxy
106
106
  return value
107
107
  when Extension::Array::ArrayWhere
@@ -111,7 +111,7 @@ module Workato
111
111
  return Workato::Types::Binary.new(value)
112
112
  end
113
113
 
114
- return Type::UnicodeString.new(value)
114
+ return Workato::Types::UnicodeString.new(value)
115
115
  else
116
116
  if value.respond_to?(:to_time)
117
117
  return Type::Time.from_time(value.to_time)
@@ -127,6 +127,8 @@ module Workato
127
127
  end
128
128
  end
129
129
 
130
+ private_constant :Schema
131
+
130
132
  class Fields < ::Array
131
133
  def initialize(fields)
132
134
  ::Array.wrap(fields).each do |field|
@@ -232,4 +234,3 @@ require_relative './schema/field/object'
232
234
  require_relative './schema/field/string'
233
235
 
234
236
  require_relative './schema/type/time'
235
- require_relative './schema/type/unicode_string'
@@ -82,7 +82,7 @@ module Workato
82
82
 
83
83
  def read_plain_file
84
84
  all_settings = File.open(path) do |f|
85
- YAML.safe_load(f.read, [::Symbol]).to_hash.with_indifferent_access
85
+ YAML.safe_load(f.read, permitted_classes: [::Symbol]).to_hash.with_indifferent_access
86
86
  end
87
87
 
88
88
  (name ? all_settings.fetch(name) : all_settings) || {}
@@ -144,6 +144,8 @@ module Workato
144
144
  raise MissingKeyError.new(key_path: key_path, env_key: env_key) if raise_if_missing_key
145
145
  end
146
146
  end
147
+
148
+ private_constant :FixedEncryptedConfiguration
147
149
  end
148
150
  end
149
151
  end
@@ -79,6 +79,22 @@ module Workato
79
79
  data
80
80
  end
81
81
 
82
+ class << self
83
+ extend T::Sig
84
+
85
+ sig do
86
+ params(
87
+ stream: T.any(Proxy, T::Hash[T.untyped, T.untyped], String),
88
+ from: T.nilable(Integer),
89
+ frame_size: T.nilable(Integer),
90
+ blk: SorbetTypes::StreamInProc
91
+ ).void
92
+ end
93
+ def each_chunk(stream:, from:, frame_size: nil, &blk)
94
+ Reader.new(stream: stream, from: from, frame_size: frame_size).each_chunk(&blk)
95
+ end
96
+ end
97
+
82
98
  class Reader
83
99
  extend T::Sig
84
100
 
@@ -153,6 +169,9 @@ module Workato
153
169
  end
154
170
  end
155
171
 
172
+ private_constant :Reader
173
+
174
+ # @api private
156
175
  class Proxy
157
176
  extend T::Sig
158
177
 
@@ -212,9 +231,9 @@ module Workato
212
231
  class Mock
213
232
  extend T::Sig
214
233
 
215
- sig { params(chunks: T.untyped).void }
234
+ sig { params(chunks: T::Hash[T.any(Integer, String), T.untyped]).void }
216
235
  def initialize(chunks:)
217
- @chunks = chunks
236
+ @chunks = T.let(chunks.transform_keys(&:to_i), T::Hash[Integer, T.untyped])
218
237
  end
219
238
 
220
239
  sig { params(from: Integer, frame_size: Integer, _blk: Reader::ProxyReadProc).void }
@@ -56,6 +56,7 @@ module Workato
56
56
  attr_reader :connection
57
57
  end
58
58
 
59
+ # @api private
59
60
  class ProhibitedStreams < Streams
60
61
  extend T::Sig
61
62
 
@@ -57,6 +57,8 @@ module Workato
57
57
  end
58
58
  end
59
59
  end
60
+
61
+ private_constant :Summarize
60
62
  end
61
63
  end
62
64
  end
@@ -8,6 +8,7 @@ require 'active_support/all'
8
8
  require 'active_support/json'
9
9
 
10
10
  require_relative '../types/binary'
11
+ require_relative '../types/unicode_string'
11
12
 
12
13
  require_relative '../extension/array'
13
14
  require_relative '../extension/case_sensitive_headers'
@@ -16,6 +16,15 @@ module Workato
16
16
  end
17
17
  end
18
18
 
19
+ def binary?
20
+ warn <<~WARNING
21
+ WARNING: Ambiguous use of `String#binary?' method.
22
+ For correct behavior of `binary?` method use explicit Workato::Types::UnicodeString for input strings and Workato::Types::Binary for input binaries
23
+ See: https://www.rubydoc.info/gems/workato-connector-sdk/Workato/Types
24
+ WARNING
25
+ encoding == Encoding::ASCII_8BIT
26
+ end
27
+
19
28
  def is_int? # rubocop:disable Naming/PredicateName
20
29
  present? && (self !~ /\D/)
21
30
  end
@@ -5,6 +5,7 @@ module Workato
5
5
  module Testing
6
6
  class VCRMultipartBodyMatcher
7
7
  MULTIPART_HEADER_MATCHER = %r{^multipart/form-data; boundary=(.+)$}.freeze
8
+ private_constant :MULTIPART_HEADER_MATCHER
8
9
 
9
10
  class << self
10
11
  def call(request1, request2)
@@ -2,6 +2,47 @@
2
2
 
3
3
  module Workato
4
4
  module Types
5
+ # Explicit wrapper for binary data
6
+ #
7
+ # Workato runtime always converts a String to {Workato::Types::UnicodeString} and
8
+ # binary data to {Workato::Types::Binary} before execute an action.
9
+ #
10
+ # == Call action or trigger by name
11
+ #
12
+ # SDK emulator applies trigger's or action's input/output schema and normalize string when invoke them by name.
13
+ # If you call an operation like this, then emulator passes input with
14
+ # {Workato::Types::UnicodeString} or {Workato::Types::Binary} to the operation
15
+ #
16
+ # CLI
17
+ # workato exec 'actions.test_action'
18
+ # workato exec 'triggers.test_poll_trigger'
19
+ #
20
+ # RSpec
21
+ # connector.actions.test_action.invoke(input)
22
+ # connector.triggers.test_poll_trigger.invoke(input)
23
+ #
24
+ # == Direct call to execute or poll block
25
+ #
26
+ # Schema is not applied when call an action's execute block directly. For example
27
+ #
28
+ # CLI
29
+ # workato exec 'actions.test_action.execute'
30
+ #
31
+ # RSpec
32
+ # connector.actions.test_action.execute(settings, input, input_schema, output_schema)
33
+ #
34
+ # In that case if action's code relies on methods of {Workato::Types::UnicodeString} or {Workato::Types::Binary}
35
+ # then this explicit wrapper should be used for correct behavior.
36
+ #
37
+ # @example
38
+ # input = {
39
+ # file_content: Workato::Types::Binary.new(File.read('/path/to/file.bin', 'wb')),
40
+ # file_name: Workato::Types::UnicodeString.new("Hello World!")
41
+ # }
42
+ #
43
+ # connector.actions.upload(settings, input)
44
+ #
45
+ # @see Workato::Types::UnicodeString
5
46
  class Binary < ::String
6
47
  TITLE_LENGTH = 16
7
48
  SUMMARY_LENGTH = 128
@@ -19,6 +60,9 @@ module Workato
19
60
  summary
20
61
  end
21
62
 
63
+ # Returns true for binary data
64
+ #
65
+ # @return [Boolean]
22
66
  def binary?
23
67
  true
24
68
  end
@@ -0,0 +1,62 @@
1
+ # typed: true
2
+ # frozen_string_literal: true
3
+
4
+ module Workato
5
+ module Types
6
+ # Explicit wrapper for unicode strings.
7
+ #
8
+ # Workato runtime always converts a String to {Workato::Types::UnicodeString} and
9
+ # binary data to {Workato::Types::Binary} before execute an action.
10
+ #
11
+ # == Call action or trigger by name
12
+ #
13
+ # SDK emulator applies trigger's or action's input/output schema and normalize string when invoke them by name.
14
+ # If you call an operation like this, then emulator passes input with
15
+ # {Workato::Types::UnicodeString} or {Workato::Types::Binary} to the operation
16
+ #
17
+ # CLI
18
+ # workato exec 'actions.test_action'
19
+ # workato exec 'triggers.test_poll_trigger'
20
+ #
21
+ # RSpec
22
+ # connector.actions.test_action.invoke(input)
23
+ # connector.triggers.test_poll_trigger.invoke(input)
24
+ #
25
+ # == Direct call to execute or poll block
26
+ #
27
+ # Schema is not applied when call an action's execute block directly. For example
28
+ #
29
+ # CLI
30
+ # workato exec 'actions.test_action.execute'
31
+ #
32
+ # RSpec
33
+ # connector.actions.test_action.execute(settings, input, input_schema, output_schema)
34
+ #
35
+ # In that case if action's code relies on methods of {Workato::Types::UnicodeString} or {Workato::Types::Binary}
36
+ # then this explicit wrapper should be used for correct behavior.
37
+ #
38
+ # @example
39
+ # input = {
40
+ # file_content: Workato::Types::Binary.new(File.read('/path/to/file.bin', 'wb')),
41
+ # file_name: Workato::Types::UnicodeString.new("Hello World!")
42
+ # }
43
+ #
44
+ # connector.actions.upload(settings, input)
45
+ #
46
+ # @see Workato::Types::Binary
47
+ class UnicodeString < ::String
48
+ # @param str Ruby string
49
+ def initialize(str)
50
+ super(str, **{})
51
+ encode!('UTF-8')
52
+ end
53
+
54
+ # Returns false for unicode strings
55
+ #
56
+ # @return [Boolean]
57
+ def binary?
58
+ false
59
+ end
60
+ end
61
+ end
62
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: workato-connector-sdk
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.3.0
4
+ version: 1.3.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Pavel Abolmasov
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2023-01-26 00:00:00.000000000 Z
11
+ date: 2023-02-09 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activesupport
@@ -178,20 +178,6 @@ dependencies:
178
178
  - - "~>"
179
179
  - !ruby/object:Gem::Version
180
180
  version: '1.0'
181
- - !ruby/object:Gem::Dependency
182
- name: psych
183
- requirement: !ruby/object:Gem::Requirement
184
- requirements:
185
- - - "~>"
186
- - !ruby/object:Gem::Version
187
- version: '3.0'
188
- type: :runtime
189
- prerelease: false
190
- version_requirements: !ruby/object:Gem::Requirement
191
- requirements:
192
- - - "~>"
193
- - !ruby/object:Gem::Version
194
- version: '3.0'
195
181
  - !ruby/object:Gem::Dependency
196
182
  name: rack
197
183
  requirement: !ruby/object:Gem::Requirement
@@ -410,6 +396,7 @@ executables:
410
396
  extensions: []
411
397
  extra_rdoc_files: []
412
398
  files:
399
+ - ".yardopts"
413
400
  - LICENSE.md
414
401
  - README.md
415
402
  - VERSION
@@ -461,7 +448,6 @@ files:
461
448
  - lib/workato/connector/sdk/schema/field/object.rb
462
449
  - lib/workato/connector/sdk/schema/field/string.rb
463
450
  - lib/workato/connector/sdk/schema/type/time.rb
464
- - lib/workato/connector/sdk/schema/type/unicode_string.rb
465
451
  - lib/workato/connector/sdk/settings.rb
466
452
  - lib/workato/connector/sdk/stream.rb
467
453
  - lib/workato/connector/sdk/streams.rb
@@ -493,6 +479,7 @@ files:
493
479
  - lib/workato/testing/vcr_encrypted_cassette_serializer.rb
494
480
  - lib/workato/testing/vcr_multipart_body_matcher.rb
495
481
  - lib/workato/types/binary.rb
482
+ - lib/workato/types/unicode_string.rb
496
483
  - lib/workato/utilities/encoding.rb
497
484
  - lib/workato/utilities/xml.rb
498
485
  - lib/workato/web/app.rb
@@ -1,23 +0,0 @@
1
- # typed: true
2
- # frozen_string_literal: true
3
-
4
- module Workato
5
- module Connector
6
- module Sdk
7
- class Schema
8
- module Type
9
- class UnicodeString < ::String
10
- def initialize(str)
11
- super(str, **{})
12
- encode!('UTF-8')
13
- end
14
-
15
- def binary?
16
- false
17
- end
18
- end
19
- end
20
- end
21
- end
22
- end
23
- end