فهرست منبع

Add initial user control mutations

Andrew Swistak 5 سال پیش
والد
کامیت
e8a1fe797d

+ 81 - 0
app/graphql/mutations/concerns/controller_methods.rb

@@ -0,0 +1,81 @@
+# frozen_string_literal: true
+
+module ControllerMethods
+  extend ActiveSupport::Concern
+
+  private
+
+  def raise_user_error(message)
+    # raise GraphqlDevise::UserError, message
+    raise message
+  end
+
+  def raise_user_error_list(message, errors:)
+    # raise GraphqlDevise::DetailedUserError.new(message, errors: errors)
+    raise message
+  end
+
+  def remove_resource
+    controller.resource = nil
+    controller.client_id = nil
+    controller.token = nil
+  end
+
+  def request
+    controller.request
+  end
+
+  def response
+    controller.response
+  end
+
+  def controller
+    context[:controller]
+  end
+
+  def resource_name
+    self.class.instance_variable_get(:@resource_name)
+  end
+
+  def resource_class
+    controller.send(:resource_class, resource_name)
+  end
+
+  def recoverable_enabled?
+    resource_class.devise_modules.include?(:recoverable)
+  end
+
+  def confirmable_enabled?
+    resource_class.devise_modules.include?(:confirmable)
+  end
+
+  def blacklisted_redirect_url?(redirect_url)
+    DeviseTokenAuth.redirect_whitelist && !DeviseTokenAuth::Url.whitelisted?(redirect_url)
+  end
+
+  def current_resource
+    @current_resource ||= controller.send(:set_user_by_token, resource_name)
+  end
+
+  def client
+    controller.token.client if controller.token.present?
+  end
+
+  def set_auth_headers(resource)
+    auth_headers = resource.create_new_auth_token
+    response.headers.merge!(auth_headers)
+  end
+
+  def client_and_token(token)
+    {client_id: token.client, token: token.token}
+  end
+
+  def redirect_headers(token_info, redirect_header_options)
+    controller.send(
+      :build_redirect_headers,
+      token_info.fetch(:token),
+      token_info.fetch(:client_id),
+      redirect_header_options,
+    )
+  end
+end

+ 23 - 25
app/graphql/mutations/user/confirm_account.rb

@@ -1,38 +1,36 @@
 # frozen_string_literal: true
 
 module Mutations
-  module User
-    class ConfirmAccount < Mutations::BaseMutation
-      # include ::ControllerMethods
+  class User::ConfirmAccount < Mutations::BaseMutation
+    include ControllerMethods
 
-      field :user, Types::UserType, null: true
+    field :user, Types::UserType, null: true
 
-      argument :confirmation_token, String, required: true
-      argument :redirect_url, String, required: true
+    argument :confirmation_token, String, required: true
+    argument :redirect_url, String, required: true
 
-      def resolve(confirmation_token:, redirect_url:)
-        user = User.confirm_by_token(confirmation_token)
+    def resolve(confirmation_token:, redirect_url:)
+      user = User.confirm_by_token(confirmation_token)
 
-        if user.errors.empty?
-          redirect_header_options = {account_confirmation_success: true}
+      if user.errors.empty?
+        redirect_header_options = {account_confirmation_success: true}
 
-          redirect_to_link = if controller.signed_in?(resource_name)
-            signed_in_resource.build_auth_url(
-              redirect_url,
-              redirect_headers(
-                client_and_token(controller.signed_in_resource.create_token),
-                redirect_header_options,
-              ),
-            )
-          else
-            DeviseTokenAuth::Url.generate(redirect_url, redirect_header_options)
-          end
-
-          controller.redirect_to(redirect_to_link)
-          {user: user}
+        redirect_to_link = if controller.signed_in?(resource_name)
+          signed_in_resource.build_auth_url(
+            redirect_url,
+            redirect_headers(
+              client_and_token(controller.signed_in_resource.create_token),
+              redirect_header_options,
+            ),
+          )
         else
-          raise_user_error('invalid confirmation token')
+          DeviseTokenAuth::Url.generate(redirect_url, redirect_header_options)
         end
+
+        controller.redirect_to(redirect_to_link)
+        {user: user}
+      else
+        raise_user_error('invalid confirmation token')
       end
     end
   end

+ 31 - 34
app/graphql/mutations/user/login.rb

@@ -1,54 +1,51 @@
 # frozen_string_literal: true
 
 module Mutations
-  module User
-    class Login < Mutations::BaseMutation
-      # include ::ControllerMethods
+  class User::Login < Mutations::BaseMutation
+    include ControllerMethods
 
-      field :user, Types::UserType, null: false
+    field :user, Types::UserType, null: false
 
-      argument :login, String, required: true
-      argument :password, String, required: true
+    argument :login, String, required: true
+    argument :password, String, required: true
 
-      def resolve(login:, password:)
-        user = User.find_for_database_authentication(login: login)
+    def resolve(login:, password:)
+      user = ::User.find_for_database_authentication(login: login)
 
-        if user && active_for_authentication?(user)
-          if invalid_for_authentication?(user, password)
-            raise_user_error('bad credentials')
-          end
+      if user # && active_for_authentication?(user)
+        raise_user_error('bad credentials') unless user.authenticate(password)
 
-          set_auth_headers(user)
-          controller.sign_in(:user, user, store: false, bypass: false)
+        # set_auth_headers(user)
+        context[:controller].login(user)
+        # controller.sign_in(:user, user, store: false, bypass: false)
 
-          {user: user}
-        elsif user && !active_for_authentication?(user)
-          if locked?(user)
-            raise_user_error('account locked')
-          else
-            raise_user_error('account not confirmed', email: user.email)
-          end
+        {user: user}
+      elsif user && !active_for_authentication?(user)
+        if locked?(user)
+          raise_user_error('account locked')
         else
-          raise_user_error('bad credentials given')
+          raise_user_error('account not confirmed', email: user.email)
         end
+      else
+        raise_user_error('bad credentials given')
       end
+    end
 
-      private
+    private
 
-      def invalid_for_authentication?(user, password)
-        valid_password = user.valid_password?(password)
+    def invalid_for_authentication?(user, password)
+      valid_password = user.valid_password?(password)
 
-        (user.respond_to?(:valid_for_authentication?) && !user.valid_for_authentication? { valid_password }) ||
-          !valid_password
-      end
+      (user.respond_to?(:valid_for_authentication?) && !user.valid_for_authentication? { valid_password }) ||
+        !valid_password
+    end
 
-      def active_for_authentication?(user)
-        !user.respond_to?(:active_for_authentication?) || user.active_for_authentication?
-      end
+    def active_for_authentication?(user)
+      !user.respond_to?(:active_for_authentication?) || user.active_for_authentication?
+    end
 
-      def locked?(user)
-        user.respond_to?(:locked_at) && user.locked_at
-      end
+    def locked?(user)
+      user.respond_to?(:locked_at) && user.locked_at
     end
   end
 end

+ 5 - 19
app/graphql/mutations/user/logout.rb

@@ -1,26 +1,12 @@
 # frozen_string_literal: true
 
 module Mutations
-  module User
-    class Logout < Mutations::BaseMutation
-      # include ::ControllerMethods
+  class User::Logout < Mutations::BaseMutation
+    field :success, Boolean, null: false
 
-      field :user, Types::UserType, null: false
-
-      def resolve
-        if current_user && client && current_user.tokens[client]
-          current_user.tokens.delete(client)
-          current_user.save!
-
-          remove_user
-
-          yield user if block_given?
-
-          {user: current_user}
-        else
-          raise_user_error('user not found')
-        end
-      end
+    def resolve(*)
+      context[:controller].logout
+      {success: true}
     end
   end
 end

+ 41 - 43
app/graphql/mutations/user/sign_up.rb

@@ -1,60 +1,58 @@
 # frozen_string_literal: true
 
 module Mutations
-  module User
-    class SignUp < Mutations::BaseMutation
-      # include ::ControllerMethods
+  class User::SignUp < Mutations::BaseMutation
+    include ControllerMethods
 
-      argument :username, String, required: true
-      argument :email, String, required: true
-      argument :password, String, required: true
-      argument :password_confirmation, String, required: true
-      argument :confirm_success_url, String, required: false
+    argument :username, String, required: true
+    argument :email, String, required: true
+    argument :password, String, required: true
+    argument :password_confirmation, String, required: true
+    argument :confirm_success_url, String, required: false
 
-      field :user, Types::UserType, null: false
+    field :user, Types::UserType, null: false
 
-      def resolve(confirm_success_url: nil, **attrs)
-        user = ::User.new(provider: :email, **attrs)
-        raise_user_error('failed to create user') if user.blank?
+    def resolve(confirm_success_url: nil, **attrs)
+      user = ::User.new(provider: :email, **attrs)
+      raise_user_error('failed to create user') if user.blank?
 
-        redirect_url = confirm_success_url \
-          || DeviseTokenAuth.default_confirm_success_url
+      redirect_url = confirm_success_url \
+        || DeviseTokenAuth.default_confirm_success_url
 
-        if blacklisted_redirect_url?(redirect_url)
-          raise_user_error('redirect url is not allowed')
-        end
+      if blacklisted_redirect_url?(redirect_url)
+        raise_user_error('redirect url is not allowed')
+      end
+
+      # user.skip_confirmation_notification!
 
-        # user.skip_confirmation_notification!
-
-        if user.save
-          unless user.confirmed?
-            # user.send_confirmation_instructions(
-            #  redirect_url: confirm_success_url,
-            #  template_path: ['mailer/user'],
-            # )
-          end
-
-          set_auth_headers(user) if user.active_for_authentication?
-
-          {user: user}
-        else
-          # clean_up_passwords(user)
-          raise_user_error_list(
-            'registration failed',
-            errors: user.errors.full_messages,
-          )
+      if user.save
+        unless user.confirmed?
+          # user.send_confirmation_instructions(
+          #  redirect_url: confirm_success_url,
+          #  template_path: ['mailer/user'],
+          # )
         end
-      end
 
-      private
+        set_auth_headers(user) if user.active_for_authentication?
 
-      def provider
-        :email
+        {user: user}
+      else
+        # clean_up_passwords(user)
+        raise_user_error_list(
+          'registration failed',
+          errors: user.errors.full_messages,
+        )
       end
+    end
 
-      def clean_up_passwords(user)
-        # controller.send(:clean_up_passwords, user)
-      end
+    private
+
+    def provider
+      :email
+    end
+
+    def clean_up_passwords(user)
+      # controller.send(:clean_up_passwords, user)
     end
   end
 end