Permalink
Browse files

Normalize errors format, avoid duplicating sessions

  • Loading branch information...
1 parent 79892dd commit 9ad8e0d64ba796be247b41340f71757a87113fc5 @chischaschos committed Feb 21, 2014
View
@@ -32,7 +32,7 @@ class Application < Sinatra::Base
else
status 404
- { errors: user.errors.to_hash }.to_json
+ user.h_errors.to_json
end
end
@@ -51,7 +51,7 @@ class Application < Sinatra::Base
else
status 404
- { errors: session.errors.to_hash }.to_json
+ session.h_errors.to_json
end
end
@@ -70,7 +70,7 @@ class Application < Sinatra::Base
else
status 404
- { errors: session.errors.to_hash }.to_json
+ session.h_errors.to_json
end
end
@@ -79,7 +79,7 @@ class Application < Sinatra::Base
session = Models::Session.first(access_token: request.cookies[:access_token])
if !session && session && !session.destroy
status 404
- { errors: session.errors.to_hash }.to_json
+ session.h_errors.to_json
end
end
@@ -9,10 +9,16 @@ class Session
belongs_to :user, 'Todo::Models::User', key: true
+ validates_uniqueness_of :user
+
before :create do |session|
session.access_token = SecureRandom.uuid
end
+ def h_errors
+ { errors: self.errors.to_hash }
+ end
+
end
end
end
View
@@ -18,6 +18,11 @@ class User
def to_json
{ id: self.id }.to_json
end
+
+ def h_errors
+ { errors: self.errors.to_hash }
+ end
+
end
end
@@ -2,37 +2,38 @@ module Todo
module Services
class SessionCreator
+ attr_reader :h_errors, :access_token
+
def initialize(params)
@params = params
@result = nil
+ @h_errors = { errors: {} }
end
def valid?
- !!user
- end
-
- def access_token
- user && !@session && create_session
- @access_token
- end
+ if user
+ create_session
+ else
+ @h_errors.merge!({ default: 'email or password invalid' })
+ end
- def errors
- { password: 'email or password invalid' }
+ @h_errors[:errors].empty?
end
private
def user
@user ||= Todo::Models::User.first(email: @params[:email],
- password: @params[:password])
+ password: @params[:password])
end
def create_session
@session = Models::Session.create user: @user
+
if @session.saved?
@access_token = @session.access_token
else
- fail 'Session could not be created'
+ @h_errors.merge!(@session.h_errors)
end
end
View
@@ -1,33 +1,55 @@
require 'spec_helper'
describe 'Sessions API', api: true do
-
- it 'should allow a client to create a user session' do
- params = { email: 'test@test.com', password: '123test123' }
- user = Todo::Models::User.create params
-
- post '/api/session', { user: params }
-
- expect(last_response.headers['Content-Type']).to eq 'application/json;charset=utf-8'
- expect(last_response.headers['Set-Cookie']).to match /access_token=#{user.session.access_token}/
- expect(last_response.body).to eq ''
- expect(last_response.status).to eq 200
+ let(:params) { { email: 'test@test.com', password: '123test123' } }
+
+ let!(:user) { Todo::Models::User.create params }
+
+ context 'when creating sessions' do
+ context 'when a session does not exists yet' do
+ it 'should allow a client to create a user session' do
+ post '/api/session', { user: params }
+
+ expect(last_response.headers['Content-Type']).to eq 'application/json;charset=utf-8'
+ expect(last_response.headers['Set-Cookie']).to match /access_token=#{user.session.access_token}/
+ expect(last_response.body).to eq ''
+ expect(last_response.status).to eq 200
+ end
+ end
+
+ context 'when a session already exists' do
+ before do
+ session_creator = Todo::Services::SessionCreator.new(params)
+ expect(session_creator.valid?).to be_true
+ end
+
+ it 'should not allow a client to create a session' do
+ post '/api/session', { user: params }
+
+ expect(last_response.headers['Content-Type']).to eq 'application/json;charset=utf-8'
+ expect(last_response.headers['Set-Cookie']).to be_nil
+ expect(last_response.body).to have_json_path 'errors/user'
+ expect(last_response.status).to eq 404
+ end
+ end
end
- it 'should allow a client to destroy a user session' do
- params = { email: 'test@test.com', password: '123test123' }
- Todo::Models::User.create params
- session = Todo::Services::SessionCreator.new(params)
- expect(session.valid?).to be_true
+ context 'when destroying sessions' do
+ context 'when a session already exists' do
+ let!(:session) { Todo::Services::SessionCreator.new(params) }
- set_cookie "access_token=#{session.access_token}"
+ it 'should allow a client to destroy a user session' do
+ expect(session.valid?).to be_true
- delete "/api/session"
+ set_cookie "access_token=#{session.access_token}"
- expect(last_response.headers['Content-Type']).to eq 'application/json;charset=utf-8'
- expect(last_response.headers['Set-Cookie']).to be_nil
- expect(last_response.body).to eq ''
- expect(last_response.status).to eq 200
+ delete "/api/session"
+ expect(last_response.headers['Content-Type']).to eq 'application/json;charset=utf-8'
+ expect(last_response.headers['Set-Cookie']).to be_nil
+ expect(last_response.body).to eq ''
+ expect(last_response.status).to eq 200
+ end
+ end
end
end
View
@@ -2,8 +2,8 @@
describe 'Users API', api: true do
- context 'when 200 response' do
- it 'should success creating a user' do
+ context 'when creating users' do
+ it 'should create a user with email and password' do
expect(Todo::Models::User.count).to eq 0
params = { user: { email: 'test@test.com', password: '123test123' } }
@@ -16,10 +16,8 @@
expect(last_response.status).to eq 200
expect(Todo::Models::User.count).to eq 1
end
- end
- context 'when 404 response' do
- it 'should fail because of empty password' do
+ it 'should fail if missing password' do
expect(Todo::Models::User.count).to eq 0
params = { user: { email: 'test@test.com' } }
@@ -30,5 +28,6 @@
expect(last_response.status).to eq 404
expect(Todo::Models::User.count).to eq 0
end
+
end
end
@@ -2,13 +2,31 @@
describe Todo::Services::SessionCreator do
- it 'successfully creates a session for an existing user' do
- params = { email: 'test@test.com', password: '123test123' }
- user = Todo::Models::User.create! params
- session_creator = Todo::Services::SessionCreator.new params
- expect(session_creator.valid?).to be_true
- expect(session_creator.access_token).not_to be_nil
- expect(session_creator.errors).not_to be_nil
+ let(:params) { { email: 'test@test.com', password: '123test123' } }
+
+ context 'when a session does not exists yet' do
+ before { Todo::Models::User.create params }
+
+ it 'should create a session' do
+ session_creator = Todo::Services::SessionCreator.new params
+ expect(session_creator.valid?).to be_true
+ expect(session_creator.access_token).not_to be_nil
+ expect(session_creator.h_errors[:errors]).to be_empty
+ end
end
+ context 'when a session already exists' do
+ before do
+ Todo::Models::User.create(params)
+ session_creator = Todo::Services::SessionCreator.new(params)
+ expect(session_creator.valid?).to be_true
+ end
+
+ it 'should not create a session' do
+ session_creator = Todo::Services::SessionCreator.new params
+ expect(session_creator.valid?).not_to be_true
+ expect(session_creator.access_token).to be_nil
+ expect(session_creator.h_errors[:errors]).not_to be_empty
+ end
+ end
end

0 comments on commit 9ad8e0d

Please sign in to comment.