Feat: authenticate direct upload (#4160)

This commit is contained in:
Tejaswini Chile
2022-03-16 13:54:18 +05:30
committed by GitHub
parent 796a7805db
commit 207a03155e
12 changed files with 174 additions and 57 deletions

View File

@@ -1,32 +1,6 @@
class Api::V1::Accounts::BaseController < Api::BaseController
include SwitchLocale
include EnsureCurrentAccountHelper
before_action :current_account
around_action :switch_locale_using_account_locale
private
def current_account
@current_account ||= ensure_current_account
Current.account = @current_account
end
def ensure_current_account
account = Account.find(params[:account_id])
if current_user
account_accessible_for_user?(account)
elsif @resource.is_a?(AgentBot)
account_accessible_for_bot?(account)
end
account
end
def account_accessible_for_user?(account)
@current_account_user = account.account_users.find_by(user_id: current_user.id)
Current.account_user = @current_account_user
render_unauthorized('You are not authorized to access this account') unless @current_account_user
end
def account_accessible_for_bot?(account)
render_unauthorized('You are not authorized to access this account') unless @resource.agent_bot_inboxes.find_by(account_id: account.id)
end
end

View File

@@ -1,4 +1,5 @@
class Api::V1::Accounts::Conversations::BaseController < Api::V1::Accounts::BaseController
include EnsureCurrentAccountHelper
before_action :conversation
private

View File

@@ -0,0 +1,17 @@
class Api::V1::Accounts::Conversations::DirectUploadsController < ActiveStorage::DirectUploadsController
include EnsureCurrentAccountHelper
before_action :current_account
before_action :conversation
def create
return if @conversation.nil? || @current_account.nil?
super
end
private
def conversation
@conversation ||= Current.account.conversations.find_by(display_id: params[:conversation_id])
end
end

View File

@@ -1,5 +1,6 @@
class Api::V1::Widget::BaseController < ApplicationController
include SwitchLocale
include WebsiteTokenHelper
before_action :set_web_widget
before_action :set_contact
@@ -19,25 +20,6 @@ class Api::V1::Widget::BaseController < ApplicationController
@conversation ||= conversations.last
end
def auth_token_params
@auth_token_params ||= ::Widget::TokenService.new(token: request.headers['X-Auth-Token']).decode_token
end
def set_web_widget
@web_widget = ::Channel::WebWidget.find_by!(website_token: permitted_params[:website_token])
@current_account = @web_widget.account
end
def set_contact
@contact_inbox = @web_widget.inbox.contact_inboxes.find_by(
source_id: auth_token_params[:source_id]
)
@contact = @contact_inbox&.contact
raise ActiveRecord::RecordNotFound unless @contact
Current.contact = @contact
end
def create_conversation
::Conversation.create!(conversation_params)
end
@@ -96,10 +78,6 @@ class Api::V1::Widget::BaseController < ApplicationController
{ timestamp: permitted_params[:message][:timestamp] }
end
def permitted_params
params.permit(:website_token)
end
def message_params
{
account_id: conversation.account_id,

View File

@@ -0,0 +1,11 @@
class Api::V1::Widget::DirectUploadsController < ActiveStorage::DirectUploadsController
include WebsiteTokenHelper
before_action :set_web_widget
before_action :set_contact
def create
return if @contact.nil? || @current_account.nil?
super
end
end

View File

@@ -0,0 +1,28 @@
module EnsureCurrentAccountHelper
private
def current_account
@current_account ||= ensure_current_account
Current.account = @current_account
end
def ensure_current_account
account = Account.find(params[:account_id])
if current_user
account_accessible_for_user?(account)
elsif @resource.is_a?(AgentBot)
account_accessible_for_bot?(account)
end
account
end
def account_accessible_for_user?(account)
@current_account_user = account.account_users.find_by(user_id: current_user.id)
Current.account_user = @current_account_user
render_unauthorized('You are not authorized to access this account') unless @current_account_user
end
def account_accessible_for_bot?(account)
render_unauthorized('You are not authorized to access this account') unless @resource.agent_bot_inboxes.find_by(account_id: account.id)
end
end

View File

@@ -0,0 +1,22 @@
module WebsiteTokenHelper
def auth_token_params
@auth_token_params ||= ::Widget::TokenService.new(token: request.headers['X-Auth-Token']).decode_token
end
def set_web_widget
@web_widget = ::Channel::WebWidget.find_by!(website_token: permitted_params[:website_token])
@current_account = @web_widget.account
end
def set_contact
@contact_inbox = @web_widget.inbox.contact_inboxes.find_by(
source_id: auth_token_params[:source_id]
)
@contact = @contact_inbox&.contact
raise ActiveRecord::RecordNotFound unless @contact
end
def permitted_params
params.permit(:website_token)
end
end

View File

@@ -645,10 +645,17 @@ export default {
if (checkFileSizeLimit(file, MAXIMUM_FILE_UPLOAD_SIZE)) {
const upload = new DirectUpload(
file.file,
'/rails/active_storage/direct_uploads',
null,
file.file.name
`/api/v1/accounts/${this.accountId}/conversations/${this.currentChat.id}/direct_uploads`,
{
directUploadWillCreateBlobWithXHR: xhr => {
xhr.setRequestHeader(
'api_access_token',
this.currentUser.access_token
);
},
}
);
upload.create((error, blob) => {
if (error) {
this.showAlert(error);

View File

@@ -3,7 +3,7 @@
:size="4096 * 2048"
:accept="allowedFileTypes"
:data="{
direct_upload_url: '/rails/active_storage/direct_uploads',
direct_upload_url: '/api/v1/widget/direct_uploads',
direct_upload: true,
}"
@input-file="onFileUpload"
@@ -66,11 +66,15 @@ export default {
this.isUploading = true;
try {
if (checkFileSizeLimit(file, MAXIMUM_FILE_UPLOAD_SIZE)) {
const { websiteToken } = window.chatwootWebChannel;
const upload = new DirectUpload(
file.file,
'/rails/active_storage/direct_uploads',
null,
file.file.name
`/api/v1/widget/direct_uploads?website_token=${websiteToken}`,
{
directUploadWillCreateBlobWithXHR: xhr => {
xhr.setRequestHeader('X-Auth-Token', window.authToken);
},
}
);
upload.create((error, blob) => {