271 lines
9.4 KiB
Ruby
271 lines
9.4 KiB
Ruby
# frozen_string_literal: true
|
|
|
|
describe 'Api::V1::Profiles' do
|
|
include_context 'bearer authentication'
|
|
let!(:create_member_permission) do
|
|
create :permission,
|
|
role: 'member'
|
|
end
|
|
describe 'GET /api/v2/resource/users/me' do
|
|
it 'should reply permissions denied' do
|
|
get '/api/v2/resource/users/me'
|
|
expect_body.to eq(errors: ["jwt.decode_and_verify"])
|
|
expect(response.status).to eq(401)
|
|
end
|
|
|
|
it 'should allow traffic with Authorization' do
|
|
get '/api/v2/resource/users/me', headers: auth_header
|
|
expect(json_body[:email]).to eq(test_user.email)
|
|
expect(response.status).to eq(200)
|
|
end
|
|
end
|
|
|
|
let(:valid_otp_code) { '1357' }
|
|
let(:invalid_otp_code) { '1234' }
|
|
|
|
before do
|
|
allow(TOTPService).to receive(:validate?)
|
|
.with(test_user.uid, valid_otp_code) { true }
|
|
allow(TOTPService).to receive(:validate?)
|
|
.with(test_user.uid, invalid_otp_code) { false }
|
|
end
|
|
|
|
describe 'PUT /api/v2/resource/users/me' do
|
|
let(:correct_data) { { bar: 'baz' }.to_json }
|
|
let(:incorrect_data) { 'random string' }
|
|
|
|
it 'changes user data field' do
|
|
put '/api/v2/resource/users/me', headers: auth_header, params: {
|
|
data: correct_data
|
|
}
|
|
expect(test_user.reload.data).to eq(correct_data)
|
|
expect(response.status).to eq 200
|
|
end
|
|
|
|
it 'receives invalid data error' do
|
|
put '/api/v2/resource/users/me', headers: auth_header, params: {
|
|
data: incorrect_data
|
|
}
|
|
|
|
expect(response.status).to eq 422
|
|
expect_body.to eq errors: ['data.invalid_format']
|
|
end
|
|
end
|
|
|
|
describe 'DELETE /api/v2/resource/users/me' do
|
|
it 'receives invalid password error' do
|
|
delete '/api/v2/resource/users/me', headers: auth_header, params: {
|
|
password: 'WrongPassword'
|
|
}
|
|
|
|
expect(response.status).to eq 422
|
|
expect(test_user.reload.state).to eq 'active'
|
|
expect_body.to eq errors: ['resource.user.invalid_password']
|
|
end
|
|
|
|
it 'receives otp missing error if 2fa is enabled and param is missing' do
|
|
test_user.update(otp: true)
|
|
delete '/api/v2/resource/users/me', headers: auth_header, params: {
|
|
password: 'Tecohvi0'
|
|
}
|
|
|
|
expect(response.status).to eq 422
|
|
expect(test_user.reload.state).to eq 'active'
|
|
expect_body.to eq errors: ['resource.user.missing_otp_code']
|
|
end
|
|
|
|
it 'receives otp empty error if 2fa is enabled and param is empty' do
|
|
test_user.update(otp: true)
|
|
delete '/api/v2/resource/users/me', headers: auth_header, params: {
|
|
password: 'Tecohvi0',
|
|
otp_code: ''
|
|
}
|
|
|
|
expect(response.status).to eq 422
|
|
expect(test_user.reload.state).to eq 'active'
|
|
expect_body.to eq errors: ['resource.user.empty_otp_code']
|
|
end
|
|
|
|
it 'receives invalid otp error with wrong otp code' do
|
|
test_user.update(otp: true)
|
|
delete '/api/v2/resource/users/me', headers: auth_header, params: {
|
|
password: 'Tecohvi0',
|
|
otp_code: invalid_otp_code
|
|
}
|
|
|
|
expect(response.status).to eq 422
|
|
expect(test_user.reload.state).to eq 'active'
|
|
expect_body.to eq errors: ['resource.user.invalid_otp']
|
|
end
|
|
|
|
it 'marks user as deleted with turned on 2fa and valid otp' do
|
|
test_user.update(otp: true)
|
|
delete '/api/v2/resource/users/me', headers: auth_header, params: {
|
|
password: 'Tecohvi0',
|
|
otp_code: valid_otp_code
|
|
}
|
|
|
|
expect(response.status).to eq 200
|
|
expect(test_user.reload.state).to eq 'deleted'
|
|
end
|
|
|
|
it 'marks user as deleted with turned off 2fa' do
|
|
delete '/api/v2/resource/users/me', headers: auth_header, params: {
|
|
password: 'Tecohvi0'
|
|
}
|
|
|
|
expect(response.status).to eq 200
|
|
expect(test_user.reload.state).to eq 'deleted'
|
|
end
|
|
end
|
|
|
|
describe 'POST /api/v2/resource/otp/disable' do
|
|
it 'with dasbled 2fa' do
|
|
post '/api/v2/resource/otp/disable', headers: auth_header, params: { code: valid_otp_code }
|
|
expect_body.to eq errors: ['resource.otp.not_enabled']
|
|
end
|
|
|
|
it 'with invalid code' do
|
|
test_user.update(otp: true)
|
|
post '/api/v2/resource/otp/disable', headers: auth_header, params: { code: invalid_otp_code }
|
|
expect_body.to eq errors: ['resource.otp.invalid']
|
|
end
|
|
|
|
it 'disables 2fa' do
|
|
test_user.update(otp: true)
|
|
expect {
|
|
post '/api/v2/resource/otp/disable', headers: auth_header, params: { code: valid_otp_code }
|
|
}.to change { test_user.reload.otp }.from(true).to(false)
|
|
|
|
expect(response.status).to eq 200
|
|
end
|
|
end
|
|
|
|
describe 'POST /api/v2/resource/users/activity' do
|
|
it 'allows only [password, otp, session, all] as a topic parameter' do
|
|
get '/api/v2/resource/users/activity/invalid', headers: auth_header
|
|
expect(response.status).to eq(422)
|
|
expect_body.to eq(errors: ['resource.user.wrong_topic'])
|
|
get '/api/v2/resource/users/activity/session', headers: auth_header
|
|
expect(response.status).to eq(422)
|
|
expect_body.to eq(errors: ['resource.user.no_activity'])
|
|
end
|
|
it 'sorts user activities' do
|
|
4.times { create(:activity, user: test_user) }
|
|
get '/api/v2/resource/users/activity/all', headers: auth_header
|
|
activities = JSON.parse(response.body)
|
|
expect(activities.first['id']).to be >= activities.last['id']
|
|
end
|
|
it 'sorts user activities by result' do
|
|
4.times { create(:activity, user: test_user, result: 'succeed') }
|
|
get '/api/v2/resource/users/activity/all', params: { result: 'succeed' }, headers: auth_header
|
|
activities = JSON.parse(response.body)
|
|
expect(activities.length).to eq(4)
|
|
end
|
|
it 'sorts user activities by time range' do
|
|
4.times { create(:activity, user: test_user, result: 'succeed') }
|
|
get '/api/v2/resource/users/activity/all', params: { time_from: 5.hours.ago.to_i, time_to: 1.hours.ago.to_i }, headers: auth_header
|
|
activities = JSON.parse(response.body)
|
|
expect(activities.length).to eq(1)
|
|
end
|
|
|
|
it 'sorts user activities by time range' do
|
|
4.times { create(:activity, user: test_user, result: 'succeed') }
|
|
4.times { create(:activity, user: test_user, result: 'succeed', created_at: 10.hours.ago) }
|
|
|
|
get '/api/v2/resource/users/activity/all', params: { time_from: 5.hours.ago.to_i}, headers: auth_header
|
|
activities = JSON.parse(response.body)
|
|
expect(activities.length).to eq(4)
|
|
end
|
|
end
|
|
|
|
describe 'POST /api/v2/resource/users/password' do
|
|
let(:do_request) do
|
|
put '/api/v2/resource/users/password', params: params, headers: auth_header
|
|
end
|
|
let(:do_confirm_request) do
|
|
post '/api/v2/resource/users/confirm_password', params: { code: otp_code }, headers: auth_header
|
|
end
|
|
let(:params) do
|
|
{
|
|
old_password: old_password,
|
|
new_password: new_password,
|
|
confirm_password: confirm_password
|
|
}
|
|
end
|
|
let(:old_password) { '' }
|
|
let(:new_password) { '' }
|
|
let(:confirm_password) { '' }
|
|
context 'when params are blank' do
|
|
it 'renders 400 error' do
|
|
do_request
|
|
expect(response.status).to eq(422)
|
|
expect_body.to eq(errors: ["resource.user.empty_old_password", "resource.user.empty_new_password", "resource.user.empty_confirm_password"])
|
|
end
|
|
end
|
|
context 'when old password is not right' do
|
|
let(:old_password) { 'invalid' }
|
|
let(:new_password) { 'Gol4aid2' }
|
|
let(:confirm_password) { 'Gol4aid2' }
|
|
it 'renders 400 error' do
|
|
do_request
|
|
expect(response.status).to eq(400)
|
|
expect_body.to eq(errors: ["resource.password.prev_pass_not_correct"])
|
|
end
|
|
end
|
|
context 'when new pass and confirmation are different' do
|
|
let(:old_password) { 'Tecohvi0' } # 'Tecohvi0' - test_user password
|
|
let(:new_password) { 'Gol4aid1' }
|
|
let(:confirm_password) { 'Gol4aid2' }
|
|
it 'renders 422 error' do
|
|
do_request
|
|
expect(response.status).to eq(422)
|
|
expect_body.to eq(errors: ["resource.password.doesnt_match"])
|
|
end
|
|
end
|
|
context 'when params are valid, passwords are weak' do
|
|
let(:old_password) { 'Tecohvi0' } # 'Tecohvi0' - test_user password
|
|
let(:new_password) { 'Simple' }
|
|
let(:confirm_password) { 'Simple' }
|
|
it 'returns weak password error' do
|
|
do_request
|
|
expect_status_to_eq 422
|
|
expect_body.to eq(errors: ["temp_password.requirements"])
|
|
end
|
|
end
|
|
|
|
context 'when params are valid, confirm code not valid' do
|
|
let(:old_password) { 'Tecohvi0' } # 'Tecohvi0' - test_user password
|
|
let(:new_password) { 'Gol4aid1' }
|
|
let(:confirm_password) { 'Gol4aid1' }
|
|
let(:otp_code) { invalid_otp_code }
|
|
let(:log_in) { post '/api/v2/identity/sessions', params: { email: test_user.email, password: new_password } }
|
|
it 'changes a password' do
|
|
do_request
|
|
do_confirm_request
|
|
expect_status_to_eq 422
|
|
expect_body.to eq(errors: ["resource.password.confirm_code_not_match"])
|
|
end
|
|
end
|
|
|
|
context 'when params are valid' do
|
|
let(:old_password) { 'Tecohvi0' } # 'Tecohvi0' - test_user password
|
|
let(:new_password) { 'Gol4aid1' }
|
|
let(:confirm_password) { 'Gol4aid1' }
|
|
let(:otp_code) { valid_otp_code }
|
|
let(:log_in) { post '/api/v2/identity/sessions', params: { email: test_user.email, password: new_password } }
|
|
it 'changes a password' do
|
|
do_request
|
|
expect(response.status).to eq(201)
|
|
|
|
do_confirm_request
|
|
expect(response.status).to eq(201)
|
|
|
|
log_in
|
|
expect(response.status).to eq(200)
|
|
end
|
|
end
|
|
end
|
|
end
|
|
|