hooksniff 0.3.0 → 1.1.0
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 +4 -4
- data/Gemfile +7 -0
- data/Gemfile.lock +56 -0
- data/README.md +23 -199
- data/Rakefile +2 -0
- data/hooksniff.gemspec +48 -0
- data/lib/hooksniff/api/authentication.rb +36 -0
- data/lib/hooksniff/api/endpoint.rb +102 -0
- data/lib/hooksniff/api/event_type.rb +66 -0
- data/lib/hooksniff/api/health.rb +16 -0
- data/lib/hooksniff/api/integration.rb +42 -0
- data/lib/hooksniff/api/message.rb +48 -0
- data/lib/hooksniff/api/message_attempt.rb +38 -0
- data/lib/hooksniff/api/statistics.rb +37 -0
- data/lib/hooksniff/api/stream.rb +45 -0
- data/lib/{openapi_client → hooksniff}/api_error.rb +8 -18
- data/lib/hooksniff/background_task.rb +21 -0
- data/lib/hooksniff/connector.rb +33 -0
- data/lib/hooksniff/environment.rb +53 -0
- data/lib/hooksniff/errors.rb +129 -0
- data/lib/hooksniff/hooksniff.rb +52 -0
- data/lib/hooksniff/hooksniff_http_client.rb +128 -0
- data/lib/hooksniff/http_error_out.rb +18 -0
- data/lib/hooksniff/http_validation_error.rb +18 -0
- data/lib/hooksniff/inbound.rb +25 -0
- data/lib/hooksniff/internal.rb +7 -0
- data/lib/hooksniff/message_poller.rb +32 -0
- data/lib/hooksniff/models/endpoint_created_event.rb +50 -0
- data/lib/hooksniff/models/endpoint_created_event_data.rb +63 -0
- data/lib/hooksniff/models/endpoint_deleted_event.rb +50 -0
- data/lib/hooksniff/models/endpoint_deleted_event_data.rb +63 -0
- data/lib/hooksniff/models/endpoint_disabled_event.rb +53 -0
- data/lib/hooksniff/models/endpoint_disabled_event_data.rb +69 -0
- data/lib/hooksniff/models/endpoint_enabled_event.rb +50 -0
- data/lib/hooksniff/models/endpoint_enabled_event_data.rb +63 -0
- data/lib/hooksniff/models/endpoint_headers_in.rb +46 -0
- data/lib/hooksniff/models/endpoint_headers_out.rb +52 -0
- data/lib/hooksniff/models/endpoint_headers_patch_in.rb +53 -0
- data/lib/hooksniff/models/endpoint_in.rb +102 -0
- data/lib/hooksniff/models/endpoint_out.rb +104 -0
- data/lib/hooksniff/models/endpoint_patch.rb +97 -0
- data/lib/hooksniff/models/endpoint_secret_out.rb +50 -0
- data/lib/hooksniff/models/endpoint_secret_rotate_in.rb +53 -0
- data/lib/hooksniff/models/endpoint_update.rb +90 -0
- data/lib/hooksniff/models/endpoint_updated_event.rb +50 -0
- data/lib/hooksniff/models/endpoint_updated_event_data.rb +63 -0
- data/lib/hooksniff/models/event_in.rb +50 -0
- data/lib/hooksniff/models/event_out.rb +53 -0
- data/lib/hooksniff/models/event_type_in.rb +80 -0
- data/lib/hooksniff/models/event_type_out.rb +87 -0
- data/lib/hooksniff/models/event_type_patch.rb +66 -0
- data/lib/hooksniff/models/event_type_update.rb +67 -0
- data/lib/hooksniff/models/list_response_endpoint_out.rb +58 -0
- data/lib/hooksniff/models/list_response_event_type_out.rb +58 -0
- data/lib/hooksniff/models/list_response_message_attempt_out.rb +58 -0
- data/lib/hooksniff/models/list_response_message_out.rb +58 -0
- data/lib/hooksniff/models/message_attempt_exhausted_event.rb +53 -0
- data/lib/hooksniff/models/message_attempt_exhausted_event_data.rb +70 -0
- data/lib/hooksniff/models/message_attempt_failed_data.rb +56 -0
- data/lib/hooksniff/models/message_attempt_failing_event.rb +54 -0
- data/lib/hooksniff/models/message_attempt_failing_event_data.rb +70 -0
- data/lib/hooksniff/models/message_attempt_log.rb +112 -0
- data/lib/hooksniff/models/message_attempt_log_event.rb +53 -0
- data/lib/hooksniff/models/message_attempt_out.rb +96 -0
- data/lib/hooksniff/models/message_attempt_trigger_type.rb +33 -0
- data/lib/hooksniff/models/message_endpoint_out.rb +112 -0
- data/lib/hooksniff/models/message_in.rb +99 -0
- data/lib/hooksniff/models/message_out.rb +71 -0
- data/lib/hooksniff/models/message_status.rb +39 -0
- data/lib/hooksniff/models/message_status_text.rb +32 -0
- data/lib/hooksniff/models/ordering.rb +30 -0
- data/lib/hooksniff/models/status_code_class.rb +41 -0
- data/lib/hooksniff/operational_webhook.rb +12 -0
- data/lib/hooksniff/util.rb +69 -0
- data/lib/hooksniff/validation_error.rb +28 -0
- data/lib/hooksniff/version.rb +5 -0
- data/lib/hooksniff/webhook.rb +84 -0
- data/lib/hooksniff.rb +78 -0
- data/test/test_hooksniff.rb +86 -0
- metadata +131 -159
- data/lib/openapi_client/api/admin_api.rb +0 -452
- data/lib/openapi_client/api/alerts_api.rb +0 -322
- data/lib/openapi_client/api/analytics_api.rb +0 -208
- data/lib/openapi_client/api/api_keys_api.rb +0 -252
- data/lib/openapi_client/api/audit_log_api.rb +0 -140
- data/lib/openapi_client/api/auth_api.rb +0 -1080
- data/lib/openapi_client/api/billing_api.rb +0 -500
- data/lib/openapi_client/api/contact_api.rb +0 -88
- data/lib/openapi_client/api/custom_domains_api.rb +0 -253
- data/lib/openapi_client/api/customer_portal_api.rb +0 -700
- data/lib/openapi_client/api/delivery_details_api.rb +0 -146
- data/lib/openapi_client/api/devices_api.rb +0 -202
- data/lib/openapi_client/api/embed_api.rb +0 -128
- data/lib/openapi_client/api/endpoints_api.rb +0 -468
- data/lib/openapi_client/api/events_api.rb +0 -75
- data/lib/openapi_client/api/health_api.rb +0 -193
- data/lib/openapi_client/api/inbound_api.rb +0 -170
- data/lib/openapi_client/api/notifications_api.rb +0 -309
- data/lib/openapi_client/api/o_auth_api.rb +0 -181
- data/lib/openapi_client/api/outbound_ips_api.rb +0 -77
- data/lib/openapi_client/api/playground_api.rb +0 -143
- data/lib/openapi_client/api/rate_limits_api.rb +0 -252
- data/lib/openapi_client/api/routing_api.rb +0 -393
- data/lib/openapi_client/api/schemas_api.rb +0 -268
- data/lib/openapi_client/api/search_api.rb +0 -96
- data/lib/openapi_client/api/simulator_api.rb +0 -82
- data/lib/openapi_client/api/sso_api.rb +0 -241
- data/lib/openapi_client/api/stats_api.rb +0 -77
- data/lib/openapi_client/api/stream_api.rb +0 -88
- data/lib/openapi_client/api/teams_api.rb +0 -476
- data/lib/openapi_client/api/templates_api.rb +0 -213
- data/lib/openapi_client/api/transforms_api.rb +0 -368
- data/lib/openapi_client/api/webhooks_api.rb +0 -534
- data/lib/openapi_client/api_client.rb +0 -397
- data/lib/openapi_client/api_model_base.rb +0 -88
- data/lib/openapi_client/configuration.rb +0 -312
- data/lib/openapi_client/models/admin_revenue_get200_response_inner.rb +0 -165
- data/lib/openapi_client/models/admin_sdk_update_post_request.rb +0 -156
- data/lib/openapi_client/models/admin_users_id_plan_put_request.rb +0 -181
- data/lib/openapi_client/models/admin_users_id_status_put_request.rb +0 -147
- data/lib/openapi_client/models/alert_rule.rb +0 -237
- data/lib/openapi_client/models/api_key_info.rb +0 -185
- data/lib/openapi_client/models/apply_template_request.rb +0 -173
- data/lib/openapi_client/models/apply_template_response.rb +0 -156
- data/lib/openapi_client/models/auth2fa_enable_post200_response.rb +0 -156
- data/lib/openapi_client/models/auth_login_post200_response.rb +0 -104
- data/lib/openapi_client/models/auth_response.rb +0 -167
- data/lib/openapi_client/models/batch_replay_request.rb +0 -166
- data/lib/openapi_client/models/batch_response.rb +0 -160
- data/lib/openapi_client/models/batch_response_errors_inner.rb +0 -156
- data/lib/openapi_client/models/batch_webhook_request.rb +0 -166
- data/lib/openapi_client/models/billing_portal_post200_response.rb +0 -147
- data/lib/openapi_client/models/change_password_request.rb +0 -199
- data/lib/openapi_client/models/change_role_request.rb +0 -188
- data/lib/openapi_client/models/confirm2fa_request.rb +0 -182
- data/lib/openapi_client/models/contact_request.rb +0 -242
- data/lib/openapi_client/models/contact_response.rb +0 -156
- data/lib/openapi_client/models/create_alert_request.rb +0 -277
- data/lib/openapi_client/models/create_api_key_response.rb +0 -175
- data/lib/openapi_client/models/create_endpoint_request.rb +0 -288
- data/lib/openapi_client/models/create_team_request.rb +0 -164
- data/lib/openapi_client/models/create_transform_rule_request.rb +0 -216
- data/lib/openapi_client/models/create_webhook_request.rb +0 -201
- data/lib/openapi_client/models/custom_domains_post_request.rb +0 -147
- data/lib/openapi_client/models/customer_response.rb +0 -256
- data/lib/openapi_client/models/delivery.rb +0 -246
- data/lib/openapi_client/models/delivery_attempt.rb +0 -205
- data/lib/openapi_client/models/delivery_list_response.rb +0 -176
- data/lib/openapi_client/models/delivery_trend_response.rb +0 -158
- data/lib/openapi_client/models/delivery_trend_response_buckets_inner.rb +0 -174
- data/lib/openapi_client/models/device_token_response.rb +0 -174
- data/lib/openapi_client/models/disable2fa_request.rb +0 -164
- data/lib/openapi_client/models/enable2fa_request.rb +0 -164
- data/lib/openapi_client/models/endpoint.rb +0 -321
- data/lib/openapi_client/models/endpoint_health.rb +0 -183
- data/lib/openapi_client/models/endpoints_endpoint_id_transforms_test_post_request.rb +0 -156
- data/lib/openapi_client/models/endpoints_id_rotate_secret_post200_response.rb +0 -156
- data/lib/openapi_client/models/error.rb +0 -165
- data/lib/openapi_client/models/forgot_password_request.rb +0 -164
- data/lib/openapi_client/models/invite_request.rb +0 -207
- data/lib/openapi_client/models/invoice_response.rb +0 -183
- data/lib/openapi_client/models/latency_trend_response.rb +0 -167
- data/lib/openapi_client/models/latency_trend_response_buckets_inner.rb +0 -165
- data/lib/openapi_client/models/login_request.rb +0 -190
- data/lib/openapi_client/models/notification.rb +0 -193
- data/lib/openapi_client/models/notification_list_response.rb +0 -167
- data/lib/openapi_client/models/notification_preferences.rb +0 -201
- data/lib/openapi_client/models/notifications_unread_count_get200_response.rb +0 -147
- data/lib/openapi_client/models/outbound_ips_response.rb +0 -158
- data/lib/openapi_client/models/paginated_users.rb +0 -176
- data/lib/openapi_client/models/playground_get200_response.rb +0 -160
- data/lib/openapi_client/models/portal_notifications_put200_response.rb +0 -156
- data/lib/openapi_client/models/portal_profile.rb +0 -184
- data/lib/openapi_client/models/refresh_token_request.rb +0 -164
- data/lib/openapi_client/models/register_device_request.rb +0 -208
- data/lib/openapi_client/models/register_request.rb +0 -201
- data/lib/openapi_client/models/register_schema_request.rb +0 -191
- data/lib/openapi_client/models/resend_verification_request.rb +0 -164
- data/lib/openapi_client/models/reset_password_request.rb +0 -199
- data/lib/openapi_client/models/retry_policy.rb +0 -216
- data/lib/openapi_client/models/routing_info.rb +0 -193
- data/lib/openapi_client/models/search_result.rb +0 -158
- data/lib/openapi_client/models/simulator_post_request.rb +0 -165
- data/lib/openapi_client/models/sso_config_post_request.rb +0 -190
- data/lib/openapi_client/models/stats_response.rb +0 -210
- data/lib/openapi_client/models/stream_params.rb +0 -201
- data/lib/openapi_client/models/subscription_response.rb +0 -201
- data/lib/openapi_client/models/success_rate_response.rb +0 -183
- data/lib/openapi_client/models/system_stats.rb +0 -185
- data/lib/openapi_client/models/system_stats_plan_breakdown_inner.rb +0 -156
- data/lib/openapi_client/models/system_status.rb +0 -210
- data/lib/openapi_client/models/system_status_components_inner.rb +0 -184
- data/lib/openapi_client/models/team.rb +0 -165
- data/lib/openapi_client/models/team_detail_response.rb +0 -169
- data/lib/openapi_client/models/team_invite.rb +0 -174
- data/lib/openapi_client/models/team_member.rb +0 -193
- data/lib/openapi_client/models/test_webhook_request.rb +0 -199
- data/lib/openapi_client/models/test_webhook_response.rb +0 -174
- data/lib/openapi_client/models/transform_rule.rb +0 -201
- data/lib/openapi_client/models/two_factor_required_response.rb +0 -165
- data/lib/openapi_client/models/update_endpoint_request.rb +0 -278
- data/lib/openapi_client/models/update_notification_preferences.rb +0 -195
- data/lib/openapi_client/models/update_profile_request.rb +0 -190
- data/lib/openapi_client/models/update_routing_request.rb +0 -190
- data/lib/openapi_client/models/upgrade_request.rb +0 -209
- data/lib/openapi_client/models/upgrade_response.rb +0 -166
- data/lib/openapi_client/models/usage_response.rb +0 -201
- data/lib/openapi_client/models/user_summary.rb +0 -193
- data/lib/openapi_client/models/validate_event_request.rb +0 -164
- data/lib/openapi_client/models/verify2fa_request.rb +0 -208
- data/lib/openapi_client/models/verify_email_request.rb +0 -164
- data/lib/openapi_client/models/webhook_template.rb +0 -183
- data/lib/openapi_client/version.rb +0 -15
- data/lib/openapi_client.rb +0 -169
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "net/http"
|
|
4
|
+
|
|
5
|
+
module HookSniff
|
|
6
|
+
class MessageAttempt
|
|
7
|
+
def initialize(client)
|
|
8
|
+
@client = client
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def list_by_msg(message_id, options = {})
|
|
12
|
+
options = options.transform_keys(&:to_s)
|
|
13
|
+
res = @client.execute_request(
|
|
14
|
+
"GET",
|
|
15
|
+
"/v1/webhooks/#{message_id}/attempts",
|
|
16
|
+
query_params: {
|
|
17
|
+
"limit" => options["limit"],
|
|
18
|
+
"offset" => options["offset"],
|
|
19
|
+
"status" => options["status"]
|
|
20
|
+
}
|
|
21
|
+
)
|
|
22
|
+
ListResponseMessageAttemptOut.deserialize(res)
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
def get(attempt_id)
|
|
26
|
+
res = @client.execute_request("GET", "/v1/webhooks/attempts/#{attempt_id}")
|
|
27
|
+
MessageAttemptOut.deserialize(res)
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
def resend(message_id, endpoint_id)
|
|
31
|
+
res = @client.execute_request(
|
|
32
|
+
"POST",
|
|
33
|
+
"/v1/webhooks/#{message_id}/attempts/#{endpoint_id}/resend"
|
|
34
|
+
)
|
|
35
|
+
nil
|
|
36
|
+
end
|
|
37
|
+
end
|
|
38
|
+
end
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "net/http"
|
|
4
|
+
|
|
5
|
+
module HookSniff
|
|
6
|
+
class Statistics
|
|
7
|
+
def initialize(client)
|
|
8
|
+
@client = client
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def aggregate_event_types(options = {})
|
|
12
|
+
options = options.transform_keys(&:to_s)
|
|
13
|
+
res = @client.execute_request(
|
|
14
|
+
"GET",
|
|
15
|
+
"/v1/stats/event-types",
|
|
16
|
+
query_params: {
|
|
17
|
+
"since" => options["since"],
|
|
18
|
+
"until" => options["until"]
|
|
19
|
+
}
|
|
20
|
+
)
|
|
21
|
+
AggregateEventTypesOut.deserialize(res)
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
def app_stats(app_id, options = {})
|
|
25
|
+
options = options.transform_keys(&:to_s)
|
|
26
|
+
res = @client.execute_request(
|
|
27
|
+
"GET",
|
|
28
|
+
"/v1/stats/app/#{app_id}",
|
|
29
|
+
query_params: {
|
|
30
|
+
"since" => options["since"],
|
|
31
|
+
"until" => options["until"]
|
|
32
|
+
}
|
|
33
|
+
)
|
|
34
|
+
res
|
|
35
|
+
end
|
|
36
|
+
end
|
|
37
|
+
end
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module HookSniff
|
|
4
|
+
class StreamApi
|
|
5
|
+
def initialize(client)
|
|
6
|
+
@client = client
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
def list_channels
|
|
10
|
+
@client.request(:get, "/api/v1/stream/channels")
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
def get_channel(id)
|
|
14
|
+
@client.request(:get, "/api/v1/stream/channels/#{id}")
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
def create_channel(attrs)
|
|
18
|
+
@client.request(:post, "/api/v1/stream/channels", attrs)
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
def update_channel(id, attrs)
|
|
22
|
+
@client.request(:put, "/api/v1/stream/channels/#{id}", attrs)
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
def delete_channel(id)
|
|
26
|
+
@client.request(:delete, "/api/v1/stream/channels/#{id}")
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
def list_messages(id, params = {})
|
|
30
|
+
@client.request(:get, "/api/v1/stream/channels/#{id}/messages", params)
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
def list_subscriptions
|
|
34
|
+
@client.request(:get, "/api/v1/stream/subscriptions")
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
def disconnect_subscription(id)
|
|
38
|
+
@client.request(:delete, "/api/v1/stream/subscriptions/#{id}")
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
def publish(body)
|
|
42
|
+
@client.request(:post, "/api/v1/stream/publish", body)
|
|
43
|
+
end
|
|
44
|
+
end
|
|
45
|
+
end
|
|
@@ -1,16 +1,6 @@
|
|
|
1
|
-
|
|
2
|
-
#HookSniff API
|
|
1
|
+
# frozen_string_literal: true
|
|
3
2
|
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
The version of the OpenAPI document: 1.0.0
|
|
7
|
-
Contact: support@hooksniff.vercel.app
|
|
8
|
-
Generated by: https://openapi-generator.tech
|
|
9
|
-
Generator version: 7.22.0
|
|
10
|
-
|
|
11
|
-
=end
|
|
12
|
-
|
|
13
|
-
module OpenapiClient
|
|
3
|
+
module HookSniff
|
|
14
4
|
class ApiError < StandardError
|
|
15
5
|
attr_reader :code, :response_headers, :response_body
|
|
16
6
|
|
|
@@ -20,18 +10,18 @@ module OpenapiClient
|
|
|
20
10
|
# ApiError.new(:code => 500, :response_headers => {}, :response_body => "")
|
|
21
11
|
# ApiError.new(:code => 404, :message => "Not Found")
|
|
22
12
|
def initialize(arg = nil)
|
|
23
|
-
if arg.is_a?
|
|
24
|
-
if arg.key?(:message) || arg.key?(
|
|
25
|
-
super(arg[:message] || arg[
|
|
13
|
+
if arg.is_a?(Hash)
|
|
14
|
+
if arg.key?(:message) || arg.key?("message")
|
|
15
|
+
super(arg[:message] || arg["message"])
|
|
26
16
|
else
|
|
27
|
-
super
|
|
17
|
+
super(arg)
|
|
28
18
|
end
|
|
29
19
|
|
|
30
20
|
arg.each do |k, v|
|
|
31
|
-
instance_variable_set
|
|
21
|
+
instance_variable_set("@#{k}", v)
|
|
32
22
|
end
|
|
33
23
|
else
|
|
34
|
-
super
|
|
24
|
+
super(arg)
|
|
35
25
|
@message = arg
|
|
36
26
|
end
|
|
37
27
|
end
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module HookSniff
|
|
4
|
+
class BackgroundTask
|
|
5
|
+
def initialize(api_client)
|
|
6
|
+
@api_client = api_client
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
def list
|
|
10
|
+
@api_client.execute(method: :get, path: "/api/v1/background-tasks")
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
def get(task_id)
|
|
14
|
+
@api_client.execute(method: :get, path: "/api/v1/background-tasks/#{task_id}")
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
def cancel(task_id)
|
|
18
|
+
@api_client.execute(method: :put, path: "/api/v1/background-tasks/#{task_id}")
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
end
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module HookSniff
|
|
4
|
+
class Connector
|
|
5
|
+
def initialize(client)
|
|
6
|
+
@client = client
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
def list
|
|
10
|
+
@client.request(:get, "/api/v1/connectors")
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
def get(id)
|
|
14
|
+
@client.request(:get, "/api/v1/connectors/#{id}")
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
def list_configs
|
|
18
|
+
@client.request(:get, "/api/v1/connectors/configs")
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
def create_config(body)
|
|
22
|
+
@client.request(:post, "/api/v1/connectors/configs", body: body)
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
def update_config(id, body)
|
|
26
|
+
@client.request(:put, "/api/v1/connectors/configs/#{id}", body: body)
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
def delete_config(id)
|
|
30
|
+
@client.request(:delete, "/api/v1/connectors/configs/#{id}")
|
|
31
|
+
end
|
|
32
|
+
end
|
|
33
|
+
end
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module HookSniff
|
|
4
|
+
class Environment
|
|
5
|
+
def initialize(api_client)
|
|
6
|
+
@api_client = api_client
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
def list
|
|
10
|
+
@api_client.execute(method: :get, path: "/api/v1/environments")
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
def create(environment_in)
|
|
14
|
+
@api_client.execute(method: :post, path: "/api/v1/environments", body: environment_in)
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
def get(environment_id)
|
|
18
|
+
@api_client.execute(method: :get, path: "/api/v1/environments/#{environment_id}")
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
def update(environment_id, environment_patch)
|
|
22
|
+
@api_client.execute(method: :put, path: "/api/v1/environments/#{environment_id}", body: environment_patch)
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
def delete(environment_id)
|
|
26
|
+
@api_client.execute(method: :delete, path: "/api/v1/environments/#{environment_id}")
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
def list_variables(environment_id)
|
|
30
|
+
@api_client.execute(method: :get, path: "/api/v1/environments/#{environment_id}/variables")
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
def get_variable(environment_id, variable_id)
|
|
34
|
+
@api_client.execute(method: :get, path: "/api/v1/environments/#{environment_id}/variables/#{variable_id}")
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
def create_variable(environment_id, variable_in)
|
|
38
|
+
@api_client.execute(method: :post, path: "/api/v1/environments/#{environment_id}/variables", body: variable_in)
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
def update_variable(environment_id, variable_id, variable_in)
|
|
42
|
+
@api_client.execute(method: :put, path: "/api/v1/environments/#{environment_id}/variables/#{variable_id}", body: variable_in)
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
def delete_variable(environment_id, variable_id)
|
|
46
|
+
@api_client.execute(method: :delete, path: "/api/v1/environments/#{environment_id}/variables/#{variable_id}")
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
def bulk_upsert_variables(environment_id, bulk_in)
|
|
50
|
+
@api_client.execute(method: :post, path: "/api/v1/environments/#{environment_id}/variables/bulk", body: bulk_in)
|
|
51
|
+
end
|
|
52
|
+
end
|
|
53
|
+
end
|
|
@@ -0,0 +1,129 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module HookSniff
|
|
4
|
+
# Base error class for all HookSniff API errors
|
|
5
|
+
class ApiError < StandardError
|
|
6
|
+
attr_reader :code, :response_headers, :response_body
|
|
7
|
+
|
|
8
|
+
def initialize(code:, response_headers: {}, response_body: nil)
|
|
9
|
+
@code = code
|
|
10
|
+
@response_headers = response_headers
|
|
11
|
+
@response_body = response_body
|
|
12
|
+
super("HookSniff API error #{code}")
|
|
13
|
+
end
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
# 400 Bad Request
|
|
17
|
+
class BadRequestError < ApiError
|
|
18
|
+
def initialize(response_headers: {}, response_body: nil)
|
|
19
|
+
super(code: 400, response_headers: response_headers, response_body: response_body)
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
# 401 Unauthorized
|
|
24
|
+
class UnauthorizedError < ApiError
|
|
25
|
+
def initialize(response_headers: {}, response_body: nil)
|
|
26
|
+
super(code: 401, response_headers: response_headers, response_body: response_body)
|
|
27
|
+
end
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
# 403 Forbidden
|
|
31
|
+
class ForbiddenError < ApiError
|
|
32
|
+
def initialize(response_headers: {}, response_body: nil)
|
|
33
|
+
super(code: 403, response_headers: response_headers, response_body: response_body)
|
|
34
|
+
end
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
# 404 Not Found
|
|
38
|
+
class NotFoundError < ApiError
|
|
39
|
+
def initialize(response_headers: {}, response_body: nil)
|
|
40
|
+
super(code: 404, response_headers: response_headers, response_body: response_body)
|
|
41
|
+
end
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
# 409 Conflict
|
|
45
|
+
class ConflictError < ApiError
|
|
46
|
+
def initialize(response_headers: {}, response_body: nil)
|
|
47
|
+
super(code: 409, response_headers: response_headers, response_body: response_body)
|
|
48
|
+
end
|
|
49
|
+
end
|
|
50
|
+
|
|
51
|
+
# 422 Unprocessable Entity
|
|
52
|
+
class UnprocessableEntityError < ApiError
|
|
53
|
+
attr_reader :validation_errors
|
|
54
|
+
|
|
55
|
+
def initialize(validation_errors: [], response_headers: {}, response_body: nil)
|
|
56
|
+
super(code: 422, response_headers: response_headers, response_body: response_body)
|
|
57
|
+
@validation_errors = validation_errors
|
|
58
|
+
end
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
# 429 Rate Limited
|
|
62
|
+
class RateLimitError < ApiError
|
|
63
|
+
attr_reader :retry_after
|
|
64
|
+
|
|
65
|
+
def initialize(retry_after: nil, response_headers: {}, response_body: nil)
|
|
66
|
+
super(code: 429, response_headers: response_headers, response_body: response_body)
|
|
67
|
+
@retry_after = retry_after
|
|
68
|
+
end
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
# 500 Internal Server Error
|
|
72
|
+
class InternalServerError < ApiError
|
|
73
|
+
def initialize(response_headers: {}, response_body: nil)
|
|
74
|
+
super(code: 500, response_headers: response_headers, response_body: response_body)
|
|
75
|
+
end
|
|
76
|
+
end
|
|
77
|
+
|
|
78
|
+
# 502 Bad Gateway
|
|
79
|
+
class BadGatewayError < ApiError
|
|
80
|
+
def initialize(response_headers: {}, response_body: nil)
|
|
81
|
+
super(code: 502, response_headers: response_headers, response_body: response_body)
|
|
82
|
+
end
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
# 503 Service Unavailable
|
|
86
|
+
class ServiceUnavailableError < ApiError
|
|
87
|
+
def initialize(response_headers: {}, response_body: nil)
|
|
88
|
+
super(code: 503, response_headers: response_headers, response_body: response_body)
|
|
89
|
+
end
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
# 504 Gateway Timeout
|
|
93
|
+
class GatewayTimeoutError < ApiError
|
|
94
|
+
def initialize(response_headers: {}, response_body: nil)
|
|
95
|
+
super(code: 504, response_headers: response_headers, response_body: response_body)
|
|
96
|
+
end
|
|
97
|
+
end
|
|
98
|
+
|
|
99
|
+
# Create the appropriate error from a status code
|
|
100
|
+
def self.create_error_from_status(status_code, response_headers: {}, response_body: nil)
|
|
101
|
+
case status_code
|
|
102
|
+
when 400
|
|
103
|
+
BadRequestError.new(response_headers: response_headers, response_body: response_body)
|
|
104
|
+
when 401
|
|
105
|
+
UnauthorizedError.new(response_headers: response_headers, response_body: response_body)
|
|
106
|
+
when 403
|
|
107
|
+
ForbiddenError.new(response_headers: response_headers, response_body: response_body)
|
|
108
|
+
when 404
|
|
109
|
+
NotFoundError.new(response_headers: response_headers, response_body: response_body)
|
|
110
|
+
when 409
|
|
111
|
+
ConflictError.new(response_headers: response_headers, response_body: response_body)
|
|
112
|
+
when 422
|
|
113
|
+
UnprocessableEntityError.new(response_headers: response_headers, response_body: response_body)
|
|
114
|
+
when 429
|
|
115
|
+
retry_after = response_headers["retry-after"]&.to_i
|
|
116
|
+
RateLimitError.new(retry_after: retry_after, response_headers: response_headers, response_body: response_body)
|
|
117
|
+
when 500
|
|
118
|
+
InternalServerError.new(response_headers: response_headers, response_body: response_body)
|
|
119
|
+
when 502
|
|
120
|
+
BadGatewayError.new(response_headers: response_headers, response_body: response_body)
|
|
121
|
+
when 503
|
|
122
|
+
ServiceUnavailableError.new(response_headers: response_headers, response_body: response_body)
|
|
123
|
+
when 504
|
|
124
|
+
GatewayTimeoutError.new(response_headers: response_headers, response_body: response_body)
|
|
125
|
+
else
|
|
126
|
+
ApiError.new(code: status_code, response_headers: response_headers, response_body: response_body)
|
|
127
|
+
end
|
|
128
|
+
end
|
|
129
|
+
end
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module HookSniff
|
|
4
|
+
class HookSniffOptions
|
|
5
|
+
attr_accessor :debug
|
|
6
|
+
attr_accessor :server_url
|
|
7
|
+
|
|
8
|
+
def initialize(debug = false, server_url = nil)
|
|
9
|
+
@debug = debug
|
|
10
|
+
@server_url = server_url
|
|
11
|
+
end
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
class Client
|
|
15
|
+
attr_accessor :authentication
|
|
16
|
+
attr_accessor :endpoint
|
|
17
|
+
attr_accessor :event_type
|
|
18
|
+
attr_accessor :health
|
|
19
|
+
attr_accessor :message
|
|
20
|
+
attr_accessor :message_attempt
|
|
21
|
+
attr_accessor :statistics
|
|
22
|
+
attr_accessor :environment
|
|
23
|
+
attr_accessor :background_task
|
|
24
|
+
attr_accessor :operational_webhook
|
|
25
|
+
attr_accessor :message_poller
|
|
26
|
+
attr_accessor :inbound
|
|
27
|
+
attr_accessor :connector
|
|
28
|
+
attr_accessor :integration
|
|
29
|
+
attr_accessor :stream
|
|
30
|
+
|
|
31
|
+
def initialize(auth_token, options = HookSniffOptions.new)
|
|
32
|
+
uri = URI(options.server_url || "https://hooksniff-api-1046140057667.europe-west1.run.app")
|
|
33
|
+
api_client = HookSniffHttpClient.new(auth_token, uri)
|
|
34
|
+
|
|
35
|
+
@authentication = Authentication.new(api_client)
|
|
36
|
+
@endpoint = Endpoint.new(api_client)
|
|
37
|
+
@event_type = EventType.new(api_client)
|
|
38
|
+
@health = Health.new(api_client)
|
|
39
|
+
@message = Message.new(api_client)
|
|
40
|
+
@message_attempt = MessageAttempt.new(api_client)
|
|
41
|
+
@statistics = Statistics.new(api_client)
|
|
42
|
+
@environment = Environment.new(api_client)
|
|
43
|
+
@background_task = BackgroundTask.new(api_client)
|
|
44
|
+
@operational_webhook = OperationalWebhook.new(api_client)
|
|
45
|
+
@message_poller = MessagePoller.new(api_client)
|
|
46
|
+
@inbound = Inbound.new(api_client)
|
|
47
|
+
@connector = Connector.new(api_client)
|
|
48
|
+
@integration = IntegrationApi.new(api_client)
|
|
49
|
+
@stream = StreamApi.new(api_client)
|
|
50
|
+
end
|
|
51
|
+
end
|
|
52
|
+
end
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
require "cgi"
|
|
3
|
+
require "uri"
|
|
4
|
+
require "net/http"
|
|
5
|
+
require "securerandom"
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
module HookSniff
|
|
9
|
+
class HookSniffHttpClient
|
|
10
|
+
def initialize(token, base_url)
|
|
11
|
+
@token = token
|
|
12
|
+
@base_url = base_url
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
def execute_request(method, path, **kwargs)
|
|
16
|
+
query_params = kwargs[:query_params] || {}
|
|
17
|
+
headers = kwargs[:headers] || {}
|
|
18
|
+
body = kwargs[:body] || {}
|
|
19
|
+
|
|
20
|
+
uri = URI("#{@base_url}#{path}")
|
|
21
|
+
encoded_query = encode_query_params(query_params)
|
|
22
|
+
if encoded_query != ""
|
|
23
|
+
uri.query = encoded_query
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
http = Net::HTTP.new(uri.host, uri.port)
|
|
27
|
+
http.use_ssl = (uri.scheme == "https")
|
|
28
|
+
|
|
29
|
+
# Dynamically select the request class based on method
|
|
30
|
+
request_class = case method.to_s.upcase
|
|
31
|
+
when "GET"
|
|
32
|
+
Net::HTTP::Get
|
|
33
|
+
when "POST"
|
|
34
|
+
Net::HTTP::Post
|
|
35
|
+
when "PUT"
|
|
36
|
+
Net::HTTP::Put
|
|
37
|
+
when "DELETE"
|
|
38
|
+
Net::HTTP::Delete
|
|
39
|
+
when "PATCH"
|
|
40
|
+
Net::HTTP::Patch
|
|
41
|
+
when "HEAD"
|
|
42
|
+
Net::HTTP::Head
|
|
43
|
+
else
|
|
44
|
+
raise ArgumentError, "Unsupported HTTP method: #{method}"
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
# Create request object
|
|
48
|
+
request = request_class.new(uri.request_uri)
|
|
49
|
+
request["Authorization"] = "Bearer #{@token}"
|
|
50
|
+
request["User-Agent"] = "hooksniff-libs/#{VERSION}/ruby"
|
|
51
|
+
request["hooksniff-req-id"] = rand(0...(2 ** 64))
|
|
52
|
+
|
|
53
|
+
# Add headers
|
|
54
|
+
headers.each { |key, value| request[key] = value }
|
|
55
|
+
|
|
56
|
+
# Check if idempotency-key header already exists
|
|
57
|
+
if !request.key?("idempotency-key") && method.to_s.upcase == "POST"
|
|
58
|
+
request["idempotency-key"] = "auto_" + SecureRandom.uuid.to_s
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
# Add body for non-GET requests
|
|
62
|
+
if %w[POST PUT PATCH].include?(method.to_s.upcase) && !body.nil?
|
|
63
|
+
request.body = body.to_json
|
|
64
|
+
request["Content-Type"] = "application/json"
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
res = execute_request_with_retries(request, http)
|
|
68
|
+
|
|
69
|
+
# Execute request
|
|
70
|
+
if Integer(res.code) == 204
|
|
71
|
+
nil
|
|
72
|
+
elsif Integer(res.code) >= 200 && Integer(res.code) <= 299
|
|
73
|
+
JSON.parse(res.body)
|
|
74
|
+
else
|
|
75
|
+
fail(
|
|
76
|
+
ApiError.new(
|
|
77
|
+
:code => Integer(res.code),
|
|
78
|
+
:response_headers => res.each_header.to_h,
|
|
79
|
+
:response_body => res.body
|
|
80
|
+
)
|
|
81
|
+
)
|
|
82
|
+
end
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
private def execute_request_with_retries(request, http)
|
|
86
|
+
res = http.request(request)
|
|
87
|
+
|
|
88
|
+
[0.05, 0.1, 0.2].each_with_index do |sleep_duration, index|
|
|
89
|
+
# 429 Rate Limit — respect Retry-After header
|
|
90
|
+
if Integer(res.code) == 429
|
|
91
|
+
retry_after = res["Retry-After"]
|
|
92
|
+
delay = retry_after ? retry_after.to_f : sleep_duration
|
|
93
|
+
sleep(delay)
|
|
94
|
+
request["hooksniff-retry-count"] = index + 1
|
|
95
|
+
res = http.request(request)
|
|
96
|
+
next
|
|
97
|
+
end
|
|
98
|
+
|
|
99
|
+
unless Integer(res.code) >= 500
|
|
100
|
+
break
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
sleep(sleep_duration)
|
|
104
|
+
request["hooksniff-retry-count"] = index + 1
|
|
105
|
+
res = http.request(request)
|
|
106
|
+
end
|
|
107
|
+
|
|
108
|
+
res
|
|
109
|
+
end
|
|
110
|
+
|
|
111
|
+
private def encode_query_params(query_params = {})
|
|
112
|
+
encoded_query_pairs = []
|
|
113
|
+
query_params.each do |k, v|
|
|
114
|
+
unless v.nil?
|
|
115
|
+
if v.kind_of?(Array)
|
|
116
|
+
encoded_query_pairs.append("#{k}=" + CGI::escape(v.sort.join(",")))
|
|
117
|
+
elsif v.kind_of?(Time)
|
|
118
|
+
encoded_query_pairs.append("#{k}=#{CGI::escape(v.utc.to_datetime.rfc3339)}")
|
|
119
|
+
else
|
|
120
|
+
encoded_query_pairs.append("#{k}=#{CGI::escape(v)}")
|
|
121
|
+
end
|
|
122
|
+
end
|
|
123
|
+
end
|
|
124
|
+
|
|
125
|
+
encoded_query_pairs.join("&")
|
|
126
|
+
end
|
|
127
|
+
end
|
|
128
|
+
end
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module HookSniff
|
|
4
|
+
class HttpErrorOut
|
|
5
|
+
attr_accessor :code
|
|
6
|
+
|
|
7
|
+
attr_accessor :detail
|
|
8
|
+
|
|
9
|
+
def initialize(attributes = {})
|
|
10
|
+
if (!attributes.is_a?(Hash))
|
|
11
|
+
fail(ArgumentError, "The input argument (attributes) must be a hash in `HookSniff::HttpErrorOut` initialize method")
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
@detail = attributes[:"detail"]
|
|
15
|
+
@code = attributes[:"code"]
|
|
16
|
+
end
|
|
17
|
+
end
|
|
18
|
+
end
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module HookSniff
|
|
4
|
+
class HTTPValidationError
|
|
5
|
+
attr_accessor :detail
|
|
6
|
+
|
|
7
|
+
def initialize(attributes = {})
|
|
8
|
+
if (!attributes.is_a?(Hash))
|
|
9
|
+
fail(
|
|
10
|
+
ArgumentError,
|
|
11
|
+
"The input argument (attributes) must be a hash in `HookSniff::HTTPValidationError` initialize method"
|
|
12
|
+
)
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
@detail = attributes[:"detail"]
|
|
16
|
+
end
|
|
17
|
+
end
|
|
18
|
+
end
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module HookSniff
|
|
4
|
+
class Inbound
|
|
5
|
+
def initialize(client)
|
|
6
|
+
@client = client
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
def list_configs
|
|
10
|
+
@client.request(:get, "/api/v1/inbound/configs")
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
def create_config(body)
|
|
14
|
+
@client.request(:post, "/api/v1/inbound/configs", body: body)
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
def update_config(id, body)
|
|
18
|
+
@client.request(:put, "/api/v1/inbound/configs/#{id}", body: body)
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
def delete_config(id)
|
|
22
|
+
@client.request(:delete, "/api/v1/inbound/configs/#{id}")
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
end
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module HookSniff
|
|
4
|
+
class MessagePoller
|
|
5
|
+
def initialize(client)
|
|
6
|
+
@client = client
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
# Poll for new messages since the consumer's cursor.
|
|
10
|
+
def poll(consumer_id, limit: nil, endpoint_id: nil, event_type: nil, include_payload: true)
|
|
11
|
+
params = { consumer_id: consumer_id, include_payload: include_payload }
|
|
12
|
+
params[:limit] = limit if limit
|
|
13
|
+
params[:endpoint_id] = endpoint_id if endpoint_id
|
|
14
|
+
params[:event_type] = event_type if event_type
|
|
15
|
+
@client.request(:get, "/api/v1/message-poller/poll", params: params)
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
# Seek cursor to a specific message.
|
|
19
|
+
def seek(consumer_id, message_id, endpoint_id: nil)
|
|
20
|
+
body = { consumer_id: consumer_id, message_id: message_id }
|
|
21
|
+
body[:endpoint_id] = endpoint_id if endpoint_id
|
|
22
|
+
@client.request(:post, "/api/v1/message-poller/seek", body: body)
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
# Commit cursor — advance past a processed message.
|
|
26
|
+
def commit(consumer_id, message_id, endpoint_id: nil)
|
|
27
|
+
body = { consumer_id: consumer_id, message_id: message_id }
|
|
28
|
+
body[:endpoint_id] = endpoint_id if endpoint_id
|
|
29
|
+
@client.request(:post, "/api/v1/message-poller/commit", body: body)
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
end
|