Skip to content

Commit c58a43b

Browse files
committed
Merge pull request #280 from cerebris/transaction_fix
Add Internal Server Error support with rollback
2 parents 7080f7b + 724541b commit c58a43b

6 files changed

Lines changed: 68 additions & 1 deletion

File tree

lib/jsonapi/active_record_operations_processor.rb

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,5 +24,13 @@ def process_operation(operation)
2424
rescue ActiveRecord::RecordNotFound
2525
record_not_found = JSONAPI::Exceptions::RecordNotFound.new(operation.associated_key)
2626
return JSONAPI::ErrorsOperationResult.new(record_not_found.errors[0].code, record_not_found.errors)
27+
28+
rescue JSONAPI::Exceptions::Error => e
29+
raise e
30+
31+
rescue => e
32+
internal_server_error = JSONAPI::Exceptions::InternalServerError.new(e)
33+
Rails.logger.error { "Internal Server Error: #{e.message} #{e.backtrace.join("\n")}" }
34+
return JSONAPI::ErrorsOperationResult.new(internal_server_error.errors[0].code, internal_server_error.errors)
2735
end
2836
end

lib/jsonapi/error_codes.rb

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ module JSONAPI
2424
RECORD_NOT_FOUND = 404
2525
UNSUPPORTED_MEDIA_TYPE = 415
2626
LOCKED = 423
27+
INTERNAL_SERVER_ERROR = 500
2728

2829
TEXT_ERRORS =
2930
{ VALIDATION_ERROR => 'VALIDATION_ERROR',
@@ -50,6 +51,7 @@ module JSONAPI
5051
FORBIDDEN => 'FORBIDDEN',
5152
RECORD_NOT_FOUND => 'RECORD_NOT_FOUND',
5253
UNSUPPORTED_MEDIA_TYPE => 'UNSUPPORTED_MEDIA_TYPE',
53-
LOCKED => 'LOCKED'
54+
LOCKED => 'LOCKED',
55+
INTERNAL_SERVER_ERROR => 'INTERNAL_SERVER_ERROR'
5456
}
5557
end

lib/jsonapi/exceptions.rb

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,22 @@ module JSONAPI
22
module Exceptions
33
class Error < RuntimeError; end
44

5+
class InternalServerError < Error
6+
attr_accessor :exception
7+
8+
def initialize(exception)
9+
@exception = exception
10+
end
11+
12+
def errors
13+
[JSONAPI::Error.new(code: JSONAPI::INTERNAL_SERVER_ERROR,
14+
status: 500,
15+
title: 'Internal Server Error',
16+
detail: 'Internal Server Error')]
17+
end
18+
19+
end
20+
521
class InvalidResource < Error
622
attr_accessor :resource
723
def initialize(resource)

lib/jsonapi/operations_processor.rb

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,18 @@ def rollback
8282

8383
def process_operation(operation)
8484
operation.apply
85+
86+
rescue JSONAPI::Exceptions::Error => e
87+
# :nocov:
88+
raise e
89+
# :nocov:
90+
91+
rescue => e
92+
# :nocov:
93+
internal_server_error = JSONAPI::Exceptions::InternalServerError.new(e)
94+
Rails.logger.error { "Internal Server Error: #{e.message} #{e.backtrace.join("\n")}" }
95+
return JSONAPI::ErrorsOperationResult.new(internal_server_error.errors[0].code, internal_server_error.errors)
96+
# :nocov:
8597
end
8698
end
8799
end

test/controllers/controller_test.rb

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -631,6 +631,28 @@ def test_update_with_links
631631
json_response['data']['relationships']['tags']['data'])
632632
end
633633

634+
def test_update_with_internal_server_error
635+
set_content_type_header!
636+
post_object = Post.find(3)
637+
title = post_object.title
638+
639+
put :update,
640+
{
641+
id: 3,
642+
data: {
643+
id: '3',
644+
type: 'posts',
645+
attributes: {
646+
title: 'BOOM'
647+
}
648+
}
649+
}
650+
651+
assert_response 500
652+
post_object = Post.find(3)
653+
assert_equal title, post_object.title
654+
end
655+
634656
def test_update_remove_links
635657
set_content_type_header!
636658
put :update,

test/fixtures/active_record.rb

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -611,6 +611,13 @@ def subject
611611
@model.title
612612
end
613613

614+
def title=(title)
615+
@model.title = title
616+
if title == 'BOOM'
617+
raise 'The Server just tested going boom. If this was a real emergency you would be really dead right now.'
618+
end
619+
end
620+
614621
filters :title, :author, :tags, :comments
615622
filters :id, :ids
616623

0 commit comments

Comments
 (0)