nahook 0.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.
@@ -0,0 +1,148 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "cgi"
4
+
5
+ module Nahook
6
+ module Resources
7
+ # Resource for managing applications via the Management API.
8
+ #
9
+ # Applications group endpoints for multi-tenant use cases.
10
+ # Each application can have its own set of endpoints and a developer portal.
11
+ #
12
+ # @example
13
+ # mgmt = Nahook::Management.new("nhm_token")
14
+ # mgmt.applications.list("ws_abc123", limit: 10)
15
+ # mgmt.applications.create("ws_abc123", name: "Acme Corp")
16
+ class Applications
17
+ # @api private
18
+ # @param http [Nahook::HttpClient]
19
+ def initialize(http)
20
+ @http = http
21
+ end
22
+
23
+ # List applications in a workspace with optional pagination.
24
+ #
25
+ # @param workspace_id [String] the workspace public ID
26
+ # @param limit [Integer, nil] maximum number of results
27
+ # @param offset [Integer, nil] number of results to skip
28
+ # @return [Hash] response with "data" key containing an array of applications
29
+ def list(workspace_id, limit: nil, offset: nil)
30
+ query = {}
31
+ query["limit"] = limit if limit
32
+ query["offset"] = offset if offset
33
+
34
+ data = @http.request(
35
+ method: :get,
36
+ path: "/management/v1/workspaces/#{e(workspace_id)}/applications",
37
+ query: query.empty? ? nil : query
38
+ )
39
+ { "data" => data }
40
+ end
41
+
42
+ # Create a new application.
43
+ #
44
+ # @param workspace_id [String] the workspace public ID
45
+ # @param name [String] the application name
46
+ # @param external_id [String, nil] an external identifier for your system
47
+ # @param metadata [Hash, nil] arbitrary key-value metadata
48
+ # @return [Hash] the created application
49
+ def create(workspace_id, name:, external_id: nil, metadata: nil)
50
+ body = { "name" => name }
51
+ body["externalId"] = external_id if external_id
52
+ body["metadata"] = metadata if metadata
53
+
54
+ @http.request(
55
+ method: :post,
56
+ path: "/management/v1/workspaces/#{e(workspace_id)}/applications",
57
+ body: body
58
+ )
59
+ end
60
+
61
+ # Get a single application by ID.
62
+ #
63
+ # @param workspace_id [String] the workspace public ID
64
+ # @param id [String] the application public ID
65
+ # @return [Hash] the application
66
+ def get(workspace_id, id)
67
+ @http.request(
68
+ method: :get,
69
+ path: "/management/v1/workspaces/#{e(workspace_id)}/applications/#{e(id)}"
70
+ )
71
+ end
72
+
73
+ # Update an existing application.
74
+ #
75
+ # @param workspace_id [String] the workspace public ID
76
+ # @param id [String] the application public ID
77
+ # @param name [String, nil] updated name
78
+ # @param metadata [Hash, nil] updated metadata
79
+ # @return [Hash] the updated application
80
+ def update(workspace_id, id, name: nil, metadata: nil)
81
+ body = {}
82
+ body["name"] = name unless name.nil?
83
+ body["metadata"] = metadata unless metadata.nil?
84
+
85
+ @http.request(
86
+ method: :patch,
87
+ path: "/management/v1/workspaces/#{e(workspace_id)}/applications/#{e(id)}",
88
+ body: body
89
+ )
90
+ end
91
+
92
+ # Delete an application.
93
+ #
94
+ # @param workspace_id [String] the workspace public ID
95
+ # @param id [String] the application public ID
96
+ # @return [nil]
97
+ def delete(workspace_id, id)
98
+ @http.request(
99
+ method: :delete,
100
+ path: "/management/v1/workspaces/#{e(workspace_id)}/applications/#{e(id)}"
101
+ )
102
+ end
103
+
104
+ # List endpoints belonging to an application.
105
+ #
106
+ # @param workspace_id [String] the workspace public ID
107
+ # @param app_id [String] the application public ID
108
+ # @return [Hash] response with "data" key containing an array of endpoints
109
+ def list_endpoints(workspace_id, app_id)
110
+ data = @http.request(
111
+ method: :get,
112
+ path: "/management/v1/workspaces/#{e(workspace_id)}/applications/#{e(app_id)}/endpoints"
113
+ )
114
+ { "data" => data }
115
+ end
116
+
117
+ # Create an endpoint within an application.
118
+ #
119
+ # @param workspace_id [String] the workspace public ID
120
+ # @param app_id [String] the application public ID
121
+ # @param url [String] the endpoint URL
122
+ # @param type [String, nil] endpoint type ("webhook" or "slack")
123
+ # @param description [String, nil] human-readable description
124
+ # @param metadata [Hash, nil] arbitrary key-value metadata
125
+ # @param config [Hash, nil] endpoint-specific configuration
126
+ # @return [Hash] the created endpoint
127
+ def create_endpoint(workspace_id, app_id, url:, type: nil, description: nil, metadata: nil, config: nil)
128
+ body = { "url" => url }
129
+ body["type"] = type if type
130
+ body["description"] = description if description
131
+ body["metadata"] = metadata if metadata
132
+ body["config"] = config if config
133
+
134
+ @http.request(
135
+ method: :post,
136
+ path: "/management/v1/workspaces/#{e(workspace_id)}/applications/#{e(app_id)}/endpoints",
137
+ body: body
138
+ )
139
+ end
140
+
141
+ private
142
+
143
+ def e(value)
144
+ CGI.escape(value.to_s)
145
+ end
146
+ end
147
+ end
148
+ end
@@ -0,0 +1,114 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "cgi"
4
+
5
+ module Nahook
6
+ module Resources
7
+ # Resource for managing webhook endpoints via the Management API.
8
+ #
9
+ # @example
10
+ # mgmt = Nahook::Management.new("nhm_token")
11
+ # mgmt.endpoints.list("ws_abc123")
12
+ # mgmt.endpoints.create("ws_abc123", url: "https://example.com/webhook")
13
+ class Endpoints
14
+ # @api private
15
+ # @param http [Nahook::HttpClient]
16
+ def initialize(http)
17
+ @http = http
18
+ end
19
+
20
+ # List all endpoints in a workspace.
21
+ #
22
+ # @param workspace_id [String] the workspace public ID
23
+ # @return [Hash] response with "data" key containing an array of endpoints
24
+ def list(workspace_id)
25
+ data = @http.request(
26
+ method: :get,
27
+ path: "/management/v1/workspaces/#{e(workspace_id)}/endpoints"
28
+ )
29
+ { "data" => data }
30
+ end
31
+
32
+ # Create a new endpoint.
33
+ #
34
+ # @param workspace_id [String] the workspace public ID
35
+ # @param url [String] the endpoint URL
36
+ # @param type [String, nil] endpoint type ("webhook" or "slack")
37
+ # @param description [String, nil] human-readable description
38
+ # @param metadata [Hash, nil] arbitrary key-value metadata
39
+ # @param config [Hash, nil] endpoint-specific configuration
40
+ # @param auth_username [String, nil] basic auth username
41
+ # @param auth_password [String, nil] basic auth password
42
+ # @return [Hash] the created endpoint
43
+ def create(workspace_id, url:, type: nil, description: nil, metadata: nil, config: nil,
44
+ auth_username: nil, auth_password: nil)
45
+ body = { "url" => url }
46
+ body["type"] = type if type
47
+ body["description"] = description if description
48
+ body["metadata"] = metadata if metadata
49
+ body["config"] = config if config
50
+ body["authUsername"] = auth_username if auth_username
51
+ body["authPassword"] = auth_password if auth_password
52
+
53
+ @http.request(
54
+ method: :post,
55
+ path: "/management/v1/workspaces/#{e(workspace_id)}/endpoints",
56
+ body: body
57
+ )
58
+ end
59
+
60
+ # Get a single endpoint by ID.
61
+ #
62
+ # @param workspace_id [String] the workspace public ID
63
+ # @param id [String] the endpoint public ID
64
+ # @return [Hash] the endpoint
65
+ def get(workspace_id, id)
66
+ @http.request(
67
+ method: :get,
68
+ path: "/management/v1/workspaces/#{e(workspace_id)}/endpoints/#{e(id)}"
69
+ )
70
+ end
71
+
72
+ # Update an existing endpoint.
73
+ #
74
+ # @param workspace_id [String] the workspace public ID
75
+ # @param id [String] the endpoint public ID
76
+ # @param url [String, nil] updated URL
77
+ # @param description [String, nil] updated description
78
+ # @param metadata [Hash, nil] updated metadata
79
+ # @param is_active [Boolean, nil] whether the endpoint is active
80
+ # @return [Hash] the updated endpoint
81
+ def update(workspace_id, id, url: nil, description: nil, metadata: nil, is_active: nil)
82
+ body = {}
83
+ body["url"] = url unless url.nil?
84
+ body["description"] = description unless description.nil?
85
+ body["metadata"] = metadata unless metadata.nil?
86
+ body["isActive"] = is_active unless is_active.nil?
87
+
88
+ @http.request(
89
+ method: :patch,
90
+ path: "/management/v1/workspaces/#{e(workspace_id)}/endpoints/#{e(id)}",
91
+ body: body
92
+ )
93
+ end
94
+
95
+ # Delete an endpoint.
96
+ #
97
+ # @param workspace_id [String] the workspace public ID
98
+ # @param id [String] the endpoint public ID
99
+ # @return [nil]
100
+ def delete(workspace_id, id)
101
+ @http.request(
102
+ method: :delete,
103
+ path: "/management/v1/workspaces/#{e(workspace_id)}/endpoints/#{e(id)}"
104
+ )
105
+ end
106
+
107
+ private
108
+
109
+ def e(value)
110
+ CGI.escape(value.to_s)
111
+ end
112
+ end
113
+ end
114
+ end
@@ -0,0 +1,121 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "cgi"
4
+
5
+ module Nahook
6
+ module Resources
7
+ # Resource for managing environments via the Management API.
8
+ #
9
+ # @example
10
+ # mgmt = Nahook::Management.new("nhm_token")
11
+ # mgmt.environments.list("ws_abc123")
12
+ # mgmt.environments.create("ws_abc123", name: "Staging", slug: "staging")
13
+ class Environments
14
+ # @api private
15
+ # @param http [Nahook::HttpClient]
16
+ def initialize(http)
17
+ @http = http
18
+ end
19
+
20
+ # List all environments in a workspace.
21
+ #
22
+ # @param workspace_id [String] the workspace public ID
23
+ # @return [Hash] response with "data" key containing an array of environments
24
+ def list(workspace_id)
25
+ data = @http.request(
26
+ method: :get,
27
+ path: "/management/v1/workspaces/#{e(workspace_id)}/environments"
28
+ )
29
+ { "data" => data }
30
+ end
31
+
32
+ # Create a new environment.
33
+ #
34
+ # @param workspace_id [String] the workspace public ID
35
+ # @param name [String] the environment name
36
+ # @param slug [String] the environment slug
37
+ # @return [Hash] the created environment
38
+ def create(workspace_id, name:, slug:)
39
+ @http.request(
40
+ method: :post,
41
+ path: "/management/v1/workspaces/#{e(workspace_id)}/environments",
42
+ body: { "name" => name, "slug" => slug }
43
+ )
44
+ end
45
+
46
+ # Get a single environment by ID.
47
+ #
48
+ # @param workspace_id [String] the workspace public ID
49
+ # @param id [String] the environment ID
50
+ # @return [Hash] the environment
51
+ def get(workspace_id, id)
52
+ @http.request(
53
+ method: :get,
54
+ path: "/management/v1/workspaces/#{e(workspace_id)}/environments/#{e(id)}"
55
+ )
56
+ end
57
+
58
+ # Update an existing environment.
59
+ #
60
+ # @param workspace_id [String] the workspace public ID
61
+ # @param id [String] the environment ID
62
+ # @param name [String, nil] the updated name
63
+ # @return [Hash] the updated environment
64
+ def update(workspace_id, id, name: nil)
65
+ body = {}
66
+ body["name"] = name unless name.nil?
67
+ @http.request(
68
+ method: :patch,
69
+ path: "/management/v1/workspaces/#{e(workspace_id)}/environments/#{e(id)}",
70
+ body: body
71
+ )
72
+ end
73
+
74
+ # Delete an environment.
75
+ #
76
+ # @param workspace_id [String] the workspace public ID
77
+ # @param id [String] the environment ID
78
+ # @return [nil]
79
+ def delete(workspace_id, id)
80
+ @http.request(
81
+ method: :delete,
82
+ path: "/management/v1/workspaces/#{e(workspace_id)}/environments/#{e(id)}"
83
+ )
84
+ end
85
+
86
+ # List event type visibility for an environment.
87
+ #
88
+ # @param workspace_id [String] the workspace public ID
89
+ # @param env_id [String] the environment ID
90
+ # @return [Hash] response with "data" key containing an array of event type visibility entries
91
+ def list_event_type_visibility(workspace_id, env_id)
92
+ data = @http.request(
93
+ method: :get,
94
+ path: "/management/v1/workspaces/#{e(workspace_id)}/environments/#{e(env_id)}/event-types"
95
+ )
96
+ { "data" => data }
97
+ end
98
+
99
+ # Set event type visibility for an environment.
100
+ #
101
+ # @param workspace_id [String] the workspace public ID
102
+ # @param env_id [String] the environment ID
103
+ # @param event_type_id [String] the event type ID
104
+ # @param published [Boolean] whether the event type is published in this environment
105
+ # @return [Hash] the updated visibility entry
106
+ def set_event_type_visibility(workspace_id, env_id, event_type_id, published:)
107
+ @http.request(
108
+ method: :put,
109
+ path: "/management/v1/workspaces/#{e(workspace_id)}/environments/#{e(env_id)}/event-types/#{e(event_type_id)}/visibility",
110
+ body: { "published" => published }
111
+ )
112
+ end
113
+
114
+ private
115
+
116
+ def e(value)
117
+ CGI.escape(value.to_s)
118
+ end
119
+ end
120
+ end
121
+ end
@@ -0,0 +1,97 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "cgi"
4
+
5
+ module Nahook
6
+ module Resources
7
+ # Resource for managing event types via the Management API.
8
+ #
9
+ # @example
10
+ # mgmt = Nahook::Management.new("nhm_token")
11
+ # mgmt.event_types.list("ws_abc123")
12
+ # mgmt.event_types.create("ws_abc123", name: "order.paid")
13
+ class EventTypes
14
+ # @api private
15
+ # @param http [Nahook::HttpClient]
16
+ def initialize(http)
17
+ @http = http
18
+ end
19
+
20
+ # List all event types in a workspace.
21
+ #
22
+ # @param workspace_id [String] the workspace public ID
23
+ # @return [Hash] response with "data" key containing an array of event types
24
+ def list(workspace_id)
25
+ data = @http.request(
26
+ method: :get,
27
+ path: "/management/v1/workspaces/#{e(workspace_id)}/event-types"
28
+ )
29
+ { "data" => data }
30
+ end
31
+
32
+ # Create a new event type.
33
+ #
34
+ # @param workspace_id [String] the workspace public ID
35
+ # @param name [String] the event type name (e.g. "order.paid")
36
+ # @param description [String, nil] human-readable description
37
+ # @return [Hash] the created event type
38
+ def create(workspace_id, name:, description: nil)
39
+ body = { "name" => name }
40
+ body["description"] = description if description
41
+
42
+ @http.request(
43
+ method: :post,
44
+ path: "/management/v1/workspaces/#{e(workspace_id)}/event-types",
45
+ body: body
46
+ )
47
+ end
48
+
49
+ # Get a single event type by ID.
50
+ #
51
+ # @param workspace_id [String] the workspace public ID
52
+ # @param id [String] the event type public ID
53
+ # @return [Hash] the event type
54
+ def get(workspace_id, id)
55
+ @http.request(
56
+ method: :get,
57
+ path: "/management/v1/workspaces/#{e(workspace_id)}/event-types/#{e(id)}"
58
+ )
59
+ end
60
+
61
+ # Update an existing event type.
62
+ #
63
+ # @param workspace_id [String] the workspace public ID
64
+ # @param id [String] the event type public ID
65
+ # @param description [String, nil] updated description
66
+ # @return [Hash] the updated event type
67
+ def update(workspace_id, id, description: nil)
68
+ body = {}
69
+ body["description"] = description unless description.nil?
70
+
71
+ @http.request(
72
+ method: :patch,
73
+ path: "/management/v1/workspaces/#{e(workspace_id)}/event-types/#{e(id)}",
74
+ body: body
75
+ )
76
+ end
77
+
78
+ # Delete an event type.
79
+ #
80
+ # @param workspace_id [String] the workspace public ID
81
+ # @param id [String] the event type public ID
82
+ # @return [nil]
83
+ def delete(workspace_id, id)
84
+ @http.request(
85
+ method: :delete,
86
+ path: "/management/v1/workspaces/#{e(workspace_id)}/event-types/#{e(id)}"
87
+ )
88
+ end
89
+
90
+ private
91
+
92
+ def e(value)
93
+ CGI.escape(value.to_s)
94
+ end
95
+ end
96
+ end
97
+ end
@@ -0,0 +1,47 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "cgi"
4
+
5
+ module Nahook
6
+ module Resources
7
+ # Resource for creating developer portal sessions via the Management API.
8
+ #
9
+ # Portal sessions generate short-lived URLs that grant your customers
10
+ # access to a self-service endpoint management portal.
11
+ #
12
+ # @example
13
+ # mgmt = Nahook::Management.new("nhm_token")
14
+ # session = mgmt.portal_sessions.create("ws_abc123", "app_def456")
15
+ # puts session["url"] # => "https://portal.nahook.com/..."
16
+ class PortalSessions
17
+ # @api private
18
+ # @param http [Nahook::HttpClient]
19
+ def initialize(http)
20
+ @http = http
21
+ end
22
+
23
+ # Create a portal session for an application.
24
+ #
25
+ # @param workspace_id [String] the workspace public ID
26
+ # @param app_id [String] the application public ID
27
+ # @param metadata [Hash, nil] optional metadata for the session
28
+ # @return [Hash] session with "url", "code", and "expiresAt" keys
29
+ def create(workspace_id, app_id, metadata: nil)
30
+ body = {}
31
+ body["metadata"] = metadata if metadata
32
+
33
+ @http.request(
34
+ method: :post,
35
+ path: "/management/v1/workspaces/#{e(workspace_id)}/applications/#{e(app_id)}/portal",
36
+ body: body
37
+ )
38
+ end
39
+
40
+ private
41
+
42
+ def e(value)
43
+ CGI.escape(value.to_s)
44
+ end
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,70 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "cgi"
4
+
5
+ module Nahook
6
+ module Resources
7
+ # Resource for managing endpoint subscriptions via the Management API.
8
+ #
9
+ # Subscriptions link event types to endpoints, controlling which
10
+ # events are delivered to which endpoint.
11
+ #
12
+ # @example
13
+ # mgmt = Nahook::Management.new("nhm_token")
14
+ # mgmt.subscriptions.list("ws_abc123", "ep_def456")
15
+ # mgmt.subscriptions.create("ws_abc123", "ep_def456", event_type_ids: ["evt_ghi789"])
16
+ class Subscriptions
17
+ # @api private
18
+ # @param http [Nahook::HttpClient]
19
+ def initialize(http)
20
+ @http = http
21
+ end
22
+
23
+ # List subscriptions for an endpoint.
24
+ #
25
+ # @param workspace_id [String] the workspace public ID
26
+ # @param endpoint_id [String] the endpoint public ID
27
+ # @return [Hash] response with "data" key containing an array of subscriptions
28
+ def list(workspace_id, endpoint_id)
29
+ data = @http.request(
30
+ method: :get,
31
+ path: "/management/v1/workspaces/#{e(workspace_id)}/endpoints/#{e(endpoint_id)}/subscriptions"
32
+ )
33
+ { "data" => data }
34
+ end
35
+
36
+ # Subscribe an endpoint to one or more event types.
37
+ #
38
+ # @param workspace_id [String] the workspace public ID
39
+ # @param endpoint_id [String] the endpoint public ID
40
+ # @param event_type_ids [Array<String>] event type public IDs to subscribe to
41
+ # @return [Hash] response with "subscribed" count
42
+ def create(workspace_id, endpoint_id, event_type_ids:)
43
+ @http.request(
44
+ method: :post,
45
+ path: "/management/v1/workspaces/#{e(workspace_id)}/endpoints/#{e(endpoint_id)}/subscriptions",
46
+ body: { "eventTypeIds" => Array(event_type_ids) }
47
+ )
48
+ end
49
+
50
+ # Delete a subscription.
51
+ #
52
+ # @param workspace_id [String] the workspace public ID
53
+ # @param endpoint_id [String] the endpoint public ID
54
+ # @param event_type_id [String] the event type public ID to unsubscribe
55
+ # @return [nil]
56
+ def delete(workspace_id, endpoint_id, event_type_id)
57
+ @http.request(
58
+ method: :delete,
59
+ path: "/management/v1/workspaces/#{e(workspace_id)}/endpoints/#{e(endpoint_id)}/subscriptions/#{e(event_type_id)}"
60
+ )
61
+ end
62
+
63
+ private
64
+
65
+ def e(value)
66
+ CGI.escape(value.to_s)
67
+ end
68
+ end
69
+ end
70
+ end
@@ -0,0 +1,5 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Nahook
4
+ VERSION = "0.1.0"
5
+ end
data/lib/nahook.rb ADDED
@@ -0,0 +1,29 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "nahook/version"
4
+ require_relative "nahook/errors"
5
+ require_relative "nahook/http_client"
6
+ require_relative "nahook/client"
7
+ require_relative "nahook/management"
8
+ require_relative "nahook/resources/endpoints"
9
+ require_relative "nahook/resources/event_types"
10
+ require_relative "nahook/resources/applications"
11
+ require_relative "nahook/resources/subscriptions"
12
+ require_relative "nahook/resources/portal_sessions"
13
+ require_relative "nahook/resources/environments"
14
+
15
+ # Official Ruby SDK for the Nahook webhook platform.
16
+ #
17
+ # Nahook provides two main entry points:
18
+ #
19
+ # - {Nahook::Client} for sending webhook payloads (ingestion API)
20
+ # - {Nahook::Management} for managing resources (management API)
21
+ #
22
+ # @example Sending a webhook
23
+ # client = Nahook::Client.new("nhk_us_your_api_key")
24
+ # client.send("ep_abc123", payload: { order_id: "12345" })
25
+ #
26
+ # @example Managing endpoints
27
+ # mgmt = Nahook::Management.new("nhm_your_token")
28
+ # mgmt.endpoints.list("ws_abc123")
29
+ module Nahook; end