phcdevworks_accounts_stytch 0.1.0.pre.1 → 0.2.0.pre.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (44) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +43 -4
  3. data/app/controllers/concerns/error_handler.rb +19 -0
  4. data/app/controllers/concerns/handle_service_action.rb +17 -0
  5. data/app/controllers/concerns/organization_setter.rb +11 -0
  6. data/app/controllers/phcdevworks_accounts_stytch/b2b/authenticate_controller.rb +81 -0
  7. data/app/controllers/phcdevworks_accounts_stytch/b2b/magic_links_controller.rb +57 -0
  8. data/app/controllers/phcdevworks_accounts_stytch/b2b/passwords_controller.rb +95 -0
  9. data/app/controllers/phcdevworks_accounts_stytch/b2c/authenticate_controller.rb +99 -0
  10. data/app/controllers/phcdevworks_accounts_stytch/b2c/magic_links_controller.rb +90 -0
  11. data/app/controllers/phcdevworks_accounts_stytch/b2c/passwords_controller.rb +94 -0
  12. data/app/views/layouts/phcdevworks_accounts_stytch/application.html.erb +2 -0
  13. data/app/views/phcdevworks_accounts_stytch/b2b/magic_links/invite.html.erb +12 -0
  14. data/app/views/phcdevworks_accounts_stytch/b2b/magic_links/login_or_signup.html.erb +12 -0
  15. data/app/views/phcdevworks_accounts_stytch/b2b/passwords/reset_existing_password.html.erb +22 -0
  16. data/app/views/phcdevworks_accounts_stytch/b2b/passwords/reset_password.html.erb +17 -0
  17. data/app/views/phcdevworks_accounts_stytch/b2b/passwords/reset_start.html.erb +12 -0
  18. data/app/views/phcdevworks_accounts_stytch/b2b/passwords/reset_with_session.html.erb +17 -0
  19. data/app/views/phcdevworks_accounts_stytch/b2c/magic_links/invite.html.erb +12 -0
  20. data/app/views/phcdevworks_accounts_stytch/b2c/magic_links/login_or_signup.html.erb +12 -0
  21. data/app/views/phcdevworks_accounts_stytch/b2c/passwords/reset_existing_password.html.erb +22 -0
  22. data/app/views/phcdevworks_accounts_stytch/b2c/passwords/reset_password.html.erb +17 -0
  23. data/app/views/phcdevworks_accounts_stytch/b2c/passwords/reset_start.html.erb +12 -0
  24. data/app/views/phcdevworks_accounts_stytch/b2c/passwords/reset_with_session.html.erb +17 -0
  25. data/config/routes/b2b.rb +30 -0
  26. data/config/routes/b2c.rb +27 -0
  27. data/config/routes.rb +2 -4
  28. data/lib/phcdevworks_accounts_stytch/authentication/b2b/magic_link_service.rb +63 -0
  29. data/lib/phcdevworks_accounts_stytch/authentication/b2b/password_service.rb +80 -0
  30. data/lib/phcdevworks_accounts_stytch/authentication/b2c/magic_link_service.rb +55 -0
  31. data/lib/phcdevworks_accounts_stytch/authentication/b2c/password_service.rb +76 -0
  32. data/lib/phcdevworks_accounts_stytch/engine.rb +6 -0
  33. data/lib/phcdevworks_accounts_stytch/stytch/client.rb +45 -0
  34. data/lib/phcdevworks_accounts_stytch/stytch/error.rb +26 -0
  35. data/lib/phcdevworks_accounts_stytch/stytch/method_options.rb +21 -0
  36. data/lib/phcdevworks_accounts_stytch/stytch/organization.rb +51 -0
  37. data/lib/phcdevworks_accounts_stytch/stytch/response.rb +44 -0
  38. data/lib/phcdevworks_accounts_stytch/stytch/success.rb +19 -0
  39. data/lib/phcdevworks_accounts_stytch/version.rb +1 -1
  40. data/lib/phcdevworks_accounts_stytch.rb +3 -4
  41. metadata +37 -13
  42. data/app/controllers/phcdevworks_accounts_stytch/authentication/login_controller.rb +0 -26
  43. data/app/controllers/phcdevworks_accounts_stytch/authentication/processor_controller.rb +0 -36
  44. data/lib/phcdevworks_accounts_stytch/stytch_client.rb +0 -10
@@ -0,0 +1,51 @@
1
+ # frozen_string_literal: true
2
+
3
+ module PhcdevworksAccountsStytch
4
+ module Stytch
5
+ class Organization
6
+ def initialize
7
+ @client = PhcdevworksAccountsStytch::Stytch::Client.b2b_client
8
+ end
9
+
10
+ def find_organization_id_by_slug(slug)
11
+ response = search_organization_by_slug(slug)
12
+ extract_organization_id(response, slug)
13
+ rescue StandardError => e
14
+ handle_error(e)
15
+ end
16
+
17
+ private
18
+
19
+ def search_organization_by_slug(slug)
20
+ @client.organizations.search(
21
+ query: {
22
+ operator: 'OR',
23
+ operands: [
24
+ { filter_name: 'organization_slugs', filter_value: [slug] }
25
+ ]
26
+ }
27
+ )
28
+ end
29
+
30
+ def extract_organization_id(response, slug)
31
+ organizations = response['organizations']
32
+ if organizations&.any?
33
+ organization = organizations.first
34
+ organization['organization_id']
35
+ else
36
+ raise PhcdevworksAccountsStytch::Stytch::Error.new(
37
+ status_code: 404,
38
+ error_message: "Organization with slug '#{slug}' not found"
39
+ )
40
+ end
41
+ end
42
+
43
+ def handle_error(error)
44
+ raise PhcdevworksAccountsStytch::Stytch::Error.new(
45
+ status_code: error.respond_to?(:status_code) ? error.status_code : 500,
46
+ error_message: error.message
47
+ )
48
+ end
49
+ end
50
+ end
51
+ end
@@ -0,0 +1,44 @@
1
+ # frozen_string_literal: true
2
+
3
+ module PhcdevworksAccountsStytch
4
+ module Stytch
5
+ module Response
6
+ def self.handle_response(response)
7
+ response = response.is_a?(Hash) ? response : JSON.parse(response)
8
+
9
+ status_code = response['status_code'] || 500
10
+
11
+ if success_status?(status_code)
12
+ build_success_response(status_code, response)
13
+ else
14
+ build_error_response(response, status_code)
15
+ end
16
+ end
17
+
18
+ def self.success_status?(status_code)
19
+ status_code.between?(200, 299)
20
+ end
21
+
22
+ def self.build_success_response(status_code, response)
23
+ PhcdevworksAccountsStytch::Stytch::Success.new(
24
+ status_code: status_code,
25
+ message: "Successfully processed request with status code #{status_code}.",
26
+ data: response
27
+ )
28
+ end
29
+
30
+ def self.build_error_response(response, status_code)
31
+ error_code = response['error_type'] || 'unknown_error'
32
+ error_message = response['error_message'] || 'An unknown error occurred'
33
+
34
+ Rails.logger.error "Stytch API error: #{response.inspect}"
35
+
36
+ raise PhcdevworksAccountsStytch::Stytch::Error.new(
37
+ status_code: status_code,
38
+ error_code: error_code,
39
+ error_message: error_message
40
+ )
41
+ end
42
+ end
43
+ end
44
+ end
@@ -0,0 +1,19 @@
1
+ # frozen_string_literal: true
2
+
3
+ module PhcdevworksAccountsStytch
4
+ module Stytch
5
+ class Success
6
+ attr_reader :status_code, :message, :data
7
+
8
+ def initialize(status_code:, message: 'Action completed successfully.', data: {})
9
+ @status_code = status_code
10
+ @message = message
11
+ @data = data
12
+ end
13
+
14
+ def success?
15
+ true
16
+ end
17
+ end
18
+ end
19
+ end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module PhcdevworksAccountsStytch
4
- VERSION = '0.1.0.pre.1'
4
+ VERSION = '0.2.0.pre.1'
5
5
  end
@@ -1,10 +1,9 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'phcdevworks_accounts_stytch/version'
3
+ require 'stytch'
4
4
  require 'phcdevworks_accounts_stytch/engine'
5
+ require 'phcdevworks_accounts_stytch/version'
6
+ require 'phcdevworks_accounts_stytch/stytch/client'
5
7
 
6
- # PhcdevworksAccountsStytch
7
- # This module serves as the namespace for the PhcdevworksAccountsStytch engine.
8
8
  module PhcdevworksAccountsStytch
9
- # Your code goes here...
10
9
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: phcdevworks_accounts_stytch
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0.pre.1
4
+ version: 0.2.0.pre.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - PHCDevworks
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2024-07-15 00:00:00.000000000 Z
12
+ date: 2024-09-16 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: rails
@@ -17,20 +17,14 @@ dependencies:
17
17
  requirements:
18
18
  - - "~>"
19
19
  - !ruby/object:Gem::Version
20
- version: '7.1'
21
- - - ">="
22
- - !ruby/object:Gem::Version
23
- version: 7.1.3.4
20
+ version: '7.2'
24
21
  type: :runtime
25
22
  prerelease: false
26
23
  version_requirements: !ruby/object:Gem::Requirement
27
24
  requirements:
28
25
  - - "~>"
29
26
  - !ruby/object:Gem::Version
30
- version: '7.1'
31
- - - ">="
32
- - !ruby/object:Gem::Version
33
- version: 7.1.3.4
27
+ version: '7.2'
34
28
  - !ruby/object:Gem::Dependency
35
29
  name: stytch
36
30
  requirement: !ruby/object:Gem::Requirement
@@ -58,18 +52,48 @@ files:
58
52
  - Rakefile
59
53
  - app/assets/config/phcdevworks_accounts_stytch_manifest.js
60
54
  - app/assets/stylesheets/phcdevworks_accounts_stytch/application.css
55
+ - app/controllers/concerns/error_handler.rb
56
+ - app/controllers/concerns/handle_service_action.rb
57
+ - app/controllers/concerns/organization_setter.rb
61
58
  - app/controllers/phcdevworks_accounts_stytch/application_controller.rb
62
- - app/controllers/phcdevworks_accounts_stytch/authentication/login_controller.rb
63
- - app/controllers/phcdevworks_accounts_stytch/authentication/processor_controller.rb
59
+ - app/controllers/phcdevworks_accounts_stytch/b2b/authenticate_controller.rb
60
+ - app/controllers/phcdevworks_accounts_stytch/b2b/magic_links_controller.rb
61
+ - app/controllers/phcdevworks_accounts_stytch/b2b/passwords_controller.rb
62
+ - app/controllers/phcdevworks_accounts_stytch/b2c/authenticate_controller.rb
63
+ - app/controllers/phcdevworks_accounts_stytch/b2c/magic_links_controller.rb
64
+ - app/controllers/phcdevworks_accounts_stytch/b2c/passwords_controller.rb
64
65
  - app/helpers/phcdevworks_accounts_stytch/application_helper.rb
65
66
  - app/jobs/phcdevworks_accounts_stytch/application_job.rb
66
67
  - app/mailers/phcdevworks_accounts_stytch/application_mailer.rb
67
68
  - app/models/phcdevworks_accounts_stytch/application_record.rb
68
69
  - app/views/layouts/phcdevworks_accounts_stytch/application.html.erb
70
+ - app/views/phcdevworks_accounts_stytch/b2b/magic_links/invite.html.erb
71
+ - app/views/phcdevworks_accounts_stytch/b2b/magic_links/login_or_signup.html.erb
72
+ - app/views/phcdevworks_accounts_stytch/b2b/passwords/reset_existing_password.html.erb
73
+ - app/views/phcdevworks_accounts_stytch/b2b/passwords/reset_password.html.erb
74
+ - app/views/phcdevworks_accounts_stytch/b2b/passwords/reset_start.html.erb
75
+ - app/views/phcdevworks_accounts_stytch/b2b/passwords/reset_with_session.html.erb
76
+ - app/views/phcdevworks_accounts_stytch/b2c/magic_links/invite.html.erb
77
+ - app/views/phcdevworks_accounts_stytch/b2c/magic_links/login_or_signup.html.erb
78
+ - app/views/phcdevworks_accounts_stytch/b2c/passwords/reset_existing_password.html.erb
79
+ - app/views/phcdevworks_accounts_stytch/b2c/passwords/reset_password.html.erb
80
+ - app/views/phcdevworks_accounts_stytch/b2c/passwords/reset_start.html.erb
81
+ - app/views/phcdevworks_accounts_stytch/b2c/passwords/reset_with_session.html.erb
69
82
  - config/routes.rb
83
+ - config/routes/b2b.rb
84
+ - config/routes/b2c.rb
70
85
  - lib/phcdevworks_accounts_stytch.rb
86
+ - lib/phcdevworks_accounts_stytch/authentication/b2b/magic_link_service.rb
87
+ - lib/phcdevworks_accounts_stytch/authentication/b2b/password_service.rb
88
+ - lib/phcdevworks_accounts_stytch/authentication/b2c/magic_link_service.rb
89
+ - lib/phcdevworks_accounts_stytch/authentication/b2c/password_service.rb
71
90
  - lib/phcdevworks_accounts_stytch/engine.rb
72
- - lib/phcdevworks_accounts_stytch/stytch_client.rb
91
+ - lib/phcdevworks_accounts_stytch/stytch/client.rb
92
+ - lib/phcdevworks_accounts_stytch/stytch/error.rb
93
+ - lib/phcdevworks_accounts_stytch/stytch/method_options.rb
94
+ - lib/phcdevworks_accounts_stytch/stytch/organization.rb
95
+ - lib/phcdevworks_accounts_stytch/stytch/response.rb
96
+ - lib/phcdevworks_accounts_stytch/stytch/success.rb
73
97
  - lib/phcdevworks_accounts_stytch/version.rb
74
98
  - lib/tasks/phcdevworks_accounts_stytch_tasks.rake
75
99
  homepage: https://phcdevworks.com/
@@ -1,26 +0,0 @@
1
- # app/controllers/phcdevworks_accounts_stytch/authentication/login_controller.rb
2
- # frozen_string_literal: true
3
-
4
- require 'phcdevworks_accounts_stytch/stytch_client'
5
-
6
- module PhcdevworksAccountsStytch
7
- module Authentication
8
- class LoginController < ApplicationController
9
- include StytchClient
10
-
11
- def create
12
- email = params[:email]
13
- response = send_magic_link(email)
14
- render json: response
15
- rescue StandardError => e
16
- render json: { error: e.message }, status: :internal_server_error
17
- end
18
-
19
- private
20
-
21
- def send_magic_link(email)
22
- stytch_client.magic_links.email.discovery.send(email_address: email)
23
- end
24
- end
25
- end
26
- end
@@ -1,36 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module PhcdevworksAccountsStytch
4
- module Authentication
5
- class ProcessorController < ApplicationController
6
- include StytchClient
7
-
8
- def create
9
- token = params[:token]
10
- response = authenticate_token(token)
11
- render_success(response)
12
- rescue StandardError => e
13
- render_error(e)
14
- end
15
-
16
- private
17
-
18
- def authenticate_token(token)
19
- stytch_client.magic_links.discovery.authenticate(discovery_magic_links_token: token)
20
- end
21
-
22
- def render_success(response)
23
- render plain: success_message(response)
24
- end
25
-
26
- def render_error(error)
27
- render plain: error.message, status: :unauthorized
28
- end
29
-
30
- def success_message(response)
31
- "Hello, #{response.email_address}! Complete the Discovery flow by creating an " \
32
- "Organization with your intermediate session token: #{response.intermediate_session_token}."
33
- end
34
- end
35
- end
36
- end
@@ -1,10 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module StytchClient
4
- def stytch_client
5
- @stytch_client ||= StytchB2B::Client.new(
6
- project_id: StytchClientConfig.project_id,
7
- secret: StytchClientConfig.secret
8
- )
9
- end
10
- end