• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

mgmodell / devise_token_auth_multi_email / #1601

07 Apr 2026 01:47PM UTC coverage: 83.553% (-7.0%) from 90.564%
#1601

push

web-flow
Merge pull request #10 from mgmodell/copilot/fix-unique-violation-error

Fix RecordNotUnique crashing tests and add standard/multi-email model test separation

22 of 25 new or added lines in 3 files covered. (88.0%)

141 existing lines in 8 files now uncovered.

1016 of 1216 relevant lines covered (83.55%)

379.15 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

43.9
/app/controllers/devise_token_auth/unlocks_controller.rb
1
# frozen_string_literal: true
2

3
module DeviseTokenAuth
1✔
4
  class UnlocksController < DeviseTokenAuth::ApplicationController
1✔
5
    skip_after_action :update_auth_header, only: [:create, :show]
1✔
6

7
    # this action is responsible for generating unlock tokens and
8
    # sending emails
9
    def create
1✔
10
      return render_create_error_missing_email unless resource_params[:email]
21✔
11

12
      @email = get_case_insensitive_field_from_resource_params(:email)
19✔
13
      @resource = find_resource(:email, @email)
19✔
14

UNCOV
15
      if @resource
×
UNCOV
16
        yield @resource if block_given?
×
17

UNCOV
18
        @resource.send_unlock_instructions(
×
19
          email: @email,
20
          provider: 'email',
21
          client_config: params[:config_name]
22
        )
23

UNCOV
24
        if @resource.errors.empty?
×
UNCOV
25
          return render_create_success
×
26
        else
27
          render_create_error @resource.errors
×
28
        end
29
      else
UNCOV
30
        render_not_found_error
×
31
      end
32
    end
33

34
    def show
1✔
UNCOV
35
      @resource = resource_class.unlock_access_by_token(params[:unlock_token])
×
36

UNCOV
37
      if @resource.persisted?
×
UNCOV
38
        token = @resource.create_token
×
UNCOV
39
        @resource.save!
×
UNCOV
40
        yield @resource if block_given?
×
41

UNCOV
42
        redirect_header_options = { unlock: true }
×
UNCOV
43
        redirect_headers = build_redirect_headers(token.token,
×
44
                                                  token.client,
45
                                                  redirect_header_options)
UNCOV
46
        redirect_to(@resource.build_auth_url(after_unlock_path_for(@resource),
×
47
                                             redirect_headers),
48
                                             redirect_options)
49
      else
UNCOV
50
        render_show_error
×
51
      end
52
    end
53

54
    private
1✔
55
    def after_unlock_path_for(resource)
1✔
56
      #TODO: This should probably be a configuration option at the very least.
UNCOV
57
      '/'
×
58
    end
59

60
    def render_create_error_missing_email
1✔
61
      render_error(401, I18n.t('devise_token_auth.unlocks.missing_email'))
2✔
62
    end
63

64
    def render_create_success
1✔
UNCOV
65
      render json: {
×
66
        success: true,
67
        message: success_message('unlocks', @email)
68
      }
69
    end
70

71
    def render_create_error(errors)
1✔
72
      render json: {
×
73
        success: false,
74
        errors: errors
75
      }, status: 400
76
    end
77

78
    def render_show_error
1✔
UNCOV
79
      raise ActionController::RoutingError, 'Not Found'
×
80
    end
81

82
    def render_not_found_error
1✔
UNCOV
83
      if Devise.paranoid
×
UNCOV
84
        render_create_success
×
85
      else
UNCOV
86
        render_error(404, I18n.t('devise_token_auth.unlocks.user_not_found', email: @email))
×
87
      end
88
    end
89

90
    def resource_params
1✔
91
      params.permit(:email, :unlock_token, :config)
40✔
92
    end
93
  end
94
end
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc